侯体宗的博客
  • 首页
  • Hyperf版
  • beego仿版
  • 人生(杂谈)
  • 技术
  • 关于我
  • 更多分类
    • 文件下载
    • 文字修仙
    • 中国象棋ai
    • 群聊
    • 九宫格抽奖
    • 拼图
    • 消消乐
    • 相册

python爬虫 猫眼电影和电影天堂数据csv和mysql存储过程解析

Python  /  管理员 发布于 7年前   568

字符串常用方法

# 去掉左右空格'hello world'.strip()  # 'hello world'# 按指定字符切割'hello world'.split(' ') # ['hello','world']# 替换指定字符串'hello world'.replace(' ','#') # 'hello#world'

csv模块

作用:将爬取的数据存放到本地的csv文件中

使用流程

  • 导入模块
  • 打开csv文件
  • 初始化写入对象
  • 写入数据(参数为列表)
import csvwith open('test.csv','w') as f:  writer = csv.writer(f) # 初始化写入对象 # 写一行 writer.writerow(['超哥哥',20]) writer.writerow(['步惊云',22])with open('test.csv','a') as f: writer = csv.writer(f) # 写多行 data_list = [('聂风',23),('秦霜',30)] writer.writerows(data_list)

Windows中使用csv模块默认会在每行后面添加一个空行,使用newline=''可解决

with open('xxx.csv','w',newline='') as f:

猫眼电影top100抓取案例

确定URL网址

猫眼电影 - 榜单 - top100榜 目标

电影名称、主演、上映时间 操作步骤

1、查看是否为动态加载

右键 - 查看网页源代码 - 搜索爬取关键字(查看在源代码中是否存在)

2、找URL规律

  • 第1页:https://maoyan.com/board/4?offset=0
  • 第2页:https://maoyan.com/board/4?offset=10
  • 第n页:offset=(n-1)*10

3、正则表达式

<div class="movie-item-info">.*?title="(.*?)".*?class="star">(.*?)</p>.*?releasetime">(.*?)</p>

4、编写程序框架,完善程序

  • 打印程序执行时间
  • 随机的User-Agent,(确保每次发请求使用随机)
  • 数据爬下来后做处理(字符串),定义成字典
  • 一条龙: 获取 -> 调用解析 -> 数据处理
  • 猫眼电影数据存入本地 maoyanfilm.csv 文件
from urllib import requestimport timeimport reimport csvimport randomclass MaoyanSpider(object): def __init__(self):  self.page = 1 # 用于记录页数  self.url = 'https://maoyan.com/board/4?offset={}'  self.agent = [   'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/535.1 (KHTML, like Gecko) Chrome/14.0.835.163 \   Safari/535.1',   'Mozilla/5.0 (Windows NT 6.1; WOW64; rv:6.0) Gecko/20100101 Firefox/6.0',   'Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; WOW64; Trident/4.0; SLCC2; .NET CLR 2.0.50727; \   .NET CLR 3.5.30729; .NET CLR 3.0.30729; Media Center PC 6.0; .NET4.0C; InfoPath.3)',   'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/535.1 (KHTML, like Gecko) Chrome/14.0.835.163 Safari/535.1'] # 请求 def get_page(self, url):  headers = {'User-Agent': random.choice(self.agent)} # 每次使用随机的user-agent  req = request.Request(url=url, headers=headers)  # 创建请求对象  res = request.urlopen(req)       # 发起请求  html = res.read().decode('utf-8')     # 获取请求内容  self.parse_page(html)        # 直接调用解析函数 # 解析 def parse_page(self, html):  pattren = re.compile(   '<div class="movie-item-info">.*?title="(.*?)".*?class="star">(.*?)</p>.*?releasetime">(.*?)</p>', re.S)  r_list = pattren.findall(html)  # rlist: [('霸王别姬', '\n    主演:张国荣,张丰毅,巩俐\n  ', '上映时间:1993-01-01'),(...),(...)]  self.write_page(r_list)    # 写入csv文件 # # 保存,打印输出 # def write_page(self,r_list): #  one_film_dict = {} #  for rt in r_list: #   one_film_dict['name'] = rt[0].strip() #   one_film_dict['star'] = rt[1].strip() #   one_film_dict['time'] = rt[2].strip()[5:15] # #   print(one_film_dict) # 保存到csv文件(writerows) -- 推荐使用此方法 def write_page(self, r_list):  # 空列表,最终writerows()的参数: [(),(),()]  film_list = []  with open('maoyan.csv', 'a',newline="") as f:   writer = csv.writer(f)   for rt in r_list:    # 把处理过的数据定义成元组    t = (rt[0], rt[1].strip(), rt[2].strip()[5:15])    film_list.append(t)   writer.writerows(film_list) def main(self):  for offset in range(0, 31, 10):   url = self.url.format(offset)   self.get_page(url)   time.sleep(random.randint(1, 3))   print('第%d页爬取完成' % self.page)   self.page += 1if __name__ == '__main__': start = time.time() spider = MaoyanSpider() spider.main() end = time.time() print('执行时间: %.2f' % (end - start))

数据持久化存储(MySQL数据库)

让我们来回顾一下pymysql模块的基本使用

import pymysqldb = pymysql.connect('localhost', 'root', '123456', 'maoyandb', charset='utf8')cursor = db.cursor() # 创建游标对象# execute()方法第二个参数为列表传参补位cursor.execute('insert into film values(%s,%s,%s)', ['霸王别姬', '张国荣', '1993'])db.commit() # 提交到数据库执行cursor.close() # 关闭db.close()

让我们来回顾一下pymysql中executemany()的用法

import pymysql# 数据库连接对象db = pymysql.connect('localhost', 'root', '123456', charset='utf8')cursor = db.cursor() # 游标对象ins_list = []   # 存放所有数据的大列表for i in range(2): name = input('请输入第%d个学生姓名:' % (i + 1)) age = input('请输入第%d个学生年龄:' % (i + 1)) ins_list.append([name, age])ins = 'insert into t3 values(%s,%s)' # 定义插入语句cursor.executemany(ins, ins_list) # 一次数据库的IO操作可插入多条语句,提升性能db.commit()  # 提交到数据库执行cursor.close() # 关闭游标db.close()  # 关闭数据库ins = 'insert into maoyanfilm values(%s,%s,%s)'cursor.execute(['霸王', '国荣', '1991'])cursor.executemany([  ['月光宝盒', '周星驰', '1993'],  ['大圣娶亲', '周星驰', '1993']])

练习:把猫眼电影案例中电影信息存入MySQL数据库中(尽量使用executemany方法)

from urllib import requestimport timeimport reimport pymysqlimport randomclass MaoyanSpider(object): def __init__(self):  self.page = 1 # 用于记录页数  self.url = 'https://maoyan.com/board/4?offset={}'  self.ua_list = [   'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/535.1 (KHTML, like Gecko) \   Chrome/14.0.835.163 Safari/535.1',   'Mozilla/5.0 (Windows NT 6.1; WOW64; rv:6.0) Gecko/20100101 Firefox/6.0',   'Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; WOW64; Trident/4.0; SLCC2; \   .NET CLR 2.0.50727; .NET CLR 3.5.30729; .NET CLR 3.0.30729; Media Center PC 6.0; .NET4.0C; InfoPath.3)']  # 创建数据库连接对象和游标对象  self.db = pymysql.connect('localhost', 'root', '123456', 'maoyandb', charset='utf8')  self.cursor = self.db.cursor() # 获取 def get_page(self, url):  # 每次使用随机的user-agent  headers = {'User-Agent': random.choice(self.ua_list)}  req = request.Request(url=url, headers=headers)  res = request.urlopen(req)  html = res.read().decode('utf-8')  self.parse_page(html)  # 直接调用解析函数 # 解析 def parse_page(self, html):  pattren = re.compile(   '<div class="movie-item-info">.*?title="(.*?)".*?class="star">(.*?)</p>.*?releasetime">(.*?)</p>', re.S)  # rlist: [('霸王别姬','张国荣','1993'),(),()]  r_list = pattren.findall(html)  print(r_list)  self.write_page(r_list) # 存入mysql数据库(executemany([ [],[],[] ])) def write_page(self, r_list):  film_list = []  ins = 'insert into filmtab values(%s,%s,%s)'  # 定义插入语句  # 处理数据,放到大列表film_list中  for rt in r_list:   one_film = [rt[0], rt[1].strip(), rt[2].strip()[5:15]]   # 添加到大列表中   film_list.append(one_film)  # 一次数据库IO把1页数据存入  self.cursor.executemany(ins, film_list)  # 提交到数据库执行  self.db.commit() def main(self):  for offset in range(0, 31, 10):   url = self.url.format(offset)   self.get_page(url)   time.sleep(random.randint(1, 3))   print('第%d页爬取完成' % self.page)   self.page += 1  # 断开数据库(所有页爬完之后)  self.cursor.close()  self.db.close()if __name__ == '__main__': start = time.time() spider = MaoyanSpider() spider.main() end = time.time() print('执行时间: %.2f' % (end - start))

让我们来做个SQL命令查询

1、查询20年以前的电影的名字和上映时间

select name,time from filmtab where time<(now()-interval 20 year);

2、查询1990-2000年的电影名字和上映时间

select name,time from filmtab where time>='1990-01-01' and time<='2000-12-31';

让我们来复习一下mongdb数据库

import pymongo# 1.连接对象conn = pymongo.MongoClient(host='127.0.0.1', port=27017)db = conn['maoyandb']  # 2.库对象myset = db['filmtab']  # 3.集合对象myset.insert_one({'name': '赵敏'}) # 4.插入数据库

练习:把猫眼电影案例中电影信息存入MongDB数据库中

from urllib import requestimport reimport timeimport randomimport pymongoclass MaoyanSpider(object): def __init__(self):  self.url = 'https://maoyan.com/board/4?offset={}'  # 计数  self.num = 0  # 创建3个对象  self.conn = pymongo.MongoClient('localhost', 27017)  self.db = self.conn['maoyandb']  self.myset = self.db['filmset']  self.ua_list = [   'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/535.1 (KHTML, like Gecko) Chrome/14.0.835.163 Safari/535.1',   'Mozilla/5.0 (Windows NT 6.1; WOW64; rv:6.0) Gecko/20100101 Firefox/6.0',   'Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 6.1; WOW64; Trident/4.0; SLCC2; .NET CLR 2.0.50727; .NET \   CLR 3.5.30729; .NET CLR 3.0.30729; Media Center PC 6.0; .NET4.0C; InfoPath.3)', ] def get_html(self, url):  headers = {   'User-Agent': random.choice(self.ua_list)  }  req = request.Request(url=url, headers=headers)  res = request.urlopen(req)  html = res.read().decode('utf-8')  # 直接调用解析函数  self.parse_html(html) def parse_html(self, html):  re_bds = r'<div class="movie-item-info">.*?title="(.*?)".*?class="star">(.*?)</p>.*?releasetime">(.*?)</p>'  pattern = re.compile(re_bds, re.S)  # film_list: [('霸王别姬','张国荣','1993'),()]  film_list = pattern.findall(html)  # 直接调用写入函数  self.write_html(film_list) # mongodb数据库 def write_html(self, film_list):  for film in film_list:   film_dict = {    'name': film[0].strip(),    'star': film[1].strip(),    'time': film[2].strip()[5:15]   }   # 插入mongodb数据库   self.myset.insert_one(film_dict) def main(self):  for offset in range(0, 31, 10):   url = self.url.format(offset)   self.get_html(url)   time.sleep(random.randint(1, 2))if __name__ == '__main__': start = time.time() spider = MaoyanSpider() spider.main() end = time.time() print('执行时间:%.2f' % (end - start))

电影天堂案例(二级页面抓取)

1、查看是否为静态页面,是否为动态加载

  右键 - 查看网页源代码

2、确定URL地址

  百度搜索 :电影天堂 - 2019年新片 - 更多

3、目标

*********一级页面***********
1、电影名称
2、电影链接
*********二级页面***********

1、下载链接

4、步骤

找URL规律

第1页 :https://www.dytt8.net/html/gndy/dyzz/list_23_1.html

第2页 :https://www.dytt8.net/html/gndy/dyzz/list_23_2.html

第n页 :https://www.dytt8.net/html/gndy/dyzz/list_23_n.html

写正则表达式

1、一级页面正则表达式(电影名称、电影详情链接)

<table width="100%".*?<td height="26">.*?<a href="https:/article/(.*?)" rel="external nofollow" rel="external nofollow" .*?>(.*?)</a>

2、二级页面正则表达式

<td style="WORD-WRAP.*?>.*?>(.*?)</a>

代码实现

# decode('gbk','ignore') 注意ignore参数

# 注意结构和代码可读性(一个函数不要太冗余)

from urllib import requestimport reimport timeimport randomfrom useragents import *import pymysqlclass FilmSky(object): def __init__(self):  self.url = 'https://www.dytt8.net/html/gndy/dyzz/list_23_{}.html'  # 定义两个对象  self.db = pymysql.connect('127.0.0.1', 'root', '123456', 'maoyandb', charset='utf8')  self.cursor = self.db.cursor() # 获取html函数(因为两个页面都需要发请求) def get_page(self, url):  req = request.Request(url=url, headers={'User-Agent': random.choice(ua_list)})  res = request.urlopen(req)  # ignore参数,实在处理不了的编码错误忽略  # 查看网页源码,发现网页编码为 gb2312,不是 utf-8  html = res.read().decode('gbk', 'ignore')  return html # 解析提取数据(把名称和下载链接一次性拿到) # html为一级页面响应内容 def parse_page(self, html):  # 1. 先解析一级页面(电影名称 和 详情链接)  pattern = re.compile('<table width="100%".*?<td height="26">.*?<a href="https:/article/(.*?)" rel="external nofollow" rel="external nofollow" .*?>(.*?)</a>', re.S)  # film_list: [('详情链接','名称'),()]  film_list = pattern.findall(html)  # [('/html/gndy/dyzz/20190806/58956.html', '019年惊悚动作《报仇雪恨/血债血偿》BD中英双字幕'),(),()]  ins = 'insert into filmsky values(%s,%s)'  for film in film_list:   film_name = film[1]   film_link = 'https://www.dytt8.net' + film[0]   # 2. 拿到详情链接后,再去获取详情链接html,提取下载链接   download_link = self.parse_two_html(film_link)   self.cursor.execute(ins, [film_name, film_link])   self.db.commit()   # 打印测试   d = {'电影名称': film_name, '下载链接': download_link}   print(d) # {'电影名称': '019年惊悚动作《报仇雪恨/血债血偿》BD中英双字幕', '下载链接': 'ftp://ygdy8:[email protected]:8590/阳光电影www.ygdy8.com.报仇雪恨.BD.720p.中英双字幕.mkv'} # 解析二级页面,获取下载链接 def parse_two_html(self, film_link):  two_html = self.get_page(film_link)  pattern = re.compile('<td style="WORD-WRAP.*?>.*?>(.*?)</a>', re.S)  download_link = pattern.findall(two_html)[0]  return download_link # 主函数 def main(self):  for page in range(1, 11):   url = self.url.format(page)   html = self.get_page(url)   self.parse_page(html)   time.sleep(random.randint(1, 3))   print('第%d页完成' % page)if __name__ == '__main__': start = time.time() spider = FilmSky() spider.main() end = time.time() print('执行时间:%.2f' % (end - start))

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。


  • 上一条:
    详解Python3 pandas.merge用法
    下一条:
    python爬取Ajax动态加载网页过程解析
  • 昵称:

    邮箱:

    0条评论 (评论内容有缓存机制,请悉知!)
    最新最热
    • 分类目录
    • 人生(杂谈)
    • 技术
    • linux
    • Java
    • php
    • 框架(架构)
    • 前端
    • ThinkPHP
    • 数据库
    • 微信(小程序)
    • Laravel
    • Redis
    • Docker
    • Go
    • swoole
    • Windows
    • Python
    • 苹果(mac/ios)
    • 相关文章
    • 在python语言中Flask框架的学习及简单功能示例(0个评论)
    • 在Python语言中实现GUI全屏倒计时代码示例(0个评论)
    • Python + zipfile库实现zip文件解压自动化脚本示例(0个评论)
    • python爬虫BeautifulSoup快速抓取网站图片(1个评论)
    • vscode 配置 python3开发环境的方法(0个评论)
    • 近期文章
    • 在go语言中使用api.geonames.org接口实现根据国际邮政编码获取地址信息功能(1个评论)
    • 在go语言中使用github.com/signintech/gopdf实现生成pdf分页文件功能(0个评论)
    • gmail发邮件报错:534 5.7.9 Application-specific password required...解决方案(0个评论)
    • 欧盟关于强迫劳动的规定的官方举报渠道及官方举报网站(0个评论)
    • 在go语言中使用github.com/signintech/gopdf实现生成pdf文件功能(0个评论)
    • Laravel从Accel获得5700万美元A轮融资(0个评论)
    • 在go + gin中gorm实现指定搜索/区间搜索分页列表功能接口实例(0个评论)
    • 在go语言中实现IP/CIDR的ip和netmask互转及IP段形式互转及ip是否存在IP/CIDR(0个评论)
    • PHP 8.4 Alpha 1现已发布!(0个评论)
    • Laravel 11.15版本发布 - Eloquent Builder中添加的泛型(0个评论)
    • 近期评论
    • 122 在

      学历:一种延缓就业设计,生活需求下的权衡之选中评论 工作几年后,报名考研了,到现在还没认真学习备考,迷茫中。作为一名北漂互联网打工人..
    • 123 在

      Clash for Windows作者删库跑路了,github已404中评论 按理说只要你在国内,所有的流量进出都在监控范围内,不管你怎么隐藏也没用,想搞你分..
    • 原梓番博客 在

      在Laravel框架中使用模型Model分表最简单的方法中评论 好久好久都没看友情链接申请了,今天刚看,已经添加。..
    • 博主 在

      佛跳墙vpn软件不会用?上不了网?佛跳墙vpn常见问题以及解决办法中评论 @1111老铁这个不行了,可以看看近期评论的其他文章..
    • 1111 在

      佛跳墙vpn软件不会用?上不了网?佛跳墙vpn常见问题以及解决办法中评论 网站不能打开,博主百忙中能否发个APP下载链接,佛跳墙或极光..
    • 2016-10
    • 2016-11
    • 2018-04
    • 2020-03
    • 2020-04
    • 2020-05
    • 2020-06
    • 2022-01
    • 2023-07
    • 2023-10
    Top

    Copyright·© 2019 侯体宗版权所有· 粤ICP备20027696号 PHP交流群

    侯体宗的博客