在上一个问题中,seaworthy询问如何从数组中删除前5个元素: How do I remove the first five elements of an array?
在几个建议中,friedo提供了这个:
my $cnt = 0;
@array = map { ++$cnt < 5 ? ( ) : $_ } @array;
我没有得到()位。请解释一下这对我有什么用,因为我无法理解它?
我知道三元钩子算子的工作原理如下: (如果有的话)? (然后这样做):(否则这样做)
例如:$a=2; print ($a==2 ? 3 : 4)
#the print:3
因为我们有:($ a == 2?3:4)
这意味着:(如果$ a等于2)? (然后打印3):(否则打印4)
所以使用friedo的代码,首先$ cnt增加到1,然后我们有:
$cnt < 5 ? ( ) : $_
意思是:
if $cnt is less than 5 ? then ( ) : otherwise $_
我可以看到$ _位是如何工作的,因为我有时会使用这样的地图:
@array = map { $_, "\n" } @array
这会复制@array中的一个元素,将副本放入$ ,然后添加一个\ n换行符,然后将$ 中的值复制回@array(它会对所有值执行此操作)在@array所以基本上它为@array中的每个元素添加换行符
因此:
@array = map { if $cnt is less than 5 then ( ) otherwise $_ } @array
意思是:
@array = map { if $cnt is less than 5 then ( ) otherwise copy the element back to @array }
如此清楚()意味着“摆脱它”之类的东西 但我只是不确定它是如何工作的。请你解释一下吗?
答案 0 :(得分:10)
在map
中,数组中的每个项都被传递到代码块(在$_
中),在那里它可以转换为其他值。换句话说,map
会转换列表。
在这种情况下,我们想要丢弃count($cnt
)小于5的值。那么当条件为真时,如何使map
块返回“nothing”?
我们不能说
my $cnt = 0; @array = map { ++$cnt < 5 ? undef : $_ } @array;
因为那时我们最终会得到一个看起来像
的数组( undef, undef, undef, undef, undef, 6, 7, 8 ... )
这不是我们想要的。
但是返回( )
会返回空列表。考虑push @foo, ( );
或@bar = ( 1, 2, 3, ( ), 4, 5, 6 );
在每种情况下,空的parens集是一个零项列表,对相关数组没有任何影响。
空列表在需要返回列表项或根本不需要任何内容的三元组中很有用。强制列表上下文在表达式上获取计数也很有用:
my $count = ( ) = $str =~ /\d/g;
这里,我们将正则表达式放在列表上下文中,方法是将其分配给一个空列表,给出字符串中的数字位数。然后我们将该空列表分配给$count
。
在map
中使用列表的另一个常见示例是当您将某些内容转换为哈希时。例如,
my %unique = map { $_ => 1 } @duplicates;
此处@duplicates
中的每个单项都会转换为一个看起来像( 'foo' => 1 )
的双元素列表,尽管由于没有涉及到parens,因此它并不那么明显。然后,所有两项列表都构建成一个交替键和值的大列表,构成哈希。假设你想制作这个哈希但是排除了一些项目。在这种情况下,我们需要返回一个键/值,或者 nothing 。所以这是一个使用空列表的好机会:
my %filtered_unique = map { some_test( $_ ) ? ( ) : ( $_ => 1 ) } @duplicates;
答案 1 :(得分:2)
我知道我在游戏中有点晚了,但为什么不做一些简单的事情?
我的@truncated = @array [5 .. $#array]
答案 2 :(得分:1)
显然你可以返回一个列表而不是一个元素,map通过连接这些列表和元素来构造结果。在这种情况下,()
只是空列表。要获得更多信息,请复制粘贴示例,然后将()
替换为(1, 2, 3)
。