Python正则表达式删除匹配括号的文件。

3

我有一个Latex文件,其中许多文本都带有\red{}标记,但在\red{}内部也可能有括号,例如:\red{这里是\underline{下划线}文本}。我想要去掉红色并进行一些搜索后,我写了这个Python脚本:

import os, re, sys
#Start program in terminal with
#python RedRemover.py filename
#sys.argv[1] then has the value filename
ifn = sys.argv[1]
#Open file and read it
f = open(ifn, "r")
c = f.read() 
#The whole file content is now stored in the string c
#Remove occurences of \red{...} in c
c=re.sub(r'\\red\{(?:[^\}|]*\|)?([^\}|]*)\}', r'\1', c)
#Write c into new file
Nf=open("RedRemoved_"+ifn,"w")
Nf.write(c)

f.close()
Nf.close()

但是这将会把

\red{这里有\underline{下划线}文本}

转换成

这里有\underline{下划线文本}

这不是我想要的。我想要的是

这里有\underline{下划线}文本

2个回答

6

由于re模块不支持递归,因此无法匹配未确定嵌套括号的级别。为了解决这个问题,您可以使用新的regex模块

import regex

c = r'\red{here is \underline{underlined} text}'

c = regex.sub(r'\\red({((?>[^{}]+|(?1))*)})', r'\2', c)

其中(?1)是对第一组捕获进行递归调用。

非常感谢!我需要执行pip install regex,然后它就像魔法般地运行了。 - thomasfermi
@user2609987:确实不是默认安装的。 - Casimir et Hippolyte
@ridgerunner:谢谢。当上下文不含模糊的整数或由花括号包围的一对整数时,花括号通常不需要转义。许多风格不将右花括号视为特殊字符。捕获组2用于替换。 - Casimir et Hippolyte
好答案。+1 (但我仍然会转义那些花括号。:^) - ridgerunner

1

我认为你需要保留花括号,考虑这个情况:\red{\bf test}

import re

c = r'\red{here is \underline{underlined} text} and \red{more}'
d = c 

# this may be less painful and sufficient, and even more correct
c = re.sub(r'\\red\b', r'', c)
print "1ST:", c

# if you want to get rid of the curlies:
d = re.sub(r'\\red{([^{]*(?:{[^}]*}[^}]*)*)}', r'\1', d)
print "2ND:", d

给出:
1ST: {here is \underline{underlined} text} and {more}
2ND: here is \underline{underlined} text and more

谢谢你的回答!但是,如果有多个红色文本的情况,这种方法将不起作用,例如 c = r'\red{这里是\underline{下划线}文字}\red{还有其他}'。 - thomasfermi
谢谢。我也感谢您关于保留花括号的评论,但在我的文件中,您提到的情况并没有发生。 - thomasfermi

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接