Python 使用lambda替换搜索模式
我需要在文件中写入前后搜索替换模式。我已经写了下面的代码。我在编写输出文件时使用了这个函数,它工作得很好。但是我有大约20个这样的替换模式,我觉得我写的代码不好,因为我需要为所有这些替换创建函数。你能让我知道有没有其他的方法来实现这一点Python 使用lambda替换搜索模式,python,regex,python-3.x,Python,Regex,Python 3.x,我需要在文件中写入前后搜索替换模式。我已经写了下面的代码。我在编写输出文件时使用了这个函数,它工作得很好。但是我有大约20个这样的替换模式,我觉得我写的代码不好,因为我需要为所有这些替换创建函数。你能让我知道有没有其他的方法来实现这一点 import re Report_file = open("report.txt", "w") st = '''<TimeLog> <InTime='10Azx'>1056789</InTime> <OutTime='
import re
Report_file = open("report.txt", "w")
st = '''<TimeLog>
<InTime='10Azx'>1056789</InTime>
<OutTime='14crg'>1056867</OutTime>
<PsTime='32lxn'>1056935</PsTime>
<ClrTime='09zvf'>1057689</ClrTime>
</TimeLog>'''
def tcnv(str):
Report_file.write("Previous TS: " + str + "\n\n")
v1 = re.search(r"(?i)<clrtime='(\d+\w+)'>", str)
val1 = v1.group(1)
v2 = re.search(r"(?i)(<clrtime='(\d+\w+)'>(.*?)</clrtime>)", str)
val2 = v2.group(3)
soutval = "<Clzone><clnvl='" + val1 + "'>" + val2 + "</clnvl></Clzone>"
Report_file.write("New TS: " + soutval + "\n")
return soutval
st = re.sub(r"(?i)(<clrtime='(\d+\w+)'>(.*?)</clrtime>)", lambda m: tcnv(m.group(1)), st)
st = re.sub(r"(?i)<intime='(\d+\w+)'>(.*?)</intime>", "<Izone><Invl='\\1'>\\2</Invl></Izone>", st)
st = re.sub(r"(?i)<outtime='(\d+\w+)'>(.*?)</outtime>", "<Ozone><onvl='\\1'>\\2</onnvl></Ozone>", st)
st = re.sub(r"(?i)<pstime='(\d+\w+)'>(.*?)</pstime>", "<Pszone><psnvl='\\1'>\\2</psnvl
重新导入
Report\u file=open(“Report.txt”、“w”)
st='''
1056789
1056867
1056935
1057689
'''
def tcnv(str):
报告文件。写入(“以前的TS:+str+”\n\n)
v1=重新搜索(r“(?i)”,str)
val1=v1.组(1)
v2=重新搜索(r“(?i)(.*?”),str)
val2=v2.组(3)
soutval=”“+val2+“”
报告文件。写入(“新TS:+soutval+”\n)
返回soutval
st=re.sub(r)(?i)(*?)”,λm:tcnv(m.group(1)),st)
st=re.sub(r“(?i)(*?”,“\\2”,st)
st=re.sub(r“(?i)(*?”,“\\2”,st)
st=re.sub(r“(?i)(.*?”,“\\2我不明白您为什么将re.IGNORECASE标志放在(?i)
的形式下,因此我不在下面的解决方案中使用它,并且根据您的示例,在必要时使用大写字母编写模式
请注意,您应该使用with
语句打开文件,这样会更好:
with open('filename.txt','rb') as f:
ch = f.read()
答案
import re
st = '''<InTime='10Azx'>1056789</InTime>
<OutTime='14crg'>1056867</OutTime>
<PsTime='32lxn'>1056935</PsTime>
<ClrTime='09zvf'>1057689</ClrTime>
'''
d = dict(zip(('InTime','OutTime','PsTime','ClrTime'),
(('Izone><Invl','/Invl></Izone'),
('Ozone><onvl','/onnvl></Ozone'),
('Pszone><psnvl','/psnvl></Pszone'),
('Clzone><clnvl','/clnvl></Clzone'))
)
)
def ripl(ma,d=d):
return "<{}='{}'>{}<{}>".format(d[ma.group(1)][0],
ma.group(2),
ma.group(3),
d[ma.group(1)][1])
st2 = re.sub(r"<(InTime|OutTime|PsTime|ClrTime)='(\d+\w+)'>(.*?)</\1>",
ripl, st)
print '%s\n\n%s\n' % (st,st2)
重新导入
st=''1056789
1056867
1056935
1057689
'''
d=dict(zip('InTime','OutTime','PsTime','ClrTime'),
(('Izone>感谢您的反馈。因为我是python新手,所以我以这种方式打开文件。您能解释一下ripl函数吗?我无法创建包含搜索前后替换模式的报告。@new2pythonripl()
是一个用于接收参数ma
上的匹配对象的函数。它使用字典d
。我将此字典作为参数d
的默认值。事实上,该函数可以由定义ripl(ma,dico):
和参数dico
将替换函数块中的d
:dico[ma.group(1)][0]
和dico[ma.group(1)][1]
。定义参数的默认值很有趣,因为函数定义的执行只执行一次(根据定义,您必须理解:描述函数的文本块)@new2pythonripl
返回的内容必须是一个字符串:此字符串用于替换处理文本中的每个匹配(=匹配部分)。由于ripl
是一个函数,它返回的内容可能因匹配而异。匹配(=匹配部分)被替换的内容包含在传递给参数ma
的匹配(=MatchObject)中:它是ma.group(0)
。我的意思是regex模式中可能定义了几个组,但对于每个匹配,被替换的文本部分是完整的匹配(在group(0)中捕获)
即使模式中没有定义组)@new2python我的回答只公开了在一次过程中进行多次替换的方式,而不是打开、读取和写入文件的方式。一旦替换了文本,您就可以随心所欲了。