【Python】vectorbtで爆速バックテスト入門|for文なしで1000戦略を数秒で検証する

バックテストのfor文ループが遅すぎて、パラメータを少し変えるたびに「うーん、終わるまで5分か。。。」となっていた。移動平均の期間を10〜200まで1刻みで試そうとしたら計算が終わる前に子供が起きてきた。そのとき同僚から「vectorbtって知ってる?」と聞かれて試したら、もう戻れなくなった。

vectorbtとは何か、なぜ速いのか

vectorbtはPython製のバックテストライブラリで、GitHubのスターが1万を超えており、機関投資家やクオンツ界隈でも使われている。公式サイトには「Run thousands of trading ideas before others finish one(他の人が1戦略終わる前に数千の戦略を実行できる)」と書いてある。なかなかの自信だ。

速さの秘密はNumPy配列のベクトル演算Numba(JITコンパイラ)の組み合わせにある。通常のバックテストはfor文で1本ずつバーを処理するが、vectorbtは全てのバーを配列にまとめて一括処理する。CPUが「バーを1つずつ処理」するのではなく「全バーを並列に計算」するイメージ。これが従来比100倍以上の速度差を生む。

また、複数パラメータの組み合わせを一度に流せる機能(パラメータグリッドサーチ)も内蔵しているので、「短期MAを10〜50まで、長期MAを50〜200まで試す」という2次元のパラメータスキャンが数行のコードで書ける。Optunaと組み合わせて最適化する手もあるが、まず全探索できるのは強い。

インストールと基本的な使い方

インストールはpipで一発。ただし依存ライブラリが多いので、できれば仮想環境(venv)の中で入れたほうが安全。

# インストール
pip install vectorbt yfinance

# 確認
import vectorbt as vbt
print(vbt.__version__)

基本的なワークフローはこうなる:①データ取得 → ②シグナル生成 → ③vbt.Portfolio.from_signals()に渡す → ④結果を確認。たったこれだけ。

移動平均クロスオーバーをvectorbtで実装する

まずはシンプルな移動平均ゴールデン/デッドクロス戦略から。対象はドル円(USDJPY=X)の日足データ。

import vectorbt as vbt
import yfinance as yf
import pandas as pd

# ===== データ取得 =====
data = yf.download("USDJPY=X", start="2022-01-01", end="2026-05-31", auto_adjust=True)
close = data["Close"].dropna()

# ===== 移動平均の計算 =====
fast_window = 20   # 短期MA
slow_window = 60   # 長期MA

fast_ma = vbt.MA.run(close, window=fast_window)
slow_ma = vbt.MA.run(close, window=slow_window)

# ===== シグナル生成 =====
# 短期MAが長期MAを上抜け → 買い
# 短期MAが長期MAを下抜け → 売り(空売りはなし、ポジションクローズ)
entries = fast_ma.ma_crossed_above(slow_ma)
exits   = fast_ma.ma_crossed_below(slow_ma)

# ===== バックテスト実行 =====
pf = vbt.Portfolio.from_signals(
    close,
    entries,
    exits,
    init_cash=1_000_000,   # 初期資金100万円
    fees=0.0003,            # 手数料0.03%
    freq="D"
)

# ===== 結果確認 =====
print(pf.stats())

pf.stats()を実行すると、総リターン・最大ドローダウン・シャープレシオ・勝率など主要な統計がまとめて出てくる。グラフ描画も一行で済む:

# 資産曲線の表示(Jupyter Notebookで動くインタラクティブチャート)
pf.plot().show()

複数パラメータを一気に試す(グリッドサーチ)

vectorbtの真骨頂はここ。短期MAと長期MAの組み合わせを一度に全部試せる。

import numpy as np

# 短期MA: 10〜50(10刻み)、長期MA: 60〜200(20刻み)
fast_windows = np.arange(10, 55, 10)   # [10, 20, 30, 40, 50]
slow_windows = np.arange(60, 220, 20)  # [60, 80, 100, ..., 200]

# 全組み合わせで一括計算
fast_ma = vbt.MA.run(close, window=fast_windows, short_name="fast")
slow_ma = vbt.MA.run(close, window=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,
    init_cash=1_000_000,
    fees=0.0003,
    freq="D"
)

# 全組み合わせの総リターンをDataFrameで取得
returns = pf.total_return()
print("最高リターンの組み合わせ:")
print(returns.idxmax())
print(f"リターン: {returns.max():.2%}")

# ヒートマップ表示
returns.vbt.heatmap(
    x_level="fast_window",
    y_level="slow_window",
    slider_level=None
).show()

5×8 = 40通りのパラメータ組み合わせが数秒で終わる。これを普通のfor文でやると、体感10〜20倍の時間がかかる。子供が眠っている深夜に試行錯誤するにはこれぐらいのスピードが必要。。。

日本株への応用

ドル円と同じ要領で日本株にも使える。複数銘柄を同時にバックテストすることもできる。

# 複数銘柄(トヨタ・デンソー・日立)を同時にバックテスト
tickers = ["7203.T", "6902.T", "6501.T"]
data_multi = yf.download(tickers, start="2022-01-01", end="2026-05-31", auto_adjust=True)
close_multi = data_multi["Close"].dropna(how="all")

fast_ma = vbt.MA.run(close_multi, window=20)
slow_ma = vbt.MA.run(close_multi, window=60)

entries = fast_ma.ma_crossed_above(slow_ma)
exits   = fast_ma.ma_crossed_below(slow_ma)

pf_multi = vbt.Portfolio.from_signals(
    close_multi,
    entries,
    exits,
    init_cash=1_000_000,
    fees=0.001,  # 日本株は手数料やや高め
    freq="D"
)

print(pf_multi.stats())

注意点:vectorbtの落とし穴

vectorbtはとにかく強力なのだが、いくつか気をつけることがある。まず学習コストが若干高め。APIのドキュメントが英語で、公式のやり方と検索で出てくるやり方が微妙に違うことがある。バージョンアップで互換性が壊れることもあったので、バージョンを固定(pip install vectorbt==0.26.2など)しておくのが安全。

次にグリッドサーチは過学習のリスクを高める点に注意が必要。何十・何百の組み合わせを試して「一番良い」パラメータを採用しても、それは過去データに最適化しただけかもしれない。グリッドサーチした後は必ず「試してないデータ(アウトオブサンプル)」で結果を確認すること。この話は次の記事で詳しく書く予定。

まとめ

vectorbtを使えば「アイデアを思いついたら即バックテスト」が実現できる。for文のループを書く必要がなく、パラメータのグリッドサーチも数行で済む。Jupyter Notebookとの相性もよく、インタラクティブなチャートで結果をすぐに確認できるのも嬉しい。

僕はこれを使い始めてから「試したいアイデアを即夜検証して翌朝結果確認」というサイクルが回せるようになった。子供が寝た深夜の1〜2時間でサクッと回せるのが個人的に最高で、次はドル円の短期スキャルピング戦略をvectorbtでまとめて検証してみようと思っている。

タイトルとURLをコピーしました