【发布时间】:2020-08-05 20:39:31
【问题描述】:
打印匹配值的 perl 正则表达式是什么?例如,我想从此字符串打印195
"2011-04-11 00:39:28,736::[main]::INFO (Main.java:73) Test.Main::main() Total Successful Transactions = 195".
我该怎么做?提前致谢
【问题讨论】:
打印匹配值的 perl 正则表达式是什么?例如,我想从此字符串打印195
"2011-04-11 00:39:28,736::[main]::INFO (Main.java:73) Test.Main::main() Total Successful Transactions = 195".
我该怎么做?提前致谢
【问题讨论】:
您可以在正则表达式中使用括号来捕获子字符串。捕获的组存储在 $1、$2 等中。示例:
while (<>) {
if (/Total Successful Transactions = (\d+)/) {
print "$1\n";
}
}
或者,稍微短一点:
while (<>) {
print "$1\n" if /Total Successful Transactions = (\d+)/;
}
您还可以利用列表上下文中的匹配运算符 (//) 返回由组匹配的列表:
$\ = '\n'; # Output newline after each print.
while (<>) {
print for /Total Successful Transactions = (\d+)/;
}
这让您可以编写一个紧凑的单行(-l 选项自动为每个打印添加换行符等):
perl -lne 'print for /Total Successful Transactions = (\d+)/'
【讨论】:
只是想以不同的方式重新构建以前的答案;请注意,在这种情况下:
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /Xy = 3/;'
1
...我们得到 1 被打印出来 - 就像“是的,我有一个匹配”。如果我们想返回匹配的文本部分,正如@markusk 指出的那样,“在正则表达式中使用括号来捕获子字符串”:
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /(Xy = 3)/;'
Xy = 3
但是,请注意,在捕获时使用此习语连接字符串时可能会遇到问题:
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /Xy = 3/ . "\n";'
1 # OK
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /(Xy = 3)/ . "\n";'
1 # NOT OK
...所以在这种情况下最好将事情分开:
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /(Xy = 3)/ ; print "\n";'
Xy = 3 # OK again
但是,如果我们想要捕获“某物”,比如说一个数字 - 那么,由于我们使用括号,我们会自动返回与该习语匹配的内容(而不是整个“搜索”字符串):
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /Xy = (\d)/ ; \
print "\n";'
3
...因此,要完整捕获搜索到的字符串,我们应该将其再次用括号括起来:
$ perl -e '$str="the variable Xy = 3 in this case"; print $str =~ /(Xy = (\d))/ ; \
print "\n";'
Xy = 33
.... 但是,我们没有得到预期的结果,因为现在有两个匹配项,$1 和 $2;显然成语“print $str =~ /.../”输出所有匹配项(在本例中为“$1$2”)。
所以为了在这个嵌套匹配的情况下只获取搜索到的字符串,我们现在有明确指定只$1:
$ perl -e '$str="the variable Xy = 3 in this case"; $str =~ /(Xy = (\d))/ ; \
print "$1 \n";'
Xy = 3
编辑 2013 年 10 月:通过 Assign one of multiple regex matches to variable as Perl one-liner (dereference array?) - 这也可以用于单班轮:
$ perl -e '$str="the variable Xy = 3 in this case"; \
print ( ( $str =~ /(Xy = (\d))/ )[1] ); print "\n";'
3
...但是,请注意,print 需要第二组括号,以便直接使用返回的正则表达式(匿名?)数组。
最后,在多行上下文中,确保首先将整个文件/文本“啜”成一个字符串;然后使用/s(单行模式=换行匹配)和/g(全局/多个匹配)-最后,确保匹配表达式在while循环中,以便遍历所有匹配:
$ echo "some data
IN
123
OUT
some more data
is about to follow:
IN
256
OUT
done with data
out" | perl -e '$str = do { local $/; <> }; while ($str =~ /(IN(.*?)OUT)/sg) { print "$1\n"} '
IN
123
OUT
IN
256
OUT
嗯,希望这对某人有所帮助,
干杯!
【讨论】:
perl -ne 'print if /IN/../OUT/'
怎么样:
print $string =~ /Total Successful Transactions = (\d+)/;
您实际上很少需要使用$1 和朋友。
【讨论】:
/(\d+$)/;
print $1;
我猜你只是想要号码195。对吧?
【讨论】:
my $str = '"2011-04-11 00:39:28,736::[main]::INFO (Main.java:73) Test.Main::main() Total Successful Transactions = 195".';
$str =~ /Total Successful Transactions = (\d+)/;
print $1;
195 将存储在 $1 中
【讨论】:
检查" 和. 之前的最后一位数字。
#!/usr/bin/env perl
use strict;
use warnings;
my $string = q{"2011-04-11 00:39:28,736::[main]::INFO (Main.java:73) Test.Main::main() Total Successful Transactions = 195".};
my ($number) = $string =~ m{ (\d+) " \. \z}x;
print "Matched number: $number\n" if defined $number;
@markusk 接受的答案的命令行版本非常紧凑:
perl -ne '/Total Successful Transactions = (\d+)/ && print "$1\n";'
【讨论】:
像这样:
if ("2011-04-11 00:39:28,736::[main]::INFO (Main.java:73) Test.Main::main() Total Successful Transactions = 195" =~ /(\d+)$/) {
print $1;
}
匹配后,匹配的组将以 $1..$n 的形式提供。
【讨论】: