当作为参数传递给外部方法时,不会评估Python正则表达式替换反向引用

时间:2017-09-13 06:27:05

标签: python regex lambda urlparse

e.g。我想将文本中的网址更改为其绝对路径,例如"a src=./url b""a src=hxxp://www.example.com/url b"。 但是当我在下面尝试这些代码时:

re.sub(r"(a\s+src=)(.*?)(\s+b)", r"\1"+urlparse.urljoin( "hxxp://www.example.com/",r"\2" )+r"\3", string_text)

当网址已经是绝对路径时,它不会表现良好,例如

输入:"a src=hxxp://www.google.com b"
输出:"a src=hxxp://www.example.com/hxxp://www.google.com b"

当使用函数lambda时,它可以正常工作

re.sub(r"(a\s+src=)(.*?)(\s+b)", lambda m:m.group(1)+urlparse.urljoin("hxxp://www.example.com/", m.group(2) )+m.group(3), string_text)

我想知道为什么,有人知道吗?

1 个答案:

答案 0 :(得分:0)

urlparse.urljoin( "hxxp://www.example.com/",r"\2" )不起作用的原因是\2 bakcreference仅在字符串替换模式中使用时才有效。如果您将其传递给另一个方法,则会放置\2文字字符串,因为re在此时没有机会对其进行评估。 re引擎仅在匹配期间对其进行评估,但在r"\1"+urlparse.urljoin( "hxxp://www.example.com/",r"\2" )+r"\3"引擎尝试查找匹配项之前评估re部分。

这就是为什么可以使用"回调" re.sub内的方法作为替换参数:您可以将匹配的组值传递给任何外部方法以进行高级操作。