diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/.devcontainer/Dockerfile b/magistrale/Anno 1/Carpi/appunti libro/latext/.devcontainer/Dockerfile new file mode 100644 index 000000000..a43b91816 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/.devcontainer/Dockerfile @@ -0,0 +1,10 @@ +FROM qmcgaw/latexdevcontainer + +# update del package manager +RUN tlmgr update --self + +# installo pacchetti necessari +RUN tlmgr install listings caption xcolor float wrapfig footmisc emoji fontspec emptypage && texhash + +# installo font emoji +RUN apt install fonts-noto-color-emoji \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/.devcontainer/devcontainer.json b/magistrale/Anno 1/Carpi/appunti libro/latext/.devcontainer/devcontainer.json new file mode 100644 index 000000000..54a7db705 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/.devcontainer/devcontainer.json @@ -0,0 +1,51 @@ +{ + "name": "project-dev", + "dockerComposeFile": [ + "docker-compose.yml" + ], + "service": "vscode", + "runServices": [ + "vscode" + ], + "shutdownAction": "stopCompose", + "workspaceFolder": "/workspace", + "postCreateCommand": "", + "extensions": [ + "james-yu.latex-workshop", + // Git + "eamodio.gitlens", + // Other helpers + "shardulm94.trailing-spaces", + "stkb.rewrap", // rewrap comments after n characters on one line + // Other + "vscode-icons-team.vscode-icons", + // spell checker + "streetsidesoftware.code-spell-checker", + "streetsidesoftware.code-spell-checker-italian" + ], + "settings": { + // General settings + "files.eol": "\n", + // vscode + "editor.rulers": [ + 80, + 120 + ], + // Latex settings + "latex-workshop.chktex.enabled": true, + "latex-workshop.latex.recipe.default": "latexmk (lualatex)", + "latex-workshop.latex.clean.subfolder.enabled": true, + "latex-workshop.latex.autoClean.run": "onBuilt", + "editor.formatOnSave": true, + "files.associations": { + "*.tex": "latex" + }, + "latex-workshop.latexindent.path": "latexindent", + "latex-workshop.latexindent.args": [ + "-c", + "%DIR%/", + "%TMPFILE%", + "-y=defaultIndent: '%INDENT%'" + ] + } +} \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/.devcontainer/docker-compose.yml b/magistrale/Anno 1/Carpi/appunti libro/latext/.devcontainer/docker-compose.yml new file mode 100644 index 000000000..763258778 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/.devcontainer/docker-compose.yml @@ -0,0 +1,23 @@ +version: "3.2" + +services: + vscode: + build: . + image: latexdevcontainer + volumes: + - ../:/workspace + # Docker socket to access Docker server + - /var/run/docker.sock:/var/run/docker.sock + # SSH directory + # - ~/.ssh:/root/.ssh + # For Windows without WSL, a copy will be made + # from /tmp/.ssh to ~/.ssh to fix permissions + # - ~/.ssh:/tmp/.ssh:ro + # Shell history persistence + # - ~/.zsh_history:/root/.zsh_history:z + # Git config + - ~/.gitconfig:/root/.gitconfig + environment: + - TZ= + entrypoint: ["zsh", "-c", "while sleep 1000; do :; done"] + \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/.gitignore b/magistrale/Anno 1/Carpi/appunti libro/latext/.gitignore new file mode 100644 index 000000000..732ca25bf --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/.gitignore @@ -0,0 +1,3 @@ +*.pdf +*.synctex.gz +.DS_Store diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/classi_di_complessita_temporale/altri_problemi_np_completi.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/classi_di_complessita_temporale/altri_problemi_np_completi.tex new file mode 100644 index 000000000..40e8885f6 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/classi_di_complessita_temporale/altri_problemi_np_completi.tex @@ -0,0 +1,95 @@ +\section{Altri problemi NP-completi} + +Come già detto, $S A T$ è storicamente il primo esempio naturale di problema $N + P$ completo, ma non è certamente l'unico, anzi, in un certo senso, è il +capostipite di una lunga progenie di esempi. Già nel 1972, dunque un anno dopo +il teorema di Cook-Levin, Karp propose una lista di 21 problemi $N P$-completi +$S$. La strategia usata per riconoscerli tali è meccanica e ripetitiva. Va +infatti provato anzitutto che $S \in N P$, poi che $S$ è $N P$-arduo. +Relativamente al secondo punto basta mostrare che $S A T \leq_p S$ (oppure che +qualche altro problema di cui è nota la $N P$ completezza si riduce +polinomialmente a $S$ ). Tramite $S A T$, o comunque tramite l'altro esempio di +riferimento, si prova allora che tutto $N P$ si riduce in $\leq p$ a $S$; +infatti $\leq_p$ gode della proprietà transitiva: se un dato $S$ soddisfa +$S^{\prime} \leq_p S A T$ e inoltre $S A T \leq_p S$, allora $S^{\prime} \leq_p + S$. Dunque $S$ è $N P$-arduo (e $N P$-completo). In questo modo, Karp procedette +per i suoi 21 problemi. Ma la costruzione dei problemi $N P$-completi non si +esaurì certamente con la lista di Karp e col 1972. Negli anni successivi, nuovi +esempi sono stati scoperti, distribuiti in svariati ambiti di studi e ricerca: +in Informatica, in Matematica, in Biologia, in Chimica, in Enigmistica.\\ + +Qui mostriamo che tutti gli esempi di problemi in $N P$ dati nel paragrafo $6.2$, cioè $3 S A T, 3 C O L, I S, V C$ (o CLIQUE), KNAPSACK, equazioni quadratiche a coefficienti interi, sono $N P$-completi. Nei casi che più ci interessano in futuro (come $3 S A T, 3 C O L, I S$ ), diamo una dimostrazione dettagliata di questa asserzione. Negli altri ci limitiamo a sintetizzare le informazioni essenziali e a fornire possibili riferimenti bibliografici per chi è interessato ad approfondire. + +\paragraph{Teorema 8.7.1} \textit{$3 S A T$ è $N P$-completo.} + +\begin{proof} + Sappiamo che $3 S A T \in N P$, ci basta mostrare che $3 S A T$ è $N P$ + arduo, e anzi, come già spiegato, che $S A T \leq_p 3 S A T$. Cerchiamo dunque + un algoritmo deterministico che lavora in tempo al più polinomiale e traduce + ogni insieme finito $I$ di clausole in un insieme finito $I(3)$ di clausole + con 3 lettere tale che + $$ + I(3) \in 3 S A T \text { se e solo se } I \in S A T \text {. } + $$ + In dettaglio, ad ogni clausola $k$ di $I$ associamo un insieme $I_k$ di + clausole con 3 lettere (eventualmente nuove) nel modo che segue.\\ + Se $k$ consta di un'unica lettera $p_0\left(\text{o } P_0\right)$, prendiamo + due nuove lettere minuscole $q_0, q_1$ e formiamo + $$ + I_k=\left\{p_0 q_0 q_1, p_0 q_0 Q_1, p_0 Q_0 q_1, p_0 Q_0 Q_1\right\} . + $$ + Notiamo che una valutazione $v$ soddisfa $I_k$ se e solo se $v$ soddisfa + $k$, cioè $p_0$ (infatti in nessun caso $v$ può soddisfare + contemporaneamente $q_0 q_1, q_0 Q_1, Q_0 q_1, Q_0 Q_1$ ). Se $k=p_0 p_1$ + consta di due lettere, prendiamo una nuova lettera minuscola $q$ non usata + precedentemente e formiamo + $$ + I_k=\left\{p_0 p_1 q, p_0, p_1 Q\right\} + $$ + Di nuovo, è facile notare che una valutazione $v$ soddisfa $I_k$ se e solo + se $v$ soddisfa $k$, cioè $p_0$ o $p_1$.\\ + Se $k$ ha 3 lettere, si pone $I_k=\{k\}$.\\ + Finalmente assumiamo che $k$ consti di $h \geq 4$ lettere, + $$ + k=p_0 p_1 \cdots p_{h-1} + $$ + Prendiamo $h-3$ nuove lettere + $$ + q_0, \ldots, q_{h-4} + $$ + e formiamo + $$ + I_k=\left\{p_0 p_1 q_0, p_2 Q_0 q_1, p_3 Q_1 q_2, \ldots, p_{h-3} Q_{h-5} q_{h-4}, p_{h-2} p_{h-1} Q_{h-4}\right\} . + $$ + Supponiamo che $v$ sia una valutazione che soddisfa $I_k$ e mostriamo che + $v$ soddisfa anche $k$. Altrimenti + $v\left(p_0\right)=v\left(p_1\right)=\cdots=v\left(p_{h-1}\right)=0$. Da + $v\left(p_0\right)=v\left(p_1\right)=0$ + + deduciamo $v\left(q_0\right)=1$ perché $p_0 p_1 q_0 \in I_k ;$ così $v\left(Q_0\right)=0$ e deve essere $v\left(q_1\right)=$ 1 perché $p_2 Q_0 q_1 \in I_k$. Ripetendo il procedimento si deduce $v\left(q_{h-4}\right)=1$ e quindi $v\left(Q_{h-4}\right)=0$. Ma anche $v\left(p_{h-2}\right)=v\left(p_{h-1}\right)=0$, e questo è impossibile perché $p_{h-2} p_{h-1} Q_{h-4} \in I_k$.\\ + Viceversa, sia $v$ una valutazione che soddisfa $k$, mostriamo che c'è qualche valutazione $v_k$ che estende $v$ e soddisfa $I_k$. Per ipotesi esiste $j1$ in base 2. Il loro numero è + $2^{l-1}$ perché essi si compongono di $l$ cifre, ciascuna delle quali + può assumere i valori 0,1, salvo la prima che è ovviamente 1. Per + esempio, i numeri di 4 cifre in base 2 + $$ + 1000,1001, \ldots, 1111 + $$ + sono $2^3=8$.\\ + Possiamo cercare le possibili soluzioni intere della + nostra equazione prima fissandone la lunghezza (limitata!) e poi + procedendo per tentativi, coinvolgendo cioè ogni possibile coppia $(X, + Y)$ di lunghezza lecita $l$; ma si tratta di un meccanismo + esponenzialmente lungo essendo $2^{l-1}$ i casi da esaminare + per $X$ o per $Y$, fissata $l$. Pur tuttavia, se la soluzione $(X, Y)$ + è nota, verificarla, controllare cioè $a X^2+b Y=c$, è compito che si + può svolgere con rapidità.\\ + In conclusione, $a x^2+b y=c$ ha radici + intere se e solo se esistono $X, Y$ di lunghezza polinomialmente + limitata da quella di $a, b, c$ per cui $a X^2+b Y=c$. Il problema è + quindi in $N P$. + + \item Consideriamo adesso grafi finiti $G = (V, E)$. Introduciamo le + seguenti definizioni: un sottoinsieme $V_0$ di $V$ si dice + \begin{itemize} + \item \textit{indipendente} se, per ogni scelta di $v, v^{\prime} + \in V_0,\left(v, v^{\prime}\right) \notin E$; + \item un \textit{ricoprimento} di vertici se, per ogni scelta di + $v, v^{\prime} \in V$ con $\left(v, v^{\prime}\right) + \in$ $E, v \in V_0$ o $v^{\prime} \in V_0$ + \item una \textit{cricca} (in inglese, clique) se, per ogni scelta + di $v, v^{\prime} \in V_0 \operatorname{con} v \neq + v^{\prime}$, $\left(v, v^{\prime}\right) \in E$. + \end{itemize} + Ricordiamo che la nostra definizione di grafo esclude $(v, v) \in E$ + per $v \in V$. $\mathrm{Ci}$ interessano i seguenti tre problemi. + \begin{enumerate} + \item $I S=$ problema dell'insieme indipendente. + \begin{itemize} + \item INPUT: $(V, E)$ grafo finito, $k$ intero positivo + minore o uguale della cardinalità $|V|$ di $V$. + \item OUTPUT: Sì/NO secondo che $(V, E)$ abbia un + sottoinsieme indipendente $V_0$ di $k$ vertici. + \end{itemize} + \item $V C=$ problema del ricoprimento dei vertici. + \begin{itemize} + \item INPUT: $(V, E), k$ come sopra. + \item OUTPUT: Si/NO secondo che $(V, E)$ abbia un + ricoprimento di $k$ vertici. + \end{itemize} + \item CLIQUE = problema della cricca. + \begin{itemize} + \item INPUT: $(V, E), k$ come sopra. + \item OUTPUT: Sİ/NO secondo che $(V, E)$ contenga una + cricca di $k$ vertici. + \end{itemize} + + \end{enumerate} + + I tre problemi sono, in realtà, lo stesso, nel senso che segue. + Notiamo anzitutto che in un grafo $(V, E)$ un sottoinsieme $V_0$ è + indipendente se e solo se $V-V_0$ è un ricoprimento (il lettore può + verificare il motivo con un facile esercizio). Inoltre $V_0$ è + indipendente in $(V, E)$ se e solo se $V_0$ è una cricca nel grafo che + si ottiene da $(V, E)$ mantenendone i vertici, ma collegandone due + (distinti) tra loro se e solo se non sono uniti da lati in $E$. Per + esempio $v_0, v_2$ formano un insieme indipendente nel seguente grafo + $(V, E)$ + \begin{center} + \begin{tikzpicture} + \node (V0) at (2.5, 3) {$V_0$}; \node (V1) at (1, 1) {$V_1$}; + \node (V2) at (4, 1) {$V_2$}; + + \draw[-] (V1) -- (V0); + \end{tikzpicture} + \end{center} + + e una cricca nel grafo che se ne ottiene nel modo sopra descritto. + \begin{center} + \begin{tikzpicture} + \node (V0) at (2.5, 3) {$V_0$}; \node (V1) at (1, 1) {$V_1$}; + \node (V2) at (4, 1) {$V_2$}; + + \draw[-] (V0) -- (V2); \draw[-] (V2) -- (V1); + \end{tikzpicture} + \end{center} + Dunque procedimenti per riconoscere un insieme indipendente si + adattano a controllare anche i ricoprimenti dei vertici, o le cricche. + Anzi la traduzione di un'istanza di $I S$ a una di $V C$, o di $C L I + Q U E$, o viceversa, avviene in modo polinomialmente limitato dalle + dimensioni dei grafi coinvolti. Non è tuttavia chiaro se IS (o $V C$ o + CLIQUE) siano in $P$. In effetti, i sottoinsiemi con $k$ elementi di + un insieme $V$ con $n$ elementi sono + $$ + \left(\begin{array}{l} + n \\ + k + \end{array}\right)=\frac{n !}{k !(n-k) !} + $$ + (talora "troppi" rispetto a $n$ e $k$; infatti, quando $k$ si accosta + a $\frac{n}{2},\left(\begin{array}{l}n \\ k\end{array}\right)$ + approssi$\left.\operatorname{ma} 2^k\right)$ Tuttavia, ciascuno di + essi ha, appunto, $k \leq n$ elementi e il controllo di un eventuale + $V_0$, cioè la verifica che i suoi vertici lo rendono indipendente + perché sono comunque scollegati (oppure un ricoprimento perché capaci + di coinvolgere ogni lato in $E$, oppure ancora una cricca perché, se + distinti, congiunti da un opportuno lato), si può svolgere + semplicemente osservando il grafo $(V, E)$, e più direttamente + $V_0$.\\ + Così $I S, V C, C L I Q U E$ sono in $N P$. + \item KNAPSACK\\ + Il Problema dello Zaino, o KNAPSACK secondo la terminologia ufficiale + e la lingua inglese, è la questione che in genere affligge la notte + prima della partenza per le vacanze: abbiamo uno zaino di volume $V$ + da riempire e vogliamo infilarci $n$ oggetti ognuno con un determinato + volume: ciascuno di essi ci pare, infatti, indispensabile per il buon + esito delle nostre ferie. $\mathrm{Ci}$ chiediamo se possiamo + sceglierne alcuni in modo da colmare esattamente lo zaino. Assumiamo + poi che lo zaino non sia rigido e si presti ad essere deformato in + ogni modo possibile, così che la soluzione dipenda solo dal volume + degli oggetti coinvolti, e non dalla loro figura. Formalmente abbiamo + \begin{itemize} + \item INPUT: uno zaino di volume $V$ e $n$ oggetti $0,1, \ldots, + n-1$, rispettivamente di volume $v(0), \ldots, v(n-1)$; assumiamo + $n, V, v(0), \ldots, v(n-1)$ interi positivi; + \item OUTPUT: SÍ/NO secondo che esista un sottoinsieme $I$ di + $\{0, \ldots, n-1\}$ tale che + \end{itemize} + $$ + V=\sum_{i \in I} v(i) . + $$ + L'esperienza comune ci insegna che la questione è tutto meno che + semplice: in genere, la sera prima delle ferie, i tentativi si + sprecano e le ore volano prima che gli oggetti siano finalmente + sistemati, se mai lo possono essere in modo soddisfacente. Del resto, + la difficoltà ha un suo logico fondamento e non è evidente se $K N A P + S A C K$ sia in $P$, visto che le possibili combinazioni di oggetti da + infilare nello zaino sono tante quanti i sottoinsiemi di $\{0,1, + \ldots, n-$ $1\}$, e cioè $2^n$. Non v'è dubbio però che il problema + stia in $N P$ : se conosciamo l'opportuno insieme $I$, verificare che, + appunto, $V=\sum_{i \in I} v(i)$ (in relazione agli input $n, V, v(0), + \ldots, v(n-1))$ è controllo rapido e di poca fatica. +\end{enumerate} + +Dopo tanti esempi, ecco una semplice osservazione che collega la classe $P$ +considerata nel precedente paragrafo e la nuova classe $N P$. Ricordiamo che $P$ +include tutti e soli i problemi che hanno algoritmo "rapido" di decisione; +invece, in base alle osservazioni e agli esempi di questo paragrafo, $N P$ può +essere considerata come la classe dei problemi che hanno algoritmo "rapido" di +verifica della soluzione. È naturale ammettere che trovare una soluzione sia più +difficile che verificarla. In altre parole, si ha: + +\paragraph{Teorema 8.2.1} $P \subseteq N P$. + +\begin{proof} + Sia $S \in P$. Guardiamo alla definizione di $N P$ e poniamo + $$ + S^{\prime}=S, p_S=1(\text { anzi } y=\emptyset \text { per ogni } w \text { ). } + $$ + $S^{\prime}, p_S$ testimoniano $S \in P$. +\end{proof} + + +Come nel caso di $P$ e coP, possiamo ora introdurre: + +\paragraph{Definizione.} $coNP$ è la classe dei problemi $S$ su +alfabeti finiti $A$ tali che il complementare $S^c=A^{\star}-S$ di $S$ è in $N + P$.\\ + +Stavolta, però, non è affatto chiaro che $\operatorname{coN} N=N P$. Il lettore +può cercare di intuire le difficoltà che emergono a questo proposito, oppure +attendere il paragrafo $8.9$ dove le descriveremo in maggior dettaglio. diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/classi_di_complessita_temporale/la_classe_p_e_la_tesi_di_edmondscookkarp.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/classi_di_complessita_temporale/la_classe_p_e_la_tesi_di_edmondscookkarp.tex new file mode 100644 index 000000000..9f0670f59 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/classi_di_complessita_temporale/la_classe_p_e_la_tesi_di_edmondscookkarp.tex @@ -0,0 +1,603 @@ +\section{La classe \textit{P} e la Tesi di Edmonds-Cook-Karp} + +Lavoriamo con un alfabeto finito $A$ e con $S \subseteq A^{\star}$. Ricordiamo +che una macchina di Turing $M$ su $A$ decide $S$ se $M$ converge su tutti gli +input $w \in A^{\star}$ e, + +\begin{itemize} + \item se $w \in S$, risponde "SI" (produce cioè un output convenzionalmente + identificato con "SI"), + \item se $w \notin S$, risponde "NO" (allo stesso modo). +\end{itemize} + + +Si dice invece che $M$ accetta $S$ se, per ogni $w \in A^{\star}$, + +\begin{itemize} + \item se $w \in S, M$ converge su $w$, + \item se $w \notin S, M$ diverge su $w$. +\end{itemize} + + +È da ribadire che, in generale, le due nozioni, decidere e accettare, non +coincidono. L'alternativa convergere/divergere non può sostituire le risposte +sì/no. Infatti non è possibile a priori realizzare che una macchina di Turing +diverge; un osservatore esterno vede sviluppare la computazione per $1,10,10^2, + 10^3, \ldots, 10^n, \ldots$ passi, ma non può prevedere se $M$ convergerà al +passo successivo oppure continuerà a lavorare all'infinito.\\ +Ciò premesso, +vediamo come sia possibile misurare la complessità di una macchina di Turing $M$ +su un alfabeto finito $A$, privilegiando il parametro tempo. Facciamo quindi +riferimento al numero dei passi delle computazioni convergenti di $M$. +Specificamente definiamo una funzione $c_M$ (complessità temporale di $M$ ) come +segue: per ogni $n \in \mathbb{N}, c_M$ è definita su $n$ se e solo se esiste +almeno un input di lunghezza $\leq n$ su cui $M$ converge e, in tal caso, +$c_M(n)$ è il massimo numero di passi di una tale computazione di $M$. Notiamo +che, siccome $A$ è finito, c'è al più un numero finito di parole su $A$ di +lunghezza $\leq n$. Quindi c'è un numero finito di computazioni convergenti su +tali input e dunque, tra esse, ce n'è una di lunghezza massima. In conclusione +$q_M$ è ben definita. Possiamo anche ragionevolmente ammettere che una tale +funzione $c_M($ da $\mathbb{N}$ a $\mathbb{N})$ soddisfi (i), (ii), (iii). +Escludere (i) significa infatti supporre che $M$ non converga mai, su nessun +input: situazione ammissibile, ma di nessun interesse pratico. +(ii) è condizione facile da accettare. Quanto a (iii), contraddirla significa +ammettere che $M$, quando converge, lo fa in un numero prefissato di passi, a +prescindere dalla lunghezza dell'input che le viene proposto. Di nuovo, si +tratta di situazione possibile, ma certamente non interessante dal punto di +vista pratico. Così possiamo assumere (i), (ii), (iii) per $c_M$. Si tratta ora +di decidere, in riferimento all'analisi finale del paragrafo precedente, quali +condizioni su $c_M$ possono certificare che $M$ è efficiente rispetto al tempo +(cioè rapida) nelle sue computazioni. C'è una proposta a questo proposito, +avanzata a metà degli anni sessanta da Edmonds, anticipata comunque da von +Neumann, Rabin e Cobham, e poi ribadita da Cook e Karp, la quale afferma, a +livello di slogan, che +$$ + \text { rapido }=\text { polinomiale } \text {. } +$$ +In termini rigorosi, poniamo la seguente \paragraph{Definizione.} $P$ è la +classe dei problemi $S$ su alfabeti finiti $A$ per i quali c'è una macchina di +Turing $M$ su $A$ che accetta $S$ e ha complessità $c_M=O\left(n^k\right)$ per +qualche intero positivo $k$.\\ + +Dunque la $\operatorname{MdT} M$, di fronte ad un input $w \in A^{\star}$ di +lunghezza $n$, + +\begin{itemize} + \item se $w \in S$, converge su $w$ in al più $c \cdot n^k$ passi (dove $c$ + è una costante reale positiva prefissata); + \item se $w \notin S$, diverge su $w$. +\end{itemize} + +Conviene aprire una breve parentesi a proposito della definizione ora data. +Abbiamo infatti tenuto a sottolineare in precedenza la differenza tra decidere e +accettare $S$. In generale, questa distinzione va ben tenuta presente. Ma, nel +caso particolare ora in esame, sappiamo che la MdT $M$ sull'input $w$, se +converge, lo fa entro $c \cdot n^k$ passi, dove $n$ è la lunghezza di $w$. Così +possiamo dedurre che, se non c'è stata convergenza entro il passo $c \cdot n^k, + M$ certamente divergerà. Dunque è possibile controllare anche la divergenza e, +nella situazione che viene a crearsi, + +\begin{center} + rispondere \textit{SI/NO} +\end{center} + +equivale perfettamente a + +\begin{center} + \textit{convergere/divergere}. +\end{center} + +Ciò premesso, possiamo enunciare con maggior precisione la + +\paragraph{Tesi di Edmonds-Cook-Karp.} Sia $S$ un insieme di parole su un +alfabeto finito A. Allora $S$ ha un algoritmo rapido di decisione se e solo se +$S \in P$.\\ + +Si stabilisce dunque che un problema è computabile quando la sua soluzione +richiede tempo al più polinomiale nella lunghezza dell'input. La parola tesi è +da intendersi qui come nel caso di Church-Turing, descritto nella prima parte. +Non è un teorema, o un assioma; è solo una ipotesi di lavoro con qualche base +sperimentale, eventualmente da discutere (ne parleremo tra qualche riga), da +accettare finché l'evidenza la sostiene, da rivedere, correggere, adeguare +altrimenti. + +\paragraph{Commenti sulla Tesi di Edmonds-Cook-Karp.} + +\begin{itemize} + \item La tesi di Edmonds-Cook-Karp si riferisce non tanto agli algoritmi + quanto ai problemi. Individua i problemi "rapidamente" risolubili come + quelli che ammettono un algoritmo (cioè una macchina di Turing) che li + decide (equivalentemente, li accetta) in tempo al più polinomiale nella + lunghezza dell'input. + \item Dunque la tesi esclude che un problema i cui algoritmi lavorano tutti in + tempo almeno esponenziale $2^n$ possa ritenersi di rapida soluzione: + affermazione che pare facilmente condivisibile se si ricorda quanto rapidamente + crescono le potenze $2^n$ di 2 all'aumentare dell'esponente $n$. + \item Viceversa la tesi afferma che, se c'è un algoritmo che decide (o accetta) + un problema in tempo al più polinomiale $O\left(n^k\right)$, allora il problema + ha rapida soluzione. Questa seconda osservazione appare assai più discutibile, + per almeno due motivi. + \begin{enumerate} + \item Quanto rapido è un algoritmo che lavora in tempo $n^{10^6}, n^{10^9}$, + oppure $n^{5 \cdot 10^{17}}$ rispetto alla lunghezza dell'input? (Ricordiamo + che $5 \cdot 10^{17}$ secondi è il tempo stimato dall'inizio dell'universo + ad oggi secondo la teoria del Big Bang). + \item Non va dimenticato il ruolo della costante $c$ nella definizione di $O$. + Se $c$ è enormemente grande, per esempio $5 \cdot 10^{17}$, anche per $k$ + piccolo, quanto rapido può ritenersi un algoritmo che lavora in tempo $c \cdot + n^k$ rispetto alla lunghezza $n$ dell'input? + \end{enumerate} + Sotto questo punto di vista, possono esserci ragionevoli riserve all'adozione + della tesi di Edmonds-Cook-Karp. D'altra parte, da un punto di vista teorico, + + \begin{itemize} + \item possiamo ad esempio ammettere che algoritmi che lavorano in tempo al + più lineare $O(n)$, o al più quadratico $O\left(n^2\right)$ nella lunghezza + dell"input siano "rapidi"; + \item una volta concordato che algoritmi che impiegano tempo $O\left(n^k\right)$ + (per un qualche intero positivo $k$ ) sono rapidi, quale motivo può indurci ad + escludere come "lenti" quelli che richiedono tempo $O\left(n^{k+1}\right)$ ? + \end{itemize} +\end{itemize} + +Così la tesi di Edmonds-Cook-Karp è comunemente accettata, pur con i dubbi sopra riferiti.\\ +Vediamo adesso alcuni esempi, più o meno difficili e famosi, di problemi che stanno in $P$ ( e sono dunque da ritenersi di "rapida" soluzione). + +\paragraph{Esempi.} +\begin{enumerate} + \item Grafi 2-colorabili $(2 C O L)$.\\ + Ricordiamo che un grafo è̀ una struttura $G=(V, E)$ dove $V$ è un + insieme non vuoto ed $E$ è una relazione binaria su $A$ irriflessiva e + simmetrica (in altre parole, nessun $v \in V$ è in relazione con se + stesso e dunque soddisfa $(v, v) \in$ $E$; se poi $v, w \in V$ e $(v, + w) \in E$, allora anche $(w, v) \in E)$.\\ + Possiamo dunque pensare gli elementi $v$ di $V$ come possibili tappe + da raggiungere, e le coppie $(v, w) \in E$ come strade dirette che li + congiungono. In effetti, + i punti di $V$ si chiamano vertici e le coppie di $E$ lati. Nessun + lato può unire un vertice a se stesso per la irriflessività, ma ogni + lato è a doppio senso (per la simmetria). La sequenza di vertici $v_0, + v_1, \ldots, v_{n-1}$ viene detta cammino di lunghezza $n$ se, per + ogni $i0$, si divide $a$ per $b, b$ per l'eventuale resto + non nullo $r_0$, e così via finché non si trova un resto nullo $r_s$; + l'ultimo resto non nullo $r_{s-1}$ è $(a, b)$.\\ + Se la procedura si + ferma subito, cioè $(a, b)=b, b$ si scrive $a \cdot 0+b \cdot 1$, + dunque si pone $X=0, Y=1$. Altrimenti, si procede per induzione sul + numero $s$ dei passi necessari per determinare $(a, b)$. Ammettiamo + così di aver ottenuto la decomposizione di $\left(b, r_0\right)$ (il + cui calcolo richiede un passo in meno rispetto ad $(a, b))$ e di aver + provato $\left(b, r_0\right)=b X^{\prime}+r_0 Y^{\prime}$ per + $X^{\prime}, Y^{\prime}$ interi opportuni; ricordiamo $a-b q_0=r_0$ + per qualche $q_0$ e deduciamo + + $$(a, b)=\left(b, r_0\right)=b + X^{\prime}+r_0 Y^{\prime}=b X^{\prime}+\left(a-b q_0\right) + Y^{\prime}=a Y^{\prime}+b\left(X^{\prime}-q_0 Y^{\prime}\right) + $$ + + , così $X=Y^{\prime}$ e $Y=X^{\prime}-q_0 Y^{\prime}$ soddisfano quanto + l'identità di Bézout richiede. Anzi si noti che $X, Y$ così + determinati hanno lunghezza polinomialmente limitata da quella dei + coefficienti $a, b, c$. Infatti, la proprietà è ovvia quando $X=0, + Y=1$, e si preserva ad ogni passo induttivo; così ci basta ricordare + che $X, Y$ sono calcolati entro $S$ passi dove $S \leq \log _2 N$.\\ + + Torniamo adesso al nostro problema di esistenza di soluzioni intere + per $a x+$ $b y=c$. È facile tracciare un programma che lo risolve: + dati $a, b, c$, + + \begin{itemize} + \item calcoliamo $(a, b)$ (per esempio tramite l'algoritmo + euclideo delle divisioni successive), + \item controlliamo poi se $(a, b)$ divide o no $c$. + \end{itemize} + + L'esistenza di soluzioni intere corrisponde infatti ad una risposta + positiva all'ultima verifica.\\ + Questa procedura pone il problema in + $P$. Infatti i tempi di lavoro sono più o meno quelli dell'algoritmo + di Euclide, visto che la divisione finale di $c$ per $(a, b)$ e il + calcolo del relativo resto non incidono significativamente, e sappiamo + dal Capitolo 5 che il procedimento di Euclide impiega tempo al più + polinomiale, anzi quadratico, rispetto alla lunghezza degli input $a, + b$. + \item \textit{PRIMI}\\ + L'ultimo esempio che vogliamo citare riguarda un + problema famoso e datato, che risale ai tempi di Euclide, e dunque a 2 + millenni or sono, e anche più.\\ + È dato: + + \begin{itemize} + \item INPUT: un intero $N>1$; mentre + \item OUTPUT: consiste nel + \begin{enumerate}[label=(\alph*)] + \item rispondere $SI/NO$ secondo che $N$ sia primo, o composto; + o addirittura + \item decomporre $N$ nei suoi fattori primi. + \end{enumerate} + + \end{itemize} + + Ricordiamo che $N$ è primo se non ha divisori naturali diversi da 1 e + da $N$ e che ogni intero maggiore di 1 si decompone in modo unico nel + prodotto di fattori primi. Come si vede, la questione è duplice. + Infatti, per $N$ composto, a) si accontenta di saperlo, b) pretende + invece di conoscere $i$ divisori non banali di $N$. a) è poi un + problema di decisione, b), invece, un problema di computazione. + Come detto, la questione è classica, eppure ancora attuale, visto + che molti protocolli crittografici (usati per esempio per garantire + transazioni sicure in rete), si basano sulle attuali conoscenze e + ignoranze su algoritmi di primalità e fattorizzazione. Pur tuttavia, + metodi molto semplici riescono a soddisfare l'una e l'altra questione. + Vediamone uno.\\ + Dato $N$, si divide $N$ per ogni numero $q$ tale che $10$ per $n>4$. Inoltre $f$ è crescente per $n \geq 4$. + \item Anche la + funzione $f(n)=2^n$, per ogni $n \in \mathbb{N}$, soddisfa (i), (ii), (iii). + \item Lo stesso vale per + $$ + f(n)=2^{2^n} \text{, } f(n)=2^{2^{2^n}} \text{, } f(n)=2^{2^{\iddots^{2^n}}}, + $$ + o + $$ + f(n)=2^{2 n}, f(n)=2^{n^2},(n \in \mathbb{N}) + $$ + e così via. Tutte queste funzioni sono ovunque definite, crescenti e illimitate. + \item La funzione $n \mapsto \log _2 n$ è definita per $n>0$, assume valori reali + $\geq 0$ per $n \geq 1$, è poi crescente e non limitata. I suoi valori non + corrispondono però in genere a numeri naturali, tranne il caso in cui $n$ sia + una potenza di 2 , cioè $n=2^t$ con $t$ (allora $\log _2 n=t$ ). Tuttavia, se + sostituiamo, per ogni $n$, $\log _2 n$ con la parte intera $\left\lfloor\log _2 + n\right\rfloor$ di $\log _2 n$, cioè con il massimo naturale $\leq \log _2 n$, + otteniamo una funzione $L$ ancora definita per $n \geq 1$, crescente e + illimitata, tale dunque da soddisfare le condizioni (i), (ii), (iii), e in più a + valori naturali. Si ha infatti + $$ + L(1)=\log _2 1=0, L(2)=L(3)=1, L(4)=\cdots=L(7)=2 \text { e così via } + $$ +\end{enumerate} + +Naturalmente ci possiamo attendere esempi più "irregolari" di quelli sin qui +proposti, come la funzione +$$ + \begin{gathered} + f(0)=f(1)=f(2)=\cdots=f(29)=1 \\ + f(n)=2^n \text { per } n \geq 30, + \end{gathered} +$$ +(che coincide con l'esponenziale da 30 in poi, ha comportamento autonomo prima), +o casi ancora peggiori. Anche $f$ soddisfa (i), (ii), (iii). Del resto $f$ +coincide asintoticamente con l'esponenziale $n \mapsto 2^n$.\\ +Le funzioni che ci +interessano sono dunque quelle che obbediscono a (i), (ii), (iii). Infatti, +quando esse corrispondono ad un particolare algoritmo nel modo sopra descritto, +possono ben costituire un indice della sua efficienza. Ma in relazione a quanto +già detto all'inizio del paragrafo, non ha gran senso lasciarsi condizionare da +un singolo valore di $f$, come $f(10)$ (che si limita comunque ad un campione +parzialissimo di input, quelli di lunghezza $\leq 10$ ), ci interessa piuttosto +uno studio generale del grafico di $f$, in particolare il suo comportamento +asintotico, quando $n$ tende a farsi grande (e si avvicina a $+\infty$ +). In altre parole, date $f, g$ che soddisfano (i), (ii), (iii), per dichiarare +$f$ "migliore" di $g$ (e dunque la procedura di $f$ più efficiente di quella di +$g$ ) non basta notare +$$ + f(10) \leq g(10) +$$ +ma occorre qualcosa di più significativo. Si dà a questo proposito la seguente +definizione. Assumiamo di trattare funzioni $f, g, \ldots$ per cui valgano (i), +(ii), (iii). + +\paragraph{Definizione} Si pone $f=O(g)$ se e solo se esistono un naturale +$N_0$ e un reale positivo $c$ tale che +$$ + f(n) \leq c \cdot g(n) \text {, per ogni } n \geq N_0 . +$$ +La relazione ora introdotta tra le nostre funzioni stabilisce dunque un +confronto asintotico tra $f$ e $g ; f=O(g)$ vale, parlando alla buona, se da un +certo $N_0$ in poi, $g(n)$ domina $f(n)$ a meno della costante $c$. Tale +relazione è chiaramente riflessiva e transitiva (cioè si ha $f=O(f)$ per ogni +$f$, e se $f=O(g)$ e $g=O(h)$, allora $f=O(h)$ per ogni scelta di $f, g, h$, +come è facile verificare). Non è tuttavia antisimmetrica, non costituisce cioè +una relazione di ordine parziale. Per esempio. per $f(n)=n$ e $g(n)=2 n$ per +ogni $n \in \mathbb{N}, f \neq g$ ma $f=O(g)$ (perché $f(n) \leq g(n)$ per ogni +$n \in \mathbb{N}$ ), $g=O(f)$ (perché $g(n) \leq 2 f(n)$ per ogni $n \in + \mathbb{N}$, dunque per $c=2$ ). Si ha comunque il seguente + +\paragraph{Teorema 7.2.1} \textit{Siano $f, g$ tali da soddisfare (i), (ii), (iii).} +\begin{enumerate} + \item Se $\lim _{n \rightarrow+\infty} + \frac{f(n)}{g(n)}=l \neq 0$, allora $f=O(g)$ e $g=O(f)$. + \item Se $\lim _{n + \rightarrow+\infty} \frac{f(n)}{g(n)}=0$, ovvero $\lim _{n \rightarrow+\infty} + \frac{g(n)}{f(n)}=+\infty$, allora $f=O(g)$ ma $g \neq O(f)$ +\end{enumerate} + +\begin{proof} + Notiamo che (iii) assicura che $g(n) \neq 0$ e dunque che il + rapporto $\frac{f(n)}{g(n)}$ ha senso per ogni $n$ abbastanza grande. Ciò + premesso, 1) e 2) sono facili conseguenze della definizione di limite. Vediamo i + dettagli. + \begin{enumerate} + + \item Anzitutto $l>0$ perché $f, g$ hanno valori naturali. Per ogni reale + $\varepsilon>0$ (senza perdita di generalità, $\varepsilon0$ naturale tale che, per ogni $n \geq N_{\varepsilon}$, + $$ + l-\varepsilon<\frac{f(n)}{g(n)}0$; otteniamo + $$ + g(n)<\frac{1}{l-\varepsilon} \cdot f(n), \text { per ogni } n \geq N_{\varepsilon} + $$ + che ancora basta a dedurre $g=O(f)$ per $c=\frac{1}{l-\varepsilon}$. + \item Per ogni + $\varepsilon>0$, esiste $N_{\varepsilon}$ tale che, per ogni $n \geq + N_{\varepsilon}, \frac{f(n)}{g(n)}<\varepsilon$, cioè $f(n)<$ $\varepsilon \cdot + g(n)$. Allora $c=\varepsilon$ garantisce $f=O(g)$. Invece $g=O(f)$ impone $g(n) + \leq$ $c \cdot f(n)$ per $c>0$ opportuno e per ogni $n$ sufficientemente grande. + Ne segue $\frac{f(n)}{g(n)} \geq \frac{1}{c}>0$ per ogni $n$ grande, e questo + esclude $\lim _{n \rightarrow+\infty} \frac{f(n)}{g(n)}=0$. + \end{enumerate} +\end{proof} \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/complessita/introduzione.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/complessita/introduzione.tex new file mode 100644 index 000000000..14b64eb0d --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/complessita/introduzione.tex @@ -0,0 +1,270 @@ +\section{Introduzione} + +Nella prima parte degli appunti abbiamo proposto ed approfondito la definizione +astratta del concetto di computabilità fornita da Church, Turing e altri. Sulla +sua base si possono finalmente distinguere i problemi $S$ che sono computabili +da quelli che non lo sono. Ma, anche quando $S$ corrisponde al primo caso, può +capitare che i migliori algoritmi che lo risolvono richiedano costi +irraggiungibili nella pratica: impiegano tempi proibitivi, o necessitano di +risorse di memoria ed energia che nessun calcolatore può assicurare. Questi +problemi $S$, pur computabili in teoria, non lo sono in realtà. Ma allora la +nozione di computabilità affermata dalla tesi di Church-Turing va forse +rimeditata e riveduta in riferimento ai costi effettivi che le computazioni +richiedono. Concentriamo dunque, in questa seconda parte degli appunti, la nostra +attenzione su quei problemi che possono comunque risolversi con opportuni +programmi, e vogliamo misurare quali sono le risorse minime richieste da questa +soluzione; valutare dunque l'efficienza dei relativi algoritmi e il costo delle +loro computazioni. L'attenzione a questo argomento si è risvegliata in modo +naturale con l'avvento e lo sviluppo dei calcolatori. Infatti gli strumenti +moderni e la loro potenza computazionale permettono di gestire situazioni sempre +più difficili e affrontare input sempre più complicati. Nasce allora l'esigenza +di trovare programmi rapidi e poco costosi per trattare queste situazioni. Del +resto è facile osservare, come l'uso di tecniche appropriate possa produrre +significativi miglioramenti a questo proposito. Citiamo alcuni esempi abbastanza +intuitivi, attinti dalla Matematica elementare. + +\paragraph{Esempi} + +\begin{enumerate} + \item Ammettiamo di dover + calcolare il valore di un dato polinomio + $$ + x^7+5 x^6+2 x^4+12 x^3+5 x^2+2 x+21 + $$ + per certi input $x$. Un semplice controllo mostra come la computazione + richiede, se il polinomio è proposto nella forma appena descritta, + \begin{itemize} + \item 6 moltiplicazioni (per ottenere $x^7$), + \item 6 moltiplicazioni $\left(\operatorname{per} 5 x^6\right)$, + \item 4 moltiplicazioni (per $\left.2 x^4\right)$, + \item 3 moltiplicazioni (per $\left.12 x^3\right)$, + \item 2 moltiplicazioni (per $5 x^2$ ), + \item 1 moltiplicazioni (per $2 x$ ), + \end{itemize} + + (dunque complessivamente 22 moltiplicazioni) e 6 addizioni. Se però + riscriviamo il polinomio come + $$ + \left(\left(\left(\left((x+5) x^2+2\right) x+12\right) x+5\right) x+2\right) x+21 + $$ + ci vengono richieste ancora 6 addizioni, ma solamente 5 + moltiplicazioni; il risparmio è ovvio. + \item Ammettiamo di dover + calcolare il massimo comun divisore $(a, b)$ di due interi positivi + $a, b$. Immaginiamo naturalmente che $a$ e $b$ siano molto grandi, e + si compongano di molte cifre rispetto alla tradizionale base 10 . Il + metodo più familiare, quello che si impara sin dalle scuole medie, è + \begin{itemize} + + \item decomporre $a, b$ in fattori primi, + \item ottenere $(a, b)$ come prodotto + + \end{itemize} + dei fattori primi occorrenti in entrambe le decomposizioni, presi con + il loro esponente minimo. + + Il procedimento non è tuttavia facile da svolgere per $a, b$ grandi: + infatti, non sono attualmente conosciuti algoritmi soddisfacentemente + rapidi di decomposizione in fattori primi. Funziona invece molto + meglio l'algoritmo delle divisioni successive di Euclide, che + ricapitoliamo brevemente. Per $a \geq b$, + + \begin{itemize} + + \item dividiamo $a$ per $b$, con + resto $r_0$ e quoziente $q_0, a=b q_0+r_0, r_0$ + $\left.r_0>r_1>r_2>\cdots\right)$ + $$ + r_{s-2}=r_{s-1} q_s, r_s=0 . + $$ + + Ovviamente l'ultimo resto non nullo $r_{s-1}$ è il massimo comun + divisore di $r_{s-2}$ e $r_{s-1}$ e non è difficile controllare, osservando + tutte le uguaglianze corrispondenti alle varie divisioni, che $r_{s-1}$ è anche + il massimo comun denominatore richiesto $(a, b)$. Il suo calcolo è costato un + numero di divisioni che è ovviamente molto minore di $b$ e si rivela comunque di + gran lunga preferibile all'approccio mediante decomposizione in fattori primi, + come vedremo in maggior dettaglio più tardi: lo si può svolgere in un numero di + passi approssimato in qualche senso dal quadrato del logaritmo in base 10 di + $a$. + \item In algebra lineare si imparano a risolvere sistemi di $m$ equazioni + lineari in $n$ incognite. Ammettiamo $m=n$ per semplicità. Per $n=2$, + consideriamo per esempio + $$ + \left\{\begin{array}{l} + 2 x+3 y=5 \\ + x-y=0 + \end{array}\right. + $$ + Si fa allora riferimento alle due matrici associate al sistema, quella + incompleta e quella completa, rispettivamente + $$ + A=\left(\begin{array}{cc} + 2 & 3 \\ + 1 & -1 + \end{array}\right), \ A^{\prime}=\left(\begin{array}{ccc} + 2 & 3 & 5 \\ + 1 & -1 & 0 + \end{array}\right) + $$ + Possiamo risolvere il sistema calcolando il determinante di $A$ + $$ + \operatorname{det}\left(\begin{array}{cc} + 2 & 3 \\ + 1 & -1 + \end{array}\right)=-2-3=-5 + $$ + Se questo è diverso da 0 (come nel nostro caso), il sistema ammette una e una + sola soluzione, che (per la regola di Cramer) è data da + $$ + \begin{aligned} + & x=\frac{1}{-5} \cdot \operatorname{det}\left(\begin{array}{cc} + 5 & 3 \\ + 0 & -1 + \end{array}\right)=\frac{-5}{-5}=1 \\ + & y=\frac{1}{-5} \cdot \operatorname{det}\left(\begin{array}{cc} + 2 & 5 \\ + 1 & 0 + \end{array}\right)=\frac{-5}{-5}=1 . + \end{aligned} + $$ + È richiesto, dunque, il ripetuto calcolo di determinanti. Per $n=2$, è esercizio + semplice. Per $n$ molto grande, le cose si complicano. Infatti, sfogliando + $\mathrm{i}$ manuali di algebra lineare, si vede che il determinante di una + matrice $n \times n$ è la somma di $n$ ! addendi: per $n=2,2 !=2$ è valore + innocuo, ma per $n=10^2, 10^3, 10^{10}, \ldots$ sono da attendersi grosse + difficoltà. Ricordiamo infatti che, per $n \geq 4, n ! \geq 2^n$. + C'è comunque un altro metodo di risoluzione del sistema, che estende i + ben noti procedimenti di sostituzione, addizione e sottrazione e così + via, e fa riferimento al rango delle matrici $A, A^{\prime}$. + Riducendole in forma triangolare, si arriva alle matrici + $$ + \left.\left(\begin{array}{ll} + 2 & 3 \\ + 0 & 5 + \end{array}\right),\left(\begin{array}{ccc} + 2 & 3 & 5 \\ + 0 & 5 & 5 + \end{array}\right) \text { (anzi }\left(\begin{array}{ccc} + 2 & 3 & 5 \\ + 0 & 1 & 1 + \end{array}\right)\right) + $$ + che hanno lo stesso rango 2. Si deduce che ci sono soluzioni, le quali + coincidono con quelle del sistema + $$ + \left\{\begin{array}{cc} + 2 x+3 y & =5 \\ + y & =1 + \end{array}\right. + $$ + Facilmente si ottiene di nuovo $x=y=1$. Il numero delle computazioni richieste + dal procedimento si valuta approssimativamente in $n^3$. Per $n=2,2^3=8$ può + sembrare livello peggiore del precedente 2!. Lo stesso vale per $n=3,4$. Ma già + per $n=5, n^3=125$ e $n !=120$. Per $n \geq 6, n^3$ diviene molto + minore di $2^n$ e perciò di $n !$. +\end{enumerate} + +Dunque gli esempi proposti mostrano quanto la scelta di una tecnica invece di +un'altra possa incidere significativamente nella soluzione del problema. Vale la +pena di approfondire la questione. Un discorso rigoroso richiede comunque che +precisiamo: + +\begin{enumerate} + \item con quale criterio intendiamo misurare il costo delle + computazioni, quindi l'efficienza degli algoritmi e in definitiva la complessità + di un problema; + \item a quale modello astratto di computazione (una macchina di + Turing o qualcosa di più aggiornato) vogliamo fare riferimento. +\end{enumerate} + +Si tratta di questioni delicate (soprattutto la prima), meritevoli di +approfondimenti futuri. Anticipiamo comunque qualche riflessione. + +\begin{enumerate} + \item Ci sono + vari possibili parametri atti a determinare il livello di risorse necessarie per + risolvere un problema: tempo, memoria, spazio, energia,... tra loro collegati, + ma non direttamente dipendenti. + \item Come sappiamo, il modello della macchina di + Turing (che anche in questa seconda parte del testo continueremo sovente ad + abbreviare con MdT) è ancor oggi perfettamente adeguato quando si parla di + computabilità. I problemi che hanno algoritmo di soluzione sono ancora da + identificarsi con quelli decisi da macchine di Turing. Quando però l'accento si + sposta sulla ricerca di procedure efficienti di computazione (quale che sia il + criterio scelto per giudicare questa efficienza) si può dubitare che la MdT sia + ancora un modello aggiornato e che miglioramenti e perfezionamenti non siano + possibili in ragione di progressi tecnici, o anche dei criteri stessi di + efficienza. +\end{enumerate} + +Così faremo riferimento in partenza al modello di Turing, ma ci riprometteremo +di esplorare nuove prospettive nel seguito.\\ + +C'è anche da stabilire quali sono i "problemi" che vogliamo considerare. +Lavoriamo, al solito, su un dato alfabeto $A$, meglio se finito. A meno di +codifiche standard, $A=\{0,1\}$ può essere il nostro punto di riferimento. $A^*$ +denota al solito l'insieme delle parole su $A$. Pensiamo allora a + +\begin{center} + (1) problemi + di decisione volti a considerare linguaggi $S \subseteq A^{\star}$ e a decidere, + per ogni parola $w$ su $A$, se $w \in S$ oppure no; l'input è dunque $w \in + A^{\star}$, l'output un $S I$ o un $N O$ (semmai codificati in un modo + opportuno). +\end{center} + +Formalmente il nostro problema si identifica con il linguaggio $S$ inteso come +insieme degli input $w$ per cui si ha output $SI$. Anzi, spesso nel seguito +useremo "problema" proprio come sinonimo di "linguaggio". Questo contesto non +sarà comunque tale da esaurire ogni possibile interesse. Possiamo infatti +pensare a + +\begin{center} + (2) problemi di computazione: per $f$ funzione da $A^{\star}$ a + $A^{\star}$, eventualmente parziale, cioè ristretta a $S \subseteq A^{\star}$, + calcoliamo i valori di $f$; l'input è, nuovamente, $w \in$ $A^{\star}$ (semmai + $w$ nel dominio di $f$ ), l'output richiesto è $f(w)$. +\end{center} + + + +Il panorama non si restringe qui, possiamo pensare a problemi di ottimizzazione, +ricerca, e così via. Del resto, le distinzioni tra questi vari obiettivi non +sono nette e distinte, matematicamente separate in modo rigoroso. Per +semplicità, comunque, ci limiteremo nelle pagine future principalmente ad (1) e +talora anche a (2). Possiamo inoltre immaginare di decidere, o computare, +coppie, o terne, o sequenze finite di input. Ma opportune funzioni di codifica +possono ridurre questi ambiti generalizzati al caso di una sola parola $w$.\\ +C'è +un altro punto che vogliamo sottolineare in questa introduzione. Ci stiamo +muovendo per determinare le risorse minime necessarie per risolvere un problema +(e dunque per limitare inferiormente la sua difficoltà). Ci attendiamo quindi +ragionevolmente + +\begin{center} + risultati di carattere prevalentemente negativo +\end{center} +atti a +certificare che un particolare problema non si risolve senza impegnare una certa +quantità di risorse, oppure anche + +\begin{center} + risultati di confronto +\end{center} + +atti a comparare +problemi di varia natura $\mathrm{e}$ a dichiarare che l'uno è almeno tanto +difficile o dichiaratamente più difficile dell'altro; oppure a collegare +procedure tese a risolvere lo stesso problema e, nuovamente, a ordinarle in +ragione della loro efficienza. La complessità computazionale è volta +principalmente a questi obiettivi. \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/complessita/main.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/complessita/main.tex new file mode 100644 index 000000000..2b3be3c99 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/complessita/main.tex @@ -0,0 +1,5 @@ +\chapter{Complessità} + +\input{capitoli/complessita/introduzione.tex} +\input{capitoli/complessita/come_misuarare_la_complessita.tex} +\input{capitoli/complessita/un_esempio.tex} \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/complessita/un_esempio.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/complessita/un_esempio.tex new file mode 100644 index 000000000..ef50c400f --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/complessita/un_esempio.tex @@ -0,0 +1,122 @@ +\section{Un esempio} + +Concludiamo questo capitolo discutendo il tema della lunghezza dell'input +e del costo di una computazione nel contesto familiare dei numeri naturali. +Cominciamo parlando della lunghezza.\\ +Sappiamo tutti che un numero naturale viene comunemente scritto, in base 10, +elencando a partire da destra la cifra delle unità, quella delle decine, quella +delle centinaia, quella delle migliaia, e così via. Un numero da $0$ a $9$ +(cioè fino a $10$ escluso) richiede una sola cifra, uno tra $10$ e $100 = 10^2$ +(escluso) necessita di due cifre, uno tra $100$ e $1000 = 10^3$ (escluso) di 3, +e così via di seguito. Dunque la lunghezza di un numero intero (positivo) $N$ si +riferisce al suo logaritmo in base 10 o meglio alla sua parte intera, che infatti +vale + +\begin{itemize} + \item 0 per numeri fino a 10 escluso, + \item 1 per numeri da 10 fino a $10^2$ escluso, + \item 2 per numeri da $10^2$ a $10^3$ escluso. +\end{itemize} + +e così via. Il valore preciso della lunghezza di $N$ in base 10 è, infatti + +$$ + \lfloor \log_{10} N \rfloor + 1 +$$ + +(dove $\lfloor\ldots\rfloor$ denota la parte intera).\\ +Naturalmente, il +riferimento alla base 10 non è l'unico possibile, e si potrebbe preferire +un'altra base, per esempio 2, e rappresentare così i naturali solo con le cifre +0 e 1 , così che +$$ + 0,1,2,3,4,5,6,7,8,9,10,11,12, \ldots +$$ +diventano +$$ + 0,1,10,11,100,101,110,111,1000,1001,1010,1011,1100, \ldots +$$ +La lunghezza aumenta, ma la regola che la calcola rimane formalmente la stessa, +riferita ovviamente alla base 2. In effetti, non è difficile convincersi, anche +con pochi semplici esempi, che la lunghezza di $N$ in base 2 è +$$ + \left\lfloor\log _2 N\right\rfloor+1 +$$ +(e dunque è strettamente collegato a $\log _2 N$ ). Ricordiamo poi la formula +che lega i logaritmi di $N$ in base 10 e 2 : +$$ + \log _{10} N=\log _{10} 2 \cdot \log _2 N . +$$ +Così anche le lunghezze pur diverse di $N$ nelle basi 10, 2 crescono "quasi +proporzionalmente" tramite la costante $\log _{10} 2$. Analoghe considerazioni +possono farsi a proposito di altre possibili basi $3,4,5$, e così via. Notiamo +anche che $N=10^{\log _{10} N}=2^{\log _2 N}$ è esponenziale rispetto alla sua +lunghezza. Così un algoritmo che richiede costo $N$ (o vicino a $N$ ) su $N$ è +da ritenersi poco efficiente: constatazione che sarà bene ricordare in futuro. +In genere, la base cui si fa più spesso riferimento è 2. Le cifre 0,1 che vi +ricorrono si chiamano bit. Così 1001 (cioè 9 in base 10 ) si compone di 4 bit (e +la sua lunghezza in base 2 è 4). Abbiamo così trattato il tema della lunghezza +degli input. Adesso dobbiamo considerare il costo delle computazioni sui +naturali. Anticipando il tema del prossimo capitolo, ammettiamo di misurare la +complessità di una computazione tramite il numero complessivo di passi da essa +svolto prima di concludere. Ovviamente è da chiarire che cosa si intende per +passo di computazione nel nostro ambito, quando si trattano naturali $N$ in +notazione binaria e si svolgono le varie operazioni di somma, prodotto e così +via. In genere si conviene che ogni singola operazione sui bit degli input $N$ +coinvolti corrisponde ad un passo di computazione. Per esempio si assume che +l'addizione +$$ + \begin{array}{r} + 1001 \ + \\ + 11110 = \\ + \hline + 100111 \ \ \ + \end{array} +$$ + +(ovvero $9+30=39$ in base 10 ) richiede 5 passi per svolgere i calcoli sulle +varie colonne. In questa ottica, si può notare che sommare due numeri di $k$ +bits richiede al più $k$ passi, ed è dunque al più lineare nella lunghezza $k$, +mentre la moltiplicazione degli stessi numeri si può svolgere in $k^2$ passi +(dunque al più in costo al più quadratico in $k$ ). Lo stesso vale per la +divisione (intendendo come divisione il calcolo di quoziente e resto, come in +genere si conviene tra i naturali). Illustriamo allora la situazione riferendoci +come esempio al calcolo del massimo comun divisore tramite l'algoritmo di +Euclide delle divisioni successive. Vogliamo mostrare che secondo i parametri +appena introdotti, questo procedimento ha costo al più quadratico rispetto alla +lunghezza dell'input (come già anticipato a livello intuitivo nell'introduzione +di questo capitolo). Consideriamo dunque due naturali $a, b$. Possiamo supporre +$a>b>0$ per semplicità. I due primi passi dell'algoritmo di Euclide +corrispondono alle divisioni +$$ + \begin{gathered} + a=b \cdot q_0+r_0 \operatorname{con} r_0r_0+r_1>2 r_1 . +$$ +Così due applicazioni dell'algoritmo determinano un resto $r_1<\frac{1}{2} a$. +Non è difficile ripetere l'osservazione e notare che $r_1>2 r_3$, dunque $a>2 + r_1>2^2 r_3$; in generale, dopo $t$ iterazioni si deduce +$$ + a>2^t \cdot r_{2 t-1} +$$ +(dove $r_{2 t-1}$ è il resto ottenuto al passo $2 t-1$ ). Sia $s$ il passo +finale (quello che produce $r_s=0$ e dunque dichiara $r_{s-1}=(a, b)$ ). +Supponiamo per semplicità che $s$ sia pari, dunque $s=2 T$, per $T$ numero +naturale, e deduciamo +$$ + a>2^T r_{2 T-1} . +$$ +Siccome $r_{s-1}>0, \frac{a}{2^T} \geq 1$, cioè $a \geq 2^T$ e $T \leq \log _2 + a$, da cui $s-1 \leq 2 \log _2 a$. Così le varie divisioni successive da +svolgere sono $O\left(\log _2 a\right)$. Inoltre i calcoli sui bit dei vari +numeri coinvolti in ciascuna divisione si svolgono certamente in tempo +$O\left(\log _2^2 a\right)$ perché riguardano interi al più lunghi quanto $a$, e +anzi possono ridursi a $O\left(\log _2 a\right)$ con qualche accorgimento. +Dunque il numero di passi dell'algoritmo euclideo è $O\left(\log _2^2 a\right)$, +dunque al più polinomiale (e anzi quadratico) nella lunghezza dell'input $a$ (e +conseguentemente anche in quella di $b$, visto che $b \leq a$ ). \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/calcolabilita_secondo_church.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/calcolabilita_secondo_church.tex new file mode 100644 index 000000000..5092164bb --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/calcolabilita_secondo_church.tex @@ -0,0 +1,95 @@ +\section{Calcolabilità secondo Church} + +II nostro proposito in questo capitolo è quello di presentare un approccio alla +computabilità + +\begin{itemize} + \item contemporaneo a quello di Turing, + \item formalmente diverso da + quello di Turing, anzi più astratto e matematico, + \item tuttavia completamente equivalente a quello di Turing. +\end{itemize} + + +Si basa sulla nozione di \textit{funzione ricorsiva}. Ma +prima di introdurre questo nuovo concetto, inquadriamo nuovamente e brevemente +il nostro obiettivo generale: per un fissato alfabeto finito $A$ ed in +riferimento all' insieme $A^{\star}$ di tutte le stringhe di simboli +$\operatorname{di} A$, intendiamo + +\begin{enumerate} + \item riconoscere quei linguaggi su $A$ che + ammettono un algoritmo di decisione, + \item riconoscere quelle funzioni da + $A^{\star}$ (o da sottoinsiemi delle sue potenze cartesiane) ad $A^{\star}$ che + ammettono un algoritmo di calcolo. +\end{enumerate} + + +L'analisi di Turing, sviluppata negli scorsi capitoli, ci ha allora +rispettivamente condotto alle corrispondenti nozioni di: + +\begin{enumerate} + \item linguaggio \textit{decidibile}, + \item funzione \textit{calcolabile}. +\end{enumerate} + + +Come detto, vogliamo adesso esplorare un +approccio alternativo. Ricordiamo che non è restrittivo per i nostri propositi +supporre di lavorare con numeri naturali, dunque riferirci ad un qualche +alfabeto per i numeri naturali (ad esempio $A=$ $\{0,1,2, \ldots, 9\}$, ma anche +$A=\{0,1\}$ se preferiamo la rappresentazione dei naturali in base 2) ed +assumere conseguentemente, senza perdita di generalità, che $A^{\star}$ coincida +con l'insieme $\mathbb{N}$ stesso. Opportune codifiche permettono di ridurre +qualunque $A$ a questa situazione. Consideriamo allora + +\begin{enumerate} + \item insiemi $L$ di naturali, o di $k$-uple di naturali, + \item funzioni (eventualmente parziali) da $\mathbb{N}^k$ a $\mathbb{N}$ +\end{enumerate} + +per qualche intero positivo $k$ (ricordiamo che una funzione parziale ha dominio +contenuto in $\mathbb{N}^k$ ma non necessariamente coincidente con tutto +$\mathbb{N}^*$; in quest'ultimo caso la funzione si dice \textit{totale}; ricordiamo +anche che una funzione -parziale o totale- da $\mathbb{N}^k$ a $\mathbb{N}$ si +dice $k$-aria). In questo ambito vogliamo esaminare nuove possibili strategie +per definire la decidibilità degli insiemi e la calcolabilità delle funzioni. +D'altra parte possiamo ricordare che, per $L \subseteq \mathbb{N}^k$, resta +definita la \textit{funzione caratteristica} $f_L$ di $L$, quella funzione (totale) da +$\mathbb{N}^k$ a $\mathbb{N}$ che ad ogni $x \in \mathbb{N}^k$ associa + +\begin{itemize} + \item 1 se $x \in L$, + \item 0 altrimenti. +\end{itemize} + +Possiamo evidentemente affermare che + +\begin{center} + \textit{esiste un algoritmo + per decidere, per ogni $x \in \mathbb{N}^k$, se $x \in L$ o no} +\end{center} + +se e solo se + +\begin{center} + \textit{esiste un algoritmo per calcolare $f_L(x)$ per ogni $x \in \mathbb{N}^k$.} +\end{center} + +Basterà allora per i nostri propositi definire con precisione per quali insiemi +$L \subseteq$ $\mathbb{N}^k$ + +\begin{center} + \textit{esiste un algoritmo per calcolare $f_L(x)$ per ogni + $x \in \mathbb{N}^k$.} +\end{center} + +In altre parole, possiamo concentrare il nostro lavoro a +definire in modo appropriato la calcolabilità delle funzioni (anche parziali): +infatti tramite $f_L$ possiamo coinvolgere in questo ambito anche il problema di +decidere $L$. Il nostro obiettivo è dunque quello di precisare per quali +funzioni parziali $k$-arie $f$ esiste un algoritmo per calcolare $f(x)$ per ogni +$x$ nel dominio di $f$. Turing ci ha suggerito una possibile strategia, tramite +le macchine di Turing. Come detto, iniziamo qui a considerarne una alternativa. + diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/church_o_turing.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/church_o_turing.tex new file mode 100644 index 000000000..7220a475e --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/church_o_turing.tex @@ -0,0 +1,161 @@ +\section{Church o Turing ?} + +L'approccio alla calcolabilità tramite le funzioni ricorsive pare chiaramente +diverso da quello mediante le macchine di Turing. Il primo è assai più astratto, +l'altro più concreto, ed anzi dichiaratamente ispirato dal tentativo di simulare +il comportamento della mente umana. In questo ambito, anzi, il secondo approccio +risulta più convincente, se è vero, come è vero, che scienziati importanti come +Gödel, assai dubbiosi a proposito della Tesi di Church, si dichiaravano invece +assolutamente persuasi dalla calcolabilità secondo Turing, proprio per questa +sua maggiore concretezza. Possiamo allora chiederci a chi credere, se a Church +oppure a Turing, dunque quale modello di computabilità preferire. In realtà la +scelta è tutto men che drammatica, perchè è possibile dimostrare che +$\mathrm{i}$ due approcci, pur così differenti in natura, sono tuttavia tra loro +equivalenti e dunque ugualmente accettabili (o rifiutabili). Conseguentemente le +due tesi, quella sulle macchine di Turing e quella di Church, sono coincidenti, +tanto che le abbiamo già implicitamente congiunte nel Capitolo 2 quando abbiamo +parlato tranquillamente di \textit{Tesi di Church-Turing}.\\ +Non va poi trascurato che +proprio questa equivalenza, e dunque la coincidenza concentrica di punti di +vista tanto diversi verso lo stesso obiettivo, è argomento che corrobora e +sostiene ulteriormente i due approcci alla calcolabilità, tanto quello di Turing +che quello di Church. Ma passiamo alla enunciazione e alla dimostrazione del +teorema di equivalenza. + +\paragraph{Teorema 4.4.1} \textit{Sia $f$ una funzione parziale $k$-aria (dai naturali ai naturali). + Allora f è calcolabile (nel senso di Turing) se e solo se f è parziale + ricorsiva.}\\ + +In particolare, quando $f$ è totale, si può dedurre che $f$ è calcolabile +(secondo Turing) se e solo se è ricorsiva. Si può poi dedurre facilmente: + +\paragraph{Corollario 4.4.2} \textit{Sia $L \subseteq \mathbb{N}^{k}$. Allora $L$ è + decidibile (secondo Turing) se e solo se $L$ è ricorsivo.}\\ + +Basta infatti osservare che un insieme $L$ di $k$-uple di naturali è decidibile +(secondo Turing) se e solo se la sua funzione caratteristica è calcolabile +(secondo Turing). Passiamo ora alla dimostrazione del teorema: ne daremo solo i +cenni principali, evitando di disperderci in troppi dettagli. + +\begin{proof} + Assumiamo dapprima $f$ parziale ricorsiva e verifichiamo che $f$ + è calcolabile secondo Turing. Ricordiamo che le funzioni ricorsive sono quelle + che si ottengono dalle funzioni iniziali applicando un numero finito di volte + $\mathrm{i}$ procedimenti di composizione, recursione e minimalizzazione. Ci + basta allora dimostrare quanto segue: + + \begin{enumerate} + \item[(i)] le funzioni iniziali sono calcolabili + con MdT, + \item[(ii)] funzioni che si ottengono per composizione, oppure per recursione, + oppure per minimalizzazione da funzioni che sono calcolabili con MdT sono a loro + volta calcolabili con MdT. + \end{enumerate} + + Le relative verifiche sono più noiose che difficili. Del resto, $(i)$ è già + stato trattato nel Capitolo 2 almeno a livello di esercizi e quando abbiamo + introdotto composizione, recursione e minimalizzazione, abbiamo anche accennato + ad algoritmi capaci di calcolare le funzioni corrispondentemente ottenute. Tutti questi + procedimenti si possono adattare con un minimo di pazienza al contesto e al + linguaggio delle MdT.\\ + + Passiamo allora a controllare l'implicazione inversa: abbiamo una funzione + parziale $k$-aria $f$ che è calcolabile secondo Turing e vogliamo mostrare + che $f$ è parziale ricorsiva. Sia $M$ una MdT che computa $f$. Siano poi + $q_0, \ldots, q_n$ gli stati di $M$. Possiamo assumere che $M$ si arresti se + e solo se $M$ entra nello stato $q_n$: se questo non è il caso, ci basta + aggiungere a $M$ un nuovo stato (senza istruzioni che lo riguardino) e alla + funzione di transizione di $M$ le istruzioni che conducano ogni + configurazione di arresto di $M$ al nuovo stato. Definiamo a questo punto + quattro funzioni totali $(k+1)$-arie + + $$ + q_M, \ \ i_M, \ \ s_M, \ \ d_M + $$ + + tali che, per ogni scelta di $\vec{x} \in \mathbb{N}^k$ e $t \in + \mathbb{N}$, + $$ + q_M(\vec{x}, t), \ i_M(\vec{x}, t), \ s_M(\vec{x}, t), \ d_M(\vec{x}, t) + $$ + + codificano rispettivamente + + \begin{itemize} + \item lo stato di $M$, + \item che cosa è scritto sulla cella esaminata da $M$, + \item che cosa è scritto sul nastro a sinistra della cella esaminata da $M$, + \item che cosa è scritto sul nastro a destra della cella esaminata da $M$ + \end{itemize} + + al passo $t$ della computazione di $M$ sull'input + corrispondente a $\vec{x}$. Ad esempio, $q_M(\vec{x}, t)$ è rappresentato + dall'indice 0, o $1, \ldots$, o $n$ dello stato corrispondente; + $i_M(\vec{x}, t)$ è una cifra di un qualche alfabeto dei naturali (ad + esempio, 0, o $1, \ldots$, o 9 se adoperiamo la rappresentazione decimale) + oppure un ulteriore numero (10, se vogliamo) per denotare il carattere + bianco $\star$; $s_M$ e $d_M$ richiedono invece una definizione più accurata, + che utilizza in modo opportuno le consuete tecniche di codifica ed in + particolare il teorema di decomposizione in fattori primi: ne omettiamo qui + i dettagli. Osserviamo poi che, se per un certo input $\vec{x}$ $M$ converge + in $T$ passi, allora per ogni naturale $t>T$ si conviene + $$ + \begin{aligned} + q_M(\vec{x}, t) & =q_M(\vec{x}, T), \ i_M(\vec{x}, t)=i_M(\vec{x}, T), \\ + d_M(\vec{x}, t) & =d_M(\vec{x}, T), \ s_M(\vec{x}, t)=s_M(\vec{x}, T) + \end{aligned} + $$ + si cristallizza cioè la situazione al momento dell'arresto di $M$. In questo + modo si ottiene che le nostre quattro funzioni diventino totali. A questo + punto si prova che $q_M, i_M, x_M, d_M$ sono ricorsive. Ad esempio si + osserva che, per ogni $\vec{x} \in \mathbb{N}^k$, + $$ + q_M(\vec{x}, 0)=0, + $$ + perché al passo iniziale $M$ è nello stato $q_0$, e + $$ + i_M(\vec{x}, 0) + $$ + + è la prima cifra della prima componente $x_1$ di $\vec{x}$ (quella più a + sinistra quando inizia la computazione), mentre, per ogni naturale $t$, + $$ + q_M(\vec{x}, t+1), i_M(\vec{x}, t+1) + $$ + si desumono in modo effettivo dalle istruzioni della funzione di transizione di + $M$ sulla coppia + $$ + \left(q_M(\vec{x}, t), i_M(\vec{x}, t)\right) + $$ + ed inoltre da $s_M(\vec{x}, t)$ e $d_M(\vec{x}, t)$. Analogamente per + $s_M(\vec{x}, t+1), d_M(\vec{x}, t+1)$. In questo modo, con qualche maggior + attenzione per i dettagli, si mostra che le nostre quattro funzioni sono + ricorsive. A questo punto si nota che, per ogni $\vec{x} \in \mathbb{N}^k$, + + \begin{itemize} + \item $\vec{x}$ è nel dominio di $f$ se e solo se $M$ converge su $\vec{x}$, e quindi + se e solo se, per qualche naturale $t, M$ entra nello stato $q_n$ al passo $t$ + della computazione su $\vec{x}$, ovvero $q_M(\vec{x}, t)=n$; + \item in tal caso, + $f(\vec{x})$ si ottiene da $i_M(\vec{x}, t), s_M(\vec{x}, t)$ e $d_M(\vec{x}, + t)$ dove $t$ è il minimo naturale per cui $q_M(\vec{x}, t)=n$. + \end{itemize} + + + Si intravede in questa definizione il meccanismo di minimalizzazione applicato a + funzioni ricorsive (quali $q_M, i_M, s_M$ e $d_M$ ). Se ne deduce che $f$ è, a + sua volta, parziale ricorsiva, proprio come volevamo dimostrare. + +\end{proof} + +Il teorema ci aiuta a caratterizzare in termini di funzioni ricorsive anche la +semidecidibilità. Infatti con riferimento al teorema 3.5.1 possiamo considerare +linguaggi $L \subseteq \mathbb{N}$ tali che $L=\emptyset$ oppure $L$ è immagine +di qualche funzione totale ricorsiva 1aria $f$. Chiamiamo ricorsivamente +enumerabile un tale linguaggio $L$ e deduciamo banalmente: + +\paragraph{Corollario 4.4.3} \textit{$L \subseteq \mathbb{N}$ è ricorsivamente enumerabile se + e solo se è semidecidibile.}\\ + +I linguaggi ricorsivamente enumerabili si riconoscono allora anche come i domini +delle funzioni parziali ricorsive 1-arie (sempre per il teorema 3.5.1). diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/esempi_a_volonta.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/esempi_a_volonta.tex new file mode 100644 index 000000000..11d515145 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/esempi_a_volonta.tex @@ -0,0 +1,3 @@ +\section{Esempi a volontà} + +%%TODO: Decidere se includere questa parte, pagina 73 \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/le_funzioni_parziali_ricorsive.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/le_funzioni_parziali_ricorsive.tex new file mode 100644 index 000000000..6b5c73dc2 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/le_funzioni_parziali_ricorsive.tex @@ -0,0 +1,200 @@ +\section{Le funzioni parziali ricorsive} +Consideriamo anzitutto le seguenti funzioni +parziali: + +\begin{itemize} + \item la funzione successore $s$ da $\mathbb{N}$ a $\mathbb{N}$, quella + che ad ogni naturale $x$ associa $x+1$; + \item la funzione costante zero $Z$ da + $\mathbb{N}$ a $\mathbb{N}$, quella che ad ogni naturale $x$ associa 0 ; + \item finalmente, per ogni intero positivo $k$ e per ogni $i=1, \ldots, k$, la + funzione \textit{proiezione} $P_i^k$ da $\mathbb{N}^k$ a $\mathbb{N}$, quella che ad ogni + $k$-upla $\vec{x}=\left(x_1, \ldots, x_k\right)$ di naturali associa la sua + componente $i$-ma $x_i$. +\end{itemize} + +Si noti che il terzo gruppo di funzioni include anche l'identità di $\mathbb{N}$ +come $P_1^1$. Possiamo senz'altro convenire che tutte queste funzioni +ammettono un algoritmo di calcolo: dunque, quale che sia la definizione di +calcolabilità che ci proponiamo di concordare, essa non potrà escluderle. +Chiamiamo per semplicità \textit{"iniziali"} le funzioni sin qui considerate, e cioè +successore, zero e proiezioni.\\ + +Adesso osserviamo che la funzione costante che ad ogni naturale associa 1 +ammette ovviamente un algoritmo di calcolo e, del resto, si ottiene come +\textit{composizione} delle funzioni zero e successore. Le stesse considerazioni si +possono fare a proposito della funzione $s^2$ (quella che ad ogni naturale $x$ +associa $x+2$, e che è la composizione di $s$ per se stessa), o anche di $s^3$, +e così via. In generale, possiamo ragionevolmente convenire che la composizione +di funzioni che hanno un algoritmo di calcolo ammetta a sua volta un algoritmo +di calcolo. Dunque la nozione rigorosa di calcolabilità che cerchiamo di +ottenere, quale che essa sia, dovrà preservare la composizione di funzioni. Per +fissare opportunamente il contesto ed adattarlo anche al caso di funzioni +parziali e di $k$-uple di naturali, poniamo la seguente: + +\paragraph{Definizione.} Per $k$ e $n$ interi positivi, siano $h$ una funzione parziale +$n$-aria e $g$, $\ldots, g_n$ $n$ funzioni parziali $k$-arie. Una funzione +parziale $k$-aria $f$ si dice definita per \textit{composizione} da $h$ e $g_1, \ldots, + g_n$ se e solo se, per ogni $\vec{x} \in \mathbb{N}^k$, + +\begin{itemize} + \item $\vec{x}$ è nel + dominio di $f$ se e solo se $\vec{x}$ è nel dominio di $g_i$ per ogni $i=1, + \ldots, n$ e la $n$-upla $\left(g_1(\vec{x}), \ldots, g_n(\vec{x})\right)$ è nel + dominio di $h$; + \item in tal caso, $f(\vec{x})=h\left(g_1(\vec{x}), \ldots, + g_n(\vec{x})\right)$. +\end{itemize} + +Come già osservato, è facilmente accettabile che, se $h$, +$g_1, \ldots, g_n$ hanno i loro algoritmi di calcolo, anche $f$ lo ottiene: dato +$\vec{x} \in \mathbb{N}^k$, si computano, se possibile, $g_1(\vec{x}), \ldots, + g_n(\vec{x})$ con i relativi algoritmi, poi la loro immagine in $h$ (cioè +$f(\vec{x})$) mediante l'algoritmo di $h$. Notiamo poi che, se $h, g_1, \ldots, + g_n$ sono funzioni totali (ovvero sempre definite), anche $f$ lo è.\\ + +Un altro metodo familiare per definire una funzione $f$ da $\mathbb{N}$ a +$\mathbb{N}$ è quello di ricorrere al \textit{Principio di Induzione}, ovvero a quella +fondamentale proposizione sui naturali che ci dice che, se una proprietà è +soddisfatta da 0 e si preserva da $y$ a $y+1$ per ogni naturale $y$, allora +quella proprietà vale per tutto $\mathbb{N}$. Applicandola a $f$, possiamo +dedurre che, una volta specificati +$$ + f(0)=g_0 \in \mathbb{N} +$$ +e poi, per ogni naturale $y$, +$$ + f(y+1)=h(y, f(y)) +$$ +per qualche $h$ 2-aria indipendente da $y$ -dunque $f(y+1)$ come funzione di $y$ +e $f(y)$ tramite $h$-, allora $f$ risulta definita su tutto $\mathbb{N}$. +Possiamo ragionevolmente convenire che, se $g_0$ è dato esplicitamente e $h$ +ammette un suo algoritmo di calcolo, allora anche $f$ ottiene un procedimento +effettivo che la computa per ogni naturale $y$: basta considerare anzitutto +$f(0)=g_0$, poi calcolare $f(1)=h(0, f(0))$ da $f(0)$ tramite l'algoritmo di +$h$, e così via finchè non si arriva a $f(y)$. Comunque, per fissare +opportunamente il discorso nell'ambito più generale (per funzioni parziali e +$k$-uple di elementi), conviene nuovamente che poniamo una + +\paragraph{Definizione.} Per $k$ intero non negativo, siano $g$ una funzione parziale +$k$-aria e $h$ una funzione parziale $(k+2)$-arie. Una funzione parziale +$(k+1)$-aria $f$ si dice definita per \textit{recursione} da $g$ e $h$ se e solo se, per +ogni $\vec{x} \in \mathbb{N}^k$, + +\begin{itemize} + \item $(\vec{x}, 0)$ è nel dominio di $f$ se e solo se $\vec{x}$ è nel + dominio di $g$ e, in tal caso, $f(\vec{x}, 0)=g(\vec{x})$, + \item per ogni naturale $y,(\vec{x}, y+1)$ è nel dominio di $f$ se e solo se + $(\vec{x}, y)$ è nel dominio di $f$ e $(\vec{x}, y, f(\vec{x}, y))$ è nel + dominio di $h$ e, in tal caso, $f(\vec{x}, y+1)=$ $h(\vec{x}, y, f(\vec{x}, + y))$. + +\end{itemize} + +Con un minimo di pazienza, si potrà riconoscere in questo ambito generale anche +la situazione particolare prima descritta, quella relativa a una funzione $f$ +1-aria: infatti, per $k=0$, anzitutto la sequenza $\vec{x}$ è vuota, possiamo +poi intendere che $g$ si riduca ad una costante $g_0$, che $h$ sia 2-aria e che +la funzione $f$ che $g$ e $h$ determinano per recursione sia 1-aria: +$$ + f(0)=g_0, \ f(y+1)=h(y, f(y)) \ \forall y \in \mathbb{N}, +$$ +appunto. Possiamo poi convenire senza problemi che, anche nel caso della +definizione generale, se $g$ e $h$ ammettono un qualche algoritmo di calcolo, +anche $f$ lo ottiene (arrangiando opportunamente quelli di $g$ e $h$ ). Notiamo +finalmente che, se $g$ e $h$ sono totali (cioè definite ovunque), anche $f$ lo +è.\\ + +Un'altra proprietà che contraddistingue i naturali e si presta per definirne le +funzioni è il \textit{Principio del Minimo}, secondo cui ogni insieme non vuoto di +naturali ammette un minimo elemento. Corrispondentemente consideriamo la +seguente definizione. + +\paragraph{Definizione.} Per $k$ intero positivo, sia $g$ una funzione \textbf{totale} $(k+1)$-aria. +Una funzione parziale $k$-aria $f$ si dice definita per \textit{minimalizzazione} da $g$ +se e solo se, per ogni $\vec{x} \in \mathbb{N}^k$, + +\begin{itemize} + \item $\vec{x}$ è nel dominio di + $f$ se e solo se c'è qualche naturale $y$ per cui $g(\vec{x}, y)=0$, + \item in tal + caso, $f(\vec{x})$ è il minimo naturale con questa proprietà, cioè +\end{itemize} +\[ + f(\vec{x})=\min \{y \in \mathbb{N}: g(\vec{x}, y)=0\} +\] + +\begin{center} + (che taluni preferiscono indicare anche con la notazione $\mu y(g(\vec{x}, + y)=0)$). +\end{center} + +Osserviamo che, se $g$ ha un suo algoritmo di calcolo, anche $f$ lo +ottiene, ad esempio nel modo seguente. Sia dato $\vec{x} \in \mathbb{N}^k$; + +\begin{itemize} + \item si + calcola $g(\vec{x}, 0)$ tramite l'algoritmo di $g$; siccome $g$ è totale (cioè + sempre definita), la computazione ha termine e ci è consentito controllare se + $g(\vec{x}, 0)=$ 0 o no; se sì, si pone $f(\vec{x})=0$; + \item altrimenti si passa a + calcolare $g(\vec{x}, 1)$ sempre con l'algoritmo di $g$ (e grazie alla totalità + di $g)$, si controlla poi se $g(\vec{x}, 1)=0$ o no; se sì, si pone + $f(\vec{x})=1$; + \item se no, si prosegue, considerando $g(\vec{x}, 2)$, e così via. +\end{itemize} + +Può ovviamente capitare che $g(\vec{x}, y)$ non si annulli per nessun $y$; ma +questo significa semplicemente che $\vec{x}$ non appartiene al dominio della +$f$.\\ + +Le precedenti considerazioni ci mostrano l'importanza di assumere che $g$ sia +totale, ma evidenziano anche che la funzione $f$ può benissimo non essere +altrettanto totale. Ad esempio, se $g(\vec{x}, y)=1$ per ogni $y$, si ha che +$\vec{x}$ non è nel dominio di $f$. In conclusione, possiamo convenire che la +nostra nozione di computabilità, quale che essa sia, dovrà preservarsi, oltre +che per composizione e per recursione, anche per minimalizzazione. Dunque la +classe di funzioni "\textit{calcolabili}" che vogliamo formare dovrà includere le +funzioni iniziali e restare chiusa per composizione, recursione e +minimalizzazione. Poniamo a questo punto la seguente: + +\paragraph{Definizione.} Una funzione parziale $f$ si dice \textit{parziale ricorsiva} se e solo se +esiste una sequenza ordinata finita $f_0, \ldots, f_n$ di funzioni parziali +delle quali $f=f_n$ è l'ultima e tali che, per ogni $i \leq n, f_i$ è iniziale +oppure si ottiene da funzioni precedenti per composizione, o per recursione, o +per minimalizzazione. Definiamo poi \textit{ricorsiva} una funzione parziale ricorsiva +che sia anche totale. Diciamo, finalmente, \textit{ricorsivo} un insieme $S \subseteq + \mathbb{N}^k$ la cui funzione caratteristica $f_S$ (totale!) sia ricorsiva.\\ + +Una proposta che possiamo riferire ad Alonzo Church e al 1936 (lo stesso anno di +Turing) e chiamare almeno provvisoriamente \textit{Tesi di Church} afferma (a livello di +slogan) +$$ + \text { calcolabile }=\text { ricorsivo } . +$$ +Per la precisione afferma: + +\paragraph{Tesi di Church (1936).} Una funzione parziale $f$ da +$\mathbb{N}^{k}$ a $\mathbb{N}$ ammette un algoritmo di calcolo se e solo se +$f$ è parziale ricorsiva. In particolare, per $f$ totale, $f$ ammette un +algoritmo di calcolo se e solo se $f$ è ricorsiva. Finalmente, un sottoinsieme +$L$ di $\mathbb{N}^k$ ammette un algoritmo di decisione se e solo se $L$ è +ricorsivo.\\ + +Come già la Tesi a proposito delle macchine di Turing, anche questa Tesi di +Church non si propone come un teorema da dimostrare, ma piuttosto come la +affermazione (che si può condividere o rifiutare) che le nozioni di funzione e +insieme ricorsivi costituiscono il modo rigoroso e preciso di introdurre il +concetto intuitivo di algoritmo. Naturalmente, c'è da chiedersi quanto credito +possiamo dare a questa ipotesi. Non ci sono dubbi ad accettare che tutto quanto +è ricorsivo ammette un algoritmo di calcolo o di decisione: la definizione +stessa di ricorsività si preoccupa di garantire questa situazione. Semmai c'è da +chiedersi se è vero anche il contrario, se cioè tutte le funzioni che hanno un +algoritmo di calcolo e tutti gli insiemi che hanno un algoritmo di decisione +corrispondono alla condizione di ricorsività. Il prossimo paragrafo è dedicato a +fornire qualche semplice esempio al riguardo.\\ +Per completare questo paragrafo, +osserviamo nuovamente come l'approccio alla calcolabilità tramite la +ricorsività, anche se definito nel caso specifico dei numeri naturali, si +estende facilmente a funzioni e linguaggi su ogni alfabeto finito, grazie alle +usuali procedure di codifica. diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/main.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/main.tex new file mode 100644 index 000000000..3f2225561 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/funzioni_ricorsive/main.tex @@ -0,0 +1,7 @@ +\chapter{Funzioni Ricorsive} + +\input{capitoli/funzioni_ricorsive/calcolabilita_secondo_church.tex} +\input{capitoli/funzioni_ricorsive/le_funzioni_parziali_ricorsive.tex} +\input{capitoli/funzioni_ricorsive/esempi_a_volonta.tex} +\input{capitoli/funzioni_ricorsive/church_o_turing.tex} + diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/introduzione/breve_storia_della_computabilita.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/introduzione/breve_storia_della_computabilita.tex new file mode 100644 index 000000000..9fc539e75 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/introduzione/breve_storia_della_computabilita.tex @@ -0,0 +1,78 @@ +\section{Breve Storia della computabilità} + +Questo esame si interessa anzitutto del tema della computabilità: parola forse impegnativa e difficile, e pur tuttavia ovviamente collegata all'informatica, capace di +richiamare l'idea del computer e del calcolatore. +Vale allora la pena di spiegarne subito la rilevanza, anche per introdurre in maniera adeguata i temi della prima parte del corso. +Nella accezione originaria e comune, computare, o calcolare, significa far di conto con i numeri usuali, e cioè gli interi $0, \pm 1, \pm 2, ...$: +sommarli, moltiplicarli, semmai sottrarli e dividerli. Per chi ha qualche maggior dimestichezza con un pò +di matematica, l'arte di far di conto si può estendere ad operazioni più sofisticate e a contesti più ampi (limiti, derivate, integrali). Ma, in realtà, tutti i problemi +che si prestano a formalizzazioni tramite modelli matematici possono essere "computati". +Già René Descartes (Cartesio), secoli fa, all'inizio del Seicento, vagheggiava la possibilità di tradurre in termini matematici ogni problema, e dunque di risolverlo +tramite equazioni e computazioni; applicava poi l'intuizione al campo geometrico, identificando, ad esempio, punti del piano con coppie ordinate +di numeri (reali), rette del piano con equazioni di primo grado in due incognite, e così via. +Pochi anni dopo, nel 1666, Gottfried Wilhelm Leibniz esortava appassionatamente "Calculemus" (calcoliamo!), invitando ad usare conti e computazioni +anche per risolvere oggettivamente gli stessi conflitti umani e condurre a termine le controversie trasferendole "dai ragionamenti complicati ai calcoli semplici, dai +vocaboli di significato incerto e vago a caratteri determinati". Del resto lo stesso Leibniz provvedeva a chiarire di intendere per calcolo +"qualunque notazione che rappresenti il ragionamento, quand'anche non avesse alcun rapporto con i numeri ". +A queste applicazioni computazionali, rivolte ad orizzonti sempre più larghi, si accompagnava il tentativo di costruire macchine calcolatrici capaci di aiutare, +simulare e, talora, sostituire, la mente umana nel suo lavoro. Proprio al Seicento risalgono vari esempi di meccanismi automatici per fare di conto e svolgere almeno +le tradizionali operazioni di somma, prodotto, sottrazione e divisione. Possiamo così ricordare che proprio Leibniz aveva concepito nel 1671 una ruota adatta +a sviluppare questo genere di computazione, preceduto comunque in questo da Blaise Pascal e da Wilhelm Schickard che, rispettivamente nel 1643 e nel 1623, +avevano inventato analoghi procedimenti meccanici. Nei secoli successivi ci furono anche casi di macchine capaci di svolgere computazioni fuori dal solo ambito +numerico. Si parla, ad esempio, di un automa di Kempelen capace di giocare a scacchi (1768) e di anticipare in questo senso il moderno Deep Blue (il computer IBM capace di sconfiggere +qualche anno fa anche il campione del mondo degli scacchi): ma, nel caso di Kempelen, non fu mai chiaro quale fosse il segreto programma della macchina e ci fu chi +fondatamente dubitò trattarsi soltanto di un imbroglio ben riuscito (i lettori appassionati di libri polizieschi potranno trovare ampia discussione dell' argomento +nel giallo "L'Automa" di J. Dickson Carr). Nell'Ottocento, tuttavia, Charles Babbage concepì teoricamente un meccanismo automatico, da lui chiamato macchina analitica (analytical engine), +virtualmente capace di adattarsi non solo a numeri e a mosse di scacchi, ma ad ogni possibile contesto, dunque una sorta di hardware universale, che Ada Lovelace Byron +si preoccupò in quegli stessi anni di corredare di quel che oggi chiameremmo il software. +A questi progressi tecnici dovevano del resto accompagnarsi corrispondenti approfondimenti teorici, +a proposito di una questione che diventa fondamentale non appena si affronta il tema del +rapporto uomo-macchina: si tratta infatti di + +\begin{itemize} + \item identificare un linguaggio astratto appropriato, con simboli opportuni, in cui + formulare i problemi (matematici e non) da risolvere, per poterli poi proporre + alla macchina che deve computarli, + \item individuare, ancora, le leggi che la macchina deve seguire per svolgere i suoi + calcoli. +\end{itemize} + +Entrambe le questioni sono tutto men che trascurabili. Oggi, ad esempio, siamo +abituati ad usare le cifre $0, 1, 2, 3, 4, 5, 6, 7, 8, 9$ per rappresentare i numeri interi, +e i simboli $+, \cdot , -$, : per indicare le loro usuali operazioni. Ma la genesi di questi +simboli non è stato processo banale ed ha richiesto talora il progresso di secoli; +del resto, gli antichi Greci e Romani non utilizzavano ancora questi caratteri, ma +altri ben più complicati. Ancora nel Rinascimento, o nello stesso Seicento, queste notazioni si affacciavano timidamente. +Anzi, proprio a Leibniz si attribuisce l'idea di un linguaggio universale +("lingua characteristica" nella denominazione latina da lui adoperata) con cui formulare le comunicazioni scientifiche +tra uomini di idiomi diversi, e dunque anche tra uomo e macchina. +Sempre Leibniz propugnò l'idea di un calcolo della ragione ("calculus ratiocinator" in latino) atto ad individuare +le leggi fondamentali di sviluppo del pensiero (e delle computazioni), utile dunque anche nella programmazione di nuove +macchine pensanti. Come si vede, siamo qui agli albori di quelle che oggi si chiamano +intelligenza artificiale e deduzione automatica, della capacità, cioè, di sviluppare calcoli e pensieri in modo meccanico, +dunque delegabile ai "computers". Del resto, l'idea di uno studio dei procedimenti del pensiero +(quello che in termini ufficiali si chiama Logica) è ben precedente Leibniz, e risale almeno ad Aristotele e +al 300 avanti Cristo. Il calculus ratiocinator fu comunque ampiamente sviluppato +già nell'Ottocento da George Boole, che formulò una sorta di teoria algebrica del +pensiero, oggi comunemente conosciuta proprio come algebra Booleana. +Come si vede, il tema della computabilità si collega a svariatissimi argomenti +come + +\begin{itemize} + \item le macchine calcolatrici per attuare le computazioni, + \item i linguaggi e le regole con cui favorire la loro collaborazione, +\end{itemize} + +ed altri ancora. Tra l'altro, è interessante osservare come queste riflessioni anticipino largamente la nascita +dei moderni computers e si sviluppino nei secoli precedenti. Infatti i primi calcolatori +(come oggi comunemente li intendiamo) risalgono a tempi relativamente recenti, al periodo della seconda guerra mondiale e +agli anni immediatamente successivi se è vero, come è vero, che il primo computer elettronico, l'ENIAC +(architettato da Von Neumann) è del 1946. +La computabilità che vogliamo qui trattare si interessa ovviamente a tutte queste +problematiche, ma vuole anche sottolinearne un aspetto ulteriore. In effetti, il suo +ideale punto di partenza e, se vogliamo, l'anno stesso di nascita della moderna +Informatica Teorica (se pure ha senso istituire un'anagrafe delle correnti scientifiche) si colloca in una +data intermedia, che segue tutti i germi computazionali che abbiamo descritto, +ma precede di una decina di anni la nascita di ENIAC. Infatti, +la data che attira il nostro interesse è il 1936. Nel prossimo paragrafo tenteremo +di spiegare il perché. \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/introduzione/caratteristiche_di_un_algoritmo.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/introduzione/caratteristiche_di_un_algoritmo.tex new file mode 100644 index 000000000..9330c9964 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/introduzione/caratteristiche_di_un_algoritmo.tex @@ -0,0 +1,124 @@ +\section{Caratteristiche di un Algoritmo} + +Il grande scrittore di fantascienza Isaac Asimov fissò nei suoi racconti le 3 leggi +fondamentali che dovevano regolare il comportamento dei robot nei loro rapporti +con l'Uomo, ispirandole a principi inderogabili di rispetto, obbedienza e collaborazione. +Il nostro obiettivo qui è per certi versi analogo. Come già detto, vogliamo +infatti descrivere in modo rigoroso come avviene una computazione e precisare: + +\begin{itemize} + \item anzitutto chi computa (l'algoritmo che la svolge e la macchina su cui si svolge), + \item ma anche e soprattutto come si computa\\ + (le regole che algoritmo e macchina + devono rispettare nel loro lavoro); +\end{itemize} + +formulare in conclusione una specie di decalogo del bravo algoritmo e del bravo +calcolatore. Dunque il nostro contesto richiama in qualche senso le leggi dei robot androidi di Asimov. +Ma per ottenere il nostro obiettivo seguiamo, più che i romanzi di fantascienza, le riflessioni che gli +autorevoli scienziati citati alla fine dello scorso paragrafo, e tra essi segnatamente Alan Turing, +svolsero intorno al 1936. +Notiamo anzitutto che, per calcolare un dato problema, serve anzitutto un alfabeto appropriato con cui formalizzame i +contenuti (una lingua characteristica, per dirla alla Leibniz): una sequenza finita di simboli che descrivano i termini +della questione. Questo alfabeto può essere semplicemente quello della lingua italiana, o magari quello della lingua +scientifica dominante (l'inglese), ma può anche talora allargarsi in ragione del contesto. +Ad esempio, se trattiamo i polinomi a coefficienti interi, come nel caso del Decimo Problema di Hilbert, +è bene che prevediamo anche i simboli $0, 1, 2, 3, 4, 5, 6, 7, 8, 9, +, \cdot, -$. Altri ambiti ci potranno +poi suggerire alfabeti ancor più specialistici e mirati. Concordato dunque il nostro alfabeto, +possiamo formulare in modo adeguato il nostro problema e trasmetterlo all'algoritmo e alla macchina calcolatrice +per la loro computazione. +A questo punto dobbiamo finalmente pensare a concordare con precisione a quali +modelli di algoritmo e di macchina intendiamo ricorrere. In questo possiamo fare +momentaneo riferimento alla nostra esperienza personale e a un'idea intuitiva di +algoritmo e di calcolatore, per immaginare quali regole di buon comportamento ci +aspettiamo che essi rispettino durante il loro lavoro. Semmai, nei casi più delicati +ed incerti, proviamo a riferirci al modo di agire della mente umana come possibile +termine di paragone. Possiamo allora convenire quanto segue. + +\begin{enumerate} + \item Un algoritmo è di lunghezza finita. + \item Esiste un agente di calcolo (la macchina calcolatrice, appunto) che sviluppa la + computazione eseguendo le istruzioni dell' algoritmo. + \item L'agente di calcolo ha a disposizione una memoria, dove vengono immagazzinati i risultati intermedi + del calcolo. + \item Il calcolo avviene per passi discreti. + \item Il calcolo non è probabilistico. +\end{enumerate} + +I punti 1-3 hanno un'ovvia interpretazione. Il punto 4 afferma che il calcolo non +avviene mediante dispositivi analogici, ma si svolge ordinatamente, un passo dietro l'altro. +Il punto 5 afferma che il calcolo non è soggetto a fattori casuali, ma si +svolge in modo assolutamente preciso e rigoroso (o anche, come in genere si dice, +"deterministico"). Altre caratteristiche degli algoritmi sono le seguenti. + +\begin{enumerate} + \setcounter{enumi}{5} + \item Non deve esserci alcun limite finito alla lunghezza dei dati di ingresso. + \item Allo stesso modo, non deve esserci alcun limite alla quantità di memoria + disponibile. +\end{enumerate} + +Il punto 6 ci dice che l'input del problema può essere arbitrariamente lungo. +La condizione è assolutamente ragionevole: ad esempio, un algoritmo di somma tra +gli interi si deve applicare ad ogni possibile addendo, quindi ad ogni numero intero, comunque grande. +Anche il punto 7 è meritevole di qualche chiarimento. +Asserisce la possibilità di accedere ad una memoria potenzialmente illimitata. +Per sostenere la plausibilità di questa assunzione, proviamo a pensare che cosa accade in caso contrario, +se ammettiamo di limitare preliminarmente ad un livello uniforme prefissato le potenzialità di memoria. +In queste condizioni può capitare che algoritmi anche elementari, costruiti per eseguire semplici computazioni, +si trovino talora nell'impossibilità di completarle. Ad esempio, la funzione che ad +ogni intero associa il suo quadrato $f(x) = x^{2}$ non è più calcolabile, perchè lo +spazio di memoria necessario per computare il quadrato di $x$ dipende ovviamente +da $x$ e dunque, per $x$ molto grande, si trova ad infrangere i limiti eventualmente +prefissati. Così 7 risulta del tutto plausibile. +Anche le seguenti osservazioni sono essenziali per cogliere la natura del calcolo. + +\begin{enumerate} + \setcounter{enumi}{7} + \item Deve esserci un limite finito alla complessità delle istruzioni eseguibili dal + dispositivo. + \item Il numero di passi della computazione è finito ma non limitato. + \item Sono ammesse computazioni senza fine. +\end{enumerate} + +Il punto 8 ribadisce, insieme al punto 1, l'intrinseca finitezza del dispositivo di calcolo. +Ci deve essere una limitazione finita non solo per il numero delle istruzioni +di un algoritmo (come 1 sostiene), ma anche per la complessità delle singole istruzioni; in altre parole, +solo una porzione finita della memoria dell'agente di calcolo +deve essere occupata da queste istruzioni iniziali al momento in cui la computazione su un dato input si avvia. +La condizione non contraddice la condizione 7, +che riguarda i successivi passi del calcolo e afferma la possibilità di accoglierne +senza limite le informazioni nella restante porzione di memoria. D' altra parte 8 +si può intuitivamente giustificare proprio in riferimento alle caratteristiche della +mente umana, considerandone l'intrinseca limitatezza (ma anche le possibilità potenzialmente illimitate di crescita). +Il punto 9, poi, ci dice che non è possibile stabilire a priori un limite massimo per +Il numero dei passi richiesti per eseguire un generico algoritmo su un certo input. +11 punto 10, infine, fa riferimento all'eventualità di dover affrontare problemi senza soluzione, +come quelli accennati nei precedenti paragrafi: in questi casi una +computazione è destinata a prolungarsi indefinitamente senza riuscire a produrre +risposte soddisfacenti. +Queste sono le condizioni che possiamo ragionevolmente richiedere ad un qualunque sistema di computazione +(che includa sia il programma di calcolo che la macchina che lo esegue). +Sono 10, e quindi completano il nostro decalogo nel +senso stretto del termine. Sono anche sufficienti ad individuare il nostro obiettivo. Infatti, proprio a partire da +queste riflessioni, Alan Turing affrontò nel 1936 +il problema di definire rigorosamente che cosa possa intendersi per computabile, +proponendo un semplicissimo modello di calcolatore ante litteram (la macchina +di Turing, appunto) e sostenendo che computabile è esattamente quanto una macchina di Turing riesce a computare; +dimostrò conseguentemente l'impossibilità +di risolvere, ad esempio, l'Entscheidungsproblem di Hilbert, perchè non ci sono +macchine di Turing che lo soddisfino e, di conseguenza, neppure algoritmi di alcun genere con questa capacità. +Tra parentesi, potrà essere interessante anticipare che, qualche anno dopo, nel 1970, anche il Decimo Problema di Hilbert +dte. qualche anno dopo, nel 1970, anche il Decimo Problema di Hilbert ottenne la +ottenne la stessa risposta negativa, come racconteremo in maggior dettaglio nelle prossime pagine. +In realtà, nei capitoli che verranno, avremo modo di presentare, descrivere e discutere vari modelli di computazione, +anzitutto quello di Turing, ma anche altri, +classici come quello delle funzioni ricorsive o delle grammatiche, ed altri relativamente più recenti, +collegati ai linguaggi di programmazione. Avremo modo +di confrontare questi approcci e di mostrarne la sostanziale equivalenza. Incontreremo anche +(come già anticipato nelle scorse righe) casi di funzioni che non +si possono calcolare e di problemi che non si possono risolvere (perché estranei +a qualunque trattamento mediante i nostri modelli di calcolo). La teoria della +computabilità si interessa principalmente a tutte queste tematiche; in questo senso precorre ed inaugura, +come già accennato, la moderna Informatica Teorica; +concorre ancora sostanzialmente al suo sviluppo. \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/introduzione/main.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/introduzione/main.tex new file mode 100644 index 000000000..495752447 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/introduzione/main.tex @@ -0,0 +1,5 @@ +\chapter{Introduzione} + +\input{capitoli/introduzione/breve_storia_della_computabilita.tex} +\input{capitoli/introduzione/problema_di_matematica.tex} +\input{capitoli/introduzione/caratteristiche_di_un_algoritmo.tex} \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/introduzione/problema_di_matematica.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/introduzione/problema_di_matematica.tex new file mode 100644 index 000000000..4dc850b2a --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/introduzione/problema_di_matematica.tex @@ -0,0 +1,118 @@ +\section{Problema di Matematica} + +Apriamo una piccola parentesi, e parliamo ancora dei numeri interi +$0, \pm 1, \pm 2, \pm 3, ...$ +e delle operazioni $+, \cdot, -$ che li riguardano. In particolare, costruiamo +attraverso $+, \cdot, -$ polinomi a coefficienti interi, come + +\[ + 2x + 3, \ x + 2, \ x^{2} + y^{2} + 1, \ x^{2} + y^{2} - 2, \ + x^{2} - 2, \ x^{2} + 1 +\] + +e così via. Notiamo che alcuni di questi polinomi (il secondo e il quarto, per la +precisione) hanno anche radici intere: ad esempio: + +\begin{itemize} + \item $x + 2 = 0$ è risolto da $x = -2$, + \item $x^{2} + y^{2} - 2 = 0$ da $x = \pm 1, \ y = \pm 1$. +\end{itemize} + +Tuttavia gli altri polinomi della lista, pur avendo coefficienti interi, non hanno +radici intere: + +\begin{itemize} + \item non $2x + 3$, perché $3$ è dispari; + \item non $x^{2} - 2, \ x^{2} + 1$, perché $2$ e $-1$ non hanno radici quadrate tra gli interi; + \item non $x^{2} + y^{2} + 1$ per analoghi motivi (per ogni scelta di $x, y$ interi, si ha $x^{2} + + y^{2} + 1 > x^{2} + y{^2} \geq 0$ dunque $x^{2} + y{^2} + 1$ non si annulla mai tra gli interi). +\end{itemize} + +Anzi, proprio per ovviare a queste deficienze si è portati ad allargare l'ambito +numerico degli interi e formare rispettivamente gli insiemi dei razionali (con $- \frac{3}{2}$), +dei reali (con $\sqrt{2}$), dei complessi (con $i = \sqrt{-1}$). +Comunque, rimanendo nell'ambito dei polinomi a coefficienti interi, potrebbe interessarci distinguere +quali tra essi hanno anche radici intere, e quali no. Si tratta di questione tutto men che banale se +è vero, come è vero, che un matematico illustre come David Hilbert la segnalò nel 1900 in una lista di +23 problemi matematici meritevoli a suo avviso di lavoro e di attenzione. +Più precisamente la questione era collocata al posto 10 nella lista.\\ +\ \\ +\textbf{Decimo problema di Hilbert.} Determinare un procedimento capace di stabilire, +per ogni polinomio a coefficienti interi, se esso ha o no radici intere. + +Nel linguaggio odierno ci viene dunque richiesto un algoritmo che abbia + +\begin{itemize} + \item INPUT: un polinomio a coefficienti interi; + \item OUTPUT: SÌ/NO, secondo che il polinomio abbia o no radici intere. +\end{itemize} + +Si noti che il polinomio non ha limitazioni né sul grado (1, o 2, o anche maggiore) +né sul numero delle variabili coinvolte ($x$, eventualmente $y$, ma anche $z, t, ...$). + +Il decimo problema di Hilbert, formulato, come detto, nel 1900, non ebbe certo +soluzione nel 1936. Anzi, si dovette attendere il 1970 perché potesse trovare +una risposta per molti versi inattesa e sorprendente. Ma gli sviluppi del 1936 +ebbero un ruolo fondamentale in questa soluzione del 1970. Vediamo perché, +e collochiamoci idealmente negli anni '30, tre decenni dopo la proposizione del +quesito di Hilbert. + +Di fronte alla difficoltà di determinare l'algoritmo richiesto, si poteva reagire in +due modi: + +\begin{itemize} + \item pensare che i tempi (e le conoscenze matematiche) non erano ancora così maturi + da permetterne la soluzione, e che ulteriori progressi scientifici erano richiesti; + \item dubitare che l'algoritmo potesse davvero trovarsi e che nessuno, nel 1930 e + negli anni successivi, fosse effettivamente in grado di concepirlo. +\end{itemize} + +La prima reazione sembra più ragionevole e realistica; la seconda, più pessimista, +aveva comunque all'epoca fondate motivazioni. Infatti altre questioni di matematica e logica condividevano +la stessa situazione del Decimo Problema di Hilbert: una soluzione che tardava a venire, +ostacolata da formidabili complicazioni tecniche e teoriche. Ad esempio, era questo il caso del fondamentale +problema di logica che lo stesso Hilbert aveva sollevato, chiamandolo Entscheidungsproblem +(problema di decisione). Chi ha dimestichezza con la Logica Matematica ne conosce i termini; +gli altri lettori saranno, se non altro, soddisfatti di sapere che esso chiede di riconoscere quali affermazioni +di un usuale linguaggio logico (quello denominato "del primo ordine") sono da ritenersi valide +(cioè universalmente accettabili) e quali no. +Del resto, a favore della visione più "pessimista" contribuiva in quegli anni '30 +la fresca dimostrazione (proprio del 1931) di due famosissimi risultati di +Logica Matematica - i Teoremi di Incompletezza di Kurt Gidel - che stabilivano in qualche modo l'incapacità +umana di cogliere i reali fondamenti dei numeri interi +con le loro usuali operazioni $+, \cdot, -$ e conseguentemente l'impossibilità di delegare completamente la ricerca +matematica alle macchine, secondo le idee accennate nel paragrafo precedente. +Non ci attardiamo comunque su queste pur affascinanti connessioni e torniamo al +nostro problema delle radici intere, e alla possibilità di una risposta negativa del +tipo: "l' algoritmo richiesto non esiste". Ora, per convincere che un algoritmo per +il Decimo problema di Hilbert c'è, basta proporlo: stabilirne le istruzioni e verificarne la correttezza. +Invece, per escluderne l'esistenza, non ci basta formulare +qualche tentativo più o meno maldestro e poi denunciarne il fallimento. Dobbiamo +infatti stabilire una volta per tutte che nessuno, nel 1930 o oggi o in futuro, saprà +mai escogitare un procedimento di calcolo. Ma allora dobbiamo anticipatamente +convenire una qualche definizione generale di + +\begin{itemize} + \item ciò che è computabile (il problema) +\end{itemize} + +e, parallelamente, di + +\begin{itemize} + \item chi computa (l'algoritmo che affronta il problema e la macchina che lo svolge), + \item come si computa (le regole che algoritmo e macchina devono rispettare); +\end{itemize} + +dimostrare conseguentemente che il Decimo problema di Hilbert, \\o l'Entscheidungsproblem non rientrano in questa +classe di questioni "calcolabili" (se davvero questa è la loro sorte). +Così la questione si allarga dai contesti particolari +dei numeri interi o delle proposizioni logiche, e va ad introdurre temi basilari di +informatica: + +\begin{itemize} + \item che cosa è un "calcolatore"? + \item quali sono i problemi che i calcolatori sanno (o non sanno) risolvere? +\end{itemize} + +Fu nel 1936 che queste domande ebbero una prima risposta grazie a personaggi illustri degli albori +dell'informatica moderna, come Turing, Church, Kleene, Gòdel e altri. \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/alfabeti_stringhe_linguaggi.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/alfabeti_stringhe_linguaggi.tex new file mode 100644 index 000000000..bdff90ca8 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/alfabeti_stringhe_linguaggi.tex @@ -0,0 +1,214 @@ +\section{Alfabeti, Stringhe e Linguaggi} + +L'abilità nel rappresentare l'informazione è cruciale nel processo di calcolo\\ +dell'informazione stessa. Le società umane hanno creato linguaggi parlati +per comunicare ad un livello elementare, e hanno sviluppato il metodo della +scrittura per raggiungere un livello ben più sofisticato. +La lingua italiana, ad esempio, nella +sua forma parlata si basa su un insieme finito di suoni elementari, +le parole sono definite in termini di sequenze finite di tali suoni, le frasi vengono derivate da +sequenze finite di parole, i discorsi sono ottenuti da sequenze di frasi, e così via. +L'italiano scritto usa un insieme finito di simboli come insieme di primitive, le +parole sono definite da sequenze finite di simboli, i periodi vengono derivati da +sequenze finite di parole, i paragrafi da sequenze finite di periodi, e così via. +Approcci simili sono stati sviluppati anche in altri contesti; per esempio, abbiamo +già visto nel precedente capitolo che un numero naturale può essere rappresentato +come una sequenza finita di cifre decimali $0, 1, 2, 3, 4, 5, 6, 7, 8, 9$; ma anche +alternativamente in forma binaria cioè come sequenza finita di bit $0, 1$, quando + +\[ + 0, 1, 2, 3, 4, 5, ... , 10, 11, 12, ... +\] + +diventano rispettivamente + +\[ + 0, 1, 10, 11, 100, 101, ... , 1010, 1011, 1100, ... +\] + +Ci sono del resto altre possibili rappresentazioni dei naturali, +rispetto a basi ancora diverse; +ad esempio un naturale si può esprimere in modo molto rozzo con l'uso +del solo simbolo 1, come sequenza finita di 1: in questo caso + +\[ + 0, 1, 2, 3, ... +\] + +diventano +\[ + 1, 11, 111, 1111, ... +\] + +e così via.\\ +Se poi parliamo di polinomi a coefficienti interi, possiamo espandere i simboli +precedenti accogliendo $+, \cdot, -, x, y, z, t, ...$ e costruire l'oggetto della +nostra attenzione - i polinomi, appunto - come sequenze finite di tutti questi +elementi. Ovviamente ci si aspetta che i processi di calcolo trattino +l'informazione anche in ambiti più generali: +infatti essi manipolano non solo interi, ma anche grafi, programmi, e molti altri +tipi di entità. Comunque questi oggetti possono essere tutti +descritti come sequenze finite di lettere su opportuni alfabeti; dunque possiamo +assumere in astratto che i processi di calcolo considerino stringhe di simboli +scelti in un insieme finito e non vuoto (che viene in genere chiamato alfabeto). +Una sequenza finita di simboli di un dato alfabeto $A$ viene chiamata \textit{stringa} o +\textit{parola} su $A$. La stringa, formata dalla sequenza di simboli +$a_1, a_2, ..., a_n$, viene usualmente denotata $a_1a_2...a_n$. +Ammettiamo anche l'eventualità di una stringa +costituita da nessun simbolo, chiamata \textit{stringa vuota} e denotata +dalla lettere greca $\lambda$. + +\paragraph{Esempio.} $A = \{a, b, c, ..., z\}$ e $B = \{0, 1, 2, ..., 9\}$ sono alfabeti. +$abb$ è una stringa su $A$, mentre $123$ è una stringa su $B$. $b12$ non è una stringa +su $A$, in quanto contiene simboli non di $A$. Analogamente, +l'allineamento delle cifre decimali di $\pi$: $1415...$ +non è una stringa su $B$, perchè non è una sequenza finita.\\ + +Ribadiamo che un alfabeto $A$ non è mai vuoto: infatti, per costruire stringhe, +dobbiamo avere dei simboli che le compongano. Inoltre si assume di solito $A$ finito. +In realtà, già nei casi del Decimo problema di Hilbert e dei polinomi a +coefficienti interi, si ammettono infinite indeterminate $x, y, z, t,...$ +e dunque infiniti simboli; +ma si può facilmente rimediare con qualche artificio, ad esempio adoperando per +le indeterminate due soli simboli $x, |$ e convenendo di rappresentare +$x, y, z, t,...$ come + +\[ + x, x|, x||, x|||, ... +\] + +cioè come stringhe su $x, |$.\\ + +La lunghezza di una stringa $\alpha$ - denotata $l(\alpha)$ - è il numero dei +simboli che la compongono: per $\alpha = a_1a_2 \cdots a_n, \ l(\alpha) = n$. + +\paragraph{Esempio.} +$aa$ è una stringa di lunghezza $2$; $l(\lambda) = 0$; $l(ab) + l(b) = 3$.\\ + +Date due stringhe $\alpha, \beta$ se ne può formare un'altra in cui $\alpha$ è +seguita da $\beta$: essa è +denotata $\alpha\beta$ e chiamata la \textit{concatenazione} di $\alpha$ e $\beta$. +La notazione $\alpha^{i}$ è usata per la +stringa ottenuta concatenando $i$ copie della stringa $\alpha$ quando +$i$ è un intero positivo. +Così $\alpha^2 = \alpha\alpha$, $\alpha^3 = \alpha\alpha\alpha$ e via dicendo. +Si intende poi $\alpha^1 = \alpha $ e $\alpha^0 = \lambda$. +La concatenazione si applica ovviamente anche alle lettere di $A$, +viste come parole su $A$, e anzi rappresenta la via +secondo cui esse generano le altre stringhe. + +\paragraph{Esempio.} +La concatenazione di $ab$ con $baa$ produce la stringa $abbaa$, quella di $baa$ +con $ab$ determina $baaab$, cioè $ba^{3}b$. Le concatenazioni $\lambda\alpha$ e +$\alpha\lambda$, per ogni stringa $\alpha$, producono la stessa stringa $\alpha$. +In particolare, $\lambda\lambda = \lambda$.\\ + +Diciamo che una stringa $\alpha$ è una \textit{sottostringa} +di $\beta$ se $\beta = \gamma\alpha\rho$, per qualche scelta +di stringhe $\gamma$ e $\rho$. Una sottostringa $\alpha$ +di una stringa $\beta$ si chiama \textit{prefisso} di $\beta$ se +$\beta = \alpha\rho$ per qualche stringa $\rho$ (dunque per $\gamma = \lambda$); +$\alpha$ è un \textit{prefisso proprio} se +$\rho \neq \lambda$. Una sottostringa $\alpha$ di una stringa $\beta$ +è un \textit{suffisso} di $\beta$ se $\beta = \gamma\alpha$ per +qualche stringa $\gamma$; $\alpha$ è un \textit{suffisso proprio} se $\gamma \neq \lambda$. + +\paragraph{Esempio.} +$\lambda, a, b, ab, abb$ sono sottostringhe di $abb$. $\lambda, a, ab$ sono prefissi +propri di $abb$. $\lambda, b, bb$ sono suffissi propri di $abb$. +$abb$ è prefisso e suffisso di $abb$.\\ + +Se $\alpha = a_1 \cdots a_n$, allora $a_n \cdots a_1$ è chiamata +l'\textit{inversa} di $\alpha$ e viene denotata $\alpha^{rev}$. +L'insieme di tutte le stringhe su un alfabeto $A$ viene indicato $A*$, +mentre $A+$ denota l'insieme $A* - \{\lambda\}$ delle stringhe non vuote su $A$. +Un alfabeto $A$, come insieme finito di simboli, si può sempre ordinare in più +modi possibili. Sarà spesso conveniente nel seguito di questi appunti fissare +un tale ordinamento totale $<$ e, per $A = \{a_1, ...,a_n\}$, assumere ad esempio + +\[ + a_1 < a_2 < \cdots < a_n. +\] + +In realtà è bene concordare sin d'ora un qualche ordinamento anche per +le parole su $A$. Infatti in Scienza dell'Informazione si affrontano +comunemente tecniche di ricerca sequenziale e binaria, +\textit{insertion sort}, \textit{quick sort} e \textit{merge sort} che +trattano stringhe e si riferiscono a un loro prefissato ordinamento. Una strategia +frequentemente usata è quella \textit{lessicografica}, definita nel modo che segue. + +\paragraph{Definizione.} +Sia $A$ un alfabeto (ordinato da qualche relazione $\le$) e siano $\alpha$ e +$\beta$ stringhe in $A*$. Si dice che $\alpha$ è \textit{lessicograficamente minore} +di $\beta$, $\alpha < \beta$, o +equivalentemente $\beta$ \textit{lessicograficamente maggiore} di $\alpha$, +$\beta > \alpha$, se vale uno dei due casi: + +\begin{enumerate} + \item $\alpha$ è prefisso di $\beta$, + \item $\alpha$ ha un prefisso $\gamma a$, + $\beta$ ha un prefisso $\gamma b$, per lo stesso $\gamma \in A*$, + con $a, b \in A$ e $a < b$ in $A$. +\end{enumerate} + +\paragraph{Esempi.} +\begin{enumerate} + \item Se $A$ è l'alfabeto della lingua italiana, ordinato ponendo + $a < b < c < \cdots$, + l'ordine lessicografico in $A*$ non è quello comune dei vocabolari; + infatti $aba < abb$ perché $a < b$, e $abb$ precede $abba$ perché ha lunghezza + minore, proprio + come nei dizionari, ma $z$ precede $ab$ perché ha lunghezza minore. + \item Consideriamo ora l'alfabeto $A = \{0, 1, 2, 3, 4, 5, 6, 7, 8, 9\}$ + dove si fissa, come di consueto, $0 < 1 < 2 < \cdots < 9$. + L'ordine che ne deriva sui naturali, intesi + come stringhe in $A*$ è il loro ordine abituale: ad esempio + \begin{itemize} + \item $151 < 153$ perché $1 < 3$, + \item $151 < 1327$ perché $151$ ha lunghezza minore. + \end{itemize} +\end{enumerate} + +Consideriamo ancora i numeri naturali $\mathbb{N}$, +intesi come parole su $A = \{0, 1, 2, ..., 9\}$ rispetto alla loro tradizionale +rappresentazione in base $10$. È ben noto che +$N$ è primo se $N \ge 2$ e gli unici divisori di $N$ sono $1$ e $N$, +e che ogni $N \ge 2$ si decompone in modo unico nel prodotto di fattori primi. +Nascono così due classici problemi: entrambi hanno per input il nostro $N \ge 2$, + +\begin{itemize} + \item il primo chiede se $N$ è primo o no, + \item il secondo di decomporre $N$ nei suoi fattori primi. +\end{itemize} + +Allora la prima domanda intende riconoscere tra le stringhe su $A$ +quelle che corrispondono ai numeri primi; la seconda vuole calcolare, +per ogni $N$, quelle stringhe +che rappresentano numeri primi che dividono $N$. +Nel primo caso si vuole individuare un sottoinsieme di $A*$, nel secondo +computare una funzione che da parole +su $A$ genera nuove sequenze di parole su $A$. Sotto questo punto di vista, +il Decimo problema di Hilbert presenta molte analogie col quesito di riconoscere +i primi. È vero che tratta polinomi piuttosto che +numeri, e che adopera tutt'altro criterio di selezione +(l'esistenza di radici intere piuttosto che la primalità); +tuttavia ha ancora a che fare con un alfabeto $A$ +(quello dei polinomi a coefficienti interi) e con parole su $A$ +(i polinomi, appunto) e vuole scegliere quelle parole che soddisfano il criterio +fissato (l'esistenza di radici intere), +individuare quindi un particolare sottoinsieme di $A*$. +In generale, dato un alfabeto $A$, un sottoinsieme $L$ di $A*$ si chiama \textit{linguaggio + formale}, o più semplicemente \textit{linguaggio}, o anche \textit{problema}. +La prima notazione fa riferimento alla sua natura di insieme di parole, +come ogni lingua tradizionale; la seconda alla questione computazionale che $L$ +ovviamente propone, e cioè +riconoscere le stringhe su $A$ che stanno in $L$ e escludere le altre. + +\paragraph{Esempio.} +L'insieme dei numeri primi è un linguaggio su $A = \{0, 1, 2, ..., 9\}$ +(e su qualunque alfabeto per i naturali). L'insieme dei polinomi a coefficienti e +radici intere è un linguaggio sull'alfabeto del Decimo problema di Hilbert.\\ + +Non dimentichiamo che, accanto al "problema" di riconoscere un linguaggio, c'è +anche quello di computare funzioni su stringhe su un alfabeto $A$, come il caso +della decomposizione in fattori primi ci ha sopra illustrato. \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/codifiche_di_stringhe.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/codifiche_di_stringhe.tex new file mode 100644 index 000000000..05eba44c4 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/codifiche_di_stringhe.tex @@ -0,0 +1,192 @@ +\section{Codifiche di Stringhe} + +Abbiamo sin qui considerato stringhe su alfabeti $A$ arbitrari. In realtà è +possibile ridurre il nostro ambito ai numeri naturali e a uno degli alfabeti che +servono a rappresentarli, come $\{1\}$ o $\{0, 1\}$ o $\{0, 1, 2, \ldots\}$. +L'idea che si può seguire è la stessa in base alla quale + +\begin{itemize} + \item in un teatro ogni poltrona ha un numero di riconoscimento, + \item o in una biblioteca ogni volume riceve un suo numero di etichetta. +\end{itemize} + +I numeri non sono né poltrone né libri, ma servono a identificarli senza ambiguità. +Procedimenti effettivi di codifica relativamente elementari svolgono la stessa +funzione per le stringhe su un qualunque alfabeto $A$. Vediamone alcuni. Per $A$ +arbitrario, cerchiamo di definire in modo esplicito una funzione di numerazione $\sharp$ +da $A^*$ a $\mathbb{N}$. + +\begin{enumerate} + \item Una prima strategia può fare riferimento alla rappresentazione dei + naturali in base 10, o 2, o qualunque valore prefissato $>0$. Ammettiamo, ad + esempio, per semplicità, che l'alfabeto $A$ abbia nove elementi. È immediato + identificarli con le cifre $1,2, \ldots, 9$ e magari indicarli con + $a_1, a_2, \ldots, a_9$. Così + + \[ + j \mapsto a_j \text{ per ogni } j=1, \ldots, 9 + \] + + è una corrispondenza biunivoca tra $\{1,2, \ldots, 9\}$ e $A$. A questo + punto ad ogni parola non vuota $w=a_{j_1} \cdots a_{j_k}$ su $A$ possiamo + associare $j_1 \cdots j_k$ in base 10, cioè porre + + $$ + \sharp(w)=j_1 \cdot 10^{k-1}+j_2 \cdot 10^{k-2}+\cdots+j_{k-1} \cdot 10^1+j_k \cdot 10^0 + $$ + + gli indici dei simboli di $w$ determinano i coefficienti di questa + rappresentazione, la lunghezza $k$ di $w$ ne regola il numero degli addendi + ($k$, appunto, da $10^0$ a $10^{k-1}$). Si noti che $\sharp(w) \neq 0$ perché + $j_1, \ldots, j_k>0$ e $k>0$. Alla parola vuota $\lambda$, che non ha + simboli e ha lunghezza 0 , associamo allora 0: + + $$ + \sharp(\lambda)=0 . + $$ + + Parole distinte ricevono così in modo effettivo numeri distinti. + Per esempio + + $$ + \sharp\left(a_1 a_2 a_3\right)=123, \ \ \sharp\left(a_2 a_4\right)=24, + $$ + + e via dicendo. Viceversa 2154 è il numero di $a_2 a_1 a_5 a_4$, mentre + 1004 non corrisponde a nessuna parola perché contiene 0, ma non è 0. + Quindi $\sharp$ non è suriettiva. Tuttavia per ogni naturale $n$ è + possibile stabilire in modo effettivo se $n$ è o no nell'immagine + di $\sharp$, se sì, a quale parola corrisponde.\\ + Il procedimento si estende facilmente al caso in cui l'alfabeto $A$ ha non + più nove, ma un numero arbitrario $N>0$ di simboli. Si scrivono gli + elementi di $A$ come $a_1, \ldots, a_N$ e poi si fa riferimento a $N+1>1$ + e alla rappresentazione dei naturali in base $N+1$, al fatto cioè che ogni + $j$ si scrive in modo unico come + + $$ + j=j_1 \cdot(N+1)^{k-1}+j_2 \cdot(N+1)^{k-2}+\cdots+j_{k-1} \cdot(N+1)^1+j_k \cdot(N+1)^0 + $$ + + per $k>0$, $j_1, \ldots, j_k$ naturali opportuni. Si pone allora, per + $w \in A^*$ + + \begin{itemize} + \item se $w=\lambda$ è vuota, $\sharp(w)=0$, + \item se $w=a_{j_1} \cdots a_{j_k}$ non è vuota, + \end{itemize} + + $$ + \sharp(w)=j_1 \cdot(N+1)^{k-1}+j_2 \cdot(N+1)^{k-2}+\cdots+j_{k-1} \cdot(N+1)^1+j_k \cdot(N+1)^0 . + $$ + + Le proprietà osservate per $N=9$ si preservano. In particolare ogni + parola su $A$ riceve il "suo" numero $\sharp(w)$ e, viceversa, da ogni + naturale si può recuperare in modo effettivo la parola corrispondente, + se esiste. + I pignoli potrebbero semmai obiettare che la numerazione data da + $\sharp$ ha il difetto di non saper distinguere simboli da parole. + Per spiegarci meglio, riferiamoci per un attimo alla lingua italiana, dove + $a$ ha ruolo sia di lettera (vocale) che di parola (preposizione: andare + "$a$" Roma). Questa duplice veste meriterebbe un duplice numero di codice, + uno come simbolo e uno come stringa. Ma $\sharp$ le assegna soltanto il valore 1, + come prima lettera dell'alfabeto. + + \item Cerchiamo di ovviare all'ultima obiezione proponendo un'altra strategia + di numerazione che fa stavolta ricorso al teorema fondamentale + dell'Aritmetica, quello secondo cui ogni naturale $\geq 2$ si decompone + in modo unico nel prodotto di fattori primi: ad esempio + $12=2^2 \cdot 3$,$15=3 \cdot 5$, e cosi via. Cominciamo allora col + numerare i simboli dell'alfabeto $A$, cui assegniamo + valori \textit{dispari} (per motivi che saranno chiari più tardi). + Definiamo dunque una funzione $\sharp_0$ da $A$ a $\mathbb{N}$ ponendo, + per $A=\{a_1, \ldots, a_N\}$ e per $j=1, \ldots, N$, + + $$ + \sharp_0\left(a_j\right)=2 \cdot j+1 + $$ + + cioè $\sharp_0(a_1)=3, \sharp_0(a_2)=5$ e via dicendo.\\ + Passiamo poi a numerare le stringhe di $A^*$, introducendo la seguente + funzione $\sharp$ da $A^*$ a $\mathbb{N}$. Sia $w \in A^*$: + + \begin{itemize} + \item se $w=\lambda$, conveniamo $\sharp(w)=1$, + \item altrimenti sia $w=a_{j_1} \cdots a_{j_k}$; in riferimento ai valori + $2 \cdot j_j+1, \ldots .2 \cdot j_k+1$ già associati da $\sharp_0$ + a $j_1, \ldots, j_k$, poniamo + + $$ + \sharp_1(w)=2^{2 \cdot j_1+1} \cdot 3^{2 \cdot j_2+1} \cdots p_k^{2 \cdot j_k+1} + $$ + + dove $p_k$ denota il $k$-mo numero della sequenza dei primi. + \end{itemize} + + Assegniamo quindi le codifiche (tramite $\sharp_0$) dei simboli di $w$ + come esponenti a $\sharp_1(w)$ nella sua decomposizione in fattori primi. + Per esempio + + $$ + \sharp_1\left(a_1 a_4 a_2 a_1 a_1\right)=2^3 \cdot 3^9 \cdot 5^5 \cdot 7^3 \cdot 11^3 \text {. } + $$ + + In questo modo, stringhe distinte ricevono in modo effettivo valori + distinti. Viceversa, per ogni numero naturale $n$, è possibile stabilire + in modo effettivo se $n$ è o no immagine di $\sharp_1$, se sì, risalire + alla parola corrispondente: basta fare riferimento alla decomposizione di + $n$ in fattori primi, oppure constatare che $n=1$. Per esempio, il numero + dei fattori primi coinvolti rivela la lunghezza della eventuale stringa + corrispondente. Stavolta, poi, gli elementi $a_j$ di $A$ ricevono due + numeri distinti + + \begin{itemize} + \item l'uno $2 \cdot j+1$ come simboli, + \item l'altro $2^{2 \cdot j+1}$ come parole. + \end{itemize} + + Né c'è pericolo di confondere questi valori, perché i numeri dei simboli + sono dispari $\geq 3$, mentre quelli delle parole sono 1 oppure pari, + perché esplicitamente divisibili per 2. + Questo secondo procedimento di numerazione fu ideato da Kurt Gödel nella + sua dimostrazione dei Teoremi di Incompletezza cui si è accennato nel + primo capitolo. + Una volta trattati simboli e stringhe, esso permette anche di numerare + coppie, o terne, o $n$-uple ordinate di stringhe. A questo proposito, + abbiamo già visto una possibile strategia: tradurre queste sequenze in + stringhe in un alfabeto più lungo che utilizzi anche il simbolo bianco + $\star$. Così $\left(w_1, w_2\right)$ diviene + $w_1 \star w_2$, $\left(w_1, w_2, w_3\right)$ diviene + $w_1 \star w_2 \star w_3$ e via dicendo; in questo modo + $\left(w_1, w_2\right)$, $\left(w_1, w_2, w_3\right), \ldots$ vengono a + condividere il numero che $w_1 \star w_2, w_1 \star w_2 \star w_3, \ldots$ + ricevono in $A \cup\{\star\}$. + Il procedimento di Gödel consente tuttavia di evitare il ricorso al simbolo + estraneo $\star$. Infatti, di fronte alla $n$-upla $(w_1, w_2, \ldots, w_n)$ + di stringhe di $A$ (con $n \ge 2$), possiamo + + \begin{itemize} + \item ricordare che $w_1, w_2, \ldots, w_n$ hanno già un loro numero + di codice, $\sharp_1(w_1)$, $\sharp_1\left(w_2\right), \ldots, sharp_1\left(w_n\right)$ + rispettivamente, + \item ricorrere allora nuovamente al teorema fondamentale dell'Aritmetica, + \item associare a $\left(w_1, w_2, \ldots, w_n\right)$ il numero + $$ + \sharp_2\left(w_1, w_2, \ldots, w_n\right)=2^{\sharp_1\left(w_1\right)} \cdot 3^{\sharp_1\left(w_2\right)} \cdots p_k^{\sharp_1\left(w_n\right)} . + $$ + \end{itemize} + + Si ottiene così una funzione effettiva $\sharp_2$ dall'insieme delle + sequenze finite di stringhe su $A$ di ogni possibile lunghezza $n \geq 2$ + a $\mathbb{N}$. Sequenze distinte ricevono da $\sharp_2$ numeri distinti, + per il teorema fondamentale dell'Aritmetica e l'unicità della + decomposizione in fattori primi. Viceversa, per ogni naturale $m$, è + possibile effettivamente riconoscere se $m$ è o no immagine di $\sharp_2$ + di qualche sequenza di stringhe e, se sì, di quale: di nuovo basta + ricorrere alla decomposizione di $m$ in fattori primi, il numero dei + fattori primi distinti coinvolti rivela la lunghezza della sequenza, gli + esponenti di questi fattori dicono le stringhe della sequenza. Di più, + non c'è pericolo di confondere i valori assegnati alle sequenze di stringhe + e quelli associati in precedenza a simboli o stringhe, perché questi ultimi + sono dispari oppure pari con esponenti dispari $\geq 3$ nella loro + decomposizione in fattori primi, i nuovi sono pari e con esponenti pari. +\end{enumerate} \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/imgs/mdt_piu_nastri.png b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/imgs/mdt_piu_nastri.png new file mode 100644 index 000000000..1e51d16e7 Binary files /dev/null and b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/imgs/mdt_piu_nastri.png differ diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/la_macchina_di_turing.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/la_macchina_di_turing.tex new file mode 100644 index 000000000..e75c08b22 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/la_macchina_di_turing.tex @@ -0,0 +1,309 @@ +\section{La Macchina di Turing} + +La Macchina di Turing, qui abbreviata MdT, prende il nome dal matematico +inglese Alan Turing, che la introdusse nel 1936 precedendo di almeno un decennio +l'era del computer. +È il primo dei modelli di calcolo che vogliamo trattare. +L'idea di Turing è infatti +quella di immaginare un semplice meccanismo astratto che riassuma e +simuli tutte le potenzialità computazionali dell'uomo comune. +Così Turing prende a esplicito +modello l'"\textit{impiegato diligente}", che svolge con ordine e cura gli +incarichi assegnatigli, ma non fa niente di più: +all'ora stabilita timbra il cartellino e torna a casa. +Vediamo come la MdT traduce questo comportamento. +Da un punto di vista fisico la MdT può essere pensata come composta da una unità +di controllo a stati finiti, un nastro di lunghezza infinita e una testina di +lettura e scrittura, che permette la comunicazione tra controllo e nastro. +Il nastro è infinito e suddiviso in celle (anche chiamate quadri). +Ogni cella è in +grado di memorizzare un simbolo di un certo alfabeto $A = \{a_0, a_1, ..., a_n,\}$, +oppure un simbolo "bianco" $*$ che denota l'assenza di scrittura in una cella. +Il nastro contiene solo un numero finito di simboli di $A$; +tutte le altre celle contengono comunque il simbolo bianco $*$. +La testina di lettura e scrittura permette all'unità di +controllo di leggere e scrivere un simbolo per volta dal nastro, +quindi a ogni istante la testina può indicare una sola cella del nastro +(e leggere o scrivere il simbolo che la riguarda). +L'unità di controllo, oltre ad avere gli organi meccanici per lo +spostamento del nastro e della testina, contiene il programma secondo cui verrà +eseguito il calcolo e mantiene lo stato della macchina. +L'insieme di possibili stati della macchina è un insieme finito +$Q = \{q_0, q_1, ..., q_m\}$. +Se vogliamo riprendere il paragone con l'impiegato diligente, $A$ +rappresenta l'insieme di lettere con cui egli legge la domanda di partenza e +svolge i suoi calcoli successivi; +gli stati di $Q$ corrispondono invece alle possibilità che l'impiegato ha +di scrivere la stessa lettera in più modi distinti, sottolineandola, o +evidenziandola, o colorandola per darle maggiore risalto. +La computazione della MdT avviene per passi discreti. Si concorda che, all'avvio +di ogni sua computazione, la macchina si trovi in uno stato iniziale prefissato +$q_0$. +Ad ogni passo l'unità di controllo prende atto dello stato in cui si trova e dal +simbolo contenuto nella cella che la testina indica, e di conseguenza esegue le +operazioni sotto elencate: + +\begin{itemize} + \item rivede il suo stato; + \item scrive un simbolo nella cella indicata dalla testina, sostituendo il + simbolo esistente (ricordiamo che tra i simboli ammessi c'è anche $*$); + \item sposta la testina di una posizione a sinistra o a destra. +\end{itemize} + +Il nuovo stato assunto dall'unità di controllo, il simbolo da scrivere sulla cella +indicata dalla testina e lo spostamento della testina a sinistra o a destra sono +determinati dal programma della MdT, che stabilisce il comportamento della macchina +stessa. Il programma di una MdT può quindi essere pensato come un insieme +di quintuple della forma $(q, a, q', a', x)$, dove $q$ indica lo stato dell'unità +di controllo, $a$ il simbolo nella cella indicata dalla testina mentre $q', a' , x$ +specificano l'azione che la MdT deve intraprendere: +in dettaglio $q'$ rappresenta il nuovo stato +dell'unità di controllo, $a'$ il simbolo da scrivere nella cella esaminata +dalla testina e $x = \pm 1$ lo spostamento della testina: una posizione a sinistra +se $x = -1$, a destra se $x = +1$. $+1$ sarà talora denotato semplicemente con $1$ +nel seguito. +Ovviamente ogni singola MdT si riconosce, non tanto dal suo aspetto esteriore di +nastri, celle e testine, quanto proprio da queste quintuple, e cioè dal programma +che le si richiede di svolgere e dalle istruzioni che esso prevede, +tutte ridotte a +semplici ordini di cambiamento di stato, di scrittura e di spostamento: così Turing +schematizzava il comportamento della mente dell'impiegato diligente, +sintetizzandone le capacità operative minime, e secondo questo modello si +prevede di +riconoscere linguaggi o computare funzioni. +Notiamo poi che un impiegato diligente esegue ordinatamente le sue istruzioni +finché ne ha e purché non ne abbia troppe tra loro in concorrenza. Nel primo caso, +quando gli ordini mancano, l'impiegato si ferma e ritiene concluso il suo lavoro; +nel secondo, invece, resta nell'imbarazzo della scelta: responsabilità che non si +può scaricare sulle sue spalle. +È dunque importante che le istruzioni relative ad una coppia $(q, a)$, +quando esistono, siano univoche. Si può ammettere che manchino, non che si +moltiplichino. Il +passaggio da $(q, a)$ alla corrispondente terna $(q', a', x)$ deve essere +assolutamente deterministico e lontano da ogni ambiguità. +Il programma di una MdT può essere descritto mediante una tabella a righe e +colonne, la cosiddetta matrice funzionale; le righe corrispondono ai possibili +stati $q$ della macchina mentre le colonne corrispondono ai possibili simboli $a$ +dell'alfabeto (incluso $*$). All'incrocio di ciascuna coppia $q$ e $a$ si pone +l'istruzione che +deve essere eseguita dalla macchina quando l'unità di controllo si trova nello +stato $q$ e la testina legge il simbolo $a$: la terna che descrive in che stato +entrare, che +cosa scrivere, dove spostarsi. È ammesso che una casella della matrice funzionale +sia bianca. In tal caso, si conviene che la macchina non ha azioni da compiere e +quindi termina il calcolo. +La matrice funzionale della macchina rappresenta una specie di tabella in cui +sono concentrate tutte le istruzioni: l'impiegato diligente esegue il suo lavoro +applicandola pedissequamente. +Ma è tempo di dare una definizione formalmente rigorosa delle MdT, che ne +riassuma i caratteri essenziali, l'alfabeto, gli stati, le istruzioni. +Possiamo allora dire: + +\paragraph{Definizione.} +Una Macchina di Turing $M$ è una quadrupla $(Q, A, \delta, q_0)$, dove: + +\begin{itemize} + \item $Q$ è un insieme finito di stati; + \item $A$ è un alfabeto, cui si aggiunge il simbolo bianco $*$; + \item $\delta$ è una funzione da $Q \times (A \cup \{*\})$ a + $Q \times (A \cup \{*\}) \times \{ -1, +1\}$: $\delta$ è chiamata + \textit{funzione di transizione}, e gli elementi $(q, a, q', a', x)$ + di $\delta$ sono chiamati \textit{regole + di transizione} o \textit{istruzioni} di $M$; + \item $q_0 \in Q$ è lo stato iniziale. +\end{itemize} + +Come già sottolineato, l'informazione cruciale su una MdT è quella fornita dalla +funzione di transizione $\delta$, quella che descrive il programma delle istruzioni. +È $\delta$ che regola il comportamento di $M$. +Così, se $M$ si trova nello stato $q \in Q$, la +testina legge il simbolo $a \in A \cup \{*\}$ e $\delta(q, a) = (q', a', x)$, +allora $M$ si sposta +nello stato $q'$, il simbolo $a'$ sostituisce $a$ nella cella in esame e la +testina si sposta +di una posizione a sinistra se $x = -1$, o a destra se $x = +1$. Se invece $M$ si +trova nello stato $q \in Q$, la testina legge il simbolo $a \in A \cup \{*\}$ ma +$\delta(q, a)$ non +è definito, allora $M$ si arresta. In questo senso, la matrice sopra descritta +altro +non è che il grafico di $\delta$. Spesso, quando chiaro dal contesto, +identificheremo una +macchina di Turing $M$ con la sua funzione di transizione $\delta$. +L'istruzione di $\delta$ che +genera la terna $(q', a', x)$ da $(q, a)$ si scriverà talora + +\[ + (q, a) \xrightarrow{ \ \delta \ } (q', a', x) +\] + +invece che $\delta (q, a) = (q', a' x)$ o $(q, a, q', a', x) \in \delta$; +qualche volta, quando non ci +sono rischi di ambiguità, ometteremo $\delta$ e scriveremo semplicemente + +\[ + (q, a) \rightarrow (q', a', x). +\] + +Una MdT, così come l'abbiamo appena definita, viene anche detta \textit{deterministica}, +a sottolineare che ogni tripla $(q', a', x)$, se esiste, è unica e univocamente +determinata dalla coppia $(q, a)$. +Tra qualche paragrafo incontreremo anche MdT non +deterministiche e ne spiegheremo le differenze rispetto a quanto appena descritto. +Torniamo adesso ad una descrizione informale del modo in cui una MdT esegue le +sue computazioni a partire da un dato input e restituisce il relativo output. +Ci è utile introdurre anche il concetto di configurazione istantanea di una MdT: +una sorta +di "fotografia" che ritrae la macchina ad un dato istante di lavoro, +illustrandone lo +stato, il contenuto del nastro e la posizione della testina. +Poichè il nastro di una MdT è sempre vuoto, salvo che per un numero finito di celle, +è possibile riassumerne il contenuto con una stringa finita di simboli e fornire +la descrizione istantanea di una MdT con una quadrupla del tipo $(\xi, q, a, \eta)$, +dove $q$ rappresenta lo stato della macchina all'istante in considerazione, +$a$ è il simbolo in lettura, $\xi \in (A \cup \{*\})^*$ è la stringa di simboli a +sinistra del simbolo in lettura ed +$\eta \in (A \cup \{*\})^*$ è la stringa di simboli a destra del simbolo in lettura +prima che il nastro diventi definitivamente bianco. Per esempio, +per $A = \{1\}$, $(11, q_0 , 1, \lambda)$ ci +dice che la macchina esamina una cella con $1$ nello stato $q_0$, che il nastro è +bianco +a destra della cella considerata, contiene $11$ e poi diventa bianco a sinistra. +Poniamo adesso: + +\paragraph{Definizione.} +Una configurazione istantanea di una Macchina di Turing +$M =(Q, A, \delta, q_0)$ è un elemento dell'insieme: +$(A \in \{*\})^* \times Q \times (A \cup \{*\}) \times (A \cup \{*\})^*$.\\ + +Riepiloghiamo allora come avviene una computazione di una macchina $M$ su una +stringa di input $w \in A^*$. + +\begin{itemize} + \item Al passo iniziale $0$, $M$ esamina una sequenza $w$ scritta da sinistra + verso destra sul nastro di input: la testina indica il primo carattere + $a_0$ di $w$ e lo stato interno della macchina è quello iniziale $q_0$. + Questa configurazione è detta + \textit{configurazione iniziale} su $w$. + Se $w = a_0w'$ , la 4-upla che la rappresenta è + $(\lambda, q_0, a_0, w')$. + \item Ammettiamo che al passo $i$ della computazione la macchina si trovi + nella + configurazione $C_i = (\xi, q, a, \eta)$. + In base alla funzione $\delta$, se esiste una regola di transizione + $(q, a) \xrightarrow{ \ \delta \ } (q', a', x)$, + allora la macchina passa nella nuova configurazione $C_{i+1}$ derivata + da $C_i$ secondo questa istruzione. Se invece $\delta(q, a)$ + non è definita $M$ si arresta. + Per esempio, se $C_i$ è come sopra + $(11, q_0, 1, \lambda)$ e + $(q_0, 1) \xrightarrow{ \ \delta \ } (q_1, 1, 1)$, si ha + $C_{i+1} = (111, q_1, *, \lambda)$; se invece + $(q_0, 1) \xrightarrow{ \ \delta \ } (q_1, 1, -1)$, + allora $C{i+1}= (1, q_1, 1, 1)$. + \item Se $M$ si ferma dopo un numero $n$ finito di passi, + allora si dice che $M$ \textit{converge} + sull'input $w$ (in notazione, $M \downarrow w$); + $C_n$ si chiama \textit{configurazione finale}, la + sequenza di configurazioni $C_0, C_1, ..., C_n$ è una computazione + completa (finita) + di $M$ sull'input $w$ e la stringa contenuta sul nastro di input è l' + output di tale computazione. + Per esempio, se $C_n = (\xi, q, a, \eta)$, allora $\xi a \eta$ è l'output. + \item Se $M$ non si arresta mai, allora si dice che $M$ \textit{diverge} + sull'input $w$ e si scrive + $M \uparrow w$. +\end{itemize} + +Per formalizzare rigorosamente questo comportamento computazionale possiamo +introdurre una relazione binaria $\vdash_M$ tra le configurazioni di $M$. +Sostanzialmente $\vdash_M$ associa ad ogni configurazione di $M$ quella che la +segue dopo l'esecuzione dell'istruzione di $M$ corrispondente. +Per esempio, se $C$ è, come sopra, $(11, q_0, 1, \lambda)$, $C'$ è +$(111, q_1, *, \lambda)$ e in $M$ si ha l'istruzione +$(q_0, 1) \xrightarrow{ \ \delta \ } (q_1, 1 , 1)$, si +pone $C \vdash_M C'$. +Il lettore potrà scrivere per esercizio, se ha voglia e pazienza, +tutti i dettagli della definizione di $\vdash_M$. +Se poi per una data $C$ non esiste alcuna configurazione $C$ tale che +$C \vdash_M C'$, +allora scriveremo $C \nvdash_M$.\\ + +Sia \(\vdash^*_M\) la chiusura riflessiva e transitiva di \(\vdash_M\); vale dire, +per \(C, C'\) configurazioni, \(C \vdash^*_M C'\) significa che esistono un +naturale $n$ e configurazioni $C_0, C_1, \ldots$ $C_n$, tali che +$C = C_0 \vdash_M C_1 \vdash_M \ldots \vdash_M C_n = C^{\prime}$. +Chiamiamo poi \textit{computazione} di una MdT $M$ su un input $w$ una sequenza +(eventualmente infinita) di configurazioni + +\[ + C_0 \vdash_M C_1 \vdash_M \ldots \vdash_M C_i \vdash_M \ldots +\] + +tale che $C_0$ è una configurazione iniziale su $w$. Chiaramente +$M \downarrow w$ se questa computazione è finita + +\[ + C_0 \vdash_M C_1 \vdash_M \ldots \vdash_M C_n +\] + +e inoltre $C_n \nvdash_M$; $C_n$ è la configurazione finale di $M$ su $w$. +Altrimenti, se $M \uparrow w$, la computazione non ha mai fine. + +\paragraph{Esempio.} +Si consideri l'alfabeto $A = \{\star, 1\}$ composto dal solo 1 e dal simbolo +bianco $\star$. Definiamo una MdT $M$ che, presa come input una successione di +1 consecutivi, restituisce come output tale successione aumentata di un elemento. +In dettaglio $M$ dispone di due stati interni, lo stato iniziale $q_0$ e uno stato +di "arresto" $q_1$, e la funzione di transizione $\delta$ è composta dalle +istruzioni + +\[ + \left(q_0, 1\right) \rightarrow\left(q_0, 1,+1\right), \quad\left(q_0, \star\right) \rightarrow\left(q_1, 1,+1\right) . +\] + +Secondo le convenzioni stabilite, alla partenza $M$ ha lo stato $q_0$ e la testina +indica il primo simbolo a sinistra dell'input. +Fintanto che la testina trova celle segnate con 1, allora, in virtù della prima +regola di transizione, $M$ scrive 1 sulla cella osservata +(cioè il simbolo letto viene lasciato inalterato) e la testina si sposta a +destra di una cella, mantenendo lo stato $q_0$. +Quando la testina arriva ad una cella vuota, $M$ passa alla seconda regola di +transizione, in virtù della quale la macchina segna con 1 la cella osservata, +sposta la testina a destra (la scelta della direzione di spostamento è in questo +caso ininfluente) e assume lo stato $q_1$, per il quale non è definita nessuna +regola di transizione e, quindi, la macchina si arresta. + +\paragraph{Esempio.} +Consideriamo adesso una MdT che ha lo stesso alfabeto $A = {1, \star}$ +dell'esempio precedente, ancora due stati $q_0, q_1$, ma una sola istruzione +$(q_0, \star) \rightarrow (q_0, \star, +1)$. Ammettiamo che la macchina abbia +come input il nastro bianco, e dunque si trovi a leggere $\star$ nello +stato $q_0$ al momento in cui la computazione si avvia. È facile verificare che +la macchina scivola verso destra continuando a ristampare $\star$ su ogni nuova +cella considerata e a rimanere nello stato $q_0$. Quindi la computazione diverge.\\ + +In conclusione, la macchina di Turing costituisce un soddisfacente modello di +calcolo, e comunque corrisponde al decalogo fissato nel Capitolo 1. Infatti si ha +quanto segue. + +\begin{itemize} + \item La funzione di transizione di una MdT costituisce un insieme finito di + istruzioni. + \item La MdT così descritta è anche l'agente di calcolo che esegue le istruzioni + di cui al punto 1). + \item La MdT può utilizzare il nastro per memorizzare i risultati intermedi. + \item La MdT opera in modo discreto. + \item La MdT opera in modo deterministico, con istruzioni univocamente + specificate. + \item Non esiste nessuna limitazione sulla lunghezza delle stringhe di ingresso, + in quanto si assume che il nastro è illimitato. + \item Il nastro della MdT costituisce, appunto, una memoria di capacità non + limitata. + \item Le operazioni che la MdT può eseguire sono molto semplici, quindi di + complessità finita. + \item Non esiste nessun limite al numero delle istruzioni eseguite durante una + computazione: infatti, le istruzioni sono di numero finito, ma è ammessa la + possibilità di usare più volte la stessa istruzione. + \item Esiste la possibilità di computazioni infinite, come l'esempio precedente + ci mostra. +\end{itemize} diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/la_tesi_di_Church-Turing.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/la_tesi_di_Church-Turing.tex new file mode 100644 index 000000000..3c4930ea6 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/la_tesi_di_Church-Turing.tex @@ -0,0 +1,130 @@ +\section{La Tesi di Church-Turing} + +Come già accennato nel Capitolo 1, la macchina di Turing non è l'unico modello +astratto di computabilità finora comparso. Anzi, durante gli anni '30 e all'inizio +degli anni '40, molte importanti caratterizzazioni della calcolabilità hanno visto la +luce: oltre a quella di Turing, anche quella di Kleene, basata sulle equazioni +funzionali, quella di Church, fondata sul $\lambda$-calcolo, ed altre ancora. In ogni caso, +gli autori hanno elaborato modelli elementari di computazione e hanno formulato +l'ipotesi che la loro nozione di calcolabilità fosse la più generale possibile e che +non potessero esistere procedimenti algoritmici di calcolo non esprimibili nel loro +formalismo. Alcuni esempi di questi modelli alternativi saranno presentati nei +capitoli successivi. D'altra parte, tutti i tentativi fatti nell'ambito della logica +matematica e dell'informatica teorica di definire modelli e paradigmi alternativi +alle MdT hanno condotto a caratterizzazioni di insiemi decidibili, semidecidibili e +di funzioni calcolabili equivalenti a quelle di Turing (esempi di queste equivalenze +verranno dimostrati nei prossimi capitoli). Questa circostanza ha condotto alla +formulazione di quella che oggi è nota come \textit{Tesi di Church-Turing} e viene ancora +ritenuta universalmente valida. Questa tesi afferma che ogni procedimento +algoritmico, espresso in un qualunque modello di calcolo, è realizzabile mediante una +macchina di Turing. In realtà il contributo di Alonzo Church alla formulazione di +questa affermazione può sembrare misterioso, e si potrebbe ritenere più consono +chiamarla semplicemente \textit{Tesi di Turing}. Spiegheremo nel Capitolo 4 il ruolo di +Church. In conclusione si ha: + +\paragraph{Tesi di Church-Turing.} \textit{Una funzione è calcolabile se e solo se + esiste una macchina di Turing che la calcola (e cioè se e solo se la funzione è + calcolabile secondo Turing).}\\ + +Che ogni funzione calcolata da una MdT sia effettivamente calcolabile è banale. Ciò +che è invece rilevante e problematico è l'implicazione inversa, per la quale ogni +procedimento algoritmico è riconducibile a una MdT. "Algoritmo" e "funzione +calcolabile" sono concetti intuitivi, non specificati in modo formale, per cui non è +possibile una dimostrazione rigorosa di equivalenza con il concetto di macchina di +Turing. La Tesi di Church-Turing non è dunque una congettura che, in linea di +principio, potrebbe un giorno diventare un teorema. Tuttavia, la nozione intuitiva di +funzione calcolabile è contraddistinta da un insieme di caratteristiche (quali +determinismo, finitezza di calcolo, etc.), che possono essere considerate in larga +misura "\textit{oggettive}". Questo fa sì che sia praticamente sempre possibile una +valutazione concorde nel decidere se un dato procedimento di calcolo possa essere +considerato algoritmico o meno. Quindi, almeno in linea di principio, è ammissibile +che venga "scoperto" un controesempio alla Tesi di Church-Turing: che si individui +cioè una funzione che sia effettivamente calcolabile secondo questi parametri +informali, ma che non sia computata da nessuna MdT. Almeno finora, però, nessun +controesempio alla tesi di Church-Turing è stato trovato nonostante gli ovvi +progressi teorici e pratici che l'Informatica ha avuto dagli anni '30. In effetti, +gli argomenti a favore della Tesi di Church-Turing possono essere raccolti in tre +gruppi. + +\begin{enumerate} + \item \textit{Evidenza euristica.} + \begin{itemize} + \item Per ogni singola funzione calcolabile che sia stata esaminata, è + sempre stato possibile trovare una MdT in grado di computarla. Lo + stesso si può dire dei procedimenti che producono effettivamente + nuove funzioni a partire da altre. Eppure questa indagine è stata + condotta per un gran numero di funzioni, di classi di funzioni e + di procedure, con l'intento di renderla la più esaustiva + possibile. + \item I metodi per dimostrare che le funzioni computabili sono + calcolabili secondo Turing sono stati sviluppati con un grado di + generalità tale da far ritenere improbabile che possa essere + scoperta una funzione calcolabile cui l'approccio di Turing non + possa essere applicato. + \item I vari metodi tentati per costruire funzioni effettivamente + calcolabili, ma non computabili da MdT, hanno condotto tutti al + fallimento, nel senso che le funzioni ottenute si dimostrano a + loro volta calcolabili secondo Turing, oppure in realtà non + calcolabili. + \end{itemize} + \item \textit{Equivalenza delle diverse formulazioni proposte.} Tutti i tentativi + che sono stati elaborati per caratterizzare in modo rigoroso la classe di + tutte le funzioni effettivamente calcolabili si sono rivelati tra loro + equivalenti. Ciò che è particolarmente rilevante è la diversità degli + strumenti e dei concetti impiegati nelle diverse formulazioni; in molti + casi esse traggono la loro origine da concetti matematici preesistenti. Che + punti di vista talmente diversi e vasti convergano concentricamente alla + stessa conclusione (e siano comunque equivalenti al modello di Turing) può + essere inteso come forte argomento a sostegno di ognuno di loro e in + particolare della tesi di Church-Turing. + \item \textit{L'impiegato diligente.} In realtà, i precedenti ragionamenti si + applicano indifferentemente a tutti i vari approcci equivalenti alla + calcolabilità. Ma c'è un'ulteriore riflessione che serve in particolare a + sostenere l'approccio di 'Turing. In effetti, le caratteristiche che lo + distinguono dagli altri sono la sua naturalezza, la sua minore astrazione, + e anzi il suo dichiarato proposito di simulare meccanicamente il + comportamento di un essere umano che esegue un calcolo (l'impiegato + diligente). In questo senso il modello di Turing si lascia preferire. Del + resto, avremo modo nei prossimi capitoli di presentare altri approcci alla + calcolabilità e di constatare direttamente le loro maggiori complicazioni + teoriche. Anzi, ci furono matematici illustri, come Kurt Gòdel, che, pur + perplessi di fronte all'astrazione di questi metodi alternativi, si + dichiararono tuttavia pienamente convinti e conquistati dalla naturalezza + del modello di Turing. +\end{enumerate} + +Queste argomentazioni hanno indotto la teoria della computabilità a sviluppare la +tendenza di considerare la Tesi di Church-Turing come una sorta di "legge empirica", +piuttosto che come un enunciato a carattere "\textit{logico-formale}". In altre +parole, si è autorizzati a procedere come segue. Se un certo linguaggio ammette un +qualche algoritmo (di qualunque natura) che lo decide o accetta, oppure se una certa +funzione ha un algoritmo che la calcola, allora, sulla base della tesi di +Church-Turing, possiamo assumere che ci sia una macchina di Turing che decide o +accetta quel linguaggio, o calcola quella funzione: non c'è bisogno di descrivere in +dettaglio la MdT, possiamo affidarci all'autorevolezza della tesi e non attardarci in +ulteriori verifiche.\\ +La tesi di Church-Turing permette allora, per +ogni algoritmo che sia intuitivamente tale (anche se espresso in maniera informale), +di dedurre l'esistenza di una MdT che lavora in modo equivalente. L'uso della tesi di +Church-Turing consente di esprimere rapidamente risultati che un approccio più +formale costringerebbe a raggiungere più faticosamente. Per esempio, lavoriamo con +numeri naturali $x, y, z$ e con un alfabeto che li rappresenta, e consideriamo la +funzione così definita: + +\[ + f(x, y, z) = \begin{cases} + 1 & \textrm{se l'}x\textrm{-esima macchina } M_x \textrm{ converge in } z \textrm{ passi sull'input } y, \\ + 0 & \textrm{altrimenti;} \\ + \end{cases} +\] + +sulla base della tesi di Church-Turing, possiamo dire che essa è calcolabile senza +fornire necessariamente una MdT che la computa. È infatti sufficiente fornire un +algoritmo che la calcoli anche ricorrendo a procedure di più alto livello. Per +esempio: si manda in esecuzione $M_x$ sull'input $y$ per $z$ passi di computazione; +a ogni passo si incrementa di 1 un contatore $C$ (che inizialmente viene posto a +0) e si controlla se la macchina di Turing ha terminato la sua esecuzione (cioè +ha raggiunto una configurazione terminale). Se $M_x$ si arresta quando il contatore +non ha ancora raggiunto $z$ allora l'algoritmo dà in output il valore 1. Se invece +il contatore supera $z$ senza che $M_x$ si sia fermata, l'algoritmo termina e +restituisce in output 0. \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/le_macchine_di_turing_a_piu_nastri.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/le_macchine_di_turing_a_piu_nastri.tex new file mode 100644 index 000000000..1922b5aee --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/le_macchine_di_turing_a_piu_nastri.tex @@ -0,0 +1,183 @@ +\section{Macchine di Turing a più nastri} + +La descrizione informale della macchina di Turing data nel paragrafo 2 in termini di +nastro, celle e testina è assai elementare, essenziale e schematica, certamente +passibile di adattamenti, modifiche e migliorie. Per esempio, tra le varianti +ammissibili, possiamo considerare l'eventualità di disporre di più nastri di lavoro. +Ma il meccanismo che ne deriva, anche se apparentemente più duttile e potente della +semplice MdT, mantiene in realtà le medesime capacità computazionali: i linguaggi +decisi o accettati restano esattamente gli stessi, così come le funzioni calcolate. +Vediamo perché.\\ +Consideriamo allora una macchina di Turing M a più nastri (si veda la figura +sottostante) immaginata come composta da: + +\begin{itemize} + \item una unità di controllo a stati finiti, + \item un nastro $N_0$ di input-output di lunghezza infinita con relativa testina, + \item $m$ nastri ausiliari $N_1, \ldots, N_m$ di lunghezza infinita ($m \ge 0$), + ciascuno dotato di propria testina +\end{itemize} + +\begin{figure}[H] + \centering + \includegraphics[width=10cm, keepaspectratio]{capitoli/le_macchine_di_turing/imgs/mdt_piu_nastri.png} + \caption{Schema di una Macchina di Turing a più nastri} +\end{figure} + +Ogni nastro è suddiviso in celle, e ogni cella è in grado di memorizzare un simbolo +di un certo alfabeto $A = {a_0, a_1, \ldots, a_n}$, o il simbolo bianco $*$. Il +nastro di input-output $N_0$ contiene l'input iniziale e l'eventuale output finale di +ogni computazione; ma, durante il lavoro, anche gli altri nastri $N_1, \ldots, N_m$ +possono +essere coinvolti e adoperati. Ogni nastro è scandito dalla sua testina, secondo le +convenzioni usuali per MdT semplici. L'unità di controllo, oltre a contenere il +programma secondo cui la computazione deve essere eseguita, controlla lo stato della +macchina. All'inizio della computazione, l'input è scritto su $N_0$ e la testina ne +indica il simbolo più a sinistra; gli altri nastri sono vuoti e la testina ne esamina +una cella arbitraria; la macchina $M$ è nello stato $q_0$. Ogni successiva mossa di $M$ +è determinata da + +\begin{itemize} + \item il suo stato, + \item i simboli indicati dalle testine sui vari nastri $N_0, N_1, \ldots, N_m$, +\end{itemize} + +e consiste in + +\begin{itemize} + \item aggiornare lo stato, + \item riscrivere i simboli esaminati su ogni nastro, + \item spostare in ogni nastro la testina di un passo verso destra o verso + sinistra. +\end{itemize} + +Come già detto, si conviene che l'eventuale output della computazione sia la stringa +scritta in $N_0$ se e quando $M$ si arresta.\\ +Tutte le definizioni già date per la MdT +semplice possono essere adattate al nuovo modello, ovviamente con le opportune +modifiche. In particolare, le regole di transizione di una macchina $M$ a $m$ nastri +ausiliari sono fatalmente più elaborate, perché devono tenere conto non solo dello +stato di $M$ e del simbolo indicato su $N_0$, ma anche dei simboli considerati sui +nastri ausiliari $N_1, \ldots, N_m$; la transizione sarà caratterizzata, come detto, +dalla scelta di un nuovo stato e dalle istruzioni di scrittura e spostamento per +ciascun nastro, sia di $N_0$ che di $N_1, \ldots, N_m$. Una regola di transizione +sarà allora della forma + +$$ + \delta\left(q, b_0, b_1, \ldots, b_m\right)=\left(q^{\prime}, b^{\prime}_0, x_0, b_1^{\prime}, x_1, \ldots, b_m^{\prime}, x_m\right) +$$ + +dove: + +\begin{itemize} + \item $q, q^{\prime}$ rappresentano gli stati di $M$ rispettivamente prima e dopo + la transizione. + \item per ogni i $\in\{0,1, \ldots, m\}, b_i \in A \cup\{*\}$ è il + simbolo indicato dalla testina sul nastro $N_i, b^{\prime}_i \in A \cup\{*\}$ il simbolo che + lo sostituisce, $x_i \in\{-1,+1\}$ lo spostamento che la testina deve compiere. + +\end{itemize} + +II modello che si ottiene sembra più potente ed espressivo delle semplici MdT. + +\paragraph{Esempio.} Vediamo in particolare come una MdT con un nastro ausiliario +$N_1$ sappia controllare, per ogni parola $w=a_{j_1} \ldots a_{j_k}$ su $A$, se +$w=w^{\text {rev }}$ e cioè se +$$ + a_{j_1} a_{j_2} \ldots a_{j_k}=a_{j_k} a_{j_{k-1}} \ldots a_{j_1}; +$$ +sappia cioè decidere il linguaggio +$$ + \left\{\left(w, w^{r e v}\right) \mid w \in A^*, w=w^{r e v}\right\} . +$$ +La computazione di $M$ su un generico $w$ avviene come segue: $M$ inizia il suo +lavoro muovendo simultaneamente la testina di $N_0$ e quella del nastro ausiliario +$N_1$ verso destra, una cella per volta, finchè la testina di $N_0$ non incontra +$*$, cioè termina di leggere $w$. Durante questo movimento, $M$ +copia su $N_1$ i simboli letti; quindi $M$ scorre all'indietro $N_1$ e individua il +primo simbolo non bianco. Finalmente, $M$ legge simultaneamente il nastro $N_0$ da +destra a sinistra e $N_1$ da sinistra a destra e controlla che i simboli esaminati +coincidano uno a uno. A seconda dell'esito della verifica scrive $SI$ o $NO$ su $N_0$.\\ + +Nonostante le apparenze, le capacità computazionali di una MdT a più nastri sono le +stesse di quelle a un solo nastro, come adesso proviamo. + +\paragraph{Teorema 2.10.1} \textit{Per ogni $MdT \ M = (Q, A, \delta, q_0)$ a $m$ + nastri ausiliari, esiste una $MdT \ M^{\prime} = (Q^{\prime}, A^{\prime}, \delta^{\prime}, + q_0)$ con $A \supseteq A^{\prime}$ tale che:} +\textit{\begin{itemize} + \item per ogni linguaggio $L$ su $A$, $L$ è accettato o deciso da $M$ + se e solo se lo è da $M^{\prime}$ + \item per ogni funzione $f$ su stringhe in $A^{\star}$, $f$ è calcolata + da $M$ se e solo se lo è da $M^{\prime}$ + \end{itemize} +} + +\textit{Dimostrazione}. +Dobbiamo simulare il comportamento di $M$ con una MdT "tradizionale" $M^{\prime}$, +nel senso che, per ogni $w \in A^{\star}$, + +\begin{enumerate} + \item se $M \downarrow w$, allora $M^{\prime} \downarrow w$ e $M, M^{\prime}$ + hanno lo stesso output su $w$; + \item se $M \uparrow w$, allora $M^{\prime} \uparrow w$. +\end{enumerate} + +Suddividiamo allora l'unico nastro di $M^{\prime}$ in $2 m+2$ tracce consecutive +$$ + N_0^{\prime}, N_1^{\prime}, \ldots, N_m^{\prime}, N_0^{\prime \prime}, N_1^{\prime \prime}, \ldots, N_m^{\prime \prime} \text {. } +$$ +Un nuovo simbolo $\Delta$ nell'alfabeto serve a separarle, segnalando inizio e fine +di ognuna; un ulteriore simbolo $\nabla$ delimita a sinistra e a destra la sequenza +delle tracce. Per ogni $i=0,1, \ldots, m$, le tracce $N_i^{\prime}, N_i^{\prime + \prime}$ corrispondono al nastro $N_i$ di $M$, in particolare + +\begin{itemize} + \item $N_i^{\prime}$ ne ricopia il contenuto significativo (cioè non vuoto), + \item $N_i^{\prime \prime}$ provvede a indicare la posizione della testina di + $N_i$. +\end{itemize} + +A quest'ultimo proposito, ammettiamo che $A^{\prime}$ includa due ulteriori simboli +$+,-$ e conveniamo che la cella di $N_i^{\prime \prime}$ corrispondente a quella +indicata dalla testina di $N_i$ contenga $+$, le altre $-$. Per esempio, se +$N_i^{\prime}$ contiene la stringa $a_0 a_1 a_0 a_2$ e la testina indica $a_1, + N_i^{\prime}$ presenta $a_0 a_1 a_0 a_2$ e $N_i^{\prime \prime}-+--$. Naturalmente il +numero delle celle nella traccia $N_i^{\prime}$ è lo stesso che in $N_i^{\prime + \prime}$, ma questo comune valore può variare durante la computazione in ragione dei +movimenti di $M$ su $N$ : i delimitatori $\triangle, \nabla$ possono però spostarsi e +segnalare con chiarezza i confini. All'inizio della computazione su un dato input +$w$, il nastro di $M^{\prime}$ si presenta allora nel seguente modo: + +\begin{itemize} + \item $N_0^{\prime}$ contiene $w, N_0^{\prime \prime}$ ha + nella prima cella, - + nelle altre; + \item per $i=1, \ldots, m, N_i^{\prime}$ è bianca, cioè contiene $\star, + N_i^{\prime \prime}$ ha $+$ nella prima cella e $-$ in tutte le altre. +\end{itemize} + +A questo punto $M^{\prime}$ può iniziare la simulazione delle macchine $M$. Ad ogni +regola di transizione di $M$ +$$ + \delta\left(q, b_0, b_1, \ldots, b_m\right)=\left(q^{\prime}, b_0^{\prime}, x_0, b_1^{\prime}, x_1, . ., b_m^{\prime}, x_m\right) +$$ +$M^{\prime}$ fa corrispondere le istruzioni adeguate a svolgere il seguente lavoro: + +\begin{itemize} + \item $M^{\prime}$ entra nello stato $q^{\prime}$; + \item per ogni $i=1, \ldots, m, M^{\prime}$ sostituisce $b_i$ con $b_i^{\prime}$ + su $N_i^{\prime}$, e registra lo spostamento $x_i$ su $N_i^{\prime \prime}$ con + l'uso appropriato $\mathrm{di}+\mathrm{e}-$. +\end{itemize} + +Quando $M$ converge, $M^{\prime}$ opera una opportuna pulizia del nastro lasciando +solo il contenuto di $N_0^{\prime}$. Ovviamente questa descrizione del comportamento +di $M^{\prime}$ è forzatamente imprecisa. Le operazioni sopra descritte +necessiterebbero di una implementazione in termini di quintuple secondo quanto +richiesto da una MdT tradizionale. Ma, con un minimo di pazienza, il discorso può +essere precisato. In conclusione $M^{\prime}$ simula adeguatamente il comportamento di $M$, e +corrisponde alle richieste dell'enunciato del teorema.\\ + +Viceversa, ogni MdT tradizionale può essere facilmente intesa come MdT a più nastri +(che in realtà non ha bisogno di ricorrere ai nastri ausiliari). Dunque i due +modelli, con o senza nastri ausiliari, si rivelano equivalenti. \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/macchine_che_calcolano.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/macchine_che_calcolano.tex new file mode 100644 index 000000000..02cfa474d --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/macchine_che_calcolano.tex @@ -0,0 +1,34 @@ +\section{Macchine che calcolano} + +Un processo di calcolo è finalizzato ad elaborare informazioni. +Può essere semplice quanto una stima della durata di un percorso tra due città, +e complicato quanto ana previsione metereologica. +Lo studio della calcolabilità si prefigge l'obiettivo +di fornire l'intuizione degli elementi e delle proprietà salienti che +caratterizzano il processo. +Tale intuizione può essere usata per predire la complessità della computazione, +per scegliere in modo consapevole un tipo di calcolo piuttosto che un +altro, e per sviluppare strumenti che facilitino il progetto del processo stesso. +Lo studio della computabilità rivela addirittura che ci sono problemi che non +possono avere risposta; inoltre, ci mostra che tra i problemi che invece possono +essere risolti, ce ne sono alcuni che richiedono risorse così ingenti +(ad esempio, un tempo di calcolo dell'ordine del milione di anni) da scoraggiare +ogni tentativo di soluzione pratica. Lo studio della computabilità riesce a +identificare queste situazioni; permette così di determinare con opportuni +strumenti i casi "positivi" in cui la soluzione si ottiene, magari anche a +costi accessibili. +In questa prima parte degli appunti ci concentreremo in realtà solo sul primo aspetto, +ci dedicheremo cioè a distinguere quali problemi si possono risolvere, e quali no. +Presenteremo quattro modelli astratti di calcolo che permettono questa +identificazione: nell'ordine, macchine di Turing, funzioni ricorsive, +grammatiche, prop-ammi. Non faremo invece alcun alcun riferimento al tema +della complessità computazionale, non ci interesseremo dunque dei costi dei +problemi che hanno soluzione: questo aspetto sarà ampiamente trattato nella +seconda parte degli appunti. +In particolare, in questo capitolo verranno inizialmente introdotti le nozioni di +stringa e di linguaggio, e il ruolo che essi hanno nel rappresentare l'informazione. +Verrà poi presentato il formalismo delle Macchine di Turing: dapprima sarà +definita la versione più semplice, si passerà poi a varianti più complesse, +utili per approfondire aspetti particolari del concetto di calcolo. +Verranno poi presentate le nozioni di calcolabilità e di decidibilità +indotte dal modello della macchina di Turing. \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/macchine_di_turing_e_funzioni.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/macchine_di_turing_e_funzioni.tex new file mode 100644 index 000000000..1d806b5d0 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/macchine_di_turing_e_funzioni.tex @@ -0,0 +1,90 @@ +\section{Macchine di Turing e Funzioni} + +In questo paragrafo discutiamo come le Macchine di Turing possano calcolare le +funzioni sulle stringhe di un certo alfabeto $A$. + +\paragraph{Definizione.} +Sia $f$ una funzione con dominio e immagine in $A*$. Si dice che una +MdT $M = (Q, A, \delta, q_0)$ \textit{calcola o computa}$f$ se e solo se, $\forall w \in A*$, + +\begin{enumerate} + \item se $w$ è nel dominio di $f$, allora $M \downarrow w$ con output $f(w)$; + \item se invece $f(w)$ non è definita, allora $M \uparrow w$. +\end{enumerate} + +\paragraph{Definizione.} +La funzione $f$ è detta \textit{calcolabile secondo Turing} o +\textit{computabile secondo Turing} se esiste una macchina di Turing $M$ che la +calcola; \textit{non calcolabile}, +o \textit{non computabile secondo Turing} altrimenti.\\ + +Le precedenti definizioni si estendono facilmente al caso in cui il dominio o +l'immagine di $f$ si compongono di coppie, o terne, o $n$-uple di parole invece che +direttamente di stringhe. Basterà convenire di rappresentare una coppia $(w_1, w_2)$ +di parole su $A$ come una stringa $w_1* w_2$ in cui $w_2$ succede a $w_1$, separata +da un simbolo bianco, e procedere analogamente per terne, o sequenze più complicate. +Si noti poi che tra le funzioni computabili secondo Turing sono ammessi anche +esempi parziali, definiti solo su porzioni di $A*$, e non sulla sua totalità. +Questa scelta non deve sorprendere né scandalizzare. Si osservi che molte operazioni +comuni ed elementari, come la divisione tra i naturali, non sempre si possono +eseguire; per esempio non c'è verso di calcolare 5 : 2. Nel caso specifico, si può +cercare di rimediare ammettendo un eventuale resto minore del divisore. Così, per +5 : 2, si ottiene quoziente approssimato 2 e resto 1 + +\[ + 5 = 2 \cdot 2 + 1 +\] + +Pur tuttavia, certe divisioni, quelle con divisore O come 5 : 0, restano ancora +impossibili. La divisione è, quindi, una funzione solo parziale. + +\paragraph{Esempio.} +Presentiamo una MdT $M$ che computa la funzione totale di addizione tra i naturali. +Come già in precedenza, lavoriamo sull'alfabeto $A = \{1\}$. Assumiamo che $M$ +abbia quattro stati $q_0, q_1, q_2, q_3$ e le istruzioni + +$$ + \begin{gathered} + \left(q_0, \star\right) \rightarrow\left(q_1, 1,+1\right),\left(q_0, 1\right) \rightarrow\left(q_0, 1,+1\right),\left(q_1, \star\right) \rightarrow\left(q_2, \star,-1\right), \\ + \left(q_1, 1\right) \rightarrow\left(q_1, 1,+1\right),\left(q_2, 1\right) \rightarrow\left(q_3, \star,-1\right),\left(q_3, 1\right) \rightarrow\left(q_3, \star, 1\right) . + \end{gathered} +$$ + +Mostriamo come, per esempio, $M$ verifichi che $2+3$ fa 5, cioè produca l'output +111111 quando il suo input è la coppia $(2,3)$, cioè $111 \star 1111$. +Infatti le istruzioni relative a $q_0$ fanno ricopiare a $M$ la prima sequenza di +1 senza cambiare stato + +$$ + \left(\lambda, q_0, 1,11 \star 1111\right) \vdash_M^*\left(111, q_0, \star, 1111\right), +$$ + +poi le fanno aggiungere un ulteriore 1 e passare ad esaminare la seconda sequenza +di 1 nello stato $q_1$ + +$$ + \left(111, q_0, \star, 1111\right) \vdash_M\left(1111, q_1, 1,111\right) . +$$ + +L'istruzione su $\left(q_1, 1\right)$ ha ancora l'effetto di riprodurre inalterata +questa seconda sequenza + +$$ + \left(1111, q_1, 1,111\right) \vdash_M^{\star}\left(11111111, q_1, \star, \lambda\right) ; +$$ + +a questo punto $M$ cancella gli ultimi due 1, passa allo stato $q_3$ e si ferma +producendo l'output desiderato 111111 + +$$ + \begin{aligned} + & \left(11111111, q_1, \star, \lambda\right) \vdash_M\left(1111111, q_2, 1, \lambda\right) \vdash_M \\ + & \vdash_M\left(111111, q_3, 1, \lambda\right) \vdash_M\left(111111 \star, q_3, \star, \lambda\right) . + \end{aligned} +$$ + +Finalmente notiamo che ogni MdT $M$ con alfabeto $A$ computa una funzione, +eventualmente parziale, da $A^*$ a $(A \cup\{*\})^*$, e più in generale +dall'insieme delle sequenze finite di stringhe di $A^*$ e $\star$ all'insieme +stesso: la funzione associa ad ogni stringa (o sequenza di stringhe) l'output della +eventuale computazione convergente di $M$ su di essa. \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/macchine_di_turing_e_linguaggi.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/macchine_di_turing_e_linguaggi.tex new file mode 100644 index 000000000..dd6f057b9 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/macchine_di_turing_e_linguaggi.tex @@ -0,0 +1,113 @@ +\section{Macchine di Turing e Linguaggi} + +Vediamo adesso come una MdT $M$ gestisce la questione di identificare un linguaggio +$L$ in un alfabeto $A$. Ovviamente $M$ avrà lo stesso alfabeto $A$ di $L$, e quindi +sarà $M = (Q, A, \delta, q_0)$ per opportuni $Q$ e $\delta$. Possiamo immaginare per +$M$ due possibili strategie per distinguere gli elementi di $L$. + +\begin{enumerate} + \item $M$ fissa preventivamente, a prescindere da $L$, due stringhe di output + tra loro distinte, da intendersi una volta per tutte come "$SI$" e "$NO$". + Si chiede poi a $M$, per ogni input $w \in A^*$, di: + \begin{itemize} + \item convergere su $SI$ se $w \in L$, + \item convergere su $NO$ se $w \notin L$. + \end{itemize} + Si dice allora che $M$ \textit{decide} $L$. + \item Alternativamente si ammette che, per ogni $w \in A^*$, $M$ converge su + $w$ se e solo se $w \in L$; dunque + \begin{itemize} + \item $M \downarrow w \ se \ w \in L$, + \item $M \uparrow w \ se \ w \notin L$. + \end{itemize} + Si dice allora che $M$ \textit{accetta} $L$. +\end{enumerate} + +Notiamo che le due strategie non sono tra loro equivalenti e che in realtà solo la +prima è adeguata a distinguere effettivamente gli elementi di $L$ da quelli fuori di +$L$. Infatti, se $M$ si limita ad accettare $L$, $M$ sa riconoscere gli elementi +di $L$, perché converge su di essi; ma non sa escludere gli elementi fuori di $L$, +per i quali segue l'evoluzione della corrispondente computazione, prende atto che +essa non si conclude né dopo 10, né dopo 100, né dopo $10^n$ passi, ma non può su +questa base prevedere che essa prosegua indefinitamente (come in realtà accade), o +non si arresti proprio al passo $10^n + 1$, o poco dopo. + +Quando $M$ accetta un linguaggio $L$ e dunque $L$ si compone delle parole +$w \in A^*$ per cui $M \downarrow w$, diremo comunque che (almeno) $L$ è +riconosciuto da $M$.\\ + +Diciamo poi: + +\paragraph{Definizione.} +Un linguaggio $L$ è \textit{decidibile} secondo Turing +(o, più semplicemente, \textit{decidibile}) se esiste una macchina di Turing $M$ che +decide $L$, \textit{indecidibile} (secondo Turing) altrimenti. + +\paragraph{Definizione.} +Un linguaggio $L$ è detto \textit{semidecidibile} secondo Turing +(o, più semplicemente, \textit{semidecidibile}) se esiste una macchina di Turing +$M$ che accetta $L$.\\ + +Nei prossimi capitoli studieremo formalmente le relazioni tra decidibilità e +semidecidibilita. Non è difficile convincersi, comunque, che se un linguaggio è +decidibile allora è anche semidecidibile. È facile, infatti, trasformare una MdT +$M$ che risponde "$SI$" alle stringhe che appartengono al linguaggio e +"$NO$" alle stringhe che non appartengono al linguaggio in una macchina di Turing +$M$ che converge quando $M$ dichiara "$SI$" e diverge quando $M$ dice "$NO$". +Nel seguito saranno proposti molti esempi di linguaggi decidibili e semidecidibili. +Per il momento ci accontentiamo di un caso molto semplice. + +\paragraph{Esempio.} +Sia $A = \{1\}$. Sappiamo che i numeri naturali $0,1,2,3,4, \ldots$ si possono +rappresentare, in verità in modo assai rozzo, come parole su $A 1,11,111, 1111,$ e +cosi via: dunque ogni naturale $N$ diventa una stringa di 1 di lunghezza $N+1$. +Sia $L$ l'insieme dei pari. Vogliamo provare che $L$ e decidibile e quindi +costruire una MdT $M$ su $\{1\}$ che lo decide. Identifichiamo anzitutto le risposte +$SI$ e $NO$ rispettivamente con i numeri 1 e 0, e dunque con le codifiche 11 e 1. +Informalmente $M$ conta la parità di un dato input $N$ e risponde 1 o 11 di +conseguenza. Per ottenere questo obiettivo ci servono quattro stati +$q_0, q_1, q_2, q_3$ e una funzione di transizione $\delta$ con le seguenti istruzioni + +\begin{alignLetter} + & \left(q_0, \star\right) \rightarrow\left(q_3, 1,+1\right),\left(q_1, \star\right) \rightarrow\left(q_2, 1,+1\right), \\ + & \left(q_0, 1\right) \rightarrow\left(q_1, \star,+1\right),\left(q_1, 1\right) \rightarrow\left(q_0, \star,+1\right), \\ + & \left(q_2, \star\right) \rightarrow\left(q_3, 1,+1\right). & +\end{alignLetter} + +Vediamo allora come $M$ verifica che 4, cioè 11111, è pari. Anzitutto $M$ usa le +istruzioni in (b) per cancellare ogni 1 e giungere finalmente a $\star$ nello stato +$q_1$, secondo la computazione che adesso mostriamo: + +$$ + \begin{aligned} + & \left(\lambda, q_0, 1,1111\right) \vdash_M\left(\lambda, q_1, 1,111\right) \vdash_M\left(\lambda, q_0, 1,11\right) \vdash_M\left(\lambda, q_1, 1,1\right) \vdash_M \\ + & \vdash_M\left(\lambda, q_0, 1, \lambda\right) \vdash_M\left(\lambda, q_1, \star, \lambda\right) ; + \end{aligned} +$$ + +a questo punto (a), (c) intervengono e implicano + +$$ + \left(\lambda, q_1, \star, \lambda\right) \vdash_M\left(1, q_2, \star, \lambda\right) \vdash_M\left(11, q_3, \star, \lambda\right), +$$ + +dopo di che, in assenza di istruzioni su $q_3, M$ si arresta con l'output atteso 11, +cioè $SI$.\\ + +Consideriamo ora la computazione di $M$ sull'input 3, cioè 1111. Stavolta (b) +implica + +$$ + \begin{aligned} + & \left(\lambda, q_0, 1,111\right) \vdash_M\left(\lambda, q_1, 1,11\right) \vdash_M\left(\lambda, q_0, 1,1\right) \vdash_M\left(\lambda, q_1, 1,\lambda\right) \\ + & \vdash_M\left(\lambda, q_0, \star, \lambda\right) + \end{aligned} +$$ + +cui (a) aggiunge + +\[ + (\lambda, q_0, \star, \lambda) \vdash_M (1, q_3, \star, \lambda) +\] + +dopo di che si arresta con l'output 1, cioè $NO$. \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/macchine_di_turing_non_deterministiche.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/macchine_di_turing_non_deterministiche.tex new file mode 100644 index 000000000..320f803f0 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/macchine_di_turing_non_deterministiche.tex @@ -0,0 +1,81 @@ + +\section{Macchine di Turing non deterministiche} + +In questa sezione mostreremo un'altra possibile estensione +delle MdT, quella delle così dette macchine di Turing "\textit{non deterministiche}"; ne +discuteremo brevemente utilità e motivazione, ma dimostreremo che anche questa +generalizzazione equivale in definitiva al modello delle macchine di Turing +tradizionali. In una comune $\operatorname{MdT} M=\left(Q, A, \delta, q_0\right)$, +per ogni stato $q \in Q$ e per ogni simbolo $a \in A \cup\{\star\}$, c'è al più +un'istruzione da eseguire a proposito di $(q, a)$. In altre parole, $\delta$ è una +"funzione": +\begin{itemize} + \item associa a $(q, a)$ un'unica terna $\left(q^{\prime}, a^{\prime}, + x\right)$ con $q^{\prime} \in Q, a^{\prime} \in A \cup\{\star\}, x=\pm 1$, + \item oppure esclude $(q, a)$ dal suo dominio (nel qual caso $M$ si ferma non appena incontra $(q, + a))$. +\end{itemize} + +Del resto, queste convenzioni sono stabilite per simulare in modo adeguato il +comportamento tipico di un impiegato diligente che, se non ha istruzioni, si ferma; +se ne ha una sola, la esegue; se ne ha più d'una, resta nel dubbio e non si prende +responsabilità. Ma a un impiegato diligente e fortunato si può anche concedere la +facoltà di scegliere, confidando che la buona sorte gli ispiri l'opzione migliore. +Corrispondentemente a una MdT non deterministica si concederà, per certe - o per +tutte - le coppie $(q, a)$, la possibilità di scegliere tra più possibili terne +$\left(q, a^{\prime}, x\right)$, tra loro concorrenziali. In altre parole, si +ritirerà a $\delta$ la qualifica di funzione da coppie in $Q \times(A \cup\{\star\})$ +a terne in $Q \times((A \cup\{\star\}) \times\{-1,+1\}$, e la si ridurrà al rango di +una semplice relazione tra coppie e terne, quindi a un insieme di 5 -uple in +$$ + Q \times(A \cup\{\star\}) \times Q \times((A \cup\{\star\}) \times\{-1,+1\} . +$$ +Si porrà in conclusione + +\paragraph{Definizione.} Una macchina di Turing \textit{non deterministica} $M$ è una 4 -upla +$(Q, A, \delta, q_0)$ come nella definizione delle MdT tradizionali, +dove però $\delta$ è una relazione in + +$$ + Q \times(A \cup\{\star\}) \times Q \times((A \cup\{\star\}) \times\{-1,+1\} . +$$ + +In effetti le MdT tradizionali si chiamano talora "\textit{deterministiche}", a sottolineare +l'univocità delle loro istruzioni. Va però osservato che le MdT deterministiche +rientrano tra quelle non deterministiche: hanno maggiore rigidità e meno libertà +rispetto alle altre - al più una istruzione da eseguire per una data coppia $(q, + a)-$, ma non ne contraddicono la definizione. In ragione della molteplicità di +istruzioni, una MdT non deterministica $M$ può svolgere più possibili computazioni e +produrre diversi possibili output per lo stesso input $w$. Diremo che $M$ converge su +$w$ se almeno una di queste computazioni ha fine, e dedurremo che $M$ diverge su $w$ +se tutte queste computazioni divergono. + +\paragraph{Esempio.} Sia $M$ la MdT non deterministica +che ha due stati $q_0, q_1$, l'alfabeto $\{1\}$ e due sole istruzioni +$$ + \left(q_0, \star\right) \rightarrow\left(q_1, 1,+1\right), \quad\left(q_0, \star\right) \rightarrow\left(q_0, \star,+1\right), +$$ +tutte relative a $\left(q_0, \star\right)$. Ammettiamo che $M$ inizi la computazione +dal nastro bianco e quindi si trovi a considerare al primo passo proprio la coppia +$(q, \star)$. Se $M$ esegue la prima istruzione, $M$ entra nello stato $q_1$ e subito +dopo si arresta. Se invece $M$ sceglie la seconda istruzione, $M$ ricopia $\star$, va +a destra e resta nello stato $q$, cioè si ritrova nella situazione di partenza, una +cella più a destra. Se $M$ continua a eseguire indefinitamente la seconda istruzione +su $(q_0, \star), M$ diverge. Comunque $M$ converge sul nastro bianco +perché almeno una delle sue computazioni sul nastro bianco ha fine.\\ + +È evidente che questa capacità di computazioni plurime dà a una MdT non +deterministica $M$ maggiori potenzialità, almeno apparenti: dove una MdT +deterministica ha un'unica via da seguire, $M$ ha più alternative e quindi la +possibilità di concludere più rapidamente scegliendo la strada migliore. Così, $M$ +accetta un linguaggio $L$ se e solo se gli elementi di $L$ coincidono con gli input +di $M$ su cui almeno una computazione di $M$ converge. Tuttavia, alla resa dei conti, +questi presunti vantaggi non aumentano realmente il potere computazionale delle +macchine, nel senso del seguente + +\paragraph{Teorema 2.11.1} \textit{Per ogni MdT non deterministica $M$, c'è una MdT deterministica + $M^{\prime}$ che accetta lo stesso insieme di $L$.}\\ + +\textit{Dimostrazione}. (Ci limitiamo a cenni informali). Per ogni input $w, M^{\prime}$ segue +contemporaneamente tutte le computazioni di $M$ su $w$, e si arresta non appena una +di queste si arresta; continua a osservare il comportamento di $M$ altrimenti. \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/main.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/main.tex new file mode 100644 index 000000000..471e770c3 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/main.tex @@ -0,0 +1,13 @@ +\chapter{Le Macchine di Turing} + +\input{capitoli/le_macchine_di_turing/macchine_che_calcolano.tex} +\input{capitoli/le_macchine_di_turing/alfabeti_stringhe_linguaggi.tex} +\input{capitoli/le_macchine_di_turing/la_macchina_di_turing.tex} +\input{capitoli/le_macchine_di_turing/macchine_di_turing_e_linguaggi.tex} +\input{capitoli/le_macchine_di_turing/macchine_di_turing_e_funzioni.tex} +\input{capitoli/le_macchine_di_turing/codifiche_di_stringhe.tex} +\input{capitoli/le_macchine_di_turing/numeri_e_coppie.tex} +\input{capitoli/le_macchine_di_turing/numeri_e_macchine.tex} +\input{capitoli/le_macchine_di_turing/la_tesi_di_Church-Turing.tex} +\input{capitoli/le_macchine_di_turing/le_macchine_di_turing_a_piu_nastri.tex} +\input{capitoli/le_macchine_di_turing/macchine_di_turing_non_deterministiche.tex} \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/numeri_e_coppie.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/numeri_e_coppie.tex new file mode 100644 index 000000000..20bc9e83a --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/numeri_e_coppie.tex @@ -0,0 +1,78 @@ +\section{Numeri e coppie} + +Visto che stiamo trattando coppie, o terne, o $n$-uple di elementi, varrà la pena +di citare un'osservazione importante sulle coppie di numeri naturali, che ci sarà +presto utile nel seguito. Si tratta di un risultato dimostrato dal matematico +Georg Cantor nella seconda metà dell'Ottocento. + +\paragraph{Teorema 2.7.1} +\textit{C'è una corrispondenza biunivoca $r$ tra ${\mathbb{N}}^2$ e $\mathbb{N}$: + specificamente, per ogni scelta di $n,m$ naturali,} + +\[ + r(n,m) = \frac{(n+m)(n+m+1)}{2} + n. +\] + +L'affermazione è per certi versi sorprendente: si può infatti osservare che ogni +naturale $n$ compare infinite volte come ascissa di una coppia $(n, m) \in + \mathbb{N}^2$, al variare di $m$. Così $\mathbb{N}^2$ "sembra" infinitamente più grande +di $\mathbb{N}$. Eppure è in corrispondenza biunivoca con $N$ tramite $r$ e quindi, +in questo senso, ci sono tante coppie ordinate di naturali quanti naturali. Al di là +della complessità della formula che definisce $r$, cerchiamo di capire l'idea che +Cantor seguì per ottenerla. Supponiamo allora di disporre le coppie ordinate di +numeri naturali in una tabella (infinita): + +$$ + \begin{array}{cccccc} + (0,0) & (0,1) & + (0,2) & \ldots & (0, n) & \ldots \\ (1,0) & (1,1) & (1,2) & \ldots & (1, n) & \ldots + \\ (2,0) & (2,1) & (2,2) & \ldots & (2, n) & \ldots \\ \vdots & \vdots & \vdots & + \vdots & \vdots & \vdots \\ (n, 0) & (n, 1) & (n, 2) & \ldots & (n, n) & \ldots \\ + \vdots & \vdots & \vdots & \vdots & \vdots & \vdots + \end{array} +$$ +Le righe +corrispondono alle ascisse, le colonne alle ordinate. Per enumerare le coppia di +numeri naturali si percorra la tabella sulle diagonali come indicato nella figura che +segue: + +$$ + \begin{array}{cccccc} + \swarrow & \swarrow & \swarrow & \swarrow & \ldots & \ldots \\ + \swarrow & \swarrow & \swarrow & \ldots & \ldots & \ldots \\ + \swarrow & \swarrow & \ldots & \ldots & \ldots & \ldots \\ + \swarrow & \ldots & \ldots & \ldots & \ldots & \ldots \\ + \vdots & \vdots & \vdots & \vdots & \vdots & \vdots + \end{array} +$$ + +La prima diagonale contiene solo $(O, O)$, la seconda $(0, 1)$ e $(1, 0), ...$, +la $k$-esima contiene $(0, k - 1), (1, k - 2), ..., (k - 2, 1)$ e $(k - 1, 0)$ e +così via. La generica diagonale $k$ contiene $k$ coppie, precisamente quelle in +cui la somma delle coordinate è $k - 1$. In questo modo, le coppie $(n, m)$ di +$\mathbb{N}^2$ risultano enumerate come segue: + +$$ + (0, 0), (O, 1), (1, 0), (0, 2), (1, 1), (2, O), (O, 3), (1, 2), (2, 1), (3, 0), \ldots +$$ + +e così via, dunque \textit{prima} secondo $m + n$ e poi secondo $n$. +Non è difficile controllare che la funzione $r$ associa alle coppie sopra elencate +nell'ordine + +$$ + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, \ldots +$$ + +cioè proprio la sequenza dei naturali. In generale $r$ associa ad ogni coppia $(n, m)$ +il numero di passi necessari per raggiungerla meno 1. Dalla costruzione segue allora +che la funzione $r$ è una biezione: ogni coppia $(n, m)$ compare una sola volta +nella tabella e quindi è univocamente determinato il numero di passi necessario +per raggiungerla lungo le varie diagonali. Inoltre $r$ è data effettivamente e +ammette, come ogni biiezione, la sua funzione inversa: una corrispondenza biunivoca +da $\mathbb{N}$ a $\mathbb{N}^2$, ancora effettiva. Sono quindi anche note le +proiezioni di tale inversa su $\mathbb{N}$ cioè le due funzioni (sempre effettive) +$\pi_1 : \mathbb{N} \rightarrow \mathbb{N}$ e $\pi_2 : \mathbb{N} \rightarrow \mathbb{N}$\ +tali che, per ogni $t$ naturale, $\pi_1(t)$, $\pi_2(t)$ sono rispettivamente quei +naturali $n, m$ per cui $r(n, m) = t$. A proposito, un insieme che - come $\mathbb{N}^2$ - +è in corrispondenza biunivoca con $\mathbb{N}$ si dice \textit{numerabile}. \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/numeri_e_macchine.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/numeri_e_macchine.tex new file mode 100644 index 000000000..101370797 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/capitoli/le_macchine_di_turing/numeri_e_macchine.tex @@ -0,0 +1,156 @@ +\section{Numeri e Macchine} + +Adesso mostriamo che, per ogni alfabeto $A$, anche le Macchine di Turing che +corrispondono ad $A$ formano un insieme che è numerabile, e cioè è in corrispondenza +biunivoca con $\mathbb{N}$. Anzi, è possibile dare un esempio esplicito di tale biiezione. +Vediamo come. Precisiamo anzitutto il contesto. Se $A$ è fissato, una MdT $M$ su $A$ +è determinata da + +\begin{itemize} + \item l'insieme $Q$ dei suoi stati, + \item la funzione di transizione $\delta$, con le + sue istruzioni +\end{itemize} + +Possiamo convenire per semplicità di disporre a priori di un serbatoio infinito +(numerabile) di stati + +\[ + q_0, q_1, \ldots, q_n, \ldots +\] + +da cui ogni $M$ estrae quegli $n+1$ + +\[ + q_0, q_1, \ldots, q_n, \ldots +\] + +che le sono necessari per formare $Q$. Notiamo che il numero degli stati di $M$ è +sempre finito, ma può essere arbitrariamente grande; quindi non possiamo porre +limiti al serbatoio cui $M$ attinge e dobbiamo ammetterlo infinito. $M$ risulta allora +determinata da + +\begin{itemize} + \item il numero $n + 1$ dei suoi stati, + \item la sua funzione di transizione. +\end{itemize} + +Possiamo ora provare: + +\paragraph{Teorema 2.8.1} \textit{C'è una corrispondenza biunivoca effettiva tra le MdT su un + alfabeto $A$ e i numeri naturali.}\\ + +\textit{Dimostrazione}. Poniamo anzitutto $A=\left\{a_1, \ldots, a_N\right\}$ con +$a_1 \neq \cdots \neq a_N$. Procediamo in cinque passi consecutivi, in modo per certi +versi analogo a quelloseguito per numerare simboli, stringhe e sequenze di stringhe +su un alfabeto. Per la precisione numeriamo successivamente + +\begin{enumerate} + \item i simboli che compaiono nelle istruzioni delle $\operatorname{MdT}$ su $A$, + \item le istruzioni stesse, + \item le funzioni di transizione, + \item le MdT su $A$ e. finalmente, + \item costruiamo la biiezione richiesta tra MdT e numeri. +\end{enumerate} +Ecco i dettagli dei vari passi. +\begin{enumerate} + \item Ricordiamo che i simboli che compaiono nelle istruzioni di una MdT su $A$ + sono + \begin{itemize} + \item gli elementi $a_1, \ldots, a_N$ di $A$ e il simbolo bianco $*$; + \item stati tra $q_0, q_1, \ldots q_n, \ldots$ + \item indici di spostamento $\pm 1$. + \end{itemize} + Li numeriamo con + una funzione $\sharp_0$ che opera come segue: + $$ + \begin{array}{cccccccccccc}-1 & +1 & + \star & a_1 & a_2 & \cdots & a_N & q_0 & q_1 & \cdots & q_N & \cdots \\ + \downarrow & \downarrow & \downarrow & \downarrow & \downarrow & \cdots & + \downarrow & \downarrow & \downarrow & \cdots & \downarrow & \cdots \\ 3 & 5 & 7 + & 9 & 11 & \cdots & 2 N+7 & 2 N+9 & 2 N+11 & \cdots & 2 N+2 n+2 & + \cdots\end{array} + $$ + Così i valori di $\sharp_0$ sono tutti dispari $\ge 3$; $\sharp_0$ è + iniettiva ed effettiva. + \item Passiamo adesso alle istruzioni. Ciascuna di esse è una 5-upla + $\Omega=(q, a, q', a', x)$ dove $q, q^{\prime}$ + sono tra $q_0, q_1, \ldots q_n, \ldots$, $a, a^{\prime}$ appartengono ad + $A \cup\{\star\}$, $x=\pm 1$. Definiamo una funzione $\sharp_1$ che + associa ad ogni $\Omega$ il numero naturale $\sharp_1(\Omega)$ in cui i + codici dei + cinque simboli componenti di $\Omega$ compaiono in ordine come esponenti + dei primi $2,3,5,7,11$ + $$ + \sharp_1(\Omega)=2^{\sharp_0(q)} 3^{\sharp_0(a)} 5^{\sharp_0\left(q^{\prime}\right)} 7^{\sharp_0\left(a^{\prime}\right)} 11^{\sharp_0(x)} . + $$ + Si noti che i codici assegnati da $\sharp_1$ sono numeri pari che hanno gli + esponenti dispati o nulli nella loro decomposizione in fattori primi: + dunque, non si confondono con quelli di $\sharp_0$, che sono dispari. Anche + $\sharp_1$ è una funzione iniettiva, come conseguenza del teorema + fondamentale dell'aritmetica e dell'iniettività di $\sharp_0$; $\sharp_1$ è anche + effettiva. + \item A questo punto siamo in grado di associare un numero naturale anche ad ogni + funzione di transizione $\delta$. Supponiamo che $\delta$ si componga delle + quintuple $\Omega_1, \Omega_2, \ldots, \Omega_k$. Ordiniamo le componenti + delle 5-uple convenendo, per esempio, + \begin{itemize} + \item $q_0k(f)$, $\Sigma(k)>f(k)$.} + +\begin{proof} + Rappresentiamo per semplicità i naturali $n$ + sull'alfabeto $\{1\}$, come stringhe di 1: quindi $0,1,2,3, \ldots$ diventano + rispettivamente $1,11,111,1111$, e così via. In genere ogni $n$ viene espresso da una + stringa di $n+1$ caratteri uguali a 1. Osserviamo poi che, se $f$ è calcolabile, + anche la funzione $g$ che ad ogni naturale $n$ associa il valore massimo tra $f(2 + n+1)$ e $f(2 n+2)$ è chiaramente calcolabile. C'è dunque una MdT $M(g)$ su $\{1\}$ + che la computa. Supponiamo che $M(g)$ ammetta $n(g)$ stati. Consideriamo adesso un + qualunque numero naturale $n$. Possiamo costruire una MdT $M_n$ che, a partire + dall'input bianco, prima vi stampa $n$ e poi simula $M(g)$, computando quindi in + conclusione $g(n)$. Le istruzioni per $M_n$ sono relativamente semplici da + organizzare. Anzitutto dobbiamo consentirle di scrivere $n$, dunque $n+1$ cifre + consecutive tutte uguali a 1 (dopo di che la macchina deve tornare al simbolo 1 più a + sinistra per poter simulare $M(g)$). Dobbiamo conseguentemente prevedere per $M_n$ + $n+1$ stati $q_0, \ldots, q_n$ in aggiunta a quelli di $M(g)$ e, per quanto riguarda + la sua funzione di transizione $\delta_n$, l'istruzione $\delta_n\left(q_i, + \star\right)=\left(q_{i+1}, 1,-1\right)$ per ogni $ik(f)$, + distinguiamo i due casi in cui $k$ è dispari oppure pari (dunque $k=2 n+1$ oppure + $k=2 n+2$ con $n \geq n(g)$ ) per concludere comunque $\Sigma(k)>f(k)$. +\end{proof} diff --git a/magistrale/Anno 1/Carpi/appunti libro/latext/main.tex b/magistrale/Anno 1/Carpi/appunti libro/latext/main.tex new file mode 100644 index 000000000..bb663bd05 --- /dev/null +++ b/magistrale/Anno 1/Carpi/appunti libro/latext/main.tex @@ -0,0 +1,39 @@ +\documentclass[a4paper]{book} + +\usepackage{enumitem} +\usepackage{hyperref} +\usepackage{amsfonts} +\usepackage{mathtools} +\usepackage{amssymb} +\usepackage{float} +\usepackage{amsthm} +\usepackage{mathdots} +\usepackage{tikz} + +\setlength{\parindent}{0pt} +\begin{document} + +\tableofcontents + +\newenvironment{alignLetter}{ + \setcounter{equation}{0} + \renewcommand\theequation{\alph{equation}} + \flalign +}{ + \endalign +} + +%% cambio nome al comando proof +\renewcommand*{\proofname}{Dimostrazione} + +%%TODO: aggiuntere una prima pagina fatta bene !! +%%TODO: sostituire le dimostrazioni con il comando apposta proof !! + +\include{capitoli/introduzione/main.tex} +\include{capitoli/le_macchine_di_turing/main.tex} +\include{capitoli/problemi_senza_soluzione/main.tex} +\include{capitoli/funzioni_ricorsive/main.tex} +\include{capitoli/complessita/main.tex} +\include{capitoli/classi_di_complessita_temporale/main.tex} + +\end{document} \ No newline at end of file diff --git a/magistrale/Anno 1/Carpi/Computability_and_Complexity_OFFICIAL.pdf b/magistrale/Anno 1/Carpi/appunti slide/Computability_and_Complexity_OFFICIAL.pdf similarity index 100% rename from magistrale/Anno 1/Carpi/Computability_and_Complexity_OFFICIAL.pdf rename to magistrale/Anno 1/Carpi/appunti slide/Computability_and_Complexity_OFFICIAL.pdf diff --git a/magistrale/Anno 1/Carpi/latex/Introduzione.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/Introduzione.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/Introduzione.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/Introduzione.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo10.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo10.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo10.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo10.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo11.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo11.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo11.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo11.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo12.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo12.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo12.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo12.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo13.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo13.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo13.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo13.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo14.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo14.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo14.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo14.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo15.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo15.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo15.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo15.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo16.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo16.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo16.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo16.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo17.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo17.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo17.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo17.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo18.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo18.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo18.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo18.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo19.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo19.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo19.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo19.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo2.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo2.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo2.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo2.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo3.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo3.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo3.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo3.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo4.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo4.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo4.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo4.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo5.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo5.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo5.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo5.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo6.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo6.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo6.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo6.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo7.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo7.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo7.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo7.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo8.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo8.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo8.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo8.tex diff --git a/magistrale/Anno 1/Carpi/latex/capitolo9.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/capitolo9.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/capitolo9.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/capitolo9.tex diff --git a/magistrale/Anno 1/Carpi/latex/frontmatter.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/frontmatter.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/frontmatter.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/frontmatter.tex diff --git a/magistrale/Anno 1/Carpi/latex/main.tex b/magistrale/Anno 1/Carpi/appunti slide/latex/main.tex similarity index 100% rename from magistrale/Anno 1/Carpi/latex/main.tex rename to magistrale/Anno 1/Carpi/appunti slide/latex/main.tex diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/Macchina-Turing.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/Macchina-Turing.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/Macchina-Turing.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/Macchina-Turing.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/accertare-gap.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/accertare-gap.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/accertare-gap.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/accertare-gap.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/albero.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/albero.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/albero.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/albero.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/algo-turing.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/algo-turing.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/algo-turing.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/algo-turing.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/algo.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/algo.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/algo.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/algo.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/algoritmo.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/algoritmo.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/algoritmo.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/algoritmo.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/arresto.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/arresto.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/arresto.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/arresto.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/assurdo.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/assurdo.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/assurdo.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/assurdo.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/biiezione.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/biiezione.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/biiezione.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/biiezione.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/bit.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/bit.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/bit.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/bit.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/bitnot.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/bitnot.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/bitnot.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/bitnot.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/calcolo-di-r.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/calcolo-di-r.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/calcolo-di-r.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/calcolo-di-r.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cantor.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cantor.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cantor.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cantor.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f1.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f1.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f1.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f1.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f3.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f3.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f3.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f3.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f4.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f4.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f4.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f4.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f5.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f5.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f5.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f5.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f6.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f6.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f6.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f6.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f7.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f7.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f7.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f7.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f8.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f8.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f8.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f8.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f9.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f9.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6f9.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6f9.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6foto2.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6foto2.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap6foto2.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap6foto2.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f1.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f1.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f1.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f1.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f10.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f10.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f10.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f10.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f11.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f11.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f11.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f11.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f12.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f12.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f12.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f12.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f13.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f13.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f13.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f13.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f14.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f14.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f14.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f14.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f16.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f16.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f16.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f16.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f17.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f17.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f17.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f17.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f18.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f18.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f18.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f18.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f19.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f19.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f19.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f19.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f2.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f2.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f2.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f2.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f20.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f20.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f20.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f20.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f3.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f3.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f3.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f3.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f4.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f4.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f4.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f4.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f5.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f5.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f5.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f5.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f6.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f6.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f6.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f6.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f8.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f8.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f8.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f8.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f9.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f9.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/cap7f9.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/cap7f9.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/contraddizione.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/contraddizione.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/contraddizione.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/contraddizione.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/diagonalizzazione.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/diagonalizzazione.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/diagonalizzazione.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/diagonalizzazione.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/dio1.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/dio1.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/dio1.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/dio1.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/es-cantor.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/es-cantor.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/es-cantor.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/es-cantor.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/ese-turing.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/ese-turing.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/ese-turing.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/ese-turing.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/esempio.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/esempio.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/esempio.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/esempio.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f10cap9.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f10cap9.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f10cap9.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f10cap9.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f1cap16.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f1cap16.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f1cap16.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f1cap16.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f1cap8.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f1cap8.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f1cap8.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f1cap8.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f1cap9.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f1cap9.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f1cap9.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f1cap9.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f2cap8.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f2cap8.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f2cap8.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f2cap8.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f2cap9.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f2cap9.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f2cap9.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f2cap9.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f3cap8.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f3cap8.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f3cap8.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f3cap8.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f3cap9.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f3cap9.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f3cap9.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f3cap9.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f4cap8.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f4cap8.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f4cap8.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f4cap8.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f4cap9.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f4cap9.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f4cap9.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f4cap9.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f5cap8.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f5cap8.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f5cap8.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f5cap8.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f5cap9.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f5cap9.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f5cap9.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f5cap9.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f6cap8.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f6cap8.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f6cap8.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f6cap8.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f6cap9.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f6cap9.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f6cap9.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f6cap9.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/f7cap8.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f7cap8.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/f7cap8.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/f7cap8.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/figura1cap15.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/figura1cap15.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/figura1cap15.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/figura1cap15.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto-ultima.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto-ultima.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto-ultima.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto-ultima.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto10cap11.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto10cap11.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto10cap11.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto10cap11.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto10cap12.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto10cap12.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto10cap12.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto10cap12.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto10cap14.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto10cap14.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto10cap14.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto10cap14.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto10cap15.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto10cap15.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto10cap15.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto10cap15.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto11cap12.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto11cap12.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto11cap12.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto11cap12.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto11cap14.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto11cap14.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto11cap14.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto11cap14.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto11cap15.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto11cap15.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto11cap15.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto11cap15.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto12cap14.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto12cap14.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto12cap14.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto12cap14.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap10.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap10.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap10.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap10.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap11.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap11.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap11.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap11.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap12.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap12.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap12.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap12.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap13.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap13.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap13.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap13.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap14.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap14.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap14.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap14.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap17.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap17.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap17.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap17.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap18.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap18.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto1cap18.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto1cap18.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap10.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap10.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap10.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap10.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap11.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap11.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap11.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap11.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap12.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap12.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap12.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap12.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap13.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap13.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap13.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap13.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap14.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap14.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap14.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap14.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap15.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap15.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap15.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap15.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap16.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap16.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap16.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap16.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap18.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap18.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto2cap18.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto2cap18.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap10.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap10.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap10.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap10.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap11.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap11.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap11.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap11.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap12.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap12.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap12.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap12.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap14.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap14.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap14.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap14.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap15.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap15.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap15.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap15.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap16.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap16.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap16.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap16.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap18.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap18.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto3cap18.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto3cap18.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap10.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap10.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap10.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap10.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap11.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap11.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap11.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap11.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap12.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap12.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap12.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap12.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap13.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap13.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap13.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap13.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap14.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap14.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap14.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap14.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap16.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap16.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap16.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap16.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap18.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap18.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto4cap18.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto4cap18.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto5cap11.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto5cap11.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto5cap11.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto5cap11.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto5cap12.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto5cap12.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto5cap12.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto5cap12.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto5cap13.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto5cap13.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto5cap13.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto5cap13.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto5cap14.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto5cap14.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto5cap14.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto5cap14.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto5cap18.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto5cap18.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto5cap18.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto5cap18.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto6cap11.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto6cap11.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto6cap11.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto6cap11.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto6cap12.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto6cap12.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto6cap12.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto6cap12.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto6cap13.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto6cap13.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto6cap13.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto6cap13.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto6cap14.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto6cap14.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto6cap14.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto6cap14.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto6cap15.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto6cap15.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto6cap15.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto6cap15.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto6cap18.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto6cap18.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto6cap18.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto6cap18.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto7cap11.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto7cap11.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto7cap11.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto7cap11.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto7cap12.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto7cap12.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto7cap12.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto7cap12.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto7cap14.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto7cap14.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto7cap14.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto7cap14.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto7cap15.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto7cap15.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto7cap15.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto7cap15.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto7cap18.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto7cap18.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto7cap18.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto7cap18.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto8cap12.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto8cap12.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto8cap12.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto8cap12.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto8cap15.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto8cap15.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto8cap15.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto8cap15.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto9cap12.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto9cap12.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto9cap12.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto9cap12.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto9cap14.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto9cap14.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto9cap14.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto9cap14.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto9cap15.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto9cap15.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto9cap15.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto9cap15.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto9cap18.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto9cap18.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/foto9cap18.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/foto9cap18.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/funzione.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/funzione.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/funzione.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/funzione.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/goedel.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/goedel.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/goedel.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/goedel.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/inverso.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/inverso.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/inverso.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/inverso.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin1.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin1.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin1.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin1.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin2.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin2.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin2.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin2.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin3.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin3.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin3.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin3.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin4.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin4.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin4.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin4.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin5.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin5.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin5.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin5.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin6.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin6.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin6.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin6.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin7.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin7.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin7.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin7.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin8.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin8.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin8.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin8.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin9.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin9.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/levin9.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/levin9.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/logoDMI.jpg b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/logoDMI.jpg similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/logoDMI.jpg rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/logoDMI.jpg diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/logoUniPg.jpg b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/logoUniPg.jpg similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/logoUniPg.jpg rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/logoUniPg.jpg diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/nl1.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/nl1.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/nl1.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/nl1.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/nl2.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/nl2.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/nl2.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/nl2.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/nl3.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/nl3.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/nl3.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/nl3.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/nulla.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/nulla.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/nulla.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/nulla.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/nulla2.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/nulla2.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/nulla2.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/nulla2.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/numeri.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/numeri.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/numeri.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/numeri.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/official.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/official.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/official.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/official.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/pal.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/pal.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/pal.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/pal.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/sem1.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/sem1.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/sem1.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/sem1.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/semi2.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/semi2.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/semi2.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/semi2.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/semi3.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/semi3.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/semi3.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/semi3.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/semi4.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/semi4.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/semi4.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/semi4.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/semi5.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/semi5.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/semi5.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/semi5.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/semi6.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/semi6.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/semi6.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/semi6.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/sotto.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/sotto.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/sotto.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/sotto.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/tesi.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/tesi.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/tesi.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/tesi.png diff --git a/magistrale/Anno 1/Carpi/latex/tesi_stile/img/turing.png b/magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/turing.png similarity index 100% rename from magistrale/Anno 1/Carpi/latex/tesi_stile/img/turing.png rename to magistrale/Anno 1/Carpi/appunti slide/latex/tesi_stile/img/turing.png diff --git a/magistrale/Anno 1/Carpi/domande_esame.md b/magistrale/Anno 1/Carpi/domande_esame.md new file mode 100644 index 000000000..b85fd14e0 --- /dev/null +++ b/magistrale/Anno 1/Carpi/domande_esame.md @@ -0,0 +1,46 @@ +# Domande Esame Carpi + +## 16 Giugno 2022 + +- Che cos'è una macchina di turning + - _Risposta_: la giovannona sta facendo un mega spiegone della macchina. Ha iniziato dalla definizione per poi continuare con la definizione di istruzioni. Definisce configurazione istantanea. +- Definizione di linguaggio accettato/deciso dalla macchina di turing +- Problema dell'equivalenza delle macchine di turing. In sostanza ha chiesto la dimostrazione +- Che cos'è una riduzione +- Definizione della funzione complessità temporale di una macchina di turing + + +- Che cos'è una funzione ricorsiva parziale. Legame tra funzioni ricorsive parziali e macchina di turing. Dimostrazione del fatto che una funzione ricorsiva parziale è calcolabile da una machina di turing +- Operazione di minimizzazione +- Definizione di problema NP-completo + - _Risposta_: il tipo ha iniziato a dare anche la definizione di riduzione polinomiale +- Esempio di NP-completo: + - _Risposta_: LHALT, 3SAT, e ne elanca molti altri +- Definizione del problema dell'arresto + - Risposta: il tipo la dimostra per allungare il brodo + + +- Definizione di aritmetizzazione delle macchine di turing (associare una macchina ad un indice) + - Riposta: l'ha detta un po a cazzo, ha mancato un passaggio (la funzione G1) +- Macchine Autoapplicate/ autoriferimento (teorema di recursione) + - Risposta: la tipa spiega il teorema di Rice. Carpi chiede la dimostrazione di questo +- La funzione di complessità spaziale di una macchina di Turing: + - Risposta: la tipa fa la differenza tra macchina di turing deterministica e non deterministica +- Teorema di Savich. Chiede anche le ipotesi + + +## 30 Giugno 2022 + +_a sto tizio gli vuole dare la lode e gli sta facendo taaante domane. Gli ha dato la lode_ + +- Cos'e' una macchina di turing (*) +- Definizione di linguaggio accettato/deciso (*) +- Un esempio di linguaggio accettato/deciso. + - Il tipo sta dimostrando il problema dell'arresto +- La funzione complessita' temporale +- Cos'e' un problema NP +- Il teorema di savich +- Le funzioni ricorsive parziali + - ha parlato tipo taaantissimo + +Era solo sto tizio \ No newline at end of file