張喜紅
(亳州職業(yè)技術(shù)學(xué)院智能工程系,安徽亳州 236800)
伴隨著大數(shù)據(jù)時(shí)代的快速到來,人們越來越傾向于借助數(shù)據(jù)揭示事物內(nèi)在規(guī)律,進(jìn)而指導(dǎo)決策[1-2].因此,如何利用大數(shù)據(jù)做好中藥材價(jià)格走勢的及時(shí)預(yù)測,為中藥材市場運(yùn)營決策提供支撐,促進(jìn)市場有序運(yùn)營,極具研究意義.目前對于價(jià)格推測、分析的方法主要有兩類,其一是基于影響價(jià)格變化因素采用特定的技術(shù)方法進(jìn)行推理;其二是基于歷史數(shù)據(jù)的推理法.因素法由于影響因子多維善變、因子權(quán)重難于確定等原因,難于建模;時(shí)間序列分析是一種基于歷史價(jià)格數(shù)據(jù)的變化規(guī)律預(yù)測未來價(jià)格走勢的方法,是當(dāng)前價(jià)格預(yù)測的主流方法之一.時(shí)間序列分析法實(shí)施的難點(diǎn)在于如何獲取足夠多且相對完整的歷史價(jià)格數(shù)據(jù)[3].
互聯(lián)網(wǎng)技術(shù)自誕生以來,在各行業(yè)得到了廣泛的應(yīng)用,互聯(lián)網(wǎng)在中醫(yī)、中藥領(lǐng)域的應(yīng)用也達(dá)到了前所未有的廣度,積累了相當(dāng)豐厚的網(wǎng)絡(luò)數(shù)據(jù)資源.如中藥材天地網(wǎng)就積累了相當(dāng)數(shù)量的中藥材價(jià)格信息,為時(shí)間序列分析法提供了強(qiáng)有力的數(shù)據(jù)支撐.然而,如何從網(wǎng)絡(luò)上快速、高效的收集這些數(shù)據(jù),并將其整理為便于分析的結(jié)構(gòu)化數(shù)據(jù),是極為關(guān)鍵的一步.網(wǎng)絡(luò)爬蟲是收集、提取網(wǎng)絡(luò)數(shù)據(jù)的主流技術(shù)手段[4-5].
基于上述背景,為了滿足基于時(shí)間序列分析法開展中藥材價(jià)格預(yù)測研究的數(shù)據(jù)需求,鑒于Python語言在爬蟲設(shè)計(jì)方面具有程序簡潔、資源豐富、便于實(shí)現(xiàn)等優(yōu)點(diǎn),本文以中藥材天地網(wǎng)為目標(biāo)網(wǎng)站,基于Python語言設(shè)計(jì)了一款用于中藥材價(jià)格信息收集的網(wǎng)絡(luò)爬蟲,采用Requests模塊實(shí)現(xiàn)網(wǎng)頁的Http請求,采用Beautifulsoup實(shí)現(xiàn)了目標(biāo)信息的過濾、解析、提取,最終將目標(biāo)數(shù)據(jù)保存為便于分析的結(jié)構(gòu)化文本文件數(shù)據(jù),同時(shí)就爬蟲的定時(shí)啟動(dòng)、抓取進(jìn)行了介紹.
從互聯(lián)網(wǎng)獲取相關(guān)信息,最直接的方法是通過瀏覽器輸入U(xiǎn)RL向服務(wù)器發(fā)起Http請求,請求成功后服務(wù)器返回一個(gè)包含目標(biāo)網(wǎng)頁內(nèi)容的Response,經(jīng)瀏覽器解析后呈現(xiàn)給用戶.如果用戶想統(tǒng)計(jì)、收集某個(gè)網(wǎng)站成千上萬條的信息記錄條,若以瀏覽器人工訪問網(wǎng)頁的方式進(jìn)行,不僅效率低下且易出錯(cuò)[6].基于此,爬蟲的概念便誕生了,爬蟲通俗來講是一段實(shí)現(xiàn)自動(dòng)訪問網(wǎng)頁,并自動(dòng)定向提取網(wǎng)頁中目標(biāo)信息的程序.網(wǎng)絡(luò)爬蟲典型的工作流程大致包含如下幾個(gè)步驟:①模擬或自動(dòng)調(diào)用網(wǎng)頁瀏覽器發(fā)送請求并獲取網(wǎng)頁源碼;如在Python中可使用Request庫的相關(guān)方法向服務(wù)器發(fā)起模擬請求,待響應(yīng)成功后,將返回一個(gè)包含多種媒體格式的Response.②過濾、提取網(wǎng)頁源碼中包含的目標(biāo)信息;即從網(wǎng)頁源碼中通過XPath、正則表達(dá)式或Beautifulsoup等模塊的相應(yīng)方法,定位、提取目標(biāo)信息.③將提取的目標(biāo)信息存儲(chǔ);保存形式多樣化,可以保存成文本,也可以保存至數(shù)據(jù)庫,或者保存成特定格式的文件.
中藥材天地網(wǎng)自建站以來,其市場價(jià)格欄目每天實(shí)時(shí)公布亳州、安國、玉林及荷花池4個(gè)藥市數(shù)百種中藥材的規(guī)格與價(jià)格信息,且其公布的中藥材價(jià)格數(shù)據(jù)真實(shí)可靠,為中藥材價(jià)格走勢的預(yù)測提供了真實(shí)、可靠的源數(shù)據(jù).在網(wǎng)頁瀏覽器中輸入藥材價(jià)格欄目的首頁URL地址:http://www.zyctd.com/jiage/1-0-0.html,可得到圖1所示的頁面,在頁面的價(jià)格信息區(qū)按品名、規(guī)格、市場、當(dāng)前價(jià)格等題頭逐行呈現(xiàn)中藥材的價(jià)格信息,且分多頁顯示,在頁面的底部給出了分頁鏈接信息.根據(jù)上述分析可知,在爬蟲的設(shè)計(jì)過程中,需要解決如下問題:①獲取各個(gè)分頁的URL鏈接地址;②提取各分頁信息記錄條的目標(biāo)信息.
如前面所述爬蟲要想從網(wǎng)頁中提取信息,首先需將網(wǎng)頁源碼下載到本地,網(wǎng)頁源碼的下載通過Http請求實(shí)現(xiàn),Requests模塊是Python語言開發(fā)的Http庫,其功能強(qiáng)大,實(shí)現(xiàn)簡單[7-9].對于采用GET方式打開的網(wǎng)頁,可采用語句requests.get(“URL地址參數(shù)”).text方法模擬請求,得到網(wǎng)頁源后將其存儲(chǔ)為文本格式.同時(shí)BeautifulSoup是基于Python語言開發(fā)的一個(gè)用于解析html對象的第三方庫.對于結(jié)構(gòu)化網(wǎng)頁信息的提取,與正則表達(dá)式相比更具優(yōu)勢.其提供的find()與find_all()方法使信息定位、過濾、提取的實(shí)現(xiàn)更加簡單[10-13].同時(shí)考慮到中藥材天地網(wǎng)結(jié)構(gòu)規(guī)范,且要提取的目標(biāo)信息都是文本字段,最終決定采用Requests模塊進(jìn)行模擬Http請求下載目標(biāo)網(wǎng)頁源碼,采用BeautifulSoup模塊過濾、解析、提取目標(biāo)信息.
借助瀏覽器的審查元素工具,分析各頁中的源碼架構(gòu),如圖2所示,每頁中的每條信息記錄條處于同一
def get_page_values(self, now_url): # 其中now_url參數(shù)為網(wǎng)頁的URL地址
now_html = requests.get(now_url).text # 下載網(wǎng)頁源碼,并以文本方式儲(chǔ)存
now_Soup = BeautifulSoup(now_html, 'lxml')# 以網(wǎng)頁文檔解析源碼
all_value_li = now_Soup.find('div', class_='priceTable').find_all('li')#定位所有
for tag in all_value_li:#遍歷所有
name = tag.find('span', class_='w1').get_text().encode('utf-8')
#提取“品名”
guige = tag.find('span', class_='w2').get_text().encode('utf-8')
#提取“規(guī)格”
shichang = tag.find('span', class_='w9').get_text().encode('utf-8')
#提取“市場”
price = tag.find('span', class_='w3').get_text().encode('utf-8')
#提取“價(jià)格”
self.write_txt(name, guige, shichang, price)#將目標(biāo)信息存入文件
通過瀏覽器查看各個(gè)分頁的URL地址可知:各分頁的URL地址是由首頁URL地址加一個(gè)“-”與分頁號構(gòu)成,如:首頁的URL地址為:http://www.zyctd.com/jiage/1-0-0.html,第201頁的URL地址為:http://www.zyctd.com/jiage/1-0-0-201.html.如圖1(b)所示,首頁底部的分頁鏈接按鈕給出了分頁面的總數(shù),如當(dāng)前一共有201個(gè)頁面.通過審查元素工具,可知分頁總數(shù)位于
def get_all_page_values(self):#獲取所有分頁面中記錄條信息
# 下載首頁源碼
html = requests.get('http://www.zyctd.com/jiage/1-0-0.html').text
# 以網(wǎng)頁解析文檔
Soup = BeautifulSoup(html, 'lxml')
# 定位到最后一頁的頁碼值對應(yīng)的標(biāo)簽區(qū)
all_li = Soup.find('div', class_='pageBreak').find_all('a')
# 提取最后一頁的頁碼值,#獲取最大頁碼值,即頁面總數(shù)
Page_max = int(all_li[4].get_text())
all_page_value = []
for i in range(1, Page_max + 1):
if i == 1:
# 為1時(shí)是首頁,URL地址較特殊
temp_url = 'http://www.zyctd.com/jiage/1-0-0.html' else:
# 字串拼接構(gòu)造分頁URL地址
temp_url = 'http://www.zyctd.com/jiage/1-0-0-' + str(i) + '.html'
# 調(diào)用頁面目標(biāo)信息提取函數(shù),獲取當(dāng)前分頁中所有記錄條的品名、規(guī)格、市場、價(jià)格等目標(biāo)信息
now_page = self.get_values(temp_url)
all_page_value.extend(now_page)
result_df = pd.DataFrame(all_page_value)
returnresult_df
鑒于文本文件的通用性較好,且便于后期的跨平臺(tái)分析,文中將提取到的目標(biāo)數(shù)據(jù)采用文本文件進(jìn)行存儲(chǔ).為了便于后期按分隔符導(dǎo)入表格文件,在寫入文本文件時(shí),一條記錄條的品名、規(guī)格、市場及價(jià)格之間采用逗號分隔,各條記錄條間采用回車進(jìn)行分隔.同時(shí)考慮到中藥材天地網(wǎng)的價(jià)格信息是按天發(fā)布,為了避免信息的重復(fù),在每天爬取數(shù)據(jù)時(shí),以當(dāng)前系統(tǒng)日期為文件名創(chuàng)建文件,當(dāng)前系統(tǒng)日期的獲取通過Python的datetime模塊中的datetime.now().date().isoformat()實(shí)現(xiàn).詳細(xì)實(shí)現(xiàn)代碼如下:
def write_txt(self,name,guige,shichang,price):
#以當(dāng)前系統(tǒng)日期為文件名創(chuàng)建本次存儲(chǔ)文件
file_name=str(self.path_)+'/'+datetime.now().date().isoformat()+'.txt'
with open(file_name, 'a') as f:
f.write(name)#品名
f.write(',')#逗號分隔
f.write(guige)#規(guī)格
f.write(',')#逗號分隔
f.write(shichang)#市場
f.write(',')#逗號分隔
f.write(price)#價(jià)格
f.write(' ')#不同記錄條間“回車”分隔
中藥材天地網(wǎng)按天更新各藥材價(jià)格信息,因此需每天運(yùn)行爬蟲,對更新的價(jià)格進(jìn)行采集,如果爬蟲每天的啟動(dòng)工作由用戶人工完成,事必增加了用戶的工作事項(xiàng),多有不便.倘若有一天用戶忘記了此項(xiàng)任務(wù),將會(huì)導(dǎo)致當(dāng)天信息缺失.考慮到當(dāng)前用戶電腦以windows系統(tǒng)為主流,同時(shí)windows系統(tǒng)自帶任務(wù)計(jì)劃程序安排功能,因此采用windows自帶的任務(wù)計(jì)劃來實(shí)現(xiàn)爬蟲的定時(shí)啟動(dòng).以Win7系統(tǒng)為例,具體的部署方法是:①創(chuàng)建bat批處理文件,在文件中書寫如:“python 爬蟲文件名.py”格式的命令;②依次進(jìn)入系統(tǒng)“控制面板”/“管理工具”/“任務(wù)計(jì)劃程序”/“創(chuàng)建任務(wù)”欄目,創(chuàng)建一個(gè)每天指定時(shí)間啟動(dòng)①中批處理文件的新任務(wù);③在“任務(wù)計(jì)劃程序”任務(wù)安排列表中選中②中創(chuàng)建的新任務(wù),并點(diǎn)選“運(yùn)行”按鈕啟動(dòng).
將所設(shè)計(jì)的爬蟲按照上述方法,部署到CPU型號為Intel(R) Core(TM) i3-4160 3.6GHz,內(nèi)存為4GB,操作系統(tǒng)為Win7-64位的平臺(tái)上,對目標(biāo)網(wǎng)頁進(jìn)行信息爬取,得到如圖3所示的目標(biāo)信息,此次測試運(yùn)行共計(jì)收集201頁20051條記錄,用時(shí)約1026毫秒.經(jīng)人工與網(wǎng)頁實(shí)際數(shù)據(jù)對比,信息記錄條數(shù)一致,無重復(fù),無缺項(xiàng).進(jìn)一步證實(shí),所設(shè)計(jì)的爬蟲運(yùn)行效率較高,準(zhǔn)確無誤,可用于中藥材價(jià)格數(shù)據(jù)的收集.
圖3 目標(biāo)信息片斷
本文以中藥材價(jià)格預(yù)測的研究為背景,為了收集大量的中藥材價(jià)格數(shù)據(jù),瞄準(zhǔn)互聯(lián)網(wǎng)上的數(shù)據(jù)資源,以中藥材天地網(wǎng)為目標(biāo)網(wǎng)站,在深入分析其網(wǎng)頁布局結(jié)構(gòu)及信息發(fā)布規(guī)則的基礎(chǔ)上,基于Python語言的Requests、Beautifulsoup等模塊,設(shè)計(jì)了一款中藥材價(jià)格信息爬蟲,同時(shí)就爬蟲在windows系統(tǒng)如何實(shí)現(xiàn)定時(shí)自動(dòng)運(yùn)行的部署進(jìn)行了介紹.經(jīng)實(shí)驗(yàn)測試,所設(shè)計(jì)的爬蟲運(yùn)行可靠、效率較高,所得數(shù)據(jù)與網(wǎng)頁公布一致無誤,為從互聯(lián)網(wǎng)收集中藥材相關(guān)信息提供了參考方法.雖然所設(shè)計(jì)的爬蟲能夠準(zhǔn)確無誤的獲取中藥材價(jià)格信息,但是為了拓寬其使用人群范圍,需在后續(xù)的研究中解決其跨平臺(tái)部署不便的問題,讓其能脫離Python環(huán)境運(yùn)行.