[英]Perl grep a multi line output for a pattern
我在下面的代碼中嘗試對變量中的模式進行grep。 變量中包含多行文字。
$output
多行文本如下所示
_skv_version=1
COMPONENTSEQUENCE=C1-
BEGIN_C1
COMPONENT=SecurityJNI
TOOLSEQUENCE=T1-
END_C1
CMD_ID=null
CMD_USES_ASSET_ENV=null_jdk1.7.0_80
CMD_USES_ASSET_ENV=null_ivy,null_jdk1.7.3_80
BEGIN_C1_T1
CMD_ID=msdotnet_VS2013_x64
CMD_ID=ant_1.7.1
CMD_FILE=path/to/abcI.vc12.sln
BEGIN_CMD_OPTIONS_RELEASE
-useideenv
我用於grep模式的代碼
use strict;
use warnings;
my $cmd_pattern = "CMD_ID=|CMD_USES_ASSET_ENV=";
my @matching_lines;
my $output = `cmd to get output` ;
print "output is : $output\n";
if ($output =~ /^$cmd_pattern(?:null_)?(\w+([\.]?\w+)*)/s ) {
print "1 is : $1\n";
push (@matching_lines, $1);
}
我從$output
得到了多行輸出,但是在$output
上使用的正則表達式模式匹配沒有給我任何結果。
所需的輸出
jdk1.7.0_80
ivy
jdk1.7.3_80
msdotnet_VS2013_x64
ant_1.7.1
關於您的正則表達式:
while
, while
不是一個if
(否則,您將只匹配一次); 進行此更改時,您還需要/gc
修飾符 /s
修飾符,因為它使.
匹配\\n
,您不會使用它(請參閱末尾的注釋) /m
修飾符,以使^
匹配每行的開頭,而不僅僅是字符串的開頭 ^
之后立即在正則表達式中添加\\s*
,因為在至少一行中,您有一個前導空格 $cmd_pattern
左右$cmd_pattern
括號; 否則,您將獲得兩個選項,第一個選項是^CMD_ID=
,第二個選項是CMD_USES_ASSET_ENV=
然后是其余的表達式 您還可以將(\\w+([\\.]?\\w+)*)
簡化為(.+)
。
結果將是:
while ($output =~ /^\s*(?:$cmd_pattern)(?:null_)?(.+)/gcm ) {
print "1 is : $1\n";
push (@matching_lines, $1);
}
話雖如此,您的正則表達式仍不會jdk1.7.3_80
拆分ivy
和jdk1.7.3_80
; 我建議添加一個拆分並刪除_null
,例如:
while ($output =~ /^\s*(?:$cmd_pattern)(?:null_)?(.+)/gcm ) {
my $text = $1;
my @text;
if ($text =~ /,/) {
@text = split /,(?:null_)?/, $text;
}
else {
@text = $text;
}
for (@text) {
print "1 is : $_\n";
push (@matching_lines, $_);
}
}
剩下的唯一問題是孤行CMD_ID=null
。 我要留給你:-)
(我最近寫了一篇有關正則表達式最佳做法的博客文章-http://blog.codacy.com/2016/03/30/best-practices-for-regular-expressions/-您會發現始終有一條注釋在Perl中需要/s
;我在這里提到您不需要它的原因是,您沒有使用實際需要的那個,這可能意味着您不確定/s
的含義)
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.