初学爬虫(二)

流过昼夜 提交于 2019-12-05 09:48:32

1.首先,我们确定需要爬取的网页及robots协议,爬取的网页为最好大学网http://www.zuihaodaxue.cn/zuihaodaxuepaiming2019.html,查看robots协议打开http://www.zuihaodaxue.cn/robots.txt,发现:not found,说明没有对爬取进行robots协议限制,可以进行爬取。

2.我们需要打开网页源代码,查看此网页的信息是写在html代码中,还是由js文件动态生成的,如果是后者,那么我们目前仅仅采用requests和BeautifulSoup还很难爬取到排名的信息。

查看网页源代码,我们可以发现,排名信息是写在html页面中的,这时候我们利用BeautifulSoup库就可以对信息进行提取

3、程序的结构设计:

  步骤1,从网络上获取大学排名网页内容,getHTMLText()

  步骤2、提取网页内容中信息到合适的数据结构,fillUnivList()

  步骤3、利用数据结构展示并输出结果,printUnivList()

4.首先我们先忽略代码的具体实现,写出爬取的逻辑:

 1 #CrawUnivRankingB.py
 2 import requests
 3 from bs4 import BeautifulSoup
 4 import bs4
 5 
 6 def getHTMLText(url)://获取内容
 7    
 8 
 9 def fillUnivList(ulist, html)://将数据存到list中
10     
11 
12 def printUnivList(ulist, num)://展示输出结果
13    
14     
15 def main():
16     uinfo = []
17     url = 'http://www.zuihaodaxue.cn/zuihaodaxuepaiming2017.html'
18     html = getHTMLText(url)
19     fillUnivList(uinfo, html)
20     printUnivList(uinfo, 20) # 20 univs//提取前20个信息
21 main()
5.然后我们来实现每个函数

首先第一个函数很好实现,就是requests库直接抓取网页

1 def getHTMLText(url):
2     try:
3         r = requests.get(url, timeout=30)
4         r.raise_for_status()
5         r.encoding = r.apparent_encoding
6         return r.text
7     except:
8         return ""

timeout设定超时时间,以秒为单位

我们发现所有的排名信息都在一个tbody的标签里面,然后每个tr标签又存储了每个大学的信息,具体的信息存在每个td标签里。
所以,思路救出来了
第一步,提取出tbody标签,也就是页面中第一个tbodybiaoqian
第二步,提取出里面所有的tr标签
第三步,对每个tr标签里的td信息存储到相应的数据结构里
#将数据存到list中
def fillUnivList(ulist,html):
    soup=BeautifulSoup(html,'html.parser')
    #查看HTML源码发现每一所大学都在tbody标签中,这里一个tr表示一所大学
    for tr in soup.find('tbody').children:
        if isinstance(tr,bs4.element.Tag):#判断是否为标签类型,过滤掉字符串
            tds=tr('td')
            ulist.append([tds[0].string,tds[1].string,tds[2].string])
    #pass 
#将num个list中的数据打印显示出来,可视化输出

find()意思是搜索且返回一个结果是字符串类型,同.find_all()参数。

.childreny意思是字节点迭代类型,与.contents类似,用于循环遍历儿子节点。其他扩展:

.contents子节点的列表,将<tag>所有儿子节点存入列表;

.descendans子节点的迭代类型,包含所有的子孙节点,用于循环遍历。


def printUnivList(ulist, num):
#打印表头
    tplt = "{0:^10}\t{1:{3}^10}\t{2:^10}"#用中文空格进行填充
    print(tplt.format("排名","学校名称","总分",chr(12288)))
    for i in range(num):
        u=ulist[i]
        print(tplt.format(u[0],u[1],u[2],chr(12288)))
    

6.全部代码

#CrawUnivRankingB.py
import requests
from bs4 import BeautifulSoup
import bs4

def getHTMLText(url):
    try:
        r = requests.get(url, timeout=30)
        r.raise_for_status()
        r.encoding = r.apparent_encoding
        return r.text
    except:
        return ""

def fillUnivList(ulist, html):
    soup = BeautifulSoup(html, "html.parser")
    for tr in soup.find('tbody').children:
        if isinstance(tr, bs4.element.Tag):
            tds = tr('td')
            ulist.append([tds[0].string, tds[1].string, tds[3].string])

def printUnivList(ulist, num):
    tplt = "{0:^10}\t{1:{3}^10}\t{2:^10}"
    print(tplt.format("排名","学校名称","总分",chr(12288)))
    for i in range(num):
        u=ulist[i]
        print(tplt.format(u[0],u[1],u[2],chr(12288)))
    
def main():
    uinfo = []
    url = 'http://www.zuihaodaxue.cn/zuihaodaxuepaiming2019.html'
    html = getHTMLText(url)
    fillUnivList(uinfo, html)
    printUnivList(uinfo, 20) # 20 univs
main()

运行结果

排名    学校名称    总分
1    清华大学    94.6
2    北京大学    76.5
3    浙江大学    72.9
4   上海交通大学   72.1
5    复旦大学    65.6
6  中国科学技术大学  60.9
7   华中科技大学   58.9
7    南京大学    58.9
9    中山大学    58.2
10  哈尔滨工业大学   56.7
11  北京航空航天大学  56.3
12    武汉大学    56.2
13    同济大学    55.7
14   西安交通大学   55.0
15    四川大学    54.4
16   北京理工大学   54.0
17    东南大学    53.6
18    南开大学    52.8
19    天津大学    52.3
20   华南理工大学   52.0
[Finished in 3.9s]

 





标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!