如何从网站上使用Beautiful Soup(python)递归获取所有链接

时间:2013-11-25 17:04:59

标签: python beautifulsoup

我希望能够以递归方式从网站获取所有链接,然后按照这些链接获取这些网站的所有链接。深度应为5-10,以便返回它找到的所有链接的数组。最好使用美丽的汤/蟒蛇。谢谢!

到目前为止,我已经尝试了这个并且它无法工作......任何帮助都将受到赞赏。

from BeautifulSoup import BeautifulSoup
import urllib2

def getLinks(url):
    if (len(url)==0):
        return [url]
    else:
        files = [ ]
        page=urllib2.urlopen(url)
        soup=BeautifulSoup(page.read())
        universities=soup.findAll('a',{'class':'institution'})
        for eachuniversity in universities:
           files+=getLinks(eachuniversity['href'])
        return files

print getLinks("http://www.utexas.edu/world/univ/alpha/")

2 个答案:

答案 0 :(得分:4)

抓取页面的数量将呈指数级增长,涉及的许多问题在初看时可能看起来并不复杂,请查看scrapy架构概述,以了解在现实生活中应该如何完成

enter image description here

除了其他强大的功能之外,scrapy不会重复抓取相同的网页(除非您强制执行)并且可以配置为最大DEPTH_LIMIT

更好的是,scrapy有一个内置的链接提取工具link-extractors

答案 1 :(得分:1)

递归算法用于将大问题减少到具有相同结构的较小问题,然后将结果组合起来。它们通常由不会导致递归的基本情况和导致递归的另一种情况组成。例如,假设您出生于1986年,并且您想要计算您的年龄。你可以写:

def myAge(currentyear):
    if currentyear == 1986: #Base case, does not lead to recursion.
        return 0
    else:                   #Leads to recursion
        return 1+myAge(currentyear-1)

我,我自己,并没有真正看到在你的问题中使用递归的重点。我的建议是你首先在代码中设置一个限制。你给我们的东西只会无限地运行,因为程序会陷入无限嵌套的for循环中;它永远不会达到目的并开始回归。因此,您可以在函数外部使用一个变量,每次进入某个级别时都会更新,并且在某个时刻停止该函数启动新的for循环并开始返回它所找到的内容。

但是你开始改变全局变量,你会以一种奇怪的方式使用递归,而代码会变得混乱。

现在阅读评论并选择你真正想要的东西,我必须说,这不是很清楚,你可以在你的代码中使用递归算法的帮助,但不能递归写出所有这些。

def recursiveUrl(url,depth):

    if depth == 5:
        return url
    else:
        page=urllib2.urlopen(url)
        soup = BeautifulSoup(page.read())
        newlink = soup.find('a') #find just the first one
        if len(newlink) == 0:
            return url
        else:
            return url, recursiveUrl(newlink,depth+1)


def getLinks(url):
    page=urllib2.urlopen(url)
    soup = BeautifulSoup(page.read())
    links = soup.find_all('a', {'class':'institution'})
    for link in links:
        links.append(recursiveUrl(link,0))
    return links

现在仍然存在这样的问题:链接并不总是链接到网页,而是链接到文件和图像。这就是我在'url-opening'函数的递归部分编写if / else语句的原因。另一个问题是你的第一个网站有2166个机构链接,创建2166 * 5个漂亮的东西并不快。上面的代码运行2166次递归函数。这不应该是一个问题,但你正在处理大的html(或任何PHP)文件,所以制作2166 * 5的汤需要花费大量的时间。