機器學習實作 Lab 7:用 SVM、隨機森林與神經網絡預測價差跑配對交易
第 31 課・共 34 課
目錄
理論課之後落手做。本講是 Liu Peng 課程的 Lab 7 實作課,承接第 27 講機器學習與配對交易的框架及第 28 講三大模型的數學原理,在 Google Colab 上用 Python 把支援向量機、隨機森林與神經網絡逐一裝進配對交易策略,示範由特徵工程、模型訓練到回測評分的完整機器學習實作流程。本篇筆記按原片脈絡重構,公式以 LaTeX 重寫。
學習重點
- 機器學習版配對交易的核心改動:不再用滾動均值估計價差中樞,改為訓練模型預測價差,再將預測與實際的標準化差距轉成 Z 分數訊號
- 特徵工程實作:兩隻股票的對數回報、價差滾動均值、兩隻股票的滾動波動率,共五個特徵配一個預測目標
- 三大模型同場操練:sklearn 的 SVR(線性核)、RandomForestRegressor(100 棵樹)與 PyTorch 前饋神經網絡(5-64-32-1)
- 神經網絡訓練迴圈五部曲:清零梯度、前向傳播、計算損失、反向傳播、更新權重
- 本 Lab 最重要的結論:預測誤差更低不等於交易回報更高,預測與獲利是兩個獨立階段
詳細筆記
實驗設定:沿用協整股票對與對數價差
環境方面,講者除 yfinance 外另裝 torchsummary 套件,稍後用來列印神經網絡的架構與參數量。開首照例固定隨機種子確保結果可重現,股票對沿用 GOOG 與 MSFT——過去幾講的協整分析顯示兩者關係穩定,數據取 2022 年全年的調整後收盤價。
價差沿用簡單定義:兩隻股票對數價格之差
$$s_t = \log P^{(1)}_t - \log P^{(2)}_t$$講者說明這只是示範用的定義,重點在於展示「用機器學習預測價差」的流程。策略構想是:假設能預測未來價差,便可將預測值與當前價差比較,價差偏離預測越遠,回歸的交易機會越大,由此產生買賣訊號。
以對數價格差定義的價差走勢(2022 年 GOOG/MSFT)。截圖出自原片(Liu Peng)
特徵工程與訓練測試集劃分
原始數據只有兩條價格序列,講者先做特徵工程(Feature Engineering)擴充輸入維度,共構建五個特徵:
- 資產一的對數回報 log return,即 $r^{(1)}_t = \log P^{(1)}_t - \log P^{(1)}_{t-1}$
- 資產二的對數回報 $r^{(2)}_t$,定義相同
- 價差的滾動平均值,捕捉價差的近期中樞
- 資產一的滾動標準差(滾動波動率)
- 資產二的滾動標準差
講者提醒,這些是技術分析常見的特徵,並無標準答案,學員可自行增刪,觀察模型準確度是否改善——特徵選擇本身就是一場實驗。五個特徵組成一個 DataFrame,滾動運算產生的空值列直接剔除,預測目標(target)則是價差本身。
數據劃分採 80/20:首 80% 數據為訓練集,用來擬合模型;餘下 20% 為測試集,扮演「未來」的角色,用來評估模型的樣本外表現。由於是時間序列,劃分按時間順序切開,不能隨機打亂,否則等於用未來的數據訓練、回頭預測過去,犯下前視偏差。這是機器學習的基本紀律——訓練與評估必須用不同數據,否則無從得知模型是學到規律還是背了答案。
模型一:支援向量機回歸
首個上場的是支援向量機的回歸版本 SVR,由 sklearn 匯入,核函數選線性核(linear kernel),即不做非線性變換。流程是標準三步:fit 擬合訓練集、predict 分別預測訓練集與測試集,再以均方根誤差評分:
原片結果:訓練集 RMSE 約 0.040,測試集 RMSE 約 0.123。講者指出訓練誤差低於測試誤差是典型現象——模型對見過的數據自然更準,兩者的差距正是判斷擬合程度的初步線索,若訓練誤差極低而測試誤差極高,便要警惕過度擬合。
SVR 訓練程式碼與 RMSE 輸出,下方開始定義評分函數。截圖出自原片(Liu Peng)
評分函數:由預測價差到終值回報
為公平比較不同模型,講者把「模型 → 回測績效」包裝成單一評分函數:傳入任何訓練好的模型,輸出策略的終值回報(terminal return)。函數開首以 if-else 處理介面差異——sklearn 模型直接呼叫 predict;PyTorch 神經網絡則要將輸入轉成張量、呼叫模型本身(底層執行 forward),再 detach 轉回 NumPy 陣列。
取得測試集的預測價差後,以其均值與標準差將實際價差標準化,得出 Z 分數:
$$z_t = \frac{s_t - \bar{\hat{s}}}{\sigma_{\hat{s}}}$$之後的邏輯與第 29 講的實作課完全相同:Z 分數穿越入場門檻即開倉(一腿造好、一腿造淡),回落至離場門檻內即平倉,兩腿回報相加得策略回報,期末輸出終值回報。換言之,整個 Lab 唯一的改動,是把「價差中樞」的來源由滾動窗口統計換成機器學習預測,其餘回測骨架原封不動。SVM 模型的終值回報約 1.11,作為後續模型的比較基準。
模型二:隨機森林回歸
第二個模型是隨機森林回歸(Random Forest Regressor),設定 100 棵決策樹(n_estimators=100)。流程依樣畫葫蘆:擬合、預測、計算 RMSE。原片結果:訓練集 RMSE 約 0.0056,測試集 RMSE 約 0.073,兩者都明顯低於 SVM——單看預測精度,隨機森林勝出。
但講者隨即點出本 Lab 最重要的觀察:預測更準,不保證交易更賺。評分函數給出的終值回報約 0.91,反而低於 SVM 的 1.11。預測精度與交易績效之間並無必然關係,這是機器學習應用於交易時最容易誤判的一環。
模型三:PyTorch 前饋神經網絡
壓軸是神經網絡,以 PyTorch 實作。先把特徵與目標轉成張量(tensor)格式,再定義網絡架構。類別分兩部分:初始化函數規定各層規格,forward 函數規定資訊流向。架構為三層全連接網絡:
- 輸入層 5 個節點,對應五個特徵
- 第一隱藏層 64 個節點,第二隱藏層 32 個節點——相鄰兩層的輸出與輸入維度必須吻合才能相接
- 輸出層 1 個節點,因為預測目標只有價差一個數值
每層之間以 ReLU 作激活函數。forward 的寫法是:輸入經第一線性層、ReLU、第二線性層、ReLU、第三線性層後輸出。每個線性層本質上是仿射變換 $y = Wx + b$,權重矩陣 $W$ 與偏置向量 $b$ 就是可訓練參數。
以 torchsummary 檢視,全網絡約 2,500 個參數:第一層 $5 \times 64 + 64 = 384$,第二層 \$64 \times 32 + 32 = 2{,}080$,輸出層 \$32 \times 1 + 1 = 33$。講者特別說明,激活函數只做非線性變換,不增減權重數目,故沒有參數。
forward 函數與 torchsummary 的架構摘要。截圖出自原片(Liu Peng)
訓練迴圈與結果解讀
損失函數用均方誤差(MSE),優化器用 Adam,學習率 0.001。講者形容 Adam 是隨機梯度下降的進階版,在現代神經網絡中廣泛使用。訓練是迭代過程,共跑 100 個 epoch,每輪五個步驟:
- 清零梯度:梯度下降會累積歷史梯度,每輪開始必先清走
- 前向傳播:將訓練輸入送入網絡,得出預測輸出
- 計算損失:比較輸出與目標,得出 MSE
- 反向傳播:由損失出發,靠 PyTorch 的 autograd 自動計算各參數梯度
- 更新權重:優化器沿令損失下降的方向調整權重
訓練完成後同樣計算訓練與測試 RMSE,再交評分函數算終值回報。至此三個模型的流程完全對齊:同一份數據、同五個特徵、同一個評分函數,唯一分別是預測價差的模型。講者總結時再三強調:不能單憑這次結果斷言哪個模型較好——由預測價差到終值回報是兩階段過程,中間還有訊號生成、門檻設定與持倉邏輯,環節互相影響,預測能力強的模型最終回報未必更高。本 Lab 的價值在於展示機器學習如何嵌入策略流程的其中一環,而非選出「贏家」。
Adam 優化器設定與訓練迴圈五部曲。截圖出自原片(Liu Peng)
🙏 覺得內容有用?本站所有內容免費提供,使用推薦碼開戶就是支持我們繼續營運的最大鼓勵:
ZA Bank 邀請碼 P20923
—— 你享 HKD 2,000 迎新獎賞,本站獲得營運支持。
立即開戶 →
(聯盟連結|投資涉及風險,受條款及細則約束,此資料僅可於香港境內分發)
欣利克的看法
- 釐清「預測準」與「賺到錢」的鴻溝:本 Lab 最值得記住的實驗結果,是隨機森林的預測誤差明顯低於 SVM,終值回報卻更低。原因是回歸模型對整段價差「平均而言」更準,但交易只在乎價差偏離極端時的方向是否判對。兩者優化的目標函數不同,結果自然可以背馳。
- 常見誤區:把測試集 RMSE 當成策略績效:不少初學者見到模型樣本外誤差低,便誤以為策略可行。本 Lab 的設計正好示範正確做法——預測能力只是一個輸入,必須再經訊號生成與回測這第二層漏斗,才知道對績效的實際貢獻。
- 80/20 時序劃分只是起點:本課按時間順序切分訓練與測試集,方向正確,但單一切分點的結果受該段市況影響甚大。更嚴謹的做法是滾動窗口或 walk-forward 驗證,多次更換測試區間,結論才站得住腳。
- 結果的時效與規模限制:原片實驗只用 2022 年一年、兩隻股票的日線數據,約二百多個樣本,且未計交易成本與滑價。這是教學示範的合理簡化,但任何模型間的勝負都不應視為普遍結論,更不構成任何買賣依據。
名詞解釋
- 支援向量機 Support Vector Machine:以最大間隔超平面劃分數據的模型,回歸版本 SVR 是本 Lab 首個模型
- 隨機森林 Random Forest:以多棵決策樹投票的集成模型,本 Lab 預測最準但回報不敵 SVM
- 神經網絡 Neural Network:多層線性變換加非線性激活的函數逼近器,本 Lab 以 PyTorch 實作
- 特徵工程 Feature Engineering:由原始數據構建模型輸入變量的工序,本 Lab 造了五個特徵
- 均方根誤差 Root Mean Square Error:預測誤差平方平均再開方的指標,本 Lab 的模型評分標準
- Adam 優化器 Adaptive Moment Estimation:具自適應學習率的梯度下降變體,訓練神經網絡的主流選擇
- ReLU 激活函數 Rectified Linear Unit:正數原值通過、負數歸零的激活函數,為網絡引入非線性
- Z 分數 Z-Score:價差偏離中樞的標準化倍數,交易訊號的依據
- 對數回報 Log Return:對數價格的一階差分,本 Lab 五個特徵中的兩個
- 過度擬合 Overfitting:模型遷就訓練數據而失效於樣本外的風險,訓練誤差遠低於測試誤差是警號
常見問題 FAQ
為甚麼預測更準的模型,交易回報反而更低?
因為兩者優化的目標不同。RMSE 衡量的是整段價差的平均預測偏差,而配對交易只在 Z 分數觸及門檻的少數時點行動,關鍵是那些極端位置的方向判斷是否正確。一個整體更準的模型,完全可能在關鍵時點上判錯方向。原片的隨機森林正是這樣:測試 RMSE 最低,終值回報卻輸給 SVM。
神經網絡的 2,500 個參數是怎樣數出來的?
每個全連接層的參數量是「輸入維度 × 輸出維度+輸出維度」,後者是偏置項。本 Lab 的網絡:第一層 $5 \times 64 + 64 = 384$,第二層 \$64 \times 32 + 32 = 2{,}080$,輸出層 \$32 \times 1 + 1 = 33$,合計 2,497,約 2,500。激活函數只做固定的非線性變換,不含可訓練參數。
訓練迴圈每輪為甚麼要先清零梯度?
PyTorch 預設會把每次反向傳播算出的梯度累加到參數的梯度屬性上,這是為配合梯度累積等進階技巧而設。若不清零,上一輪的梯度會混入本輪更新,權重便會沿錯誤方向修正。因此每個 epoch 的標準起手式是 optimizer.zero_grad(),再前向傳播、計算損失、反向傳播、更新。
這三個模型的比較結果可以照搬到其他股票對嗎?
不可以。原片只用 2022 年一年、單一股票對的日線數據示範,樣本約二百多個,未計交易成本,訓練測試集亦只有單一切分點。模型間的勝負很可能是該段數據的偶然結果。原片的目的在於展示機器學習嵌入策略流程的方法,而非推薦任何模型或參數,內容亦不構成投資建議。
原影片
本文整理自以下影片,版權屬原創作者所有,建議配合原片觀看: