perl – 理解代码:Hash,grep for duplicatelicates(修改为检查
码:
@all_matches = grep { ! ( $seensentence { $_->[0] .'-'. $_->[1] .'-'. $_->[5] } ++ ) } @all_matches; 目的:此代码从数组@all_matches(AoA)中删除某些元素的重复项. 我完全崩溃的尝试(?? ?? ??我不确定的地方): Grep返回返回true的@all_matches元素. 哈希%seesentence的关键是??三个元素?? of @all_matches.由于散列只能有唯一键,因此第一次通过它的值会从undef(0)递增到1.下一次,它是一个定义的值,但是!表示grep仅在它是undef(与该元素关联的唯一值)时才返回它. 我的问题: (1)我怎样才能转{$_-> [0] .’-‘. $_-> [1].’ – ‘. $_-> [5]}变成了HoH? 我被告知这是实现它的另一种(惯用的)方式.在黑暗中刺伤将是: ( {$_->[0] => 0,$_->[1] => 0,$_->[5] => 0} )++ (1b)因为我不明白原作是如何做我想要的.我读到-bareword等同于“-bareword”所以我尝试了:{“$_-> [0]”. “$_-> [1]”. “$_-> [5]”}它似乎完全相同.我仍然不明白:它是将每个元素分别视为一个键(a)(如一个键数组)还是它(b)正确:所有同时(因为.将它们连接成一个字符串)或者它( c)没有做我认为的事情? (2)这是什么意思:$_-> [0] || $_-> [1] || $_-> [5]?它与上面没有相同的做法. 我读到:短路逻辑运算符返回最后一个值,所以它会检查{$_-> [0]}的值,如果有的话,我认为那里的值会增加,如果没有,它会检查下一个元素,直到没有为真,这是grep传递唯一值的时候. 谢谢你的时间,我尽量尽可能彻底(出错?)但是如果有任何遗漏,请告诉我. 解决方法
首先让我们将grep转换为foreach循环,以便我们可以更清楚地检查它.为了清楚起见,我将把一些习语扩展为更大的构造.
my @all_matches = ( ... ); { my %seen; my @no_dupes; foreach my $match ( @all_matches ) { my $first_item = $match->[0]; my $second_item = $match->[1]; my $third_item = $match->[5]; my $key = join '-',$first_item,$second_item,$third_item; if( not $seen{ $key }++ ) { push @no_dupes,$match; } } @all_matches = @no_dupes; } 换句话说,原始编码器使用$match中保存的数组引用创建一个哈希键,对于$match-> [0],1和5的每个引用索引.由于哈希键是唯一的,任何重复项将在推入@no_dupes之前检查密钥是否已存在将被删除. grep {}机制只是一个更有效的代码(即,更快的类型,没有一次性变量)成语来完成同样的事情.如果它有效,为什么要重构呢?你需要改进的是什么不做? 要对HoH做同样的事情,你可以这样做: my @all_matches = ( ... ); { my %seen; my @no_dupes; foreach my $match ( @all_matches ) { my $first_item = $match->[0]; my $second_item = $match->[1]; my $third_item = $match->[5]; if( not $seen{ $first_item }->{ $second_item }->{ $third_item }++ ) { push @no_dupes,$match; } } @all_matches = @no_dupes; } 哪个可以翻译成grep如下: my @all_matches = ( ... ); { my %seen; @all_matches = grep { not $seen{$_->[0]}->{$_->[1]}{$_->[5]}++ } @all_matches; } 但是,在这种情况下,我没有看到构建数据结构的明显优势,除非您打算使用%稍后看到的其他内容. 关于||运算符,那是一种不同的动物.我想不出在这种情况下使用它的任何有用方法.例如,“$a || $b || $c”的逻辑短路运算符测试$a的布尔真值.如果是,则返回其值.如果它是假的,它会以同样的方式检查$b.如果它是假的,它会以同样的方式检查$c.但如果$a为真,则$b永远不会被检查.如果$b为真,则$c永远不会被检查. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |