【问题标题】:VI delete everything except a patternVI 删除除图案外的所有内容
【发布时间】:2016-04-10 18:33:35
【问题描述】:

我有一个巨大的 JSON 输出,我只需要删除每行中除了一个小字符串之外的所有内容。

字符串的格式为

"title": "someServerName"

“someServerName”(引号内的部分)可以有很大的不同。

我最接近的是:

:%s/\("title":\s"*"\)

但这只是设法删除

"title": "

我想要在每一行中留下的唯一东西是

"title": "someServerName"

编辑回答发布的问题:

我将使用的文本格式类似于

{"_links": {"self": {"href": "/api/v2/servers/32", "title": "someServerName"},tons_of_other_json_crap_goes_here

最后只剩下:

"title": "someServerName"

【问题讨论】:

  • 您能发布您的输入和预期输出吗?您的帖子中很不清楚

标签: regex vim pattern-matching vi


【解决方案1】:

它应该是.* 而不是* 来匹配一组任意字符。这样就可以了:

%s/^.*\("title":\s".*"\).*$/\1/

各部分说明:

  • %s/ 在每个匹配的行上替换。
  • ^.* 忽略从行首开始的任何字符。
  • \("title":\s".*"\) 捕获标题和服务器名称。 ".*" 将匹配引号之间的任何字符。
  • .*$ 忽略该行的其余部分。
  • /\1/ 替换的结果将是第一个捕获的组。该组被括号\(...\)捕获。

【讨论】:

  • 您能否详细说明这些部分的含义?我想我知道很多,但很多时候人们对它们的解释不同。我还想看看是否可以尝试更改它以保留“title”的每个实例:“someServerName”如果文件中有多个该模式的实例
  • 好的,我添加了一个细分。该命令确实处理多个匹配行。
【解决方案2】:
 %s/\v.*("title":\s".*").*/\1

解释和来源here

【讨论】:

    【解决方案3】:

    这听起来像是grep 的工作。

    :%!grep -o '"title":\s*"[^"]*"'
    

    有关 Vim 过滤的更多帮助,请参阅:h :range!

    有关-o/--only-matching 标志的更多信息,请参阅man grep

    【讨论】:

      【解决方案4】:

      如果您将替换命令分为以下两个步骤,则很方便。 (p.s.这个技能是最近从好书《Practical Vim》中学到的)。

      第一步:搜索你要保留的内容

      • \v"title":\s.*"
        这将匹配“title”:“someServerName”。你可以通过q/命令反复尝试打开搜索命令窗口并修改正则表达式(这是我认为最优秀的部分)。
      • \v^.*("title":\s.*").*$
        然后添加括号以供以后使用并添加 .* 以匹配您要删除的其他部分。

      第 2 步:替换匹配的内容

      • :%s//\1/g 注意这个替换命令中的原始字符串是上次搜索中匹配的部分(vim 中非常好的特性)。而\1 表示使用匹配组,这实际上是您希望保留的部分。

      希望你能发现它比冗长晦涩的替代命令更方便。

      【讨论】:

        【解决方案5】:

        我认为解决这个问题最优雅的方法是使用 ':g' 更全面的细节在下面的这个链接中! Power fo G

        它可能无法完全归档您正在查找的内容,但该死的很接近 ;)

        【讨论】:

        • 请记住,这是一篇非常古老的帖子。并尝试发布特定的答案,例如使用 :g!/pattern/d
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2022-11-03
        • 1970-01-01
        • 2022-01-13
        相关资源
        最近更新 更多