if(!$_) 的含义
Meaning of if(!$_)
我有一个正在读取文件的 Perl 脚本。在某些时候,代码在 for 循环中使用以下 if 语句:
for (my $i = 0; $i<10 ; $i++ ) {
$_ = <INPUT>;
if (!$_) {last;}
...
我是 Perl 新手,所以我想知道 !$_ 的含义。在这个例子中,$_ 是我文件的一行。那么,如果语句为真,该行应该包含哪些内容。
if
条件,即 ()
中的内容,在 boolean scalar context 中进行评估以测试“真实性”。因此,如果它是 undef
或 ''
(空字符串)或 0
(或字符串 "0"
)则为假。
!
否定其后的内容,因此如果 $_
为假(undef
或 ''
或 0
,则 if (!$_)
为真或 "0"
)。但是,在这种情况下,$_
是从 <>
operator 分配的,所以它总是在末尾有一个换行符——除非 <>
的源已经耗尽,在这种情况下 <>
returns undef
.
因此,在这种情况下,if (!$_)
测试是否没有更多内容可从 INPUT
读取,如果是,则使用 last
退出 for
循环是这样的。
对显示的代码的一些评论。
那个 C 风格的 for
循环也可以写成 for my $i (0..9)
,这被认为更好,更易读。† 参见 foreach, and really follow links for flow-control key-words
这段代码
$_=<INPUT>
if (!$_) { last; }
...
从 INPUT
文件句柄读取并在文件结束时退出其循环(参见 last)。 (这不必是实际文件,而是可通过文件句柄读取的任何资源。)
这至少可以说是笨拙的;一种常见的做法是
while (<INPUT>) {
...
}
† 如此之多,以至于即使是硬核编译语言现在也拥有它。 C++11
引入了range-based for loop
for (auto var: container) ... // (really, const auto&), or auto&, or auto&&
上面链接的标准参考说
Used as a more readable equivalent to the traditional for
loop [...]
我有一个正在读取文件的 Perl 脚本。在某些时候,代码在 for 循环中使用以下 if 语句:
for (my $i = 0; $i<10 ; $i++ ) {
$_ = <INPUT>;
if (!$_) {last;}
...
我是 Perl 新手,所以我想知道 !$_ 的含义。在这个例子中,$_ 是我文件的一行。那么,如果语句为真,该行应该包含哪些内容。
if
条件,即 ()
中的内容,在 boolean scalar context 中进行评估以测试“真实性”。因此,如果它是 undef
或 ''
(空字符串)或 0
(或字符串 "0"
)则为假。
!
否定其后的内容,因此如果 $_
为假(undef
或 ''
或 0
,则 if (!$_)
为真或 "0"
)。但是,在这种情况下,$_
是从 <>
operator 分配的,所以它总是在末尾有一个换行符——除非 <>
的源已经耗尽,在这种情况下 <>
returns undef
.
因此,在这种情况下,if (!$_)
测试是否没有更多内容可从 INPUT
读取,如果是,则使用 last
退出 for
循环是这样的。
对显示的代码的一些评论。
那个 C 风格的
for
循环也可以写成for my $i (0..9)
,这被认为更好,更易读。† 参见 foreach, and really follow links for flow-control key-words这段代码
$_=<INPUT> if (!$_) { last; } ...
从
INPUT
文件句柄读取并在文件结束时退出其循环(参见 last)。 (这不必是实际文件,而是可通过文件句柄读取的任何资源。)这至少可以说是笨拙的;一种常见的做法是
while (<INPUT>) { ... }
† 如此之多,以至于即使是硬核编译语言现在也拥有它。 C++11
引入了range-based for loop
for (auto var: container) ... // (really, const auto&), or auto&, or auto&&
上面链接的标准参考说
Used as a more readable equivalent to the traditional
for
loop [...]