百度贴吧爬虫实战(BeautifulSoup+lxml)

avatar
作者
筋斗云
阅读量:0

文章目录


在实际爬虫之前还需要了解和下载两个模块:BeautifulSoup和lxml。

BeautifulSouplxml 是Python中两个非常流行的库,它们在网页内容解析和数据提取方面非常有用。以下是关于这两个库的详细介绍:

BeautifulSoup

BeautifulSoup 是一个用于提取HTML和XML文件中数据的Python库。它能够通过你喜欢的解析器来解析网页,提供一些简单的方法和Pythonic的方式来导航、搜索和修改解析树。BeautifulSoup 的主要特点包括:

  • 易于使用:提供了简洁的API,使得即使是新手也能快速上手。
  • 可读性强:能够以可读的方式呈现解析后的文档结构。
  • 灵活:支持多种解析器,如Python内置的 html.parser,快速高效的 lxml,以及 html5lib 等。
  • 强大的搜索功能:可以轻松地通过标签名、属性等找到所需的元素。
  • 广泛的文档和社区支持:拥有大量的文档和活跃的社区,方便查找解决方案。

lxml

lxml 是一个Python库,用于处理XML和HTML文件。它具有以下特点:

  • 性能lxml 使用高效的libxml2库,因此在解析速度上通常比 BeautifulSoup 使用的内置解析器快。
  • 易用性:虽然 lxml 主要用于XML,但它也提供了对HTML的解析支持,且API直观易用。
  • 功能丰富:除了基本的解析和元素查找功能外,lxml 还支持XPath和XSLT,这使得在复杂的文档中进行数据提取变得更加容易。
  • 兼容性lxml 能够处理不规范的HTML代码,容错性较好。

使用场景

  • 当您需要快速解析HTML或XML文件,并从中提取数据时,BeautifulSoup 是一个很好的选择,特别是当您需要一个易于学习和使用的库时。
  • 如果性能是您的主要关注点,或者您需要处理大型文件和复杂的查询,lxml 可能是更合适的选择。

BeautifulSoup 是一个可以从HTML或XML文件中提取数据的Python库。要安装 BeautifulSoup,可以使用Python的包管理器 pip。以下是安装步骤:

  1. 打开命令行界面(在Windows上是命令提示符或PowerShell,在macOS或Linux上是终端)。

  2. 输入以下命令来安装 beautifulsoup4

pip install beautifulsoup4 

如果使用的是Python 3,并且系统同时安装了Python 2,可能需要使用 pip3 来代替 pip

pip3 install beautifulsoup4 
  1. 等待安装完成。

此外,BeautifulSoup 需要一个解析器来解析网页,最常用的解析器是 lxmlhtml.parser(Python标准库中包含)。html.parser 不需要额外安装,但 lxml 更快且能更好地处理不规范的HTML。如果想使用 lxml 作为解析器,可以使用以下命令安装:

pip install lxml 

或者,如果使用的是Python 3:

pip3 install lxml 

安装完成后,可以在Python脚本中导入并使用 BeautifulSoup

from bs4 import BeautifulSoup 

具体代码

#!/usr/bin/python3 # -*- coding: utf-8 -*-   #Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/124.0.0.0 Safari/537.36 Edg/124.0.0.0 #Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.110 Safari/537.36 import requests import json from bs4 import BeautifulSoup  class TiebaSpider():      def __init__(self, kw, max_pn):         self.max_pn = max_pn         self.kw = kw         self.base_url = "https://tieba.baidu.com/f?kw={}&ie=utf-8&pn={}"         self.headers = {             "User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.110 Safari/537.36"         }         pass      def get_url_list(self):         '''         获取 url 列表         :return:         '''         # 写法一         '''         url_list = []         for pn in range(0,self.max_pn,50):             url = self.base_url.format(self.kw,pn)             url_list.append(url)         return url_list         '''         # 写法二         return [self.base_url.format(self.kw, pn) for pn in range(0, self.max_pn, 50)]      def get_content(self, url):         '''         发送请求获取响应内容         :param url:         :return:         '''         response = requests.get(             url=url,             headers=self.headers          )          return response.content      # def get_items(self, content, index):     #     '''     #     从响应内容中提取数据     #     :param content:     #     :return:     #     '''     #     with open('tieba-{}.html'.format(index), 'wb') as f:     #         f.write(content)     #     return None     def get_items(self, content, index):         '''         从响应内容中提取页面标题,并保存HTML内容到文件         :param content: HTML内容的字节串         :param index: 用于文件命名的索引         :return: 页面标题和URL的字典         '''         # 解析HTML内容         soup = BeautifulSoup(content, 'html.parser')          # 提取页面标题         title = soup.title.string if soup.title else '无标题'          # 构造URL,这里使用index作为页码         url = self.base_url.format(self.kw, index)          # 保存HTML内容到文件         with open(f'tieba-{index}.html', 'wb') as f:             f.write(content)          # 返回包含URL和标题的字典         return {'url': url, 'title': title}      # def save_items(self, items):     #     '''     #     保存数据     #     :param items:     #     :return:     #     '''     def save_items(self, items):         '''         保存提取的页面标题和URL到JSON文件         :param items: 字典,包含URL和标题         :return:         '''         # 检查items是否为None         if items is not None:             # 保存到JSON文件             with open(f'tieba-{items["url"].split("&pn=")[1]}.json', 'w', encoding='utf-8') as f:                 json.dump(items, f, ensure_ascii=False, indent=4)      def run(self):         # 1. 获取 url 列表         url_list = self.get_url_list()          for url in url_list:             # 2. 发送请求获取响应             content = self.get_content(url)             # 3. 从响应中提取数据             items = self.get_items(content, url_list.index(url) + 1)             # 4. 保存数据             self.save_items(items)          pass   if __name__ == '__main__':     spider = TiebaSpider("英雄联盟", 150)     spider.run() 

具体解析

1. 导入模块
import requests import json from bs4 import BeautifulSoup 

这部分代码导入了三个库:requests用于发送HTTP请求,json用于处理JSON数据,BeautifulSoup用于解析HTML。

2. 定义爬虫类
class TiebaSpider(): 

定义了一个名为TiebaSpider的类,它将包含爬取数据的方法。

3. 初始化方法
def __init__(self, kw, max_pn):     self.max_pn = max_pn     self.kw = kw     self.base_url = "https://tieba.baidu.com/f?kw={}&ie=utf-8&pn={}"  # 注意这里修复了HTML实体     self.headers = {         "User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_0) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.110 Safari/537.36"     } 

__init__方法初始化爬虫的关键词kw,最大页码max_pn,基础URLbase_url(修复了HTML实体"),以及包含User-Agent的请求头。

4. 获取URL列表
def get_url_list(self):     return [self.base_url.format(self.kw, pn) for pn in range(0, self.max_pn, 50)] 

get_url_list方法生成一个包含所有请求URL的列表。它使用列表推导式,根据页码范围生成URL。

5. 获取页面内容
def get_content(self, url):     response = requests.get(url=url, headers=self.headers)     return response.content 

get_content方法通过requests.get发送GET请求,获取指定URL的页面内容。

6. 提取页面数据
def get_items(self, content, index):     soup = BeautifulSoup(content, 'html.parser')     title = soup.title.string if soup.title else '无标题'     url = self.base_url.format(self.kw, index)     with open(f'tieba-{index}.html', 'wb') as f:         f.write(content)     return {'url': url, 'title': title} 

get_items方法使用BeautifulSoup解析页面内容,提取页面标题,并保存HTML到文件。然后返回一个包含URL和标题的字典。

7. 保存数据
def save_items(self, items):     if items is not None:         with open(f'tieba-{items["url"].split("&pn=")[1]}.json', 'w', encoding='utf-8') as f:             json.dump(items, f, ensure_ascii=False, indent=4) 

save_items方法检查items是否为None,然后尝试将items字典保存为JSON文件。

8. 运行爬虫
def run(self):     url_list = self.get_url_list()     for url in url_list:         content = self.get_content(url)         items = self.get_items(content, url_list.index(url) + 1)         self.save_items(items) 

run方法是爬虫的主要逻辑,依次调用其他方法执行爬取任务。

9. 主程序
if __name__ == '__main__':     spider = TiebaSpider("英雄联盟", 150)     spider.run() 

主程序创建TiebaSpider的实例,传入关键词和最大页码,然后调用run方法启动爬虫。

总结

这个爬虫程序通过发送HTTP请求获取页面内容,然后解析HTML以提取页面标题,并将页面内容保存为HTML文件。最后,它将每个页面的URL和标题保存为JSON文件。但是后续尝试将其中每篇文章的标题和url提取出来,有点翻车,明天再琢磨一下怎么解决。

广告一刻

为您即时展示最新活动产品广告消息,让您随时掌握产品活动新动态!