【问题标题】:bash grep text within squared brackets方括号内的 bash grep 文本
【发布时间】:2017-01-17 16:00:51
【问题描述】:

我尝试从 linux bash 上的日志文件中 grep 文本。文本在两个方括号内。

例如在:

32432423 jkhkjh [234] hkjh32 2342342

我正在搜索234

通常应该会找到它

 \[(.*?)\]

但不是

|grep \[(.*?)\]

用 grep 进行正则表达式搜索的正确方法是什么

【问题讨论】:

  • 您不需要括号。或者问号。
  • 你的意思是这样 |grep \[.*\] ?在红帽 linux 上不适合我
  • 当我尝试echo "32432423 jkhkjh [234] hkjh32 2342342" | grep '\[.*\]' 时,它似乎在我的 Debian 系统上运行良好。它与[234] 部分匹配。

标签: regex bash grep


【解决方案1】:

要 grep 方括号包括括号之间的所有值,您可以使用基于 POSIX BRE 的 grep 命令,例如

grep -o '\[[^][]*]' file

...和同类的 BONUS 解决方案:

grep -o '<[^<>]*>' file # Extracting all strings between angle brackets
grep -o '([^()]*)' file # Extracting all strings between parentheses
grep -o '{[^{}]*}' file # Extracting all strings between curly braces
grep -o '"[^"]*"'  file # Extracting all strings between double quotes
grep -o "'[^']*'"  file # Extracting all strings between single quotes

请参阅online grep demo-o 选项使 grep 仅输出匹配的子字符串,而不是整行,并且 \[[^][]*] 模式匹配 [,然后出现 0 次或多次除 [] 之外的任何字符(请参阅否定[^][]* 括号表达式),然后是 ]

如果您需要获取方括号内的值排除方括号,您可以使用基于 PCRE 正则表达式的grep 命令,例如

grep -oP '\[\K[^][]*(?=])' file

another online demo

\[\K[^][]*(?=]) 模式匹配

  • \[ - 一个 [ 字符
  • \K - 匹配重置运算符,将匹配的文本从匹配内存缓冲区中丢弃
  • [^][]* - 除了 ][ 之外的 0 个或多个字符
  • (?=]) - 一个正向前瞻,需要在当前位置右侧紧接一个 ] 字符。

【讨论】:

    【解决方案2】:

    由于贪婪,我更喜欢\\[[^]]*](即:\\[ [ ^] ]* ],即方括号中的任何东西,但右方括号)而不是\\[.*]

    $ grep -o \\[.*] <<<"[this] and that too]"
    [this] and that too]
    

    对比

    $ grep -o \\[[^]]*] <<<"[this] and that too]"
    [this]
    

    然后grep 不是万能的工具(毕竟是g/re/p)。如果您只想要方括号内的内容,我会使用sed

    $ sed 's/.*\[\([^]]*\)].*/\1/' foo
    234
    

    即。 用括号中的内容替换所有内容...sies

    【讨论】:

      【解决方案3】:

      [ 对于 shell grep 都有特殊的含义,所以你需要引用它两次。反斜杠防止grep 将它们视为括号表达式的一部分;引用整个内容可防止 shell 在将正则表达式传递给 grep 之前尝试将其扩展为模式。

      ... | grep '\[(.*?)\]'
      

      在您的尝试中,shell 在强制 shell 按字面意思对待它们之后剥离了反斜杠,大约是 ... | grep '[(.*?)]'

      【讨论】:

        【解决方案4】:

        您可以查找左括号并使用\K 转义序列清除。然后,匹配右括号:

        $ grep -Po '\[\K[^]]*' <<< "32432423 jkhkjh [234] hkjh32 2342342"
        234
        

        请注意,您可以省略 -P(Perl 扩展正则表达式):

        $ grep -o '\[.*]' <<< "32432423 jkhkjh [234] hkjh32 2342342"
        [234]
        

        但是,如您所见,这也会打印括号。这就是让-P 执行后视和后视很有用的原因。

        你还在你的正则表达式中提到了?。好吧,正如您已经知道的那样,*? 是让正则表达式匹配以非贪婪的方式表现。我们来看一个例子:

        $ grep -Po '\[.*?]' <<< "32432423 jkhkjh [23]4] hkjh32 2342342"
        [23]
        $ grep -Po '\[.*]' <<< "32432423 jkhkjh [23]4] hkjh32 2342342"
        [23]4]
        

        对于.*?,在[23]4] 中匹配[23]。只有.*,它匹配到最后一个],因此得到[23]4]。此行为仅适用于 -P 选项。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 2013-05-27
          • 2023-01-01
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多