用=〜匹配bash regex中的行尾

问题描述

我正在尝试使用bash regex匹配从多行字符串中解析出一行。为什么以下方法不起作用?

if [[ $qout =~ ${q}[^\n]* ]] ; then

它与字母n匹配。我尝试使用\\n甚至\\\n,但没有任何效果

$qout包含:

unrouted    0   0   running
dead-letter 0   0   running

$q包含unrouted

${BASH_REMATCH[0]的计算结果为:

unrouted    0   0   ru

我在做什么错了?

解决方法

假设:

  • 从多行变量(qout)中提取包含模式(q)的行
  • 从模式(q)提取到行尾(将在${BASH_REMATCH[0]}中捕获)

对多行变量进行了一些修改:

$ echo ${qout)
this is unrouted    0   0   running
dead-letter    0   0   running

注意:我在第一行添加了“ this is”前缀,以便我们可以验证解析的开始位置。

一个主意-从此答案中借用(shell regex to end of line):

$ sfx=$'[^\n]*'                  # match up to first newline (`\n`) character;
                                 # must use single quotes;
                                 # double quotes will cause the `\n` to be evaluated as the character `n`

$ [[ $qout =~ ${q}${sfx} ]] && echo 'match'
match
$ echo "${BASH_REMATCH[0]}"
unrouted    0   0   running

FWIW,将测试/ echo包装在set -/+ xv中显示:

$ [[ $qout =~ ${q}${sfx} ]] && echo 'match'
+ [[ this is unrouted    0   0   running
dead-letter    0   0   running =~ unrouted[^
]* ]]
+ echo match
match

在组合中添加@David C. Rankin的注释(将\n直接放在正则表达式中):

$ [[ $qout =~ ${q}[^$'\n']* ]] && echo 'match'
match
$ echo "${BASH_REMATCH[0]}"
unrouted    0   0   running

注意:如果David想发布自己的答案,我可以删除它。

,

[\n]与换行符不匹配-它与文字反斜杠或n匹配。如果您运行nl=$'\n'然后使用$nl作为您的正则表达式,那么事情将按预期进行。

#!/usr/bin/env bash
qout='unrouted    0   0   running
dead-letter 0   0   running'

q=unrouted

nl=$'\n'
if [[ $qout =~ ${q}[^$nl]*[$nl] ]]; then
  declare -p BASH_REMATCH
else
  echo "No match found" >&2
fi

...作为输出发出:

declare -ar BASH_REMATCH=([0]=$'unrouted    0   0   running\n')