Het gevaar van 'Data Leakage' in machine learning modellen
Stel je voor: je hebt een prachtig machine learning model gebouwd dat aandelenkoersbewegingen voorspelt. Je backtests draaien als een zonnetje, de winstcurves gaan omhoog als een raket.
Je zet het live via je broker API en… boem, het verliest geld. Waarom?
Omdat er een stille dief in je code zat: data leakage. Dit is het gevaarlijkste probleem waar beginnende en ervaren quants mee te maken krijgen. Het geeft een vals gevoel van zekerheid en vernietigt je risicomanagement. Vandaag duiken we in de keuken van dit probleem, specifiek voor algoritmische trading bots in Python.
Wat is data leakage precies?
Stel je voor dat je een voetbalcoach bent die een wedstrijd analyseert. Je bekijkt de beelden van na de wedstrijd om te voorspellen wie gaat scoren.
Dat werkt perfect op de beelden, maar in de echte wedstrijd heb je die beelden niet.
Data leakage is precies dat: je model krijgt informatie tijdens de training die het in de echte wereld niet heeft. In trading betekent dit dat je toekomstige data per ongeluk gebruikt om het verleden te voorspellen. Een klassieke fout is het berekenen van een indicator op een hele dataset voordat je splitst in train- en testdata.
Je model ziet dan de toekomst en presteert perfect in de backtest, maar faalt in de live trading. Denk aan een simpele Python strategie met een Simple Moving Average (SMA).
Je laadt data van 2020 tot 2024, berekent de SMA over 50 dagen en test de strategie op diezelfde dataset. De SMA op dag 50 gebruikt data van dag 1 tot 50, maar als je de dataset niet netjes splitst, lekt er informatie door. Je model ziet de 'toekomstige' candle van dag 51 al in de berekening zitten. Dit is geen magie, het is een programmeerfout die je winstcurve vals hoog maakt. Bij een broker zoals Interactive Brokers of DEGIRO betaal je transactiekosten van €3-5 per trade, en leakage zorgt ervoor dat je te veel trades plaatst op basis van vals vertrouwen.
Waarom is dit zo gevaarlijk voor trading bots?
Data leakage is een stille moordenaar van je trading bot. Het geeft je een perfecte backtest, maar een teleurstellende live performance.
Je risicomanagement wordt compleet ondermijnd omdat je denkt dat je drawdown maximaal 5% is, terwijl het in werkelijkheid 20% wordt. Stel je voor dat je een bot bouwt voor EUR/USD op basis van een API van een broker zoals Alpaca of XT. Je gebruikt historische data van 2019-2023, maar je normaliseert de prijzen over de hele dataset voordat je splitst.
Je model leert patronen die alleen in die specifieke dataset bestaan, niet in de echte markt.
Resultaat: je bot draait 6 maanden live en verliest consistent geld, terwijl je backtest een jaarlijks rendement van 30% liet zien. De impact is groter dan je denkt. In algorithmic trading gaat het om snelle beslissingen, soms in milliseconden via API's. Als je model leakage heeft, neemt het risico's die het niet ziet.
Je risicomanagement parameters, zoals stop-loss op 2% of position sizing van 1% van je kapitaal, zijn gebaseerd op foutieve data. Dit leidt tot grotere verliezen dan gepland.
Denk aan een Python bot die short gaat op basis van een foute feature. Je betaalt dividend en borrow fees, en de verliezen lopen op. Een goede backtest zonder leakage toont de echte uitdagingen, zoals slippage van €0.01 per aandeel of commissies van €0.001 per aandeel bij low-cost brokers.
Hoe werkt leakage in je Python code?
Laten we concreet worden met een voorbeeld in Python, voor een momentum-strategie op aandelen. Je gebruikt libraries zoals pandas en numpy, en laadt data via een API van je broker.
Stel, je hebt een dataset van 1000 dagen voor een aandeel van €50.
Je berekent een RSI indicator over 14 dagen. De fout die veel traders maken: je berekent de RSI op de hele dataset eerst, en splitst dan pas in train- en test sets. Hierdoor lekt de RSI-waarde van dag 15 tot 1000 door in je training data.
Je model ziet dus patronen die het in de live markt niet heeft. Een correcte aanpak is om per dag de RSI te berekenen op alleen de voorgaande data, en pas na de split te testen. Een ander variant is lookahead bias bij het selecteren van features. Stel je bouwt een bot die voorspelt of een aandeel morgen stijgt.
Je voegt een feature toe zoals 'morgen openingsprijs'. In de training lijkt dit perfect te correleren, maar zodra je je getrainde model gaat inzetten, heb je die prijs niet.
Dit gebeurt vaak in backtesting frameworks zoals Backtrader of Zipline in Python. Je script draait soepel, maar de resultaten zijn te mooi om waar te zijn.
Specifieke prijzen: als je een aandeel van €100 koopt en de API-call kost €0.01, maar leakage zorgt voor 100 extra trades per jaar, kost je dat €1 extra per trade, oftewel €100 per jaar op een klein kapitaal. Pas op met features zoals 'volume gemiddelde van de komende week' – die bestaat niet in de toekomst. Een derde variant is leakage via time series splitting.
In trading is tijd lineair; je kunt niet terug in de tijd.
Gebruik een TimeSeriesSplit van scikit-learn, maar zorg dat je geen toekomstige data gebruikt voor elke fold. Bijvoorbeeld: voor een bot op crypto via een exchange API, split je data in 80% train en 20% test, maar de test set moet de toekomst zijn, niet een willekeurig stuk uit het verleden. Voordat je jouw dataset voorbereidt, moet je begrijpen dat als je dit verkeerd doet, je patronen leert die alleen in het verleden bestaan, niet in de toekomstige markt. Test dit altijd met een out-of-sample periode van minimaal 6 maanden om echte prestaties te zien.
Varianten en modellen met prijsindicaties
Er zijn verschillende soorten leakage, afhankelijk van je model. Voor eenvoudige modellen zoals lineaire regressie op prijsdata, is leakage vaak in de feature engineering.
Bijvoorbeeld, een model dat de volgende dag sluitingsprijs voorspelt, maar per ongeluk de huidige sluitingsprijs als feature gebruikt.
Dit is subtiel maar dodelijk. Voor complexere modellen zoals LSTM-neural networks in Python, kan leakage optreden in de sequence length. Stel je gebruikt een window van 50 dagen; als je die window berekent op de hele dataset, lekt er informatie door.
Prijzen voor dit soort modellen: een cloud server voor training kost €50-100 per maand via AWS, maar als leakage je model onbruikbaar maakt, verspil je dat geld. Een andere variant is leakage in risicomanagement features.
Stel je voegt de Sharpe ratio toe als feature, maar berekent die op de hele historische dataset. In live trading kun je die ratio pas berekenen na de trade, niet ervoor. Dit leidt tot te optimistische positiebepaling. Voor een bot die trade op basis van Python en API's van brokers zoals Interactive Brokers (kosten €10 per maand voor data), test je model op een demo account met €10.000 virtueel kapitaal.
Als leakage aanwezig is, zie je een winst van 15% in de backtest, maar in de demo verlies je 5%.
Modellen zoals random forests zijn gevoelig voor leakage in feature importance; ze 'leren' de toekomst en geven verkeerde gewichten. Voor high-frequency trading bots, is leakage nog gevaarlijker. Stel je bouwt een bot die in milliseconden handelt via API's van exchanges zoals Binance (transactiekosten 0.1%).
Leakage in de order book data kan ervoor zorgen dat je bot denkt te kunnen voorspellen wat er na jouw order gebeurt, wat onmogelijk is. Een prijsindicatie: backtesting op een VPS van €20 per maand is goedkoop, maar als leakage je live verliezen oploopt tot €500 per maand op een kapitaal van €10.000, is de schade groot. Kies voor modellen die tijdreeksen correct splitten, zoals die in de library QuantConnect, die gratis is maar wel tijd kost om te leren.
Praktische tips om leakage te voorkomen
Checklist om leakage te vermijden in je trading bots. Ten eerste, splits je data altijd op tijd: gebruik een cutoff datum, bijvoorbeeld 80% voor training (2018-2022) en 20% voor test (2023-2024).
Bereken alle features, zoals SMA of RSI, apart voor elke set, zonder naar de toekomst te kijken. In Python, gebruik libraries zoals sklearn voor TimeSeriesSplit, en zorg dat je geen data uit de toekomst importeert via API's. Een andere tip: gebruik een aparte validatieset.
- Splits data op tijd, niet willekeurig – test altijd out-of-sample.
- Bereken features per dag, zonder global normalisatie.
- Gebruik een demo account van je broker om live te testen na backtesting.
- Log elke stap in je code: print de data range voor elke berekening.
- Test met een klein kapitaal, bijvoorbeeld €1.000, om risico's te minimaliseren.
Na de train-test split, reserveer een validatie set voor hyperparameter tuning. Dit voorkomt dat je tuning leakage introduceert.
Voor risicomanagement, stel je stop-loss in op basis van historische volatiliteit, maar bereken die alleen op train data.
Als je een bot bouwt met een budget van €5.000, begin met paper trading via een API als die van Alpaca (gratis voor basis data). Controleer of je backtest resultaten overeenkomen met de demo. Als niet, zoek naar leakage. Ten slotte, documenteer je process.
Schrijf op hoe je elke feature berekent en waarom. Vraag een collega of forumlid om je code te reviewen – communities zoals Reddit's r/algotrading zijn gratis en behulpzaam.
Onthoud: een goede backtest toont de echte uitdagingen, zoals slippage en kosten. Als je leakage oplost, bouw je bots die echt werken, niet alleen op papier. Zo blijf je veilig handelen en groeit je kapitaal stap voor stap.
