聊天視窗

數據驅動投資分析:從基礎到量化交易 - 第 5 章

第5章 量化策略設計與回測

發布於 2026-03-04 18:46

# 第5章 量化策略設計與回測 ## 5.1 何為「策略」 在數據驅動投資的語境下,\*策略\*不是一個靜態的規則集合,而是**可執行、可測量、可改進**的交易機制。它需要: 1. **訊號產生** – 從前面建立的模型或統計指標得到買賣訊號。 2. **風險控制** – 以止損、倉位限制或多因子分散等方式降低非預期損失。 3. **執行機制** – 考慮滑點、手續費、執行速度等實務條件。 4. **績效評估** – 使用 Sharpe、Sortino、最大回撤等指標來量化回報與風險。 本章將把這四個模塊串連起來,並示範如何在 Python 環境下實作、回測與優化。 ## 5.2 策略設計流程 1. **定義投資目標**:\*高頻量化、日內套利、長期機會發掘\* 等。 2. **選擇市場與資產**:如 US Equities、ETF、外匯或期貨。 3. **建立訊號來源**: - *技術指標*(如 MACD、RSI) - *機器學習預測*(如 XGBoost 方向預測) - *經濟事件*(利率公告、GDP 增速) 4. **設計風險管理規則**: - 風險敞口上限(10% 個別、30% 風險因子) - 止損、止盈、風險/報酬比率 5. **模擬執行(回測)**:結合歷史行情、滑點模型與手續費。 6. **績效評估與改進**:使用多指標、Walk‑Forward Validation、交叉驗證。 以下示範以 *日內均線交叉* 為簡單訊號,並加入 XGBoost 方向預測以提升訊號信噪比。 ## 5.3 技術架構 | 模組 | 主要工具 | 說明 | |------|----------|------| | 數據獲取 | `yfinance`, `pandas-datareader` | 下載歷史行情、成交量 | | 特徵工程 | `ta-lib`, `pandas` | 計算技術指標 | | 訊號預測 | `xgboost` | 方向預測 | | 回測引擎 | `backtrader`, `zipline` | 模擬交易、滑點 | | 評估工具 | `pyfolio`, `quantstats` | 生成報表 | ## 5.4 範例:日內均線交叉 + XGBoost 預測 ```python import pandas as pd import numpy as np import yfinance as yf from ta.trend import EMAIndicator from xgboost import XGBClassifier from sklearn.model_selection import train_test_split from sklearn.preprocessing import StandardScaler import backtrader as bt # 1. 下載資料 symbol = "AAPL" start = "2020-01-01" end = "2023-12-31" price = yf.download(symbol, start=start, end=end, interval="1h") # 2. 特徵工程 price['ema_20'] = EMAIndicator(price['Close'], window=20).ema_indicator() price['ema_50'] = EMAIndicator(price['Close'], window=50).ema_indicator() price['macd'] = price['ema_20'] - price['ema_50'] price['rsi'] = price['Close'].rolling(14).apply(lambda x: 100 - 100/(1+((x[-1]-x.mean())/x.std()))) # 3. 方向標籤(下個時間段收盤價相對於本期) price['future_ret'] = price['Close'].shift(-1) - price['Close'] price['label'] = (price['future_ret'] > 0).astype(int) # 4. XGBoost 訓練 features = ['ema_20','ema_50','macd','rsi'] X = price[features].fillna(0) y = price['label'] X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.3, shuffle=False) scaler = StandardScaler() X_train = scaler.fit_transform(X_train) X_test = scaler.transform(X_test) model = XGBClassifier(n_estimators=200, learning_rate=0.05, max_depth=3) model.fit(X_train, y_train) price['pred'] = model.predict(scaler.transform(X)) # 5. 策略定義(Backtrader) class MomentumStrategy(bt.Strategy): params = dict(risk_per_trade=0.01) def __init__(self): self.dataclose = self.datas[0].close self.ema20 = bt.indicators.ExponentialMovingAverage(self.datas[0], period=20) self.ema50 = bt.indicators.ExponentialMovingAverage(self.datas[0], period=50) self.pred = [] # 從 DataFrame 取預測訊號 def next(self): i = len(self.datas[0]) - 1 if self.ema20[i] > self.ema50[i] and self.pred[i] == 1: if not self.position: size = (self.broker.getcash() * self.params.risk_per_trade) / self.dataclose[0] self.buy(size=size) elif self.ema20[i] < self.ema50[i] and self.pred[i] == 0: if self.position: self.close() # 6. 初始化 Backtrader cerebro = bt.Cerebro() data = bt.feeds.PandasData(dataname=price, fromdate=pd.Timestamp(start), todate=pd.Timestamp(end)) cerebro.adddata(data) cerebro.addstrategy(MomentumStrategy) cerebro.broker.set_cash(100000) cerebro.broker.setcommission(commission=0.001) # 7. 回測 results = cerebro.run() cerebro.plot() ``` > **注意**:上述示範僅為概念驗證,實務中需加入滑點模型、執行延遲測試以及多策略併發。 ## 5.5 回測的七大陷阱 1. **前瞻性偏差(Look‑ahead bias)**:使用未來資訊進行特徵或訊號。解法:確保所有特徵都在「時間戳」之前。 2. **過度擬合(Over‑fitting)**:模型在訓練集表現極佳,但在測試集失敗。做法:使用 Walk‑Forward、交叉驗證、正則化。 3. **交易成本忽略**:滑點、手續費若未納入,績效高估。加上實際交易成本。 4. **資料稀疏**:低頻資料對高頻策略不適。確保資料頻率與策略匹配。 5. **市場微結構失真**:如深度資料缺失,影響滑點估算。使用 Level‑2 資料或第三方數據。 6. **風險模型不精確**:單純使用每日波動率無法捕捉波動聚集。考慮 GARCH、EWMA 等。 7. **策略穩定性**:不同時期、不同市場條件可能導致策略失效。進行多市場、不同時間段的驗證。 ## 5.6 進階優化 ### 5.6.1 超參數調整 利用 **Optuna** 或 **Ray Tune** 進行大規模超參數搜索,結合多目標(收益率、夏普比率、最大回撤)。 ```python import optuna def objective(trial): max_depth = trial.suggest_int('max_depth', 3, 10) learning_rate = trial.suggest_loguniform('learning_rate', 0.001, 0.1) n_estimators = trial.suggest_int('n_estimators', 100, 500) # 重新訓練並評估回測績效 model = XGBClassifier(max_depth=max_depth, learning_rate=learning_rate, n_estimators=n_estimators) # ... return -sharpe # 目標最小化 study = optuna.create_study(direction='minimize') study.optimize(objective, n_trials=50) ``` ### 5.6.2 風險平衡 採用 **Kelly** 或 **Equal‑Risk** 分配,將每筆交易的風險量化為「可接受最大虧損」而非固定倉位。 ### 5.6.3 多策略組合 使用 **Markowitz Portfolio Optimization** 或 **Black‑Litterman** 把多個子策略的期望報酬與共變量組合,實現分散與風險控制。 ## 5.7 真實環境部署 1. **執行平台**:雲端(AWS、GCP)或自建 EC2,使用 Docker 容器化。 2. **資料來源**:訂閱實時行情 API(如 IEX Cloud、Polygon)。 3. **滑點模擬**:使用 **VWAP**、**TWAP** 或實際委託書深度。 4. **監控**:實時寫入 **Prometheus**,用 Grafana 做 Dashboard;設定警報(失敗率、滑點異常)。 5. **自動化回測**:CI/CD pipeline,持續整合每次模型更新。 ## 5.8 小結 - **策略不是模型**:模型僅產生訊號,完整策略還需風險管理、執行機制與績效評估。 - **回測是檢驗**:一套策略必須經過嚴謹的回測與現實成本模擬,才能確定其可行性。 - **迭代是關鍵**:市場在變,策略也須持續調整。建立「策略迭代週期」是長期成功的關鍵。 > **提示**:下章將深入探討如何把已驗證的策略實際部署到高頻交易環境,並介紹實時風險監控與自動化交易的架構設計。