Python利用Beautiful Soup模块搜索内容详解

 更新时间:2017年03月29日 08:43:57   作者:Glumes  
这篇文章主要给大家介绍了python中 Beautiful Soup 模块的搜索方法函数。 方法不同类型的过滤参数能够进行不同的过滤,得到想要的结果。文中介绍的非常详细,对大家具有一定的参考价值,需要的朋友们下面来一起看看吧。

前言

我们将利用 Beautiful Soup 模块的搜索功能,根据标签名称、标签属性、文档文本和正则表达式来搜索。

搜索方法

Beautiful Soup 内建的搜索方法如下:

  • find()
  • find_all()
  • find_parent()
  • find_parents()
  • find_next_sibling()
  • find_next_siblings()
  • find_previous_sibling()
  • find_previous_siblings()
  • find_previous()
  • find_all_previous()
  • find_next()
  • find_all_next()

使用 find() 方法搜索

首先还是需要建立一个 HTML 文件用来做测试。

<html>
<body>
<div class="ecopyramid">
 <ul id="producers">
 <li class="producerlist">
  <div class="name">plants</div>
  <div class="number">100000</div>
 </li>
 <li class="producerlist">
  <div class="name">algae</div>
  <div class="number">100000</div>
 </li>
 </ul>
 <ul id="primaryconsumers">
 <li class="primaryconsumerlist">
  <div class="name">deer</div>
  <div class="number">1000</div>
 </li>
 <li class="primaryconsumerlist">
  <div class="name">rabbit</div>
  <div class="number">2000</div>
 </li>
 </ul>
 <ul id="secondaryconsumers">
 <li class="secondaryconsumerlist">
  <div class="name">fox</div>
  <div class="number">100</div>
 </li>
 <li class="secondaryconsumerlist">
  <div class="name">bear</div>
  <div class="number">100</div>
 </li>
 </ul>
 <ul id="tertiaryconsumers">
 <li class="tertiaryconsumerlist">
  <div class="name">lion</div>
  <div class="number">80</div>
 </li>
 <li class="tertiaryconsumerlist">
  <div class="name">tiger</div>
  <div class="number">50</div>
 </li>
 </ul>
</div>
</body>
</html>

我们可以通过 find() 方法来获得 <ul> 标签,默认情况下会得到第一个出现的。接着再获取 <li> 标签,默认情况下还是会得到第一个出现的,接着获得 <div> 标签,通过输出内容来验证是否获取了第一个出现的标签。

from bs4 import BeautifulSoup
with open('search.html','r') as filename:
 soup = BeautifulSoup(filename,'lxml')
first_ul_entries = soup.find('ul')
print first_ul_entries.li.div.string

find() 方法具体如下:

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

正如上代码所示,find() 方法接受五个参数:name、attrs、recursive、text 和 **kwargs 。name 、attrs 和 text 参数都可以在 find() 方法充当过滤器,提高匹配结果的精确度。

搜索标签

除了上面代码的搜索 <ul> 标签外,我们还可以搜索 <li> 标签,返回结果也是返回出现的第一个匹配内容。

tag_li = soup.find('li')
# tag_li = soup.find(name = "li")
print type(tag_li)
print tag_li.div.string

搜索文本

如果我们只想根据文本内容来搜索的话,我们可以只传入文本参数 :

search_for_text = soup.find(text='plants')
print type(search_for_text)
<class 'bs4.element.NavigableString'>

返回的结果也是 NavigableString 对象 。

根据正则表达式搜索

如下的一段 HTML 文本内容

<div>The below HTML has the information that has email ids.</div>
 abc@example.com 
<div>xyz@example.com</div> 
 <span>foo@example.com</span>

可以看到 abc@example 邮件地址并没有包括在任何标签内,这样就不能根据标签来找到邮件地址了。这个时候,我们可以使用正则表达式来进行匹配。

email_id_example = """
 <div>The below HTML has the information that has email ids.</div>
 abc@example.com
 <div>xyz@example.com</div>
 <span>foo@example.com</span>
 """
email_soup = BeautifulSoup(email_id_example,'lxml')
print email_soup
# pattern = "\w+@\w+\.\w+"
emailid_regexp = re.compile("\w+@\w+\.\w+")
first_email_id = email_soup.find(text=emailid_regexp)
print first_email_id

在使用正则表达式进行匹配时,如果有多个匹配项,也是先返回第一个。

根据标签属性值搜索

可以通过标签的属性值来搜索:

search_for_attribute = soup.find(id='primaryconsumers')
print search_for_attribute.li.div.string

根据标签属性值来搜索对大多数属性都是可用的,例如:id、style 和 title 。

但是对以下两种情况会有不同:

  • 自定义属性
  • 类 ( class ) 属性

我们不能再直接使用属性值来搜索了,而是得使用 attrs 参数来传递给 find() 函数。

根据自定义属性来搜索

在 HTML5 中是可以给标签添加自定义属性的,例如给标签添加 属性。

如下代码所示,如果我们再像搜索 id 那样进行操作的话,会报错的,Python 的变量不能包括 - 符号。

customattr = """
 <p data-custom="custom">custom attribute example</p>
   """
customsoup = BeautifulSoup(customattr,'lxml')
customsoup.find(data-custom="custom")
# SyntaxError: keyword can't be an expression

这个时候使用 attrs 属性值来传递一个字典类型作为参数进行搜索:

using_attrs = customsoup.find(attrs={'data-custom':'custom'})
print using_attrs

基于 CSS 中的 类 进行搜索

对于 CSS 的类属性,由于在 Python 中 class 是个关键字,所以是不能当做标签属性参数传递的,这种情况下,就和自定义属性一样进行搜索。也是使用 attrs 属性,传递一个字典进行匹配 。

除了使用 attrs 属性之外,还可以使用 class_ 属性进行传递,这样与 class 区别开了,也不会导致错误。

css_class = soup.find(attrs={'class':'producerlist'})
css_class2 = soup.find(class_ = "producerlist")
print css_class
print css_class2

使用自定义的函数搜索

可以给 find() 方法传递一个函数,这样就会根据函数定义的条件进行搜索。

函数应该返回 true 或者是 false 值。

def is_producers(tag):
 return tag.has_attr('id') and tag.get('id') == 'producers'
tag_producers = soup.find(is_producers)
print tag_producers.li.div.string

代码中定义了一个 is_producers 函数,它将检查标签是否具体 id 属性以及属性值是否等于 producers,如果符合条件则返回 true ,否则返回 false 。

联合使用各种搜索方法

Beautiful Soup 提供了各种搜索方法,同样,我们也可以联合使用这些方法来进行匹配,提高搜索的准确度。

combine_html = """
 <p class="identical">
  Example of p tag with class identical
 </p>
 <div class="identical">
  Example of div tag with class identical
 <div>
 """
combine_soup = BeautifulSoup(combine_html,'lxml')
identical_div = combine_soup.find("div",class_="identical")
print identical_div

使用 find_all() 方法搜索

使用 find() 方法会从搜索结果中返回第一个匹配的内容,而 find_all() 方法则会返回所有匹配的项。

find() 方法中用到的过滤项,同样可以用在 find_all() 方法中。事实上,它们可以用到任何搜索方法中,例如:find_parents()find_siblings() 中 。

# 搜索所有 class 属性等于 tertiaryconsumerlist 的标签。
all_tertiaryconsumers = soup.find_all(class_='tertiaryconsumerlist')
print type(all_tertiaryconsumers)
for tertiaryconsumers in all_tertiaryconsumers:
 print tertiaryconsumers.div.string

find_all() 方法为 :

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

它的参数和 find() 方法有些类似,多个了 limit 参数。limit 参数是用来限制结果数量的。而 find() 方法的 limit 就是 1 了。

同时,我们也能传递一个字符串列表的参数来搜索标签、标签属性值、自定义属性值和 CSS 类。

# 搜索所有的 div 和 li 标签
div_li_tags = soup.find_all(["div","li"])
print div_li_tags
print
# 搜索所有类属性是 producerlist 和 primaryconsumerlist 的标签
all_css_class = soup.find_all(class_=["producerlist","primaryconsumerlist"])
print all_css_class
print

搜索相关标签

一般情况下,我们可以使用 find()find_all() 方法来搜索指定的标签,同时也能搜索其他与这些标签相关的感兴趣的标签。

搜索父标签

可以使用 find_parent() 或者 find_parents() 方法来搜索标签的父标签。

find_parent() 方法将返回第一个匹配的内容,而 find_parents() 将返回所有匹配的内容,这一点与 find() find_all() 方法类似。

# 搜索 父标签
primaryconsumers = soup.find_all(class_='primaryconsumerlist')
print len(primaryconsumers)
# 取父标签的第一个
primaryconsumer = primaryconsumers[0]
# 搜索所有 ul 的父标签
parent_ul = primaryconsumer.find_parents('ul')
print len(parent_ul)
# 结果将包含父标签的所有内容
print parent_ul
print
# 搜索,取第一个出现的父标签.有两种操作
immediateprimary_consumer_parent = primaryconsumer.find_parent()
# immediateprimary_consumer_parent = primaryconsumer.find_parent('ul')
print immediateprimary_consumer_parent

搜索同级标签

Beautiful Soup 还提供了搜索同级标签的功能。

使用函数 find_next_siblings() 函数能够搜索同一级的下一个所有标签,而 find_next_sibling() 函数能够搜索同一级的下一个标签。

producers = soup.find(id='producers')
next_siblings = producers.find_next_siblings()
print next_siblings

同样,也可以使用 find_previous_siblings() find_previous_sibling() 方法来搜索上一个同级的标签。

搜索下一个标签

使用 find_next() 方法将搜索下一个标签中第一个出现的,而 find_next_all() 将会返回所有下级的标签项。

# 搜索下一级标签
first_div = soup.div
all_li_tags = first_div.find_all_next("li")
print all_li_tags

搜索上一个标签

与搜索下一个标签类似,使用 find_previous()find_all_previous() 方法来搜索上一个标签。

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家学习或者使用python能带来一定的帮助,如果有疑问大家可以留言交流,谢谢大家对脚本之家的支持。

相关文章

  • Python 实现简单智能聊天机器人

    Python 实现简单智能聊天机器人

    这篇文章主要介绍了Python 实现简单智能聊天机器人,首先通过计算机接收用户的语音输入再将用户输入的语音输入转化为文本信息展开实现过程,需要的小伙伴可以参考一下
    2022-05-05
  • Python查找不限层级Json数据中某个key或者value的路径方式

    Python查找不限层级Json数据中某个key或者value的路径方式

    今天小编就为大家分享一篇Python查找不限层级Json数据中某个key或者value的路径方式,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2020-02-02
  • Python中的getattr、__getattr__、__getattribute__、__get__详解

    Python中的getattr、__getattr__、__getattribute__、__get__详解

    这篇文章主要为大家介绍了Python中的getattr,__getattr__,__getattribute__和__get__,具有一定的参考价值,感兴趣的小伙伴们可以参考一下,希望能够给你带来帮助
    2021-12-12
  • Python深入学习之闭包

    Python深入学习之闭包

    这篇文章主要介绍了Python深入学习之闭包,闭包(closure)是函数式编程的重要的语法结构,Python也支持这一特性,本文就这一特性做了讲解,需要的朋友可以参考下
    2014-08-08
  • SVM算法的理解及其Python实现多分类和二分类问题

    SVM算法的理解及其Python实现多分类和二分类问题

    这篇文章主要介绍了SVM算法的理解及其Python实现多分类和二分类问题,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2023-02-02
  • python之Django自动化资产扫描的实现

    python之Django自动化资产扫描的实现

    这篇文章主要介绍了python之Django自动化资产扫描的实现,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2021-04-04
  • 基于Python实现温度转换程序

    基于Python实现温度转换程序

    这篇文章主要为大家详细介绍了如何基于Python实现简单的温度转换程序,文中的示例代码讲解详细,感兴趣的小伙伴可以跟随小编一起学习一下
    2023-10-10
  • Python读取视频的两种方法(imageio和cv2)

    Python读取视频的两种方法(imageio和cv2)

    这篇文章主要为大家详细介绍了Python读取视频的两种方法,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2018-04-04
  • 详解numpy.ndarray.reshape()函数的参数问题

    详解numpy.ndarray.reshape()函数的参数问题

    这篇文章主要介绍了详解numpy.ndarray.reshape()函数的参数问题,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2020-10-10
  • 用Python写王者荣耀刷金币脚本

    用Python写王者荣耀刷金币脚本

    今天给大家带来的是用Python语言写一个关于手游王者荣耀刷金币的脚本,有兴趣的朋友参考学习下。
    2017-12-12

最新评论