使用 Shell 脚本将类似表的文本转换为带有列名的单独值



我有一个文本文件,如下所示:

Execution ID, Unique number, Result 1, Result 2
1234567 , 1002 , Dron,  User suppressed due to Inactivity Rule
1234567 , 1002 , Dron,  User suppressed due to Wrong Email Address
2348976 , 1003 , Dron,  User suppressed due to Language Rule

我希望上面的文本像下面这样转换:

Execution ID: 1234567
Unique number: 1002
Result 1: Dron
Result 2: User suppressed due to Inactivity Rule, User suppressed due to Wrong Email Address
Execution ID: 2348976
Unique number: 1003
Result 1: Dron
Result 2: User suppressed due to Language Rule

您可以使用这样的awk来做到这一点:

awk 'BEGIN{FS=", "}NR==1{split($0, h)}NR>1{printf "%s: %sn%s: %sn%s: %sn%s: %snn",h[1],$1,h[2],$2,h[3],$3,h[4],$4}' textfile

这是一个概念证明:

$ awk -V | head -1
GNU Awk 5.0.1, API: 3.0 (GNU MPFR 3.1.6-p2, GNU MP 6.1.2)
$ cat csv 
Execution ID, Unique number, Result 1, Result 2
1234567, 1002, Dron, User suppressed due to Inactivity Rule
2348976, 1002, Dron, User suppressed due to Language Rule
$ awk 'BEGIN{FS=", "}NR==1{split($0, h)}NR>1{printf "%s: %sn%s: %sn%s: %sn%s: %snn",h[1],$1,h[2],$2,h[3],$3,h[4],$4}' csv 
Execution ID: 1234567
Unique number: 1002
Result 1: Dron
Result 2: User suppressed due to Inactivity Rule
Execution ID: 2348976
Unique number: 1002
Result 1: Dron
Result 2: User suppressed due to Language Rule
$ 

你能试试下面的吗?

awk '
BEGIN{
FS=SUBSEP=OFS=","
}
FNR==1{
split($0,header,", ")
next
}
{
a[$1,$2,$3]=(a[$1,$2,$3]?a[$1,$2,$3]":":"")$4
}
END{
for(i in a){
val=i OFS a[i]
num=split(val,array,",")
for(o=1;o<=num;o++){
print header[o],array[o]
}
delete array
}
}
' Input_file


说明:为上述代码添加详细说明。

awk '                                                     ##Starting awk program from here.
BEGIN{                                                    ##Starting BEGIN section here.
FS=SUBSEP=OFS=","                                       ##Setting FS, OFS and SUBSEP as comma here.
}                                                         ##Closing BEGIN BLOCK for this awk code.
FNR==1{                                                   ##Checking condition if this is first line then do following.
split($0,header,",")                                    ##Splitting line into an array named header whose delimiter is comma here.
next                                                    ##next will skip all further statements from here.
}                                                         ##Closing BLOCK for FNR==1 condition here.
{
a[$1,$2,$3]=(a[$1,$2,$3]?a[$1,$2,$3]":":"")$4           ##Creating an array named a whose index is $1,$2,$3 and value is $4 with concatenating each line its own value in it.
}
END{                                                      ##Starting END block for this awk code here.
for(i in a){                                            ##Traversing through array a all elements.
val=i OFS a[i]                                        ##Creating a variable val and its value is variable i(index of array a) OFS and array a value here.
num=split(val,array,",")                              ##Splitting variable val to array named array whose delimiter is comma here.
for(o=1;o<=num;o++){                                  ##Starting a for loop from o=1 to till value of num.
print header[o],array[o]                            ##Printing header array with index of o and array with index of o here.
}
delete array                                          ##Deleting array here, to avoid confusions, since each cycle new array will be created.
}
}
'  Input_file                                             ##Mentioning Input_file name here.

最新更新