快速入门¶
以下是ffn功能的简要概述。如需更完整的指南,请阅读源代码,或查看API文档。
import ffn
%matplotlib inline
数据检索¶
数据检索的主要方法是get
函数。get函数使用数据提供者从外部服务下载数据,并将该数据打包到pandas DataFrame中以进行进一步操作。
注意
您应该注意,在导入ffn时,它会修改pandas.core.base.PandasObject,以便为pandas对象(包括DataFrames)提供额外的功能。
data = ffn.get('agg,hyg,spy,eem,efa', start='2010-01-01', end='2014-01-01')
print(data.head())
agg hyg spy eem efa
Date
2010-01-04 74.942818 43.466671 89.225403 33.181232 38.846069
2010-01-05 75.283783 43.672871 89.461578 33.422070 38.880318
2010-01-06 75.240242 43.785816 89.524582 33.491989 39.044666
2010-01-07 75.153183 43.962566 89.902481 33.297764 38.894009
2010-01-08 75.196701 44.031300 90.201675 33.561905 39.202148
默认情况下,数据是从雅虎财经下载的,并且使用调整后的收盘价作为证券的价格。其他数据源也可用,您也可以选择其他字段。字段通过以下格式指定:{股票代码}:{字段}。因此,如果我们想要获取苹果公司的开盘价、最高价、最低价和收盘价,我们可以这样做:
print(ffn.get('aapl:Open,aapl:High,aapl:Low,aapl:Close', start='2010-01-01', end='2014-01-01').head())
aaplopen aaplhigh aapllow aaplclose
Date
2010-01-04 7.622500 7.660714 7.585000 7.643214
2010-01-05 7.664286 7.699643 7.616071 7.656429
2010-01-06 7.656429 7.686786 7.526786 7.534643
2010-01-07 7.562500 7.571429 7.466071 7.520714
2010-01-08 7.510714 7.571429 7.466429 7.570714
默认的数据提供者是 ffn.data.web()
。这基本上只是 pandas 的 pandas.io.data 提供者的一个薄包装。请参考相关文档以获取更多信息(数据源等)。当我们想从本地文件加载数据时,也可以使用 ffn.data.csv()
提供者。在这种情况下,我们可以告诉 ffn.data.get()
使用 csv 提供者。在这种情况下,我们还希望将这些新数据与之前下载的现有数据合并。因此,我们将提供 data 对象作为 existing 参数,新数据将被合并到现有的 DataFrame 中。
data = ffn.get('dbc', provider=ffn.data.csv, path='test_data.csv', existing=data)
print(data.head())
agg hyg spy eem efa dbc
Date
2010-01-04 74.942818 43.466671 89.225403 33.181232 38.846069 25.24
2010-01-05 75.283783 43.672871 89.461578 33.422070 38.880318 25.27
2010-01-06 75.240242 43.785816 89.524582 33.491989 39.044666 25.72
2010-01-07 75.153183 43.962566 89.902481 33.297764 38.894009 25.40
2010-01-08 75.196701 44.031300 90.201675 33.561905 39.202148 25.38
如上所示,dbc列已添加到DataFrame中。在内部,get函数使用了ffn.merge函数,这在您想要将TimeSeries和DataFrames合并在一起时非常有用。我们计划随着时间的推移添加更多的数据源。如果您熟悉Python并希望贡献一个数据提供者,请随时提交拉取请求——我们始终欢迎贡献!
数据操作¶
现在我们有一些数据,让我们开始处理它。在量化金融中,我们通常对给定时间序列的回报感兴趣。让我们通过简单地调用to_returns
或to_log_returns
扩展方法来计算回报。
returns = data.to_log_returns().dropna()
print(returns.head())
agg hyg spy eem efa dbc
Date
2010-01-05 0.004539 0.004733 0.002643 0.007232 0.000881 0.001188
2010-01-06 -0.000579 0.002583 0.000704 0.002090 0.004218 0.017651
2010-01-07 -0.001158 0.004029 0.004212 -0.005816 -0.003866 -0.012520
2010-01-08 0.000579 0.001562 0.003322 0.007901 0.007891 -0.000788
2010-01-11 -0.000772 -0.000893 0.001395 -0.002085 0.008176 -0.003157
让我们看看不同的分布,看看它们是什么样子的。
ax = returns.hist(figsize=(12, 5))

我们还可以使用numpy、pandas等库中的众多函数来进一步分析收益。例如,我们可以使用corr函数来获取资产之间的两两相关性。
returns.corr().as_format('.2f')
agg | hyg | spy | eem | efa | dbc | |
---|---|---|---|---|---|---|
agg | 1.00 | -0.12 | -0.33 | -0.23 | -0.29 | -0.18 |
hyg | -0.12 | 1.00 | 0.77 | 0.75 | 0.76 | 0.49 |
spy | -0.33 | 0.77 | 1.00 | 0.88 | 0.92 | 0.59 |
eem | -0.23 | 0.75 | 0.88 | 1.00 | 0.90 | 0.62 |
efa | -0.29 | 0.76 | 0.92 | 0.90 | 1.00 | 0.61 |
dbc | -0.18 | 0.49 | 0.59 | 0.62 | 0.61 | 1.00 |
这里我们使用了便捷方法 as_format 来获得更美观的输出。 我们还可以绘制热图以更好地可视化结果。
returns.plot_corr_heatmap();

我们使用了ffn.core.plot_corr_heatmap()
,这是一个便捷的方法,它简单地调用了ffn的ffn.core.plot_heatmap()
,并带有合理的参数。
让我们开始看看所有这些证券在这段时间内的表现如何。为了实现这一点,我们将绘制重新基准的时间序列,以便我们可以看到它们彼此之间的相对表现。
ax = data.rebase().plot(figsize=(12,5))

性能测量¶
为了更全面地查看每个资产在期间的表现,我们可以使用ffn.core.calc_stats()
方法,该方法将创建一个ffn.core.GroupStats
对象。GroupStats对象将一堆ffn.core.PerformanceStats
对象包装在一个字典中,并添加了一些方便的方法。
perf = data.calc_stats()
现在我们有了GroupStats对象,我们可以更详细地分析性能。例如,plot方法会生成一个类似于上图的图表。
perf.plot();

我们还可以展示包含在PerformanceStats对象中的各种统计数据。这在文档中可能看起来不太美观,但请在Notebook中尝试一下。我们也在积极努力改进展示这些统计数据的方式。
print(perf.display())
Stat agg hyg spy eem efa dbc
------------------- ---------- ---------- ---------- ---------- ---------- ----------
Start 2010-01-04 2010-01-04 2010-01-04 2010-01-04 2010-01-04 2010-01-04
End 2013-12-31 2013-12-31 2013-12-31 2013-12-31 2013-12-31 2013-12-31
Risk-free rate 0.00% 0.00% 0.00% 0.00% 0.00% 0.00%
Total Return 16.36% 39.22% 76.92% 5.46% 33.43% 1.66%
Daily Sharpe 1.11 0.97 0.93 0.18 0.44 0.11
Daily Sortino 1.84 1.51 1.48 0.29 0.69 0.17
CAGR 3.87% 8.65% 15.37% 1.34% 7.50% 0.41%
Max Drawdown -5.14% -10.06% -18.61% -30.87% -25.86% -24.34%
Calmar Ratio 0.75 0.86 0.83 0.04 0.29 0.02
MTD -0.56% 0.41% 2.59% -0.41% 2.18% 0.59%
3m 0.02% 3.42% 10.52% 3.48% 6.08% -0.39%
6m 0.57% 5.84% 16.32% 9.55% 18.12% 2.11%
YTD -1.98% 5.75% 32.31% -3.65% 21.44% -7.63%
1Y -1.98% 5.75% 32.31% -3.65% 21.44% -7.63%
3Y (ann.) 3.08% 7.83% 16.07% -2.34% 8.17% -2.34%
5Y (ann.) - - - - - -
10Y (ann.) - - - - - -
Since Incep. (ann.) 3.87% 8.65% 15.37% 1.34% 7.50% 0.41%
Daily Sharpe 1.11 0.97 0.93 0.18 0.44 0.11
Daily Sortino 1.84 1.51 1.48 0.29 0.69 0.17
Daily Mean (ann.) 3.86% 8.70% 15.73% 4.35% 9.73% 1.83%
Daily Vol (ann.) 3.48% 8.97% 16.83% 24.56% 22.31% 16.84%
Daily Skew -0.40 -0.55 -0.39 -0.12 -0.26 -0.47
Daily Kurt 2.30 7.50 4.03 3.06 3.64 2.90
Best Day 0.84% 3.05% 4.65% 7.20% 6.74% 4.34%
Worst Day -1.24% -4.26% -6.51% -8.34% -7.46% -6.70%
Monthly Sharpe 1.23 1.11 1.22 0.30 0.60 0.27
Monthly Sortino 2.49 2.19 2.36 0.53 1.06 0.43
Monthly Mean (ann.) 3.59% 9.51% 16.99% 6.43% 11.06% 4.61%
Monthly Vol (ann.) 2.93% 8.56% 13.91% 21.45% 18.41% 17.10%
Monthly Skew -0.34 0.14 -0.32 -0.10 -0.37 -0.74
Monthly Kurt 0.02 1.75 0.24 1.28 0.17 1.16
Best Month 1.77% 8.49% 10.91% 16.27% 11.61% 9.89%
Worst Month -2.00% -5.30% -7.95% -17.89% -11.19% -14.62%
Yearly Sharpe 0.65 2.79 1.10 -0.06 0.50 -0.40
Yearly Sortino 2.77 inf inf -0.11 1.32 -0.58
Yearly Mean 3.16% 7.85% 16.73% -1.13% 9.32% -2.24%
Yearly Vol 4.86% 2.82% 15.22% 19.05% 18.72% 5.57%
Yearly Skew -0.54 1.49 0.22 0.58 -1.69 0.27
Yearly Kurt - - - - - -
Best Year 7.70% 11.06% 32.31% 19.05% 21.44% 3.50%
Worst Year -1.98% 5.75% 1.89% -18.79% -12.23% -7.63%
Avg. Drawdown -0.48% -1.18% -1.78% -5.16% -4.96% -5.09%
Avg. Drawdown Days 16.95 15.70 17.55 78.22 60.04 107.85
Avg. Up Month 0.83% 1.86% 3.58% 5.87% 4.37% 4.28%
Avg. Down Month -0.49% -2.31% -3.21% -3.41% -4.15% -3.35%
Win Year % 66.67% 100.00% 100.00% 33.33% 66.67% 33.33%
Win 12m % 81.08% 97.30% 94.59% 59.46% 70.27% 45.95%
None
这里有很多内容可以查看。我们还可以通过索引或名称访问每个系列的底层PerformanceStats。
# we can also use perf[2] in this case
perf['spy'].display_monthly_returns()
Year Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec YTD
------ ----- ----- ----- ----- ----- ----- ----- ----- ----- ----- ----- ----- -----
2010 -5.24 3.12 6.09 1.55 -7.95 -5.17 6.83 -4.5 8.96 3.82 0 6.69 13.14
2011 2.33 3.47 0.01 2.9 -1.12 -1.69 -2 -5.5 -6.94 10.91 -0.41 1.04 1.89
2012 4.64 4.34 3.22 -0.67 -6.01 4.06 1.18 2.51 2.54 -1.82 0.57 0.89 15.99
2013 5.12 1.28 3.8 1.92 2.36 -1.33 5.17 -3 3.16 4.63 2.96 2.59 32.31
perf[2].plot_histogram();

大多数统计数据也可以作为pandas对象使用 - 请参阅 stats, return_table, lookback_returns 属性。
perf['spy'].stats
start 2010-01-04 00:00:00
end 2013-12-31 00:00:00
rf 0.0
total_return 0.769155
cagr 0.15375
max_drawdown -0.186055
calmar 0.826367
mtd 0.025926
three_month 0.105247
six_month 0.163183
ytd 0.323077
one_year 0.323077
three_year 0.16066
five_year NaN
ten_year NaN
incep 0.15375
daily_sharpe 0.93439
daily_sortino 1.478916
daily_mean 0.157279
daily_vol 0.168323
daily_skew -0.388777
daily_kurt 4.028481
best_day 0.046499
worst_day -0.065123
monthly_sharpe 1.221065
monthly_sortino 2.362922
monthly_mean 0.169906
monthly_vol 0.139146
monthly_skew -0.319921
monthly_kurt 0.235707
best_month 0.109147
worst_month -0.079455
yearly_sharpe 1.099284
yearly_sortino inf
yearly_mean 0.16731
yearly_vol 0.152199
yearly_skew 0.21847
yearly_kurt NaN
best_year 0.323077
worst_year 0.01895
avg_drawdown -0.017845
avg_drawdown_days 17.550725
avg_up_month 0.035827
avg_down_month -0.032066
win_year_perc 1.0
twelve_month_win_perc 0.945946
dtype: object
数值例程和金融函数¶
ffn 还提供了常用的数值例程,并计划在未来添加更多。可以使用均值-方差方法轻松确定适当的权重,使用 ffn.core.calc_mean_var_weights()
函数。
returns.calc_mean_var_weights().as_format('.2%')
agg 79.52%
hyg 6.47%
spy 14.01%
eem 0.00%
efa 0.00%
dbc 0.00%
dtype: object
其他一些有趣的函数是聚类例程,例如David Varadi的快速阈值聚类算法(FTCA)的Python实现
returns.calc_ftca(threshold=0.8)
{1: ['eem', 'spy', 'efa'], 2: ['agg'], 3: ['dbc'], 4: ['hyg']}