BeautifulSoup的使用与入门

1. 介绍

BeautifulSoup是用来从HTML、XML文档中提取数据的一个python库,安装如下:

pip install beautifulsoup4

它支持多种解析器,包括python标准库、lxml HTML解析器、lxml XML解析器、html5lib等。结合稳定性和速度,这里推荐使用lxml HTML解析器。安装:

pip install lxml

如果lxml不能正确解析内容,这是可以使用html5lib。安装:

pip install html5lib

2. 使用

2.1 一般流程

beautifulsoup的使用流程一般包括:1.导入库     2.实例化对象    3.调用对象

在实例化对象的时候要传入两个参数,一个是待解析的html或xml字符串(markup),另一个是选择的解析器(features)。如果未指定解析器,会调用默认解析器。

from bs4 import BeautifulSoup

soup = BeautifulSoup(html_str, 'lxml')

2.2 选择器

要定位到指定的地方提取想要的数据,就需要借助选择器进行定位。beautifulsoup有三种选择器:节点选择器、方法选择器、css选择器。

节点选择器的使用

选取标签:节点选择器是通过HTML标签进行定位的,使用方法是实例化soup对象后直接加.tag,tag就是html标签名。

import requests
from bs4 import BeautifulSoup

url = 'https://www.baidu.com'
response = requests.get(url=url)
response.encoding = response.apparent_encoding
soup = BeautifulSoup(response.text, 'lxml')
print(soup.a)

# out:

<a class="mnav" href="http://news.baidu.com" name="tj_trnews">新闻</a>

这样选取的缺点是:如果有多个相同标签,只会提取第一个标签,其他的被忽略。

获取标签信息:在获取到的标签的基础上,还可以进一步获取标签名、属性、值

print(soup.a)
print(soup.a.name)
print(soup.a.attrs)
print(soup.a.string)

# out:

<a class="mnav" href="http://news.baidu.com" name="tj_trnews">新闻</a>
a
{'href': 'http://news.baidu.com', 'name': 'tj_trnews', 'class': ['mnav']}
新闻

嵌套选择:如果一个标签里还包含一个子标签,我们还可以通过嵌套选择的方法取出子标签

print(soup.head.title)
print(soup.head.title.string)

# out:

<title>百度一下,你就知道</title>
百度一下,你就知道 

子标签列举: 有两种方式,包括contents(返回列表)、children(返回可迭代对象)。该方法会把所有子标签取出,这样我们就可以拿到指定位置的子标签。

from bs4 import BeautifulSoup
hh = '''<tr><th>IP</th><th>PORT</th><th>匿名度</th><th>类型</th><th>位置</th><th>响应速度</th><th>录取时间<div>test</div></th></tr>'''
soup = BeautifulSoup(hh, 'lxml')
print(soup.tr.contents)
print(soup.tr.children)
for index, child in enumerate(soup.tr.children):
    print(f'({index}):{child}')

# out:

[<th>IP</th>, <th>PORT</th>, <th>匿名度</th>, <th>类型</th>, <th>位置</th>, <th>响应速度</th>, <th>录取时间<div>test</div></th>]
<list_iterator object at 0x000001C4BF512E00>
(0):<th>IP</th>
(1):<th>PORT</th>
(2):<th>匿名度</th>
(3):<th>类型</th>
(4):<th>位置</th>
(5):<th>响应速度</th>
(6):<th>录取时间<div>test</div></th>

父标签列举:.parent会列出标签的父标签,.parents会列出所有的祖先元素并整合在可迭代对象里。

from bs4 import BeautifulSoup
hh = '''<tr>
            <th>IP</th>
            <th>PORT</th>
            <th>匿名度</th>
            <th>类型</th>
            <th>位置</th>
            <th>响应速度</th>
            <th>录取时间
                <div>test</div>
            </th>
            </tr>'''
soup = BeautifulSoup(hh, 'lxml')
print(soup.div.parent)
print(soup.div.parents)
for index, parents in enumerate(soup.tr.parents):
    print(f'({index}):{parents}')

 # out:

<th>录取时间
                <div>test</div>
</th>
<generator object PageElement.parents at 0x0000028479C541C0>
(0):<body><tr>
<th>IP</th>
<th>PORT</th>
<th>匿名度</th>
<th>类型</th>
<th>位置</th>
<th>响应速度</th>
<th>录取时间
                <div>test</div>
</th>
</tr></body>
(1):<html><body><tr>
<th>IP</th>
<th>PORT</th>
<th>匿名度</th>
<th>类型</th>
<th>位置</th>
<th>响应速度</th>
<th>录取时间
                <div>test</div>
</th>
</tr></body></html>

兄弟节点选取: next_sibling获取下一个兄弟节点,next_siblings获取后续所有兄弟节点,previous_sibling获取前一个兄弟节点,previous_siblings获取前面所有兄弟节点。

from bs4 import BeautifulSoup
hh = '''<tr><th>IP</th><th>PORT</th><th>匿名度</th><th>类型</th><th>位置</th><th>响应速度</th><th>录取时间<div>test</div></th></tr>'''
soup = BeautifulSoup(hh, 'lxml')
print(soup.th.next_sibling)
print(soup.th.next_siblings)
print(list(soup.th.next_siblings)[1].previous_sibling)
print(soup.th.previous_siblings)

# out:

<th>PORT</th>
<generator object PageElement.next_siblings at 0x000001EB1EEB4280>
<th>PORT</th>
<generator object PageElement.previous_siblings at 0x000001EB1EEB4280>

CSS选择器的使用

使用CSS选择器,只需要调用select()方法,结合CSS语法即可定位到元素。

在css语法中,我们可以使用类选择器、id选择器、标签选择器、以及混合使用来定位。

from bs4 import BeautifulSoup
hh = '''<tr><th>IP</th><th>PORT</th><th>匿名度</th><th>类型</th><th>位置</th><th>响应速度</th><th>录取时间<div>test</div></th></tr>'''
soup = BeautifulSoup(hh, 'lxml')
print(soup.select('th'))

# out:

[<th>IP</th>, <th>PORT</th>, <th>匿名度</th>, <th>类型</th>, <th>位置</th>, <th>响应速度</th>, <th>录取时间<div>test</div></th>]

我们只需传入css同样的定位语法即可 ,返回结果为列表。

获取节点的属性和文本用法与前面的节点选择器相同。

方法选择器的使用

使用方法选择器主要使用其中的find()和findALL()方法,finaALL方法需要传入的参数有name,attrs,text,kwargs。

name为定位条件,可以为标签名如'a',也可以是多个标签名组成的列表,还可以是正则表达式。

from bs4 import BeautifulSoup
hh = '''<tr><th>IP</th><th>PORT</th><th>匿名度</th><th>类型</th><th>位置</th><th>响应速度</th><th>录取时间<div>test</div></th></tr>'''
soup = BeautifulSoup(hh, 'lxml')
print(soup.findAll(name='th'))

# out:

[<th>IP</th>, <th>PORT</th>, <th>匿名度</th>, <th>类型</th>, <th>位置</th>, <th>响应速度</th>, <th>录取时间<div>test</div></th>]
 

attrs为属性,可根据属性定位标签。

from bs4 import BeautifulSoup
hh = '''<tr><th>IP</th><th>PORT</th><th>匿名度</th><th>类型</th><th>位置</th><th>响应速度</th><th>录取时间<div id='te'>test</div></th></tr>'''
soup = BeautifulSoup(hh, 'lxml')
print(soup.findAll(attrs={"id":"te"}))

 # out:

[<div id="te">test</div>]

string为文本,可以搜索文本信息,常与其他name或attr混用来获取标签。

from bs4 import BeautifulSoup
hh = '''<tr><th>IP</th><th>PORT</th><th>匿名度</th><th>类型</th><th>位置</th><th>响应速度</th><th>录取时间<div id='te'>test</div></th></tr>'''
soup = BeautifulSoup(hh, 'lxml')
print(soup.findAll(name='th', string='匿名度'))

# out:

[<th>匿名度</th>]

kwargs为关键字参数,比attr使用更方便,传入指定关键字参数以定位标签。class与python中的关键字冲突了,所以需要加下划线避免冲突。

from bs4 import BeautifulSoup
hh = '''<tr><th>IP</th><th>PORT</th><th>匿名度</th><th>类型</th><th>位置</th><th>响应速度</th><th>录取时间<div class='te'>test</div></th></tr>'''
soup = BeautifulSoup(hh, 'lxml')
print(soup.findAll(class_='te'))

# out:

[<div class="te">test</div>]

limit为限制参数,限制返回结果的数量

from bs4 import BeautifulSoup
hh = '''<tr><th>IP</th><th>PORT</th><th>匿名度</th><th>类型</th><th>位置</th><th>响应速度</th><th>录取时间<div class='te'>test</div></th></tr>'''
soup = BeautifulSoup(hh, 'lxml')
print(soup.findAll(name='th', limit=3))

 # out:

[<th>IP</th>, <th>PORT</th>, <th>匿名度</th>]

find方法 :相比于find_all()方法,除了limit参数不能用,其他参数均与find_all()方法相同,不过find方法只会返回一个值,而不是像find_all返回所有值。

  • 21
    点赞
  • 32
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值