c 抓取网页数据(计算机学院大数据专业大三的错误出现,有纰漏之处! )
优采云 发布时间: 2021-11-01 23:01c 抓取网页数据(计算机学院大数据专业大三的错误出现,有纰漏之处!
)
大家好,我不温柔,我是计算机学院大数据专业的大三学生。我的外号来自一个成语——不温柔,我要温柔的气质。博主作为互联网行业的新手,写博客一方面记录自己的学习过程,另一方面总结自己犯过的错误,希望能帮助到很多刚入门的年轻人他是。不过由于水平有限,博客难免会出现一些错误。如有疏漏,希望大家多多指教!暂时只在csdn平台更新,博客主页:。
PS:随着越来越多的人未经本人同意直接爬到博主文章,博主特此声明:未经本人许可禁止转载!!!
内容
前言
网络爬虫的一般流程
一、了解网址
基本 URL 收录以下内容:
模式(或协议)、服务器名(或IP地址)、路径和文件名,如“protocol://authorization/path?query”。带有授权部分的完整统一资源标识符语法如下所示:协议://用户名:密码@子域名。域名。顶级域名:端口号/目录/文件名。文件后缀?参数=值#符号。
例如:
二、常用的获取网页数据的方法2.1 URLlib
下面我们先来看一个小demo
# 百度首页
import urllib.request
response = urllib.request.urlopen("http://www.baidu.com")
html = response.read().decode("utf-8")
print(html)
2.2、urllib.request
官方文档(有兴趣的可以自行查看):
1、urllib.request.urlopen
urllib.request.urlopen(url,data = None,[timeout,]*,cafile = None, capath = None, cadefault = False,context = None)
timeout: 释放链接的超时时间
cafile/capath/cadefault:CA认证参数,用于HTTPS协议
上下文:SSL 链接选项,用于 HTTPS
2、urllib.request.Request
urllib.request.Request(url,data = None,headers = {
},origin_req_host = None,unverifiable = False,method = None)
详细代码:
# coding=utf-8
from urllib import request
from urllib.parse import urlparse
url = "http://httpbin.org/post"
headers = {
"user-agent": 'Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:73.0) Gecko/20100101 Firefox/73.0'
}
dict = {
"name":"buwenbuhuo"}
data = bytes(urllib.parse.urlencode(dict),encoding = "utf8")
req = request.Request(url=url,data=data,headers=headers,method="POST")
response = request.urlopen(req)
print(response.read().decode("utf-8"))
3、urllib.request 的高级特性
urllib.request 几乎可以做任何 HTTP 请求中的所有事情:
4、开瓶器
开场导演:
5、饼干
示例:获取百度 Cookie
import http.cookiejar,urllib.request
cookie = http.cookiejar.CookieJar()
handler = urllib.request.HTTPCookieProcessor(cookie)
opener = urllib.request.build_opener(handler)
response = opener.open("http://www.baidu.com")
for item in cookie:
print(item.name+"="+item.value)
filename = 'cookie.txt'
cookie = http.cookiejar.MozillaCookieJar(filename)
handler = urllib.request.HTTPCookieProcessor(cookie)
opener = urllib.request.build_opener(handler)
response = opener.open('http://www.baidu.com')
cookie.save(ignore_discard=True, ignore_expires=True)
2.3、请求库
Requests 是基于 urllib 用 python 语言编写的,使用 Apache2 Licensed 开源协议的 HTTP 库。与 urllib 相比,Requests 更方便,可以为我们节省很多工作。推荐爬虫使用Requests库。
官方文档链接:
1、请求库安装
在终端中运行以下命令:pip install requests
2、使用请求发起请求
import requests
import json
# 用requests发起简单的GET请求
url_get = 'http://httpbin.org/get'
response = requests.get(url_get,timeout = 5)
print(json.loads(response.text)['args'])
# 用requests发起带参数的GET请求
kvs = {
'k1':'v1','k2':'v2'}
response = requests.get(url_get,params=kvs,timeout = 5)
print(json.loads(response.text)['args'])
# 用requests 发起POST 请求
url_post = 'http://httpbin.org/post'
kvs = {
'k1':'v1','k2':'v2'}
response = requests.post(url_post,data=kvs,timeout = 5)
print(response.json()['form'])
从上图我们可以看出,方法名把请求表达的很清楚,get就是GET,post就是POST。不仅如此,我们可能得到的响应非常强大,可以直接获取很多信息,而且响应中的内容不是一次性的,requests会自动读取响应的内容并保存在text变量中。您可以根据需要多次阅读。其次,我们来看看响应中的有用信息:
print(response.url)
print(response.status_code)
print(response.headers)
print(response.cookies)
print(response.encoding) # requests会自动猜测响应内容的编码
import json
print(response.json() == json.loads(response.text)) # response.text 是响应内容,可以读取任意次,并且requests可以自动转换json
requests = response.request # 可以直接获取response对应的request
print(response.url)
print(response.headers) # 我们发起的request 是什么样子的一目了然
除了以上信息,响应还提供了很多其他信息。另外,request除了get和post之外,还提供了显式的put、delete、head、options方法,分别对应对应的HTTP方法。有兴趣的读者可以深入探讨。
3、Requests 库发起 POST 请求
这部分截取自官方文档:
通常,如果你想发送一些表单编码的数据——非常类似于 HTML 表单。为此,只需将字典传递给 data 参数。发出请求后,您的数据字典将自动对表单进行编码:
>>> payload = {
'key1': 'value1', 'key2': 'value2'}
>>> r = requests.post("https://httpbin.org/post", data=payload)
>>> print(r.text)
{
...
"form": {
"key2": "value2",
"key1": "value1"
},
...
}
data 参数对于每个键也可以有多个值。这可以通过创建数据元组列表或以列表作为值的字典来完成。当表单有多个使用相同键的元素时,这尤其有用:
import requests
>>> payload_tuples = [('key1', 'value1'), ('key1', 'value2')]
>>> r1 = requests.post('https://httpbin.org/post', data=payload_tuples)
>>> payload_dict = {
'key1': ['value1', 'value2']}
>>> r2 = requests.post('https://httpbin.org/post', data=payload_dict)
>>> print(r1.text)
{
...
"form": {
"key1": [
"value1",
"value2"
]
},
...
}
>>> r1.text == r2.text
True
4、requests.Session
import requests
# 创建一个session对象
s = requests.Session()
# 用session对象发出get请求,设置cookies
s.get('https://httpbin.org/cookies/set/sessioncookie/123456789')
# 用session对象发出另外一个get请求,获取cookies
r = s.get('https://httpbin.org/cookies')
# 显示结果
print(r.text)
请求的大多数用途类似于 urllib2。此外,请求的文档非常完整。这里我们主要讲解请求最强大最常用的功能:会话保留。上面的代码中,如果我们连续发起两次请求都没有关系,会导致部分数据不可用。喜欢:
import requests
url_cookies = 'http://httpbin.org/cookies'
url_set_cookies = 'http://httpbin.org/cookies/set?k1=v1&k2=v2'
print(requests.get(url_cookies,timeout = 5).json())
print(requests.get(url_set_cookies,timeout = 5).json())
print(requests.get(url_cookies,timeout = 5).json())
可以看到,调用url_set_cookies设置cookie前后发起的GET请求获取的cookie都是空的。这说明不同的请求之间没有关系。上面代码中第5行的输出可能会有人感到惊讶,因为在上一篇文章中,当我们使用urllib2发起同样的请求时,结果还是空的。这确实有点奇怪,因为 urllib2 默认会忽略所有请求的 cookie,即使是重定向的请求,请求也会在请求中保存 cookie(url_set_cookies 请求收录重定向请求)。
以下代码可以在一个会话中保留多个请求:
session = requests.Session()
print(requests.get(url_cookies,timeout = 5).json())
print(requests.get(url_set_cookies,timeout = 5).json())
print(requests.get(url_cookies,timeout = 5).json())
我们现在可以看到我们的第三个请求收录第二个请求设置的 cookie!是不是很简单。其实requests的内部cookies也用到了cookielib,有兴趣的同学可以深入探讨。
请求库的特点:
6、设置代理
import requests
url = 'http://httpbin.org/cookies/set?k1=v1&k2=v2'
proxies = {
'http':'http://username:[email protected]:port','http://username:[email protected]:port'}
print(requests.get(url,proxies = proxies,timeout = 5).json()['args'])
# 上面的方法要给每个请求都要加上proxies参数,比较繁琐,可以为每个session设置一个默认的proxies
session = requests.Session()
session.proxies = proxies # 一个session中的所有请求都使用同一套代理
print(session.get(url,timeout = 5).json()['args'])
当然上面的代码是不能运行的,因为代理的格式不对。当我们需要的时候,直接重用这段代码就行了。你可能会觉得之前在urllib2上的练习都是徒劳的,因为requests非常简单易学!当然也没有白费,urllib2是一个非常基础的网络库,其他很多网络库,包括requests,都是基于urllib2开发的。我们之前进行的练习将帮助我们更好地理解网络,了解Python对网络的处理,这对我们未来开发可靠高效的爬虫有很大的帮助。
需要注意的是:
响应中的内容以 unicode 编码。为了方便阅读,我们需要把它转换成中文。无法直接打印。因为python在将dict转换为字符串时保留了unicide编码,所以直接打印的不是中文。
这里我们使用另一种转换方法:先将得到的form dict转换成unicode字符串(注意ensure_ascii=False参数,表示unicode字符没有转义),然后将得到的unicode字符串编码成UTF-8字符串最终转换为 dict 以便于输出。
三、浏览器简介
Chrome 提供了检查网页元素的功能,称为 Chrome Inspect。您可以在网页上右键查看该功能,如下图:
在这个页面调出Chrome Inspect,我们可以看到类似如下的界面:
通常我们最常用的功能是查看某个元素的源代码,点击左上角的元素定位器,可以在网页中选择不同的元素,HTML源代码区会自动显示指定的源代码元素,通常CSS显示区域也会显示这个应用于元素的样式。Chrome Inspect 比较常用的功能是监控网络交互过程。在功能栏中选择网络,可以看到如下界面:
Chrome 网络的交互区域展示了一个网页加载过程以及浏览器发起的所有请求。选择一个请求,右侧会显示请求的详细信息,包括请求头、响应头、响应内容等。Chrome网络是我们研究网页交互过程的重要工具。Cookie 和 Session 是重要的网络技术。您还可以在 Chrome Inspect 中查看网络 cookie。在功能栏中选择应用,可以看到如下界面:
在 Chrome 应用程序的左侧选择 Cookies,您可以看到以 KV 形式保存的 cookie。这个功能在我们研究网页的登录过程时非常有用。需要注意的是,在研究一个完整的网络交互过程之前,记得右键点击Cookies,然后点击Clear清除所有旧的Cookies。
HTTP 响应的第一行,即状态行,收录状态代码。状态码由三位数字组成,表示服务器对客户端请求的处理结果。状态码分为以下几类:
1xx:信息响应类型,表示接收到请求并继续处理
2xx:处理成功响应类,表示动作成功接收、理解和响应
3xx:重定向响应类,为了完成指定的动作,必须进行进一步的处理
4xx:客户端错误,客户端请求收录语法错误或服务器无法理解
5xx:服务器错误,服务器无法正确执行有效请求
以下是一些常见的状态代码及其说明:
200 OK:请求已被正确处理和响应。
301 Move Permanently:永久重定向。
302 Move Temporously:临时重定向。
400 Bad Request:服务器无法理解请求。
401 Authentication Required:需要验证用户身份。
403 Forbidden:禁止访问资源。
404 Not Found:未找到资源。
405 Method Not Allowed:对资源使用了错误的方法。例如,应该使用POST,但使用PUT。
408 请求超时:请求超时。
500 内部服务器错误:内部服务器错误。
501 方法未实现:请求方法无效。如果可能,将 GET 写为 Get。
502 Bad Gateway:网关或代理收到来自上游服务器的错误响应。
503 Service Unavailable:服务暂时不可用,您可以稍后再试。
504 Gateway Timeout:网关或代理请求上游服务器超时。
在实际应用中,大部分网站都有反爬虫策略,响应状态码代表服务器的处理结果,对于我们调整服务器的爬虫状态(如频率、ip)有重要的参考意义。履带。比如我们一直正常运行的爬虫,突然收到403响应。这可能是因为服务器识别了我们的爬虫并拒绝了我们的请求。这时候我们就得减慢爬取频率,或者重启Session,甚至更改IP。
美好的日子总是短暂的。虽然我还想继续和你谈谈,但这篇博文现在已经结束了。如果还不够,别着急,我们下篇文章见!
一本好书永远不会厌倦阅读一百遍。而如果我想成为全场最漂亮的男孩,我必须坚持通过学习获得更多的知识,用知识改变命运,用博客见证成长,用行动证明我在努力。
如果我的博客对你有帮助,如果你喜欢我的博客内容,请一键“点赞”“评论”“采集”!听说喜欢的人运气不会太差,每天都充满活力!如果你真的想当妓女,祝你天天开心,欢迎访问我的博客。
码字不易,大家的支持是我坚持下去的动力。喜欢后别忘了关注我哦!