在简书看过一篇文章Python爬虫入门 | 7 分类爬取豆瓣电影,解决动态加载问题,在此基础上我想完成如下3件事:
- 将电影信息根据评分进行排序并保存在电子表格里
- 将电影封面图片插入对应的单元格里
- 运用多进程爬取电影信息
用户未登录情况下不要使用多进程频繁请求,否则可能会出现如下提示: 检测到有异常请求从你的 IP 发出,请 [登录] 使用豆瓣。
以豆瓣青春题材电影为示例:
滚动条向下滑动至页面底部后发现页面底部有加载更多按钮。
敲击键盘上的F12打开开发者模式,依次点击
Network
和XHR
标签按钮。点击页面底部的加载更多
按钮会加载出更多的电影信息,同时我们观察到每点击一次加载更多
按钮,start
参数值就会增加20。在
Headers
里查看对应的Request URL
,其请求地址为https://movie.douban.com/j/new_search_subjects?sort=T&range=0,10&tags=&start=20
(tags
值是我们查看电影的类型,如'青春')我们定义一个函数来获取URL列表。其中
tags
是电影类型,index
是指查点击加载按钮的次数。
def getURLs(index,tags):
return ['https://movie.douban.com/j/new_search_subjects?sort=T&range=0,10&tags={0}&start={1}'.format(
parse.quote(tags), str(i*20)) for i in range(index)]
从Preview
里我们可以发现每个URL获取到的数据是包含20个字典的数组。
我们想要获取电影信息,只要根据key值取出字典里的Value即可。
def getMovies(url):
# 请求头
headers = {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; WOW64; Trident/7.0; rv:11.0) like Gecko'
}
# 代理池
proxyIPs =[ 'http://113.207.44.70:3128', 'http://39.80.33.145:81',
'http://115.231.218.102:1080','http://113.107.166.245:1080',
'http://183.230.177.170:8081','http://123.57.254.211:8118']
# 从代理池中随机取出一个IP
proxyIP = random.choice(proxyIPs)
proxies = {
'http' : proxyIP,
'https': proxyIP
}
# 定义电影数组
movies = []
try:
jsonData = requests.get(url,headers = headers,proxies = proxies).json()
# 每个jsonData里包含20个字典数据
for i in range(20):
dict = jsonData['data'][i]
# 电影简介
text = getMovieIntroduction(movieUrl)
# 创建movie字典
movie = {'影名': dict['title'], '评分': dict['rate'], '导演': '/'.join(dict['directors']),
'主演': '/'.join(dict['casts']), '链接': dict['url'], '封面': dict['cover'], '简介': text}
# 将单个movie 字典添加到数组里
movies.append(movie)
return movies
except Exception as e:
print('出错啦:{}'.format(str(e)))
return []
写入Excel文件:
def writeToExcel(movies,fileName):
columns = ['影名', '评分', '导演', '主演', '简介','封面', '链接']
df = pd.DataFrame.from_dict(movies)
# 按照固定的列名顺序生成
df = df.loc[:, columns]
# 按照'评分'排序(降序)并替换所有数据
df.sort_values('评分', ascending=False, inplace=True)
# 将index改成从1开始
df.index = range(1, len(df) + 1)
# 写入excel文件
df.to_excel('{}.xls'.format(fileName))
返回Url列表:
def getURLs(index,tags):
return ['https://movie.douban.com/j/new_search_subjects?sort=T&range=0,10&tags={0}&start={1}'.format(
parse.quote(tags), str(i*20)) for i in range(index)]
def main():
print('开始时间:{}'.format(datetime.datetime.now()))
results = []
# getMovies(5,'青春')
pool = Pool(cpu_count()) # 根据CPU数量创建
for movies in pool.map(getMovies, getURLs(10, '励志')):
for movie in movies:
results.append(movie)
print(movie)
writeToExcel(results,'movies_10')
# createExcel(results)
print('结束时间:{}'.format(datetime.datetime.now()))
if __name__ == '__main__':
main()
网友评论