Bash 将所有单词合并成一行,以分号分隔(AWK | SED)
大家好,需要帮忙。作为文件的curl输出,我有以下内容:Bash 将所有单词合并成一行,以分号分隔(AWK | SED),bash,awk,sed,merge,Bash,Awk,Sed,Merge,大家好,需要帮忙。作为文件的curl输出,我有以下内容: FINISHED JOB#1 20140428 0016 FINISHED JOB#2 20140428 0015 有没有办法通过以下方式合并这些行: JOB#1;0015;20140428;FINISHED JOB#2;0016;20140428;FINISHED JOB#3;0017;20140428;FINISHED 等等 我试过: paste -d, -s filenew.com awk-f formatter.awk输入文
FINISHED
JOB#1
20140428 0016
FINISHED
JOB#2
20140428 0015
有没有办法通过以下方式合并这些行:
JOB#1;0015;20140428;FINISHED
JOB#2;0016;20140428;FINISHED
JOB#3;0017;20140428;FINISHED
等等
我试过:
paste -d, -s filenew.com
awk-f formatter.awk输入文件
awk-f formatter.awk输入文件带有gawk
(GNU-awk)或mawk
:
awk -v RS='FINISHED' -v OFS=';' '$0 { print $1, $3, $2, RS }' file
遗憾的是,这不适用于FreeBSD/OSXawk
或严格兼容POSIX的版本,因为它们不支持多字符输入记录分隔符(RS
)。与gawk
(GNU awk)或mawk
:
awk -v RS='FINISHED' -v OFS=';' '$0 { print $1, $3, $2, RS }' file
遗憾的是,这不适用于FreeBSD/OSX
awk
或严格兼容POSIX的版本,因为它们不支持多字符输入记录分隔符(RS
)。Serg12,我假设您有一个输入错误,您的意思是输出应该是:
JOB#1;0016;20140428;FINISHED
JOB#2;0015;20140428;FINISHED
i、 e、0016在第一行,0015在第二行。使用sed,您还可以执行以下操作:
sed -n "/FINISHED/ n;h;N;s/\(.*\)\n\(.*\) \(.*\)/\1;\3;\2;FINISHED/p" file
希望有帮助。Serg12,我假设您有一个输入错误,您的意思是输出应该是:
JOB#1;0016;20140428;FINISHED
JOB#2;0015;20140428;FINISHED
i、 e、0016在第一行,0015在第二行。使用sed,您还可以执行以下操作:
sed -n "/FINISHED/ n;h;N;s/\(.*\)\n\(.*\) \(.*\)/\1;\3;\2;FINISHED/p" file
希望对您有所帮助。这里是一个简单、便携的
awk
版本:
awk '/^2014/ {print x,$2,$1,y} {y=x;x=$0}' OFS=";" file
JOB#1;0016;20140428;FINISHED
JOB#2;0015;20140428;FINISHED
以下是一个简单、便携的
awk
版本:
awk '/^2014/ {print x,$2,$1,y} {y=x;x=$0}' OFS=";" file
JOB#1;0016;20140428;FINISHED
JOB#2;0015;20140428;FINISHED
这是另一个变体
tr \n' ';' <file | sed 's/\(;FINISHED\);/\1\n/g'
tr\n'';' 这是另一个变体
tr \n' ';' <file | sed 's/\(;FINISHED\);/\1\n/g'
tr\n'';' 这可能适用于您(GNU-sed):
一次读3行并重新安排内容。这可能适合您(GNU-sed):
一次读入3行并重新排列内容。posix awk支持getline
因此:
$ awk --posix -v OFS=';' '
{Status = $0; getline Job; getline; Date = $1; Time = $2;
print Job, Time, Date, Status;}' file.txt
JOB#1;0016;20140428;FINISHED
JOB#2;0015;20140428;FINISHED
posix awk支持getline
so:
$ awk --posix -v OFS=';' '
{Status = $0; getline Job; getline; Date = $1; Time = $2;
print Job, Time, Date, Status;}' file.txt
JOB#1;0016;20140428;FINISHED
JOB#2;0015;20140428;FINISHED
请展示你试过的东西。使用awk
应该很简单。我使用了paste-d,-s myfile.txt,但它只是将所有行合并到一个paste
中,用于组合来自多个输入文件的行。我认为一次输入没有任何用处。FINISHED
在输入中是第一位的,但在输出中是最后一位的?没错,FINISHED是第一位的,在输入中是一个单独的行,与下面的两行相关:job#、date和sequences请显示您尝试了什么。使用awk
应该很简单。我使用了paste-d,-s myfile.txt,但它只是将所有行合并到一个paste
中,用于组合来自多个输入文件的行。我认为一次输入没有任何用处。FINISHED
在输入中是第一位的,但在输出中是最后一位的?没错,FINISHED是第一位的,是输入中与以下两行相关的单独一行:job#,date和sequences这不起作用,因为结束
块中的$0
不会完成
;你可以用一个文字替换它“FINISHED
”。这不起作用,因为END
块中的$0
不会FINISHED
;对于不依赖于非POSIX扩展的解决方案,您可以通过将其替换为文字“FINISHED
”+1来欺骗它,但您可以简化它:(a)无需初始化变量,因此您可以不使用BEGIN
块(也可以不使用空的END
块)。(b) 不需要变量ff1
和ff2
,因为它们只在一个块中使用-直接使用$1
和$2
。(c) 利用多变量分配(例如,finished=job=”“
)。这给了我们:awk'{if(finished==“”){finished=$0;next}if(job==“”){job=$0;next}printf(“%s;%s;%s;%s;%s\n”,job,$2,$1,finished);finished=job=“”}inputfile
+1,用于不依赖非POSIX扩展的解决方案,但您可以简化它:(a)无需初始化变量,因此,您可以不使用开始
块(也可以不使用空的结束
块)。(b) 不需要变量ff1
和ff2
,因为它们只在一个块中使用-直接使用$1
和$2
。(c) 利用多变量分配(例如,finished=job=”“
)。这给了我们:awk'{if(finished==“”){finished=$0;next}if(job==“”){job=$0;next}printf(“%s;%s;%s;%s;%s\n”,job,$2,$1,finished);finished=job=“”}输入文件
+1;如果您使用-E
而不是-r
,它也可以在FreeBSD/OSX上工作。+1;如果您使用-E
而不是-r
,它也可以在FreeBSD/OSX上工作。+1,但是严格遵循POSIX标准的awk
不支持--POSIX
:)(例如,FreeBSDawk
会受此限制;如果您省略--POSIX
,它似乎可以正常工作)@mklement0——posix
用于概念验证。我没有访问其他发行版的权限来检查它。+1,但是严格遵循POSIX的awk
不支持--POSIX
:)(例如,FreeBSDawk
会被它卡住;如果你省略--POSIX
,它似乎工作得很好)@mklement0--POSIX
是为了概念验证。我没有访问其他发行版的权限来检查它。很聪明,但我建议使用awk'/^[0-9][0-9][0-9][0-9]/{print x,$2,$1,y}{y=x;x=$0}'OFS=“;”文件
这样它明年也能工作:)(我避免了[0-9]{4}
,因为在GNUawk
4
中需要-re-interval>@mklement0或仅仅是/^20[0-9][0-9]/
,将覆盖100年。很聪明,但我建议使用awk'/^[0-9][0-9][0-9][0-9]/{print x,$2,$1,y}{y=x;x=$0}of s=“;”文件
,这样它明年也能工作:)(我避免了[0-9]{4}
,因为在GNUawk
4
中需要--re interval
选项。)@mklement0或只需/^20[0-9][0-9]/
即可覆盖100年。