如何用sed替换一部分线?

时间:2016-03-08 07:32:06

标签: regex bash sed

我有一个包含许多行的文件(行分隔符是〜)。每一行,我都有许多元素,这些元素由分隔符分隔。*'。 我想做的是,  我将在我的文件中有一个以字符串TRN开头的行。它可以包含4个(包括TRN)或更多数据点。像,

TRN*1*S521000035*1020494919~
TRN*1*S521000035*1020494919*787989800~

我想将这行中的第四个数据点替换为abc123。即,

TRN*1*S521000035*abc123~
TRN*1*S521000035*abc123*787989800~

我尝试使用带有正则表达式的sed命令

sed -i 's/^TRN\*(.*)\*(.*)\*(.*)$/abc123/g' file.txt 

但是整个字符串都被替换为abc123。

是否可以使用sed命令仅更改其第4个数据点?

5 个答案:

答案 0 :(得分:2)

sed 是你的朋友。

试试这个测试版本:

$ sed "s/^\(TRN[*][^*][^*]*[*][^*][^*]*[*]\)[^*][^*]*\(.*~\)/\1abc123\2/" afile.txt
TRN*1*S521000035*abc123~
TRN*1*S521000035*abc123*787989800~

您可能需要阅读手册页以获取有关正则表达式 sed

的更多详细信息

答案 1 :(得分:2)

使用GNU sed:

$ sed -r -i 's/^((\w+\*){3})\w*(.*)/\1abc123\3/g' file.txt

输出:

TRN*1*S521000035*abc123~
TRN*1*S521000035*abc123*787989800~ 

答案 2 :(得分:1)

这可能适合你(GNU sed):

sed 's/[^*~]\+/abc123/4' file

使用~替换第四次出现的不包含*abc123的内容。

答案 3 :(得分:0)

AWK应该以非常简洁和可读的方式完成这个技巧。 FS会更改字段分隔符,以便您可以确定要在行内打破的位置。

$ awk 'BEGIN { FS="*|~" }{ sub($4, "abc123"); print $0}' file.txt

TRN*1*S521000035*abc123~
TRN*1*S521000035*abc123*787989800~

答案 4 :(得分:0)

虽然您可以使用 sed 执行此操作,但使用 awk 可以更轻松地实现所需的效果。程序 awk 对于分析和转换表格结构数据特别有用,例如:

awk -F'*' -v OFS='*' '{$4 = "abc123"; print}'

这是:

awk         Run the program awk
 -F'*'      Use the * as a field delimiter on input
 -v OFS='*' Use the * as a field delimiter on output
 '{         On each record …
   $4 = "abc123";
            … set the 4th field to "abc123"
   print
            … and print the curent record
  }'

根据其他字段的值,也可以轻松扩展该示例以有选择地替换第4个字段。