23 nuevas estrategias verificadas esta semana8 licencias institucionales disponiblesCertificación Nivel 5 auditada · disponibleComisión del creador del 82% por venta12,400 traders activos en 94 países23 nuevas estrategias verificadas esta semana8 licencias institucionales disponiblesCertificación Nivel 5 auditada · disponibleComisión del creador del 82% por venta12,400 traders activos en 94 países
HerramientaPythonPython

Walk-forward en 120 líneas

La diferencia entre una estrategia y una curva sobreajustada se ve en una sola cifra: cuánto se degrada al salir de la muestra con la que la optimizaste. Esta utilidad la calcula. Si tu degradación supera el 40%, lo que tienes es un ajuste al ruido, y es mejor saberlo antes de arriesgar dinero que después.

Qué vas a aprender

  • Partir una serie en ventanas de entrenamiento y validación sin filtrar información del futuro
  • Medir la degradación fuera de muestra y leerla correctamente
  • Por qué un Sharpe alto en backtest no significa nada sin este paso

Un vistazo al código

Un fragmento representativo, para que puedas juzgar el oficio sin descargar nada.

walkforward.pyPython
1def walk_forward(datos, optimizar, evaluar, n_ventanas=8, ratio_is=0.7):
2 """Ventanas deslizantes: optimiza en el tramo IS, mide en el OOS.
3
4 El tramo OOS SIEMPRE va después del IS en el tiempo. Barajar los
5 datos o normalizarlos con estadísticas de toda la serie filtra
6 información del futuro y produce resultados fantásticos que no
7 existen. Es el error más común y el más caro.
8 """
9 ancho = len(datos) // n_ventanas
10 resultados = []
11
12 for i in range(n_ventanas):
13 ini = i * ancho
14 corte = ini + int(ancho * ratio_is)
15 fin = ini + ancho
16
17 tramo_is = datos[ini:corte]
18 tramo_oos = datos[corte:fin]
19 if len(tramo_oos) < 20: # muestra insuficiente: no cuenta
20 continue
21
22 params = optimizar(tramo_is)
23 resultados.append({
24 "is": evaluar(tramo_is, params),
25 "oos": evaluar(tramo_oos, params),
26 })
27
28 return resultados
29
30
31def degradacion(resultados):
32 """% que se pierde al salir de la muestra. Por encima de 40 → sobreajuste."""
33 m_is = mean(r["is"] for r in resultados)
34 m_oos = mean(r["oos"] for r in resultados)
35 if m_is <= 0:
36 return 100.0
37 return max(0.0, (1 - m_oos / m_is) * 100)

Contenido

walkforward.py121 líneas
ejemplo_uso.py46 líneas
README.md71 líneas

Qué puedes hacer con esto

Licencia Apache 2.0

Como MIT, pero además te protege frente a reclamaciones de patentes del autor.

Uso comercial
Permitido
Citar al autor
Obligatorio
Publicar tus cambios
No obligatorio