#!/usr/bin/env python3
"""Recalcule les modèles simples des séries canadiennes de l'annexe Allison."""

import csv
import sys


def serie(value):
    if not value:
        return {}
    return {int(year): float(count) for year, count in (part.split(":", 1) for part in value.split(";"))}


def attendu(annual, years, baseline, model):
    start, end = (int(part) for part in baseline.replace("–", "-").split("-"))
    points = [(year, annual[year]) for year in range(start, end + 1)]
    if model == "moyenne":
        mean = sum(value for _, value in points) / len(points)
        return sum(mean for _ in years)
    if model == "OLS":
        n = len(points)
        mean_x = sum(year for year, _ in points) / n
        mean_y = sum(value for _, value in points) / n
        slope = sum((year - mean_x) * (value - mean_y) for year, value in points) / sum((year - mean_x) ** 2 for year, _ in points)
        return sum(mean_y + slope * (year - mean_x) for year in years)
    raise ValueError(f"modèle inconnu: {model}")


def main(path):
    failures = 0
    with open(path, encoding="utf-8-sig", newline="") as source:
        for row in csv.DictReader(source):
            if ":" not in row["donnees_annuelles_utilisees"]:
                print(f'{row["claim_id"]} {row["modele"]}: non vérifié (série absente)')
                continue
            annual = serie(row["donnees_annuelles_utilisees"])
            years = [int(year) for year in row["annees_cibles"].split(";")]
            observed = sum(annual[year] for year in years)
            projected = attendu(annual, years, row["periode_reference"], row["modele"])
            excess = observed - projected
            ok = all(abs(value - float(row[key])) < 0.02 for value, key in ((observed, "observe_total"), (projected, "attendu_total"), (excess, "exces")))
            failures += not ok
            print(f'{row["claim_id"]} {row["modele"]}: observé={observed:.3f} attendu={projected:.3f} écart={excess:.3f} {"OK" if ok else "ÉCART"}')
    return 1 if failures else 0


if __name__ == "__main__":
    raise SystemExit(main(sys.argv[1] if len(sys.argv) > 1 else "resultats-aggreges.csv"))
