【问题标题】:Delete from pattern match until next pattern从模式匹配中删除直到下一个模式
【发布时间】:2019-01-31 23:52:54
【问题描述】:

在 bash 中,我有一个包含各种关键字的输入文件,有时还有以下几行的数据。我想删除以PATTERN1 开头的关键字,直到且不包括以PATTERN2 开头的行。 注意:

  • 会有多个表达式,因此-e 选项
  • 下一个*之前可能有多行

我试过 sed 之类的

sed -i.bak -e '/*FOO/,/*/d' -e '/*BAR/,/*/d $FILE

但这会删除*KEEP 行。

**START
*FOO
This wants to be deleted
*KEEP
*BAR
this also wants to be deleted
*KEEP
**END

应该变成

**START
*KEEP
*KEEP
**END

提前感谢您查看此问题

【问题讨论】:

    标签: bash awk sed


    【解决方案1】:

    使用awk 更容易做到这一点:

    awk '/^*/{d = 0} /^*(FOO|BAR)/{d = 1} !d' file
    

    *START
    *KEEP
    *KEEP
    **END
    

    如果您使用gnu awk,则使用-i inplace 以内联方式保存更改:

    awk -i inplace '/^*/{d = 0} /\*(FOO|BAR)/{d = 1} !d' file
    

    如果不使用gnu awk,则使用:

    awk '/^*/{d = 0} /^*(FOO|BAR)/{d = 1} !d' file > $$.tmp && mv file $$.tmp
    

    【讨论】:

    • 好的,谢谢。我确实必须添加 -v RS 才能停止 awk 将 ^M 添加到行尾
    • awk 不会将^M 添加到行尾。如果它们在您的输出中,那是因为它们在您的输入中。
    • 确实如此。该文件确实来自 Windows 应用程序,因此 ^M 已经存在。
    【解决方案2】:

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

    sed '/^*/h;G;/^*\(FOO\|BAR\)/M!P;d' file
    

    将每个键在其呈现时存储在保持空间中并将其附加到当前行。如果不包含以*FOO*BAR 开头的行,则打印模式空间中两行中的第一行。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-04-10
      • 2015-05-07
      • 2019-06-18
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多