在 Perl SO answer中,张贴者使用此代码匹配空字符串:
$userword =~ /^$/; #start of string, followed immediately by end of string
brian d foy对此评论说:
你不能真的这么说,因为这将匹配一个特定的非空字符串。
问题:与哪个非空字符串匹配?它是仅由“”组成的字符串\r
吗?
在 Perl SO answer中,张贴者使用此代码匹配空字符串:
$userword =~ /^$/; #start of string, followed immediately by end of string
brian d foy对此评论说:
你不能真的这么说,因为这将匹配一个特定的非空字符串。
问题:与哪个非空字符串匹配?它是仅由“”组成的字符串\r
吗?
use strict;
use warnings;
use Test::More;
ok("\n" =~ /^$/);
ok("\n" =~ /^\z/);
ok("\n" =~ /^\A\z/); # Better as per brian d. foy's suggestion
done_testing;
如果要测试字符串是否为空,请使用/^\z/
或查看长度是否$str
为零(这是我更喜欢的)。
输出:
好的 1 不行 2 不好 3
让我们检查一下文档,为什么不呢?引用perlre ,
$
: 匹配行尾(或末尾换行符之前)
给定
\z
: 仅在字符串末尾匹配
这意味着/^$/
相当于/^\n?\z/
。
$ perl -E'$_ = ""; say /^$/ ||0, /^\n?\z/ ||0, /^\z/ ||0;'
111
$ perl -E'$_ = "\n"; say /^$/ ||0, /^\n?\z/ ||0, /^\z/ ||0;'
110
请注意,/m
更改内容^
和$
匹配。在 下/m
,^
匹配任何“行”的开头,$
匹配任何换行符之前和字符串末尾。
$ perl -E'$_ = "abc\ndef\n"; say "matched at $-[0]" while /^/g'
matched at 0
$ perl -E'$_ = "abc\ndef\n"; say "matched at $-[0]" while /$/g'
matched at 7
matched at 8
并使用 /m:
$ perl -E'$_ = "abc\ndef\n"; say "matched at $-[0]" while /^/mg'
matched at 0
matched at 4 <-- new
$ perl -E'$_ = "abc\ndef\n"; say "matched at $-[0]" while /$/mg'
matched at 3 <-- new
matched at 7
matched at 8
\A
,\Z
并且\z
不受/m
:
$ perl -E'$_ = "abc\ndef\n"; say "matched at $-[0]" while /\A/g'
matched at 0
$ perl -E'$_ = "abc\ndef\n"; say "matched at $-[0]" while /\z/g'
matched at 8
$ perl -E'$_ = "abc\ndef\n"; say "matched at $-[0]" while /\Z/g'
matched at 7
matched at 8
正则表达式/^$/
匹配非空字符串"\n"
。
默认情况下,Perl 正则表达式匹配假定字符串包含单“行”文本。
^
匹配行首;在没有/m
修饰符的情况下,这与字符串的开头相同。
$
匹配行尾或末尾的换行符之前(这就是/^$/
匹配非空字符串的原因"\n"
)。
报价perldoc perlre
:
默认情况下,“^”字符保证只匹配字符串的开头,“$”字符只匹配结尾(或结尾的换行符之前),Perl 在假设字符串只包含一条线。嵌入的换行符不会被“^”或“$”匹配。但是,您可能希望将字符串视为多行缓冲区,这样“^”将匹配字符串中的任何换行符(除非换行符是字符串中的最后一个字符),而“$”将在任何换行符之前匹配。以更多开销为代价,您可以通过在模式匹配运算符上使用 /m 修饰符来做到这一点。
脚本:
my $str = "\n";
my $test1 = ($str =~ /^$/) ? 1 : 0;
my $test2 = ($str =~ /\A\z/) ? 1 : 0;
print "$test1, $test2\n";
输出:
1, 0