导出没有导出器的符号

时间:2014-03-10 07:41:34

标签: perl

我正在学习如何在Perl中使用包和对象。

有人建议我使用Exporter来使用具有package指令的模块的函数和变量。

我很想知道是否有办法在不使用Exporter的情况下导出符号?换句话说,可以以某种方式模仿Exporter吗?

我问的原因是由于我的假设,导出器带来了额外的功能,即必须尽可能快地运行的小型简单脚本不需要,并且可以通过使用几个简单的行包含该功能来避免代码。

也许简单说明我的意思可能有所帮助。

假设我有一个只执行此操作的模块

my $my_string = "my_print";
sub my_print {
  print "$my_string: ", @_;
}

允许很多小脚本使用my_print代替print,只需要一个简单的require,其中包含我的模块的文件名(并且非常一点点开销。)

然后,我想在另一个带有声明的模块中使用它,这不再有效,所以现在我必须使用package声明,因此{{1}在我的简单模块中,只是为了让它在新模块中工作。

使用Perl已经有一段时间了,我使用的事实是几乎所有东西都非常简单,直接且开销低,所以我觉得可以有这样的解决方案。如果没有,那么我会接受一个答案,解释为什么出口商是唯一的方式。

3 个答案:

答案 0 :(得分:2)

Exporter的功能非常简单。以下是不使用Exporter的方法:

在Foo.pm:

package Foo;

use strict;
use warnings;

sub answer { 42 }

sub import {
  no strict 'refs';
  my $caller = caller;
  *{$caller . "::answer"} = \&answer;
}

1;

在script.pl中:

use Foo;

print answer(), "\n";

然而,正如其他人所说,你真的不必担心使用Exporter的开销。它是一个相当小而高效的模块,并且自5.0以来已与Perl的每个版本捆绑在一起。更重要的是,你可能已经在任何地方加载了它 - 许多核心Perl模块(例如Carp,Scalar :: Util,List :: Util等)都使用它。

在上面代码的早期版本中

更新:,我忘记了no strict 'refs';。这是*{$some_string}工作所必需的。

答案 1 :(得分:0)

Exporter肯定是低开销。 See Also section中还有一个备用模块列表。

如果您感到好奇,可以为模块执行search on CPAN并自己查看the source。您会注意到大多数“代码”只是文档。但是,老实说,如果你是perl的新手,你不应该担心为了减轻你的代码重量轻,因为你应该尽可能多地利用尽可能多的资源来使编码变得更快更容易。 / p>

只是我的$ .02

答案 2 :(得分:0)

这听起来很像是在寻找避免Exporter的借口?你真的有一些启动太慢的程序吗? Exporter仅在编译阶段加载并执行。

如果你真的担心编译速度,那么你应该写

BEGIN { require MyPackage }

然后再

MyPackage::myprint($myparam)

根本不涉及来自Exporter no 开销,甚至来自等效的内联代码。

是的,实际符号从一个包导出到另一个包的代码只是Exporter.pm代码中的一行,而您可以复制它。但是你不是更愿意添加

use MyPackage;

在您开始编程时,并且知道在任何情况下,MyPackage中的符号都会被正确导出?

如果你有“必须尽快运行的小型简单脚本”,那么你应该调查让它们作为守护进程运行,而不是每次运行程序时重新编译Perl。