Как я могу использовать переменную в качестве имени модуля в Perl? - PullRequest
15 голосов
/ 15 апреля 2010

Я знаю, что можно использовать переменную в качестве имени переменной для переменных пакета в Perl. Я хотел бы использовать содержимое переменной в качестве имени модуля. Например:

package Foo;
our @names =("blah1", "blah2");
1;

И в другом файле я хочу иметь возможность установить содержимое скаляра на «foo», а затем получить доступ к массиву имен в Foo через этот скаляр.

my $packageName = "Foo";

По сути, я хочу сделать что-то вроде:

@{$packageName}::names; #This obviously doesn't work.

Я знаю, что могу использовать

my $names = eval '$'. $packageName . "::names" 

Но только если Foo::names - скаляр. Есть ли другой способ сделать это без оператора eval?

Ответы [ 2 ]

14 голосов
/ 16 апреля 2010

Чтобы получить переменные пакета в пакете $package, вы можете использовать символические ссылки:

no strict 'refs';
my $package = 'Foo';

# grab @Foo::names
my @names = @{ $package . '::names' }

Лучший способ, который избегает символьных ссылок, состоит в том, чтобы выставить метод в Foo, который будет возвращать массив. Это работает, потому что оператор вызова метода (->) может принять строку в качестве инвоканта.

package Foo;

our @names = ( ... );
sub get_names { 
    return @names;
}

package main;
use strict;

my $package = 'Foo';
my @names = $package->get_names;
4 голосов
/ 15 апреля 2010

Строгая проверка не позволяет использовать переменную (или буквальную строку) в качестве части имени, но это можно отключить локально:

my @values;
{
    no strict 'refs';
    @values = @{"Mypackage"}::var;
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...