Python 使用lambda替换搜索模式

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='

我需要在文件中写入前后搜索替换模式。我已经写了下面的代码。我在编写输出文件时使用了这个函数,它工作得很好。但是我有大约20个这样的替换模式,我觉得我写的代码不好,因为我需要为所有这些替换创建函数。你能让我知道有没有其他的方法来实现这一点

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函数吗?我无法创建包含搜索前后替换模式的报告。@new2python
ripl()
是一个用于接收参数
ma
上的匹配对象的函数。它使用字典
d
。我将此字典作为参数
d
的默认值。事实上,该函数可以由
定义ripl(ma,dico):
和参数
dico
将替换函数块中的
d
dico[ma.group(1)][0]
dico[ma.group(1)][1]
。定义参数的默认值很有趣,因为函数定义的执行只执行一次(根据定义,您必须理解:描述函数的文本块)@new2python
ripl
返回的内容必须是一个字符串:此字符串用于替换处理文本中的每个匹配(=匹配部分)。由于
ripl
是一个函数,它返回的内容可能因匹配而异。匹配(=匹配部分)被替换的内容包含在传递给参数
ma
的匹配(=MatchObject)中:它是
ma.group(0)
。我的意思是regex模式中可能定义了几个组,但对于每个匹配,被替换的文本部分是完整的匹配(在
group(0)中捕获)
即使模式中没有定义组)@new2python我的回答只公开了在一次过程中进行多次替换的方式,而不是打开、读取和写入文件的方式。一旦替换了文本,您就可以随心所欲了。