Metadata-Version: 2.4
Name: qteasy
Version: 2.2.7
Summary: A fast quantitative investment tool kit
Home-page: https://github.com/shepherdpp/qteasy
Author: Jackie PENG
Author-email: jackie PENG <jackie.pengzhao@gmail.com>
Maintainer: Jackie PENG
Maintainer-email: jackie PENG <jackie.pengzhao@gmail.com>
License: Copyright <2019> <JACKIE PENG>
        
        Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
        
        1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
        
        2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
        
        3. Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.
        
        THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS “AS IS” AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
Project-URL: Homepage, https://github.com/shepherdpp/qteasy
Project-URL: Documentation, https://qteasy.readthedocs.io/zh-cn/latest/
Project-URL: Issues, https://github.com/shepherdpp/qteasy/issues
Keywords: quantitative investment,quantitative trading,stock,finance,investment
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Financial and Insurance Industry
Classifier: Intended Audience :: End Users/Desktop
Classifier: Intended Audience :: Other Audience
Classifier: License :: OSI Approved :: BSD License
Classifier: Programming Language :: Python
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.9
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Operating System :: MacOS
Classifier: Operating System :: Microsoft :: Windows
Classifier: Topic :: Documentation :: Sphinx
Classifier: Topic :: Office/Business :: Financial
Classifier: Topic :: Office/Business :: Financial :: Investment
Requires-Python: <3.13,>=3.9
Description-Content-Type: text/markdown
License-File: LICENSE
Requires-Dist: pandas>=1.5.0
Requires-Dist: numpy<2.0.0,>=1.26.4
Requires-Dist: numba>=0.47.0
Requires-Dist: tushare>=1.2.89
Requires-Dist: pymysql>=1.1.1
Requires-Dist: dbutils>=3.0.0
Requires-Dist: mplfinance>=0.12.0
Requires-Dist: rich>=10.0.0
Requires-Dist: textual>=0.57.1
Provides-Extra: talib
Requires-Dist: ta-lib; extra == "talib"
Provides-Extra: feather
Requires-Dist: pyarrow>=3; extra == "feather"
Provides-Extra: plotly
Requires-Dist: plotly>=5.0; extra == "plotly"
Provides-Extra: dev
Requires-Dist: ta-lib; extra == "dev"
Requires-Dist: pymysql>=1.1.1; extra == "dev"
Requires-Dist: dbutils>=3.0.0; extra == "dev"
Requires-Dist: pyarrow>=3; extra == "dev"
Dynamic: license-file

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/qteasy_logo_horizontal.png)

# `qteasy` -- 一个本地化、灵活易用的高效量化投资工具包

![PyPI](https://img.shields.io/pypi/v/qteasy)
![PyPI - Wheel](https://img.shields.io/pypi/wheel/qteasy)
[![Build Status](https://app.travis-ci.com/shepherdpp/qteasy.svg?branch=master)](https://app.travis-ci.com/shepherdpp/qteasy)
[![Documentation Status](https://readthedocs.org/projects/qteasy/badge/?version=latest)](https://qteasy.readthedocs.io/zh-cn/latest/)
![GitHub](https://img.shields.io/github/license/shepherdpp/qteasy)
![GitHub repo size](https://img.shields.io/github/repo-size/shepherdpp/qteasy)
![GitHub code size in bytes](https://img.shields.io/github/languages/code-size/shepherdpp/qteasy)
![GitHub top language](https://img.shields.io/github/languages/top/shepherdpp/qteasy)
![PyPI - Implementation](https://img.shields.io/pypi/implementation/qteasy)
![PyPI - Python Version](https://img.shields.io/pypi/pyversions/qteasy)
![GitHub branch checks state](https://img.shields.io/github/checks-status/shepherdpp/qteasy/master)
![GitHub commit activity](https://img.shields.io/github/commit-activity/m/shepherdpp/qteasy)
![GitHub issues](https://img.shields.io/github/issues/shepherdpp/qteasy)
![GitHub last commit](https://img.shields.io/github/last-commit/shepherdpp/qteasy)
![GitHub contributors](https://img.shields.io/github/contributors/shepherdpp/qteasy)
![PyPI - Downloads](https://img.shields.io/pypi/dm/qteasy)
![PyPI - Downloads](https://img.shields.io/pypi/dw/qteasy)
![GitHub Repo stars](https://img.shields.io/github/stars/shepherdpp/qteasy?style=social)
![GitHub forks](https://img.shields.io/github/forks/shepherdpp/qteasy?style=social)
![GitHub watchers](https://img.shields.io/github/watchers/shepherdpp/qteasy?style=social)
![GitHub followers](https://img.shields.io/github/followers/shepherdpp?style=social)
![GitHub Sponsors](https://img.shields.io/github/sponsors/shepherdpp?style=social)


- [关于 qteasy](#关于qteasy)
- [为什么用 qteasy？——量化人关心的几点](#为什么用-qteasy量化人关心的几点)
- [qteasy 能做什么](#qteasy能做什么)
- [安装](#安装)
- [文档](#文档)
- [10分钟了解 qteasy 的功能](#10分钟了解-qteasy-的功能)
  - [初始配置——本地数据源](#配置本地数据源)
  - [下载股票价格并可视化](#下载金融历史数据)
  - [创建投资策略](#创建一个投资策略)
  - [投资策略的回测和评价](#回测并评价交易策略的性能表现)
  - [投资策略的优化](#交易策略的参数调优)
  - [投资策略的实盘运行](#部署并开始交易策略的实盘运行)

> Note:
> 
> `qteasy`已经升级到2.0版本，使得交易策略能更加灵活有效地使用历史数据、同时简化了交易策略的定义过程、提高了效率。
> 由于`qteasy`仍处于测试中，软件中不免存在一些漏洞和bug，如果大家使用中出现问题，欢迎[Issue-报告bug](https://github.com/shepherdpp/qteasy/issues/new?assignees=&labels=&projects=&template=bug-report---bug报告.md&title=)或者[提交新功能需求](https://github.com/shepherdpp/qteasy/issues/new?assignees=&labels=&projects=&template=feature-request---新功能需求.md&title=)给我，也可以进入[讨论区](https://github.com/shepherdpp/qteasy/discussions)参与讨论。也欢迎各位贡献代码！
>
> 我会尽快修复问题并回复大家的问题。

## 关于`qteasy`

- 作者: **Jackie PENG**
- email: *jackie_pengzhao@163.com*
- Created: 2019, July, 16
- Latest Version: `2.2.7`
- Document: [https://qteasy.readthedocs.io/zh-cn/latest/](https://qteasy.readthedocs.io/zh-cn/latest/)
- License: BSD 3-Clause License

`qteasy`是为量化交易人员开发的一套量化交易工具包，特点如下：

1. **全流程本地化**：数据、回测、优化、模拟均在本地，与云平台相比隐私与可控性更好，与多数开源框架比“数据→策略→回测→实盘”一体化程度高。
2. **回测可信与实盘一致**：严格“当时可见”数据注入、同一套策略逻辑用于回测与实盘，降低“回测漂亮、实盘走样”的风险。
3. **向量化 + 数据隔离**：以高速向量化回测为目标，但摒弃全时间轴一次性算指标，改用数据提前打包装配 + 按步注入数据窗口的方式——每步策略仅能访问该步对应的历史窗口，与实盘“当时能看到的数据”一致，从机制上避免未来函数；在保证正确性的前提下兼顾速度。
4. **精细交易与数据建模**：支持 T+1 交割、交易费用、MOQ、交割队列等；use_latest_data_cycle 显式控制「是否使用交易当时的最新数据」，该细节在长期回测中会对收益产生显著影响，qteasy 将其作为可配置项而非隐式假设。
5. **易用与灵活兼顾**：内置 70+ 策略、积木式多策略组合、参数可调与多优化算法；用户只需在 realize() 中 get_data() 取数并计算信号，窗口与时间对齐由框架负责，降低误用未来数据的可能。
6. **国内市场友好**：`Tushare`、A 股/指数/基金、计划 `QMT`，与 `Backtrader`/`Zipline` 等偏美股/国际的定位形成差异。

**设计理念**：qteasy 坚持本地化与可复现——你的数据在本地、策略逻辑统一用于回测与实盘、每个时点只用当时已可用的数据驱动决策，让回测结果更可信，从研究到实盘的过渡更顺畅。

## 为什么用 qteasy？——量化人关心的几点

- **回测结果可信，避免未来函数** 系统在回测时严格按「每个时点当时能看到的」历史数据驱动策略，策略无法触及未来数据，从机制上杜绝无意中的未来函数，回测结果更可信。
- **回测与实盘同一套逻辑** 你写的策略逻辑既用于历史回测，也用于实盘或模拟盘，不换引擎、不换数据接口，减少「回测很好、实盘走样」的常见落差。
- **多策略像搭积木，信号可配置合并** 可以把多个策略组合在一起，并选择如何把各策略的信号合并成最终交易信号（例如加权平均、取交集等），方便做多策略、多周期组合。
- **参数更灵活，不同标的可用不同参数** 同一套策略可以为不同股票或标的设置不同参数（例如不同股票用不同均线周期），并支持多种优化算法在历史数据上搜索更稳健的参数组合。
- **回测和优化效率极高** 回测核心以 NumPy + Numba 实现，标的维向量化、时间维顺序，支持多进程并行优化，回测和优化效率极高。
- **全流程本地、可复现** 数据获取与存储、回测、参数优化、实盘/模拟运行均在本地完成，配置清晰，便于复现结果和排查问题。

**高性能回测与设计特点**：回测与交易计算采用向量化 + Numba（`backtest_step`、`backtest_batch_steps`、`backtest_flash_steps` 等），时间维顺序以支持 T+1/交割等状态，标的维在单步内向量化；多组参数优化通过多进程并行。**防未来函数**由机制保证：每步仅向策略注入当时可见的数据窗口，策略在 `realize()` 中 `get_data()` 取到的仅是该步窗口，从根源上避免无意中使用未来数据。详见文档 [回测引擎与性能](https://qteasy.readthedocs.io/zh-cn/latest/back_testing/6.%20backtest_engine_and_performance.html)、[设计初衷与独特优势](https://qteasy.readthedocs.io/zh-cn/latest/design/08-design-rationale-and-advantages.html)。

| 对比项           | qteasy | Backtrader | VectorBT |
|------------------|--------|------------|----------|
| 回测引擎         | 时间顺序 + 标的向量化 + Numba | 事件驱动（逐 bar） | 全时间轴矩阵广播 |
| 防未来函数       | 内置（按步数据窗口注入） | 需自行保证 | 多简化资金/规则 |
| 国内数据/实盘    | Tushare、计划 QMT | 需自接；有 IB 等 | 无国内默认数据与实盘 |

### 2.0 版本亮点

2.0 在保持上述特性的基础上，进一步带来：更灵活的策略参数设置；多策略可按不同运行频率与运行时机组合；策略可同时使用多种时间周期与数据窗口；更多优化算法与更丰富的评估指标；支持追踪策略内部行为，便于排查与调试。更多变更说明见 [2.0 迁移指南](https://qteasy.readthedocs.io/zh-cn/latest/) 及文档中的「架构与设计」章节。

## `qteasy`能做什么？


### **获取并管理金融历史数据**: 

- 方便地从多渠道获取大量金融历史数据，进行数据清洗后以统一格式进行本地存储
- 通过`DataType`对象结构化管理金融数据中的可用信息，即便是复权价格、指数成份等复杂信息，也只需要一行代码即可获取
- 基于`HistoryPanel` 三维历史数据面板统一管理多标的 / 多数据类型，直接在其上完成统计、滚动窗口、收益 / 波动率、K 线技术指标与蜡烛形态识别等计算
- 基于`DataType` / `HistoryPanel` 的金融数据可视化、统计分析以及分析结果可视化
- 数据本地存储、按需取用，为回测与实盘提供一致的数据基础，便于复现

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_5_2.png)

### **以简单、安全的方式创建交易策略**

- 通过`BaseStrategy`类，交易策略定义方法直观、逻辑清晰
- 内置超过70种策略开箱即用，独特的策略混合和组机制，复杂策略可以通过简单策略拼装而来，过程如同搭积木
- 交易策略的数据输入和使用方法完全封装且安全，完全避免无意中导致未来函数、数据泄露等问题，保证策略运行结果的真实性和可靠性
- 同一套策略逻辑既用于回测也用于实盘，减少「回测漂亮、实盘走样」的落差

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_14_3.png)

### **交易策略的回测评价、优化和模拟自动化交易**

- 通过`Operator`交易员类管理策略运行，按照真实市场交易节奏回测策略，对交易结果进行多维度全方位评价，生成交易报告和结果图表
- 提供多种优化算法，包括模拟退火、遗传算法、贝叶斯优化等在大参数空间中优化策略性能
- 获取实时市场数据，运行策略模拟自动化交易，跟踪记录交易日志、股票持仓、账户资金变化等信息
- 回测、优化与实盘使用同一套运行机制，写一次策略即可全模式运行，配置清晰，便于复现与排查
- 未来将通过QMT接口接入券商提供的实盘交易接口，实现自动化交易

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/examples/img/trader_app_1.png)  
![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/examples/img/trader_app_2.png)  
![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/examples/img/trader_app_light_theme.png) 

## 安装

```bash
$ pip install qteasy
```

## 文档

关于`QTEASY`系统的更多详细解释和使用方法，请参阅[QTEASY文档](https://qteasy.readthedocs.io/zh-cn/latest/)：


### python 版本
- *`python` version >= 3.9, < 3.13* 

### 安装可选依赖包

`qteasy`所有必要的依赖包都可以在`pip`安装的同时安装好，但某些特殊情况下，您需要在安装时指定可选依赖包，以便在安装`qteasy`时同时安装，或者手动安装依赖包：

- **`pymysql`**, 用于连接`MySQL`数据库,将本地数据存储到`MySQL`数据库 从1.4版本开始，`pymysql`和`db-utils`已经是qtesay的默认依赖包，不需要手动安装
- **`pyarrow`**, 用于操作`feather`文件，将本地数据存储为`feather`文件，`pyarrow`可以在安装`qteasy`时自动安装，也可以手动安装：
    ```bash
    $ pip install 'qteasy[feather]'  # 安装qteasy时自动安装pyarrow
    $ pip install pyarrow  # 手动安装pyarrow
    ```
- **`pytables`**, 用于操作`HDF`文件，将本地数据存储到`HDF`文件，`pytables`不能自动安装，需要使用`conda`手动安装`pytables`：
    ```bash
    $ conda install pytables  # 安装pytables
    ```
- **`ta-lib`**, 以便使用所有的内置交易策略，下面的方法可以安装`ta-lib API`，但它还依赖C语言的`TA-Lib`包，安装方法请参考[FAQ](https://qteasy.readthedocs.io/zh-cn/latest/faq.html#id2)
    ```bash
    $ pip install 'qteasy[talib]'  # 安装qteasy时自动安装ta-lib
    $ pip install ta-lib  # 手动安装ta-lib
    ```

## 10分钟了解 qteasy 的功能

下面通过一个约 10 分钟的教程，快速体验从数据到回测、优化与实盘的完整流程。

### 导入`qteasy`
基本的模块导入方法如下

```python
import qteasy as qt
qt.__version__
```

### 配置本地数据源

为了使用`qteasy`，需要大量的金融历史数据，所有的历史数据都必须首先保存在本地，如果本地没有历史数据，那么`qteasy`的许多功能就无法执行。

`qteasy`默认通过`tushare`金融数据包来获取金融数据，用户需要自行申请`API Token`，获取相应的权限和积分（详情参考：[Tushare 官网](https://tushare.pro/document/2)）

因此，在使用`qteasy`之前需要对`tushare`的`token`进行必要的配置。
最简单的方式是使用`qt.start_up_settings()`和`qt.update_start_up_setting()`方法：

```python
qt.update_start_up_setting(
        tushare_token='<你的tushare_token>',
        local_data_source='db',  # 可选项：设置本地数据源类型，db表示使用MySQL数据库，默认使用csv文件
        local_db_host = '<你的数据库主机名>',  # 可选项：如果使用MySQL数据库作为本地数据源，需要设置数据库的连接地址，默认localhost
        local_db_port = 3306,  # 可选项：如果使用MySQL数据库作为本地数据源，需要设置数据库的连接端口，默认3306
        local_db_user = '<user>',  # 可选项：如果使用MySQL数据库作为本地数据源，需要设置数据库的连接用户名，默认root
        local_db_password = '<password>',  # 可选项：如果使用MySQL数据库作为本地数据源，需要设置数据库的连接密码，默认password
)
# 设置完成后，可以使用qt.start_up_settings()来查看当前的配置
qt.start_up_settings()
```
这时可以看到当前的配置输出如下：

```text
Start up settings:
--------------------
tushare_token = <你的tushare token>
...
```
请检查打印出的配置文件内容是否正确，如果正确，就可以重新导入`qteasy`，并开始正常下载和使用金融数据了。

> qteasy默认情况下将所有的金融数据以csv文件的形式保存在磁盘中，详情参见[qteasy文档数据管理](https://qteasy.readthedocs.io/zh-cn/latest/manage_data/1.%20overview.html)，如果你想把数据保存在`MySQL`数据库中，可以在配置文件中设置`local_data_source='db'`，并设置相应的数据库连接参数，如下所示：
>
>```python
> qt.update_start_up_setting(
>         local_data_source='db',  # 可选项：设置本地数据源类型，db表示使用MySQL数据库，默认使用csv文件
>         local_db_host = '<你的数据库主机名>',  # 可选项：如果使用MySQL数据库作为本地数据源，需要设置数据库的连接地址，默认localhost
>         local_db_port = 3306,  # 可选项：如果使用MySQL数据库作为本地数据源，需要设置数据库的连接端口，默认3306
>         local_db_user = '<user>',  # 可选项：如果使用MySQL数据库作为本地数据源，需要设置数据库的连接用户名，默认root
>         local_db_password = '<password>',  # 可选项：如果使用MySQL数据库作为本地数据源，需要设置数据库的连接密码，默认password
> )
>```

### 下载金融历史数据 

要下载金融价格数据，使用`qt.refill_data_source()`函数。下面的代码下载2021及2022两年内所有股票、所有指数的日K线数据，同时下载所有的股票和基金的基本信息数据。
（根据网络速度，下载数据可能需要几十秒到几分钟的时间，如果存储为`csv`文件，将占用大约200MB的磁盘空间）：

```python
qt.refill_data_source(
        tables=['stock_daily',   # 股票的日线价格
                'index_daily',   # 指数的日线价格
                'basics'],       # 股票和基金的基本信息
        start_date='20210101',  # 下载数据的起止时间
        end_date='20221231',  
)
```

数据下载到本地后，可以使用`qt.get_history_data()`来获取数据，如果同时获取多个股票的历史数据，每个股票的历史数据会被分别保存到一个`dict`中。

```python
qt.get_history_data(htypes='open, high, low, close', 
                    shares='000001.SZ, 000300.SH',
                    start='20210101',
                    end='20210115')
```
运行上述代码会得到一个`Dict`对象，包含两个股票"000001.SZ"以及"000005.SZ"的K线数据（数据存储为`DataFrame`）：
```
{'000001.SZ':
              open   high    low  close
 2021-01-04  19.10  19.10  18.44  18.60
 2021-01-05  18.40  18.48  17.80  18.17
 2021-01-06  18.08  19.56  18.00  19.56
 ... 
 2021-01-13  21.00  21.01  20.40  20.70
 2021-01-14  20.68  20.89  19.95  20.17
 2021-01-15  21.00  21.95  20.82  21.00,
 
 '000300.SH':
                  open       high        low      close
 2021-01-04  5212.9313  5284.4343  5190.9372  5267.7181
 2021-01-05  5245.8355  5368.5049  5234.3775  5368.5049
 2021-01-06  5386.5144  5433.4694  5341.4304  5417.6677
 ...
 2021-01-13  5609.2637  5644.7195  5535.1435  5577.9711
 2021-01-14  5556.2125  5568.0179  5458.6818  5470.4563
 2021-01-15  5471.3910  5500.6348  5390.2737  5458.0812}
```
除了价格数据以外，`qteasy`还可以下载并管理包括财务报表、技术指标、基本面数据等在内的大量金融数据，详情请参见[qteasy文档](https://qteasy.readthedocs.io/zh-cn/latest/manage_data/1.%20overview.html)

股票的数据下载后，使用`qt.candle()`可以显示股票数据K线图，也可以直接使用 `HistoryPanel` 在代码中对历史数据做统计与因子计算。

```python
data = qt.candle('000300.SH', start='2021-06-01', end='2021-8-01', asset_type='IDX')
```

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_5_2.png)
    
`qteasy`的K线图函数`candle`支持通过六位数股票/指数代码查询准确的证券代码，也支持通过股票、指数名称显示K线图
`qt.candle()`支持功能如下：
- 显示股票、基金、期货的K线
- 显示复权价格
- 显示分钟、 周或月K线 
- 显示不同移动均线以及MACD/KDJ等指标

详细的用法请参考文档，示例如下(请先使用`qt.refill_data_source()`下载相应的历史数据)：


```python
# 场内基金的小时K线图
qt.candle('159601', start = '20220121', freq='h')
# 沪深300指数的日K线图
qt.candle('000300', start = '20200121')
# 股票的30分钟K线，复权价格
qt.candle('中国电信', start = '20211021', freq='30min', adj='b')
# 期货K线，三条移动均线分别为9天、12天、26天
qt.candle('沪铜主力', start = '20211021', mav=[9, 12, 26])
# 场外基金净值曲线图，复权净值，不显示移动均线
qt.candle('000001.OF', start='20200101', asset_type='FD', adj='b', mav=[])
```

### 使用 HistoryPanel 操作历史数据

在掌握了基础取数之后，可以进一步使用 `HistoryPanel` 对历史数据做统计和因子计算，例如：

```python
import qteasy as qt

# 直接获取 HistoryPanel（三维数据：标的 × 时间 × 数据类型）
hp = qt.get_history_data(
        htypes='open, high, low, close, vol',
        shares='000300.SH',
        start='20230101',
        end='20231231',
        as_data_frame=False,    # 返回 HistoryPanel
)

# 计算简单收益率和 20 日波动率
ret = hp.returns(price_htype='close', method='simple')
vol = hp.volatility(window=20, price_htype='close', annualize=True)

# 叠加 20 日均线和 MACD 指标
hp_ma = hp.kline.sma(window=20, price_htype='close')
hp_ma_macd = hp_ma.kline.macd(price_htype='close')

# 识别蜡烛形态（如锤头线）
hammer = hp.candle_pattern('cdlhammer')
print(hammer[hammer['000300.SH'] != 0].head())
```

通过 `HistoryPanel`，可以在多标的、多指标维度上统一管理和计算历史数据，然后根据需要随时切换为 `DataFrame`，与 pandas / sklearn / statsmodels 等生态工具协同使用。

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_3_1.png)

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_7_2.png)

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_8_3.png)

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_3_4.png)

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_3_5.png)
    

生成的K线图可以是一个交互式动态K线图（请注意，K线图基于`matplotlib`绘制，在使用不同的终端时，显示功能有所区别，某些终端并不支持
动态图表，详情请参阅 [matplotlib文档](https://matplotlib.org/stable/users/explain/backends.html)


在使用动态K线图时，用户可以用鼠标和键盘控制K线图的显示范围：

- 鼠标在图表上左右拖动：可以移动K线图显示更早或更晚的K线
- 鼠标滚轮在图表上滚动，可以缩小或放大K线图的显示范围
- 通过键盘左右方向键，可以移动K线图的显示范围显示更早或更晚的K线
- 通过键盘上下键，可以缩小或放大K线图的显示范围
- 在K线图上双击鼠标，可以切换不同的均线类型
- 在K线图的指标区域双击，可以切换不同的指标类型：MACD，RSI，DEMA

![gif](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_dyna_plot.gif)

关于`DataSource`对象的更多详细介绍，请参见[qteasy文档](https://qteasy.readthedocs.io/zh-cn/latest/api/data_source.html)


###  创建一个投资策略并启动实盘自动化运行（模拟）

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/examples/img/trader_app_2.png) 

`qteasy`中的所有交易策略都是由`qteast.Operator`（交易员）对象来实现回测和运行的，`Operator`对象是一个策略容器，一个交易员可以同时
管理多个不同的交易策略。

`qteasy`提供了两种方式创建交易策略，详细的说明请参见使用教程：

- **使用内置交易策略组合**
- **通过策略类自行创建策略**

#### 创建一个DMA均线择时交易策略
在这里，我们将使用一个内置的`DMA`均线择时策略来生成一个最简单的大盘择时交易系统。所有内置交易策略的清单和详细说明请参见文档。

创建`Operator`对象时传入参数：`strategies='DMA'`，可以新建一个`DMA`双均线择时交易策略。
创建好`Operator`对象后，可以用`op.info()`来查看它的信息。

```python
op = qt.Operator(strategies='dma')
```

现在可以看到`op`中有一个交易策略，ID是`dma`，我们在`Operator`层面设置或修改策略的参数
时，都需要引用这个`ID`。

`DMA`是一个内置的均线择时策略，它通过计算股票每日收盘价的快、慢两根移动均线的差值`DMA`与其移动平均值`AMA`之间的交叉情况来确定多空或买卖点。：

使用`qt.built_in_doc()`函数可以查看`DMA`策略的详细说明，使用`qt.built_ins()`函数可以获取或者筛选需要的内置交易策略，例如：
```python
qt.built_in_doc('dma')
```
得到：

```
 DMA择时策略
    策略参数:
        s, int, 短均线周期
        l, int, 长均线周期
        d, int, DMA周期
    信号类型:
        PS型: 百分比买卖交易信号
    信号规则:
        在下面情况下产生买入信号:
        1， DMA在AMA上方时，多头区间，即DMA线自下而上穿越AMA线后，输出为1
        2， DMA在AMA下方时，空头区间，即DMA线自上而下穿越AMA线后，输出为0
        3， DMA与股价发生背离时的交叉信号，可信度较高
    策略属性缺省值:
        默认参数: (12, 26, 9)
        数据类型: close 收盘价，单数据输入
        窗口长度: 270
        参数范围: [(10, 250), (10, 250), (8, 250)]
    策略不支持参考数据，不支持交易数据
```
在默认情况下，策略有三个**可调参数**：`(12,26,9)`, 但我们可以给出任意大于2小于250的三个整数作为策略的参数，以适应不同交易活跃度的股票、或者适应
不同的策略运行周期。

您可以使用`qt.built_in_list()`函数查看所有内置策略的清单，并使用`qt.built_ins()`或`qt.built_in_strategies()`函数查看特定策略的详细说明。



### 回测、评价并优化交易策略的性能表现

在`qteasy`中，交易策略中使用的任何变量都可以被定义为“可调参数”，例如dma策略中的短均线周期、长均线周期等等。

这些参数的调节范围和参数类型都是人为规定的，交易策略的性能表现受可调参数的影响。

因此，针对不同类型的股票，不同的交易风格、不同的交易周期，策略的参数可能需要被设为不同的值，同时，为了使策略性能最优化，我们也需要寻找最佳的参数组合。`qteasy`提供了策略回测功能，并多种优化算法，帮助搜索最优的策略参数，提高策略表现。

#### 交易策略的回测

`qteasy`可以使用历史数据回测策略表现并输出图表如下：
![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_14_3.png)

使用默认参数回测刚才建立的DMA策略在历史数据上的表现，可以使用`qt.run()`。

```python
op = qt.Operator(strategies='dma')
qt.configure(
        asset_pool='000300.SH',         # 投资资产池
        asset_type='IDX',               # 投资资产类型
        invest_cash_amounts=[100000],   # 投资资金
        invest_start='20220501',        # 投资回测开始日期
             invest_end='20221231',          # 投资回测结束日期
        cost_rate_buy=0.0003,           # 买入费率
        cost_rate_sell=0.0001,          # 卖出费率
        visual=True,                    # 打印可视化回测图表
        trade_log=True,                 # 打印交易日志
)
res = qt.run(op, mode=1)  # 历史回测模式
```
输出结果如下：
```
     ====================================
     |                                  |
     |       BACK TESTING RESULT        |
     |                                  |
     ====================================

qteasy running mode: 1 - History back testing
time consumption for operate signal creation: 4.4 ms
time consumption for operation back looping:  82.5 ms

investment starts on      2022-05-05 00:00:00
ends on                   2022-12-30 00:00:00
Total looped periods:     0.7 years.

-------------operation summary:------------
Only non-empty shares are displayed, call 
"loop_result["oper_count"]" for complete operation summary

          Sell Cnt Buy Cnt Total Long pct Short pct Empty pct
000300.SH    6        6      12   56.4%      0.0%     43.6%   

Total operation fee:     ¥      257.15
total investment amount: ¥  100,000.00
final value:              ¥  105,773.09
Total return:                     5.77% 
Avg Yearly return:                8.95%
Skewness:                          0.58
Kurtosis:                          3.54
Benchmark return:                -3.46% 
Benchmark Yearly return:         -5.23%

------strategy loop_results indicators------ 
alpha:                            0.142
Beta:                             1.003
Sharp ratio:                      0.637
Info ratio:                       0.132
250 day volatility:               0.138
Max drawdown:                    11.92% 
    peak / valley:        2022-08-17 / 2022-10-31
    recovered on:         Not recovered!

===========END OF REPORT=============
```
![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_21_1.png)

#### 交易策略的参数调优

交易策略的表现与参数有关，如果输入不同的参数，策略回报相差会非常大。`qteasy`可以用多种不同的优化算法，帮助搜索最优的策略参数，

要使用策略优化功能，需要设置交易策略的优化标记`opt_tag=1`，并配置环境变量`mode=2`即可:

```python
import qteasy as qt

op = qt.Operator(strategies='dma')
qt.configure(
             opti_start='20220501',     # 优化区间开始日期
             opti_end='20221231',       # 优化区间结束日期
             test_start='20220501',     # 测试区间开始日期
             test_end='20221231',       # 测试区间结束日期
             opti_sample_count=1000,    # 优化样本数量
             visual=True,               # 打印优化结果图表
             parallel=False             # 不使用并行计算
)
op.set_parameter('dma', opt_tag=1)
res = qt.run(op, mode=2)  # 策略优化模式
```

`qteasy`将在同一段历史数据（优化区间）上反复回测，找到结果最好的30组参数，并把这30组参数在另一段历史数据（测试区间）上进行独立测试，并显
示独立测试的结果：
```commandline
==================================== 
|                                  |
|       OPTIMIZATION RESULT        |
|                                  |
====================================

qteasy running mode: 2 - Strategy Parameter Optimization

... # 省略部分输出

# 以下是30组优化的策略参数及其结果（部分结果省略）
    Strategy items Sell-outs Buy-ins ttl-fee     FV      ROI  Benchmark rtn MDD 
0     (35, 69, 60)     1.0      2.0    71.45 106,828.20  6.8%     -3.5%     9.5%
1   (124, 104, 18)     3.0      2.0   124.86 106,900.59  6.9%     -3.5%     7.4%
2   (126, 120, 56)     1.0      1.0    72.38 107,465.86  7.5%     -3.5%     7.5%
...
27   (103, 84, 70)     1.0      1.0    74.84 114,731.44 14.7%     -3.5%     8.8%
28  (143, 103, 49)     1.0      1.0    74.33 116,453.26 16.5%     -3.5%     4.3%
29   (129, 92, 56)     1.0      1.0    74.55 118,811.58 18.8%     -3.5%     4.3%

===========END OF REPORT=============
```

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_24_1.png)   
将优化后的参数应用到策略中，并再次回测，可以看到结果明显提升：

```python
op.set_parameter('dma', par_values=(143, 99, 32))
res = qt.run(op, mode=1)  # 历史回测模式
```
结果如下：

![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_26_1.png)   


关于策略优化结果的更多解读、以及更多优化参数的介绍，请参见详细文档

### 启动交易策略的实盘自动化模拟运行

在配置好`Operator`对象并设置好策略后，`qteasy`可以自动定期运行、自动盯盘、自动下载实时数据并根据策略结果生成交易指令，模拟交易过程并记录交易结果。

`Qteasy`的实盘一旦启动，就会在`terminal`中启动一个单独的线程在后台运行，运行的时机也是跟真实的股票市场一致的，股票市场收市的时候不运行，交易日早上9点15分唤醒系统开始拉取实时股价，9点半开始运行交易策略，交易策略的运行时机和运行频率在策略的属性中设置。如果策略运行的结果产生交易信号，则根据交易信号模拟挂单，挂单成交后修改响应账户资金和股票持仓，交易费用按照设置中的费率扣除。如果资金不足或持仓不足会导致交易失败，当天买入的股票同真实市场一样T+1交割，第二个交易日开始前交割完毕。

```python
# 创建一个交易策略alpha
alpha = qt.get_built_in_strategy('ndayrate')  # 创建一个N日股价涨幅交易策略

# 设置策略的运行参数
alpha.window_length = 20  # 数据窗口长度
alpha.sort_ascending = False  # 优先选择涨幅最大的股票
alpha.condition = 'greater'  # 筛选出涨幅大于某一个值的股票
alpha.ubound = 0.005  # 筛选出涨幅大于0.5%的股票
alpha.sel_count = 7  # 每次选出7支股票

# 创建一个交易员对象，运行alpha策略
op = qt.Operator(alpha)

# 设置策略运行参数
# 交易股票池包括所有的银行股和家用电器股
asset_pool = qt.filter_stock_codes(industry='银行, 家用电器', exchange='SSE, SZSE')

qt.configure(
        asset_type='E',  # 交易的标的类型为股票
        asset_pool=asset_pool,  # 交易股票池为所有银行股和家用电器股
        trade_batch_size=100,  # 交易批量为100股的整数倍
        sell_batch_size=1,  # 卖出数量为1股的整数倍
        live_trade_account_id=None,  # 不指定实盘交易账户，给出账户名称并创建一个新的账户
        live_trade_account_name='new_account',
        # 如果想要使用已有的账户，应该指定账户ID同时不给出account_name：
        live_trade_account_id=1
        live_trade_account_name=None
        live_trade_ui_type='tui',  # 使用TUI界面监控实盘交易，默认使用CLI界面
)
```
完成上述设置后，使用下面的代码运行交易策略，运行交易策略时指定模式0，代表实盘交易:

```python
qt.run(op, mode=0)  # 交易模式为实盘运行
```

`Qteasy`的实盘运行有一个“账户”的概念，就跟您在股票交易市场开户一样，一个账户可以有自己的持有资金，股票持仓，单独计算盈亏。运行过程中您可以随时终止程序，这时所有的交易记录都会保存下来，下次重新启动时，只要引用上一次运行使用的账户ID（account ID）就可以从上次中断的地方继续运行了，因此启动时需要指定账户，如果不想继续上次的账户，可以新开一个账户运行。

在启动实盘时可以通过`qteasy`的系统配置变量`live_trade_account_name`来指定使用的账户名，系统会自动创建一个新的账户并赋予账户ID；如果想要使用已有的账户，可以在启动时通过`live_trade_account_id`指定账户ID。

#### 实盘自动化交易的控制界面

为了对策略运行过程进行监控，同时与`qteasy`进行互动，`qteasy`提供了两种不同的交互界面：

#### 命令行用户界面 CLI

- **`TraderShell`** 交互式命令行界面CLI，可以在命令行中输入命令，查看交易日志、查看持仓、查看账户资金变化等信息：
   
   在命令行界面中，启动后默认显示的是交易策略的dashboard(状态页)，在该屏幕上会滚动显示交易策略运行日志，打印产生的交易信号、交易结果、当前最新股票价格等信息。
   
   ![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_27_1.png)  
   在策略运行过程中，用户可以通过键入"Ctrl+C"进入主菜单，按1键进入交互模式，这时用户可以通过键盘输入命令来查看持仓、查看账户资金变化、查看交易日志等信息，也可以通过命令来控制交易策略的运行，例如暂停、继续、终止交易策略的运行。

   ![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/img/output_27_3.png) 


   
   CLI界面目前支持的交互命令较多，包括：
  - 暂停、恢复、终止交易策略的运行
  - 查看持仓、账户资金、交易订单、交易历史等信息
  - 手动调整持仓数量、资金数量、手动调整交易配置
  - 手动下单，手动撤单
  - 设置实时价格监控的股票代码



#### Terminal图形用户界面 TUI

- **`TraderApp`** (v1.2.0新增) 交互式图形界面TUI，可以在图形界面中查看交易日志、查看持仓、查看账户资金变化等信息：

   在TUI图形界面中，用户的Terminal会被划分为多个区域，显示策略运行过程中的所有关键信息，例如在顶部显示当前资产总额、浮动盈亏，在画面中部以图表显示当前持仓、交易订单历史记录、实时股票价格、以及策略运行参数等信息，在画面底部显示交易日志。

   ![png](https://raw.githubusercontent.com/shepherdpp/qteasy/master/docs/source/examples/img/trader_app_light_theme.png)


   用户可以在TUI界面中以快捷键或者鼠标按钮点击的方式与qteasy的自动化交易程序互动，目前支持的功能较少，包括：
  - 设置或调整实时价格监控的股票代码
  - 更多的功能正在逐步添加中

上面两种方式都可以在实盘运行时使用，根据`qteasy`的配置参数进入不同的交互界，关于更多实盘运行的介绍，请参见[`QTEASY`文档](https://qteasy.readthedocs.io/zh-cn/latest/tutorials/1-get-started.html)
