在Python中获取URL的特定部分

1 投票
3 回答
685 浏览
提问于 2025-04-17 16:43

我正在使用Python,想要从一个网址中提取特定的部分,如下所示:

from urlparse import urlparse as ue

url = "https://www.google.co.in"
img_url = ue(url).hostname

结果

www.google.co.in

案例1

其实我会有很多网址(存储在一个列表里或者其他地方),我想要做的是,从网址中找到域名,提取出www.后面和.co.in前面的部分,也就是从第一个点后面开始,到第二个点前面结束的字符串,这样在当前的例子中结果就是google

假设给定的网址是www.gmail.com,我应该只提取出gmail,所以无论给定什么网址,代码都应该提取出从第一个点开始到第二个点前面的部分。

案例2:

还有一些网址可能直接是这样的domain.com, stackoverflow.com,没有www,在这种情况下,它应该只提取出stackoverflowdomain

最后,我的目的是从网址中提取出主要的名称,比如gmail, stackoverflow, google等等……

一般来说,如果我有一个网址,我可以使用列表切片来提取字符串,但我会有很多网址,所以需要动态地提取出想要的部分,如上所述。

有没有人能告诉我如何实现这个想法呢?

3 个回答

1

那使用一组预定义的顶级域名怎么样呢?

import re
from urlparse import urlparse

#Fake top level domains... EG: co.uk, co.in, co.cc
TOPLEVEL = [".co.[a-zA-Z]+", ".fake.[a-zA-Z]+"]

def TLD(rgx, host, max=4): #4 = co.name
        match = re.findall("(%s)" % rgx, host, re.IGNORECASE)
        if match: 
            if len(match[0].split(".")[1])<=max:
                return match[0]
        else:
            return False

parsed = []
urls = ["http://www.mywebsite.xxx.asd.com", "http://www.dd.test.fake.uk/asd"]
for url in urls:
    o = urlparse(url)
    h = o.hostname
    for j in range(len(TOPLEVEL)):
        TL = TLD(TOPLEVEL[j], h)
        if TL: 
            name = h.replace(TL, "").split(".")[-1]
            parsed.append(name)
            break
        elif(j+1==len(TOPLEVEL)): 
            parsed.append(h.split(".")[-2])
            break

print parsed

这有点像小聪明,可能对某些人来说有点难懂,但确实能解决问题,而且不需要做其他的事情 :)

2

为什么你不能直接这样做:

from urlparse import urlparse as ue
urls = ['https://www.google.com', 'http://stackoverflow.com']
parsed = []
for url in urls:
    decoded = ue(url).hostname
    if decoded.startswith('www.'):
        decoded = ".".join(decoded.split('.')[1:])
    parsed.append(decoded.split('.')[0])
#parsed is now your parsed list of hostnames

另外,你可能需要修改一下for循环里的if语句,因为有些域名可能会以其他东西开头,你可能想把那些去掉。

0

这是我的解决方案,最后的 domains 里会保存你期待的域名列表。

import urlparse
urls = [
    'https://www.google.com', 
    'http://stackoverflow.com',
    'http://www.google.co.in',
    'http://domain.com',
    ]
hostnames = [urlparse.urlparse(url).hostname for url in urls]
hostparts = [hostname.split('.') for hostname in hostnames]
domains = [p[0] == 'www' and p[1] or p[0] for p in hostparts]
print domains # ==> ['google', 'stackoverflow', 'google', 'domain']

讨论

  1. 首先,我们使用 urlparse.urlparse() 从网址列表中提取主机名。提取出来的 hostnames 列表看起来是这样的:

    [ 'www.google.com', 'stackoverflow.com', ... ]

  2. 接下来,我们把每个主机名用点号分开,分成不同的部分。每个主机部分的样子是这样的:

    [ ['www', 'google', 'com'], ['stackoverflow', 'com'], ... ]

  3. 接下来的操作比较有意思。这一行的意思是:“如果点号前面的第一部分是 www,那么域名就是第二部分(p[1])。否则,域名就是第一部分(p[0])。”所以 domains 列表看起来是这样的:

    [ 'google', 'stackoverflow', 'google', 'domain' ]

  4. 我的代码不知道怎么处理 login.gmail.com.hk。希望其他人能解决这个问题,因为我该睡觉了。更新:可以看看 John Kurkowski 的 tldextract,它应该能满足你的需求。

撰写回答