利用网络爬虫技术爬取爱奇艺热播电影榜


一、选题的背景
通过网络爬虫爬取爱奇艺网址上的热播电影榜,了解近几年因疫情影响,人们对于娱乐方式的喜爱变化。后疫情时代短视频平台成为了健康传播的热门途径。以短视频为主的视频平台用户迅猛增长,爱奇艺是国内用户数一数二的视频平台,通过对该平台上热播电影的爬取,可以从侧面反映出疫情时代人们对于娱乐主要方式的态度。
二、主题式网络爬虫设计方案
1.主题式网络爬虫名称:
通过网络爬虫技术爬取爱奇艺热播电影榜单
2.主题式网络爬虫爬取的内容与数据特征分析:
通过爬取该网站热播电影的电影名称,热度数据及排行,然后将三者通过绘图技术表现出来,以分析出人们对于电影的种类娱乐化的规律。
3.主题式网络爬虫设计方案概述(包括实现思路与技术难点)
先确定爬取网站,用requests请求网站打印出html页面,之后用BeautifulSoup提取数据,将数据保存为csv文件中;之后进行pandas进行数据分析和数据可视化;难点在于怎么将数据进行加工保存下来,由于网站更新导致部分数据不一致
 
三、主题页面的结构特征分析
1.主题页面的结构与特征分析:
发现所有信息都被写在tbody标签下的tr中,每个tr表示一个电影名称,tr下的每个td表示一个具体信息。注意第一个tr中的信息表示格索引头,以此进行爬虫。
 
2.Htmls 页面解析

 

 

3.节点(标签)查找方法与遍历方法

 

 

 

 

 

 通过对网站源代码的分析,得出我们所要分析的标题的标签为class=“tittle”排名的标签为图二所示,以及得分的排名为图一蓝色矩形框所示。接下来我们用网络爬虫对所得到的数据进行分析。

四、网络爬虫程序设计(60 分)
 1 import requests
 2 from bs4 import BeautifulSoup
 3 import bs4
 4 #引入pandas用于数据可视化
 5 import pandas as pd   
 6 from pandas import DataFrame
 7 import seaborn as sns
 8 import numpy as np
 9 import matplotlib.pyplot as plt
10 from scipy.optimize import leastsq
11 from sklearn.linear_model import LinearRegression
12 
13 url='https://www.iqiyi.com/dianying_new/i_list_paihangbang.html'
14 headers={'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.89 Safari/537.36 SLBrowser/7.0.0.6241 SLBChan/30'}
15 r = requests.get(url,  headers=headers,timeout=10)
16 
17 def getHTMLText(url,timeout = 30):
18     try:
19         #用requests抓取网页信息
20         r = requests.get(url, timeout = 30)       
21         #可以让程序产生异常时停止程序
22         r.raise_for_status()                      
23         #设置编码标准
24         r.encoding = r.apparent_encoding          
25         return r.text
26     except:
27         return '产生异常'
28 
29 
30 html=r.text
31 soup=BeautifulSoup(html,'html.parser')
32 print(soup.prettify())

 

 

 1 import requests
 2 from bs4 import BeautifulSoup
 3 import bs4
 4 #引入pandas用于数据可视化
 5 import pandas as pd   
 6 from pandas import DataFrame
 7 import seaborn as sns
 8 import numpy as np
 9 import matplotlib.pyplot as plt
10 from scipy.optimize import leastsq
11 from sklearn.linear_model import LinearRegression
1 point=[]
2 for div in soup.find_all("div","site-title_score"):
3         point.append(div.span.strong.string)
4 puint

 

 

1 ulist=[]
2 
3 for p in soup.find_all("p","site-piclist_info_title"):
4         ulist.append(p.a.string)
5 ulist

 

 

1 print('{:^5}\t{:^40}\t{:^10}'.format('排名', '标题', '热度'))
2 num = 171
3 lst = []
4 for i in range(num):
5     print('{:^5}\t{:^40}\t{:^20}'.format(i+1, ulist[i], point[i]))
6     lst.append([i+1,ulist[i],point[i]])
7 df = pd.DataFrame(lst,columns=['排名','标题','评分'])

 

 

1 df

 

 

1 rank = r'rank.xlsx'
2 df.to_excel(rank)
1 df=pd.DataFrame(pd.read_excel('rank.xlsx'))
2 df

 

 

1 print(rank.duplicated())

 

 

1 #检查是否有空值
2 print(rank['评分'].isnull().value_counts())

 

 

1 print(rank.describe())

 

 

1 import seaborn as sns
2 sns.regplot(df.排名,df.评分)

 

 

 1 import matplotlib.pyplot as plt
 2 plt.rcParams['font.sans-serif']=['SimHei'] #显示中文
 3 plt.rcParams['axes.unicode_minus']=False #显示负数
 4 Type = ['9分以上', '8分~9分', '7分~8分', '6分~7分']
 5 Data = [1, 8, 8, 1]
 6 plt.pie(Data ,labels=Type, autopct='%1.1f%%')
 7 plt.axis('equal')
 8 plt.title('各评分所占的比例')
 9 plt.show()
10 plt.bar(['6分~7分','7分~8分','8分~9分','9分以上'], 
11         [1, 8, 8, 1], 
12         label="各评分所占比例")
13 plt.legend()
14 plt.show()

 

 

 1 #选择排名和热度两个特征变量,绘制分布图,用最小二乘法分析两个变量间的二次拟合方程和拟合曲线
 2 
 3 #正常显示中文
 4 plt.rcParams['font.sans-serif']=['SimHei'] 
 5 #显示负数
 6 plt.rcParams['axes.unicode_minus']=False 
 7 colnames=[" ","排名","标题","评分"]
 8 
 9 X = df.排名
10 Y = df.评分
11 Z = df.排名
12 def A():
13     plt.scatter(X,Y,color="r",linewidth=2)
14     plt.title("link",color="blue")
15     plt.grid()
16     plt.show()
17 def B():
18     plt.scatter(X,Y,color="b",linewidth=2)
19     plt.title("link",color="blue")
20     plt.grid()
21     plt.show()
22 def func(p,x):
23     a,b,c=p
24     return a*x*x+b*x+c
25 def error(p,x,y):
26     return func(p,x)-y
27 def main():
28     plt.figure(figsize=(10,6))
29     p0=[0,0,0]
30     Para = leastsq(error,p0,args=(X,Y))
31     a,b,c=Para[0]
32     print("a=",a,"b=",b,"c=",c)
33     plt.scatter(X,Y,color="blue",linewidth=2)
34     x=np.linspace(0,20,20)
35     y=a*x*x+b*x+c
36     plt.plot(x,y,color="black",linewidth=2,)
37     plt.title("评分值分布")
38     plt.grid()
39     plt.show()
40 print(A())
41 print(B())
42 print(main())

 

 

 

 

 

 

 

 

 

 完整代码如下:

  1 #导入相关库
  2 import requests
  3 from bs4 import BeautifulSoup
  4 import bs4
  5 #引入pandas用于数据可视化
  6 
  7 import pandas as pd   
  8 from pandas import DataFrame
  9 import seaborn as sns
 10 import numpy as np
 11 import matplotlib.pyplot as plt
 12 from scipy.optimize import leastsq
 13 from sklearn.linear_model import LinearRegression
 14 
 15 #输入网址
 16 
 17 url='https://www.iqiyi.com/dianying_new/i_list_paihangbang.html'
 18 #防伪编码
 19 
 20 headers={'User-Agent':'Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/84.0.4147.89 Safari/537.36 SLBrowser/7.0.0.6241 SLBChan/30'}
 21 
 22 r = requests.get(url,  headers=headers,timeout=10)
 23 
 24 def getHTMLText(url,timeout = 30):
 25     try:
 26 
 27         #用requests抓取网页信息
 28 
 29         r = requests.get(url, timeout = 30) 
 30       
 31         #可以让程序产生异常时停止程序
 32 
 33         r.raise_for_status()
 34                       
 35         #设置编码标准
 36 
 37         r.encoding = r.apparent_encoding          
 38         return r.text
 39     except:
 40         return '产生异常'
 41 
 42 html=r.text
 43 soup=BeautifulSoup(html,'html.parser')
 44 
 45 #输出更加友好
 46 
 47 print(soup.prettify())
 48 
 49 point=[]
 50 for div in soup.find_all("div","site-title_score"):
 51         point.append(div.span.strong.string)
 52 puint
 53 
 54 
 55 html=r.text
 56 soup=BeautifulSoup(html,'html.parser')
 57 print(soup.prettify())
 58 
 59 ulist=[]
 60 
 61 for p in soup.find_all("p","site-piclist_info_title"):
 62         ulist.append(p.a.string)
 63 ulist
 64 
 65 
 66 #绘制图表
 67 
 68 print('{:^5}\t{:^40}\t{:^10}'.format('排名', '标题', '热度'))
 69 num = 171
 70 lst = []
 71 for i in range(num):
 72 
 73     print('{:^5}\t{:^40}\t{:^20}'.format(i+1, ulist[i], point[i]))
 74     lst.append([i+1,ulist[i],point[i]])
 75 
 76 df = pd.DataFrame(lst,columns=['排名','标题','评分'])
 77 
 78 
 79 #保存至excel
 80 
 81 rank = r'rank.xlsx'
 82 df.to_excel(rank)
 83 
 84 df=pd.DataFrame(pd.read_excel('rank.xlsx'))
 85 df
 86 
 87 print(rank.duplicated())
 88 
 89 #检查是否有空值
 90 
 91 print(rank['评分'].isnull().value_counts())
 92 print(rank.describe())
 93 
 94 #绘制饼图
 95 #正常显示中文
 96 
 97 plt.rcParams['font.sans-serif']=['SimHei'] 
 98 #显示负数
 99 plt.rcParams['axes.unicode_minus']=False 
100 import seaborn as sns
101 import pandas as pd   
102 from pandas import DataFrame
103 import seaborn as sns
104 sns.regplot(df.排名,df.评分)
105 
106 import matplotlib.pyplot as plt
107 
108 #显示中文
109 
110 plt.rcParams['font.sans-serif']=['SimHei']
111 
112 #显示负数
113 
114 plt.rcParams['axes.unicode_minus']=False 
115 
116 Type = ['9分以上', '8分~9分', '7分~8分', '6分~7分']
117 Data = [1, 8, 8, 1]
118 plt.pie(Data ,labels=Type, autopct='%1.1f%%')
119 plt.axis('equal')
120 plt.title('各评分所占的比例')
121 plt.show()
122 plt.bar(['6分~7分','7分~8分','8分~9分','9分以上'], 
123         [1, 8, 8, 1], 
124         label="各评分所占比例")
125 plt.legend()
126 plt.show()
127 
128 #绘制折线图
129 
130 #正常显示中文
131 
132 plt.rcParams['font.sans-serif']=['SimHei'] 
133 
134 #显示负数
135 
136 plt.rcParams['axes.unicode_minus']=False 
137 a = df.排名
138 b = df.评分
139 plt.plot(a,b, color='r',label='时长')
140 plt.xlabel("排名")
141 plt.ylabel("评分")
142 plt.title('排名与评分')
143 plt.legend(loc=1)
144 plt.grid()
145 plt.show()
146 
147 import pandas as pd
148 import numpy as np
149 import matplotlib.pyplot as plt
150 import pandas as pd
151 plt.rcParams['font.sans-serif'] = ['SimHei']
152 plt.rcParams['axes.unicode_minus'] = False
153 
154 plt.scatter(df["排名"],df["评分"])
155 plt.title("排名评分的关系")
156 plt.grid()
157 plt.show()
158 
159 #选择排名和热度两个特征变量,绘制分布图,用最小二乘法分析两个变量间的二次拟合方程和拟合曲线
160 
161 #正常显示中文
162 
163 plt.rcParams['font.sans-serif']=['SimHei'] 
164 
165 #显示负数
166 
167 plt.rcParams['axes.unicode_minus']=False 
168 colnames=[" ","排名","标题","评分"]
169 
170 X = df.排名
171 Y = df.评分
172 Z = df.排名
173 def A():
174     plt.scatter(X,Y,color="r",linewidth=2)
175     plt.title("link",color="blue")
176     plt.grid()
177     plt.show()
178 
179 def B():
180     plt.scatter(X,Y,color="b",linewidth=2)
181     plt.title("link",color="blue")
182     plt.grid()
183     plt.show()
184 
185 #绘制一元二次
186 
187 def func(p,x):
188     a,b,c=p
189     return a*x*x+b*x+c
190 
191 def error(p,x,y):
192     return func(p,x)-y
193 
194 def main():
195     plt.figure(figsize=(10,6))
196     p0=[0,0,0]
197     Para = leastsq(error,p0,args=(X,Y))
198     a,b,c=Para[0]
199     print("a=",a,"b=",b,"c=",c)
200     plt.scatter(X,Y,color="blue",linewidth=2)
201     x=np.linspace(0,20,20)
202     y=a*x*x+b*x+c
203     plt.plot(x,y,color="black",linewidth=2,)
204     plt.title("评分值分布")
205 
206     #绘制网格
207 
208     plt.grid()
209     plt.show()
210 
211 print(A())
212 print(B())
213 print(main())
五、总结(10 分)
1.经过对主题数据的分析与可视化,可以得到哪些结论?是否达到预期的目标?
可以直观的看到热播电影的评分情况,人们对于好的 质量高的电影评分给出普遍客观,对于分数较低的电影,一部分原因是因为播放量不占优势,但电影所拍的剧情质量也确实差强人意,通过自己所做的工作,达到了自己的预期目标。
2.在完成此设计过程中,得到哪些收获?以及要改进的建议?
在数据爬取中不断地学习了一些函数的使用以及绘图的方法,使用图表、图形对数据的理解和分析中更加简单清晰,简单回复了以前的一些知识点,设计过程中遇到的困难通过百度和视频学习基本可解决。


免责声明!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系本站邮箱yoyou2525@163.com删除。



 
粤ICP备18138465号  © 2018-2025 CODEPRJ.COM