python find next_python爬虫——BeautifulSoup详解(附加css选择器)

BeautifulSoup是一个灵活有方便的网页解系库,处理搞笑,支持多种解析器,利用他可以不编写正贼表达式即可方便实现网页信息的提取。

解析库:

我们主要用lxml解析器

标签选择器:

# coding=utf-8

from bs4 import BeautifulSoup as bs

html = """

The Dormouse's story

The Dormouse's story

Once upon a time there were three little sisters; and their names were

Elsie,

Lacie and

Tillie;

and they lived at the bottom of a well.

...

"""

soup = bs(html, 'lxml')

print(soup.title)

print(type(soup.title))

print(soup.head)

print(type(soup.head))

print(soup.p)

print(type(soup.p))

这里我们print了soup.title、head、p三个标签以及他们的类型,结果如下:

他们的类型都是bs.elment.tag,类型,类就是标签类型,并且对于soup.p,是把第一个p标签输出,也就是说有多个相同的标签,只输出第一个

获取名称:

print(soup.title.name)

输出结果就是title

获取属性:

print(soup.title.attrs['name'])

print(soup.p['name'])

可以看到这两种方式都是相同的

获取内容:

print(soup.p.string)

嵌套选择:

也就是说从body到p,是一个嵌套的关系,p也是说,通过 .head得到的tag还可以进一步 向下索取,通过.body.p得到p标签

子节点和子孙节点(children和contents):

contents:

#coding=utf-8

from bs4 importBeautifulSoup as bs

html= """

The Dormouse's story

Once upon a time there were three little sisters; and their names were

Elsie

,

Lacie

and

Tillie

; and they lived at the bottom of a well.

...

"""soup= bs(html, 'lxml')print(soup.body.contents)

可以看到contents属性返回了一个列表,整个p中的内容。把所有的换行符 标签放进了列表

children:

当我们把contents换成children:

print(soup.body.children)

contents:

它返回了一个迭代器,需要用for循环遍历使用

后代descendants:

print(soup.body.descendants)

还是一个迭代器,并且descendants是获得所有子孙节点,也就是儿子的儿子也会获得

父节点parent:

返回父节点

父节点parents:

兄弟节点siblings:

以上是标签选择器,是通过名字进行选择,但是在选择时候,往往会有很多名字相同的标签,所以我们不能完全用标签选择器进行选择,故引入标准选择器:

标准选择器:

find_all(name, attrs, recursive, text, **kwargs)

可根据标签名、属性、内容查找文档, 把所有符合条件的结果,并以列表的形式返回

name:

可以看到findall返回的列表中的每一个项哦都是tag类型

由此我们可以嵌套for循环:

for p in soup.find_all('p'):

print(p.find_all('a'))

attrs:

print(soup.find_all(attrs={'id': 'list-1'}))print(soup.find_all(attrs={'name': 'elements'}))

attr需要传入一个字典

并且对于某一些属性,可以直接用参数传入:

print(soup.find_all(id='list-1'))print(soup.find_all(class_='elements')) #class 是python的一个关键词,所以我们用class_代替class

text:

根据文本的内容选择,而它的返回值仅仅是文本的列表而不是tag

find(name, attrs, recursive, text, **kwargs)

与find_all不同是  find返回单个元素,fan_all返回所有元素。 find查找一个不存在的元素返回None

find_parent()和find_parents():

find_parent()返回所有祖先节点,find_parent()返回直接父节点。

find_next_siblings() 和 find_next_sibling()

find_next_siblings() 返回后面所有兄弟节点 find_next_sibling()返回前面一个兄弟节点

find_all_next() 和find_next()

find_all_next()返回节点后所有符合条件的节点,find_next()返回第一个符合条件的节点

find_all_previous()和find_previous()

find_all_previous()返回节点钱所有符合条件的节点,find_previous返回第一个符合条件的节点

css选择器

通过css()直接传入css选择器即可完成选择

标签(什么都不用加).属性(加点) #id(加井号)

importrequests

frombs4importBeautifulSoup as bs

html = """

The Dormouse's story

The Dormouse's story

Once upon a time there were three little sisters; and their names were

the first b tag

Elsie

,

Lacie

and

Tillie

;and they lived at the bottom of a well.

myStory

the end a tag

the p tag sibling

"""

soup = bs(html, 'lxml')

print(soup.select('p'))

print(soup.select('p a'))

print(type(soup.select('p')[0]))

输出结果1是一个包含所有p标签的列表 2是一个包含所有p标签下的a标签的列表,3是

,也就是说。css选择器生成的结果就是一个tag类型的列表

同时对于soup.select('a.mysis‘表示class属性为mysis的所有标签。也即没有空格的表示有某一个属性的或者id的标签。 有空格代表是同等的

又因为select返回的是tag类型的列表,所以我们可以继续使用上面的方法获得属性即:、

for a in soup.select('p a'):

#方法一

print(a['href'])

#方法二

print(a.attrs['href'])

以下罗列出一些css选择器的方法:(以下内容转自https://www.cnblogs.com/kongzhagen/p/6472746.html)

1、通过标签选择

# 选择所有title标签

soup.select("title")

# 选择所有p标签中的第三个标签

soup.select("p:nth-of-type(3)") 相当于soup.select(p)[2]

# 选择body标签下的所有a标签

soup.select("body a")

# 选择body标签下的直接a子标签

soup.select("body > a")

# 选择id=link1后的所有兄弟节点标签

soup.select("#link1 ~ .mysis")

# 选择id=link1后的下一个兄弟节点标签

soup.select("#link1 + .mysis")

2、通过类名查找

# 选择a标签,其类属性为mysis的标签

soup.select("a.mysis")

3、通过id查找

# 选择a标签,其id属性为link1的标签

soup.select("a#link1")

4、通过【属性】查找,当然也适用于class

# 选择a标签,其属性中存在myname的所有标签

soup.select("a[myname]")

# 选择a标签,其属性href=http://example.com/lacie的所有标签

soup.select("a[href='http://example.com/lacie']")

# 选择a标签,其href属性以http开头

soup.select('a[href^="http"]')

# 选择a标签,其href属性以lacie结尾

soup.select('a[href$="lacie"]')

# 选择a标签,其href属性包含.com

soup.select('a[href*=".com"]')

# 从html中排除某标签,此时soup中不再有script标签

[s.extract() forsinsoup('script')]

# 如果想排除多个呢

[s.extract() forsinsoup(['script','fram']

5、获取文本及属性

html_doc ="""

The Dormouse's story

The Dormouse's story

Once upon a time there were three little sisters; and their names were

Elsie,

Lacie and

Tillie;

and they lived at the bottom of a well.

...

"""

frombs4importBeautifulSoup

'''''

以列表的形式返回

'''

soup = BeautifulSoup(html_doc, 'html.parser')

s = soup.select('p.story')

s[0].get_text()# p节点及子孙节点的文本内容

s[0].get_text("|")# 指定文本内容的分隔符

s[0].get_text("|", strip=True)# 去除文本内容前后的空白

print(s[0].get("class"))# p节点的class属性值列表(除class外都是返回字符串)

6、UnicodeDammit.detwingle()方法只能解码包含在UTF-8编码中的Windows-1252编码内容

new_doc = UnicodeDammit.detwingle(doc)

print(new_doc.decode("utf8"))

# ☃☃☃“I like snowmen!”

在创建BeautifulSoup或UnicodeDammit对象前一定要先对文档调用UnicodeDammit.detwingle()确保文档的编码方式正确.如果尝试去解析一段包含Windows-1252编码的UTF-8文档,就会得到一堆乱码,比如: ☃☃☃“I like snowmen!”.

7 、其他

html_doc ="""

The Dormouse's story

The Dormouse's story

Once upon a time there were three little sisters; and their names were

Elsie,

Lacie and

Tillie;

and they lived at the bottom of a well.

...

"""

frombs4importBeautifulSoup

'''''

以列表的形式返回

'''

soup = BeautifulSoup(html_doc, 'html.parser')

soup.select('title')# title标签

soup.select("p:nth-of-type(3)")# 第三个p节点

soup.select('body a')# body下的所有子孙a节点

soup.select('p > a')# 所有p节点下的所有a直接节点

soup.select('p > #link1')  # 所有p节点下的id=link1的直接子节点

soup.select('#link1 ~ .sister')  # id为link1的节点后面class=sister的所有兄弟节点

soup.select('#link1 + .sister')  # id为link1的节点后面class=sister的第一个兄弟节点

soup.select('.sister')# class=sister的所有节点

soup.select('[class="sister"]')# class=sister的所有节点

soup.select("#link1")  # id=link1的节点

soup.select("a#link1")  # a节点,且id=link1的节点

soup.select('a[href]')# 所有的a节点,有href属性

soup.select('a[href="http://example.com/elsie"]')# 指定href属性值的所有a节点

soup.select('a[href^="http://example.com/"]')# href属性以指定值开头的所有a节点

soup.select('a[href$="tillie"]')# href属性以指定值结尾的所有a节点

soup.select('a[href*=".com/el"]')# 支持正则匹配

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值