在对那些字符串执行正则表达式操作之后,试图将两个多行字符串合并为一个字符串时遇到了一些问题。例如,我以这种形式的数据开始:
TMS:xxxxxxx11110000
TDI:xxxxxxx00001111
TMS:xxxx00001111
TDI:xxxx11110000
要以我需要的形式获取它,我在文件中搜索关键字“ TMS:”,仅提取数据,使用正则表达式删除“ x”,反转数据,然后将每个位放在自己的一行并将其存储在字符串中。结果字符串如下所示:
0
0
0
0
1
1
1
1
然后,我在文件中搜索“ TDI:”并重复相同的过程。最后一步是将第一个字符串与第二个字符串连接起来,以得到以下输出(鉴于上面的示例):
01
01
01
01
10
10
10
10
10
10
10
10
01
01
01
01
但是,当我连接两个字符串时,我现在作为输出得到的是
0
0
0
0
1
1
1
1
1
1
1
1
0
0
0
0
1
1
1
1
0
0
0
0
0
0
0
0
1
1
1
1
是否可以在不对过程进行太多更改的情况下获得所需的结果?我试过使用split命令,chomp命令等,但没有任何运气。
答案 0 :(得分:1)
最好有一个简单的示例,看看您如何解决此问题。此外,关于输入文件还有很多不清楚的地方。例如,TMS
和TDI
是否始终在文件中配对,还是必须检查?您是否总是将下一个TDI
实例与前面的TMS
事件配对,还是可以使其更脱节? TMS
始终位于TDI
之前还是可以颠倒?
一种简单的方法是,假设数据看起来像示例中所示,可能是读取每一行并将数据存储在TMS
字符串的一个数组中,并将数据存储在一个数组中。 TDI
字符串。如果两个数组都已满,则需要一对输出,因此输出该对并清除数组以备下一个事件使用。否则,请阅读下一行以获取TDI
数据:
#!/usr/bin/env perl
use strict;
use warnings;
my (@first, @second);
while (my $elem = <DATA>) {
($elem =~ /^TMS/)
? (@first = read_string($elem))
: (@second = read_string($elem));
if (@second) {
for my $index (0..$#first) {
print "$first[$index]$second[$index]\n";
}
print "\n";
@first = @second = ();
}
}
sub read_string {
my $string = shift;
my @bits = grep {/\d/} split('', $string);
return reverse(@bits);
}
__DATA__
TMS: xxxxxxx11110000
TDI: xxxxxxx00001111
TMS: xxxx00001111
TDI: xxxx11110000
此输出将是:
01
01
01
01
10
10
10
10
10
10
10
10
01
01
01
01
答案 1 :(得分:1)
您想要的是一个zip操作。方便地List::MoreUtils为您提供了一个。
@x = qw/a b c d/;
@y = qw/1 2 3 4/;
# returns [a, 1], [b, 2], [c, 3], [d, 4]
@z = zip6 @x, @y;
要获取zip的输入,请首先将结果放入数组中,或者拆分输入字符串。
答案 2 :(得分:0)
hobbs答案正在解决一个完全不同的问题,但是部分解决方案是关于如何“旋转”多行字符串,在这里可能很有用。
首先,不要将每个位放在自己的行上,只需将不同行上不同输入行的位分开即可。将多行字符串放入$_
。
$_ = '0000111111110000
1111000000001111';
现在执行以下代码:
$_ = do {
my $o;
$o .= "\n" while s/^./$o.=$&,""/meg;
$o };
(霍布斯算法中的替换以s/.$/.../
开始。通过使用s/^./.../
,它成为用于转置而不是旋转的算法)
输入:
$_ = '0000111111110000
1111000000001111';
输出:
01
01
01
01
10
10
10
10
10
10
10
10
01
01
01
01
该算法可以轻松地将其推广到输入中任意数量的行和列。
输入:
$_='ABCDE
12345
FGHIJ
67890';
输出:
A1F6
B2G7
C3H8
D4I9
E5J0