Perl try / catch块在Error.pm中抛出错误

时间:2011-09-16 01:56:56

标签: perl exception-handling

我在写的Perl脚本中有以下代码:

#!/usr/bin/perl
use DBI;
use Getopt::Long;
use Time::HiRes;
use Error qw(:try);

....

my $starttime = Time::HiRes::time;

try {
    my $dbh = DBI->connect("dbi:Sybase:$server", $username, $password);
    $dbh->do("use $database");
    my $query="exec OfflineDatabaseReport";

    $row = $dbh->selectrow_hashref($query);

    $dbh->disconnect();
} catch Error with {
    print "boom";
    exit 1;
};
my $endtime = Time::HiRes::time;
my $timetaken = $endtime - $starttime;

脚本工作正常,直到我将数据访问部分包装在try...catch块中。现在我抛出了以下异常:

  

在/usr/lib/perl5/site_perl/5.8.8/Error.pm第217行使用“strict refs”时,不能使用字符串(“1316135985.90893”)作为HASH引用。

我确实尝试过设置:

no strict "refs";

但我仍然得到同样的错误。我在这里使用try/catch块时是否天真?

1 个答案:

答案 0 :(得分:3)

这是解析器查看代码的方式:

try({ ... }, catch(Error, with({ ... }, my $endtime = Time::HiRes::time)));

意思是,它将$endtime设置为Time::HiRes::time的结果作为with BLOCK sub的第二个参数传递。看一下Error.pm的来源,我看到了:

sub with (&;$) {
    @_
}

这意味着with BLOCK,SCALAR是一个有效的参数列表。它所做的就是将参数传递到catch,将my $endtime = Time::HiRes::time解释为$clausescatch本身返回$clauses,将整个语句转换为:

try({ ... }, my $endtime = Time::HiRes::time);

try假设$clauses是一个hashref,您可以通过调用

看到
$clauses->{'finally'}->()
    if(defined($clauses->{'finally'}));

因此perl尝试使用Time::HiRes::time的值作为hashref,但它肯定不能,因为它实际上是一个值为“1316135985.90893”的标量。

所以是的,catch区块末尾的分号。