【问题标题】:How to find and replace items not preceded or followed by specific characters with sed?如何使用 sed 查找和替换未在特定字符之前或之后的项目?
【发布时间】:2013-11-30 09:04:36
【问题描述】:

如何限制查找和替换以替换项目,但如果紧接在它之前的字符是“A”、“B”或“C”或紧随其后的字符是“X”、“Y”,则不能,或“Z”。例如。给定这些输入行,如果要将“cat”替换为“pet”:

  • “有一只猫。” → “这是一只宠物。”
  • “有 Acat。”没有改变,因为之前找到了“A”。
  • “有猫。”没有改变,因为“Y”是在后面找到的。
  • “有 CcatX。”没有改变,因为“C”出现在前面,“X”出现在后面。

【问题讨论】:

    标签: bash replace sed


    【解决方案1】:

    这个 sed 应该适合你:

    sed -r 's/(^|[^ABC])cat\>/\1pet/g; s/\<cat([^XYZ]|$)/pet\1/g' file
    

    测试:

    sed -r 's/(^|[^ABC])cat\>/\1pet/g; s/\<cat([^XYZ]|$)/pet\1/g' <<< 'cat is a cat is a cat'
    pet is a pet is a pet
    

    【讨论】:

    • cat is a cat is a cat测试。
    • @cforbish:我用那个输入进行了测试,得到:pet is a pet is a pet
    • 我收到pet is a cat is a pet。反正我投了你一票。
    【解决方案2】:

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

    sed 's/\bcat\b/pet/g' file
    

    或:

    sed 's/\<cat\>/pet/g' file
    

    或根据 cmets:

    sed -r 's/(\b|[^ABC])cat(\b|[^XYZ])/\1pet\2/g' file
    

    【讨论】:

    • 根据 OP "there are cats" 应该变成 "there are pets" 但这不会这样做。
    【解决方案3】:

    假设您的文本位于名为text.txt 的文件中。这将起作用:

    sed -i 's/\(.*[^ABC]\|^\)cat\([^XYZ].*\|$\)/\1pet\2/g' text.txt
    

    发生了什么(来自tutorialspoint.comman sedsed regex):

    -i         Edit files in place (makes backup if extension supplied)
    s/???/???/ Or s/regexp/replacement/, Attempt to match regexp against the pattern space.
    /          Field separator to 's'.
    ^          Match first character on line.
    \(         Start back reference.
    .          Match any character.
    [^ABC]     Do not match any charcter (^ = don't) in this list.
    \|         Matches regex1 or regexp2 (do not match ABC or match start of line).
    \)         End back reference.
    cat        Match cat
    \1         The first back reference.
    \2         The second back reference.
    g          Replace all matches, not just the first match.
    

    【讨论】:

    • 测试输入cat is a cat
    【解决方案4】:

    使用 可能是一个更好的主意,因为它支持前瞻/后瞻:

    perl -lape 's/(?<![ABC])cat(?![XYZ])/pet/' input
    

    【讨论】:

      猜你喜欢
      • 2015-09-03
      • 1970-01-01
      • 2017-02-21
      • 1970-01-01
      • 2020-08-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-11-13
      相关资源
      最近更新 更多