來源 | 早起Python
大家好,在之前我們講過如何用Python構建一個帶有GUI的爬蟲小程序,很多本文將迎合熱點,延續上次的NBA爬蟲GUI,探討如何爬取虎撲NBA官網數據,並且將數據寫入Excel中同時自動生成折線圖,主要有以下幾個步驟:
本文將分為以下兩個部分進行講解:
在虎撲NBA官網球員頁面中進行爬蟲,獲取球員數據。
清洗整理爬取的球員數據,對其進行可視化。
項目主要涉及的Python模塊:
requests
pandas
bs4
爬虫部分
爬虫部分整理思路如下
觀察URL1的原始碼找到球隊名稱與對應URL2觀察URL2的原始碼找到球員對應的URL3觀察URL3原始碼找到對應球員基本信息與比賽數據並進行篩選存儲
其實爬蟲就是在html上操作,而html的結構很簡單就只有一個,就是一個大框討一個小框,小框在套小框,這樣的一層層嵌套。
目標URL如下:
URL1:http://nba.hupu.com/players/
URL2(此處以湖人球隊為例):https://nba.hupu.com/players/lakers
URL3(此處以詹姆斯為例):https://nba.hupu.com/players/lebronjames-650.html
先引用模塊
from bs4 import BeautifulSoupimport requestsimport xlsxwriterimport os
查看URL1原始碼代碼,可以看到球隊名詞及其對應的URL2在span標籤中下,進而找到它的父框與祖父框,下面的思路都是如此,圖如下:
此時,可以通過requests模塊與bs4模塊進行有目的性的索引,得到球隊的名稱列表。
def Teamlists( url): TeamName =[] TeamURL=[] GET=requests. get(URL1) soup=BeautifulSoup(GET.content, 'lxml') lables=soup. select( 'html body div div div ul li span a') forlable inlables: ballname=lable.get_text TeamName.append(ballname) print(ballname) teamname=input( "請輸入想查詢的球隊名:") #此處可變為GUI介面中的按鍵值 c=TeamName.index(teamname)for item in lables: HREF=item.get('href') TeamURL.append(HREF) URL2=TeamURL[c] return URL2
就此得到了對應球隊的URL2,接著觀察URL2網頁的內容,可以看到球員名稱在標籤a中下,同時也存放著對應球員的URL3,如下圖:
此時,故依然通過requests模塊與bs4模塊進行相對應的索引,得到球員名稱列表以及對應的URL3。
#自定義函數獲取隊員列表和對應的URLdef playerlists(URL2): PlayerName=[] PlayerURL=[] GET2=requests.get(URL1) soup2=BeautifulSoup(GET2.content,'lxml') lables2=soup2.select('html body div div table tbody tr td b a')for lable2 in lables2: playername=lable2.get_text PlayerName.append(playername) print(playername) name=input("請輸入球員名:") #此處可變為GUI介面中的按鍵值 d=PlayerName.index(name)for item2 in lables2: HREF2=item2.get('href') PlayerURL.append(HREF2) URL3=PlayerURL[d]return URL3,name
現在就此得到了對應球隊的URL3,接著觀察URL3網頁的內容,可以看到球員基本信息在標籤p下,球員常規賽生涯數據與季後賽生涯數據在標籤td下,如下圖:
同樣,依然通過requests模塊與bs4模塊進行相對應的索引,得到球員基本信息與生涯數據,而對於球員的常規賽與季候賽的生涯數據將進行篩選與儲存,得到data列表。
def Competition(URL3):data=[]GET3=requests.get(URL3)soup3=BeautifulSoup(GET3.content,'lxml')lables3=soup3.select('html body div div div div div div div div p')lables4=soup3.select('div div table tbody tr td')for lable3 in lables3:introduction=lable3.get_text print(introduction) #球員基本信息for lable4 in lables4:competition=lable4.get_textdata.append(competition) for i in range(len(data)):if data[i]=='職業生涯常規賽平均數據':a=data[i+31]a=data.index(a)del(data[:a]) for x in range(len(data)):if data[x]=='職業生涯季後賽平均數據':b=data[x]b=data.index(b)del(data[b:])return data
通過上述網絡爬蟲得到了以下的數據,提供可視化數據的同時便於綁定之後的GUI介面按鍵事件:
獲取NBA中的所有球隊的標準名稱;
通過指定的一隻球隊獲取球隊中所有球員的標準名稱;
通過指定的球員獲取到對應的基本信息以及常規賽與季後賽數據;
可視化部分
思路:創建文件夾 創建表格和折線圖
自定義函數創建表格,運用os模塊進行編寫,返回已創文件夾的路徑,代碼如下:
def file_add(path): #此時的內函數path可與GUI介面的Statictext綁定creatpath=path+'Basketball'try:if not os.path.isdir(creatpath):os.makedirs(creatpath) except:print("文件夾存在")return creatpath
運用xlsxwriter模塊在creatpath路徑下自定義函數創建excel表格同時放入數據與構造折線圖,代碼如下:
def player_chart(name,data,creatpath):#此為表格名稱——球員名稱+chartEXCEL=xlsxwriter.Workbook(creatpath+''+name+'chart.xlsx')worksheet=EXCEL.add_worksheet(name) bold=EXCEL.add_format({'bold':1}) headings=data[:18]worksheet.write_row('A1',headings,bold) #寫入表頭num=(len(data))//18a=0for i in range(num):a=a+18c=a+18i=i+1worksheet.write_row('A'+str(i+1),data[a:c]) #寫入數據chart_col = EXCEL.add_chart({'type': 'line'}) #創建一個折線圖chart_col.add_series({'name': '='+name+'!$R$1', #設置折線描述名稱'categories':'='+name+'!$A$2:$A$'+str(num), #設置圖表類別標籤範圍'values': '='+name+'!$R$2:$R$'+str(num-1), #設置圖表數據範圍'line': {'color': 'red'}, }) #設置圖表線條屬性#設置圖標的標題和想x,y軸信息chart_col.set_title({'name': name+'生涯常規賽平均得分'}) chart_col.set_x_axis({'name': '年份 (年)'}) chart_col.set_y_axis({'name': '平均得分(分)'})chart_col.set_style(1) #設置圖表風格worksheet.insert_chart('A14', chart_col, {'x_offset':25, 'y_offset':3,}) #把圖標插入工作檯中並設置偏移EXCEL.close
數據表格效果展現,以詹姆斯為例如下
並且此時打開自動生成的Excel,對應的折線圖就直接展現出來,無需再次整理!
現在結合任務一的網絡爬蟲與任務二的數據可視化,可以得到實時的球員常規賽數據與季後賽數據匯總,同時還有實時球員生涯折線圖。便可以與上次的GUI介面任務設計中的」可視化「按鈕事件綁定,感興趣的讀者可以自己進一步研究!