如果您要问如何获得对类型 glob 的引用,那就是:
my $ref = \*symbol_name_here;
对于符号的“字面名称”(即您输入符号的确切名称的位置),而不是变量。但是,您可以这样做:
my $ref = Symbol::qualify_to_ref( $symbol_name );
用于变量符号。但是,上面的方法适用于strict,而下面的更简单的方法则不能:
my $ref = \*{$symbol_name};
Symbol::qualify* 的优点之一是它将包名作为第二个变量处理。所以...
my $sref = Symbol::qualify_to_ref( $symbol_name, $some_other_package );
与\*{$some_other_package.'::'.$symbol_name} 做同样的事情,它适用于strict。
一旦你有了符号 ref,为了得到这个槽,你必须尊重这个引用,所以 perl 不认为你想把它用作一个哈希,就像这样。
my $href = *{ $sref }{HASH};
my $code = *{ $sref }{CODE};
my $arref = *{ $sref }{ARRAY};
my $io = *{ $sref }{IO};
另一个拍摄
我以不同的方式将你的两个想法放在一起。如果你有一个符号表引用,你可以获得HASH 槽,这是一个引用,就像任何其他对哈希的引用一样。因此,您可以执行以下操作。
要么
*hash{HASH}->{key}
或者
${ *hash{HASH} }{key}
会起作用。不过这些更安全
( *hash{HASH} || {} )->{key};
${ *hash{HASH} || {} }{key};
如果您不想使用直接条目,而是使用对表的引用来执行此操作,您可以执行以下操作:
my $ref = \*hash;
my $value = *{ $ref }{HASH} && *{ $ref }{HASH}->{key};
注意: %hash 绝对需要是一个包变量。只有包变量驻留在符号表中(因此只有 subs 和 @ISA 和 Exporter 变量往往位于现代符号表中)。词法变量(声明为my)驻留在"pad" 中。
更新:
-
我已经不再使用Symbol 了。奇怪的是,即使它是 核心,它似乎 非标准 以 Perlers 的方式 - 并且 看到 - 事情。相反,我在我所谓的“无块”中使用直接方式,尽可能本地化它们。
# All I want is one symbol.
# Turn strict-refs off, get it, turn it back on.
my $symb = do { no strict 'refs'; \*{$symbol_name} };
或
{ no strict 'refs';
*{$package_name.'::'.$symbol_name} = $sub_I_created;
... # more reckless symbol table mucking...
}
-
我几乎总是使用 *STDERR{IO} 成语作为 glob 文件句柄引用。在现代 Perl 中,这些通常是对象。
my $fh = *STDERR{IO};
say blessed( $fh ); # IO::File
$fh->say( 'Some stuff' );