💹

お前のSignalはもう死んでいる

2021/12/17に公開

この記事はNumerai Advent Calendar 2021の18日目の記事です。

https://twitter.com/kk1110tt/status/1455088352248492039?s=20

この記事について

ファイアーエムブレム風花雪月の好きなキャラについて語る記事です。

うそですすみません。数多くあるNumerai Signalsに関する記事の1つです。

Signalsの評価方法

自分のアプローチについてお話しする前にですけど、みなさんご存知ですか、Signalsの評価方法ってTournamentと異なるんです。

Signalsでは、uploadした予測値はNumeraiが保有しているsignalsで直交化されたのち、corrが計算されます。

そのため、もしも貴方がリアルマーケットで稼げる最強の指標を持っていたとしても、その指標が有名で既にNumeraiが持っているとしたら、その指標に基づく予測値を提出しても、直交化されてしまうので何も残りません。

提出した時点で、お前のSignalはもう死んでいるんです(タイトル回収)。

Docsに書かれている通り、Targetも20日リターンではありますが、なんらかの直交化処理がされています。

ここに書かれている通り、バックテストで最強でもLiveで無双できるかというとそういうわけではないんですね。ここがTournamentと違って、Signalsの難しいところです。要は、

高いCORRを得るには、Numeraiが保有しておらず、かつtargetと相関するSignalを作らないといけない

んです。

ここは勘違いしやすいところなのですが、Signalsはよくあるダメダメ株価予測コンペのような、生リターン予測ゲーではないのです。

Numeraiが持っていないくらいオリジナリティがあり、かつtargetと相関するようなクリエイティブなSignalを作る (無理) ゲーなんです。

これでビビってはいけません。今までは評価指標の1つであるCORRに限った話です。

MMC (Meta Model Contribution)についてはCORRよりさらに厳しく、

Numeraiが保有するsignalに加えNumerai Signalsに提出された他の全てのstaked signalによって直交化(!?)されたのち、CORRが計算されたものになります。

すなわち、Numeraiも持っておらず、他のSignals参加者も持っていないけど、targetと相関するような、至高の領域に近いSignalを練り上げないと、MMCスコアは上がらないということです。

そのため、もし貴方がNumeraiが持っていないけどTargetと相関するような極上signalを練り上げたとしても、それがよくあるアプローチで他の参加者が同じsignalを提出していたとしたら、

提出した時点で、お前のSignalはもう死んでいるんです(タイトル回収)。

↑公式Docsでも、MMCがずっと高いsignalはスゲーって書いてありますね。

Signalsで稼ぐためには

いやこんな無理ゲーw キツいっすww

って自分も最初は思っていましたが、今の時代は大変恵まれていまして、ちょっと勉強すれば機械学習が誰でも使える時代です。

市場データをよく見て特徴量を考えたり、よくトレーディングで使われるテクニカル指標を集めてきたりして、与えられた(謎)Targetを予測する機械学習モデルを作るだけで、モデルが中で勝手に指標同士をいい感じに組み合わせて、Targetと相関するような予測値を作ってくれます。

そのため、結局のところ

  • (自分で集めてきた市場データの)探索的データ分析
  • 特徴量エンジニアリング
  • 機械学習モデリング

で周りと差をつけるという、結果として従来の機械学習コンペと同じ取り組みをすることになります。

機械学習なしで天上天下唯我独尊の指標を作れれば、もちろんそれでもいいと思いますし、それができたら歴史に名が刻めることでしょう笑

いいのできたらこっそり教えてください!←

自分のモデルの概要

それでは折角なので、2021年12月17日現在、CORRランク1位の自分のモデル(アンナモデルと呼ばせていただきます)について話します。

自分が公開しているStarter([NumeraiSignals] Starter for Beginners)があるのですが、これ(エーデルガルトモデルと呼ばせていただきます)に準ずるものになっています。

実のところ、このstarterだけで結構強かったです。まだまだSignalsがブルーオーシャンだからだと思いますが、3か月リターンで1位になったりしました。最近この子が強いのがバレてきたので、多くの人が使っていくにつれ今後MMCはどんどん下がっていくでしょう(哀

https://twitter.com/kk1110tt/status/1462329724181508096?s=20

アンナモデルは、こちらのエーデルガルトモデルとの差分がいくつかあります。

使用データ

使用している株価データは同一です。
無料で使えるYahoo! Finance's APIで取得してきたOHLCVデータを使っています。

無料な分データのノイズが大きいですが、自分は毎日データを取得し、以前に取得したデータに欠損値があれば埋める、という処理をしてなるべく綺麗な株価データを作ろうとしています。

こちらのデータはkaggle dataset上で公開しています。

https://www.kaggle.com/code1110/yfinance-stock-price-data-for-numerai-signals

正直、有料でも全世界株のキレイなOHLCVデータを網羅したサービスがあればそちらに移ってもいいかなと思ってますが、現在numerai tickerとのmappingが提供されているのがyahooとbloombergしかないため、今のところはyahooを使っています。

モデル

エーデルガルトモデルではXGBoostを使用していましたが、アンナモデルは線形モデルです

https://scikit-learn.org/stable/modules/generated/sklearn.linear_model.BayesianRidge.html

シングルモデルです🌟

特徴量

特徴量エンジニアリングの基本

エーデルガルトモデルで使用している特徴量は使っています。Notebookにある通り、ここで使用している特徴量は株式分析チュートリアル | 日本取引所グループと同様です。まんまパクリだと良くないかなと思って、RSIとPPO(名前がMACDになっているが実態はPPO)も特徴量に追加しています。

この時点で12個しか特徴量はありませんが、ここに自分が思いついた特徴量を30個ほど追加しています。まぁ、自分が思いついたというか、JQuants上位解法のコード↓をパクって参考にしています。

https://www.jpx.co.jp/corporate/news/news-releases/0010/20210813-01.html

ただ、GBDTモデルのfeature importanceを見る限り、自分が追加したものでキラー特徴量のようなものなさそうです。

starterにもありますが、大事なのは

  • リークしていない特徴量を使うこと:未来予測タスクなので、未来の情報を特徴量に含まないようにしないといけません
  • 定常性のある特徴量を使うこと:RSIのように、銘柄、時期によらず取りうる値が一定の範囲に収まる特徴量を使うこと

は、特徴量エンジニアリングするときに気を付ける必要があります。自分は複数の国にまたがる5,000弱の銘柄を一気にモデルに学習させているため、モデルからすると、銘柄、時期によらず比較可能な特徴量でなければ上手く学習することができません。

https://twitter.com/kk1110tt/status/1426484585550925827?s=20

RSIとかもいい特徴量の例ですね。どの銘柄でもいつの時期でも、必ず値が0 ~ 100に収まります。

TA-Lib使うべき?

TA-Libを使用して一気に金融テクニカル特徴量を自動生成するのもありだと思いますが、自分は環境構築に失敗したテクニカル分析なにもわからないマンのため使用していません。自分の理解不足でリークしてたり、定常性のない特徴量を入れてしまうのが怖いからです。

テクニカル分析完全に理解したマンなら全然アリだと思います。そうでなくても、Richmanbtcさんの旧ML botチュートリアルでもあったように、時系列でadversarial validationを行って、時期によって大きく値が異なる特徴量を除くのも手です。

注意点

もちろん機械学習でポンッ!ではなく、いくつか工夫したところはあります。

外れ値

エーデルガルトモデルでも使用している移動平均との乖離系特徴量ですが、多くはある一定の範囲で収まるものの、データのノイズ等でたまにえぐい外れ値が発生したりします。GBDTは特徴量内の相対的な大小関係のみを利用するため別に大丈夫なのですが、NNや線形モデルを使う際は外れ値に値が引っ張られないようになんとかしないといけませぬ。

参考になるのはNumerai Tournamentです。

こちらでは匿名特徴量が与えられ、全ての特徴量は0, 1, 2, 3, 4の5通りの値を取ります。これは、era内で特徴量を銘柄間でランク化し、binを取っていると考えられます。こうすることで外れ値の影響なく、全ての銘柄、全ての時間において、任意の特徴量が0 ~ 4の間を取ります。

自分も数値特徴量は同様の処理をしています(同一friday_date内でのランク化)。こうすることで外れ値に引っ張られることなく、特徴量は必ずリークしておらず、定常性があるものになるため、安全にNNや線形モデルを運用できます。同じことを鳩さんもしてますね。

https://zenn.dev/ageonsen/articles/3575c686adb53f

激強kagglerのnyanpさんも、Optiverボラ予測コンペ解法解説で同様の処理を行っていることに言及しています。

https://www.kaggle.com/c/optiver-realized-volatility-prediction/discussion/274970

アンナもこれで安心です。

使っていない特徴量

OHLCVのデータがあるものの、少なくとも使用しているyfinanceのデータだとadjusted closeとvolumeにはかなりアヤシイ数字が含まれています。そのため、それ以外の価格情報を使っています。

逆に、価格情報以外の特徴量は使用していません。

Volume系特徴量もちょっと触りましたが、特にyahooではVolumeデータの欠損が多いためか上手くいきませんでした(価格情報のみの方が精度が良かった)。

カテゴリ変数(銘柄名、セクター情報、国名など)も有力な特徴量候補ですが、こういったカテゴリ変数は軽い気持ちでモデルに投げるとめっさoverfitするため、アンナモデルでは一切使っていません。

GBDTを使うときには特に注意が必要で、LGBやCatBoostに投げるとtarget encoding(的なこと)が行われ、予測値が過去の実績に大きく引っ張られるので、feature fractionを下げる、LGBでextra_treesをTrueにする、などoverfitしないようにする工夫がいるかもです。

Validation Strategy

Numeraiから提供されるtargetデータでは

  • train: 20030131 ~ 20121228
  • validation: 20130104 ~

とtime-series splitでtrainとvalidationが別れていますが、エーデルガルトモデルと同様そのまま使っています (trainとvalidationの境目に20日ターゲットの被りによる明らかなリークがあるので、purgeが必要なんだろうなとは思ってますが、やってません...)。

Advent Calendar6日目のうしぐまさんの記事にあるようにvalidation strategyを工夫した方がいいスコアが取れるであろうことはわかっているのですが、
Numeraiが提供しているDiagnosticsが非常にカッケーので、モデル間でdiagnosticsが比較できるようにそのままです。

↓Diagnostics

自分としては(運営から与えられた訓練、検証期間だとtargetが20日であることから境目で必ずリークするため)backtestのAPYはあまり重視しておらず、sanity checkとして使っています。

Diagnositcsが良すぎる、悪すぎる、というときは、リークやデータのノイズなどなんらかのバグを疑うことができます。

実際に提出する予測値は、validation期間も含めtargetが利用できる全期間で訓練したものも使います。

↓にあるように、リークのないvalidation strategyを組むのが本来は正しいように思います。今後はそうするかもです。

https://zenn.dev/ymd/articles/fd08fb46bc868c

ただSignalsは多少リークがあっても、出来上がったsignalにオリジナリティがあり、かつTargetとそこそこ相関していれば許される優しい世界だと思っています。

実際の株式のトレーディングではここをちゃんとやらないと爆損するでしょう。

Target

Targetは、現在"target_20d", "target_4d"が提供されており、評価に使われるのは前者のみです。

とりあえずエーデルガルトモデルのように"target_20d"のみ予測しに行ってもいいのですが、オリジナリティを求められるのがSignalsですので、特徴量だけではなく、Targetもエンジニアリングした方がユニークな予測値が作れるのではないでしょうか?

実際、Numerai fireside chatでリチャードCEOは、「Signalsのtarget自体に意味はない」という趣旨の発言をしていたような記憶があります。実際、Tournamentではスコアリングされないtargetが複数提供されてますよね。

終わりに

2021年12月の時点では、(自分でもびっくりの)好成績がSignalsで出せています。自分自身は昔から数字に弱く、クオンツとかでは残念ながらないのですが、JQuantsのチュートリアルから非常に多くを学ばせてもらいました。Alpacaさんありがとうございます。

今後は競争が増えてJQuantsのチュートリアルベースの自分のモデルでは勝てなくなっていくことが予想されますが、その頃にはまたJQuants的な、新しいSignalsで活かせそうなコンペが出てきてですね、新たな知見を吸収して(結果として稼げて)いけたら理想ですね。

Signalsはかなりユニークなゲームですよね。

ぜひみなさんも手塩にかけて育てたユニークなSignalで周りの参加者を直交化するバトル、参戦してみてはいかがでしょうか。

引用

https://docs.numer.ai/numerai-signals/signals-overview

https://japanexchangegroup.github.io/J-Quants-Tutorial/

https://www.jpx.co.jp/corporate/news/news-releases/0010/20210813-01.html

https://zenn.dev/ymd/articles/fd08fb46bc868c

Discussion