Загрузка нескольких запасов сразу из yahoo finance python
У меня есть вопрос о функции финансирования Yahoo с помощью устройства чтения данных Pandas. Я уже несколько месяцев использую список с биржевыми биржами и выполняю его в следующих строках:
import pandas_datareader as pdr
import datetime
stocks = ["stock1","stock2",....]
start = datetime.datetime(2012,5,31)
end = datetime.datetime(2018,3,1)
f = pdr.DataReader(stocks, 'yahoo',start,end)
Со вчерашнего дня я получаю сообщение об ошибке "IndexError: list index out of range", которая появляется, только если я пытаюсь получить несколько акций.
Изменилось ли что-нибудь за последние дни, что я должен рассмотреть, или у вас есть лучшее решение для моей проблемы?
5 ответов
Если вы прочитаете документацию Pandas DataReader, они сразу же начнут амортизировать API-интерфейсы нескольких источников данных, одним из которых является Yahoo! Финансы.
v0.6.0 (24 января 2018 года)
Немедленное устаревание Yahoo!, Google Options и Quotes и EDGAR. Конечные точки этих API радикально изменились, и существующие читатели требуют полного переписывания. В случае большинства Yahoo! данные конечные точки были удалены. PDR хотел бы восстановить эти функции, и запросы на получение приветствуются.
Это может быть причиной того, почему вы получаете IndexError
(или любые другие, как правило, несуществующие ошибки).
Тем не менее, есть еще один пакет Python, целью которого является исправление поддержки Yahoo! Финансы для Pandas DataReader, вы можете найти этот пакет здесь:
https://pypi.python.org/pypi/fix-yahoo-finance
Согласно их документации:
Yahoo! финансы списали свой API исторических данных, в результате чего многие программы, которые полагались на него, перестали работать.
fix-yahoo-finance предлагает временное решение проблемы путем удаления данных из Yahoo! финансировать, используя и возвращая Pandas DataFrame/Panel в том же формате, что и pandas_datareader
get_data_yahoo()
,По сути "угон"
pandas_datareader.data.get_data_yahoo()
метод, имплантация fix-yahoo-finance проста и требует только импортаfix_yahoo_finance
в ваш код.
Все, что вам нужно добавить, это:
from pandas_datareader import data as pdr
import fix_yahoo_finance as yf
yf.pdr_override()
stocks = ["stock1","stock2", ...]
start = datetime.datetime(2012,5,31)
end = datetime.datetime(2018,3,1)
f = pdr.get_data_yahoo(stocks, start=start, end=end)
Или даже без необходимости Pandas DataReader:
import fix_yahoo_finance as yf
stocks = ["stock1","stock2", ...]
start = datetime.datetime(2012,5,31)
end = datetime.datetime(2018,3,1)
data = yf.download(stocks, start=start, end=end)
Для этого вы можете использовать новый модуль Python YahooFinancials с пандами. YahooFinancials хорошо построен и получает свои данные, хэшируя объект хранилища данных, присутствующий на каждой веб-странице Yahoo Finance, так что он быстрый и не зависит от устаревших API и веб-драйверов, как скребок. Данные возвращаются в формате JSON, и вы можете получить столько акций, сколько захотите, передав список тикеров акций / индексов, чтобы инициализировать класс YahooFinancials.
$ pip install yahoofinancials
Пример использования:
from yahoofinancials import YahooFinancials
import pandas as pd
# Select Tickers and stock history dates
ticker = 'AAPL'
ticker2 = 'MSFT'
ticker3 = 'INTC'
index = '^NDX'
freq = 'daily'
start_date = '2012-10-01'
end_date = '2017-10-01'
# Function to clean data extracts
def clean_stock_data(stock_data_list):
new_list = []
for rec in stock_data_list:
if 'type' not in rec.keys():
new_list.append(rec)
return new_list
# Construct yahoo financials objects for data extraction
aapl_financials = YahooFinancials(ticker)
mfst_financials = YahooFinancials(ticker2)
intl_financials = YahooFinancials(ticker3)
index_financials = YahooFinancials(index)
# Clean returned stock history data and remove dividend events from price history
daily_aapl_data = clean_stock_data(aapl_financials
.get_historical_stock_data(start_date, end_date, freq)[ticker]['prices'])
daily_msft_data = clean_stock_data(mfst_financials
.get_historical_stock_data(start_date, end_date, freq)[ticker2]['prices'])
daily_intl_data = clean_stock_data(intl_financials
.get_historical_stock_data(start_date, end_date, freq)[ticker3]['prices'])
daily_index_data = index_financials.get_historical_stock_data(start_date, end_date, freq)[index]['prices']
stock_hist_data_list = [{'NDX': daily_index_data}, {'AAPL': daily_aapl_data}, {'MSFT': daily_msft_data},
{'INTL': daily_intl_data}]
# Function to construct data frame based on a stock and it's market index
def build_data_frame(data_list1, data_list2, data_list3, data_list4):
data_dict = {}
i = 0
for list_item in data_list2:
if 'type' not in list_item.keys():
data_dict.update({list_item['formatted_date']: {'NDX': data_list1[i]['close'], 'AAPL': list_item['close'],
'MSFT': data_list3[i]['close'],
'INTL': data_list4[i]['close']}})
i += 1
tseries = pd.to_datetime(list(data_dict.keys()))
df = pd.DataFrame(data=list(data_dict.values()), index=tseries,
columns=['NDX', 'AAPL', 'MSFT', 'INTL']).sort_index()
return df
Пример нескольких данных о запасах одновременно (возвращает список объектов JSON для каждого тикера):
from yahoofinancials import YahooFinancials
tech_stocks = ['AAPL', 'MSFT', 'INTC']
bank_stocks = ['WFC', 'BAC', 'C']
yahoo_financials_tech = YahooFinancials(tech_stocks)
yahoo_financials_banks = YahooFinancials(bank_stocks)
tech_cash_flow_data_an = yahoo_financials_tech.get_financial_stmts('annual', 'cash')
bank_cash_flow_data_an = yahoo_financials_banks.get_financial_stmts('annual', 'cash')
banks_net_ebit = yahoo_financials_banks.get_ebit()
tech_stock_price_data = tech_cash_flow_data.get_stock_price_data()
daily_bank_stock_prices = yahoo_financials_banks.get_historical_stock_data('2008-09-15', '2017-09-15', 'daily')
Пример вывода JSON:
Код:
yahoo_financials = YahooFinancials('WFC')
print(yahoo_financials.get_historical_stock_data("2017-09-10", "2017-10-10", "monthly"))
Возвращение JSON:
{
"WFC": {
"prices": [
{
"volume": 260271600,
"formatted_date": "2017-09-30",
"high": 55.77000045776367,
"adjclose": 54.91999816894531,
"low": 52.84000015258789,
"date": 1506830400,
"close": 54.91999816894531,
"open": 55.15999984741211
}
],
"eventsData": [],
"firstTradeDate": {
"date": 76233600,
"formatted_date": "1972-06-01"
},
"isPending": false,
"timeZone": {
"gmtOffset": -14400
},
"id": "1mo15050196001507611600"
}
}
yahoo_finance больше не может использовать, так как Yahoo изменил формат, fix_yahoo_finance достаточно хорош для загрузки данных. Однако для разбора вам понадобятся другие библиотеки, вот простой рабочий пример:
import numpy as np #python library for scientific computing
import pandas as pd #python library for data manipulation and analysis
import matplotlib.pyplot as plt #python library for charting
import fix_yahoo_finance as yf #python library to scrap data from yahoo finance
from pandas_datareader import data as pdr #extract data from internet sources into pandas data frame
yf.pdr_override()
data = pdr.get_data_yahoo(‘^DJI’, start=”2006–01–01")
data2 = pdr.get_data_yahoo(“MSFT”, start=”2006–01–01")
data3 = pdr.get_data_yahoo(“AAPL”, start=”2006–01–01")
data4 = pdr.get_data_yahoo(“BB.TO”, start=”2006–01–01")
ax = (data[‘Close’] / data[‘Close’].iloc[0] * 100).plot(figsize=(15, 6))
(data2[‘Close’] / data2[‘Close’].iloc[0] * 100).plot(ax=ax, figsize=(15,6))
(data3[‘Close’] / data3[‘Close’].iloc[0] * 100).plot(ax=ax, figsize=(15,6))
(data4[‘Close’] / data5[‘Close’].iloc[0] * 100).plot(ax=ax, figsize=(15,6))
plt.legend([‘Dow Jones’, ‘Microsoft’, ‘Apple’, ‘Blackberry’], loc=’upper left’)
plt.show()
для объяснения кода вы можете посетить на https://medium.com/@gerrysabar/charting-stocks-price-from-yahoo-finance-using-fix-yahoo-finance-library-6b690cac5447
Это работает для меня.
assets = ['TSLA', 'MSFT', 'FB']
yahoo_financials = YahooFinancials(assets)
data = yahoo_financials.get_historical_price_data(start_date='2019-01-01',
end_date='2019-12-31',
time_interval='weekly')
prices_df = pd.DataFrame({
a: {x['formatted_date']: x['adjclose'] for x in data[a]['prices']} for a in assets})
prices_df
Результат:
Попробуйте этот простой код
watchlist=["stock1","stock2".......]
closing_price=pd.DataFrame()
symbols=[]
for i in watchlist:
Result=wb.DataReader(i,start='05-1-20', end='05-20-20',data_source='yahoo')
closing_price=closing_price.append(Result)
symbols.append(i)
print("Generating Closing price for",i)
closing_price["SYMBOL"]=symbols
print("closing_price"