qlib数据装载与模型搭建

Data Layer属于QlibInfrastructure(基层)部分,Data Layer提供了大量API接口,方便user管理(manage)和检索(retrieve)自己的数据。数据装载好后依据实际需求和任务目标收益率搭建模型进行回测或实盘进行下单操作,同时需要进行风控和指标分析。

Data Layer主要包含:

  • Data Preparation(数据准备)

  • Data API(数据接口)

  • Data Loader(数据加载)

  • Dataset(数据集)

  • Cache(缓存)

  • Data and Cache File Structure(数据与缓存文件格式)

一般的数据准备流程是:

        首先用官方或自己下载的数据,通过dump_bin.py文件将数据转换为Qlib支持的格式(.bin)。通常转换后的数据只包含一些基础列(比如OHLCV,即open、high、low、close和volume)。

        利用Qlib内置的Experssion Engine来自定义其他特征(eg. "Ref($close, 60)/$close",前60个交易日的回报),支持的表达式可以在路径.\qlib\qlib\data\ops.py找到。通常情况这个步骤在Data Handler类的Data Loader中实现。

        如果要进行更复杂的数据处理,Qlib同样支持自定义Processor(过程流)来完成更复杂的操作,路径.\qlib\qlib\data\dataset\processor.py。与上面提到的Experssion Engine不同的是Processor提供复杂的、难以使用表达式来处理的数据处理方法(eg. Dropna)。

        最后,Dataset负责把Data Handler处理好的model-specific的数据传递给模型。

        官方在介绍数据框架时仅简单介绍了默认数据集,一般我们需要用质量更高,频率更高频的数据去进行数据分析和预测建模,官方传送门:数据层:数据框架和用法 — QLib 0.9.5.99 文档,所以我们需要自定义一些数据集。

        自定义的数据集原始数据要求满足以下条件:

  • 数据文件格式为.csv

  • 数据文件中至少包含一列时间索引(且列名为date)和一列特征(如close)

        官方demo中使用的是股票bar数据,这里用自定义的minute自定义数据集,目前我在研究期货交易,这里就用期货分时数据:

import sys, os
from tqdm import tqdm
import pandas as pd, numpy as np
from  data_api import au as au  # 自己封装的数据API接口

symbols=['SN2410']


class CFG:
    start_date = '2024-07-31 00:00:00'
    end_date = '2024-08-03 00:00:00'
    update_start_date = '2024-07-31 00:00:00'
    update_end_date = '2024-08-03 00:00:00'
    upd_data_path = './SN2410_1min_upd'
    raw_data_path = './SN2410_1min'          # 原始csv数据存放位置
    target_path = './SN2410_1min_bin'        # .bin数据存放位置


if not os.path.exists(CFG.raw_data_path):
    os.mkdir(CFG.raw_data_path)

for i in symbols:
    try:
        data = au.futures_zh_minute_sina(symbol=i, period="1")
    except:
        break
    data.to_csv(f'{CFG.raw_data_path}/{i}.csv', index=False)

下载好的数据:

        接着使用官方格式转换脚本dump_bin.py.csv转换为.bin文件,有几个比较重要的参数:

--csv_path: 原始csv数据存放地址
--qlib_dir: .bin数据存放地址,即格式化后想存放的位置
--freq: 数据频率,可以选择5min或者day
--date_field_name: 表示csv中时间索引的列的列名
--include_fields: 除了时间索引列(date)之外,想要转换的列
--exclude_fields: 除了时间索引列(date)之外,不想转换的列

将上面csv转换:

python dump_bin.py dump_all --csv_path C:\Users\59980\qlib\qlib\workflow\SN2410_1min\SN2410.csv  --qlib_dir C:\Users\59980\.qlib\qlib_data\my_data --freq 5min --date_field_name datetime --include_fields close

结果是可以看到转换后的文件的。

更新自定义数据集

后续如果需要对已有的数据集更新同样只需要使用dump_bin.py脚本进行更新,首先同样要获取所有新合约的历史分时数据,更新数据需要验证几个问题:

  • 当更新数据时间范围与原有数据交叉时,是否能自行判断并衔接数据(日期重叠看是否能有效剔除重复数据)

  • 能否新增数据(除了SN2410,增加SN2409合约数据)

  • 能否只更新以前的一部分数据

我们使用下列代码获取更新数据:

python dump_bin.py dump_update --csv_path ./crypto_1min_upd --qlib_dir ./crypto_1min_bin --freq 5min --date_field_name date --include_fields close

        比较简单就跳过这部分。但自定义数据集会遇到数据不完整问题,由于我们获取的数据接口有可能产生数据缺失,下载的时候可能并不全面,而dump_bin.py脚本在处理时并不会发现这一点问题,因为它只会根据它dump的第一个.csv文件生成Calendar,而之后所有文件都公用第一个文件的Calendar。这一点很关键。

        因为这会导致一个问题:对于缺失某一时刻但与Calendar中缺失的时间戳不同的时间序列数据,在读取时可能会发生如下情况:

        也就是说,我们的时间轴对应的数据从缺失的那一时刻开始就全部错乱了。故在使用dump_bin.py脚本生成数据集时,一定要检查数据是否完整或所有.csv文件的数据条目是否相同。为了填补缺失的数据,考虑使用如下代码进行数据填补:

def fill_csv(csv:pd.DataFrame):
    loss_list = []
    date = list(csv.date.map(au.datetime_timestamp))
    pre = date[0] - 60000
    for idx, d in enumerate(date):
        if d - pre != 60000:
            loss_list.append(idx)
        pre = d
    data_list = list(csv.values)
    for fix, idx in enumerate(loss_list):
        add_item = data_list[idx+fix].copy()
        add_item[0] = cu.timestamp_2_datetime(au.datetime_timestamp(add_item[0]) - 60000)
        data_list.insert(idx+fix, add_item) # 使用后一时刻填补
    return pd.DataFrame(data_list, columns=csv.columns)

for csv in os.listdir('./SN2410_upd/'):
    fill_csv(pd.read_csv('./SN2410_upd/'+csv)).to_csv('./SN2410_upd/'+csv, index=None)

for csv in os.listdir('./SN2410/'):
    fill_csv(pd.read_csv('./SN2410/'+csv)).to_csv('./SN2410/'+csv, index=None)

填补对齐后基本就没有问题了。

### Qlib 深度学习模型使用教程和案例 #### 1. 数据准备预处理 为了有效利用Qlib进行深度学习模型的开发,首先需要准备好适当的数据格式。Qlib支持多种数据源输入方式,但对于高效能运算特别推荐使用其专有的`bin`文件格式[^4]。 ```python import qlib from qlib.constant import REG_CN provider_uri = "~/.qlib/qlib_data/cn_data" qlib.init(provider_uri=provider_uri, region=REG_CN) # 下载并转换CSV至BIN格式 from qlib.tests.data import GetData aa = GetData() aa.csv_data_cn(target_dir=provider_uri) ``` #### 2. 构建深度学习模型 Qlib不仅限于传统量化分析工具的功能,在深度学习领域同样表现出色。通过集成先进的神经网络架构,能够更精准捕捉市场动态变化特征。对于希望尝试构建自定义深度学习策略的研究者来说,可以从官方文档获取详细的API指南以及丰富的实例代码[^1]。 例如,创建一个简单的LSTM模型来进行股票价格预测: ```python from torch.nn import LSTM, Linear from torch.optim import Adam from qlib.contrib.model.pytorch_base import PyTorchBaseModel class SimpleLSTM(PyTorchBaseModel): def __init__(self, input_size=10, hidden_layer_size=100, output_size=1): super().__init__() self.lstm = LSTM(input_size=input_size, hidden_size=hidden_layer_size) self.linear = Linear(hidden_layer_size, output_size) def forward(self, x): lstm_out, _ = self.lstm(x.view(len(x), 1, -1)) predictions = self.linear(lstm_out.view(len(x), -1)) return predictions[-1] model = SimpleLSTM() optimizer = Adam(model.parameters(), lr=0.01) ``` #### 3. 训练评估 一旦完成了模型的设计工作之后,则可以通过调用相应的方法完成训练流程,并借助内置函数轻松实现性能评测。值得注意的是,Qlib还引入了元控制器的概念,其中包含了用于增强基础预测效果的各种机制,比如MetaGuideModel类就是一个很好的例子[^3]。 ```python from qlib.workflow.record_temp import SignalRecord from qlib.backtest import Backtest as BkTest from datetime import timedelta train_start_date = "2018-01-01" train_end_date = "2020-01-01" bk_tester = BkTest( model=model, start_time=train_start_date, end_time=train_end_date, freq="day", account=1e6, benchmark="SH000905", # 中证500指数作为基准比较对象 signal_record=SignalRecord(), adjust_factor=None, max_loss=-timedelta(days=7), min_profit=timedelta(days=7), ) results = bk_tester.run_backtest() print(results.summary()) ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值