From ec799466cf5d8a552752700aa9c6be5df5bd5275 Mon Sep 17 00:00:00 2001 From: Davide Grilli Date: Thu, 14 May 2026 10:11:55 +0200 Subject: [PATCH] aggiunge report LaTeX completo e pylatex in requirements Co-Authored-By: Claude Sonnet 4.6 --- main.py | 1 + report_completo.py | 152 +++++++++++++++++++++++++++++++++++++ report_completo.tex | 177 ++++++++++++++++++++++++++++++++++++++++++++ requirements.txt | 1 + 4 files changed, 331 insertions(+) create mode 100644 report_completo.py create mode 100644 report_completo.tex diff --git a/main.py b/main.py index d4e5176..171656b 100644 --- a/main.py +++ b/main.py @@ -10,6 +10,7 @@ MENU = [ ("Induttore 1 [t = 110.81–111.56 s]", BASE / "induttore1" / "app1.py"), ("Induttore 2 [t = 112.02–113.95 s]", BASE / "induttore2" / "app2.py"), ("Induttore 3 [t = 115.0–133.7 s]", BASE / "induttore3" / "app3.py"), + ("Report completo LaTeX", BASE / "report_completo.py"), ] def main(): diff --git a/report_completo.py b/report_completo.py new file mode 100644 index 0000000..1ac3faf --- /dev/null +++ b/report_completo.py @@ -0,0 +1,152 @@ +from pathlib import Path +from pylatex import (Document, Section, Subsection, Command, Figure, + Tabular, Math, NoEscape, Package) +from pylatex.utils import bold + +BASE = Path(__file__).parent + +INDUTTORI = [ + { + "nome": "Induttore 1", + "intervallo": "110.81 – 111.56 s", + "t0": "110.81", + "t_end": "111.56", + "n_punti": "5", + "zona_exc": None, + "A": "87.3140", + "A_err": "0.0260", + "tau": "15.7231", + "tau_err": "0.2021", + "r2": "0.999505", + "png": BASE / "induttore1" / "induttore1.png", + }, + { + "nome": "Induttore 2", + "intervallo": "112.02 – 113.95 s", + "t0": "112.02", + "t_end": "113.95", + "n_punti": "13", + "zona_exc": None, + "A": "158.3430", + "A_err": "0.2088", + "tau": "13.2844", + "tau_err": "0.2183", + "r2": "0.997314", + "png": BASE / "induttore2" / "induttore2.png", + }, + { + "nome": "Induttore 3", + "intervallo": "115.0 – 133.7 s", + "t0": "115.0", + "t_end": "133.7", + "n_punti": "125", + "zona_exc": "115.9 – 117.2 s", + "A": "185.1847", + "A_err": "0.2706", + "tau": "16.2654", + "tau_err": "0.0464", + "r2": "0.993827", + "png": BASE / "induttore3" / "induttore3.png", + }, +] + +def build_doc(): + doc = Document(geometry_options={"margin": "2.5cm"}) + + doc.packages.append(Package("booktabs")) + doc.packages.append(Package("graphicx")) + doc.packages.append(Package("amsmath")) + doc.packages.append(Package("float")) + doc.packages.append(Package("caption")) + doc.packages.append(Package("inputenc", options="utf8")) + + # Titolo + doc.preamble.append(Command("title", "Report Analisi Termica Forno")) + doc.preamble.append(Command("author", "Analisi IR -- Cevolani")) + doc.preamble.append(Command("date", NoEscape(r"\today"))) + doc.append(NoEscape(r"\maketitle")) + + # Introduzione + with doc.create(Section("Modello di fitting")): + doc.append( + "Ogni intervallo è interpolato con il modello di raffreddamento di Newton:" + ) + doc.append(Math(data=[NoEscape( + r"T(t) = T_\infty + A \cdot e^{-(t - t_0)/\tau}" + )], escape=False)) + doc.append(NoEscape( + r"dove $T_\infty = 22.99\,^\circ\mathrm{C}$ è la temperatura ambiente media ponderata. " + r"La regressione non lineare usa il metodo \textit{Trust Region Reflective} (TRF) " + r"di \texttt{scipy.optimize.curve\_fit}." + )) + + # Sezione per ogni induttore + for ind in INDUTTORI: + with doc.create(Section(ind["nome"])): + + with doc.create(Subsection("Intervallo di campionamento")): + with doc.create(Tabular("|l|l|")) as tab: + tab.add_hline() + tab.add_row([bold("Parametro"), bold("Valore")]) + tab.add_hline() + tab.add_row(["Inizio", f"{ind['t0']} s"]) + tab.add_row(["Fine", f"{ind['t_end']} s"]) + tab.add_row(["Numero di punti", ind["n_punti"]]) + if ind["zona_exc"]: + tab.add_row(["Zona esclusa (peso = 0)", ind["zona_exc"]]) + tab.add_hline() + + with doc.create(Subsection("Equazione trovata")): + t0 = ind["t0"] + A = ind["A"] + tau = ind["tau"] + doc.append(Math(data=[NoEscape( + rf"T(t) = 22.99 + {A} \cdot e^{{-(t - {t0}) / {tau}}}" + )], escape=False)) + + doc.append(NoEscape(r"\vspace{4pt}")) + with doc.create(Tabular("|l|l|l|")) as tab: + tab.add_hline() + tab.add_row([bold("Parametro"), bold("Valore"), bold("Incertezza (1σ)")]) + tab.add_hline() + tab.add_row(["A", + NoEscape(rf"${ind['A']}\,^\circ\mathrm{{C}}$"), + NoEscape(rf"$\pm\,{ind['A_err']}\,^\circ\mathrm{{C}}$")]) + tab.add_row([NoEscape(r"$\tau$"), + NoEscape(rf"${ind['tau']}\,\mathrm{{s}}$"), + NoEscape(rf"$\pm\,{ind['tau_err']}\,\mathrm{{s}}$")]) + tab.add_hline() + + doc.append(NoEscape(r"\vspace{4pt}")) + doc.append(NoEscape(rf"$R^2 = {ind['r2']}$")) + + with doc.create(Subsection("Grafico")): + with doc.create(Figure(position="H")) as fig: + fig.add_image(str(ind["png"]), width=NoEscape(r"0.9\textwidth")) + fig.add_caption(f"Fit esponenziale — {ind['nome']} [{ind['intervallo']}]") + + # Tabella riepilogativa + with doc.create(Section("Riepilogo")): + with doc.create(Tabular("|l|l|l|l|l|")) as tab: + tab.add_hline() + tab.add_row([bold("Induttore"), bold("Intervallo [s]"), + bold("A [°C]"), bold(NoEscape(r"$\tau$ [s]")), bold(NoEscape(r"$R^2$"))]) + tab.add_hline() + for ind in INDUTTORI: + tab.add_row([ind["nome"], ind["intervallo"], + ind["A"], ind["tau"], ind["r2"]]) + tab.add_hline() + + out = BASE / "report_completo" + doc.generate_tex(str(out)) + print(f"report_completo.tex generato.") + + try: + doc.generate_pdf(str(out), clean_tex=False, compiler="pdflatex") + print("report_completo.pdf generato.") + except Exception as e: + print(f"Compilazione PDF non disponibile ({e}).") + print("Installa MikTeX o TeX Live per generare il PDF da report_completo.tex.") + +if __name__ == "__main__": + build_doc() diff --git a/report_completo.tex b/report_completo.tex new file mode 100644 index 0000000..51a7204 --- /dev/null +++ b/report_completo.tex @@ -0,0 +1,177 @@ +\documentclass{article}% +\usepackage[T1]{fontenc}% +\usepackage[utf8]{inputenc}% +\usepackage{lmodern}% +\usepackage{textcomp}% +\usepackage{lastpage}% +\usepackage{geometry}% +\geometry{margin=2.5cm}% +\usepackage{booktabs}% +\usepackage{graphicx}% +\usepackage{amsmath}% +\usepackage{float}% +\usepackage{caption}% +% +\title{Report Analisi Termica Forno}% +\author{Analisi IR {-}{-} Cevolani}% +\date{\today}% +% +\begin{document}% +\normalsize% +\maketitle% +\section{Modello di fitting}% +\label{sec:Modellodifitting}% +Ogni intervallo è interpolato con il modello di raffreddamento di Newton:% +\[% +T(t) = T_\infty + A \cdot e^{-(t - t_0)/\tau}% +\]% +dove $T_\infty = 22.99\,^\circ\mathrm{C}$ è la temperatura ambiente media ponderata. La regressione non lineare usa il metodo \textit{Trust Region Reflective} (TRF) di \texttt{scipy.optimize.curve\_fit}. + +% +\section{Induttore 1}% +\label{sec:Induttore1}% +\subsection{Intervallo di campionamento}% +\label{subsec:Intervallodicampionamento}% +\begin{tabular}{|l|l|}% +\hline% +\textbf{Parametro}&\textbf{Valore}\\% +\hline% +Inizio&110.81 s\\% +Fine&111.56 s\\% +Numero di punti&5\\% +\hline% +\end{tabular} + +% +\subsection{Equazione trovata}% +\label{subsec:Equazionetrovata}% +\[% +T(t) = 22.99 + 87.3140 \cdot e^{-(t - 110.81) / 15.7231}% +\]% +\vspace{4pt}% +\begin{tabular}{|l|l|l|}% +\hline% +\textbf{Parametro}&\textbf{Valore}&\textbf{Incertezza (1σ)}\\% +\hline% +A&$87.3140\,^\circ\mathrm{C}$&$\pm\,0.0260\,^\circ\mathrm{C}$\\% +$\tau$&$15.7231\,\mathrm{s}$&$\pm\,0.2021\,\mathrm{s}$\\% +\hline% +\end{tabular}% +\vspace{4pt}% +$R^2 = 0.999505$ + +% +\subsection{Grafico}% +\label{subsec:Grafico}% + + +\begin{figure}[H]% +\centering% +\includegraphics[width=0.9\textwidth]{C:/Users/davide.grilli/Desktop/vs/temperatura/induttore1/induttore1.png}% +\caption{Fit esponenziale — Induttore 1 {[}110.81 – 111.56 s{]}}% +\end{figure} + +% +\section{Induttore 2}% +\label{sec:Induttore2}% +\subsection{Intervallo di campionamento}% +\label{subsec:Intervallodicampionamento}% +\begin{tabular}{|l|l|}% +\hline% +\textbf{Parametro}&\textbf{Valore}\\% +\hline% +Inizio&112.02 s\\% +Fine&113.95 s\\% +Numero di punti&13\\% +\hline% +\end{tabular} + +% +\subsection{Equazione trovata}% +\label{subsec:Equazionetrovata}% +\[% +T(t) = 22.99 + 158.3430 \cdot e^{-(t - 112.02) / 13.2844}% +\]% +\vspace{4pt}% +\begin{tabular}{|l|l|l|}% +\hline% +\textbf{Parametro}&\textbf{Valore}&\textbf{Incertezza (1σ)}\\% +\hline% +A&$158.3430\,^\circ\mathrm{C}$&$\pm\,0.2088\,^\circ\mathrm{C}$\\% +$\tau$&$13.2844\,\mathrm{s}$&$\pm\,0.2183\,\mathrm{s}$\\% +\hline% +\end{tabular}% +\vspace{4pt}% +$R^2 = 0.997314$ + +% +\subsection{Grafico}% +\label{subsec:Grafico}% + + +\begin{figure}[H]% +\centering% +\includegraphics[width=0.9\textwidth]{C:/Users/davide.grilli/Desktop/vs/temperatura/induttore2/induttore2.png}% +\caption{Fit esponenziale — Induttore 2 {[}112.02 – 113.95 s{]}}% +\end{figure} + +% +\section{Induttore 3}% +\label{sec:Induttore3}% +\subsection{Intervallo di campionamento}% +\label{subsec:Intervallodicampionamento}% +\begin{tabular}{|l|l|}% +\hline% +\textbf{Parametro}&\textbf{Valore}\\% +\hline% +Inizio&115.0 s\\% +Fine&133.7 s\\% +Numero di punti&125\\% +Zona esclusa (peso = 0)&115.9 – 117.2 s\\% +\hline% +\end{tabular} + +% +\subsection{Equazione trovata}% +\label{subsec:Equazionetrovata}% +\[% +T(t) = 22.99 + 185.1847 \cdot e^{-(t - 115.0) / 16.2654}% +\]% +\vspace{4pt}% +\begin{tabular}{|l|l|l|}% +\hline% +\textbf{Parametro}&\textbf{Valore}&\textbf{Incertezza (1σ)}\\% +\hline% +A&$185.1847\,^\circ\mathrm{C}$&$\pm\,0.2706\,^\circ\mathrm{C}$\\% +$\tau$&$16.2654\,\mathrm{s}$&$\pm\,0.0464\,\mathrm{s}$\\% +\hline% +\end{tabular}% +\vspace{4pt}% +$R^2 = 0.993827$ + +% +\subsection{Grafico}% +\label{subsec:Grafico}% + + +\begin{figure}[H]% +\centering% +\includegraphics[width=0.9\textwidth]{C:/Users/davide.grilli/Desktop/vs/temperatura/induttore3/induttore3.png}% +\caption{Fit esponenziale — Induttore 3 {[}115.0 – 133.7 s{]}}% +\end{figure} + +% +\section{Riepilogo}% +\label{sec:Riepilogo}% +\begin{tabular}{|l|l|l|l|l|}% +\hline% +\textbf{Induttore}&\textbf{Intervallo {[}s{]}}&\textbf{A {[}°C{]}}&\textbf{$\tau$ [s]}&\textbf{$R^2$}\\% +\hline% +Induttore 1&110.81 – 111.56 s&87.3140&15.7231&0.999505\\% +Induttore 2&112.02 – 113.95 s&158.3430&13.2844&0.997314\\% +Induttore 3&115.0 – 133.7 s&185.1847&16.2654&0.993827\\% +\hline% +\end{tabular} + +% +\end{document} \ No newline at end of file diff --git a/requirements.txt b/requirements.txt index bef2cce..4a791a3 100644 --- a/requirements.txt +++ b/requirements.txt @@ -1,3 +1,4 @@ pandas matplotlib scipy +pylatex