网络爬虫requests和bs4简单入门

网络爬虫基础(嵩天老师爬虫教学)

本博客的主要内容:介绍如何使用基本的库完成对html页面内容的爬取和分析,分以下几方面介绍

  1. 介绍网络爬虫的基本工作过程
  2. requests库的基本用法
  3. 使用BeautifulSoup对页面进行解析

1.介绍网络爬虫的基本工作过程

The Website is the API 我们应该将网页看成是一个我们获取信息的接口,我们可以通过python爬虫从中获取我们所需要的信息。
一般步骤:
(1)通过requests库爬取html页面的内容
(2)使用BeautifulSoup库对爬取到的html页面进行解析
(3)使用BeautifulSoup以及正则表达式来进一步提取我们想要的关键信息
(4)将信息格式化并输出

2.requests库的基本使用

requests库有好几种方法,这里我们介绍最主要的get和post方法
最简单的请求方法get:

import requests
r  = requests.get("http://python123.io/ws/demo.html")
print(r)
    #返回码200表示访问正常
r.encoding = r.apparent_encoding   #使用该语句将正确的编码给到 r 
r.text    #打印出html页面的内容
'This is a python demo page\r\n\r\n

The demo python introduces several python courses.

\r\n

Python is a wonderful general-purpose programming language. You can learn Python from novice to professional by tracking the following courses:\r\nBasic Python and Advanced Python.

\r\n'

以上说明成功访问了,但是存在一些网站我们通过以上的操作访问不成功,且手动点击却可以访问成功。大概率是因为我们的请求头的原因,看一下我们的请求头

r.request.headers
{'User-Agent': 'python-requests/2.18.4', 'Accept-Encoding': 'gzip, deflate', 'Accept': '*/*', 'Connection': 'keep-alive'}

可以看到我们的User-Agent非常诚实地告诉服务器,这个请求来自python,有一些服务器过滤了python的请求,自然就访问不到了。
这时我们可以自己构造请求头,使用headers参数,以字典形式传入

import requests
url = "http://python123.io/ws/demo.html"
head = {'User-Agent' : 'Mozilla/5.0 (Windows NT 6.1; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/53.0.2785.116 Safari/537.36',
'Accept-Encoding': 'gzip, deflate', 'Accept': '*/*', 'Connection': 'keep-alive'}
r = requests.get(url,headers=head)
r.request.headers
{'User-Agent': 'Mozilla/5.0 (Windows NT 6.1; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/53.0.2785.116 Safari/537.36',
 'Accept-Encoding': 'gzip, deflate', 'Accept': '*/*', 'Connection': 'keep-alive'}

这时可以看到我们的User-Agent变了。同理,其他参数也可以在字典中构建

如何向get中传递参数呢?这里我们使用百度搜索来介绍:我们打开百度的网址,进行一个简单的搜索,可以发现百度搜索是使用get传参的:www.baidu.com/s?wd=keyword 我们来尝试使用python搜索

import requests
kv = {'wd':'python'}
url = "http://www.baidu.com/s"
r = requests.get(url,params=kv)
print(r.request.url)
https://www.baidu.com/s?wd=python

成功进行访问。

这就是简单的get方式请求方法,对于POST方法,其实就是多了一个data参数


kv = {'key','value1','key2':'value2'}
r = requests.request('POST','http://python123.io.ws',data=kv)
body = '主体内容'
r = requests.request('POST', 'http://python123.io/ws', data=body)

举一个常见的例子,很多账号登陆的过程都是使用POST提交账号密码以及验证码

网络爬虫requests和bs4简单入门_第1张图片
我们可以看到提交是通过POST方式提交的,提交的内容email、password、vcode
接下来我们使用POST来提交这些参数。

kv = {'email':'[email protected]', 'password': '123', 'vcode':12}
r = requests.post(url,data=kv)
r.request.body #查看到自己所提交的内容

一样也是很简单。

最后我们写一个简单的爬取网络图片的代码框架

import requests
import os
 url = "http://pic16.nipic.com/20110819/1058141_160828281110_2.jpg"   #这是我在网上随便找的一张图
 root = "D://pics//"   #
 path = root + url.split('/')[-1]   #使用图片原来的名称
try:
	if not os.path exists(root):  #判断我们电脑上是否存在该路径,没有的话创建该路径
		os.mkdir(root)
	if not os.path.exists(path):  #判断该图片是否存在电脑,不存在就爬取
		r = requests.get(path)
		with open(path, 'wb') as f:
			f.write(r.content)    #r.content保存图片的二进制格式
			f.close()
			print(“文件保存成功”)
	else:
		print(“文件已存在”)
except:
	print("爬取失败")		

建议同学们使用try except来规范自己的代码。

使用BeautifulSoup对页面进行解析

主要功能:对html页面进行解析,通过各种方法以及属性提取关键信息
获取网页的html信息,接下来我们学习基于这个demo

import requests
from bs4 import BeautifulSoup
r = requests.get("http://python123.io/ws/demo.html")
r.encoding = r.apparent.encoding
demo  = r.text
soup = BeautifulSoup(demo,'html.parser')  # BeautifulSoup有好几种解析器,我们使用html.parser解析html页面
soup.find('a')   #以标签的格式返回第一个标签,为什么强调标签格式,因为后面使用的find_all()返回的是一个列表形式
*Basic Python*
soup.find_all('a')   #返回的是所有标签,并且是以列表形式返回的
*[Basic Python,
 Advanced Python]*

上面是使用标签来定位查找,我们也可以用标签内关键字来查找,比如使用id来查找

import re
soup.find_all(id=re.compile('link'))
*[Basic Python,
 Advanced Python]*

还可以使用字符串来查找,也就是我们html页面看到的内容

soup.find_all(string=re.compile('python'))
*['This is a python demo page',
 'The demo python introduces several python courses.']*

通过以上方法我们可以得到指定标签指定属性的值,或者是字符串的内容。

打印所有标签:

for tag in soup.find_all(True):
	print(tag.name)
html
head
title
body
p
....

中国大学排名 http://www.zuihaodaxue.com/zuihaodaxuepaiming2016.html 网站获取中国2016大学排名并输出
功能描述:
输入大学排名url链接
输出大学排名信息(排名,大学名称,总分)
设计步骤:
(1)从网络获取大学排名网页内容 getHTMLText()
(2)提取网页内容中的信息到合适的数据结构 fillUnivList()
(3)利用数据结构展示并输出结果 printUnivList()

import requests
import bs4
from bs4 import BeautifulSoup

#第一步,实现页面内容的读取
def getHTMLText(url):
	try:
		r = requests.get(url,timeout = 30)
		r.raise_for_status()
		r.encoding = r.apparent_encoding
		return r.text
	except:
		return " "
		
#第二步,提取html中关键的数据,这里我们使用二维的数据列表即可。
def fillUnivList(ulist,html):
	soup = BeautifulSoup(html, 'html.parser')  #html = getHTMLText(url)
	for tr in soup.find('tbody').children:  #从页面源码分析我们得到大学排名的标签是tbody的子标签
		if isinstance(tr, bs4.element.Tag) #	这里因为开始和最后有两个非element.Tag属性的标签,需要去除掉
			tds = tr.find_all('td')    #将下的标签传给tds,这样tds就是一个标签的列表
			ulist.append([tds[0].string, tds[1].string, tds[3].string])  #将排名,学校名称,分数以列表形式传递给ulist

#第三步:指定打印出多少个学校
def printUnivList(ulist, num):  #num指多少个学校
	tplt = "{0:^10}\t{1:{3}^10}\t{2:^10}"    #{3}表示以format中第三个变量来填充,chr(12288)是中文字符的空格,所以能够很好地显示    
	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.com/zuihaodaxuepaiming2016.html"    
    html = getHTMLText(url)    
    fillUnivList(uinfo, html)    
    printUnivList(uinfo, 20)
main()

效果图:

网络爬虫requests和bs4简单入门_第2张图片

你可能感兴趣的:(python)