BeautifulSoup库/bs4 基础&深入 技术干货

BeautifulSoup库的安装

pip install bs4

对HTML的装载,prettify()即表示整理,能清晰的显示文档结构(文档数)

 soup  = BeautifulSoup(doc,"lxml")
 s = soup.prettify()
 print("s")

如果HTML缺失缺失,beautifulsoup库会自动补缺。

BeautifulSoup查找文档元素

获取网页html代码以后,那么我们要把它装在在一个beautifulsoup的对象当中,那么如何在文档中找到目标元素

  1. 如何查找html元素
    利用find_all()函数,其原型为:
find_all(self,name = None, attrs = {},
recursive = True, text = None, 
limit = None,**kwargs)
元素含义
self类成员函数
name要查找的tag元素名称,默认是None,如果不提供,就是查找所有的元素
attrs是元素的属性,字典,默认是空,如果提供就是查找有这个指定属性的元素

find_all函数是查找所有满足要求的元素节点,如果只查找一个元素节点就可以使用find()函数

find(self, name = None, attrs = {}, 
recursive = True,text = None,
 limit = None, **kwargs)

其使用方法与find_all类似,不同的是它只返回第一个满足要求的节点,不是一个列表。

示例:查找文档中class="title"的< p >元素

from bs4 import BeautifulSoup
doc = '''
<html><head><title>the Dormouse's story</title></head>
<body>
<p class="title"><b>the Dormouse's story</b></p>
<p class="story">
once uopn a time ther were three little sisters;and their names were
<a href="http://example.com/elsie"class="sister"
id="link1"elsie</a>,
<a href="http://example.com/lacie"class="sister"
id="link2">lacie</a>and
<a href="http://example.com/tillie"class="sister"
id="link3">tillie</a>;
and they lived an the bottom of a well.
</p>
<p class="story">...</p>
</body>
</html>

'''

利用find()函数

soup = BeautifulSoup(doc,"lxml")
tag = soup.find_all("p", attrs = {"class":"title"})
print(tag)
#result:<p class="title"><b>the Dormouse's story</b></p>

因为这条目标信息因为其位置在最前面,所以用find()同样也能找到。

soup = BeautifulSoup(doc,"lxml")
tags = soup.find_all(name = None, attrs = {"class":"sister"})
for tag in tags:
    print(tag)
#result:
<a class="sister" elsie="" href="http://example.com/elsie" id="link1">,
</a>
<a class="sister" href="http://example.com/lacie" id="link2">lacie</a>
<a class="sister" href="http://example.com/tillie" id="link3">tillie</a>

对于这个文档同样可以使用:

tags = soup.find_all("a")
tags_1 = soup.find_all("a",attrs = {"class","sister"})
print(tags)
print("\n",tags_1)
#result:
[<a class="sister" elsie="" href="http://example.com/elsie" id="link1">,
</a>, <a class="sister" href="http://example.com/lacie" id="link2">lacie</a>, <a class="sister" href="http://example.com/tillie" id="link3">tillie</a>]

 [<a class="sister" elsie="" href="http://example.com/elsie" id="link1">,
</a>, <a class="sister" href="http://example.com/lacie" id="link2">lacie</a>, <a class="sister" href="http://example.com/tillie" id="link3">tillie</a>]

两者效果一致

BeautifulSoup获取元素的属性值

如果一个元素已经找到,例如找到< a >元素,则可以通过tag[attrName]来获取tag元素的名称为attrName的属性值,其中tag是一个bs4.element.Tag对象。
例如:查找文档中所有的超链接地址

soup = BeautifulSoup(doc,"lxml")
tags = soup.find_all("a")
for tag in tags:
    print(tag["href"])
 #result:
 http://example.com/elsie
http://example.com/lacie
http://example.com/tillie

BeautifulSoup获取元素包含的文本值

使用方法:tag,text来获取tag元素包含的文本值,其中tag是一个bs4.element.Tag对象。
例如:查找文本中所有< a >超级链接包含的文本值

soup = BeautifulSoup(doc,"lxml")
tags = soup.find_all("a")
for tag in tags:
    print(tag.text)
#result:
,

lacie
tillie

tag.text获取的结果为一个标签下的所有文本

BeautifulSoup的高级查找

一般find或者find_all都能满足我们的需要,如果还不能,则可以设计一个查找函数来进行查找。

def mefilter(tag):
    print(tag.name)
    return(tag.name == "a" and tag.has_attr("href")and tag["href"]=="http://example.com/lacie")

soup = BeautifulSoup(doc,"lxml")
tag = soup.find_all(mefilter)
print("tag")
#result:
html
head
title
body
p
b
p
a
a
a
p
tag

说明:程序的运行中定义了一个筛选函数myfilter(tag)它的参数是tag对象,在调用soup.find_all(myfilter)时候会把每个tag元素传递给myfilter函数,返回True则取,否则就丢弃。

BeautifulSoup查找文档元素

高级查找要注意“class”标签为列表结构

def mefilter(tag):
    if tag.name == "p" and tag["class"] =="story":
        return True
soup = BeautifulSoup(doc,"html.parser")
tags = soup.find_all(mefilter)
print(tags)

def mefilter(tag):
    if tag.name == "p" and tag["class"] == ["story"]:
        return True
soup = BeautifulSoup(doc,"html.parser")
tags = soup.find_all(mefilter)
print("\n",tags)
#result:
[]

 [<p class="story">
once uopn a time ther were three little sisters;and their names were
<a a="" class="sister" elsie<="" href="http://example.com/elsie" id="link1">,
<a class="sister" href="http://example.com/lacie" id="link2">lacie</a>and
<a class="sister" href="http://example.com/tillie" id="link3">tillie</a>;
and they lived an the bottom of a well.
</a></p>, <p class="story">...</p>]

tag[“class”]是一个很特殊的属性
倘若文本为< p class=“story exem”>,那么就应该写为:

tag["class"] == ["story","exem"]

BeautifulSoup遍历文档元素

获取元素节点的父节点、子节点、临近节点,所有子孙节点,兄弟节点

目的操作
获取父节点tag.parent
获取元素的直接子节点tag.children
获取tag节点的所有子孙节点元素,包括element,text等类型的节点tag.desendants
下一个兄弟节点tag.next_sibling
前一个兄弟节点tag.previous_sibling
#eg_1
soup = BeautifulSoup(doc,"lxml")
print(soup.name)
tag = soup.find("b")
while tag:
	print(tag.name)
	tag = tag.parent
#eg_2
suop = BeautifulSoup(doc,"lxml")
tag = soup.find("b")
print(tag.previous_sibling)

BeautifulSoup使用CSS语法查找元素
其除了自身的函数,还可以用CSS语法
CSS语法
tag.select(css)
其结构为:
[tagName][attName[=value]]
其中[…]部分是可选的

变量含义
tagName元素名称,没有指定就是所有元素
attName = value属性名称,value是它对应的值
tag.select(css)返回一个bs4.element.Tag的列表,可能只有一个元素

各种应用具体操作方法

目标代码
soup.select(“p a”)查找文档中所有< p >节点下的所有< a >节点
soup.select(“p[class=‘story’] a”)查找文档中所有属性class="story"的< p >节点下的所有< a >元素节点
soup.select(“p[class] a”)查找文档中所有具有class属性的< p >< a >元素节点
soup.select(“body head title”)查找下面< head >的< title >节点
soup.select(“body[class]”)查找< body >下面所有具有class属性的节点
soup.select(“body[class] a”)查找< body >下面所有具有class属性的节点下面的< a >节点
soup.select(“a[id=‘link1’]”)查找属性id="link1"的< a >节点

属性的语法规则

选择器描述
[attName]用于选取带有指定属性的元素
[attName-value]用于选取带有指定属性的元素
attName^=value]匹配属性值以指定值开头的每个元素
[attName$=value]匹配属性值以指定结尾的每个元素
[attName*=value]匹配属性中包含指定值的每个元素
#查找所有< div >节点下面的所有直接子节点< p >
#不包含孙节点
#注意 p左右有空格
soup.select("div > p")
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

高山莫衣

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值