点对点数据库
介绍
在进行任何历史市场分析时,点对点数据是一个非常重要的考虑因素。
例如,假设我们正在回测一个交易策略,并且将过去五年的历史数据作为输入。我们的模型假定每天只进行一次交易,在收盘时进行。我们假设我们正在回测的是2020年1月1日的交易信号。在那个时候,我们应该只有2020年1月1日、2019年12月31日、2019年12月30日等日期的数据。
在金融数据(尤其是财务报告)中,同一份数据可能会随着时间的推移进行多次修改。如果我们只使用最新版本进行历史回测,将会发生数据泄露。 点对点数据库旨在解决这个问题,确保用户能够在任何历史时间戳获得正确的数据版本。它将保持在线交易和历史回测的性能一致。
数据准备
Qlib提供了一个爬虫来帮助用户下载金融数据,然后提供了一个转换器来以Qlib格式导入数据。 请参考 scripts/data_collector/pit/README.md 下载和转换数据。 此外,您还可以在那里找到一些附加的使用示例。
基于文件的PIT数据设计
Qlib为PIT数据提供了基于文件的存储方式。对于每个特征,它包含4列,即日期、期间、值和 _next。 每一行对应一个声明。
文件名为 XXX_a.data 的每个特征的含义如下:
date:声明的发布日期。
- period:声明的期间。 (例如,在大多数市场上,它将是每季度频率)
如果是年度期间,则为对应的年份的整数。
如果是季度期间,则为一个整数,类似于 <year><index of quarter>。最后两位数字表示季度的索引,其他位表示年份。
value:描述的值。
_next:下一个字段出现位置的字节索引。
除了特征数据外,还包括索引 XXX_a.index 以提高查询性能。
声明按照文件开始处的 date 按升序排序。
# the data format from XXXX.data
array([(20070428, 200701, 0.090219 , 4294967295),
(20070817, 200702, 0.13933 , 4294967295),
(20071023, 200703, 0.24586301, 4294967295),
(20080301, 200704, 0.3479 , 80),
(20080313, 200704, 0.395989 , 4294967295),
(20080422, 200801, 0.100724 , 4294967295),
(20080828, 200802, 0.24996801, 4294967295),
(20081027, 200803, 0.33412001, 4294967295),
(20090325, 200804, 0.39011699, 4294967295),
(20090421, 200901, 0.102675 , 4294967295),
(20090807, 200902, 0.230712 , 4294967295),
(20091024, 200903, 0.30072999, 4294967295),
(20100402, 200904, 0.33546099, 4294967295),
(20100426, 201001, 0.083825 , 4294967295),
(20100812, 201002, 0.200545 , 4294967295),
(20101029, 201003, 0.260986 , 4294967295),
(20110321, 201004, 0.30739301, 4294967295),
(20110423, 201101, 0.097411 , 4294967295),
(20110831, 201102, 0.24825101, 4294967295),
(20111018, 201103, 0.318919 , 4294967295),
(20120323, 201104, 0.4039 , 420),
(20120411, 201104, 0.403925 , 4294967295),
(20120426, 201201, 0.112148 , 4294967295),
(20120810, 201202, 0.26484701, 4294967295),
(20121026, 201203, 0.370487 , 4294967295),
(20130329, 201204, 0.45004699, 4294967295),
(20130418, 201301, 0.099958 , 4294967295),
(20130831, 201302, 0.21044201, 4294967295),
(20131016, 201303, 0.30454299, 4294967295),
(20140325, 201304, 0.394328 , 4294967295),
(20140425, 201401, 0.083217 , 4294967295),
(20140829, 201402, 0.16450299, 4294967295),
(20141030, 201403, 0.23408499, 4294967295),
(20150421, 201404, 0.319612 , 4294967295),
(20150421, 201501, 0.078494 , 4294967295),
(20150828, 201502, 0.137504 , 4294967295),
(20151023, 201503, 0.201709 , 4294967295),
(20160324, 201504, 0.26420501, 4294967295),
(20160421, 201601, 0.073664 , 4294967295),
(20160827, 201602, 0.136576 , 4294967295),
(20161029, 201603, 0.188062 , 4294967295),
(20170415, 201604, 0.244385 , 4294967295),
(20170425, 201701, 0.080614 , 4294967295),
(20170728, 201702, 0.15151 , 4294967295),
(20171026, 201703, 0.25416601, 4294967295),
(20180328, 201704, 0.32954201, 4294967295),
(20180428, 201801, 0.088887 , 4294967295),
(20180802, 201802, 0.170563 , 4294967295),
(20181029, 201803, 0.25522 , 4294967295),
(20190329, 201804, 0.34464401, 4294967295),
(20190425, 201901, 0.094737 , 4294967295),
(20190713, 201902, 0. , 1040),
(20190718, 201902, 0.175322 , 4294967295),
(20191016, 201903, 0.25581899, 4294967295)],
dtype=[('date', '<u4'), ('period', '<u4'), ('value', '<f8'), ('_next', '<u4')])
# - each row contains 20 byte
# 来自 XXXX.index 的数据格式,包含两部分
# 1) 数据的起始索引。所以信息的第一部分会像这样
2007
# 2) 剩余索引数据将类似下面的信息
# - 数据指示了每个期间第一个数据更新的字节索引。
# - 例如,因为字节索引 80 和 100 处的信息对应于 200704。第一次出现的字节索引(即 100)被记录在数据中。
array([ 0, 20, 40, 60, 100,
120, 140, 160, 180, 200,
220, 240, 260, 280, 300,
320, 340, 360, 380, 400,
440, 460, 480, 500, 520,
540, 560, 580, 600, 620,
640, 660, 680, 700, 720,
740, 760, 780, 800, 820,
840, 860, 880, 900, 920,
940, 960, 980, 1000, 1020,
1060, 4294967295], dtype=uint32)
已知限制:
目前,PIT数据库设计用于季度或年度因子,可以处理大多数市场的财务报告基本数据。
Qlib利用文件名识别数据类型。文件名为 XXX_q.data 的文件对应季度数据。文件名为 XXX_a.data 的文件对应年度数据。
PIT的计算方式不够优化。有很大的潜力提升PIT数据的计算性能。