Python正则表达式查找成对引号的第二个引号

3 投票
5 回答
1157 浏览
提问于 2025-04-18 07:05

我在想有没有办法从一对引号中只找到第二个引号,也就是成对的引号。

比如说,如果我有一个字符串像 '"aaaaa"' 或者 '""',我只想找到最后那个 '"'。再比如,如果我有 '"aaaa""aaaaa"aaaa""',我想找到第二个、第四个和第六个 '"'。但是如果我有 '"aaaaaaaa' 或者 'aaa"aaa',我就不想找到任何引号,因为它们没有成对的引号。如果我有 '"aaa"aaa"',我只想找到第二个 '"',因为第三个 '"'没有配对。

我尝试过使用“向后查找”,但它在使用量词时不太好用,所以我尝试的代码是 '(?<=\"a*)\"',结果没成功。

5 个回答

0

请查看我的回答,了解为什么在这种情况下不建议使用正则表达式,尽管你可以用它来处理一些非正则的工作。

好的,那么你可能想要我在链接中提供的解决方案之一,在那里你需要使用递归正则表达式来匹配所有的配对。


编辑:以下内容是在问题更新之前写的,当时的问题只是在询问第二个双引号。

不过,如果你只想在字符串中找到第二个双引号,其实不需要用正则表达式:

>>> s1='aoeu"aoeu'
>>> s2='aoeu"aoeu"aoeu'
>>> s3='aoeu"aoeu"aoeu"aoeu'
>>> def find_second_quote(s):
...     pos_quote_1 = s2.find('"')
...     if pos_quote_1 == -1:
...         return -1
...     pos_quote_2 = s[pos_quote_1+1:].find('"')
...     if pos_quote_2 == -1:
...         return -1
...     return pos_quote_1+1+pos_quote_2
... 
>>> find_second_quote(s1)
-1
>>> find_second_quote(s2)
4
>>> find_second_quote(s3)
4
>>> 

这里如果没有第二个引号,就会返回-1,如果有的话,就会返回第二个引号的位置。

0

一个解析器可能是更好的选择,但这要看你想要从中得到什么。如果你只需要引号之间的数据:

 import re
 re.findall(r'".*?"', '"aaaa""aaaaa"aaaa""')
 ['"aaaa"',
 '"aaaaa"',
 '""']

如果你需要索引(位置),你可以像这样用生成器或者其他类似的方法来实现:

 def count_quotes(mystr):
     count = 0
     for i, x in enumerate(mystr):
         if x == '"':
              count += 1
              if count % 2 == 0:
                  yield i

list(count_quotes('"aaaa""aaaaa"aaaa""'))
[5, 12, 18]
1

如果你想要改变第二个引号,你可以先匹配整个字符串,然后把第二个引号前面的部分放进一个捕获组里。接着,用第一个匹配组加上你想替换的内容,就能解决这个问题。

举个例子,这个正则表达式会匹配第二个引号之前的所有内容,并把它放进一个组里。

(\"[^"]*)\"

如果你用整个匹配的内容(包括第二个引号)来替换,但只用捕获组的值(不包括第二个引号),那么你就会把第二个引号去掉。

你可以查看这个在线示例

import re
p = re.compile(ur'(\"[^"]*)\"')
test_str = u"\"test1\"test2\"test3\""
subst = r"\1"

result = re.sub(p, subst, test_str)
print result #result -> "test1test2"test3
2

其实你并不需要用正则表达式来解决这个问题。你可以这样做:

[i for i, c in enumerate(s) if c == '"'][1::2] 

这样可以找到每个其他的 '"' 的位置。下面是一个示例用法:

>>> for s in ['"aaaaa"', '"aaaa""aaaaa"aaaa""', 'aaa"aaa', '"aaa"aaa"']:
    print(s, [i for i, c in enumerate(s) if c == '"'][1::2])


"aaaaa" [6]
"aaaa""aaaaa"aaaa"" [5, 12, 18]
aaa"aaa []
"aaa"aaa" [4]
1
import re
reg = re.compile(r'(?:\").*?(\")')

然后

for match in reg.findall('"this is", "my test"'):
    print(match)

给出

"
"

撰写回答