在文本块中查找并替换URL,返回文本和URL列表

2 投票
4 回答
2168 浏览
提问于 2025-04-17 03:48

我想找到一种方法,可以把一段文字中的所有网址替换成其他文字,然后返回新的文字和找到的网址列表。就像这样:

text = """This is some text www.google.com blah blah http://www.imgur.com/12345.jpg lol"""
text, urls = FindURLs(text, "{{URL}}")

应该会得到:

text = "This is some text {{URL}} blah blah {{URL}} lol"
urls = ["www.google.com", "http://www.imgur.com/12345.jpg"]

我知道这需要用到一些正则表达式(regex)——我在这里找到了一些看起来不错的网址检测正则表达式:http://www.regexguru.com/2008/11/detecting-urls-in-a-block-of-text/

不过我对正则表达式不太在行,所以用Python实现起来有点困难。网址返回的顺序其实没什么关系。

谢谢 :)

4 个回答

1

你可能很难找到一个可以匹配没有协议的谷歌网址的方式,不过下面这个方法可以用在真实的网址上:

>>> re.findall('http[s]?://(?:[a-zA-Z]|[0-9]|[$-_@.&+]|[!*\(\),]|(?:%[0-9a-fA-F][0-9a-fA-F]))+', text)
['http://www.imgur.com/12345.jpg']
1

如果你出于某种原因想让网址格式正确,可以使用一些正则表达式的技巧。否则,你可以直接用split()把你的文本分开,遍历这个列表,如果某个词是以“www”或“http”开头的,就按照需要处理它。最后,再用join()把列表合并回去。

text = """This is some text www.google.com blah blah http://www.imgur.com/12345.jpg lol"""
s = text.split()
urls = []
for i in range(len(s)):
    item = s.pop(0)
    if item.startswith("www") or item.startswith("http"):
        s.append("{{URL}}")
        urls.append(item)
    else:
        s.append(item)    

print " ".join([i for i in s])   
print urls  
4

这个正则表达式在这里应该足够宽松,可以匹配没有http或www的链接。

下面是一段简单的Python代码,它可以进行文本替换,并给你一个结果列表:

import re

url_regex = re.compile(r"""(?i)\b((?:[a-z][\w-]+:(?:/{1,3}|[a-z0-9%])|www\d{0,3}[.]|[a-z0-9.\-]+[.][a-z]{2,4}/)(?:[^\s()<>\[\]]+|\(([^\s()<>\[\]]+|(\([^\s()<>\[\]]+\)))*\))+(?:\(([^\s()<>\[\]]+|(\([^\s()<>\[\]]+\)))*\)|[^\s`!(){};:'".,<>?\[\]]))""")

text = "This is some text www.google.com blah blah http://www.imgur.com/12345.jpg lol"
matches = []

def process_match(m):
    matches.append(m.group(0))
    return '{{URL}}'

new_text = url_regex.sub(process_match, text)

print new_text
print matches

撰写回答