本次實踐是抓取了雅虎財經(jīng)的成分股數(shù)據(jù)蝌麸,該數(shù)據(jù)是美股各大公司歷年來的股票價格拔第,具體包括開盤價,收盤價聊替,最高最低價格楼肪。利用這些數(shù)據(jù)制作了一個圖形界面,方便打印出各個時間段的圖表惹悄。最終具體表現(xiàn)形式如下:
一春叫、制作圖形界面
首先創(chuàng)建一個StockFrame類,這個類關(guān)于圖形界面泣港,里面包含多個函數(shù)暂殖,所有在圖形界面上的操作均在內(nèi)部定義,內(nèi)部基本分為 畫圖形界面当纱、載入數(shù)據(jù)呛每、選擇操作、點擊操作等.
本文中圖形界面主要包含了 狀態(tài)欄坡氯、textField晨横、列表框、按鈕等元素箫柳,UI界面是用wxpython制作的手形,也有其他圖形界面的庫,如果有這方面需求的可以深入了解下悯恍,具體代碼上傳到了github库糠。
二、獲取雅虎財經(jīng)數(shù)據(jù)
由于雅虎財經(jīng)采用動態(tài)加載涮毫,無法直接讀取是獲取不了數(shù)據(jù)的瞬欧,需要使用自動化工具驅(qū)動瀏覽器來獲取數(shù)據(jù)。數(shù)據(jù)獲取的代碼如下:
采用自動化工具驅(qū)動谷歌瀏覽器
driver = webdriver.Chrome()
driver.get('https://finance.yahoo.com/quote/%5EDJA')
找到并自動點擊Components項
element = driver.find_element_by_link_text('Components')
webdriver.ActionChains(driver).click(element).perform()
time.sleep(5)
轉(zhuǎn)碼
dStr = driver.page_source.encode('utf-8')
正則表達(dá)式獲取成分股中所需要的參數(shù)
m = re.findall(r'<td class="Py.*?><.*?>(.*?)</a></td>.*?>(.*?)</td>.*?>(.*?)</td>.*?</tr>', dStr)
if m:
print m
print len(m)
top.setData(m)
else:
wx.MessageBox('Download failed.', 'Message', wx.OK | wx.ICON_INFORMATION)
driver.close()
思路就是利用Selenium模塊中的webdriver自動化工具來進(jìn)入網(wǎng)頁罢防,
然后利用正則表達(dá)式獲取所需要的參數(shù)艘虎,這里我們需要的是公司縮寫、全稱以及當(dāng)前股價咒吐,如下圖所示:
如果直接用網(wǎng)頁獲取源代碼野建,是得不到以上幾個數(shù)據(jù)的,轉(zhuǎn)碼后打印dStr渤滞,得到我們需要解析的數(shù)據(jù)是:
< td class ="Py(10px) Ta(start)" > < a href="/quote/ED?p=ED" class ="C($actionBlue) Cur(p) Td(u)" title="ED" > ED < / a > < / td > < td class ="Py(10px) Ta(start) Pstart(35px)" > Consolidated Edison, Inc.< / td > < td class ="Py(10px) W(16%)" > 78.53 < / td > < td class ="Py(10px)
W(16%)" > -0.05 < / td > < td class ="Py(10px) W(16%)" > < span class ="Trsdu(0.3s) C($dataRed)" > -0.06 % < / span > < / td > < td class ="Py(10px) W(16%)" > 1, 578, 790 < / td > < / tr > < tr class ="BdT Bdc($lightGray) Ta(end) Fz(s) W(12%)" >
三贬墩、將數(shù)據(jù)載入圖形界面中
將數(shù)據(jù)放入設(shè)定好的位置
def setData(self, data):
self.list.ClearAll()
self.list.InsertColumn(0, "Symbol")
self.list.InsertColumn(1, "Name")
self.list.InsertColumn(2, "Last Trade")
pos = 0
for row in data:
pos = self.list.InsertStringItem(pos + 1, row[0])
self.list.SetStringItem(pos, 1, row[1].replace("&", "&"))
self.list.SetColumnWidth(1, -1)
self.list.SetStringItem(pos, 2, row[2])
if (pos % 2 == 0):
self.list.SetItemBackgroundColour(pos, (134, 225, 249))
self.FitInside()
pass
四、選擇某家公司妄呕,便能生成如下界面:
五陶舞、根據(jù)選擇參數(shù)制圖
制圖主要包括兩個函數(shù),一個是時間段選擇的函數(shù) :
def _wxdate2pydate(date):
import datetime
if date.IsValid():
ymd = map(int, date.FormatISODate().split('-'))
return datetime.date(*ymd)
else:
return None
另外就是圖表制作的函數(shù):
#code:公司代碼绪励;start, end:起止時間肿孵;list:所需要顯示的指標(biāo)
def PlotData(code, start, end, list):
start_date = _wxdate2pydate(start)
end_date = _wxdate2pydate(end)
#根據(jù)公司代碼唠粥,起止時間得到所有數(shù)據(jù)
quotes = quotes_historical_yahoo_ochl(code, start_date, end_date)
fields = ['date', 'open', 'close', 'high', 'low', 'volume']
list1 = []
#格式化時間,將時間參數(shù)放入list1列表
for i in range(0, len(quotes)):
x = date.fromordinal(int(quotes[i][0]))
y = datetime.strftime(x, '%Y-%m-%d')
list1.append(y)
print list1
#根據(jù)數(shù)據(jù)停做,時間列表晤愧,所有指標(biāo)生成dataFrame
quotesdf = pd.DataFrame(quotes, index=list1, columns=fields)
#剔除date數(shù)據(jù),這里是因為格式不一致
quotesdf = quotesdf.drop(['date'], axis=1)
quotesdftemp = pd.DataFrame()
#將所選擇的指標(biāo)蛉腌,如close,open的dateFrame賦予一個臨時dateFrame中
for i in range(0, len(list)):
quotesdftemp[list[i]] = quotesdf[list[i]]
print quotesdftemp
print "ready to plot"
#畫圖
quotesdftemp.plot(marker='o')
plt.show()
dateFrame的表現(xiàn)形式為 :
目的就是為了生成這個表格官份,并根據(jù)這個表格作圖 :
代碼地址:https://github.com/Kerwin1992/yahooFinance