关于 vectorbt
vectorbt 是面向量化交易者和研究者的 Python 向量化回测库。它将基于 pandas 的信号、参数搜索、绩效分析和绘图整合到同一工作流中。
主要功能
- 01向量化投资组合回测
- 02布尔型进出场信号
- 03参数网格搜索
- 04内置绩效指标
- 05回测结果绘图
适用场景
- 01在价格数据上测试交易策略
- 02比较不同参数组合
- 03查看风险与交易统计
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ agiprolabs/ claude-trading-skills --skill vectorbt安装后在 Claude Code 中输入/vectorbt确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
references/api_guide.mdoptimization_guide.mdscripts/backtest_example.pyparameter_sweep.py详细介绍
使用 vectorbt 进行向量化回测
概述
vectorbt 是一个用于向量化回测的 Python 库,可通过 NumPy/pandas 数组运算运行策略模拟,而不是逐根 K 线循环。这使它比事件驱动框架(backtrader、zipline)快 100–1000 倍,可在几秒内完成数千种组合的参数优化。
主要优势:
- 借助 NumPy 向量化实现极快的运行速度
- 内置参数网格搜索与优化
- 内置 50 多种绩效指标(夏普比率、索提诺比率、卡玛比率、最大回撤、盈利因子)
- 丰富的绘图功能(权益曲线、回撤、交易标记、热力图)
- 原生集成 pandas——数据始终保留在 DataFrame 中
安装
uv pip install vectorbt pandas numpy
vectorbt 会自动安装 pandas、NumPy 和 Plotly。若要使用技术指标,还需安装 pandas-ta:
uv pip install vectorbt pandas-ta
核心概念
1. 信号——布尔入场/离场数组
在 vectorbt 中,策略通过布尔型 pandas Series(或数组)表示,用于指示入场和离场的位置:
import vectorbt as vbt
import pandas as pd
# Entry: buy when fast EMA crosses above slow EMA
entries = fast_ema > slow_ema
# Exit: sell when fast EMA crosses below slow EMA
exits = fast_ema < slow_ema
vectorbt 会自动处理冲突信号(持仓期间无法再次入场)。
2. 投资组合——回测引擎
vbt.Portfolio.from_signals() 是主要的回测函数。它接收价格数据和入场/离场信号,模拟交易并计算绩效:
pf = vbt.Portfolio.from_signals(
close=close_prices,
entries=entries,
exits=exits,
init_cash=10_000,
fees=0.003, # 0.3% per trade
slippage=0.005, # 0.5% slippage
freq="1h", # hourly data
)
3. 指标——内置绩效分析
# Full stats summary
print(pf.stats())
# Individual metrics
print(f"Total Return: {pf.total_return():.2%}")
print(f"Sharpe Ratio: {pf.sharpe_ratio():.3f}")
print(f"Max Drawdown: {pf.max_drawdown():.2%}")
print(f"Win Rate: {pf.trades.win_rate():.2%}")
4. 参数优化——几秒内完成网格搜索
传入数组而非标量,即可同时测试多个参数组合:
import numpy as np
fast_periods = np.arange(5, 25, 2) # 10 values
slow_periods = np.arange(20, 60, 5) # 8 values
fast_ma = vbt.MA.run(close, fast_periods, short_name="fast")
slow_ma = vbt.MA.run(close, slow_periods, short_name="slow")
# This creates 80 parameter combinations automatically
entries = fast_ma.ma_crossed_above(slow_ma)
exits = fast_ma.ma_crossed_below(slow_ma)
基本工作流
步骤 1:加载 OHLCV 数据
import pandas as pd
# From CSV
df = pd.read_csv("ohlcv.csv", parse_dates=["timestamp"], index_col="timestamp")
close = df["close"]
# From Yahoo Finance (traditional markets)
btc = vbt.YFData.download("BTC-USD", start="2023-01-01", end="2025-01-01")
close = btc.get("Close")
对于 Solana 代币,可通过 birdeye-api 技能获取数据并加载到 DataFrame 中。
步骤 2:计算指标
import pandas_ta as ta
# Using pandas-ta (see pandas-ta skill)
df.ta.ema(length=12, append=True)
df.ta.ema(length=26, append=True)
df.ta.rsi(length=14, append=True)
df.ta.bbands(length=20, std=2, append=True)
# Or using vectorbt built-ins
rsi = vbt.RSI.run(close, window=14)
bbands = vbt.BBANDS.run(close, window=20, alpha=2)
步骤 3:生成入场/离场信号
# EMA crossover
entries = df["EMA_12"] > df["EMA_26"]
exits = df["EMA_12"] < df["EMA_26"]
# RSI mean reversion
entries = rsi.rsi_below(30)
exits = rsi.rsi_above(70)
步骤 4:运行回测
pf = vbt.Portfolio.from_signals(
close=close,
entries=entries,
exits=exits,
init_cash=10_000,
fees=0.003,
slippage=0.005,
size=0.95, # use 95% of available cash
size_type="percent",
freq="1h",
)
步骤 5:分析结果
# Summary statistics
print(pf.stats())
# Trade-level analysis
trades = pf.trades.records_readable
print(f"\nTrade count: {len(trades)}")
print(f"Avg holding period: {trades['Duration'].mean()}")
# Equity curve
pf.plot().show()
# Drawdown chart
pf.drawdowns.plot().show()
主要投资组合参数
| 参数 | 说明 | 示例 |
|---|---|---|
close | 价格序列(pd.Series 或 DataFrame) | df["close"] |
entries | 布尔入场信号 | fast > slow |
exits | 布尔离场信号 | fast < slow |
init_cash | 初始资金 | 10_000 |
fees | 每笔交易的手续费(比例) | 0.003(0.3%) |
slippage | 每笔交易的滑点(比例) | 0.005(0.5%) |
size | 持仓规模 | 0.95 |
size_type | 持仓规模的解释方式 | "percent"、"amount"、"value" |
freq | 数据频率 | "1h"、"4h"、"1d" |
direction | 交易方向 | "both"、"longonly"、"shortonly" |
accumulate | 是否允许加仓 | False |
sl_stop | 止损位(比例) | 0.05(5%) |
tp_stop | 止盈位(比例) | 0.10(10%) |
绩效指标
收益
total_return()— 周期内累计收益annualized_return()— 年化复合收益daily_returns()— 每日收益 Series
风险
max_drawdown()— 峰值到谷值的最大跌幅annualized_volatility()— 年化收益标准差value_at_risk()— 指定置信水平下的风险价值(VaR)
风险调整指标
sharpe_ratio()— 每单位波动率对应的超额收益sortino_ratio()— 每单位下行偏差对应的超额收益calmar_ratio()— 年化收益 / 最大回撤omega_ratio()— 按概率加权的盈亏比
交易统计
trades.win_rate()— 盈利交易所占比例trades.profit_factor()— 总盈利 / 总亏损trades.expectancy()— 每笔交易的平均盈亏trades.avg_winning_trade()— 盈利交易的平均利润trades.avg_losing_trade()— 亏损交易的平均亏损trades.count()— 已完成交易的总数
参数优化
网格搜索
fast_windows = [5, 8, 12, 15, 20]
slow_windows = [20, 26, 30, 40, 50]
# Run all 25 combos at once
fast_ma = vbt.MA.run(close, fast_windows, short_name="fast")
slow_ma = vbt.MA.run(close, slow_windows, short_name="slow")
entries = fast_ma.ma_crossed_above(slow_ma)
exits = fast_ma.ma_crossed_below(slow_ma)
pf = vbt.Portfolio.from_signals(close, entries, exits, fees=0.003)
# Find best params by Sharpe
sharpe = pf.sharpe_ratio()
best_idx = sharpe.idxmax()
print(f"Best params: {best_idx}, Sharpe: {sharpe[best_idx]:.3f}")
滚动前向验证
始终使用样本外数据验证优化后的参数:
# Split: 70% train, 30% test
split_idx = int(len(close) * 0.7)
train_close = close.iloc[:split_idx]
test_close = close.iloc[split_idx:]
# Optimize on training data
# ... (run grid search on train_close)
# Validate best params on test data
# ... (run single backtest on test_close with best params)
有关滚动前向方法和防止过拟合的详细说明,请参阅 references/optimization_guide.md。
加密货币专项注意事项
24/7 市场
加密货币市场永不休市。请使用按小时或分钟计算的频率,而不是按工作日计算的频率:
# Correct for crypto
pf = vbt.Portfolio.from_signals(close, entries, exits, freq="1h")
# Wrong — business days assume market closures
# pf = vbt.Portfolio.from_signals(close, entries, exits, freq="1B")
真实的手续费
Solana 上的 DEX 兑换通常需要 0.25–1% 的费用(包括 AMM 手续费)。CEX 现货交易手续费为 0.05–0.1%。
# Solana DEX (conservative)
pf = vbt.Portfolio.from_signals(close, entries, exits, fees=0.005)
# CEX spot
pf = vbt.Portfolio.from_signals(close, entries, exits, fees=0.001)
滑点
流动性较低的代币可能会出现 1–5% 的滑点。请务必对其建模:
# High-liquidity (SOL, ETH): 0.1–0.5%
pf = vbt.Portfolio.from_signals(close, entries, exits, slippage=0.003)
# Low-liquidity memecoins: 1–3%
pf = vbt.Portfolio.from_signals(close, entries, exits, slippage=0.02)
历史数据较短
许多代币的历史数据不足 1 年。根据较短的样本计算年化指标时,请务必谨慎。
常见策略模式
EMA 交叉
fast = vbt.MA.run(close, 12, short_name="fast")
slow = vbt.MA.run(close, 26, short_name="slow")
entries = fast.ma_crossed_above(slow)
exits = fast.ma_crossed_below(slow)
RSI 均值回归
rsi = vbt.RSI.run(close, 14)
entries = rsi.rsi_crossed_below(30)
exits = rsi.rsi_crossed_above(70)
布林带突破
bb = vbt.BBANDS.run(close, window=20, alpha=2)
entries = close > bb.upper
exits = close < bb.lower
止损和止盈
pf = vbt.Portfolio.from_signals(
close, entries, exits,
sl_stop=0.05, # 5% stop-loss
tp_stop=0.10, # 10% take-profit
)
相关技能
- pandas-ta — 计算技术指标(为 vectorbt 信号提供数据)
- birdeye-api — 获取 Solana 代币 OHLCV 数据,用于回测
- trading-visualization — 为回测结果生成高级图表
- portfolio-analytics — 深入分析投资组合层面的风险与收益
- position-sizing — 最优仓位规模方法
- risk-management — 投资组合层面的风险防护措施
- regime-detection — 感知市场状态,以调整策略
文件
参考资料
references/api_guide.md— vectorbt 的完整 API 参考,涵盖 Portfolio、指标、绘图和数据加载references/optimization_guide.md— 网格搜索、滚动验证、防止过拟合和优化最佳实践
脚本
scripts/backtest_example.py— 使用合成数据对比三种策略的回测(EMA 交叉、RSI 均值回归、布林带突破)scripts/parameter_sweep.py— 通过滚动验证对 EMA 交叉参数进行网格搜索