我是靠谱客的博主 外向小松鼠,最近开发中收集的这篇文章主要介绍Python笔记九:网络爬虫及requests库、beautifulsoup4库解析和处理HTML,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

一、网络爬虫及requests库

# 网络爬虫
import requests
def gethtml(url):
    try:
        r = requests.get(url,timeout=300)
        #r.raise_for_status() #如果不是200则产生异常,页面状态返回304,也会异常,所以暂时注释
        r.encoding = 'utf-8'
        return r.text
    except:
        return "error"
print(gethtml("https://www.xxxx.edu.cn/yxsz/jsjxy.htm"))

直接调用gethtml()函数可能会被防火墙拦截,导致无法访问

 1.解决办法:添加请求标头

# 网络爬虫天添加使用请求标头访问
import requests
def gethtml(url,headers):
    try:
        r = requests.get(url,headers=headers,timeout=300)
        #r.raise_for_status() #如果不是200则产生异常,页面状态返回304,也会异常,所以暂时注释
        r.encoding = 'utf-8'
        return r.text
    except:
        return "error"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/103.0.5060.134 Safari/537.36 Edg/103.0.1264.77",
"Cookie":"__jsluid_s=68e5061305a17f63a83b50893c264a29; JSESSIONID=D7C74F0B47831552FAD50EFF5AFCB159"
}

soup = gethtml("https://www.xxx.edu.cn/yxsz/jsjxy.htm",headers)
print(soup)

绕过限制成功访问

2.请求标头的通用方法:

headers = """Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9
Accept-Encoding: gzip, deflate, br
Accept-Language: zh-CN,zh;q=0.9,en;q=0.8,en-GB;q=0.7,en-US;q=0.6
Cache-Control: max-age=0
Connection: keep-alive
Cookie: __jsluid_s=68e5061305a17f63a83b50893c264a29; JSESSIONID=D7C74F0B47831552FAD50EFF5AFCB159
Host: www.xxx.edu.cn
Upgrade-Insecure-Requests: 1
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/103.0.5060.134 Safari/537.36 Edg/103.0.1264.77
"""

pattern = re.compile(r"([a-z.-]+):s*(.+)",re.I)#查找:英文+空格+字符串+n
dt=pattern.findall(headers)
headers = dict(dt)

 使用正则表达式,需引入re库。

第30行生成正则表达式,用“冒号:将每一行分割出两部分,re.I忽略大小写。更详细的正则参考

Python 正则表达式 | 菜鸟教程 (runoob.com)

第31行使用findall()函数将headers变量转换为列表,每行为键值对的元组。

使用浏览器访问网站,使用F12打开开发人员工具,复制请求标头到代码headers变量中,即可模拟浏览器访问

3.使用python变量时候,一定要注意变量的类型,例如:m=‘{1:2,3:4}’,尽管m变量内容与字典一致,但仍为字符串变量,不能使用dict(m)转换为字典。而使用eval(m)转换为字典。

m = '{1:2,3:4}'
print(dict(m))

list()将字符串的每个字符都作为元素,创建一个列表 

m = '[1,2,3,4]'
print(list(m))

 结论:值或内容符合列表、字典等数据内容的字符串变量,可以使用eval()函数转换为相应的python数据类型。

m = '{1:2,3:4}'
n = eval(m)
print(type(n),n)

dict()函数可以直接将每个元素为双元素元组的列表直接转为字典。

m = [(1,2),('a','b')]
n = dict(m)
print(type(n),n)

还可以使用正则表达式的findall()函数将headers变量转换为元素为元组的列表,再用dict()转为字典类型。 参见前文。 

 二、beautifulsoup4库解析和处理HTML

# 网络爬虫
import requests
from bs4 import BeautifulSoup
def gethtml(url,headers):
    try:
        r = requests.get(url,headers=headers,timeout=300)
        #r.raise_for_status() #如果不是200则产生异常,页面状态返回304,也会异常,所以暂时注释
        r.encoding = 'utf-8'
        soup = BeautifulSoup(r.text)
        return soup
    except:
        return "error"
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/103.0.5060.134 Safari/537.36 Edg/103.0.1264.77",
"Cookie":"__jsluid_s=68e5061305a17f63a83b50893c264a29; JSESSIONID=D7C74F0B47831552FAD50EFF5AFCB159"
}

soup = gethtml("https://www.xxx.edu.cn/yxsz/jsjxy.htm",headers)
dd = soup.find_all("dd")
print(dd)
link = {}
for a in dd:
    aa = a.find_all("a")
    for s in aa:
        link[s.string] = s.attrs["href"]
#print(link)

 1.使用BeautifulSoup()函数创建一个BeautifulSoup对象,BeautifulSoup对象是一个树形结构,它包含HTML页面中的每一个Tag标签(元素),如<head>,<body>,可以使用<a>.<b>,<a>为对象名称,<b>为HTML标签的名字,直接调用soup.b只能返回一个b标签,要访问多个则使用find_all(b)。

 

 

 第22行,循环dd,第23行,获取每个<dd>.<a>,第24循环aa,将HTML中的<a>的string及属性attrs中的href分别作为键值写入字典link中。

2.BeautifulSoup对象的常用属性有:name(字符串)、attrs(字典)、contents(列表)、string(字符串)

对应Tag标签结构

<a class="v1" href="mkszyxy.htm">马克思主义学院</a>

其中尖括号<>中标签的名字a为name,尖括号内其他项“class="v1" href="mkszyxy.htm"”都是attrs,尖括号之间“马克思主义学院”为string,这个Tag下的所有子Tag的内容为contents

3、爬取页面table

soup = gethtml("https://zhaosh.xijing.edu.cn/zhaosheng/search?year=2021&cengci=3&shengfen=&kelei=",headers)
table = soup.find_all("table")
print(table)

Python执行结果:

BeautifulSoup对象table

3.find_all()函数

find_all(tag, attributes, recursive, text, limit, keywords)
find(tag, attributes, recursive, text, keywords)

 一般只用前2个参数:tag,attributes

tag
可以传一个标签的名称或多个标签名称组成的 Python列表做标签参数。例如:.find_all({"h1","h2","h3","h4","h5","h6"})

attributes
属性参数 attributes 是用一个 Python 字典封装一个标签的若干属性和对应的属性值。例如,下面这个函数会返回 HTML 文档里红色与绿色两种颜色的 span 标签:
.find_all("span", {"class":{"green", "red"}})
如果只返回一种颜色的,如绿色:
.find_all("span", {"class": "green"})

recursive
递归参数 recursive 是一个布尔变量。你想抓取 HTML 文档标签结构里多少层的信息?如果recursive 设置为 True , find_all 就会根据你的要求去查找标签参数的所有子标签,以及子标签的子标签。如果 recursive 设置为 False , find_all 就只查找文档的一级标签。 find_all默认是支持递归查找的( recursive 默认值是 True );一般情况下这个参数不需要设置。

text
文本参数 text 有点不同,它是用标签的文本内容去匹配,而不是用标签的属性。假如我们想查找前面网页中包含“the prince”内容的标签数量,我们可以把之前的 find_all 方法换成下面的代码:

nameList = bsObj.find_all(text="the prince")
print(len(nameList))

limit
范围限制参数 limit ,显然只用于 find_all 方法。 find 其实等价于 find_all 的 limit 等于1 时的情形。如果你只对网页中获取的前 x 项结果感兴趣,就可以设置它。

keywords
可以让你选择那些具有指定属性的标签,属于冗余的技术,如下所示:第一行采用keywords,第二行采用前两个参数:tag、attributes

bsObj.find_all(id="text")
bsObj.find_all("", {"id":"text"})
用 keyword 偶尔会出现问题,尤其是在用 class 属性查找标签的时候,因为 class 是 Python 中受保护的关键字。所以一般只采用前2个参数tag、attributes即可。

最后

以上就是外向小松鼠为你收集整理的Python笔记九:网络爬虫及requests库、beautifulsoup4库解析和处理HTML的全部内容,希望文章能够帮你解决Python笔记九:网络爬虫及requests库、beautifulsoup4库解析和处理HTML所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(39)

评论列表共有 0 条评论

立即
投稿
返回
顶部