从豆瓣获取数据
建立SQLite数据库,将爬取的数据存入数据库中
用FLASK开发Web应用程序,即进行数据可视化
前两点主要是有关爬虫的知识,第三点则是有关数据可视化的前端内容。这篇博客就主要写写有关爬虫的内容吧
下载python,我用的是Python3.9。
python的集成开发环境,本文使用Pycharm2020专业版进行开发。
在弹出窗口中找到Project:xxx,其下有一个Python interpreter,点击,右边窗口有一个“+”号,点击。
# iml
#encoding='utf-8'
from bs4 import BeautifulSoup #网页解析,获取数据
import re #正则表达式,进行文字匹配
import urllib.request,urllib.error #指定URL,获取网页数据
import xlwt #进行excel操作
import sqlite3 #进行SQLite数据库操作
def main():
baseurl="https://movie.douban.com/top250?start="
datalist = getdata(baseurl)#获取数据存入列表
#savepath="豆瓣电影Top250.xls"#xls文件路径
dbpath="movie.db"#SQlite数据库路径
#saveData(datalist,savepath)#保存数据到xls文件
savedata2db(datalist,dbpath)#保存数据到数据库
#创建正则表达式对象,表示规则(字符串的模式)
#影片详情链接的规则
findLink = re.compile(r'')
#影片图片
findImgSrc = re.compile(r',re.S) #re.S 让换行符包含在字符中
#影片片名
findTitle = re.compile(r'(.*)')
#影片评分
findRating = re.compile(r' ')
#找到评价人数
findJudge = re.compile(r'(\d*)人评价')
#找到概况
findInq = re.compile(r'(.*)')
#找到影片的相关内容
findBd = re.compile(r'(.*?)
',re.S)
def getdata(baseurl): #获取数据的代码块
datalist=[]
for i in range(0,10):
url=baseurl+str(i*25)
html=askurl(url)
#逐一解析数据
soup = BeautifulSoup(html,"html.parser")
for item in soup.find_all('div', class_="item"): # 查找符合要求的字符串,形成列表
#print(item) # 测试:查看电影item全部信息
data = [] # 保存一部电影的所有信息
item = str(item)
# 影片详情的链接
link = re.findall(findLink, item)[0] # re库用来通过正则表达式查找指定的字符串
data.append(link) # 添加链接
imgSrc = re.findall(findImgSrc, item)[0]
data.append(imgSrc) # 添加图片
titles = re.findall(findTitle, item) # 片名可能只有一个中文名,没有外国名
if (len(titles) == 2):
ctitle = titles[0] # 添加中文名
data.append(ctitle)
otitle = titles[1].replace("/", "") # 去掉无关的符号
data.append(otitle) # 添加外国名
else:
data.append(titles[0])
data.append(' ') # 外国名字留空
rating = re.findall(findRating, item)[0]
data.append(rating) # 添加评分
judgeNum = re.findall(findJudge, item)[0]
data.append(judgeNum) # 添加评价人数
inq = re.findall(findInq, item)
if len(inq) != 0:
inq = inq[0].replace("。", "") # 去掉句号
data.append(inq) # 添加概述
else:
data.append(" ") # 留空
bd = re.findall(findBd, item)[0]
bd = re.sub('
(\s+)?', " ", bd) # 去掉
bd = re.sub('/', " ", bd) # 替换/
data.append(bd.strip()) # 去掉前后的空格
datalist.append(data) # 把处理好的一部电影信息放入datalist
return datalist
#得到指定一个URL的网页内容
def askurl(url):
head={
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36"
}#伪装成浏览器
request=urllib.request.Request(url,headers=head)#对网页头信息进行抓取
html=""
try:
response=urllib.request.urlopen(request)#读取结果
html=response.read().decode("utf-8")
except urllib.error.URLError as e:
if hasattr(e,"code"):
print(e.code)
if hasattr(e,"reason"):
print(e.reason)
return html
#保存数据到excel表
# def savedata(datalist,savepath):
# print('save...')
# book=xlwt.Workbook(encoding='utf-8',style_compression=0)
# sheet=book.add_sheet('豆瓣Top250',cell_overwrite_ok=True)
# col=('电影详情链接','图片链接','中文名','外文名','评分','评价数','概括','相关信息')
# for i in range(0,8):
# sheet.write(0,i,col[i]) #列名
# for i in range(0,250):
# print("第%d条" %(i+1))
# data = datalist[i]
# for j in range(0,8):
# sheet.write(i+1,j,data[j]) #数据
# book.save(savepath)
def savedata2db(datalist,dbpath): #保存数据到数据库
init_db(dbpath) #在dbpath路径创建数据库
conn=sqlite3.connect(dbpath) #打开数据库连接
cur=conn.cursor() #获取操作游标
for data in datalist:
for index in range(len(data)):
if index==4 or index==5:
continue
data[index]='"'+data[index]+'"'
sql='''
insert into movie250(
info_link,pic_link,cname,ename,score,rated,introduction,info)
values(%s)'''%",".join(data)
cur.execute(sql)
conn.commit()
cur.close()
conn.close()
def init_db(dbpath): #创建数据库
sql='''
create table movie250
(
id integer primary key autoincrement,
info_link text,
pic_link text,
cname varcher,
ename varcher,
score numeric,
rated numeric,
introduction text,
info text
)
'''
conn=sqlite3.connect(dbpath)
cursor=conn.cursor()
cursor.execute(sql)
conn.commit()
conn.close()
if __name__=='__main__':
main()
首先我们要有一个具体的爬虫思路:
根据这个思路,我们可以建立主函数(这里有一些注释的代码是把数据存入excel表的,不多赘述,有兴趣的可以尝试以下,代码块是savedata):
def main():
baseurl="https://movie.douban.com/top250?start="
datalist = getdata(baseurl)#获取数据存入列表
#savepath="豆瓣电影Top250.xls"#xls文件路径
dbpath="movie.db"#SQlite数据库路径
#saveData(datalist,savepath)#保存数据到xls文件
savedata2db(datalist,dbpath)#保存数据到数据库
首先确定我们的初始地址"https://movie.douban.com/top250?start="
豆瓣top250里有250部电影的信息,以25部为一页,start=0~249,数字代表从某一部电影开始往下数25部作为一页的信息,大家可以点击上面的链接自己在网址那里加数字试试。了解了这个,我们之后就可以利用这个特点做一个循环来遍历每一页的信息啦。
接下来我们编写获取数据模块和存储数据模块的函数。
1. 爬取数据
#得到指定一个URL的网页内容
def askurl(url):
head={
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36"
}#伪装成浏览器
request=urllib.request.Request(url,headers=head)#对网页头信息进行抓取
html=""
try:
response=urllib.request.urlopen(request)#读取结果
html=response.read().decode("utf-8")
except urllib.error.URLError as e:
if hasattr(e,"code"):
print(e.code)
if hasattr(e,"reason"):
print(e.reason)
return html
2. 解析数据
#创建正则表达式对象,表示规则(字符串的模式)
findLink = re.compile(r'') #影片详情链接的规则
findImgSrc = re.compile(r',re.S) #影片图片
findTitle = re.compile(r'(.*)')#影片片名
findRating = re.compile(r' ')#影片评分
findJudge = re.compile(r'(\d*)人评价')#找到评价人数
findInq = re.compile(r'(.*)')#找到概况
findBd = re.compile(r'(.*?)
',re.S)#找到影片的相关内容
def getdata(baseurl): #获取数据的代码块
datalist=[]
for i in range(0,10):
url=baseurl+str(i*25)
html=askurl(url)
#逐一解析数据
soup = BeautifulSoup(html,"html.parser")
for item in soup.find_all('div', class_="item"): # 查找符合要求的字符串,形成列表
#print(item) # 测试:查看电影item全部信息
data = [] # 保存一部电影的所有信息
item = str(item)
# 影片详情的链接
link = re.findall(findLink, item)[0] # re库用来通过正则表达式查找指定的字符串
data.append(link) # 添加链接
imgSrc = re.findall(findImgSrc, item)[0]
data.append(imgSrc) # 添加图片
titles = re.findall(findTitle, item) # 片名可能只有一个中文名,没有外国名
if (len(titles) == 2):
ctitle = titles[0] # 添加中文名
data.append(ctitle)
otitle = titles[1].replace("/", "") # 去掉无关的符号
data.append(otitle) # 添加外国名
else:
data.append(titles[0])
data.append(' ') # 外国名字留空
rating = re.findall(findRating, item)[0]
data.append(rating) # 添加评分
judgeNum = re.findall(findJudge, item)[0]
data.append(judgeNum) # 添加评价人数
inq = re.findall(findInq, item)
if len(inq) != 0:
inq = inq[0].replace("。", "") # 去掉句号
data.append(inq) # 添加概述
else:
data.append(" ") # 留空
bd = re.findall(findBd, item)[0]
bd = re.sub('
(\s+)?', " ", bd) # 去掉
bd = re.sub('/', " ", bd) # 替换/
data.append(bd.strip()) # 去掉前后的空格
datalist.append(data) # 把处理好的一部电影信息放入datalist
return datalist
3.保存数据
def init_db(dbpath): #创建数据库
sql='''
create table movie250
(
id integer primary key autoincrement,
info_link text,
pic_link text,
cname varcher,
ename varcher,
score numeric,
rated numeric,
introduction text,
info text
)
'''
conn=sqlite3.connect(dbpath)
cursor=conn.cursor()
cursor.execute(sql)
conn.commit()
conn.close()
此处主要是使用数据库语句来建立表格,创建好之后,可以测试一下,会发现自动生成了这样一个库。其中,id:排名,info_link:详情链接,pic_link:图片链接,cname:中文名,enamel:外文名,score:评分,rated:评价人数,introduction:概述,info:相关信息。
创建好数据库,然后打开数据库连接并获取游标。用sql语句执行,把datalist中的数据存到建立的数据库中。这里因为创建数据库时只声明了score和rated是数字类型,其他的都可以用文本类型,所以可以把其他的数据加上双引号。
def savedata2db(datalist,dbpath): #保存数据到数据库
init_db(dbpath) #在dbpath路径创建数据库
conn=sqlite3.connect(dbpath) #打开数据库连接
cur=conn.cursor() #获取操作游标
for data in datalist:
for index in range(len(data)):
if index==4 or index==5:
continue
data[index]='"'+data[index]+'"'
sql='''
insert into movie250(
info_link,pic_link,cname,ename,score,rated,introduction,info)
values(%s)'''%",".join(data)
cur.execute(sql)
conn.commit()
cur.close()
conn.close()