我正在尝试编写一个正则表达式,以确保根据规范正确地重新格式化“标记”。 (我正在更新一堆遗留的东西。)
一般的想法是,标记可以包含()
或[]
中的括号内容。但是,现有标签可能格式不正确:
Sample (sample)
Sample [sample]
Sample (( sample )
Sample [(sample]]
我目前正在处理一系列正则表达式,但我想知道技术上是否可以在一个正则表达式中进行。
在代码的简化版本中......
RE_tag_collapse = re.compile(\
"""
([\[\(])+ ### opening bracket
\s*
( # the contents
[^\]\)]+
)
\s*
([\]\)])* # closing bracket
"""
,
re.I | re.VERBOSE
)
edited= re.sub( RE_tag_collapse , r'\1\2\1' , tag )
此正则表达式的问题在于结束标记(第二个\1
)与开始标记相同。
我想要做的是将结束标记映射为开始标记的反转:
(
反转为)
[
反转为]
有谁知道这是否容易实现?在我看来,我最好的解决方案是保持原样并使用多个正则表达式。
答案 0 :(得分:2)
如果我正确理解您的问题,您需要确保代码中的括号匹配。据我所知,python中的正则表达式无法计算出现次数。但是,您可以使用函数来检查括号是否匹配:
def check_tag(tag):
charstack = []
for c in tag:
if c in ["(","]"]:
charstack.append(c)
else if c in [")","]"]:
popped = charstack.pop()
if not ((c == ")" and popped == "(" ) or (c == "]" and popped == "[")):
return False
return len(charstack) == 0
这个函数的工作方式是,每当它找到一个左括号时,它就会将它推到一个堆栈上。每次遇到右括号时,它都会从堆栈中推出一个元素,看它们是否匹配。如果没有,则标签格式不正确。
答案 1 :(得分:2)
修改正则表达式以将所有左右括号捕获为组,然后您可以从左括号集生成正确的右括号集并在正则表达式替换中使用
像这样:
>>> def subber(matchobj):
return ' '.join([matchobj.group(1),
matchobj.group(2),
matchobj.group(1).replace('[',']').replace('(', ')')[::-1]])
>>> new_RE = re.compile(\
"""
([\[\(]+) ### opening brackets
\s*
( # the contents
[^\]\)]+
)
\s*
([\]\)]+) # closing brackets
"""
,
re.I | re.VERBOSE
)
>>> txt = 'Sample [(sample]]'
>>> new_RE.sub(subber, txt)
'Sample [( sample )]'
>>>
结束括号只是将每个开放式括号替换为收尾的组合,然后将其反转。