カスタムインジケーターのライフサイクル

cBots (自動売買)

サンプルコードの構造

この記事では、コードの構造をガイドし、cTraderインジケーターのイベントとライフサイクルの背後にあるロジックを説明します。カスタムインジケーターにアクセスするには、’Algo‘アプリケーションの‘Local’タブを開きます。

Image title

例として、以下のサンプルコードをコードエディタウィンドウに入力して、新しいインジケーター「LifeCycle Test」を作成できます。

Image title

コードをボイラープレートコードにリセットするには、以下のコードをコピーします。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
{
    [Indicator(AccessRights = AccessRights.None)]
    public class LifeCycleTest : Indicator
    {
        [Parameter(DefaultValue = "Hello world!")]
        public string Message { get; set; }

        [Output("Main")]
        public IndicatorDataSeries Result { get; set; }

        protected override void Initialize()
        {
            // cTrader Algoの詳細については、ヘルプセンターをご覧ください:
            // https://help.ctrader.com/ctrader-algo/


            Print(Message);
        }

        public override void Calculate(int index)
        {
            // 指定されたインデックスの値を計算します
            // Result[index] = 
        }
    }
}

一目でわかるように、コード構造にはInitialize()メソッドとCalculate()メソッドの2つのメソッドだけが含まれています。テストを続行するには、「Build」をクリックしてください。後でその目的を説明するためにOnDestroy()と呼ばれる追加のメソッドも追加します。

初期化イベント

cTraderインジケーターがチャートに初めて追加されたとき、またはユーザーがパラメーター設定を変更したとき、インジケーターインスタンスが再作成され、Initialize()メソッドが呼び出されます。このメソッドは、インジケーターで使用する変数を初期化するために使用されます。追加のインジケーターを定義して参照し、他のインジケーターの数式を使用して単一のインジケーターを作成することもできます。

デフォルトでは、新しいコードテンプレートには「Hello world!」の値を持つMessageというパラメーター設定が含まれています。

1
2
[Parameter(DefaultValue = "Hello world!")]
public string Message { get; set; }

Initialize()メソッドでは、このメッセージをログに出力するコード行があります。

1
Print(Message);

Initialize()メソッドを示すために、「+」をクリックしてインジケーターインスタンスを追加し、「Build」アイコンの横にある「+」をクリックしてシンボルを選択します。インジケーター行の「More」をクリックして「Add an Instance」を選択すると、EURUSDシンボルが自動的に追加され、時間枠がh1になります。

Image title

Note

cTrader Algoでのインスタンスの追加は、’Trade‘アプリケーションでインジケーターをチャートにアタッチするのと同じです。

次に、チャートの下の「TradeWatch」パネルにある「Log」タブを開きます。ご覧のとおり、「Hello world」というメッセージが出力されています。

Image title

インジケーターが初めてチャートに追加されるたびに、チャートが更新されます。パラメーター設定が変更されるたびに、インジケーターインスタンスが再作成され、Initialize()メソッドが再度呼び出されます。「Parameters」セクションに異なるメッセージを入力してみると、ログエントリが対応して変更されます。

Image title

インジケーター出力の計算

Calculate()メソッドは、過去のデータの各インデックスおよび各着信ティックに対して呼び出されます。たとえば、現在のチャートに1000本のバーがある場合、Calculate()メソッドはインデックス0、1、2 … 999まで呼び出されます。

1
public override void Calculate(int index)

Calculate()メソッドは、市場が高い変動性を持つ期間中は1秒間に多く呼び出され、平坦な市場では呼び出される回数が少なくなります。その動作をテストするために、Calculate()メソッドの本文にコード行を追加して、新しいデータティックごとにメソッドに渡されるインデックス値をログに出力します。コードエディタウィンドウで変更を加えるたびに「Build」をクリックすることを忘れないでください。

1
Print("Index: " + index);

コードエディタウィンドウからチャートに切り替えるには、追加されたインジケーターインスタンスをクリックします。今、「TradeWatch」パネルの「Log」タブを開くと、メソッドに渡されるインデックス値がログに出力されるのがわかります。

Image title

OnDestroy()メソッド

最後のイベントは、インジケーターがチャートから削除され、もう必要なくなったときに呼び出されるOnDestroy()メソッドです。このメソッドは新しいインジケーターを作成するときに含まれないので、自分でコードを記述する必要があります。

1
2
3
4
protected override void OnDestroy()
        {
            base.OnDestroy();            
        }

このメソッドは、プログラマーにとって便利です。これにより、非管理メモリリソースを自由に解放し、他の最終化タスクを実行できます。これにより、メモリリークを防ぎ、インジケーターが削除された後もリソースを保持しないようにします。いくつかの例として、外部データフィードへの接続を閉じる、大量のデータを保持するオブジェクトを解放する、その他メモリを消費するすべてのものがあります。

まとめ

まとめとして、Initialize()Calculate()、およびOnDestroy()メソッドは、カスタムインジケーターのライフサイクルの異なる段階を示しています。’Algo‘アプリでサンプルコードを調整することで、インジケーター変数を初期化し、インジケーター出力を計算し、最終化タスクを実行する方法を自由に決定できます。