正文
本文是下面两篇文章的续篇
爬虫基本原理
爬虫代码改进(一)
本系列包括如下内容
-
抓取豆瓣top250一页多个字段
-
整合成列表
-
存储为json文件
-
定义成函数形式
-
多页抓取之构造url
-
多页抓取之翻页
-
抓取二级页面数据
-
通过生成器优化代码
-
改写为类的形式
本文主要讲
-
多页抓取之构造url
-
多页抓取之翻页
-
抓取二级页面数据
上一篇文章我们定义函数,抓取豆瓣top250一页的数据,代码如下
import requests # 导入网页请求库
from bs4 import BeautifulSoup # 导入网页解析库
import json
def start_requests(url):
r = requests.get(url)
return r.content
def parse(text):
soup = BeautifulSoup(text, 'html.parser')
movie_list = soup.find_all('div', class_ = 'item')
result_list = []
for movie in movie_list:
mydict = {}
mydict['title'] = movie.find('span', class_ = 'title').text
mydict['score'] = movie.find('span', class_ = 'rating_num').text
mydict['quote'] = movie.find('span', class_ = 'inq').text
star = movie.find('div', class_ = 'star')
mydict['comment_num'] = star.find_all('span')[-1].text[:-3]
result_list.append(mydict)
return result_list
def write_json(result):
s = json.dumps(result, indent = 4, ensure_ascii=False)
with open('movies.json', 'w', encoding = 'utf-8') as f:
f.write(s)
def main():
url = 'https://movie.douban.com/top250'
text = start_requests(url)
result = parse(text)
write_json(result)
if __name__ == '__main__':
main()
接下来我们要根据这个代码进行改进。
多页抓取之构造url
上一篇文章我们已经完善了抓取一个页面的爬虫代码,现在我们需要抓取10个页面250个电影的信息,抓取多页信息一般有两种方式,一种是构造url,一种是翻页,本节我们来讲如何构造url。
我们可以直接看这几页的链接有什么规律
第一页 https://movie.douban.com/top250
第二页 https://movie.douban.com/top250?start=25&filter=
第三页 https://movie.douban.com/top250?start=50&filter=
第四页 https://movie.douban.com/top250?start=75&filter=
可以发现除了第一页,后面都只换了一个数字,而且是等差数列。那么我们可以猜想第一页这样可不可以
https://movie.douban.com/top250?start=0&filter=
将这个链接输入浏览器发现其实就是第一页,所以我们就可以根据这个规律构造url字符串了,抓取250个电影只需要一个循环。我们现在还是只抓取标题打印出来
import requests # 导入网页请求库
from bs4 import BeautifulSoup # 导入网页解析库
def start_requests(url):
r = requests.get(url)
return r.content
def parse(text):
soup = BeautifulSoup(text, 'html.parser')
movie_list = soup.find_all('div', class_ = 'item')
for movie in movie_list:
print(movie.find('span', class_ = 'title').text)
def main():
for i in range(10):
url = 'https://movie.douban.com/top250?start={}&filter='.format(i * 25)
text = start_requests(url)
parse(text)
if __name__ == '__main__':
main()
接下来,我们需要抓取多个字段,存储到json文件中,这时,我们就要把多页的电影信息放在一个list里,再保存为文件。(注意代码中的注释)
import requests # 导入网页请求库
from bs4 import BeautifulSoup # 导入网页解析库
import json
def start_requests(url):
r = requests.get(url)
return r.content
def parse(text):
soup = BeautifulSoup(text, 'html.parser')
movie_list = soup.find_all('div', class_ = 'item')
for movie in movie_list:
mydict = {}
mydict['title'] = movie.find('span', class_ = 'title').text
mydict['score'] = movie.find('span', class_ = 'rating_num').text
quote = movie.find('span', class_ = 'inq')
mydict['quote'] = quote.text if quote else None # 抓取10页就总会遇到这种特殊情况要处理
star = movie.find('div', class_ = 'star')
mydict['comment_num'] = star.find_all('span')[-1].text[:-3]
result_list.append(mydict) # 向全局变量result_list中加入元素
def write_json(result):
s = json.dumps(result, indent = 4, ensure_ascii=False)
with open('movies.json', 'w', encoding = 'utf-8') as f:
f.write(s)
def main():
for i in range(10):
url = 'https://movie.douban.com/top250?start={}&filter='.format(i * 25)
text = start_requests(url)
parse(text)
write_json(result_list) # 所有电影都存进去之后一起输出到文件
if __name__ == '__main__':
# 初始化,注意不要在main()函数里定义,因为那里不是全局变量,其他函数无法调用
result_list = []
main()
多页抓取之翻页
翻页原理是爬取一页的信息的同时,把下一页的url也爬取到,再对抓取到的这个url进行爬取。这种方法适用于有“下一页”标签的网站,而且一般是网页url无法构造的时候才用这种方法。