我有以下脚本:
use strict;
use List::MoreUtils qw/uniq/;
use Data::Dumper;
my @x = (3,2);
my @y = (4,3);
print "unique results \n";
print Dumper([uniq(@x,@y)]);
print "sorted unique results\n";
print Dumper([sort uniq(@x,@y)]);
输出
unique results
$VAR1 = [
3,
2,
4
];
sorted unique results
$VAR1 = [
2,
3,
3,
4
];
所以它看起来排序不适用于uniq。 我不明白为什么。
我使用-MO = Deparse运行perl脚本并获得了
use List::MoreUtils ('uniq');
use Data::Dumper;
use strict 'refs';
my(@x) = (3, 2);
my(@y) = (4, 3);
print "unique results \n";
print Dumper([uniq(@x, @y)]);
print "sorted unique results\n";
print Dumper([(sort uniq @x, @y)]);
我的解释是perl决定从uniq(@ x,@ y)中删除括号,并使用uniq作为sort的函数。
为什么perl决定这样做?
我如何避免这些和类似的陷阱?
谢谢, 大卫
答案 0 :(得分:7)
sort
builtin接受子程序名称或块作为传递两个项目的第一个参数。然后必须返回一个确定项目之间顺序的数字。这些片段都是一样的:
use feature 'say';
my @letters = qw/a c a d b/;
say "== 1 ==";
say for sort @letters;
say "== 2 ==";
say for sort { $a cmp $b } @letters;
say "== 3 ==";
sub func1 { $a cmp $b }
say for sort func1 @letters;
say "== 4 ==";
sub func2 ($$) { $_[0] cmp $_[1] } # special case for $$ prototype
say for sort func2 @letters;
请注意,函数名称和列表之间没有任何逗号,请注意Perl中的parens主要用于确定优先级 - sort func1 @letters
和sort func1 (@letters)
是相同的,并且都不是执行func1(@letters)
。
要消除歧义,请在函数名前加+
:
sort +uniq @letters;
为了避免这种意外行为,最好的解决方案是在您不确定某个内置行为的行为时阅读文档 - 遗憾的是,许多人都有一些特殊的解析规则。
答案 1 :(得分:3)
您可以将括号括在唯一函数周围:
print Dumper([sort (uniq(@x,@y))]);
<强>输出:强>
$VAR1 = [
2,
3,
4
];