一、選題的背景
通過網絡爬蟲爬取愛奇藝網址上的熱播電影榜,了解近幾年因疫情影響,人們對於娛樂方式的喜愛變化。后疫情時代短視頻平台成為了健康傳播的熱門途徑。以短視頻為主的視頻平台用戶迅猛增長,愛奇藝是國內用戶數一數二的視頻平台,通過對該平台上熱播電影的爬取,可以從側面反映出疫情時代人們對於娛樂主要方式的態度。
二、主題式網絡爬蟲設計方案
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.在完成此設計過程中,得到哪些收獲?以及要改進的建議?
在數據爬取中不斷地學習了一些函數的使用以及繪圖的方法,使用圖表、圖形對數據的理解和分析中更加簡單清晰,簡單回復了以前的一些知識點,設計過程中遇到的困難通過百度和視頻學習基本可解決。
