字符串的正则表达式可选地用引号

时间:2017-09-15 10:03:13

标签: regex perl

我正在尝试构建一个匹配字符串的正则表达式,这些字符串用引号括起来或两边都没有引号。此外,正则表达式必须匹配的字符串可能在中间有引号。这是我目前努力的结果:

^("?+)(.*[^"])(\1)$

适用于在开头和结尾都有引号的字符串,在任何一侧都没有引号或仅在开头有引号:

$ echo '"blah "blah" blah"' | perl -ne 'if(/^("?+)(.*[^"])(\1)$/){print "$1\n$2\n$3"}'
"
blah "blah" blah
"
$ echo 'blah "blah" blah' | perl -ne 'if(/^("?+)(.*[^"])(\1)$/){print "$1\n$2\n$3"}'

blah "blah" blah

$ echo '"blah "blah" blah' | perl -ne 'if(/^("?+)(.*[^"])(\1)$/){print "$1\n$2\n$3"}'

但它匹配仅在结尾处有引号的字符串:

$ echo 'blah "blah" blah"' | perl -ne 'if(/^("?+)(.*[^"])(\1)$/){print "$1\n$2\n$3"}'

blah "blah" blah"

任何想法正则表达式的问题是什么以及如何解决它?

1 个答案:

答案 0 :(得分:2)

在上一个案例中,("?+)匹配空字符串。 (\1)实际上变为无操作:它还匹配空字符串。

这让我们留下了^(.*[^"])$。这匹配是因为您的输入字符串末尾有一个非"字符:换行符("\n")。

您可以在运行正则表达式(perl -ne 'chomp; ...')之前删除换行符来解决此问题。

作为旁注,您可能希望将正则表达式的中间部分设置为可选。否则它将不匹配空字符串或由两个引号("")组成的字符串。