Waarom een backtest bij een broker vaak afwijkt van je eigen code
Je hebt je Python-strategie getest, de cijfers zien er perfect uit en dan probeer je diezelfde strategie bij je broker via hun backtesting-tool en paf: de resultaten zijn compleet anders. Waarom? Omdat een backtest bij een broker zelden hetzelfde is als wat je in je eigen code ziet.
Het voelt frustrerend, maar er zitten logische redenen achter. Laten we eens rustig kijken wat er precies gebeurt en hoe je die kloof dicht.
Definitie: wat bedoelen we met een afwijkende backtest?
Een backtest bij een broker is een simulatie die hun platform draait op historische data, terwijl je eigen code een eigen simulatie bouwt in Python.
Het doel is hetzelfde: uitproberen wat er zou zijn gebeurd. Toch komt er vaak een andere equity-curve uit rollen. Die afwijking zit ’m in data, uitvoering en kosten. Je broker gebruikt zijn eigen datafeed en zijn eigen regels voor orderuitvoering.
Jij gebruikt wat je zelf hebt binnengehaald en wat je eigen script berekent. Dat levert al snel verschillen op van enkele procenten tot tientallen procenten, afhankelijk van de strategie.
Waarom dit echt belangrijk is: vertrouwen en risico
Als je backtest niet klopt, klopt je risicomanagement ook niet. Je kunt te veel risico nemen zonder het te weten, of juist te voorzichtig zijn en kansen missen.
Bij hefboomproducten of futures kan een kleine fout al snel honderden euro’s schelen. Stel je voor: je script voorspelt een jaarwinst van 12% met een drawdown van 8%. De broker-tool laat 6% winst zien met 15% drawdown. Dat verschil bepaalt of je live kunt traden of niet. Zonder goede validatie stap je blind het verkeerde pad op.
Waarom brokers anders zijn: data, uitvoering en kosten
Data is de grootste boosdoener. Brokers zoals Interactive Brokers, DEGIRO of Saxo Bank gebruiken hun eigen historische prijzen.
Die kunnen afwijken van de data die je via Yahoo Finance, Alpha Vantage of je eigen tick-data van Tick Data Suite binnenhaalt. Zelfs kleine verschillen in tijdreeksen leiden tot andere signalen.
Denk aan de slippage en fill-kansen. Een broker simuleert hoe hun orderboek destijds eruitzag. Als jij in Python een market-order plaatst zonder slippage, dan is dat te optimistisch. In de praktijk betaal je soms €0,02 tot €0,10 extra per aandeel, of een spread van 0,5 tot 2 pips bij forex.
Kosten zijn de derde factor. Brokers rekenen commissies, spreads en financieringskosten.
In je eigen code kun je die vergeten. Bij een broker-tool staan ze vaak wel standaard aan. Zelfs kleine verschillen tellen op: een commissie van €2 per trade lijkt weinig, maar bij 200 trades per maand is het €480 extra kosten op een account van €25.000.
“Een backtest is een schatting, geen garantie.”
Hoe het werkt: de kern van het verschil
Data-kwaliteit en -frequentie
Brokers gebruiken vaak 1-minuut- of 5-minuut-bars. Als je eigen code op tick-niveau draait, ontstaan er andere entry- en exitmomenten.
Zelfs een verschil van enkele seconden kan bij een scalping-strategie het verschil tussen winst en verlies betekenen. Let op de marktdekkingsdata.
Orderuitvoering en slippage
Bijvoorbeeld: een broker heeft geen data voor small-cap aandelen buiten kantoortijden. Jij kunt die in je script wel meenemen. Dat leidt tot extra trades in je eigen backtest die de broker nooit ziet. Brokers simuleren limit- en market-orders met hun eigen fill-kansen.
In Python kun je een perfecte fill aannemen op de slotprijs. In de praktijk is een limit-order soms maar 50% gevuld, of voert hij uit op een slechter prijsniveau.
Kosten en voorwaarden
Stel je voor: je koopt 500 aandelen op €10,50. De broker simuleert een gemiddelde fill op €10,53. Dat lijkt klein, maar bij 50 trades per maand scheelt het al snel €75 tot €150 aan extra kosten.
Bij hefboomproducten wordt dat effect groter. Spread, commissie en financieringskosten verschillen per broker en per product.
Bij DEGIRO is een aandelentrade vaak €2 + €0,01% (tot een maximum).
Bij Interactive Brokers hangt het af van het volume. Bij Saxo Bank betaal je een vaste commissie per trade, afhankelijk van het abonnement. Voor CFD’s of forex zijn de spreads soms 0,5 tot 2 pips, plus een overnight-fee.
Tijdszones en handelsuren
In je eigen code kun je die vergeten. In de broker-tool zitten ze vaak standaard ingebouwd.
Zelfs een spread van 1 pip bij EUR/USD op een account van €10.000 met hefboom 1:30 kan al snel €10 tot €30 per trade schelen.
Brokers houden rekening met lokale handelstijden. Een aandeel op de NASDAQ sluit om 22:00 uur Nederlandse tijd.
Jij kunt in je Python-script een order na sluitingstijd plaatsen en die wordt dan meegenomen in de volgende sessie. De broker telt dat niet mee. Ook bij forex speelt tijd een rol. De Aziatische sessie heeft vaak lagere volumes en bredere spreads. Als je strategie daarop is gebaseerd, maar je backtest bij de broker gebruikt Europese data, ontstaat er een mismatch.
Verschillende modellen en prijsindicaties
Er zijn verschillende manieren om een betrouwbare backtest uit te voeren, elk met eigen voor- en nadelen. De keuze bepaalt hoe dicht je bij de werkelijkheid komt en hoeveel kosten je moet rekenen.
Standaard broker-backtests (zoals bij Interactive Brokers TWS of Saxo’s OpenAPI) zijn vaak grof.
Ze gebruiken aggregated data en een eenvoudig slippagemodel. Die zijn snel en makkelijk, maar geven een te rooskleurig beeld. Zelf een event-driven backtester bouwen in Python (met bibliotheken zoals Backtrader of Zipline) is realistischer.
Ze verwerken elke tick of bar en simuleren orderboekgedrag. Je kunt daar slippage en commissies zelf instellen. Nadeel: het is trager en complexer. Voorbeeld prijsindicaties:
- Aandelen: commissie €2 + 0,01% per trade bij DEGIRO; slippage 0,05% tot 0,10% per trade.
- Forex: spread 0,5–2 pips; commissie vaak €5–€7 per miljoen verhandeld; overnight-fee 0,01%–0,03% per dag.
- CFD’s: spread 1–3 pips; financieringskosten 0,01%–0,05% per dag; commissie €5–€10 per miljoen.
- Futures: commissie €1–€3 per contract; slippage 0,5–2 ticks; exchange fees €0,50–€2 per contract.
Stel je voor: een daytrading-strategie op de DAX-futures met 20 trades per dag.
Een slippage van 1 tick (€5) en commissie van €2 per contract leiden al snel tot €140 kosten per dag. Als je dat in je eigen backtest vergeet, is je resultaat volledig vertekend.
Praktische tips om de kloof te dichten
- Gebruik dezelfde data. Haal historische data bij je broker op (bijvoorbeeld via Interactive Brokers Historical Data of Saxo’s OpenAPI) en vergelijk die met je eigen dataset. Zoek verschillen in sluitingsprijzen, volumes en timestamps.
- Voeg slippage en commissies toe in Python. Gebruik een realistisch model: 0,05%–0,10% slippage voor aandelen, 0,5–2 pips voor forex. Reken met de daadwerkelijke tarieven van je broker.
- Test met beperkte ordergrootte. Simuleer een account van €10.000 en handel met posities van maximaal 1–2% per trade. Zo zie je snel of liquiditeit een rol speelt en of je fills slechter worden bij grotere orders.
- Check handelsuren en marktdekkingsdata. Zorg dat je eigen script rekening houdt met sluitingstijden, feestdagen en marktsessies. Bij een broker-tool controleer je welke data wel en niet wordt meegenomen.
- Valideer met out-of-sample data. Deel je dataset op: gebruik de eerste 70% voor ontwikkeling en de laatste 30% voor validatie. Als de resultaten sterk afwijken, is je model te optimistisch.
- Draai een kleine live-test. Start met een paper trading-account of een klein echt account (bijvoorbeeld €1.000–€2.500). Vergelijk de live resultaten met je backtest en pas je slippage- en kostenparameters aan.
- Documenteer je aannames. Schrijf op welke data, slippage, commissies en handelsuren je gebruikt. Zo kun je later makkelijk bijstellen en vergelijken.
Als je deze stappen volgt, komt je broker-backtest dichter bij je Python-code. Het verschil verdwijnt niet helemaal, maar het wordt beheersbaar. Vraag jezelf bij het analyseren af of je deze backtest in het echt durft te draaien, want dat is precies wat je nodig hebt voor betrouwbaar risicomanagement.
