OR_Training / plan_generator.py
rogarces85's picture
Create plan_generator.py
fc5b9e3 verified
from datetime import date
from dateutil.relativedelta import relativedelta
DISTANCES = {"5K": 5, "10K": 10, "21K": 21.097, "42K": 42.195}
def weeks_until(target_iso):
tgt = date.fromisoformat(target_iso)
today = date.today()
return max(4, (tgt - today).days // 7)
def base_paces(current_5k_pace_min_per_km: float):
# Deriva ritmos aproximados básicos (puedes ajustar a tu criterio)
easy = current_5k_pace_min_per_km + 0.45 # ~+27s/km
tempo = current_5k_pace_min_per_km - 0.15 # ~-9s/km
intervals = current_5k_pace_min_per_km - 0.30
return round(easy,2), round(tempo,2), round(intervals,2)
def build_plan(goal:str, target_date:str, days_per_week:int, long_run_day:str,
current_5k_pace:float, long_run_km:int|float, experience:str):
weeks = min(20, max(8, weeks_until(target_date)))
easy, tempo, intervals = base_paces(current_5k_pace)
goal_km = DISTANCES[goal]
# volumen inicial y progresión simple
base_vol = max(20, int(long_run_km*2.5))
peak_vol = { "5K": 35, "10K": 45, "21K": 55, "42K": 80 }[goal]
progression = [(base_vol + int((peak_vol-base_vol)*i/(weeks-1))) for i in range(weeks)]
week_plan = []
for w in range(1, weeks+1):
vol = progression[w-1]
sessions = []
slots = min(5, max(3, days_per_week))
mix = ["Easy","Tempo","Easy","Intervals","LR"][:slots]
for s in mix:
if s=="Easy":
sessions.append({"tipo":"Rodaje suave","km": round(vol*0.20,1), "ritmo": f"{easy} min/km"})
elif s=="Tempo":
sessions.append({"tipo":"Tempo (umbral)","estructura": "2km cal + 4-6km tempo + 1km enf",
"ritmo": f"{tempo} min/km"})
elif s=="Intervals":
rep = 5 if goal in ("10K","21K") else 4
dist = 1.0 if goal!="5K" else 0.8
sessions.append({"tipo":"Intervalos", "estructura": f"{rep} x {dist}km (rec 2-3')",
"ritmo": f"{intervals} min/km"})
elif s=="LR":
lr = min(goal_km+10, max(long_run_km, int(vol*0.35)))
sessions.append({"tipo":f"Fondo {long_run_day}","km": lr, "ritmo": f"{easy+0.15} min/km"})
week_plan.append({"semana": w, "volumen_km": vol, "sesiones": sessions})
return {
"resumen": {
"semanas": weeks,
"volumen_pico_km": max(progression),
"ritmos": {"easy": easy, "tempo": tempo, "intervalos": intervals}
},
"plan": week_plan
}