AIで回収率110%を目指す検証(第40回)|19年分・240万頭を掘って、天井は95.6%でした

19年分・240万頭を掘って、天井は95.6%でした 実験ログ

前回(第38回)は「的中率を3倍にしても回収率は動かなかった」という話でした。
今回は、その続きです。動かなかった理由が分かり、動く場所も見つかり、それでも足りませんでした。


前回の宿題

前回わかったのは、オッズから作った指標は、どう料理しても回収率が動かないということでした。

理由は考えてみれば当たり前で、オッズから作った量には、市場がすでに知っている情報しか入っていないからです。10等分しても、安定した馬だけ選んでも、締切直前の動きを見ても、全部平らでした。

だとすれば、オッズの外を見るしかありません。


オッズを使わない条件を、19年分で探す

ここで、私は自分の思い込みをひとつ壊しました。

数日前に「もう測れる期間が残っていない」と書いたのですが、それはオッズの記録に限った話でした。着順と払戻の記録は 2007年から、約29万レース分あります。オッズを使わない条件なら、私が言っていた量の20倍以上が使えたのです。

手順はこうしました。

探索期  2007〜2020(約184万頭)  ← ここで条件を探す
検証期  2021〜2024(約54万頭)   ← 探索期で決めた条件を、1度だけ当てる

条件は探索期の数字だけを見て機械的に決めます。検証期の数字を見てから条件を選ぶと、検証が検証でなくなるからです。この分け方を測る前に決めておくのが肝心で、後から決めると必ず自分に都合よく切ってしまいます。

まず、出走表にそのまま載っている項目を11本試しました。7本が、探索期と検証期で同じ向きに出ました。基準線(全馬に賭けたときの回収率)はおよそ70%で、そこから +2〜3pt ほど動きます。

ついでに、使えない項目も確定しました。ある2項目は、地方競馬ではほぼ全馬が同じ値で、そもそも区別になりません。「まだ試していない列がある」と言い続けないために、これは価値のある結果です。


「そのまま載っている値」より「そこから作った値」が強い

ここが今回のいちばんの発見です。

出走表の項目をそのまま使うと +2〜3pt でした。ところが、前走と比べて作った量にすると、はっきり強くなりました。

作った量 探索期 検証期
前走で先行していたか(4角の位置) +6.9 +5.3
前走の着順 +6.1 +5.2
前走より距離が短くなったか +4.2 +4.5

生の値の倍近く効きます。

逆に、再現しなかったものも記録しておきます。出走間隔は、探索期で −3.7 だった帯が検証期では +2.4 と符号が反転しました。こういうものは、探索期の数字がどれだけ良くても捨てます。片方だけで良く見えるものは、たいてい偶然です。


重ねると、上がり方が加速した

条件を9本そろえて、該当した本数ごとに回収率を出しました。

該当本数 n 複勝回収率 95%区間
0本 48,245 63.0% [61.3, 65.0]
2本 156,288 70.5% [69.5, 71.3]
4本 45,054 78.2% [77.1, 79.3]
5本 11,768 82.6% [80.5, 84.5]
6本 1,835 87.6% [83.1, 92.5]
7本 147 93.1% [80.5, 106.9]

きれいに単調です。探索期でも同じ形になりました。

そして予想外だったのが、1本あたりの効きが増えていくことでした。

+3.6 → +3.9 → +3.9 → +3.8 → +4.4 → +5.0 → +5.5

普通、こういう条件を重ねると効きは減っていきます(似たようなものを何度も数えることになるので)。増えているということは、それぞれが別の情報を持っているということです。


最後に、価格と掛け合わせた

ここまでオッズを一度も使っていません。最後に単勝オッズの帯で切りました。

条件 オッズ帯 n 複勝回収率 95%区間
5本以上 〜2.0倍 3,019 94.1% [92.8, 95.6]
5本以上 2.0-4.0倍 3,383 87.5% [85.0, 89.6]
3-4本 〜2.0倍 17,041 91.5% [90.9, 92.0]
0-2本 〜2.0倍 7,926 91.8% [90.8, 92.9]
0-2本 60倍〜 116,727 50.7% [48.8, 52.3]

読み取れることは2つあります。

主役は価格です。どの条件群でも、人気馬が最も良く、大穴が最も悪い。差は40pt以上あります。

条件は、その上に乗ります。同じ「〜2.0倍」の中で、条件0-2本の91.8%に対して5本以上は94.1%。+2.3pt。これは小さく見えますが、価格が織り込んでいない情報を条件が持っているという意味で、無視できない差です。

それでも、上限は95.6%でした。

3群×7帯=21通り、探索期と検証期の両方で、100%を超える確率はすべて0.0%。


届かなかった、という記録

正直に書きます。この方向は、ここで頭打ちです。

条件を増やせば上がるのは分かっています。ただ、1本増やすたびに該当する馬が約6分の1に減ります。9本中6本該当が4年で1,835頭(1日1.3頭)、7本で147頭、8本で6頭。110%に必要な本数を積む前に、買える馬がいなくなります。

「もっと探せば見つかるのでは」と思われるかもしれません。私もそう思っています。ただ、今日いちばん価値があったのは、探した場所を潰したことです。次に同じ場所を掘らずに済みます。


おまけ:自分のコードで4回転んだ日

同じ日の記録として残しておきます。測定そのものより、測定を回す作業でつまずいた回数のほうが多い日でした。

  1. SQL に値のリストを渡す方法を間違えて、11本の測定が全滅。
  2. 直した際、SQLのコメントの中に書いた記号が、変数として解釈されてまた11本全滅。コメントの中まで解釈されるとは思っていませんでした。
  3. ファイル作成・文法チェック・実行を1行に詰め込んで、引用符が閉じずに起動失敗。
  4. データ絞り込みの条件を書いていたのに、その絞り込みより先に型変換が走ってエラー。データベースは「WHERE を先に評価する」とは約束していないのです。

どれも、11本全滅のように派手に失敗したので、すぐ気づけました。1本だけ静かに間違った値を出していたら、たぶん今も気づいていません。壊れるなら派手に壊れてほしい、というのは道具を作るときの本音です。

もうひとつ反省を。いちばん知りたかったグループを、計算の最後に置いていました。大きいグループから順に処理していたので、答えが出るまで30分近く待つことになりました。知りたい順に計算する、それだけのことです。


この記事の数字について: 探索期と検証期を測定前に分け、条件は探索期のみで機械的に選び、検証期で1度だけ当てています。それでも複数の軸を見ている以上、多重比較の影響は残ります。良い数字が出ていないので実害はありませんが、もしここから何かを使うなら、改めて前向きに登録してから測り直します。当ブログは、届かなかった記録もそのまま残す方針です。

掘り尽くした畑にも、掘った跡という収穫は残る。

この後の実験は、地方競馬に舞台を移しています。

地方競馬の市場について測った事実は連載「地方競馬の解体新書」に、当方の価格モデルによる買い目の配信(準備中)は先行案内のページにまとめています。