Perl 获取文本文件中已知模式之间的数据
下面是我想要处理的文本文件Perl 获取文本文件中已知模式之间的数据,perl,Perl,下面是我想要处理的文本文件 ##BEGIN Text file A . B. DATA1 DATA12 DATA13 A C DATA2 DATA22 DATA23 A . B. DATA3 DATA32 DATA33 A . B. DATA4 DATA42 DATA43 A . B. DATA5 DATA52 DATA53 A . B. DATA6 DATA62 DATA63 ## END text file 现在我想得到以下输出 DATA1 DATA12 DATA13 DATA3 DAT
##BEGIN Text file
A . B.
DATA1
DATA12
DATA13
A C
DATA2
DATA22
DATA23
A . B.
DATA3
DATA32
DATA33
A . B.
DATA4
DATA42
DATA43
A . B.
DATA5
DATA52
DATA53
A . B.
DATA6
DATA62
DATA63
## END text file
现在我想得到以下输出
DATA1
DATA12
DATA13
DATA3
DATA32
DATA33
DATA4
DATA42
DATA43
DATA5
DATA52
DATA53
DATA6
DATA62
DATA63
我使用了下面的perl命令行,但无法获得所需的内容。您能告诉我是否有办法在命令行中实现这一点吗
perl -ne 'print if(/B/.../^A/)' ~/data | grep -v ^A
不会:
perl -ne 'print if m/DATA/' ~/data
有没有达到预期的效果
您尝试使用的范围操作符没有您想象的那么好,因为它捕获两个模式之间的数据。。。但这样做是包容性的,但我也不确定它是否能很好地处理同一条线的开始和结束模式
快速测试:
#!/usr/bin/perl
use strict;
use warnings;
while ( <DATA> ) {
print if ( /B/ ... /^A/ );
}
__DATA__
A B
1
2
3
A B
4
5
6
A B
我认为这意味着第一个模式是“匹配”的,但是第二个模式匹配没有检查行的其余部分-它继续到下一行
所以看看你的数据——你有一个标题行,你想要的数据有一个“a”。B'在顶部(你没有的是'A C')
因此,我认为您可以设置$/
来处理此问题:
-$/
是记录分隔符-通常这是\n
因此是换行符,但如果我们将其设置为\nA
则会获取多行块。
-然后,我们测试是否存在B
(基于上述情况-您想要的是带有B的内容,而不是带有C的内容)。
-然后我们应用两个正则表达式来删除a。B
行。(有点混乱,因为它被分成了两块)
我认为哪一种应该起作用?范围运算符有两种形式:
。
和…
。两点形式可以在同一个测试中计算开始和结束表达式(尽管它将至少返回一次true),而三点形式在下一个测试之前不会计算范围结束表达式。在这种情况下,OP使用了…
,因此代码是安全的。知道运算符返回的值是从1开始返回true的次数也是很有用的。最后一次返回true时,它将E0
附加到计数。这使得识别一个范围内的第一个和最后一个项目变得很容易。我对一个2点和3点范围的操作有点不适应。打印分隔符行,但似乎只与组匹配?抱歉,中途保存了注释-张贴在我的测试代码中。我建议您创建一个数据部分,其中有五行包含a
,bx
,C
,D
,E
。然后用while()
通读它,并使用Data::Dump
显示dd标量(/B/./X/)
和dd标量(/B/../X/)的值代码>好的,这是因为第二行AB
关闭了量程操作符,但直到下一行4
它才被再次测试,因此直到第三行AB
才被再次打开。您可以使用。
在打开关闭条件的同一测试上测试关闭条件,但无法进行相反的操作。
A B
1
2
3
A B
A B
#!/usr/bin/perl
use strict;
use warnings;
{
local $/ = "\nA";
while (<DATA>) {
if ( m/B/ ) {
s/\n^A$//gm;
s/.*B\.$//gm;
print;
}
}
}
__DATA__
A . B.
DATA1
DATA12
DATA13
A C
DATA2
DATA22
DATA23
A . B.
DATA3
DATA32
DATA33
A . B.
DATA4
DATA42
DATA43
A . B.
DATA5
DATA52
DATA53
A . B.
DATA6
DATA62
DATA63
DATA1
DATA12
DATA13
DATA3
DATA32
DATA33
DATA4
DATA42
DATA43
DATA5
DATA52
DATA53
DATA6
DATA62
DATA63