rjh*_*rjh 18 perl performance types moose typechecking
有很多关于MooseX :: Method :: Signatures的讨论,甚至在此之前,像Params :: Validate这样的模块设计用于检查方法或函数的每个参数.我正在考虑使用前者用于我未来的所有Perl代码,无论是个人还是我的工作地点.但我不确定这是否值得付出努力.
我正在考虑我之前看过(和写过)的所有Perl代码,之后不执行此类检查.我很少看到一个模块这样做:
my ($a, $b) = @_;
defined $a or croak '$a must be defined!';
!ref $a or croak '$a must be a scalar!";
...
@_ == 2 or croak "Too many arguments!";
Run Code Online (Sandbox Code Playgroud)
也许是因为没有某种辅助模块它只是太多的工作,但也许是因为在实践中我们不会向函数发送过多的参数,而且我们不会将arrayref发送到期望标量的方法 - 或者如果我们这样做,我们就会use warnings;
和我们很快就听到了 - 鸭子打字的方法.
那么Perl类型的检查是否值得追求性能,或者它的优势主要体现在编译的强类型语言(如C或Java)中?
我对任何有使用这些模块并且已经看到使用它们的好处(或没有)的Perl编写经验的人的答案感兴趣; 如果您的公司/项目有任何与类型检查有关的政策; 以及类型检查和性能方面的任何问题.
更新:我最近读了一篇关于这个主题的有趣文章,称为强测试与强打字.忽略轻微的Python偏见,它实质上表明在某些情况下类型检查可能会令人窒息,即使您的程序通过了类型检查,也无法保证正确性 - 正确的测试是唯一可靠的方法.
bri*_*foy 14
如果你确定一个参数正是你所需要的那么重要,那就值得了.性能仅在您已经正常运行时才有意义.无论您获得错误答案或核心转储的速度有多快都无关紧要.:)
现在,这听起来像是一个愚蠢的事情,但考虑一些不是的情况.我真的在乎@_
这里有什么吗?
sub looks_like_a_number { $_[0] !~ /\D/ }
sub is_a_dog { eval { $_[0]->DOES( 'Dog' ) } }
Run Code Online (Sandbox Code Playgroud)
在这两个例子中,如果参数不是你所期望的,你仍然会得到正确的答案,因为无效的参数不会通过测试.有些人认为这很难看,我可以看到他们的观点,但我也认为另类是丑陋的.谁赢?
但是,有时您需要保护条件,因为您的情况并非如此简单.您必须将数据传递给下一件事可能会使它们处于特定范围或某些类型之内,并且不会优雅地失败.
当我考虑保护条件时,我想通过如果输入不好以及我对失败多少关心会发生什么.我必须根据每种情况的要求来判断.我知道这很糟糕,但我倾向于喜欢它比束缚和纪律方法更好,你必须经历所有的混乱,即使它无关紧要.
我害怕,Params::Validate
因为它的代码通常比我的子程序长.Moose的东西非常有吸引力,但是你必须意识到这是你宣布你想要的东西的方式,你仍然得到你可以手工制作的东西(你只是不必看到或做它).我讨厌Perl最大的问题是缺少可选的方法签名,这是Perl 6和Moose中最具吸引力的功能之一.
我基本上同意布莱恩.您需要担心多少方法的输入在很大程度上取决于您关注的是:a)有人会输入错误的数据,以及b)错误的数据会破坏方法的目的.我还要补充说,外部和内部方法之间存在差异.你需要对公共方法更加勤奋,因为你向你的班级消费者做出承诺; 相反,你可以对内部方法不那么勤奋,因为你对访问它的代码有更大的(理论上的)控制权,如果出现问题,你只能责怪自己.
MooseX :: Method :: Signatures是一种优雅的解决方案,可以添加一种简单的声明方式来解释方法的参数.方法::签名::简单和参数::验证很好但缺乏我觉得最有吸引力的功能之一:类型系统.我已经使用MooseX :: Declare和扩展MooseX :: Method :: Signatures进行了几个项目,我发现编写额外检查的标准非常小,几乎是诱人的.