- docs/SPEC.md sostituito da un file per argomento (indice in docs/README.md) - assunzioni A1-A24 con dove nel codice e cosa succede se false - formule in LaTeX corrette (nessuno spazio prima del dollaro di chiusura), simboli e chiavi in tabella - diagrammi Mermaid per il flusso degli algoritmi e le dipendenze dei moduli - figura dei domini sul seed 1 (docs/img/domini_esempio.png) - README ridotto a indice con avvio rapido; CLAUDE.md e docstring allineati Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
8.3 KiB
8.3 KiB
Assunzioni
Ogni assunzione ha un identificativo (A1, A2, …) richiamato nel codice e negli altri documenti. Per ognuna: cosa si assume, perché è
ragionevole, dove il codice ne dipende e cosa succede se è falsa. Le assunzioni sul segnale valgono per i dati del generatore
../gen_data (sezione finale): su dati reali vanno verificate.
Dati
| ID | Assunzione | Dove | Se è falsa |
|---|---|---|---|
| A1 | Il tempo è strettamente crescente, anche non uniforme (jitter del campionamento) | dati.leggi_csv |
il CSV è rifiutato (exit 4). Il programma non riordina né deduplica |
| A2 | Il CSV ha l'intestazione e tutte le colonne richieste da [dati] (tempo e serie), tutte numeriche, senza celle vuote |
dati.leggi_csv |
exit 4 con il nome della colonna mancante |
| A3 | Il tempo è in ms o s come dichiarato in [dati] unita_tempo |
dati.leggi_csv |
tutti i tempi e le costanti \tau risultano scalati di 1000 senza avvisi: controlla l'unità |
| A4 | Le serie condividono gli stessi domini (stessi istanti di rottura) | analisi.analizza_domini, domini.proponi |
i domini sono cercati solo su serie_riferimento (default T_C); una serie con gradini diversi non è gestita: si lancia l'analisi due volte |
Struttura del segnale
| ID | Assunzione | Dove | Se è falsa |
|---|---|---|---|
| A5 | I gradini di riscaldamento sono salti positivi tra due campioni consecutivi molto più grandi del rumore e degli scarti casuali: soglia_gradino_c (20 °C) \gg ampiezza massima degli scarti (≤ 4 °C) |
domini.trova_gradini |
gradini più piccoli della soglia non sono visti (il segnale resta un unico tratto); scarti più grandi della soglia sono scambiati per gradini. Soluzione: adattare la soglia o correggere domini.toml a mano |
| A6 | La salita dura pochi campioni (2–3): il sensore ha costante di tempo (\tau_\text{sensore} \approx 0.07 s) minore dell'intervallo di campionamento (≈ 0.15 s) |
domini.trova_gradini (estensione ai campioni adiacenti), analisi._gradino |
con un sensore più lento la salita avrebbe più campioni: verrebbe comunque raggruppata finché il salto resta sopra soglia_bordo_sigma\cdot\sigma, ma non sarebbe fittata |
| A7 | Dopo ogni gradino la temperatura decade esponenzialmente verso un asintoto: y = c + A\,e^{-t'/\tau} |
modelli.MODELLI["esp_decad"] |
residui sistematici, ρ₁ alto, «modello non adeguato». Con più processi di raffreddamento servirebbe un modello a più esponenziali (non presente, vedi limiti.md) |
| A8 | Tutti i raffreddamenti hanno la stessa costante di tempo \tau e lo stesso asintoto $c$ (stesso processo fisico: dispersione verso l'ambiente). Anche nel generatore il decadimento dopo più gradini è la somma di esponenziali con lo stesso k, quindi un'unica esponenziale |
analisi.analizza_domini (parametri raffreddamento_intermedio_fissa_da_finale) |
gli intermedi sono forzati a \tau e c del finale: se in realtà differiscono, il fit dell'ampiezza A è distorto e i residui lo mostrano. Per rimuovere il vincolo: raffreddamento_intermedio_fissa_da_finale = [] |
| A9 | Il raffreddamento finale è l'ultimo dominio ed è abbastanza lungo (centinaia di campioni) da stimare c, A, \tau liberamente |
analisi.analizza_domini |
se il CSV finisce subito dopo un gradino, il finale è corto e \tau può risultare non identificabile; allora anche gli intermedi restano liberi e possono essere indeterminati |
| A10 | Il riposo (prima del primo gradino) è una baseline costante, lineare o esponenziale lenta (l'ambiente che si assesta) | [fit.modelli_per_tipo] riposo |
il modello scelto è solo descrittivo: con una deriva lenta vince lineare o esp_decad |
| A11 | Ogni dominio è indipendente: nessun vincolo di continuità tra domini | analisi |
i modelli adiacenti possono non combaciare ai confini; il «salto» tra due raffreddamenti è il gradino |
| A12 | Non esistono gradini discendenti (un calo brusco non è un evento): si cercano solo salti positivi | domini.trova_gradini (d > soglia) |
un calo brusco resterebbe dentro un raffreddamento, aumentando RMSE e \rho_1 |
Rumore
| ID | Assunzione | Dove | Se è falsa |
|---|---|---|---|
| A13 | Il rumore è circa gaussiano bianco, con \sigma stimabile per dominio da \sigma = 1.4826\,\mathrm{MAD}(\Delta^2 y)/\sqrt{6} |
domini.sigma_rumore |
\sigma sottostimata: più domini risultano «non adeguati». La stima ignora la parte lenta del rumore (vedi A14) |
| A14 | Sul rumore bianco si aggiungono disturbi che il modello non descrive: deriva lenta (Ornstein–Uhlenbeck, \tau \approx 3.5 s) e scarti casuali (±4 °C, rientro < 1 s) |
fit.adatta (perdita robusta), uscita (residui) |
sono trattati come outlier dalla perdita soft_l1 (non spostano molto il fit) ma lasciano residui autocorrelati (\rho_1 \approx 0.7) e intervalli di confidenza troppo stretti. Non è un errore del fit |
| A15 | La quantizzazione (T a 0.01 °C, ambiente a 0.1 °C) è trascurabile rispetto al rumore | — | nessun trattamento specifico |
Statistica
| ID | Assunzione | Dove | Se è falsa |
|---|---|---|---|
| A16 | Gli intervalli al 95 % sono gaussiani asintotici: \pm 1.96\,\sigma_p con \mathrm{cov} = s^2 (J^\top J)^{-1}, s^2 = \mathrm{RSS}/(n-k) |
fit.adatta |
con pochi campioni o residui non gaussiani sono approssimati |
| A17 | L'autocorrelazione dei residui è di tipo AR(1): gli errori si allargano di \sqrt{(1+\rho_1)/(1-\rho_1)} se \rho_1 supera soglia_acf |
fit.adatta |
correzione approssimata; con autocorrelazione di altra forma gli intervalli restano stretti |
| A18 | Per i parametri fissi l'incertezza non si propaga: gli intervalli di A nei raffreddamenti intermedi sono condizionati a c e \tau del finale |
fit.adatta, uscita._params |
sono sottostimati rispetto all'incertezza totale |
| A19 | AICc e BIC si calcolano da \mathrm{RSS} come se i residui fossero gaussiani, anche se il fit usa la perdita robusta |
fit.adatta |
confronto tra modelli approssimato; sensibile agli outlier |
| A20 | Le serie con \sigma non finita o nulla (dominio troppo corto) usano scala 1 per la perdita robusta |
fit.adatta |
solo robustezza ridotta |
Progetto
| ID | Assunzione | Dove |
|---|---|---|
| A21 | La suddivisione in domini la decide l'utente: la proposta automatica è modificabile (domini.toml) e il fit non la cambia mai |
cli._passo_domini, domini.leggi_toml |
| A22 | Il programma è deterministico: nessuna partenza casuale, nessun seme | fit._partenza (griglia su \tau, minimi quadrati lineari) |
| A23 | Il riscaldamento non si fitta (2–3 campioni): si riporta il salto \Delta = y_\text{fine salita} - y_\text{prima}, che è una stima per difetto del gradino reale perché parte della salita può cadere sul campione precedente |
analisi._gradino |
| A24 | I modelli provati sono fissati per tipo di dominio in configurazione, non scelti dal programma | [fit.modelli_per_tipo] |
Origine dei dati di prova (../gen_data)
I CSV in input/gen_<seed>.csv sono prodotti dal generatore con la sua configurazione d'esempio. Caratteristiche che fondano le
assunzioni sopra (dettaglio: ../gen_data/docs/SPEC.md e ../gen_data/config.toml):
| Aspetto | Valore nel generatore | Assunzioni |
|---|---|---|
| intervallo di campionamento | 150.5 ms con jitter ±0.6 ms | A1, A6 |
| gradini di riscaldamento | 3, a ≈ 15.7, 17.8, 21.7 s, ampiezza ≈ 88, 75, 65 °C (perturbati per seed) | A5, A7 |
| raffreddamento | k = 0.063\ \mathrm{s^{-1}}, cioè \tau = 15.9 s (perturbato del 2 % per seed) |
A7, A8 |
| risposta del sensore | filtro del primo ordine, \tau_\text{sensore} = 0.07 s |
A6 |
| rumore bianco | \sigma = 0.11 °C a freddo, 0.20 a caldo; la stima per dominio dà ≈ 0.08–0.3 |
A13 |
| deriva lenta | Ornstein–Uhlenbeck, \sigma = 0.04 °C, \tau = 3.5 s |
A14 |
| scarti casuali | in riscaldamento: 0.8 Hz, \sigma 2.5 °C; in raffreddamento: 0.25 Hz, media −1 °C; ampiezza ≤ 4 °C, rientro 0.3–0.7 s |
A5, A14 |
| ambiente | 23.1 - 0.45\,e^{-t/58} °C, non sale quando T è alta |
A10; c di dT_C ≈ 0 |
dT_C |
T - T_\text{amb} calcolato dopo rumore e quantizzazione di entrambi i canali |
A4 |