Perl:如何在两个相同模式之间打印线条?

Perl : How to print lines in between two of the same patterns?

我有一些数据叫做 data_range.txt。最终我想将数据加载到数组中并比较字符串。但是我无法打印这两个 -- 模式之间的线条。

--
2020-10-07T22:14:27,545 DEBUG [recvMsgProc-0] <KdbQMHandler> calling:parameters=191216CV0
2020-10-07T22:14:27,554 INFO  [recvMsgProc-0] <KdbQMHandler> resultkx.Flip@
--
2020-10-07T22:43:12,345 DEBUG [recvMsgProc-1] <KdbQMHandler> calling:parameters=00774MAB1
2020-10-07T22:43:12,354 INFO  [recvMsgProc-1] <KdbQMHandler> resultkx.Flip@
--
2020-10-07T22:44:02,028 DEBUG [recvMsgProc-0] <KdbQMHandler> calling:parameters=00774MAB1
2020-10-07T22:44:02,036 INFO  [recvMsgProc-0] <KdbQMHandler> resultkx.Flip@
--
2020-10-07T22:55:10,691 DEBUG [recvMsgProc-1] <KdbQMHandler> calling:parameters=71647NBE8
2020-10-07T22:55:10,703 INFO  [recvMsgProc-1] <KdbQMHandler> resultkx.Flip@
--

我有一个脚本,当我尝试在两种不同的模式之间打印时通常可以使用,但是这些模式是相同的。

#!/usr/bin/perl
use warnings;
use strict;

my $file = 'data_range.txt';
open my $fh, $file  or die "Can't open $file: $!";

# Build the start and end patterns
my $beg = qr/--/;
my $end = qr/--/;

while (<$fh>)
{
    if (/$beg/ .. /$end/) {
        print if not /$end/;
    }
}

您需要稍微修改一下条件,不要跳过第二部分

if (/--/ .. /--/ && next) {
    print;
}

但放弃范围运算符并改用输入记录分隔符可能更简洁:

local $/ = "--\n";
while (<>) {
    # Here $_ contains all the lines of a section
    my @lines = split /\n/;
    # ...
}

使用 grep 预处理输入以删除 -- 行,并使用 paste 将输入更改为每行 2 条记录的文件,默认情况下加入选项卡。通过在选项卡上将记录拆分为每行 2 条记录的数组,可以轻松解析结果。

grep -v '^--' data_range.txt | paste - - | perl -F'\t' -lane 'print join "\t", map { qq{"$_"} } @F;'

# Prints:

"2020-10-07T22:14:27,545 DEBUG [recvMsgProc-0] <KdbQMHandler> calling:parameters=191216CV0"     "2020-10-07T22:14:27,554 INFO  [recvMsgProc-0] <KdbQMHandler> resultkx.Flip@"
"2020-10-07T22:43:12,345 DEBUG [recvMsgProc-1] <KdbQMHandler> calling:parameters=00774MAB1"     "2020-10-07T22:43:12,354 INFO  [recvMsgProc-1] <KdbQMHandler> resultkx.Flip@"
"2020-10-07T22:44:02,028 DEBUG [recvMsgProc-0] <KdbQMHandler> calling:parameters=00774MAB1"     "2020-10-07T22:44:02,036 INFO  [recvMsgProc-0] <KdbQMHandler> resultkx.Flip@"
"2020-10-07T22:55:10,691 DEBUG [recvMsgProc-1] <KdbQMHandler> calling:parameters=71647NBE8"     "2020-10-07T22:55:10,703 INFO  [recvMsgProc-1] <KdbQMHandler> resultkx.Flip@"

Perl one-liner 使用这些命令行标志:
-e :告诉 Perl 查找代码 in-line,而不是在文件中。
-n :一次循环输入一行,默认分配给 $_
-l : 在执行代码 in-line 之前去除输入行分隔符(默认情况下在 *NIX 上为 "\n"),并在打印时附加它。
-a : 在空格或 -F 选项中指定的正则表达式上将 $_ 拆分为数组 @F
-F'/\t/' : 在 TAB 上拆分为 @F,而不是在空格上。

另请参见:
perldoc perlrun: how to execute the Perl interpreter: command line switches