繁体   English   中英

在 bash 脚本中使用 sed 替换多行

[英]Replace multiple lines using sed in a bash script

我有一个多行的文件。 我正在寻求帮助以仅修改与正则表达式模式匹配的这些行,然后在每个结果之后添加一些文本。 我用的是mac,但是bash脚本会在linux上运行,我不知道它是否相关。

IE

someText
StringToSearch:
    | isoCode |

someOthertext
StringToSearch:
    | isoCode |

againSomOtherText
StringToSearch:
    | isoCode |

在匹配“ StringToSearch: ”之后,我需要在每个“ | isoCode | ”之后添加“ | uk | ”,因此结果将类似于:

someText
StringToSearch:
    | isoCode |
    | uk |

someOtherText
StringToSearch:
    | isoCode |
    | uk |

againSomeOtherText
StringToSearch:
    | isoCode |
    | uk |

我的正则表达式是^\s*StringToSearch:\n[^\n]+完整的工作示例可在 regex101 以下链接

我不知道如何使用 sed 在 bash 中实现它。

实际上我的 sed 看起来像这样: sed -E 's,\^\s*StringToSearch:\n\([^\n]+\),| uk |,' < inputFile sed -E 's,\^\s*StringToSearch:\n\([^\n]+\),| uk |,' < inputFile

$ awk '1; p~/StringToSearch/ && /isoCode/{print "    | uk |"} {p=$0}' ip.txt
someText
StringToSearch:
    | isoCode |
    | uk |

someOthertext
StringToSearch:
    | isoCode |
    | uk |

againSomOtherText
StringToSearch:
    | isoCode |
    | uk |
  • 一种打印包含当前记录的$0 1的惯用方式
  • {p=$0}将当前记录保存在p变量中
  • p~/StringToSearch/ && /isoCode/检查上一行是否包含StringToSearch和当前行是否包含isoCode
    • 如果条件满足, print " | uk |" 将添加您需要的新内容

据我所知,这应该适用于awk的所有版本。 所以mac/linux不会影响你。


如果你坚持sed ,你可以使用

sed '/StringToSearch/{N; s/$/\n    | uk |/}' ip.txt

我在GNU sed上进行了测试,但不确定语法/功能是否随其他实现而变化。 N命令将下一行输入添加到当前模式空间。 s/$/\n | uk |/ s/$/\n | uk |/将在两行之后添加新内容。 sed在不使用-n选项时默认打印模式空间。

sed -E 's,\^\s*StringToSearch:\n\([^\n]+\),| uk |,'
  • \(...\)将反向引用保存在常规正则表达式中。 在扩展正则表达式中使用(...) 此外,您不要在任何地方使用反向引用。
  • \n - sed解析一行 所以它不能匹配\n ,除非你 append 多行使用N个命令来模式空间。
  • \^很奇怪——它匹配一个^字符。 你的文字中没有这样的字符......

您可以使用-z选项轻松匹配多行与 GNU sed 请注意,它将整个文件加载到sed s memory 中,因此它将消耗 memory。 然后编写一个适当的正则表达式,它将全局匹配您的表达式。

也不要删除替换的字符串,使用&重新恢复它。 然后在它后面加上你要添加的字符串。

命令:

$ sed -z -E 's,\nStringToSearch:\n[^\n]+\n,&    | uk |\n,g' <<EOF
someText
StringToSearch:
    | isoCode |

someOthertext
StringToSearch:
    | isoCode |

againSomOtherText
StringToSearch:
    | isoCode |
EOF

输出:

someText
StringToSearch:
    | isoCode |
    | uk |

someOthertext
StringToSearch:
    | isoCode |
    | uk |

againSomOtherText
StringToSearch:
    | isoCode |
    | uk |

使用sed

sed -e '/^[[:space:]]*StringToSearch:/{' -e n -e n -e 'i\
\ \ \ \ | uk |' -e '}' file > outputfile

Output:

someText
StringToSearch:
    | isoCode |
    | uk |

someOthertext
StringToSearch:
    | isoCode |
    | uk |

againSomOtherText
StringToSearch:
    | isoCode |
    | uk |

这将匹配任何带有可选空格和StringToSearch:的行,然后-en -en将读取两行并清除模式空间,然后-e 'i\ \ \ \ \ | uk | -e 'i\ \ \ \ \ | uk | 将插入您选择的一行,并且-e '}'将关闭该块。

这可能对您有用(GNU sed):

sed '/StringToSearch/{n;p;s/[^| ]\+/uk/}' file

匹配包含StringToSearch的行。

打印该行并获取下一行。

打印该行并用uk代替 isoCode(该行也将作为正常 sed 流程的一部分打印)。

这里演示。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM