Perl Global符号需要显式包名称

时间:2013-05-01 16:07:12

标签: perl strict

我正在尝试将日志消息存储在散列中,具体取决于消息类型,如下所示:

#!/usr/bin/perl

use strict;
use warnings;

my %log;

opendir (DIR, '.') or die $!;
while (my $file = readdir(DIR)) {
    # some code to select TAR filename in $1
    if (-e $1.'.tar') {
        push(@{$log->{$1}}, $file); /* line 12 */
    }
    else {
        $log{$1} = [];
        push(@{$log->{$1}}, $file); /* line 16 */
}

现在这段代码给出了编译错误:

Global symbol "$log" requires explicit package name at at lines 12 & 16

我实际上在尝试使用散列“%log”。有什么方法可以摆脱这个错误?为什么会发生这种情况?

我确实看到了一些关于上下文的解释,其中人们回答说变量是在一个上下文中创建的,并且在另一个上下文中被引用但我觉得这个变量应该在这段代码中的循环中可用。只有当我使用“严格”并且工作正常时才会发生这种情况。

我已经开始使用Perl,所以我不完全了解基础知识!请帮助我理解为什么无法访问此变量。

2 个答案:

答案 0 :(得分:10)

my %log;

定义散列%log,但第12行和第16行不使用它。相反,您正在访问由您从未声明的标量$log引用的匿名哈希。你有两个选择。

  • 您可以继续使用匿名哈希。

    my $log = {};   # The creation of the hash ("{}") is currently being done
                    # implicitly by "->". This is called autovivification.
    
    
    ... $log->{...} ...
    

    这增加了一些额外的复杂性和不明显的速度降低。

  • 您可以直接使用哈希。

    my %log;
    
    ... $log{...} ...
    

答案 1 :(得分:9)

我不确定你要用$1做什么,但是哈希访问不是引用,所以改变:

$log->{$1}

$log{$1}

您收到的错误消息是:Global symbol "$log" requires explicit package,因为未定义$log变量。请记住,%log$log是两个不同的变量(哈希与标量)。