Matriks Destek ve Yardım Platformu

Matriks Ürünleri ile ilgili tüm sorularınız için bizlere buradan ulaşabilirsiniz. Daha önce sorulan soruları ve verilen cevapları ilgili sekmelerden ve arama üzerinden inceleyebilirsiniz. Sağ taraftaki kategoriler üzerinden İlgilendiğiniz özelliklerle ilgili soruları filtreleyebilirsiniz. Soru ve cevapları sosyal medyada paylaşabilirsiniz. Sorduğunuz ve cevapladığınız soruların ve yorumlarınızın aldığı oylar üzerinden puan kazanırsınız. Puan sistemine bağlı kampanyamızla ücretsiz kullanım avantajlarından faydalanabilirsiniz.

0

Backtest ve Canlı işlem tutarsızlığı V2

Soruldu
Görüntülenme
2.210 görüntülenme
Durum
Çözüldü

Merhaba,

Önceki konuda iq'da (aynı formül için) prime sinyallerinden farklı yerlerde emir gelmesi sorunu Orçun Bey sayesinde halldedildi.

Şimdi daha genel bir şey danışmak istiyorum.

iq'da yaklaşık bir saatten fazla emirleri takip ettim, prime ile aynı yerlerde emirlerin geldiğini görünce bir de backtest yapayım dedim.

Backtest sonucunda, canlıda yaptığı işlemlerden tamamen alakasız şeyler geldi.

Bu fark neden olur? Farkın olmaması için ne yapabilirim?

Bu konu çok önemli, çünkü stratejiler canlıya alınınca tamamen farklı işlemler yaparsa backtest yapmamızın anlamı kalmaz...

Ekran görüntüsü : Soldaki backtest, sağdaki canlı işlem. Ekran görüntüsünde 19:32 den beri olan işlemler var.

https://hizliresim.com/EdnHd5

 

Kod:

using System;
using System.Collections.Generic;
using System.Linq;
using Matriks.Data.Symbol;
using System.Windows.Media;
using Matriks.Engines;
using Matriks.Indicators;
using Matriks.Symbols;
using Matriks.AlgoTrader;
using Matriks.Trader.Core;
using Matriks.Trader.Core.Fields;
using Matriks.Trader.Core.TraderModels;
using Matriks.Lean.Algotrader.AlgoBase;
using Matriks.Lean.Algotrader.Models;
using Matriks.Lean.Algotrader.Trading;

 

namespace Matriks.Lean.Algotrader
{
    public class btc_test : MatriksAlgo
    {
        [SymbolParameter("XBT_USD_BMEX")]
        public string Symbol;

        [Parameter(SymbolPeriod.Min)]
        public SymbolPeriod SymbolPeriod;

        [Parameter(10)]
        public decimal Lot;

        [Parameter(1)]
        public int Pm1;
        [Parameter(3)]
        public int Pm2;
        [Parameter(1)]
        public int Pm3;

 


        SMA m1, m2, m3, m4, m5;


        public override void OnInit()
        {

            m1 = SMAIndicator(Symbol, SymbolPeriod, OHLCType.Close, Pm1);
            m2 = SMAIndicator(Symbol, SymbolPeriod, OHLCType.Close, Pm2);
            m3 = SMAIndicator(Symbol, SymbolPeriod, OHLCType.High, Pm3);
            m4 = SMAIndicator(Symbol, SymbolPeriod, OHLCType.Low, Pm3);

 


            AddSymbol(Symbol, SymbolPeriod);
            WorkWithPermanentSignal(true); //Sadece kalıcı sinyallerde işlem yap
            SendOrderSequential(true);//Bir al bir sat kuralı


        }


        public override void OnDataUpdate(BarDataCurrentValues barDataCurrentValues)
        {

            var bardata = GetBarData();
            var close = bardata.Close[barDataCurrentValues.LastUpdate.BarDataIndex -1];

            if (Ref(m1, 0) >Ref(m2, 0) && close<Ref(m3, 0))
            {
                SendMarketOrder(Symbol, Lot, OrderSide.Buy, ChartIcon.Buy);
            }

            if (Ref(m1, 0) <Ref(m2, 0) && close>Ref(m4, 0))
            {
                SendMarketOrder(Symbol, Lot, OrderSide.Sell, ChartIcon.Sell);
            }

 

        }
    }
}

 

Ek bilgi: Stratejinin Prime kodu

(MOV(c,1,s)>MOV(c,3,s)) and (c<MOV(h,1,s))

(MOV(c,1,s)<MOV(c,3,s)) and (c>MOV(l,1,s))

Paylaş
CevaplaBayrakladüzenlendi · merpermerper261

1 Cevap

1

Kabul edilen cevap

Merhabalar,

Önceki sorunuzda biraz eksik bilgi paylaşmışım. Kapanış değerinin 1 bar öncekini alarak canlıda işinizi görebilirsiniz fakat backtestte işler biraz farklılaşıyor. Backtestte bar açılışı diye bir olay olmadığı için gelen değerler hep bar kapanaşında oluşan değerlerdir. Sizde close değerini 1 önceki bardan almak istediğinizde yanlış sonuçlar ortaya çıkıyor. Bu sorununu çözmek için close değerini biraz değiştirmek yeterli. Close değerini aşağıdaki gibi tanımlarsanız backtest ve canlıda sorun yaşamazsınız.

var close = Ref(bardata,OHLCType.Close,0);

Bir tavsiye olarak lütfen kullandığınız değerleri Debug tabinde yazdırıp grafik ile kıyaslayarak gidin en doğru sonuca bu şekilde varabilirsiniz. Debug tabina verileri yazdırmanız için OnDataUpdate fonksiyonunda aşağıdaki gibi değişiklik yaptım.

public override void OnDataUpdate(BarDataCurrentValues barDataCurrentValues)
{

	var bardata = GetBarData();
	var close = Ref(bardata, OHLCType.Close, 0);
	Debug("**************************");
	Debug("Close : " + close);
	Debug("m1.CurrentValue : " + Ref(m1, 0));
	Debug("m2.CurrentValue : " + Ref(m2, 0));
	Debug("m3.CurrentValue : " + Ref(m3, 0));
	Debug("m4.CurrentValue : " + Ref(m4, 0) + "\n");

    if (Ref(m1, 0) >Ref(m2, 0) && close<Ref(m3, 0))
    {
		SendMarketOrder(Symbol, Lot, OrderSide.Buy, ChartIcon.Buy);
		Debug("Alış emri gerçekleşti.");
	}

	if (Ref(m1, 0) <Ref(m2, 0) && close>Ref(m4, 0))
	{
		SendMarketOrder(Symbol, Lot, OrderSide.Sell, ChartIcon.Sell);
		Debug("Alış emri gerçekleşti.");
	}
}

İyi çalışmalar

BağlantıBayrakladüzenlendi · merperOrçunMatriks Destek4.555

Yorumlar (12)

  • ▲0

    Teşekkür ederim Orçun Bey, kodu güncelleyip hemen canlıda takip etmeye başladım, bir saat kadar sonra bir de backtest yaparım. Umarım gerçekleşen işlemlerle backtest aynı gelir.

    Bu arada sormadan edemeyeceğim; Aşağıdaki prime formülünü iq da aynı yerlerde işlem yapacak ve backtesti de doğru gösterecek bir kodu siz nasıl yazarsınız, Belki de ben baştan birşeyleri yanlış yapıyorum.

    (MOV(c,1,s)>MOV(c,3,s)) and (c<MOV(h,1,s))

    (MOV(c,1,s)<MOV(c,3,s)) and (c>MOV(l,1,s))


     

  • ▲0
    Rica ederim. Kodunuzda bir yanlışlık yok. Bende aynı şekilde yazardım.
    OrçunMatriks DestekBayrakla
  • ▲0
    Benzer problem bendede mevcut. şu anda sabahtan bari 7 kere al 6 kere sat sat emri gerçekleşti ama backtestte 2 al 1 sat emre mevcut.
  • ▲0
    Merhaba, yukarıdaki uyarıları dikkate alarak stratejinizi oluşturduysanız sorun olmaması gerekir.

    İsterseniz stratejinizi paylaşın inceleyelim.
    OrçunMatriks DestekBayrakla
  • ▲0
    strateji bilgileri olarak aşağıdakilerini girerek test ediyorumki alım satımlardada aynı kriterler mevcut.

    Symbol CEMAS

    SymbolPeriod Min15

    SymbolPeriodShortPeriod Min

    SymbolPeriodLongPeriod Min60

    BuyOrderQuantity 10000

    SellOrderQuantity 10000

    EmaPeriodSlow 4

    EmaPeriodLong 5

    ------------------------------------
7 yorum daha göster
  • ▲0
    Merhaba,

    Stratejinizi inceledim. Stratejiniz kalıcı sinyallerle çalışmıyor. Backtestte kullandığınız indikatörlerin değerleri sadece bar kapanışında oluşan değerlerdir. Fakat stratejiyi canlıda çalıştırdığınızda bar açılışından kapanana kadar indikatör değerleri değişiklik gösterir ve her değer için strateji tetiklenir.

    Backtest ile canlı çalıştırdığınız stratejinin uyumlu olması için kalıcı sinyalle yani bar kapanışında oluşan değerlerle çalışmanız gerekmektedir. Bunun için OnInıt() fonksiyonuna WorkWithPermanentSignal(true); satırını eklemeniz gerekmektedir.

    Ayrıca yukarıdaki cevaplarda da belirttiğim gibi kalıcı sinyalde canlı strateji çalıştırırken indikatör değerlerini Ref(ema ,0); gibi çağırmanız gerekmektedir. Böyle çağırmazsanız kalıcı sinyalle canlıda çalıştırdığınız strateji yeni bar açıldığında tetikleneceği için indikatör değeri yeni açılan bara göre hesaplanacaktır. Bu da backtest ile uyumsuzluk yaratacaktır.

    Yukarı da verdiğim cevapta bulunan kodu ve hazır stratejilerimizi iyice incelemenizi tavsiye ederim.

    İyi çalışmalar
    OrçunMatriks DestekBayrakla
  • ▲0
    WorkWithPermanentSignal(true); bunu atlamışım.

    şu şekilde daha önce denemiştim hata almıştım.

    if (CrossAbove(Ref(emaLong ,0), Ref(emaShort ,0)))

    Birde stratejiyi nasıl incelediniz buraya hepsi kopyalanmamış.
  • ▲0
    Stratejiyi düzenlerken silmişim pardon. İlk attığınızda stratejiniz görünüyordu.

    if (CrossAbove(Ref(emaLong ,0), Ref(emaShort ,0)))

    Bu şekilde kullanımda nasıl bir hata aldınız. Tekrar deneyin isterseniz.
    OrçunMatriks DestekBayrakla
  • ▲0
    estğ . ben kendimden birden şüphe ettim çünkü hepsini kopyalamıştım çünkü :)

    aşağıdaki gibi bir hata geliyor.

    https://hizliresim.com/DtFjPu
  • ▲1

    Doğru gözden kaçırmışım. Cross fonksiyonları en az bir indikatör veya bardata almak zorunda. Fakat Ref() kullanımında bize decimal değer döner. Bu nedenle hata oluyor. 

    Aşağıdaki kod parçasını Cross fonksiyonlarının yerine kullanabilirsiniz.

    			if (Ref(emaLong, 1) <= Ref(emaShort, 1) && Ref(emaLong, 0) > Ref(emaShort, 0))
    			{
    
    				SendMarketOrder(Symbol, BuyOrderQuantity, (OrderSide.Buy));
    				Debug("Alış emri gönderildi.");
    				Debug("Close = " + barData.BarData.Close);
    				Debug("Ema = " + Ref(emaShort, 0));
    			}
    
    			if (Ref(emaLong, 1) >= Ref(emaShort, 1) && Ref(emaLong, 0) < Ref(emaShort, 0))
    			{
    				SendMarketOrder(Symbol, SellOrderQuantity, (OrderSide.Sell));
    				Debug("Satış emri gönderildi.");
    				Debug("Close = " + barData.BarData.Close);
    				Debug("Ema = " + Ref(emaShort, 0));
    			}

     

    OrçunMatriks DestekBayrakla
  • ▲0
    ilk ben buna benzer bir if yazmıştım ama CrossAbove fonk tam olarak nasıl çalıştığını bilmediğimden dolayı daha doğrudur diye onu kullanmıştım.

    Yardımlarınız için çok teşekkürler.
  • ▲0
    Rica ederim. Aslında Cross fonksiyonlarıyla aynı işlevi görüyor benim yazdığım kod. Fakat Cross fonksiyonlarında o anda gelen indikatör değeri ne ise o işleme giriyor. Bu durumda backtest ile uyumsuzluğa neden oluyor. Yani iki kullanım da yanlış değil yerine göre kullanmak önemli.
    OrçunMatriks DestekBayrakla

Cevabınız

Cevap yazmak için giriş yapın.Giriş yapKayıt ol