Ajax爬取豆瓣电影目录(Python)

下面的分析相当于一个框架,搞懂之后,对于类似的文字爬取,我们也可以实现。就算不能使用Ajax方法,我们也能够使用相同思想去爬取我们想要的数据。

豆瓣电影排行榜分析

网址https://movie.douban.com/explore#!type=movie&tag=%E7%83%AD%E9%97%A8&sort=recommend&page_limit=20&page_start=0

首先我们打开网页的审查元素,选中Network==》XHR==》电影相关信息网页文件

筛选并比较以下数据(三个文件数据)

请求地址

1Request URL:https://movie.douban.com/j/search_subjects?type=movie&tag=%E7%83%AD%E9%97%A8&sort=recommend&page_limit=20&page_start=0 2 3Request URL:https://movie.douban.com/j/search_subjects?type=movie&tag=%E7%83%AD%E9%97%A8&sort=recommend&page_limit=20&page_start=20 4 5Request URL:https://movie.douban.com/j/search_subjects?type=movie&tag=%E7%83%AD%E9%97%A8&sort=recommend&page_limit=20&page_start=40

查询参数

1type:movie 2tag:热门 3sort:recommend 4page_limit:20 5page_start:0 6 7type:movie 8tag:热门 9sort:recommend 10page_limit:20 11page_start:20 12 13type:movie 14tag:热门 15sort:recommend 16page_limit:20 17page_start:40

请求报头

1Host:movie.douban.com 2Referer:https://movie.douban.com/explore 3User-Agent:Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/63.0.3239.132 Safari/537.36 4X-Requested-With:XMLHttpRequest

通过比较请求地址和查询参数,得出

1请求地址 = baseurl+type+tag+sort+page_limit+page_start 2 3baseurl:https://movie.douban.com/j/search_subjects? 4type:固定为movie 5tag:关键字,需要将utf-8转换为urlencode 6sort:固定为recommend 7page_limit:表示一页显示的电影数量,固定20 8page_start:表示电影页数,从0开始,20为公差的递增函数

由此我们获取到了我们需要的数据,可以将爬虫分为三步

  1. 获取网页json格式代码
  2. 从代码中获取电影名和电影海报图片链接
  3. 将获得的图片命名为电影名

流程

准备工作

在函数外部定义伪装的请求报头

1headers={ 2 'Host': 'movie.douban.com', 3 'Referer': 'https://movie.douban.com/explore', 4 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/63.0.3239.132 Safari/537.36', 5 'X-Requested-With': 'XMLHttpRequest' 6}

获取json格式代码

1def get_page(page): 2 #请求参数 3 params={ 4 'type': 'movie', 5 'tag': '奥特曼', 6 'sort': 'recommend', 7 'page_limit': '20', 8 'page_start': page, 9 } 10 #基本网页链接 11 base_url = 'https://movie.douban.com/j/search_subjects?' 12 #将基本网页链接与请求参数结合在一起 13 url = base_url + urlencode(params) 14 try: 15 #获取网页代码 16 resp = requests.get(url, headers=headers) 17 print(url) 18 #返回json数据格式代码 19 if 200 == resp.status_code: 20 print(resp.json()) 21 return resp.json() 22 except requests.ConnectionError: 23 return None

筛选数据

通过观察电影列表代码文件的preview,进行数据筛选

1def get_image(json): 2 if(json.get('subjects')): 3 data=json.get('subjects') 4 for item in data: 5 title=item.get('title') 6 imageurl=item.get('cover') 7 #返回"信息"字典 8 yield { 9 'title':title, 10 'images':imageurl, 11 }

存储图片文件

1def save_page(item): 2 #文件夹名称 3 file_name = '奥特曼电影大全' 4 if not os.path.exists(file_name): 5 os.makedirs(file_name) 6 7 #获取图片链接 8 response=requests.get(item.get('images')) 9 #储存图片文件 10 if response.status_code==200: 11 file_path = file_name + os.path.sep + item.get('title') + '.jpg' 12 with open(file_path, 'wb') as f: 13 f.write(response.content)

多线程处理

1def main(page): 2 json = get_page(page) 3 for item in get_image(json): 4 print(item) 5 save_page(item) 6 7if __name__ == '__main__': 8 pool = Pool() 9 pool.map(main, [i for i in range(0, 200, 20)]) 10 pool.close() 11 pool.join()

总代码

1import requests 2from urllib.parse import urlencode 3import os 4from multiprocessing.pool import Pool 5 6headers={ 7 'Host': 'movie.douban.com', 8 'Referer': 'https://movie.douban.com/explore', 9 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/63.0.3239.132 Safari/537.36', 10 'X-Requested-With': 'XMLHttpRequest' 11} 12 13def get_page(page): 14 #请求参数 15 params={ 16 'type': 'movie', 17 'tag': '奥特曼', 18 'sort': 'recommend', 19 'page_limit': '20', 20 'page_start': page, 21 } 22 #基本网页链接 23 base_url = 'https://movie.douban.com/j/search_subjects?' 24 #将基本网页链接与请求参数结合在一起 25 url = base_url + urlencode(params) 26 try: 27 #获取网页代码 28 resp = requests.get(url, headers=headers) 29 print(url) 30 #返回json数据格式代码 31 if 200 == resp.status_code: 32 print(resp.json()) 33 return resp.json() 34 except requests.ConnectionError: 35 return None 36 37def get_image(json): 38 if(json.get('subjects')): 39 data=json.get('subjects') 40 for item in data: 41 title=item.get('title') 42 imageurl=item.get('cover') 43 #返回"信息"字典 44 yield { 45 'title':title, 46 'images':imageurl, 47 } 48 49def save_page(item): 50 #文件夹名称 51 file_name = '奥特曼电影大全' 52 if not os.path.exists(file_name): 53 os.makedirs(file_name) 54 55 #获取图片链接 56 response=requests.get(item.get('images')) 57 #储存图片文件 58 if response.status_code==200: 59 file_path = file_name + os.path.sep + item.get('title') + '.jpg' 60 with open(file_path, 'wb') as f: 61 f.write(response.content) 62 63def main(page): 64 json = get_page(page) 65 for item in get_image(json): 66 print(item) 67 save_page(item) 68 69if __name__ == '__main__': 70 pool = Pool() 71 pool.map(main, [i for i in range(0, 200, 20)]) 72 pool.close() 73 pool.join()

 本来是准备使用https://movie.douban.com/tag/#/ 不过在后面,刷新网页时,总是出现服务器问题。不过下面的代码还是可以用。

1import requests 2from urllib.parse import urlencode 3import os 4from hashlib import md5 5from multiprocessing.pool import Pool 6 7headers={ 8 'Host': 'movie.douban.com', 9 'Referer': 'https://movie.douban.com/tag/', 10 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/63.0.3239.132 Safari/537.36', 11} 12 13def get_page(page): 14 params={ 15 'sort':'U', 16 'range':'0,10', 17 'tags':'奥特曼', 18 'start': page, 19 } 20 base_url = 'https://movie.douban.com/j/new_search_subjects?' 21 url = base_url + urlencode(params) 22 try: 23 resp = requests.get(url, headers=headers) 24 print(url) 25 if 200 == resp.status_code: 26 print(resp.json()) 27 return resp.json() 28 except requests.ConnectionError: 29 return None 30 31def get_image(json): 32 if(json.get('data')): 33 data=json.get('data') 34 for item in data: 35 title=item.get('title') 36 imageurl=item.get('cover') 37 yield { 38 'title':title, 39 'images':imageurl, 40 } 41 42def save_page(item): 43 file_name='奥特曼大全'+os.path.sep+item.get('title') 44 if not os.path.exists(file_name): 45 os.makedirs(file_name) 46 try: 47 response=requests.get(item.get('images')) 48 if response.status_code==200: 49 file_path = '{0}/{1}.{2}'.format(file_name, md5(response.content).hexdigest(), 'jpg') 50 if not os.path.exists(file_path): 51 with open(file_path, 'wb') as f: 52 f.write(response.content) 53 else: 54 print('Already Downloaded', file_path) 55 except requests.ConnectionError: 56 print('Failed to Save Image') 57 58def main(page): 59 json = get_page(page) 60 for item in get_image(json): 61 print(item) 62 save_page(item) 63 64if __name__ == '__main__': 65 pool = Pool() 66 pool.map(main, [i for i in range(0, 200, 20)]) 67 pool.close() 68 pool.join()
点赞
收藏

评论区

加载中...

相关推荐

MySQL:[Err] 1292 - Incorrect datetime value: ‘0000-00-00 00:00:00‘ for column ‘CREATE_TIME‘ at row 1

文章目录问题用navicat导入数据时,报错:原因这是因为当前的MySQL不支持datetime为0的情况。解决修改sql\mode:sql\mode:SQLMode定义了MySQL应支持的SQL语法、数据校验等,这样可以更容易地在不同的环境中使用MySQL。全局s

Oracle 分组与拼接字符串同时使用

SELECTT.,ROWNUMIDFROM(SELECTT.EMPLID,T.NAME,T.BU,T.REALDEPART,T.FORMATDATE,SUM(T.S0)S0,MAX(UPDATETIME)CREATETIME,LISTAGG(TOCHAR(

MySQL部分从库上面因为大量的临时表tmp_table造成慢查询

背景描述Time:20190124T00:08:14.70572408:00User@Host:@Id:Schema:sentrymetaLast_errno:0Killed:0Query_time:0.315758Lock_

皕杰报表之UUID

​在我们用皕杰报表工具设计填报报表时,如何在新增行里自动增加id呢?能新增整数排序id吗?目前可以在新增行里自动增加id,但只能用uuid函数增加UUID编码,不能新增整数排序id。uuid函数说明:获取一个UUID,可以在填报表中用来创建数据ID语法:uuid()或uuid(sep)参数说明:sep布尔值,生成的uuid中是否包含分隔符'',缺省为

手写Java HashMap源码

HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程HashMap的使用教程22

java将前端的json数组字符串转换为列表

记录下在前端通过ajax提交了一个json数组的字符串,在后端如何转换为列表。前端数据转化与请求varcontracts{id:'1',name:'yanggb合同1'},{id:'2',name:'yanggb合同2'},{id:'3',name:'yang

Ajax爬取豆瓣电影目录(Python) - HelloWorld