简洁的foreach表达式在一行中

Fra*_*ank 6 syntax perl foreach

在Perl中,人们通常可以避免使用控制块,如下所示:

print "$_\n" foreach(@files);
Run Code Online (Sandbox Code Playgroud)

代替:

foreach(@files){
  print "$_\n";
}
Run Code Online (Sandbox Code Playgroud)

该语法如何在以下更复杂的情况下工作:

die("Not a file: $_") unless -f $_ foreach(@files);
Run Code Online (Sandbox Code Playgroud)

它给我一个语法错误.我不是要编写混淆代码,它只是程序中不重要的部分,所以我想尽可能简洁地表达它.

概括的答案:

我只接受一个答案作为接受的答案,但我最喜欢克里斯和乔恩的以下答案.

这个foreach按照我的意图使用,但没有syntax error:

-f or die "Not a file: $_" foreach @files;
Run Code Online (Sandbox Code Playgroud)

以下一个至少同样好.我喜欢这die是在声明的开头,因为这是读者应该注意的:

die("Not a file: $_") for grep {!-f} @files;
Run Code Online (Sandbox Code Playgroud)

Chr*_*utz 13

只是要Perlish(TMTOWTDI)你可以使用逻辑短路:

-f or die "Not a file: $_" foreach @files;
Run Code Online (Sandbox Code Playgroud)

在OS X上测试并且有效.

作为旁注,-f or die看起来像open() or die我在Perl中看到的许多常见结构,并且仍然(认为)显示了该行的意图(die在某些条件下).


Ada*_*ire 11

您可以使用@ Brent.Longborough的答案,或者如果您真的想要postfix,请执行以下操作:

do { die("Not a file: $_") unless -f $_ } foreach(@files);
Run Code Online (Sandbox Code Playgroud)

但是,我同意其他人,只是因为这是"一个不重要的部分"并不意味着简洁更好. 可读性很重要.


Cha*_*rch 7

好吧,你可能不打算写出混淆代码,但我会说你肯定会尝试.

两条线(或者甚至是一条线上的一块,就像Brent.Longborough所暗示的那样)而不是一条线那么糟糕吗?老实说,这就是我一般不喜欢尝试调试/编辑其他人的perl代码的原因,大量用perl编写的人似乎都沉迷于以最"聪明"的方式做几乎所有事情,而不是去做以一种易于理解的方式阅读其他人.


Jon*_*son 5

如果错误测试是此代码的主要部分,那么将它放在行的开头可能是有意义的.使用时略有改进grep:

die("Not a file: $_") for grep {!-f} @files;
Run Code Online (Sandbox Code Playgroud)

但是如果你计划在代码的那一部分出于某些其他原因循环遍历文件,那么最好将它添加到循环体中.