使用sed与分隔符相似的分隔符

时间:2017-06-30 01:53:42

标签: bash macos shell awk sed

给定包含文件名的文件foo.txt,例如:

2015_275_14_1,Siboney_by_The_Tailor_Maids
2015_275_16_1,Louis_Armstrong_Cant_Give_You_Anything_But_Love
2015_275_17_1,Benny_Goodman_Trio_Nice_Work_Avalon
2015_275_18_1,Feather_On_Jazz_Jazz_In_The_Concert_Hall
2015_235_1_1,Integration_Report_1
2015_273_2_1_1,Cab_Calloway_Home_Movie_1
2015_273_2_2_1,Cab_Calloway_Home_Movie_2

我希望将逗号前面的_替换为逗号.,将第二部分中的_替换为空格后的逗号。

我可以通过以下方式单独完成:

sed -E -i '' 's/([0-9]{4})_([0-9]{3})_([0-9]{2})_([0-9])/\1.\2.\3.\4./'

表示第一部分,第二部分表示:

sed -E -i '' "s/_/ /g"

但我希望通过使用sed切割以更简单的方式实现它,但这不起作用:

cut -d "," -f 1 foo.txt | sed -E -i '' "s/_/./g" foo.txt && cut -d "," -f 2 foo.txt | sed -E -i '' "s/_/ /g" foo.txt

不好。

那么,有没有办法通过sedawk或者其他我可以将,视为分隔符的其他内容来完成此操作,例如在{{1}中}?

期望的输出:

cut

5 个答案:

答案 0 :(得分:2)

您可以使用awk来实现目标,这是方法。

$ awk -F',' '{gsub(/_/,".",$1);gsub(/_/," ",$2);printf "%s,%s\n",$1,$2}' file                                                                                                    
2015.275.14.1,Siboney by The Tailor Maids
2015.275.16.1,Louis Armstrong Cant Give You Anything But Love
2015.275.17.1,Benny Goodman Trio Nice Work Avalon
2015.275.18.1,Feather On Jazz Jazz In The Concert Hall
2015.235.1.1,Integration Report 1
2015.273.2.1.1,Cab Calloway Home Movie 1
2015.273.2.2.1,Cab Calloway Home Movie 2

答案 1 :(得分:1)

您可以cutpaste

$ paste -d, <(cut -d, -f1 infile | sed 'y/_/./') <(cut -d, -f2 infile | sed 'y/_/ /')
2015.275.14.1,Siboney by The Tailor Maids
2015.275.16.1,Louis Armstrong Cant Give You Anything But Love
2015.275.17.1,Benny Goodman Trio Nice Work Avalon
2015.275.18.1,Feather On Jazz Jazz In The Concert Hall
2015.235.1.1,Integration Report 1
2015.273.2.1.1,Cab Calloway Home Movie 1
2015.273.2.2.1,Cab Calloway Home Movie 2

进程替换<()允许您将命令的输出视为文件,并且paste -d,并排粘贴每个命令的输出,用逗号分隔。

sed y命令音译字符,在这种情况下,等同于s/_/./g。和s/_/ /g

你也可以纯粹用sed做,但它有点笨拙:

sed 'h;s/.*,//;y/_/ /;x;s/,.*//;y/_/./;G;s/\n/,/' infile

说明:

h         # Copy pattern space to hold space
s/.*,//   # Remove first part including comma
y/_/ /    # Replace all "_" by spaces in the remaining second part
x         # Swap pattern and hold space
s/,.*//   # Remove second part including comma
y/_/./    # Replace all "_" by periods in the remaining first part
G         # Append hold space to pattern space
s/\n/,/   # Replace linebreak with comma

或者,(来自potong的评论):

sed 's/,/\n/;h;y/_/ /;x;y/_/./;G;s/\n.*\n/,/'  infile

说明:

s/,/\n/      # Replace comma by linebreak
h            # Copy pattern space to hold space
y/_/ /       # Replace all "_" by spaces
x            # Swap pattern and hold space
y/_/./       # Replace all "_" by periods
G            # Append hold space
s/\n.*\n/,/  # Remove second and third line in pattern space

答案 2 :(得分:1)

@CWLiu的答案类似,但我使用OFS(输出字段分隔符),而不是在逗号中添加,并且必须使用printf添加换行符。

awk -F ',' 'BEGIN {OFS = FS} {gsub(/_/, ".", $1); gsub(/_/, " ", $2); print;}' foo.txt

说明:

-F ','设置字段分隔符

BEGIN {OFS = FS}设置输出字段分隔符(默认空格)等于字段分隔符,以便打印出逗号

第一栏

gsub(/_/, ".", $1)全局替换

第二列

gsub(/_/, " ", $2)全局替换

print打印整行

答案 3 :(得分:1)

$ awk 'BEGIN{FS=OFS=","} {gsub(/_/,".",$1); gsub(/_/," ",$2)} 1' file
2015.275.14.1,Siboney by The Tailor Maids
2015.275.16.1,Louis Armstrong Cant Give You Anything But Love
2015.275.17.1,Benny Goodman Trio Nice Work Avalon
2015.275.18.1,Feather On Jazz Jazz In The Concert Hall
2015.235.1.1,Integration Report 1
2015.273.2.1.1,Cab Calloway Home Movie 1
2015.273.2.2.1,Cab Calloway Home Movie 2

答案 4 :(得分:1)

试试GNU sed

$ cat input.txt 
2015_275_14_1,Siboney_by_The_Tailor_Maids
2015_275_16_1,Louis_Armstrong_Cant_Give_You_Anything_But_Love
2015_275_17_1,Benny_Goodman_Trio_Nice_Work_Avalon
2015_275_18_1,Feather_On_Jazz_Jazz_In_The_Concert_Hall
2015_235_1_1,Integration_Report_1
2015_273_2_1_1,Cab_Calloway_Home_Movie_1
2015_273_2_2_1,Cab_Calloway_Home_Movie_2
$ sed -r ':loop;/^[^_]+,/{s/_/ /g;bend};s/_/./;bloop;:end' input.txt
2015.275.14.1,Siboney by The Tailor Maids
2015.275.16.1,Louis Armstrong Cant Give You Anything But Love
2015.275.17.1,Benny Goodman Trio Nice Work Avalon
2015.275.18.1,Feather On Jazz Jazz In The Concert Hall
2015.235.1.1,Integration Report 1
2015.273.2.1.1,Cab Calloway Home Movie 1
2015.273.2.2.1,Cab Calloway Home Movie 2

说明:

  1. 使用s/_/./_替换为.,直到_之前的所有,被替换为^[^_]+,; < / LI>
  2. 然后,如果^[^_]+,匹配,请s/_/ /g之后使用_将所有替换为,