1

我想自动化以下 Perl 代码。这样它将从两个 txt 文件中读取可变数量的行并将这些行写入另一个 txt 文件。

我有两个 txt 文件 ( 1st_file.txt) 和 ( 2nd_file.txt),我想读取变量号。这些文件中的行数。我怎样才能做到这一点?下面给出的 Perl 代码做同样的工作,但如果我更改 txt 文件,我还需要更改我的 Perl 代码,这不是很有效。

那么有人可以指导我如何为下面给出的问题编写有效的 Perl 代码吗?因此,如果我更改 txt 文件中的数据,我将得到我想要的结果,但不会更改 Perl 代码。

这里的变化是什么意思?这意味着如果我从 1st_file.txt 中删除第 5 到第 7 行207 --> A_207_P2_M2A --> T_207_P2_M2A,我也从 2nd_file.txt 中删除第 4 行P2_M2A。所以现在在删除这些行之后,我也想在我的 Perl 代码中进行更改以获得所需的结果,因为我删除了这些行。但是我想要一个 Perl 代码,如果我相应地对两个 txt 文件进行一些更改,我不需要在其中进行任何修改。

Perl 代码:

use warnings;
use strict;

open (FILE1, 'g:\perl_tests\1st_file.txt');
open (FILE2, 'g:\perl_tests\2nd_file.txt');
open (FILE3, '> g:\perl_tests\3rd_file.txt');

my @speech1 = <FILE1>;
my @speech2 = <FILE2>;

print FILE3 @speech2[0..1];
print FILE3 @speech1[1..2];
print FILE3 @speech1[5..6];
print FILE3 @speech2[4..6];
print FILE3 @speech1[9..10];
print FILE3 @speech2[8..10];
print FILE3 @speech1[13..14];
print FILE3 @speech2[12..14];
print FILE3 @speech1[17..18];
print FILE3 @speech2[16..18];
print FILE3 @speech1[21..22];
print FILE3 @speech1[25..26];
print FILE3 @speech1[29..30];

1st_file.txt

153
A_153_P1_M2A_Some text is written here
T_153_P1_M2A_Some text is written here

207
A_207_P2_M2A_Some text is written here
T_207_P2_M2A_Some text is written here

48
A_48_P1_T1B_Some text is written here
T_48_P1_T1B_Some text is written here

57
A_57_P1_T2A_Some text is written here
T_57_P1_T2A_Some text is written here

167
A_167_P1_W1C_Some text is written here
T_167_P1_W1C_Some text is written here

26
A_26_P1_W2B_Some text is written here
T_26_P1_W2B_Some text is written here

183
A_183_P2_W2B_Some text is written here
T_183_P2_W2B_Some text is written here

69
A_69_P3_W2B_Some text is written here
T_69_P3_W2B_Some text is written here

第二个文件.txt

M2A
Top_M2A
P1_M2A
P2_M2A

T1B
Top_T1B
P1_T1B

T2A
Top_T2A
P1_T2A

W1C
Top_W1C
P1_W1C

W2B
Top_W2B
P1_W2B
P2_W2B
P3_W2B

3rd_file.txt (输出:由 Perl 代码生成,应该是下面给出的那个)

M2A
Top_M2A
A_153_P1_M2A_Some text is written here
T_153_P1_M2A_Some text is written here
A_207_P2_M2A_Some text is written here
T_207_P2_M2A_Some text is written here

T1B
Top_T1B
A_48_P1_T1B_Some text is written here
T_48_P1_T1B_Some text is written here

T2A
Top_T2A
A_57_P1_T2A_Some text is written here
T_57_P1_T2A_Some text is written here

W1C
Top_W1C
A_167_P1_W1C_Some text is written here
T_167_P1_W1C_Some text is written here

W2B
Top_W2B
A_26_P1_W2B_Some text is written here
T_26_P1_W2B_Some text is written here
A_183_P2_W2B_Some text is written here
T_183_P2_W2B_Some text is written here
A_69_P3_W2B_Some text is written here
T_69_P3_W2B_Some text is written here

任何人都可以指导我解决这个问题。

4

1 回答 1

0

看来您正在按下划线后的最后一部分对行进行分组。有点不清楚应该以什么顺序打印这些行(例如,如果P1_M2AP2_M2A第二个文件中出现),但下面的代码准确地给出了您提供的数据的预期输出。

它首先将 1st_file 读入哈希,记住每个 id 没有第一行的段落(_ 之后的最后一部分)。然后,它遍历第二个文件并在打印“标题”后打印记住的行。它只测试每段第三行的id,其余行被忽略。如上所述,您尚未指定如何获取 id。如果最后一部分很重要,您将不得不稍微调整代码。

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

open my $F1,  '<', '1st_file.txt' or die $!;
my %hash1;
my $num;
while (<$F1>) {
    if (my ($id) = /^[AT]_[0-9]+_.+?_(.*)/) {
        $hash1{$id} .= $_;
    }
}

open my $F2,  '<', '2nd_file.txt' or die $!;
open my $OUT, '>', '3rd_file.txt' or die $!;
while (<$F2>) {
    if (!/_/ or /^Top_/) {
        print $OUT $_;
    } else {
        if (my ($id) = /_(.*)/) {
            print $OUT $hash1{$id} if exists $hash1{$id};
            delete $hash1{$id};
        }
    }
}
close $OUT or die $!;

更新以反映您更详细的规范:

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

open my $F1,  '<', '1st_file.txt' or die $!;
my %hash1;
my $num;
while (<$F1>) {
    if (my ($id) = /^[AT]_[0-9]+_(.*)$/) {
        $hash1{$id} .= $_;
    }
}

open my $F2,  '<', '2nd_file.txt' or die $!;
open my $OUT, '>', '3rd_file.txt' or die $!;
while (<$F2>) {
    if (!/_/ or /^Top_/) {
        print $OUT $_;
    } else {
        chomp;
        print $OUT $hash1{$_} if exists $hash1{$_};
    }
}
close $OUT or die $!;
于 2013-08-11T20:49:14.633 回答