Linux SED-保留空间-所有行都有一个值
我想使用sed转换文件。源文件具有以下格式(“deviceId”是占位符):Linux SED-保留空间-所有行都有一个值,linux,bash,text,sed,sh,Linux,Bash,Text,Sed,Sh,我想使用sed转换文件。源文件具有以下格式(“deviceId”是占位符): 创建数据库“deviceId”; 列值=88i 144513768000000 列值=68i 14451376200000000 列值=80i 1445137560000000 列值=39i 1445137500000000 转换后,应具有以下格式: 使用数据库“db”; 系列,设备=deviceId列=88i 144513768000000 系列,设备=deviceId列=68i 14451376200000000
创建数据库“deviceId”;
列值=88i 144513768000000
列值=68i 14451376200000000
列值=80i 1445137560000000
列值=39i 1445137500000000
转换后,应具有以下格式:
使用数据库“db”;
系列,设备=deviceId列=88i 144513768000000
系列,设备=deviceId列=68i 14451376200000000
系列,设备=deviceId列=80i 1445137560000000
系列,设备=deviceId列=39i 1445137500000000
但是我不明白,我怎样才能在每一行中都得到设备ID。我当前的sed.txt
包含以下代码:
s/^\(创建数据库“*”;\)$/使用数据库“db”/G
s/\(.*\).=\(.*\)\(.*\)/系列,设备=\1=\2\3/g
并生成以下输出:
USE DATABASE "db";
series,device= column=88i 1445137680000000000·
series,device= column=68i 1445137620000000000
series,device= column=80i 1445137560000000000
series,device= column=39i 1445137500000000000
有人能解释一下我是如何在每一行中获得设备ID的吗?我已经看到了使用保持空间/流动工作的可能性。我已经试过了,但我不知道该怎么做
谢谢大家! 试试这个
#!/usr/bin/perl
use strict;
use warnings;
my $deviceId = "";
while( my $line = <STDIN>) {
chomp($line);
if($line =~ m/CREATE DATABASE/) {
$deviceId = $line;
$deviceId =~ s/CREATE DATABASE "(.*)"/$1/;
print('USE DATABASE "db";' . "\n");
}
else {
$line =~ s/(.*) .*=(.*) (.*)/series,device=$deviceId $1=$2 $3\n/g;
print($line);
}
}
#/usr/bin/perl
严格使用;
使用警告;
我的$deviceId=“”;
while(我的$line=){
chomp($line);
如果($line=~m/CREATE DATABASE/){
$deviceId=$line;
$deviceId=~s/创建数据库“(.*)”/$1/;
打印('使用数据库“db”'。“\n”);
}
否则{
$line=~s/(.*)。*=(.*)(.*)/系列,device=$deviceId$1=$2$3\n/g;
打印(行);
}
}
您试图使用错误的工具。我希望你能想出一些神奇的符文来迫使sed产生你想要的输出,为了软件的健壮性、可移植性、简单性、效率和几乎所有其他可取的属性,除了在各行上进行简单的替换之外,用于任何事情的标准UNIX工具是awk:
$ awk -F'["=]' '
NR==1{dev=$(NF-1); $0 = "USE DATABASE \"db\""}
NR>1 {$0 = "series,device=" dev " column=" $2}
1' file
USE DATABASE "db"
series,device=deviceId column=88i 1445137680000000000
series,device=deviceId column=68i 1445137620000000000
series,device=deviceId column=80i 1445137560000000000
series,device=deviceId column=39i 1445137500000000000
这可能适用于您(GNU-sed):
这将在保持空间(HS)中存储第一行。将第一行更改为所需格式。然后在第一行之后的每一行上:追加存储的第一行,并使用模式匹配和反向引用将该行转换为所需的格式。我不经常使用保持缓冲区,因此我想为实践提供一个sed解决方案:
/^CREATE/ {
# strip everything surrounding deviceId
s/[^"]*"\([^"]*\).*/\1/
# copy to the hold buffer
h
# replace pattern buffer with USE ...
s/.*/USE DATABASE "db";/
}
/^column/ {
# append the hold space to the pattern buffer
# this adds a leading newline which we'll use to capture deviceId
G
# capture the 1st field, value of the 2nd, the 3rd field,
# then the appended deviceId after the newline
s/\([^ ]*\) .*=\([^ ]*\) \(.*\)\n\(.*\)/series,device=\4 \1=\2 \3/
}
谢谢,但那不是我需要的
\3
只是当前行的时间戳。我需要的是第一行的deviceId。是否需要sed?
/^CREATE/ {
# strip everything surrounding deviceId
s/[^"]*"\([^"]*\).*/\1/
# copy to the hold buffer
h
# replace pattern buffer with USE ...
s/.*/USE DATABASE "db";/
}
/^column/ {
# append the hold space to the pattern buffer
# this adds a leading newline which we'll use to capture deviceId
G
# capture the 1st field, value of the 2nd, the 3rd field,
# then the appended deviceId after the newline
s/\([^ ]*\) .*=\([^ ]*\) \(.*\)\n\(.*\)/series,device=\4 \1=\2 \3/
}