将HTML分解为链接文本和目标

5

假设有一个HTML链接:

<a href="urltxt" class="someclass" close="true">texttxt</a>

我该如何分离网址和文本?

更新

我正在使用Beautiful Soup,但无法弄清楚如何做到这一点。

我已经尝试了一些方法:

soup = BeautifulSoup.BeautifulSoup(urllib.urlopen(url))

links = soup.findAll('a')

for link in links:
    print "link content:", link.content," and attr:",link.attrs

i get

*link content: None  and attr: [(u'href', u'_redirectGeneric.asp?genericURL=/root    /support.asp')]*  ...
...

为什么我看不到内容?
编辑:根据建议详细说明了“卡住”的问题 :)

很有可能urllib.urlopen(url)出现了问题。尝试将其打印出来,看看你得到了什么。它应该是网页的纯HTML代码。 - Harley Holcombe
此外,“卡住了!”不是非常具有描述性。展示更多代码,并清楚地说明出现了什么问题。 - Harley Holcombe
感谢提供额外信息,这让我更容易看清发生了什么。 - Harley Holcombe
4个回答

8
使用Beautiful Soup。自己动手做比看起来更难,使用经过试验的模块效果更好。

编辑:

我认为您想要:

soup = BeautifulSoup.BeautifulSoup(urllib.urlopen(url).read())

顺便提一下,在那里尝试打开URL是个坏主意,因为如果出了问题,情况可能会变得很糟糕。

编辑2:

这应该会显示页面中的所有链接:

import urlparse, urllib
from BeautifulSoup import BeautifulSoup

url = "http://www.example.com/index.html"
source = urllib.urlopen(url).read()

soup = BeautifulSoup(source)

for item in soup.fetchall('a'):
    try:
        link =  urlparse.urlparse(item['href'].lower())
    except:
        # Not a valid link
        pass
    else:
        print link

我同意,Beautiful Soup 可能是处理这个的更好方法。 - monkut
在其他地方打开URL并在那里检查错误会更好吗? - sundeep
是的,并在其周围加上try...except以防它失败。 - Harley Holcombe
字符串前面的'u'表示它是Unicode编码。请参考维基百科了解其含义。这不会对您产生太大影响。 - Harley Holcombe

6

以下是一个代码示例,展示如何获取链接的属性和内容:

soup = BeautifulSoup.BeautifulSoup(urllib.urlopen(url))
for link in soup.findAll('a'):
    print link.attrs, link.contents

4

看起来您有两个问题:

  1. 应该是link.contents,而不是link.content
  2. attrs是一个字典,而不是一个字符串。它为HTML元素中的每个属性保存键值对。link.attrs['href']将获取您似乎正在寻找的内容,但您需要在其中包装一个检查,以防出现没有href属性的a标签。

3

虽然我认为其他人可能会正确地指向使用Beautiful Soup,但他们也可能不会,而使用外部库可能会过于复杂。这是一个正则表达式,可以实现你所要求的功能。

/<a\s+[^>]*?href="([^"]*)".*?>(.*?)<\/a>/

以下是匹配的内容:

'<a href="url" close="true">text</a>'
// Parts: "url", "text"

'<a href="url" close="true">text<span>something</span></a>'
// Parts: "url", "text<span>something</span>"

如果你只想得到文本(例如:在上面的第二个例子中,“textsomething”),我会再运行一个正则表达式,以删除尖括号之间的任何内容。

使用这种方法时,您需要注意源代码中的换行符。确保在编译模式时设置re.DOTALL标志。 - tgray

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接