代码之家  ›  专栏  ›  技术社区  ›  wolfsden3

sed命令删除与第一个单词上的字符串完全匹配的行

  •  1
  • wolfsden3  · 技术社区  · 6 年前

    我在这里找到了我问题的答案: "sed" command to remove a line that match an exact string on first word

    ...但这只是部分原因,因为只有当我的提问与对方的回答完全一致时,这个解决方案才有效。

    他们回答说:

     sed -i "/^maria\b/Id" file.txt
    

    ...只删掉一行以“maria”开头的单词,如果不是第一个单词,就不要删掉maria。

    我想在一个文件中删掉一个特定的url,例如:“cnn.com”-但是,我也有一些本地主机地址,0.0.0.0,两个都有一些,前面只有一个空格。我也不想删掉ads.cnn这样的子域名。com,这样代码“应该”工作,但当我使用-e选项输入更多命令时,代码就不工作了。我下面的代码似乎很好地解决了问题,只是我无法让它打败cnn。通用域名格式!我的文件名为raw。txt

     sed -r -e 's/^127.0.0.1//' -e 's/^ 127.0.0.1//' -e 's/^0.0.0.0//' -e 's/^ 0.0.0.0//' -e '/#/d' -e '/^cnn.com\b/d' -e '/::/d' raw.txt | sort | tr -d "[:blank:]" | awk '!seen[$0]++' | grep cnn.com
    

    当我为cnn工作时。我看到了所有的cnn,包括一个我不想要的,实际上是“cnn.com”。

     ads.cnn.com
     cl.cnn.com
     cnn.com <-- the one I don't want
     cnn.dyn.cnn.com
     customad.cnn.com
     gdyn.cnn.com
     jfcnn.com
     kermit.macnn.com
     metrics.cnn.com
     projectcnn.com
     smetrics.cnn.com
     tiads.sportsillustrated.cnn.com
     trumpincnn.com
     victory.cnn.com
     xcnn.com
    

    如果我用cnn的那一段代码。com chop out似乎有效。

     sed -r '/^cnn.com\b/d' raw.txt | grep cnn.com
     * I'm not using the "-e" option
    

    结果:

     ads.cnn.com
     cl.cnn.com
     cnn.dyn.cnn.com
     customad.cnn.com
     gdyn.cnn.com
     jfcnn.com
     kermit.macnn.com
     metrics.cnn.com
     projectcnn.com
     smetrics.cnn.com
     tiads.sportsillustrated.cnn.com
     trumpincnn.com
     victory.cnn.com
     xcnn.com
    

    当我将命令与“-e”选项组合在一起时,我所做的一切似乎都不起作用。我需要一些帮助来使用SED启动我的多选项命令。

    有什么建议吗?

    Ubuntu12 LTS&16支。
    sed(GNU sed)4.2.2

    2 回复  |  直到 6 年前
        1
  •  0
  •   JNevill    6 年前

    这个 . 是正则表达式中的元字符,意思是“匹配任何一个字符”。所以你不小心创建了一个正则表达式 cnnPcom cnn com cnn\com .虽然它可能适合您的需要,但最好更明确:

      sed -r '/^cnn\.com\b/d' raw.txt 
    

    区别在于 \ 前斜杠 . 时期它避开了句点元字符,因此被视为文字句点。


    对于以空格开头的行,可以在单个正则表达式中捕捉这些行(再次跳过句点元字符):

      sed -r '/(^[ ]*|^)127\.0\.0\.1\b/d' raw.txt
    

    (^[ ]*|^) 表示以任意数量的重复空格开头的行 ^[ ]* | ^ 接下来是你的对手是谁 127.0.0.1 .


    然后你可以使用 | 或在Paranthes内的操作员,以捕获所有匹配项:

      sed -r '/(^[ ]*|^)(127\.0\.0\.1|cnn\.com|0\.0\.0\.0)\b/d' raw.txt
    

    或者,你可以使用 ; 分号来分隔不同的正则表达式:

      sed -r '/(^[ ]*|^)127\.0\.0\.1\b/d; /(^[ ]*|^)cnn\.com\b/d; /(^[ ]*|^)0\.0\.0\.0\b/d;' raw.txt
    
        2
  •  0
  •   Ed Morton    6 年前

    sed不理解字符串上的匹配,只理解正则表达式,要让sed表现得像它一样,是非常困难的,请参见 Is it possible to escape regex metacharacters reliably with sed .要删除第一个空格分隔的单词为“foo”的行,只需执行以下操作:

    awk '$1 != "foo"' file
    

    要删除以“foo”或“bar”开头的行,只需执行以下操作:

    awk '($1 != "foo") && ($1 != "bar")' file
    

    如果你不止有几个单词,那么方法是列出所有单词并创建一个由它们索引的哈希表,然后测试行的第一个单词是否是哈希表的索引:

    awk 'BEGIN{split("foo bar other word",badWords)} !($1 in badWords)' file
    

    如果这不是你想要的,那么编辑你的问题以澄清你的需求,并包括简洁、可测试的样本输入和 这个 考虑到这些输入,预期的输出。