Het belang van 'Point-in-time' data om bias te voorkomen
Stel je voor: je hebt een prachtige trading bot geschreven in Python. Je backtest laat een winst van 22% per jaar zien over de afgelopen 3 jaar.
Je hart maakt een sprongetje. Dit is 'm, de heilige graal.
Je koppelt de bot aan de API van je broker, zet er €5.000 op, en wacht op de magie. En dan? Dan verliest de bot €1.000 in de eerste maand. Wat is er misgegaan?
Grote kans dat je slachtoffer bent geworden van de meest subtiele en destructieve val in algoritmische trading: data leakage. En de oplossing heet Point-in-time data.
Het voelt oneerlijk, hè? Alsof de markt je in de maling neemt. Maar het is niet de markt. Het is je eigen data.
Je hebt je bot de toekomst laten voorspellen met kennis uit de toekomst.
Het is alsof je een voetbalwedstrijd nabeschouwt en dan zegt dat je wist dat die ene goal ging vallen. Makkelijk praten achteraf. In de echte wereld, op het moment dat de markt open is, heb je die kennis niet. En jouw data moet dat ook niet hebben.
Wat is Point-in-time data eigenlijk?
Laten we het simpel houden. Point-in-time (PIT) data is data die precies weergeeft wat er op dat moment bekend was.
Het is de data zoals die eruitzag op de dag dat de beslissing genomen had moeten worden.
Het is de tegenpool van 'look-ahead bias'. Het is de data in een tijdmachine, maar eentje die alleen naar het verleden kan reizen, niet naar de toekomst. Stel je voor dat je de kwartaalcijfers van een bedrijf als Apple wilt gebruiken.
Normale data-sets geven je de cijfers van Q2 met een datum van 1 april. Maar ze geven je ook de cijfers die op 1 augustus zijn gepubliceerd, en koppelen die aan 1 april. Dat is verkeerd. Op 1 april wist niemand de cijfers van Q2. Met PIT-data staat er bij de cijfers van 1 april een 'release date' van 1 augustus.
Jouw backtest mag die data pas gebruiken vanaf 1 augustus, niet eerder.
In de wereld van Python backtesting gaat het om veel meer dan alleen prijzen. Het gaat om dividendcorrecties, om split-adjusted prices, om wijzigingen in de free float, om de samenstelling van een index.
Een normale CSV van Yahoo Finance is geen PIT-data. Een dataset van QuantConnect of een betaalde provider van €100-€500 per maand wel. Dat is het verschil tussen een fantasierijke backtest en een robuust systeem.
Waarom het je duizenden euros kan schelen
De impact is enorm en vaak onzichtbaar. Kijk naar de S&P 500 index.
De meeste data-sets passen de historische samenstelling van de index aan op basis van de huidige leden. Dus als Tesla er vandaag in zit, dan zit 'ie er in de data-set ook in vanaf 2010. Dat is handig voor visualisaties, maar een drama voor backtests van index-fondsen. Je backtest laat zien dat je de index had kunnen verslaan met een strategie die toen onmogelijk was, omdat de bedrijven die je nu selecteert er toen nog niet in zaten.
Dit heet survivorship bias. Je kijkt alleen naar de overlevers.
Het is alsof je het gemiddelde vermogen van alle inwoners van Nederland berekent, maar alleen de miljonairs meeneemt.
Het resultaat is een vertekend beeld dat je een vals gevoel van veiligheid geeft. Je systeem presteert in de backtest fantastisch, maar faalt in de live trading omdat de realiteit veel rommeliger is. Zo vang je data-onderbrekingen op bij een dividend-strategie.
Je wilt short gaan op een aandeel vlak voor de ex-dividenddatum. In een normale dataset staan de dividenddata vaak pas veel later vastgelegd.
Je bot ziet in de backtest een prachtige arbitrage-mogelijkheid die in werkelijkheid nooit heeft bestaan. Je backtest winst is €10.000, je werkelijke verlies €2.000. Dat doet pijn.
De werking: hoe filter je de data?
Het draait allemaal om de 'release date' of 'timestamp'. Elke regel in je dataset heeft een datum waarop de data gold, en een datum waarop het bekend werd.
Je backtest-algoritme moet zo simpel zijn als wat: 'Gebruik alleen data waarvan de release date kleiner of gelijk is aan de handelsdatum'. Punt uit. Niks meer, niks minder.
Stel je voor dat je een Python-script schrijft met Pandas. Je haalt een DataFrame met prijzen en volumes. Je merge dit met een tweede DataFrame dat de 'as-of' datums bevat. Mocht je hierbij missende data interpoleren met Pandas, dan filter je daarna je data op df['as_of_date'] <= trading_date. Simpel? Ja.
De kunst zit 'm in het verkrijgen van die tweede dataset. Die kost vaak geld en moeite.
Providers zoals Refinitiv, Bloomberg (kost €20.000+ per jaar) of gespecialiseerde Python-bibliotheeken zoals point-in-time-data of datasets van QuantRocket bieden dit aan. Vergeet hierbij niet om verschillende tijdzones te synchroniseren in je trading dataset. Dit is de infrastructurele investering die je moet doen. Voor de techneuten onder ons: er zijn modellen om dit te reconstrueren.
De 'Event Study' methodologie is een basis. Je bouwt een database van bedrijfsaankondigingen. splits, dividend, earnings.
En je koppelt die aan de prijsdata. Als je dit zelf doet, ben je weken zoet met het schrijven van scrapers voor AFM of SEC-filings.
Het is een project op zich. Je betaalt €0 of je betaalt €500 per maand, maar je bespaart jezelf een hoofdpijn van jewelste.
Modellen en prijsindicaties
Er zijn verschillende niveaus van PIT-data. Je hebt de 'ruwe' data, en je hebt 'gezuiverde' data.
De ruwe data is wat je van de beurs krijgt of van een simpele broker API. De zuiverde data is wat je betaalt. Laten we het hebben over prijzen, want die variëren enorm.
Je hebt de 'gratis' optie. Als je slim bent en veel tijd hebt, kun je proberen om historische SEC-filings te downloaden en te verwerken met Python libraries zoals BeautifulSoup en requests.
Dit kost je tijd (uren per week) en serverkosten (€10-€50/maand), maar de data-prijs is €0. Het risico? Fouten in je eigen code. Eén verkeerde regel en je hele backtest is waardeloos. De 'betaalbare' optie voor retail traders.
Providers als Alpaca Markets bieden gratis historische data aan, maar vaak is dit al aangepast (split-adjusted). Voor echte PIT-data kijk je naar diensten als IEX Cloud of Finnhub.
Hun prijzen liggen vaak tussen de €50 en €200 per maand voor toegang tot fundamentele data met historische datums. Dit is de sweet spot voor de serieuze retail algo-trader met een account van €10.000 - €50.000. De 'institutionele' optie.
Als je een hedge fund bent of een serieuze prop-firma, ga je naar Bloomberg Terminal of FactSet.
De kosten liggen hier makkelijk boven de €20.000 per jaar per gebruiker. Waarom? Omdat hun data extreem schoon is, met minutieze nauwkeurigheid over corporate actions. Dit is de standaard waartegen je je eigen data moet meten. Een backtest op basis van Bloomberg-data is de benchmark voor je eigen systeem.
Praktische tips om direct toe te passen
Het is tijd voor actie. Je hoeft niet alles in één keer perfect te doen.
- Check je splitsingen altijd handmatig. Neem een willekeurig aandeel uit je backtest, bijvoorbeeld Apple (AAPL). Kijk in je data-set naar de prijs rond 2020. Was er een 4-for-1 split? Zijn de prijzen voor die datum gecorrigeerd? Als niet, gooi je data dan direct weg. Dit is de makkelijkste test om te zien of je data 'adjusted' is.
- Vermeng je datastromen nooit. Zorg dat je features (bijvoorbeeld een technische indicator) en je target (toekomstige prijs) nooit samenkomen in dezelfde regel voordat je traint. Je feature mag alleen data gebruiken die op t0 beschikbaar was. Gebruik Python's
shift()functie agressief om te voorkomen dat je per ongeluk in de toekomst kijkt. - Gebruik een walk-forward validation. Stop met backtesten over de hele historie in één keer. Deel je data op in trainingsperiodes en testperiodes. Train van 2018-2019, test op 2020. Train van 2018-2020, test op 2021. Dit simuleert de echte wereld waarin je je model steeds opnieuw moet trainen.
- Betaal voor de data als je serieus bent. Als je €5.000 of meer in de markt zet, is een abonnement van €50 per maand op een fatsoenlijke data-provider een no-brainer. Het beschermt je tegen de grootste denkfouten. Zie het als een verzekering voor je eigen hersens.
Begin klein, maar begin goed. Hier is een stappenplan om je backtesting spel te versterken.
Onthoud dit: een backtest is een verhaal dat je jezelf vertelt. Zorg dat het een eerlijk verhaal is. Met Point-in-time data bouw je geen kasteel in de lucht, maar leg je een stevig fundament voor een trading bot die de echte markt aankan. En dat is wat telt.
