问题描述
我是perl的新手,我需要在找到关键字(匹配项)后通过添加一些文本来编辑文本文件,我需要将更改保存在同一文件中,但保留所有旧信息,而不覆盖任何内容。
即使文件中的其他数据发生变化,关键字(匹配)和我要添加的信息也会保持不变。
To make a summary:
data that will change (not interested)
...
empty spaces < DATA >B506JGHD (< DATA > it would be the keyword(match) and i want to add for example 00000001 after it)
output that I need:empty spaces< DATA >00000001B506JGHD
...
empty spaces< DATA >J6443MNF
output:empty spaces< DATA >00000002J6443MNF
...
empty spaces< DATA >C89583F
output:empty spaces< DATA >00000003C89583F
...
other data (not interested)
依此类推,这就像文件中的7 ,所以我想为每个添加00000000到00000006。
我正在寻找一个简单的解决方案(如果存在),我知道我可能需要阅读并遍历文本文件,找到关键字并重写所有内容,但是我不确定如何做到这一点。
What I tried so far is this:
use strict;
use warnings;
open FILE,"<FL_85E920795_Y060_H21_V001_E.odx" or die $!;
my @lines = < FILE >;
close FILE or die $!;
my $idx = 0;
my $string = '00000000';
do {
if($lines[$idx] =~ /< DATA >/)
{
splice @lines,$idx,$string++;
$idx++;
}
$idx++;
} until($idx >= @lines);
open FILE,">FL_85E920795_Y060_H21_V001_E.odx" or die $!;
print FILE join("",@lines);
close FILE;
但是对我没有太大帮助,因为我的输出是这样的: 00000000空格信息,如果我尝试将所需的数据移到之前,它将覆盖所有内容。
解决方法
#!/usr/bin/perl
use strict;
use warnings;
my $counter = "00000000";
while (<>) {
s{< DATA >\K}{ $counter++ }eg;
print;
}
用法:
fn=FL_85E920795_Y060_H21_V001_E.odx
the_script "$fn" >"$fn".new
mv "$fn".new "$fn"
\K
“保留”与\K
匹配的内容,因此仅将< DATA >
之后的空字符串替换为替换表达式返回的值。
“单线”:
perl -i -pe'BEGIN { $c = "00000000" } s{< DATA >\K}{ $c++ }eg' \
FL_85E920795_Y060_H21_V001_E.odx
,
所需的结果可以通过以下演示代码来实现
注意:
- 此解决方案将整个文件读取到内存中
- 如果文件太大,最好逐行读取方法
use strict;
use warnings;
use feature 'say';
my $count = 0;
my $re_match = qr/< DATA >/;
my $data = do { local $/; <DATA> };
$data =~ s/$re_match/sprintf "%08d",$count++/ge;
say $data;
__DATA__
To make a summary:
data that will change (not interested)
...
empty spaces < DATA >B506JGHD (< DATA > it would be the keyword(match) and i want to add for example 00000001 after it)
output that I need:empty spaces< DATA >00000001B506JGHD
...
empty spaces< DATA >J6443MNF
output:empty spaces< DATA >00000002J6443MNF
...
empty spaces< DATA >C89583F
output:empty spaces< DATA >00000003C89583F
...
other data (not interested)
输出
To make a summary:
data that will change (not interested)
...
empty spaces 00000000B506JGHD (00000001 it would be the keyword(match) and i want to add for example 00000001 after it)
output that I need:empty spaces0000000200000001B506JGHD
...
empty spaces00000003J6443MNF
output:empty spaces0000000400000002J6443MNF
...
empty spaces00000005C89583F
output:empty spaces0000000600000003C89583F
...
other data (not interested)