python

Руководство: как использовать Python для алгоритмической торговли на бирже. Часть 2

  • пятница, 30 июня 2017 г. в 03:13:24
https://habrahabr.ru/company/itinvest/blog/331940/
  • Python
  • Блог компании ITinvest




Мы продолжаем публикацию адаптации руководства DataCamp по использованию Python для разработки финансовых приложений. Первая часть материала рассказывала об устройстве финансовых рынков, акциях и торговых стратегиях, данных временных рядов, а также о том, что понадобится для начала разработки.

Теперь, когда вы уже больше знаете про требования к данным, разобрались с понятием временных рядов и познакомились с pandas, пришло время глубже погрузиться в тему финансового анализа, который необходим для создания торговой стратегии.

Jupyter notebook этого руководства можно скачать здесь.

Общий финансовый анализ: подсчет прибыли


При простом подсчете дневного процентного изменения не принимаются во внимание, например, дивиденды и другие факторы — просто отмечается процентное изменение цены приобретенных акций по сравнению с предыдущим торговым днем. Подсчитать такие изменения легко с помощью функции pct_change(), входящей в пакет Pandas.

# Import `numpy` as `np`
import numpy as np

# Assign `Adj Close` to `daily_close`
daily_close = aapl[['Adj Close']]

# Daily returns
daily_pct_change = daily_close.pct_change()

# Replace NA values with 0
daily_pct_change.fillna(0, inplace=True)

# Inspect daily returns
print(daily_pct_change)

# Daily log returns
daily_log_returns = np.log(daily_close.pct_change()+1)

# Print daily log returns
print(daily_log_returns)

Доход будет вычисляться по логарифмической шкале — это позволяет нагляднее отслеживать изменения во времени.

Знание прибыли за день — это хорошо, но что если нам нужно рассчитать этот показатель за месяц или даже квартал? В таких случаях можно использовать функцию resample(), которую мы рассматривали в прошлой части руководства:

# Resample `aapl` to business months, take last observation as value 
monthly = aapl.resample('BM').apply(lambda x: x[-1])

# Calculate the monthly percentage change
monthly.pct_change()

# Resample `aapl` to quarters, take the mean as value per quarter
quarter = aapl.resample("4M").mean()

# Calculate the quarterly percentage change
quarter.pct_change()


Использование pct_change() удобно, но в таком случае сложно понять, как именно вычисляется дневной доход. Поэтому в качестве альтернативы можно использовать фукнцию Pandas под названием shift(). Затем нужно разделить значения daily_close на daily_close.shift(1) -1. При использовании этой функции в начале результирующего датафрейма будут находиться NA-значения.

Для справки, вычисление дневного изменения стоимости акций вычисляется по формуле:

,

Где p — это цена, t — это время (в нашем случае, день), а r — это доход. Можно создать график распределения daily_pct_change:

# Import matplotlib
import matplotlib.pyplot as plt

# Plot the distribution of `daily_pct_c`
daily_pct_change.hist(bins=50)

# Show the plot
plt.show()

# Pull up summary statistics
print(daily_pct_change.describe())

image

Результат выглядит симметричным и нормально распределенным: дневное изменение цены находится в районе bin 0.00. Следует понимать, что для корректной интерпретации результатов гистограммы нужно использовать функцию describe(), примененную к daily_pct_c. В таком случае будет видно, что среднее значение также близко к bin 0.00, а стандартное отклонение составляет 0,02. Также нужно изучить процентили, чтобы понять, какой объём данных выходит за границы -0,010672, 0,001677 и 0,014306.

Показатель суммарной суточной нормы прибыли полезен для определения стоимости инвестиций на регулярных отрезках. Подсчитать суммарную суточную норму прибыли можно используя значения дневных изменений цены активов в процентах, добавляя к ним 1 и вычисляя конечные значения:

# Calculate the cumulative daily returns
cum_daily_return = (1 + daily_pct_change).cumprod()

# Print `cum_daily_return`
print(cum_daily_return)

Здесь снова можно использовать Matplotlib для быстрой отрисовки cum_daily_return. Нужно лишь добавить функцию plot() и, опционально, определить размер графика с помощью figsize.

# Import matplotlib
import matplotlib.pyplot as plt 

# Plot the cumulative daily returns
cum_daily_return.plot(figsize=(12,8))

# Show the plot
plt.show()

image

Все довольно просто. Теперь, если нужно анализировать не дневной доход, а месячный, следует вернуться к функции resample() — с ее помощью можно привести cum_daily_return к месячным значениям:

# Resample the cumulative daily return to cumulative monthly return 
cum_monthly_return = cum_daily_return.resample("M").mean()

# Print the `cum_monthly_return`
print(cum_monthly_return)

Знание того, как можно подсчитать доход — полезный навык, но на практике эти значения редко несут в себе ценную информацию, если не сравнивать их с показателями других акций. Вот почему в различных примерах часто сравнивают между собой две или более акций.

Чтобы тоже это сделать, сначала нужно загрузить больше данных — в нашем случае, c Yahoo! Finance. Для этого можно создать функцию, которая будет использовать ticker акции, а также начальную и конечные даты торгового периода. В примере ниже функция data() берет ticker для получения данных, начиная со startdate до enddate, и возвращает результат функции get(). Данные размечаются с помощью корректных тикеров (ticker), в результате получается датафрейм, содержащий эту информацию.

В коде ниже данные акций Apple, Microsoft, IBM и Google загружены в один общий датафрейм:

def get(tickers, startdate, enddate):
  def data(ticker):
    return (pdr.get_data_yahoo(ticker, start=startdate, end=enddate))
  datas = map (data, tickers)
  return(pd.concat(datas, keys=tickers, names=['Ticker', 'Date']))

tickers = ['AAPL', 'MSFT', 'IBM', 'GOOG']
all_data = get(tickers, datetime.datetime(2006, 10, 1), datetime.datetime(2012, 1, 1))

Примечание: этот код также использовался в руководстве по использованию Pandas для сферы финансов, позднее он был доработан. Также, поскольку в настоящий момент существуют проблемы с загрузкой данных с Yahoo! Finance, для корректной работы, возможно, придется загрузить пакет fix_yahoo_finance — инструкции по установке можно найти здесь или в Jupyter notebook этого руководства.

Вот результат выполнения этого кода:

image

Этот большой датафрейм можно использовать для отрисовки интересных графиков:

# Import matplotlib
import matplotlib.pyplot as plt 

# Isolate the `Adj Close` values and transform the DataFrame
daily_close_px = all_data[['Adj Close']].reset_index().pivot('Date', 'Ticker', 'Adj Close')

# Calculate the daily percentage change for `daily_close_px`
daily_pct_change = daily_close_px.pct_change()

# Plot the distributions
daily_pct_change.hist(bins=50, sharex=True, figsize=(12,8))

# Show the resulting plot
plt.show()

image

Еще один полезный для финансового анализа график — это матрица рассеяния. Получить ее можно с помощью библиотеки pandas. Нужно будет добавить к коду функцию scatter_matrix(). В качестве аргументов передаются daily_pct_change, а в качестве диагонали устанавливается значение по выбору — так, чтобы получить график оценки плотности ядра (Kernel Density Estimate, KDE). Также, с помощью аргумента alpha можно установить прозрачность, а с помощью figsize изменять размер графика.

# Import matplotlib
import matplotlib.pyplot as plt

# Plot a scatter matrix with the `daily_pct_change` data 
pd.scatter_matrix(daily_pct_change, diagonal='kde', alpha=0.1,figsize=(12,12))

# Show the plot
plt.show()

image

В случае локальной работы для построения матрицы рассеяния может понадобиться модуль plotting (т.е. pd.plotting.scatter_matrix()).

В следующей части руководства речь пойдет об использовании для финансового анализа скользящих окон, подсчете волатильности и применении обычной регрессии наименьших квадратов.

Продолжение следует…..

Другие материалы по теме финансов и фондового рынка от ITinvest: