風のライオン―後篇―

sinonomeのアバター



チャートに引かれた一本の線を、少し上へ移した。価格や日時を指定して位置を合わせたのではない。週明けの窓を含む戻り高値の扱いを直した結果だった。


検証用インジの結果をざっと眺めていて、ある戻り高値の線が目に留まった。前の取引日にできた日足実体の上端を、次の取引日の始値が上回っている場面だ。私がSラインとして見ていたのは、その始値の側だった。ところがプログラムは、一つ前の日足実体を基準に線を引いていた。私の定義とは明らかに食い違っている。

そこで、どの価格を採るのかと、その価格を採ってよい根拠がいつ揃うのかを、あらためて切り分けて整理した。直した線は、意図した位置に出た。それでも確認は終わらない。その日の日足終値をまだ知らないはずの時点で、終値を使っていないか。関係のないSラインまで動いていないか。線の価格が変わったことで、その後の構造否定を判定する時刻はどうなるのか。このSNF開発を始める以前には考えもしないことを考えていた。画面の上では数pipsの差にすぎなくても、システムの中では、価格も時刻も構造の所属も履歴の扱いも、すべてつながっている。

前篇では、私が相場をどう見ているかを書いた。構造否定を起点にして、A0とAsを区別し、ABCとFEで波の整合と伸長を追う。未来を当てる装置ではなく、自分が何を根拠にどの構造を見ているのかを明らかにするための観測軸だった。後篇では、その見方がソフトウェアになっていく過程を書くことにした。動く部品はすでにあり、実際のチャートで確かめられた挙動も増えた。ただ、部品をつないで、観測システム全体として何を保証できるのかを確かめる仕事は残っている。今のSNF開発は、ちょうどその境目にいる。

一本の線を、判断の履歴にする

Sラインの抽出を調べるために、SLineLabという独立した検証用プログラムを作った。実際の価格データを読み、戻りや押しの候補を抽出し、価格の根拠と確定時点を記録しながら線を描く。私が見ているSとプログラムが抽出したSを突き合わせて、ずれた箇所を一つずつ直してきた。現在はV0.2.8を基準にして、提示したチャート範囲での描画を確認できている。ひとまず抽出の基準にできるところまで来た。

やってみて分かったのは、「戻り高値」という短い言葉にいくつもの仕事が入っていることだった。どの安値からの戻りなのか。主となる構造に属する戻りなのか、内部の小さな戻りなのか。反発した実体が一本だけでも、ほかの条件が揃えば戻りとして扱うのか。対応する上位足の実体を優先するなら、その上位足のどこまでの情報が使えるのか。裁量では一度に見ていたものを、プログラムでは順番のある判断に分けなければならない。

線の位置が合うだけでも足りない。完成したチャートを見て正しい場所に線を置けたとしても、当時その線を出せなかったのなら、リアルタイムの観測器としては別物になる。Sの価格を決める根拠と、そのSを確定できる時点は、別々に残す必要がある。前篇に「過去を完成した未来から書き換えない」と書いたが、実装ではこれが「まだ使えない足の情報を参照しない」という制約になる。
そのため、計算の部分と、MT5での入力・描画の部分は分けてある。Sの価格選択や構造の切替を行う共有の計算コードを、チャートから離れた環境でも検査できるようにして、保存した価格データで再生する。変更した規則が狙った例に効いたかどうかに加えて、前から合っていた例を壊していないかも比べる。チャートを眺める確認と、同じ入力を流して出力を照合する確認は、同じ実装を別の角度から調べる作業になった。

表示にも責任の境界を引いた。近くに線が増えると、過去の線をまとめて表示を整理したくなる。しかしその都合で、現在の構造否定に使うSの価格まで動かすわけにはいかない。見やすくするための代表価格と、突破判定に使う元の価格は別物だ。表示を切り替えたら観測結果まで変わるようでは、表示機能が相場の定義に入り込んでしまう。

SLineLabから得たのは、線を引く機能だけではなかった。どの価格を、どの根拠から、いつ採用したのか。その判断の履歴を取り出す入口にもなった。ただ、Labの中で候補を抽出できることと、その候補がSNF本体の正式な対象として接続されていることは、まだ同じではない。今後は、抽出結果をCore側の対象、版、証拠、時点に対応付けていく。

一つの相場を、別の責任で扱う

開発を始めたころに想像していたEAは、条件と注文が近い場所にあるものだった。Sを突破したらW1とし、その後の調整を待って、W3がFE100へ進むところを取る。必要な条件を十分に書けば、裁量でやっていた判断を再現できると思っていた。今もこの売買の骨格を捨てたわけではない。変わったのは、骨格を支える部分の作り方だ。

ある入口を直したら、Sラインの定義まで変わってしまった、では困る。別の利確方法を試すために、観測の履歴を作り直したくもない。戦略をいくら増やしても、土台になる市場の観測は共通であってほしい。そこで、売買をする前に市場を記述する部分を独立させた。

SNF Observerの役割は、採用した観測軸から何が起きたかを記録することだ。その内側では、価格や境界を調べる処理と、証拠や評価に基づいて現在の状態を保持する処理を分けている。観測結果を受け取った売買側では、戦略が「どの波のどこまでを狙うか」を決め、入口が「どんな形で参加するか」を判断する。取引管理は保有と撤退の規則を適用し、執行は注文を送って結果を照合する。
たとえば、W3のFE100までを狙う戦略と、20EMAへの復帰で参加する入口は別のものだ。同じ波に別の入口から参加することもあれば、同じ入口を別の目標と組み合わせることもある。入口で20EMA上の終値確定を条件にしたからといって、保有中も毎足その条件を満たし続ける必要があるとは限らない。入る理由と、持ち続ける理由は混ぜない。

W3・FE100狙いの買い側基本形では、参加時に採用したCを、撤退判断の基準として固定している。観測側があとからBやCを更新しても、すでに始めた取引のCは自動では付け替えない。観測器は新しい情報を受けて先へ進むが、その取引が引き受けた前提は別に残る。取引側の前提が崩れたことを、そのままSNF全体の観測終了にすることもしない。

観測器の内部も同じ考え方で作る必要がある。内部の小さな構造が否定されても、親にあたる大きな構造まで否定されたとは限らない。逆に、親側で変化が起きたからといって、内部で進んでいる波の履歴を消してよいわけでもない。同じ市場点を参照することと、同じ判断や寿命を共有することは違う。前篇で書いた重なる階層は、実装では、状態の変更が「どの構造についてのものか」を限定する要求になる。

S、Range、MA、時間の測定にも、それぞれの担当がある。ただ、担当を分けるたびに各部が独自の高値や安値を作り直していたら、別々の相場を見始めてしまう。共有する市場点や証拠は共通の参照で受け取り、そこから何を判断するかだけを分ける。責任は分けたうえで、情報は共通にしておく。
その接続のために整えているのが、共通の観測・証拠契約だ。送り手が何を渡し、受け手がどこまでを確認済みとして扱ってよいかを決めた約束である。価格だけでなく、対象、版、規則、設定、出典、利用可能になった時点、不足している証拠まで対応付ける。部品を分けただけでは安全にならない。この受け渡しが明確になって、はじめて分けた意味が出てくる。

観測やトレードを再現しようと思い立った当初は、こんな領域に入るとは想像もしていなかった。ここまで来ると、もはやトレード論というよりシステム論だ。

レンジを、一つのフラグにしない

Sラインと並行して、長く整理を続けてきたのがRangeの定義だ。最初は、何往復すればレンジと呼べるのかを決める話だと思っていた。実際には、その前後の状態を定義するほうが、はるかに多くの判断を必要とした。

まず、どの山と谷から仮の帯を作るのか。価格が境界に何度も触れていても、それは同じ試行の途中なのか、独立した切返しが増えたのか。帯の内側に小さな山谷ができたら、元の帯を縮めてよいのか。それとも元の帯は維持して、小さな帯を別に観測するのか。ここを区別しなければ、同じ値動きから都合よく回数や境界を作れてしまう。

現在の初期仕様では、扱う対象と価格型を限定したうえで、仮帯の設定、切返しの確認と算入、正式認定、境界の供給、終了と訂正を別々の段階にしている。回数の条件はあるが、回数だけで認定はしない。同じ帯・同じスケールに属すること、同じ試行を二重に数えていないこと、必要な証拠が使えること。これらを合わせて判断する。個別の設問への回答と、その後の整合案の確認を経て、初期範囲を実装側に渡す整理がまとまった。ただし、すべての価格型やスケールを定義し終えたわけではない。
特に重要だったのは、レンジが成立したあとの扱いだ。境界を終値が一本突破したことと、そのレンジ構造が終了したことは、同じにしない。突破の事実は記録する。そのあと帯の外でどんな構造ができて、どの条件が揃ったら旧レンジを終了とするのかは、別に判断する。逆に、データが取れなくなったことを、市場がレンジでなくなった証拠にするわけにもいかない。

訂正と終了も違う。あとから根拠を調べ直して、最初の認定が誤りだったと分かることがある。一方、当時は有効に成立していたレンジが、その後の価格推移で役目を終えることもある。前者は過去の認定への訂正で、後者は時間の経過による構造の変化だ。画面上では同じような変化に見える場合でも、同じ履歴として保存してはいけない。
さらに、一度使えなくなった証拠があとから揃ったとき、その切返しをどこへ戻せるのかという問題がある。以前の認定記録が残っていることだけでは、現在も有効だとは言えない。復帰させたい切返しを加えたことでレンジが有効になり、その有効なレンジを根拠に切返しの復帰を認めるのでは、判断が循環する。復帰させる対象と、それを受け入れる現在の状態は、分けて確かめなければならない。

ここまで整理すると、「レンジか、レンジでないか」の一つのフラグには収まらなくなる。候補として評価中なのか。既知の条件に適合しなかったのか。必要な証拠がないのか。そもそも初期版では扱わない型なのか。どれも次にやる処理が違う。未対応の型を「確認済みの非レンジ」に分類してしまえば、プログラムは自分が知らない範囲を見失う。
目的は、定義を増やし続けることではない。今の範囲で判断できるもの、入力が揃えば判断できるもの、別の定義が必要なものを分けることだ。初期範囲の整理を一区切りにできたのも、未知の領域をすべて解いたからではなく、その扱い方を決められたからだった。

「同じ値」と「同じ時点」の間

実データに近づくほど重くなったのが、時刻と証拠の問題だ。

チャートを見ているときは、価格とMAが同じ画面に描かれている。それだけで、同じ瞬間の関係を見ているような気になる。しかしプログラムに渡すなら、どの価格更新に対応するMAなのかを確かめなければならない。過去足の最終EMAがあることと、その足が始まった瞬間の価格とEMAの関係が分かることは、別の話だ。

これを確かめるために、H1とH4の足が切り替わる境界を含めて、30分間の採取を行った。価格更新とMAの標本を保存し、足の切替も取得できた。ただ、ライブ側で新しい足を最初に読めた標本は、その足の最初の価格更新ではなく、二つ目の更新に対応していた。採取が正常に終わっていても、取り逃した最初の更新時点のEMAを、観測済みとして扱うことはできない。
そこで、保存した価格更新をテスターに流して、再生時の値を調べた。テスター内では、始値の更新に対するEMAと、直前確定EMAを使った計算との数値が対応することを確認できた。しかしこれはテスター内での確認だ。あとから計算結果の対応を確かめられたからといって、当時ライブでその値を受け取っていた証拠にはならない。再生で分かったことと、その場で記録できていたことは、別の知識として残すのだ。

再生の照合では、もう一つ気になる結果が出た。価格、時刻、数量の項目は一致したが、価格更新に付くフラグの一部が一致しなかった。厳密比較は不合格のまま残してある。違いの意味を確かめる前に、フラグを比較対象から外して合格にすることはしない。数値がよく合っていることと、入力経路全体が同じだと確認できることは、ここでも別だった。

こうした作業は、相場理論からずいぶん遠くへ来たように見える。だが実際には、理論の中心に触れている。前篇で私は、観測とは「その時点で使えた証拠から何が見えたか」を残すことだと書いた。この言葉をソフトウェアで守ろうとすると、情報が発生した時刻、受け取った時刻、評価に使えるようになった時刻を、分けて持たなければならなくなる。データが存在するだけでは、過去の判断に使ってよいとは限らない。新しい情報で過去の出来事を確認することはできても、その情報を過去の自分に渡すことはできない。これは、チャート上の波をどう数えるか以前の、検証の時間軸を成り立たせる条件だと思う。

検証できる単位を作る

SNFには、証拠と評価を受け取り、対象の状態や履歴を管理するCoreがすでにある。そこでは、証拠を登録すること、証拠を使って評価すること、認定や再開などの状態変更を実際に行うことを、別の操作にしている。証拠が届いたら、それだけで別の判断まで勝手に変わる、という構成にはしていない。保存した台帳を再生して、過去の時点に未来の証拠が紛れ込まないかも検査してきた。
ただ、Coreの単体検査が通ることと、実際の価格から必要な証拠を正しく作れることは別だ。SLineLabの抽出結果が妥当でも、それを間違った対象や版に結び付ければ、つないだシステムとしては誤りになる。部品ごとの検査に加えて、受け渡しの検査が必要になってきた。

そのための開発用の仕組みとして、Harnessの整備も進めていた。これは相場を判定する本体ではなく、資料や保存データを読んで、出典や内容の一致、不足している情報、比較条件を調べる枠組みだ。毎回その場限りの確認コードを書く代わりに、使える検査を再利用して、前回と何が同じで何が変わったのかを確かめやすくする。V71には、その第一期の還元資料も取り込んである。

ここで「検査を通った」という言葉の意味を、細かく分けている。文書に矛盾がないこと。保存したファイルが同一であること。合成入力に対して規則どおり動くこと。保存した相場の再生で期待どおりの結果になること。実際の端末上で動くこと。そして、市場の観測として妥当であること。この六つはそれぞれ違う。
たとえば、検査用の入力にわざと証拠不足を作って、システムが保留を返したなら、その動作は正しい。市場についての答えはまだ出ていないが、答えを出してはいけない場面で止まる機能は確認できた。逆に、資料のハッシュが一致したことを、相場を正しく認識した実績に数えることはできない。検査件数が多いだけでは、どこまで使えるシステムになったのかは分からない。

最新の統合でも、この区別は保っている。各専門工程で保存された実装や検査結果を取り込んだことと、その統合版で機能試験をあらためて実行したことは、別の出来事だ。現在の統合報告でも、市場受入の工程全体を通過した扱いにはしていない。実装が何もないということではなく、部品ごとの実績をそのまま全体の実績に移していない、ということだ。
検証用の場所を分けておくと、試しただけの規則が、いつの間にか本体の正式な規則に入り込むのを防げる。Labで有望な振る舞いを見つけても、どの範囲に採用するかはあらためて決める。過去に合格したHarnessでも、対象の版や列構成が変われば、そのまま使えるとは限らない。検証する道具自身も、何を対象に確かめたものなのかを持っていなければならない。

AIと、開発を続けるための記憶

これだけの定義と状態を扱うなかで、AIに任せる仕事も変わってきた。

コードを書いてもらうことは、今も大きな部分を占めている。ただ、それだけでは開発の重要な部分を説明したことにならない。実際に多くの時間を使っているのは、私の言葉から判断の条件を取り出すこと、具体例と反例を作ること、以前の採択と衝突しないかを調べること、変更がどの仕様や検査に影響するかを確認することだ。

「この場合は許容する」と私が答えたとき、その許容は何に対してなのか。同じ対象、同じ帯、同じ版であることが前提だったのか。その一例で認めたことを、全時間足に広げてよいのか。AIが文章を整理する途中で前提が抜け落ちると、読みやすくなった文章が、元とは別の規則になってしまう。だから、私が実際に答えたことと、AIが合理的だと考えて提案したことは、分けて保存している。

開発の担当も分けた。本線は統合正本と工程を管理する。Sライン、Range、共通契約、MA・pips、Jev評価、Harnessなどは、それぞれの課題を受け持つ。そこで得たものを、原問と原回答、採択範囲、実装、検査結果、残件とともに本線へ戻す。一つの対話に全部を抱え込まず、必要な原本に戻れる形にして、担当間で意味を受け渡している。
この過程で、開発の記憶をチャットの記憶力だけに任せることはできなくなった。原典、採択台帳、未決事項、現行の適用表、ソースコード、検査入力、期待値、実出力、変更履歴が要る。古い記録も消さない。ただ、古い記録に書かれた「未回答」や「未実施」を、現在の状態に戻してはいけない。過去の全文を残すことと、現在どの判断を使うかを示すことは、別の管理だ。V71でも、旧版の記録を保持したまま、各専門の後続判断を現行の対照表に取り込んでいる。

実際、統合本体の保存が進んでも、単独の案内索引への反映が追いついていない部分が残っている。索引に書かれた版だけを見て成果物を古い状態に戻すのではなく、保存記録と実ファイルを照合して現在地を確認しなければならない。「保存した」「案内を更新した」「受け手が原本を読めた」は、同じ出来事ではない。この開発管理の問題は、観測システムで扱っている時刻や状態の問題とよく似ている。
AIがすべてを覚えているから複雑な開発ができる、というわけではない。判断の根拠に戻れる形を人間とAIで作り、その原本を参照しながら次の作業を進められるようになったことが大きい。コードの生成が速いことよりも、以前の判断を壊さずに変更を積み重ねられることが、今の開発を支えている。

開発を支援するAIとは別に、将来システム内の評価に参加させる候補として、Jevとの接続準備も進めている。チャートを渡して自由に売買させる話ではない。Observerが作った観測と証拠を、限定した質問にどう渡して、返ってきた結果をどの条件で扱うのかを検討するものだ。
この部分は構想にとどまらず、接続用Adapterの初版まで進んだ。固定した証拠本文を要求に組み込み、実際のSDKを通し、送信直前の内容を検査し、応答の本文と解析結果、時刻、警告や例外を分けて保存する経路を実装している。ただし、接続先は模擬の通信経路だ。実際のJevサービスが市場の問いに正しく答えたことは、まだ確認していない。通信の組立てを検査できたことと、回答の意味を評価できたことは、分けて考えている。

ここでも、不都合な答えが出たから引き直す、ということはしない。「評価できない」「優位を確認できない」という応答も、そのまま結果として残す。SDKが内部で勝手に再送するのは抑えて、再試行するなら、その権限と回数、元の締切との関係を外側で管理する。現在の初版は一回送信だけの限定経路で、再試行を含む接続は次の工程になる。

AIを使うほど、AIに任せない範囲をはっきりさせる必要が出てきた。観測の定義を決めること。不足している証拠を確認済みに変えること。期待する答えに合わせて評価対象を作り直すこと。これらをモデルの出力で代用しない。将来の比較では、同じ時点の入力と、独立に定めた参照評価を揃えて、規則による判断とJevの結果を分けて調べることになる。

開発を助けるAIと、開発したシステムの中で評価を担当する候補。どちらもAIという言葉でひとくくりにできるが、責任も、確かめるべきことも違う。この二つを混ぜないことも、SNFの構成の一部になっている。

まず、一つの観測を最後まで通す

次の実装範囲は、かなり具体的になっている。新しいCoreやS抽出器を一から作り直すのではなく、すでにあるCore、入力経路、共通契約、SLineLabの計算部分を使って、一つの実対象を最後まで通す。

最初は、既存の入力経路で、限定した設定命題を別の保存先に適用し、台帳を読み戻して、中断からの再開と重複防止を確かめる。そのうえで、H4と日足を使うSラインの基準例を一つ選び、その原データ、設定、価格根拠、確定時点を、正式な対象と版に結び付ける。価格を読むところから、Sの候補と根拠を作り、Coreに記録して、状態を確認するところまでを、短い一本の経路としてつなぐ計画だ。

この一件を動かすのに、Rangeの全類型や、すべての親子構造、Jevの市場評価が完成するのを待つ必要はない。ただし、その一件に必要な対象や時刻の証拠が欠けているなら、そこは補わなければならない。関係のない未決事項を条件に加えて作業を止めるのも、必要な不足を見ないふりして通すのも、どちらも避けたい。

以前は、問いが残っていること自体が、設計の足りなさの証拠のように思えた。今は、その問いを誰が解くべきかを、もう少し分けて見られる。市場の意味が決まっていないなら、私の観測に戻る必要がある。必要なデータがないなら、採取や供給の問題だ。意味も入力も決まっているのにコードがつながっていないなら、実装の仕事になる。つながっていても挙動を確かめていないなら、検証の仕事だ。
この見分けがつくようになったことも、開発の進捗だと思う。未決事項が減るだけでなく、すでに決めたことを問い直さずに済む。未知を無理に既知へ変えるのではなく、今ある既知を、実際に使える形に運べるようになってきた。

最終的には売買につなぐ。その目的は変わらない。ただ、今作っているものを、売買条件を詰め込んだEAとは呼びにくくなった。Sラインが一本現れるまでにも、対象の識別、価格の選択、時点の確認、証拠の受け渡し、状態の更新、履歴の保存がある。その先に、はじめて「どの戦略がこの観測を使うのか」という話が来る。部品が動くことと、全体が使えることの間には、まだ仕事がある。観測が再現できることと、それが利益につながることの間にも、別の検証がいる。それでも、以前より進む順序ははっきりした。次に何を作り、何を確かめれば一段先へ行けるのか、見えている。

前篇では、自分がどんなレンズで相場を見ているのかを書いた。後篇で形にしているのは、そのレンズを、自分が見ていない時間にも使えるようにする仕組みだ。同じ場所に線を引かせるだけでなく、その線を引いた理由を残し、根拠が失われたときにはそれも分かるようにする。

トレーダーには風の向きは決められない。それはSNFも同じだ。しかし、いつ、何を見て、どう受け取ったのかは残せる。分からなかったことを、分からないまま記録することもできる。その積み重ねを、自分の頭の外でも続けられるようにする。今の私にとって、思想をソフトウェアに変えるとは、そういう仕事だ。

この連載: 風のライオン (2 / 2)
シリーズガイド |希望をこの手から放し、確定した価格へ戻る。

Tagged in :

sinonomeのアバター