IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> Python知识库 -> python爬虫请求和解析库概述 -> 正文阅读

[Python知识库]python爬虫请求和解析库概述

python爬虫篇2—请求和解析库概述

? 前言: 为了节省时间和避免赘述,很多内容我都会省略,因为这些内容看官方文档或者别人写的详细博客即可,我这里仅仅做概述,方便后面写案例。

? 本文思维导图:

在这里插入图片描述

一、request库:

1. 功能概述:

? request库是一个python第三方爬虫库,也是我们最为常用的请求库之一。

? 针对于静态网页,request库是最佳选择,其不仅可以实现get请求,也可以实现post请求等操作。

2. 安装方法:

? 安装方法一:

1. 打开windows的命令行窗口(win+r 输入 cmd即可打开)
2. 输入: pip install request 即可安装

? 安装方法二:

1. 对于集成环境的朋友来说,直接使用自带的安装库的方法即可

? 可以使用下面的代码检验是否安装成功:

# 导入模块
import requests
# 定义url
url = 'https://www.baidu.com'
# 请求地址|
response = requests.get(url)
# 打印结果
print(response.content.decode('utf-8'))

? 如果安装成功,结果如下:

在这里插入图片描述

3. 简单案例:

? 案例是最好的解释。

# 导入模块
import requests
# 定义url
url = 'https://www.baidu.com'
# 请求地址|
response = requests.get(url)
# 打印结果
print(response.status_code)

? 结果为:

200

? 那么,上面的代码中涉及到了两个知识点:

  • get方法
含义: get请求方式
参数1: url,需要请求的链接地址
  • response对象
含义: 响应对象
属性1:status_code ,响应状态码,200表示正常

4. response对象详解:

? response对象有几个重要的属性要说一说。

  • url属性:返回响应服务器的url

? 这个属性还是有用的,因为有时候网页会有重定向,即我们访问的是A网址,但是重定向后实际访问的是B网址,通过这个属性我们可以确定究竟访问的是哪个网页。

  • status_code属性: 返回响应状态码
  • cookies属性: 返回cookie对象
  • text属性: 返回网页的源码,但是是按照chardet模块推测出的编码进行解码的结果。
  • content属性:返回源码的bytes形式结果

5. get请求:

? get请求是平时我们最常用的请求方式之一。在requests模块中,提供给我们了非常方便的get请求方式:

import requests
url = 'http://www.baidu.com'
response = requests.get(url)
print(response.status_code)

常用的参数:

参数作用
url请求的地址
headers请求头参数(字典)
params请求的参数(字典)
cookies请求的cookies参数(字典)
timeout超时时间设置

简单案例:

? 之前我们请求百度,可以发现百度返回的内容非常少,这是我们被百度检测出我们是一个爬虫,因此返回给我们的内容十分的少。

? 这里,我们使用带有headers参数的get请求去请求百度网页,这里为了直观的看到结果,我们把返回的源码保存到一个html文件中:

import requests
url = 'http://www.baidu.com'
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/94.0.4606.71 Safari/537.36',
}
response = requests.get(url,headers=headers)
result = response.content.decode('utf-8')
f = open('test.html','w',encoding='utf-8')
f.write(result)
f.close()

? 结果如下:

在这里插入图片描述

百度搜索案例:

? 这里,我们使用百度搜索案例来演示一下params这个参数的用法。

? 首先,基于前端的简单知识(在上一篇中提及过),我们可以知道url http://xxxx/?id=1 中的问号后面接的是参数,因此,我们观察一下百度搜索的url:

https://www.baidu.com/s?wd=python

? 可以知道,它实际上是通过参数wd来判断你搜索的内容的,因此,我们可以这么来写我们的代码:

import requests
# 请求地址
url = 'https://www.baidu.com/s?'
# 参数
target = input('请输入你想要搜索的内容:')
params = {
    'wd' : target,
}
# 请求头
headers = {
    'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/97.0.4692.99 Safari/537.36',
    'Cookie': 'BIDUPSID=4CB26999F28A00A64AA6BE786D45B9A9; PSTM=1623650616; __yjs_duid=1_a457dc40612f68c8a71b918beebc7b7d1623650934507; BD_UPN=12314753; BDUSS=ViVDExTE5SMlZ6aUd6UlZndWdLREtESDUzMUhzRVNEeWQ3WHVoTHZKa2JUMVJoRUFBQUFBJCQAAAAAAAAAAAEAAABpREyizsSz8zY2NgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABvCLGEbwixhc1; BDUSS_BFESS=ViVDExTE5SMlZ6aUd6UlZndWdLREtESDUzMUhzRVNEeWQ3WHVoTHZKa2JUMVJoRUFBQUFBJCQAAAAAAAAAAAEAAABpREyizsSz8zY2NgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABvCLGEbwixhc1; BAIDUID=9FA5CAAD04AA64664A5A35D065D065F9:FG=1; BDORZ=FFFB88E999055A3F8A630C64834BD6D0; ab_sr=1.0.1_N2NjZjI2OWNkZGQ5ZjcyMTIxYzEwNjQwODA5NDI3OGZlNThkYzMxOTYyZjIwOThiZDI3YjQ2ZTYzNzM2MDE5MjMwM2IyNzU0NTE0ZGRhMzQ2OGQwZmRmN2Q5MzhjOWYyODE4NGQzOTJkMWQxMDc0OTIyODM2ZmE3YjgzNzg3YmM5OGM3NGU0NDMxNzQ3Mzk4ZTY4ZGI0M2IzYmY2ZjI5OWUxMjM4ZGRmM2MyMDlkMDdhYzRjYjU4M2M3YjAwOTkw; H_PS_PSSID=26350; H_PS_645EC=5222lq27BgNSzJVJHM%2BGLOhAPQYORidu8wdU1IM8odpIQ5jkd3wiey6dLivbK05hfv1sJaQzcjgc; BAIDUID_BFESS=9FA5CAAD04AA64664A5A35D065D065F9:FG=1; baikeVisitId=fce62568-7213-40b8-b559-bf44b3e19c3f; BDSVRTM=0'
}
response = requests.get(url=url,headers=headers,params=params)
# 保存结果于文件中
result = response.content.decode('utf-8')
f = open('test.html','w',encoding='utf-8')
f.write(result)
f.close()

? 结果如下:

在这里插入图片描述

? 这里我要提及一句,我记得一年前我写这个爬虫的时候,请求头只需要带上user-agent即可,但是现在必须还带上cookie,不然会被百度识别出来是爬虫。

6. post请求:

? post请求也是我们网站中最常用的请求方式之一,一般提交表单几乎都是post请求。而,在requests模块中,post请求与get请求的使用方法上差别在于参数(params与data):

data: 接收一个字典,里面爬虫发出的数据

? 下面举一个例子,比如豆瓣登录页面,我们知道想要登录肯定是需要输入用户名和密码的,那么我们输入的用户名和密码就是参数data中的value,那么key是哪个呢?这里有两个方法,一个就是抓包才看;另外一个就是看其css代码,如下:

在这里插入图片描述

? 不难看出,key值分别为username and password

? 因此,我们传入的data参数为:

data = {
	'username':'xx',
	'password':'123456'
}

7. 代理设置:

? 使用代理,有两个目的:

1. 提高访问效率
2. 减少自己ip暴漏风险

? 因为,一个人正常人不可能在1s内访问网页几十次,但是几十个人可以在1s内访问几十次。代理ip就是这个道理,你可以构建一个ip池,这样你的爬虫可以使用不同的ip,达到1s内访问几十次的目的。

? 而,在requests库中,get、post请求方法中都有一个参数 proxies ,这个参数就是设置代理使用的。

? 使用方法如下:

import requests

proxies = {
    # key为指定格式,后面的value为代理ip网站提供给你的ip地址和端口
    'http/https':'http/https:ip:port',
    'http/https':'http/https:ip:port',
    'http/https':'http/https:ip:port',
    'http/https':'http/https:ip:port'
}
requests.get(url,proxies=proxies)

8. 会话维持:

? 登录网站需要post请求,但是post请求是一次性的,相当于你登录成功后就又断开了,因此想要保持连接,我们称为会话维持,还是很形象。

? 使用思路如下:

#下面给出的是思路,不是具体的代码,具体的代码还是根据实际案例来讲
import requests

#创建session对象
session = requests.session()
#使用session对象去发送post请求
session.post(.....)     #这里post的用法和requests.post()用法一致
#请求成功后再用session对象去请求只有登录才能访问的页面
response = session.get(....)   #这里post的用法和requests.get()用法一致
#接下来再去操作即可

二、lxml库:

? 解析库有很多,经典的比如:lxml、re、bs4、pyquery等。掌握1-2个即可,其它的了解一下就可以了,反正又用不到那么多是吧。

1. 安装方法:

? 安装方法类似request安装方法,这里不赘述。

2. 使用案例:

from lxml import etree		#我们主要使用的lxml库中的etree库
text = '''
<body>
    <div class="key">
        <div class="iocnBox"><i class="iconfont icon-delete"></i></div>
        <div class="empty">清空</div>
        <textarea placeholder="在此述说新年寄语..." rows="1" class="van-field__control"></textarea>
        <div class="buts">发送</div>
    </div>
'''
#开始初始化
html = etree.HTML(text)		#这里需要传入一个html形式的字符串
# 之后可以开始获取内容了

? 通过上面的代码中,不难看出,想要使用lxml的一个前提是你已经获得了网页源代码

? 另外,使用lxml的第一个步骤就是初始化,生成一个lxml对象,这里我们用变量html接收。

3. 寻找节点/标签:

语法含义
nodename(节点名字)直接根据写的节点名字查找节点,如:div
//在当前节点下的子孙节点中寻找,如://div
/在当前节点下的子节点中寻找,如:/div
.代表当前节点(可省略不写,就像我们有时候写的相对路径),如:./div
当前节点的父节点,如:…/div

? 感觉上面的说明还是很详细了,但是还是需要一些例子来告诉你如何使用它们。

? 首先,我们的网页源代码为:

text = '''
<body>
    <div>这时测试的div</div>
    <div>
        <div>
            这是嵌套的div标签
            <p>
                这时嵌套的p标签
            </p>
        </div>
    </div>
    <p>这时测试的p</p>
</body>
'''

? 那么,问题一:找到所有的div标签?

html = etree.HTML(text)
result = html.xpath('//div')

? 问题二:找到div里面的p标签?

 html = etree.HTML(text)
 result = html.xpath('//div//p')

? 问题三:找到最后一个p标签?

 html = etree.HTML(text)
result = html.xpath('//body/p')

? 打印一下第一个问题的结果:

[<Element div at 0x17e41ae8ec8>, <Element div at 0x17e41ae8f08>, <Element div at 0x17e41ae8448>]

? 可以看见,返回的是一个列表,里面有三个元素,对应了三个div标签。

4. 筛选节点:

? 当我们使用筛选时,筛选的方法都是包含在[](中括号)中的。

属性筛选

方法名\符号作用
@获取属性或者筛选属性,如:@class
contains判断属性中是否含有某个值(用于多值判断),如:contains(@class,‘hello’)

? 一个小例子:

from lxml import etree

text = '''
<div class="hello">
    <p>Hello,this is used to tested</p>
</div>
<div class="hello test hi">
    <div>
        <div>你好,这是用于测试的html代码</div>
    </div>
</div>

<div class="button">
    <div class="menu">
        <input name="btn" type="button" value="按钮" />
    <div>
</div>
'''

#初始化
html = etree.HTML(text)
#根据单一属性筛选

#筛选出class="hello"的div标签
hello_tag = html.xpath('//div[@class="hello"]')		#注意筛选的方法都是在中括号里面的
print(hello_tag)	#结果为: [<Element div at 0x2ba41e6d088>],即找到了一个标签,符合条件

#找出具有name="btn"的input标签
input_tag = html.xpath('//input[@name="btn"]')
print(input_tag)	#结果为:[<Element input at 0x1751d29df08>],找到一个input标签,符合条件

#筛选出具有class="hello"的div标签
hello_tags = html.xpath('//div[contains(@class,"hello")]')
print(hello_tags)	#结果为:[<Element div at 0x1348272d248>, <Element div at 0x1348272d6c8>],即找到了两个div标签,符合条件

按序选择

? 有时候我们会有这样的需求,我们爬取的内容是一个table标签(表格标签),或者一个ul(标签),了解过html的应该都知道这样的标签,内部还有很多标签,比如table标签里就有tr、td等,ul里面就有li标签等。对于这样的标签,我们有时候需要选择第一个或者最后一个或者前几个等。这样的方式我们也可以实现。

方法作用
last()获取最后一个标签
1获取第一个标签
position() < = > num筛选多个标签(具体见实例)

? 注意:这里需要注意这里的序是从1开始而不是从0开始。

? 一个小例子:

from lxml import etree

text = '''
<ul>
    <li>1</li>
    <li>2</li>
    <li>3</li>
    <li>4</li>
    <li>5</li>
    <li>6</li>
    <li>7</li>
    <li>8</li>
</ul>     
'''

#初始化
html = etree.HTML(text)

#获取第一个li标签
first_tag = html.xpath('//li[1]')	#令人吃惊,lxml并没有first()方法
print(first_tag)

#获取最后一个li标签
last_tag = html.xpath('//li[last()]')
print(last_tag)

#获取前五个标签
li_tags = html.xpath('//li[position() < 6]')
print(li_tags)

逻辑和计算

? 其实在写筛选时是可以加入逻辑方法的,如:and、or、>、>=等。当然也是可以写入一些计算方法的,如:+、-等。

? 下面给出示例:

from lxml import etree

text = '''
<ul>
    <li>1</li>
    <li>2</li>
    <li>3</li>
    <li>4</li>
    <li>5</li>
    <li>6</li>
    <li>7</li>
    <li>8</li>
</ul>     
'''

#初始化
html = etree.HTML(text)

#获取第二个li标签,使用=判断
second_tag = html.xpath('//li[position() = 2]')
print(second_tag)

#获取第一个和第二个标签,使用or
tags = html.xpath('//li[position() = 1 or position() = 2]')
print(tags)

#获取前三个标签,使用<
three_tags = html.xpath('//li[position()<4]')
print(three_tags)

5. 获取内容:

? 我们寻找标签、筛选标签的最终目的就是获取它的属性或者文本内容。下面讲解获取文本和属性的方法。

方法作用
@获取属性或者筛选属性
text()获取文本

? 获取文本举个例子:

from lxml import etree

text = '''
<div class="hello">
    <p>Hello,this is used to tested</p>
</div>
<div class="hello test hi">
    <div>
        <div>你好,这是用于测试的html代码</div>
    </div>
</div>

<div class="button">
    <div class="menu">
        <input name="btn" type="button" value="按钮" />
    <div>
</div>
'''

#初始化
html = etree.HTML(text)

#获取第一个div中的p标签中的文本
content = html.xpath('//div/p/text()')    #注意使用text()的时机和位置
print(content)  #结果为:['Hello,this is used to tested'],仍然是以列表形式返回结果

#获取拥有第二个div中的文本,注意观察下面的不同之处
content_two = html.xpath('//div[position() = 2]/text()')
print(content_two)  #结果为: ['\n    ', '\n']

content_three = html.xpath('//div[position() = 2]//text()')
print(content_three)  #结果为: ['\n    ', '\n        ', '你好,这是用于测试的html代码', '\n    ', '\n']
#两者不同之处在于:一个为//,一个为/。我们知道//获取其子孙节点中的内容,而/只获取其子节点的内容。

? 获取属性也举个例子:

from lxml import etree

text = '''
<div class="hello" name="test">
    <p>Hello,this is used to tested</p>
</div>
<div class="hello test hi">
    <div>
        <div>你好,这是用于测试的html代码</div>
    </div>
</div>

<div class="button">
    <div class="menu">
        <input name="btn" type="button" value="按钮" />
    <div>
</div>
'''

#初始化
html = etree.HTML(text)

#获取第一个div的name属性
first_div_class = html.xpath('//div[@class="hello"]/@name')
print(first_div_class)  #结果为:['test']

#获取input标签的name值
input_tag_class = html.xpath('//input/@name')
print(input_tag_class) #结果为:['btn']
  Python知识库 最新文章
Python中String模块
【Python】 14-CVS文件操作
python的panda库读写文件
使用Nordic的nrf52840实现蓝牙DFU过程
【Python学习记录】numpy数组用法整理
Python学习笔记
python字符串和列表
python如何从txt文件中解析出有效的数据
Python编程从入门到实践自学/3.1-3.2
python变量
上一篇文章      下一篇文章      查看所有文章
加:2022-09-30 00:49:11  更:2022-09-30 00:49:41 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/16 8:42:50-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码