目前,在调试过程中,我倾向于插入
carp Dumper \@foo, \%bar;
语句到我的代码中,并经常遇到Carp
和Data::Dumper
未在当前包中导入的问题。为了避免这个问题,我在一个总是包含的中心文件中定义了以下子:
sub main::bla {
use Carp; use Data::Dumper;
carp Dumper @_;
}
所以现在我可以做到
main::bla \@foo, \%bar;
无处不在,但main::
让我烦恼。有没有类似全局软件包的东西总是在任何软件包中自动导入(就像内置插件几乎被导入到各处)?
答案 0 :(得分:4)
你可以称之为
::bla( \@foo, \%bar );
在早些时候,我曾经将util函数放在Ut
包中。这很好,但我注意到我的代码并不像我想象的那样模块化。依赖于Ut
函数的每个模块只有在有人麻烦地构建该命名空间时才能成功。
最后,我将use
和require
语句视为仅记录依赖项。有更灵活的方法来更改库模块调用的代码,而不是在main中更改它们的实现。
例如,您可以在单个use
语句中执行此操作。
use Ut blah => sub {
use Carp;
use Data::Dumper;
carp Dumper @_;
};
并定义导入:
sub import {
shift; # It's just me
my ( $name, $impl ) = @_;
if ( $name eq 'blah' && ref( $impl ) eq 'CODE' ) {
*blah = $_[1];
}
...
}
当我一次开发大量代码时,我仍然使用ut
模式。但我不介意写作
ut:dump_var( $var )
而不是保存3-4个字符(因为有时我称之为U::
)。
现在,您似乎不想长期这样做,并且转储变量对于开发来说是一件有用的事情。如果你真的想这样做,Smart::Comments
会这样做:
### @foo
### %bar
所需要的只是一个使用声明。
use Smart::Comments;
答案 1 :(得分:1)
也许只是更好地制作另一个包含导出和需要的东西? 比如,MyTest.pm:
package MyTest;
use strict;
use Carp;
use Data::Dumper;
use base qw( Exporter );
our @EXPORT = qw(
debug
)
sub debug {
carp Dumper @_;
}
1;
所以你可以在你的脚本中写一下:
use MyTest;
debug {a => 'b', c => 'd' }
答案 2 :(得分:0)
有趣的事实:Some symbols是神奇的,因为它们总是在main
包中引用它们的值。您可以将子例程分配给这些符号,它们将在任何包中显示。
{
package Foo;
# special names _ ARGV ARGVOUT ENV INC SIG STDERR STDIN STDOUT
sub ENV { print "In main::ENV ...\n" }
sub STDIN { print "In main::STDIN ...\n" }
sub _ { print "In main::_\n" }
# names that begin with ^ + upper case letter, or all digits
*{^T} = sub { scalar localtime };
*{^Gmtime} = sub { scalar gmtime };
*43 = sub { 42 };
use Data::Dumper;
*{^D} = \&Data::Dumper::Dumper;
}
{
package Bar;
&ENV;
STDIN();
print "The time is ", &^T, "\n";
print "In London it is ", &{^Gmtime}, "\n";
print "The answer is ", &43, "\n";
print "\@foo is ", &^D( \@foo );
}
除非你想让下一个维护你代码的人疯狂,否则不建议这样做。