我想出了:([^"]*["][^"]*["][^"]*)*
除了空字符串外,它适用于所有情况。我认为它会起作用,因为最后一个星号匹配前一个标记零或更多次。
有什么想法吗?
如果还有更好的方法,请告诉我并详细解释。
解决方案必须是正则表达式,因为它将被用于需要正则表达式的钩子。
它必须匹配没有引号的字符串,因为零是偶数
答案 0 :(得分:6)
试试这个表达式:
^(?:[^"]+|"[^"]*")*$
它匹配一个序列,该序列由引号([^"]+
)以外的任何字符组成,或者与("[^"]*"
)之间引用之外的任何字符组成的引号对。 *
量词会考虑空字符串。
答案 1 :(得分:4)
你的正则表达式应该匹配完全空的字符串,但不是由单个空格组成的字符串,因为正则表达式声明如果字符串不是完全为空,则需要包含至少一个双引号。这是因为正则表达式中的[“]标记后面没有*。
考虑所需正则表达式的正确方法如下:你想匹配(不带双引号的字符串)后跟(双引号)加(不带双引号的字符串)后跟(双引号)后跟(字符串)没有双引号),然后从第一个'后跟'无限重复开始重复。没有双引号的字符串是[^“] *,所以你得到(为了可读性添加了空格):
[^"]* (" [^"]* " [^"]*)*
如果将其与正则表达式进行比较,则第一个[^“] *已被移动 out 重复。
答案 2 :(得分:2)
似乎regexp不适合这项工作。编辑:但是,你似乎受限于它。鉴于这种约束,这并没有回答你的问题,但如果没有它,它就会很好。
只需迭代你的字符串并计算。例如:
bool hasEvenNumberOfQuotes(const char *str)
{
bool even = true;
while(*str != '\0')
{
if(*str == '"')
even = !even;
++str;
}
return even;
}
答案 3 :(得分:2)
基于你的正则表达式:
([^"]*["][^"]*["][^"]*)*
添加线锚:
^([^"]*["][^"]*["][^"]*)*$
添加与非"
匹配的可能性:
^([^"]*["][^"]*["][^"]*|[^"]?)*$
最后一步不允许任何内容匹配,也不允许使用任何字符。这允许匹配缺少"
的字符串。请注意,需要使用行锚点,否则substring(s)将与此匹配。
Bonus:防止组反向引用(命名/编号组可能会使regexp引擎变慢一点):
^(?:[^"]*["][^"]*["][^"]*|[^"]?)*$
答案 4 :(得分:-1)
import re
def hasPairedQuotes(s):
stripped = re.sub('[^"]', "", s)
return len(stripped) % 2 == 0
>>> hasPairedQuotes("")
True
>>> hasPairedQuotes('""')
True
>>> hasPairedQuotes('"""')
False
>>> hasPairedQuotes('"Hello world!""')
False
>>> hasPairedQuotes('"Hello world!"')
True
很好,你想要一个正则表达式,这里是一个正则表达式:^[^"]*("[^"]*")*[^"]*$
...但我认为可读性和可维护性的区别不言而喻。
>>> re.match(r'^[^"]*("[^"]*"[^"])*$', 'Hello ""')
<_sre.SRE_Match object at 0xb7cc0ce0>
>>> re.match(r'^[^"]*("[^"]*"[^"])*$', 'Hello "" "')
>>>