Perl类命名约定
假设我创建了一个名为Perl类命名约定,perl,Perl,假设我创建了一个名为Bar的类。文件Bar.pm启动 package Bar; 为了避免与其他Bar类冲突,我将该文件放在子目录Foo中。所以现在,当我使用这个类时,我必须写 use Foo::Bar; 我的问题是,我是否需要将类的名称更改为Foo::Bar?换句话说,我是否需要将Bar.pm的第一行更改为 package Foo::Bar; ??问题是,如果我这样做,我现在必须在任何地方将该类称为Foo::Bar,例如 my $obj = Foo::Bar->new(); Foo:
Bar
的类。文件Bar.pm
启动
package Bar;
为了避免与其他Bar
类冲突,我将该文件放在子目录Foo
中。所以现在,当我使用这个类时,我必须写
use Foo::Bar;
我的问题是,我是否需要将类的名称更改为Foo::Bar
?换句话说,我是否需要将Bar.pm
的第一行更改为
package Foo::Bar;
??问题是,如果我这样做,我现在必须在任何地方将该类称为Foo::Bar
,例如
my $obj = Foo::Bar->new();
Foo::Bar->doClassMethod();
这很烦人(在中也讨论了同样的问题),尤其是因为我喜欢类方法。是的,您必须更改
包的名称,以便与使用的名称完全匹配(也就是说,这是一个风格决定,而不是编译器强制执行的事情),但是遵循perlmod/perlnewmod中规定的相关指南是一个好主意,以使软件易于分发
注意,如果长名字困扰你,找一个具有自动完成功能的编辑器。引用:
如果EXPR是一个裸字,则require将假定扩展名为“.pm”,并且
将文件名中的“:”替换为“/”,以便
加载标准模块。这种形式的模块加载没有风险
更改名称空间。换句话说,如果您尝试以下方法:
require Foo::Bar; # a splendid bareword
require函数实际上会在
@INC数组中指定的目录
因此,是的,按照惯例,如果您的模块在中的某些$dir
位于$dir/Foo/Bar.pm
,那么它必须被调用Foo::Bar如果您认为类名Bar
可能与其他名为Bar
的类冲突,那么简单地移动文件是没有帮助的。如果您的程序最终同时使用了Bar
和Foo::Bar
,那么这两个名称空间都将被加载到同一名称空间中。在这一点上,你的程序会发生什么是任何人的猜测
如果不想键入长的类名,那么可以使用变量来保存名称
use My::Long::Class::Name::For::Bar;
my $bar_class = 'My::Long::Class::Name::For::Bar';
$bar_class->class_method(); # the same as My::Long::Class::Name::For::Bar->class_method()
软件包Local
仅用于此用途。例如,如果您创建一个包Bar.pm
,您可以调用该包Local::Bar
,并知道它不会与CPAN中的某些内容冲突
默认情况下,@INC
包含当前目录,因此您可以创建一个本地
子目录,然后将所有包放在那里。在公司中,我将Local
包名称空间划分为组,甚至是开发人员的名称。例如,我可以使用Local::Cm::Bar
或Local::David::Bar
。这样,如果我决定使用Alice的Bar类,我可以简单地包括Local::Alice::Bar
是的,标准CPAN规则规定不在包名称空间中使用您的名称,但是Local
包永远不会进入CPAN。您能稍微扩展一下“必须”的含义吗?我问这个问题是因为它在不更改包名的情况下工作(编译和运行)。不更改它会有什么后果?@shawkinaw如果不更改,则use
语句的import
方法将找不到正确的类,而包括构造函数在内的其他类方法(通常)将失败。这就像use
语句中的情况出错一样。它可以在不区分大小写的文件系统上工作,但只是出于偶然,其他所有东西都会被冲洗掉。不要那样做。只需将您的文件、包和使用完全对齐即可。几年后,你可能会有一些理由去做别的事情,但那只会伴随着严峻的战斗经历。这仍然是可疑的。是的,但您可能不会同时加载两个不同的Bar
类。但我明白你的意思。如果Perl允许您用一个缩短的名称引用类,那将是一件好事,但前提是不存在歧义。Tcl尽管存在所有的错误,但只要它是唯一的,您就可以通过一个缩短的名称来调用过程。