Python 第三方模块之 beautifulsoup(bs4)- 解析 HTML

简单来说,Beautiful Soup是python的一个库,最主要的功能是从网页抓取数据。官方解释如下:官网文档

Beautiful Soup提供一些简单的、python式的函数用来处理导航、搜索、修改分析树等功能。
它是一个工具箱,通过解析文档为用户提供需要抓取的数据,因为简单,所以不需要多少代码就可以写出一个完整的应用程序。

安装

pip3 install beautifulsoup4

解析器

Beautiful Soup支持Python标准库中的HTML解析器,还支持一些第三方的解析器,如果我们不安装它,则 Python 会使用 Python默认的解析器,lxml 解析器更加强大,速度更快,推荐安装。

pip3 install lxml

另一个可供选择的解析器是纯Python实现的 html5lib , html5lib的解析方式与浏览器相同,可以选择下列方法来安装html5lib:

pip install html5lib

解析器对比

在这里插入图片描述
BeautifulSoup是一个模块,该模块用于接收一个HTML或XML字符串,然后将其进行格式化,之后遍可以使用他提供的方法进行快速查找指定元素,从而使得在HTML或XML中查找指定元素变得简单。

用法

# 简单示例
from bs4 import BeautifulSouphtml_doc = """
<html><head><title>The Dormouse's story</title></head>
<body>
asdf<div class="title"><b>The Dormouse's story总共</b><h1>f</h1></div>
<div class="story">Once upon a time there were three little sisters; and their names were<a  class="sister0" id="link1">Els<span>f</span>ie</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 at the bottom of a well.</div>
ad<br/>sf
<p class="story">...</p>
</body>
</html>
"""soup = BeautifulSoup(html_doc, features="lxml")
tag1 = soup.find(name='a')        # 找到第一个a标签
tag2 = soup.find_all(name='a')    # 找到所有的a标签
tag3 = soup.select('#link2')      # 找到id=link2的标签

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

# name参数,查找所有名字为name的tag,字符串对象被忽略。 
soup.find_all('title') # keyword参数,如果一个指定名字的参数不是搜索内置的参数名,搜索时会把该参数当作指定名字tag的属性来搜索。 
soup.find_all(id='link2')# 如果多个指定名字的参数可以同时过滤tag的多个属性: 
soup.find_all(href=re.compile('elsie'),id='link1') # 有些tag属性在搜索不能使用,比如HTML5中的data*属性,但是可以通过find_all()的attrs参数定义一个字典来搜索: 
data_soup.find_all(attrs={'data-foo':'value'})# recursive参数
如果指向搜索tag的直接子节点,可以使用参数recursive=False# limit参数
可以用来限制返回结果的数量# text 参数
通过 text 参数可以搜搜文档中的字符串内容,与 name 参数的可选值一样, text 参数接受 字符串 , 正则表达式 , 列表

使用示例:

  1. text,标签内容
print(soup.text)
print(soup.get_text()) 
# 两种方式都可以返回获取的所有文本
  1. name,标签名称
tag = soup.find('a')
name = tag.name   # 获取标签名称
print(name)
tag.name = 'span' # 设置标签名称
print(soup)
  1. attrs,标签属性
tag = soup.find('a')
attrs = tag.attrs         # 获取标签属性
print(attrs)
tag.attrs = {'ik':123}    # 设置标签属性
tag.attrs['id'] = 'iiiii' # 设置标签属性
print(soup)
  1. children,所有子标签
body = soup.find('body')
v = body.children
  1. descendants,所有子子孙孙标签
body = soup.find('body')
v = body.descendants
  1. clear,将标签的所有子标签全部清空(保留标签名)
tag = soup.find('body')
tag.clear()
print(soup)
  1. decompose,递归的删除所有的标签
body = soup.find('body')
body.decompose()
print(soup)
  1. extract,递归的删除所有的标签,并获取删除的标签
body = soup.find('body')
v = body.extract()
print(soup)
  1. decode,转换为字符串(含当前标签);decode_contents(不含当前标签)
body = soup.find('body')
v = body.decode()
v = body.decode_contents()
print(v)
  1. encode,转换为字节(含当前标签);encode_contents(不含当前标签)
body = soup.find('body')
v = body.encode()
v = body.encode_contents()
print(v)
  1. find,获取匹配的第一个标签
tag = soup.find('a')
print(tag)
tag = soup.find(name='a', attrs={'class': 'sister'}, recursive=True, text='Lacie')
tag = soup.find(name='a', class_='sister', recursive=True, text='Lacie')
print(tag)
  1. find_all,获取匹配的所有标签
tags = soup.find_all('a')
print(tags)
tags = soup.find_all('a',limit=1)
print(tags)
tags = soup.find_all(name='a', attrs={'class': 'sister'}, recursive=True, text='Lacie')
# tags = soup.find(name='a', class_='sister', recursive=True, text='Lacie')
print(tags)# ####### 列表 #######
# v = soup.find_all(name=['a','div'])
# print(v)# v = soup.find_all(class_=['sister0', 'sister'])
# print(v)# v = soup.find_all(text=['Tillie'])
# print(v, type(v[0]))# v = soup.find_all(id=['link1','link2'])
# print(v)# v = soup.find_all(href=['link1','link2'])
# print(v)# ####### 正则 #######
import re
# rep = re.compile('p')
# rep = re.compile('^p')
# v = soup.find_all(name=rep)
# print(v)# rep = re.compile('sister.*')
# v = soup.find_all(class_=rep)
# print(v)# rep = re.compile('http://www.oldboy.com/static/.*')
# v = soup.find_all(href=rep)
# print(v)# ####### 方法筛选 #######
# def func(tag):
# return tag.has_attr('class') and tag.has_attr('id')
# v = soup.find_all(name=func)
# print(v)# ####### get,获取标签属性
# tag = soup.find('a')
# v = tag.get('id')
# print(v)
  1. has_attr,检查标签是否具有该属性
tag = soup.find('a')
v = tag.has_attr('id')
print(v)
  1. get_text,获取标签内部文本内容
tag = soup.find('a')
v = tag.get_text('id')
print(v)
  1. index,检查标签在某标签中的索引位置
tag = soup.find('body')
v = tag.index(tag.find('div'))
print(v)tag = soup.find('body')
for i,v in enumerate(tag):print(i,v)
  1. is_empty_element,是否是空标签(是否可以是空)或者自闭合标签,

判断是否是如下标签:’br’ , ‘hr’, ‘input’, ‘img’, ‘meta’,’spacer’, ‘link’, ‘frame’, ‘base’

tag = soup.find('br')
v = tag.is_empty_element
print(v)
  1. 当前的关联标签
soup.next
soup.next_element
soup.next_elements
soup.next_sibling
soup.next_siblings
tag.previous
tag.previous_element
tag.previous_elements
tag.previous_sibling
tag.previous_siblings
tag.parent
tag.parents
  1. 查找某标签的关联标签
# tag.find_next(...)
# tag.find_all_next(...)
# tag.find_next_sibling(...)
# tag.find_next_siblings(...)# tag.find_previous(...)
# tag.find_all_previous(...)
# tag.find_previous_sibling(...)
# tag.find_previous_siblings(...)# tag.find_parent(...)
# tag.find_parents(...)# 参数同find_all
  1. select,select_one, CSS选择器
soup.select("title")
soup.select("p nth-of-type(3)")
soup.select("body a")
soup.select("html head title")
tag = soup.select("span,a")
soup.select("head > title")
soup.select("p > a")
soup.select("p > a:nth-of-type(2)")
soup.select("p > #link1")
soup.select("body > a")
soup.select("#link1 ~ .sister")
soup.select("#link1 + .sister")
soup.select(".sister")
soup.select("[class~=sister]")
soup.select("#link1")
soup.select("a#link2")
soup.select('a[href]')
soup.select('a[href="http://example.com/elsie"]')
soup.select('a[href^="http://example.com/"]')
soup.select('a[href$="tillie"]')
soup.select('a[href*=".com/el"]')from bs4.element import Tagdef default_candidate_generator(tag):for child in tag.descendants:if not isinstance(child, Tag):continueif not child.has_attr('href'):continueyield childtags = soup.find('body').select("a", _candidate_generator=default_candidate_generator)
print(type(tags), tags)from bs4.element import Tag
def default_candidate_generator(tag):for child in tag.descendants:if not isinstance(child, Tag):continueif not child.has_attr('href'):continueyield childtags = soup.find('body').select("a", _candidate_generator=default_candidate_generator, limit=1)
print(type(tags), tags)
  1. 标签的内容
# tag = soup.find('span')
# print(tag.string)          # 获取
# tag.string = 'new content' # 设置
# print(soup)# tag = soup.find('body')
# print(tag.string)
# tag.string = 'xxx'
# print(soup)# tag = soup.find('body')
# v = tag.stripped_strings  # 递归内部获取所有标签的文本
# print(v)
  1. append在当前标签内部追加一个标签
# tag = soup.find('body')
# tag.append(soup.find('a'))
# print(soup)
#
# from bs4.element import Tag
# obj = Tag(name='i',attrs={'id': 'it'})
# obj.string = '我是一个新来的'
# tag = soup.find('body')
# tag.append(obj)
# print(soup)
  1. insert在当前标签内部指定位置插入一个标签
# from bs4.element import Tag
# obj = Tag(name='i', attrs={'id': 'it'})
# obj.string = '我是一个新来的'
# tag = soup.find('body')
# tag.insert(2, obj)
# print(soup)
  1. insert_after,insert_before 在当前标签后面或前面插入
# from bs4.element import Tag
# obj = Tag(name='i', attrs={'id': 'it'})
# obj.string = '我是一个新来的'
# tag = soup.find('body')
# # tag.insert_before(obj)
# tag.insert_after(obj)
# print(soup)
  1. replace_with 在当前标签替换为指定标签
# from bs4.element import Tag
# obj = Tag(name='i', attrs={'id': 'it'})
# obj.string = '我是一个新来的'
# tag = soup.find('div')
# tag.replace_with(obj)
# print(soup)
  1. 创建标签之间的关系
# tag = soup.find('div')
# a = soup.find('a')
# tag.setup(previous_sibling=a)
# print(tag.previous_sibling)
  1. wrap,将指定标签把当前标签包裹起来
# from bs4.element import Tag
# obj1 = Tag(name='div', attrs={'id': 'it'})
# obj1.string = '我是一个新来的'
#
# tag = soup.find('a')
# v = tag.wrap(obj1)
# print(soup)# tag = soup.find('a')
# v = tag.wrap(soup.find('p'))
# print(soup)
  1. unwrap,去掉当前标签,将保留其包裹的标签
# tag = soup.find('a')
# v = tag.unwrap()
# print(soup)

更多参数官方:http://beautifulsoup.readthedocs.io/zh_CN/v4.4.0/

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/453856.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

modal vue 关闭_Vue弹出框的优雅实践

引言页面引用弹出框组件是经常碰见的需求,如果强行将弹出框组件放入到页面中,虽然功能上奏效但没有实现组件与页面间的解耦,非常不利于后期的维护和功能的扩展.下面举个例子来说明一下这种做法的弊端.click"openModal()">点击 :is_open"is_open" close…

Python 第三方模块之 lxml - 解析 HTML 和 XML 文件

lxml是python的一个解析库&#xff0c;支持HTML和XML的解析&#xff0c;支持XPath解析方式&#xff0c;而且解析效率非常高 XPath&#xff0c;全称XML Path Language&#xff0c;即XML路径语言&#xff0c;它是一门在XML文档中查找信息的语言&#xff0c;它最初是用来搜寻XML文…

(转)Linux下PS1、PS2、PS3、PS4使用详解

Linux下PS1、PS2、PS3、PS4使用详解 原文&#xff1a;http://www.linuxidc.com/Linux/2016-10/136597.htm 1、PS1——默认提示符 如下所示&#xff0c;可以通过修改Linux下的默认提示符&#xff0c;使其更加实用。在下面的例子中&#xff0c;默认的PS1的值是“\s-\v\$”,显示出…

开放平台大抉择

开放平台大抉择之新浪SAE&#xff1a;为个人应用开发带来福音 导读&#xff1a;继上期淘宝网副总裁王文彬从平台功能特色、运营状况等多方面分享了淘宝开放平台的历程和挑战之后。国内另一家云平台服务方的典型代表——Sina App Engine(简称SAE)&#xff0c;作为新浪研发中心于…

ip68级防水可以泡多久_iPhone8防水级别升级至IP68:能在1.5米深水中坚持30分钟

1月15日&#xff0c;业界最新的泄密消息显示&#xff0c;苹果拟在今年推出的“iPhone 8”智能手机会是一款革命性的手机&#xff0c;功能和配置就不多说了。苹果还将解决iPhone 7的一个重要缺陷&#xff0c;就是大大增强iPhone 8的防水性能&#xff0c;防水级别达IP68。《韩国先…

HTTP POST 发送数据的参数 application/x-www-form-urlencoded、multipart/form-data、text/plain

HTTP 简介 HTTP/1.1 协议规定的 HTTP 请求方法有 OPTIONS、GET、HEAD、POST、PUT、DELETE、TRACE、CONNECT 这几种。 其中 POST 一般用来向服务端提交数据&#xff0c;本文主要讨论 POST 提交数据的几种方式。 我们知道&#xff0c;HTTP 协议是以 ASCII 码传输&#xff0c;建…

vue 二进制文件的下载(解决乱码和解压报错)

问题描述&#xff1a;项目中使用的是vue框架进行开发&#xff0c;因为文件下载存在权限问题&#xff0c;所以并不能通过 a 链接的 href 属性直接赋值 URL进行下载&#xff0c; &#xff08;如果你的文件没有下载权限&#xff0c;可以直接通过href属性赋值URL的方法进行文件下载…

Python 第三方模块之 psutil - 获取系统运行的进程和系统利用率信息

一、psutil模块: 官方网址&#xff1a;http://pythonhosted.org/psutil/ 1.psutil是一个跨平台库(http://pythonhosted.org/psutil/)能够轻松实现获取系统运行的进程和系统利用率&#xff08;包括CPU、内存、磁盘、网络等&#xff09;信息。它主要用来做系统监控&#xff0c;…

石头机器人红灯快闪_机器人集体“快闪”活动爆红网络 “我是AI”与您相约智能新时代...

原标题&#xff1a;机器人集体“快闪”活动爆红网络 “我是AI”与您相约智能新时代3月10日下午&#xff0c;天津科学技术馆内&#xff0c;悠扬美妙的歌声《我和我的祖国》突然响起&#xff0c;随后50个身形矫健的阿尔法机器人伴随着歌声翩翩起舞&#xff0c;动作整齐、科技感十…

浅谈云计算与数据中心计算

文/林仕鼎 云计算概念发端于Google和Amazon等超大规模的互联网公司&#xff0c;随着这些公司业务的成功&#xff0c;作为其支撑技术的云计算也得到了业界的高度认可和广泛传播。时至今日&#xff0c;云计算已被普遍认为是IT产业发展的新阶段&#xff0c;从而被赋予了很多产业和…

无线网络实体图生成工具airgraph-ng

无线网络实体图生成工具airgraph-ngairgraph-ng是aircrack-ng套件提供的一个图表生成工具。该工具可以根据airodump工具生成的CSV文件绘制PNG格式的图。绘制的图有两种类型&#xff0c;分别为AP-客户端关联图和通用探测图。通过AP-客户端关联图&#xff0c;可以更为直观的了解无…

高等代数期末考试题库及答案_数学类高等代数期末考试试题A卷(含答案)

数学类高等代数期末考试试题A卷(含答案)课程编号MTH17063 北京理工大学2010-2011学年第一学期2009级数学类高等代数期末考试试题A卷班级 学号 姓名 成绩 一、(25分)设表示域上的所有阶矩阵构成的上的线性空间。取定&#xff0c;对于任意的&#xff0c;定义。(1)证明为上的一个线…

cocos2d-lua3.7组件篇(三)-http通信demo

客户端使用lua、服务端使用QT做为服务器。 步骤&#xff1a; 客户端 -----------Post 用户名和密码 服务端接受Post请求&#xff0c;读取数据&#xff0c;返回response一、客户端代码 loadingImg require"app.scenes.LoadingLayer"local LoginScene class(&qu…

数据挖掘:如何寻找相关项

导读&#xff1a;随着大数据时代浪潮的到来数据科学家这一新兴职业也越来越受到人们的关注。本文作者Alexandru Nedelcu就将数学挖掘算法与大数据有机的结合起来&#xff0c;并无缝的应用在面临大数据浪潮的网站之中。 数据科学家需要具备专业领域知识并研究相应的算法以分析对…

Python 第三方模块之 selenium - 模拟操作 Chrome 浏览器

1、安装selenium 1.1、Python 安装 selenium 模块 pip install selenium1.2、下载驱动 选择和自己chrom版本相对应的驱动到本地&#xff0c;下载地址 http://npm.taobao.org/mirrors/chromedriver/2、Python 操作 from selenium import webdriver import time import json…

jupyter notebook代码导出_Jupyter Notebook导出包含中文的pdf_亲测有效

Jupyter Notebook是很好的数据科学创作环境&#xff0c;是非常方便的Python代码编辑器。jupyter提供导出的格式有.py、.html、.md、.pdf等。目前用其导出包含中文的pdf会遇到很多坑&#xff0c;网上也有一些解决方案&#xff0c;大致分为两种方式&#xff0c;一是安装 pandoc并…

前端之使用 POST 提交数据并跳转

GET 方式 window.location.href是我们常用来在js中实现页面跳转的方法&#xff0c;这是使用get方式发送请求&#xff0c;示例如下 window.location.href url;优点是简单易用&#xff0c;缺点是如果有参数的话&#xff0c;参数会暴露在url地址中&#xff0c;这降低了系统的安…

cef js返回c++的代码_CEF3开发者系列之外篇——IE中JS与C++交互

使用IE内核开发客户端产品&#xff0c;系统和前端页面之间的交互&#xff0c;通常给开发和维护带来很大的便利性。但操作系统和前端之间的交互却是比较复杂的。具体来说就是脚本语言和编译语言的交互。在IE内核中html和css虽然不兼容,但是IE编程接口是完全一样的,这得益于微软的…

多线程编程指南 part 2

多线程编程指南Sun Microsystems, Inc.4150 Network CircleSanta Clara, CA95054U.S.A.文件号码819–7051–102006 年10 月版权所有2005 Sun Microsystems, Inc. 4150 Network Circle, Santa Clara, CA95054 U.S.A. 保留所有权利。本文档及其相关产品的使用、复制、分发和反编译…

00030_ArrayList集合

1、数组可以保存多个元素&#xff0c;但在某些情况下无法确定到底要保存多少个元素&#xff0c;此时数组将不再适用&#xff0c;因为数组的长度不可变 2、JDK中提供了一系列特殊的类&#xff0c;这些类可以存储任意类型的元素&#xff0c;并且长度可变&#xff0c;统称为集合 3…