Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
Download

📚 The CoCalc Library - books, templates and other resources

132930 views
License: OTHER
1
%!TEX root = Programmierparadigmen.tex
2
\chapter{Typinferenz}
3
\begin{definition}[Datentyp]\index{Typ|see{Datentyp}}\xindex{Datentyp}%
4
Ein \textit{Datentyp} oder kurz \textit{Typ} ist eine Menge von Werten, mit
5
denen eine Bedeutung verbunden ist.
6
\end{definition}
7
8
\begin{beispiel}[Datentypen]
9
\begin{itemize}
10
\item $\text{\texttt{bool}} = \Set{\text{True}, \text{False}}$
11
\item $\text{\texttt{char}} = \text{vgl. \cpageref{sec:ascii-tabelle}}$
12
\item $\text{\texttt{int}}_{\text{Haskell}} = [-2^{29}, 2^{29}-1] \cap \mathbb{N}$
13
\item $\text{\texttt{int}}_{\text{C90}} = [-2^{15}-1, 2^{15}-1] \cap \mathbb{N}$\footnote{siehe ISO/IEC 9899:TC2, Kapitel 7.10: Sizes of integer types <limits.h>}
14
\item \texttt{float} = siehe IEEE 754
15
\item Funktionstypen, z.~B. $\text{\texttt{int}} \rightarrow \text{\texttt{int}}$ oder
16
$\text{\texttt{char}} \rightarrow \text{\texttt{int}}$
17
\end{itemize}
18
\end{beispiel}
19
20
\underline{Hinweis:} Typen sind unabhängig von ihrer Repräsentation. So kann ein
21
\texttt{bool} durch ein einzelnes Bit repräsentiert werden oder eine Bitfolge
22
zugrunde liegen.
23
24
Auf Typen sind Operationen definiert. So kann man auf numerischen Typen eine
25
Addition (+), eine Subtraktion (-), eine Multiplikation (*) und eine Division (/)
26
definieren.\\
27
Ich schreibe hier bewusst \enquote{eine} Multiplikation und nicht \enquote{die}
28
Multiplikation, da es verschiedene Möglichkeiten gibt auf Gleitpunktzahlen
29
Multiplikationen zu definieren. So kann man beispielsweise die Assoziativität
30
unterschiedlich wählen.
31
32
\begin{beispiel}[Multiplikation ist nicht assoziativ]
33
In Python 3 ist die Multiplikation linksassoziativ. Also:
34
\inputminted[numbersep=5pt, tabsize=4]{python}{scripts/python/multiplikation.py}
35
\end{beispiel}
36
37
\begin{definition}[Typvariable]\xindex{Typvariable}%
38
Eine Typvariable repräsentiert einen Typen.
39
\end{definition}
40
41
\underline{Hinweis:} Üblicherweise werden kleine griechische Buchstaben ($\alpha, \beta, \tau_1, \tau_2, \dots$) als Typvariablen gewählt.
42
43
Genau wie Typen bestimmte Operationen haben, die auf ihnen definiert sind,
44
kann man sagen, dass Operationen bestimmte Typen, auf die diese Anwendbar sind. So ist
45
\[\alpha+\beta\]
46
für numerische $\alpha$ und $\beta$ wohldefiniert, auch wenn $\alpha$ und $\beta$ boolesch sind
47
oder beides Strings sind könnte das Sinn machen. Es macht jedoch z.~B. keinen Sinn,
48
wenn $\alpha$ ein String ist und $\beta$ boolesch.
49
50
Die Menge aller Operationen, die auf die Variablen angewendet werden, nennt man
51
\textbf{Typkontext}\xindex{Typkontext}. Dieser wird üblicherweise mit $\Gamma$
52
bezeichnet. Der Typkontext weist freien Variablen $x$ ihren Typ $\Gamma(x)$ zu.
53
54
Das Ableiten einer Typisierung für einen Ausdruck nennt man \textbf{Typinferenz}\xindex{Typinferenz}.
55
Man schreibt: $\vdash(\lambda x.2): \alpha \rightarrow \text{int}$.
56
57
Bei solchen Ableitungen sind häufig viele Typen möglich. So kann der Ausdruck
58
\[\lambda x.\ 2\]
59
folgenderweise typisiert werden:
60
\begin{itemize}
61
\item $\vdash(\lambda x.\ 2): \text{bool} \rightarrow \text{int}$
62
\item $\vdash(\lambda x.\ 2): \text{int} \rightarrow \text{int}$
63
\item $\vdash(\lambda x.\ 2): \text{Char} \rightarrow \text{int}$
64
\item $\vdash(\lambda x.\ 2): \alpha \rightarrow \text{int}$
65
\end{itemize}
66
67
In der letzten Typisierung stellt $\alpha$ einen beliebigen Typen dar.
68
69
Wichtig ist, dass man sich von unten nach oben vorarbeitet.
70
71
\begin{beispiel}[Typinferenz\footnotemark]
72
Typisieren Sie den Term
73
\[\lambda a.\ a\ \text{true}\]
74
unter Verwendung der Regeln \verb+Var+, \verb+Abs+ und \verb+App+.
75
76
\[\ABS: \frac{\APP \frac{\VAR \frac{(a:\alpha_2)(a) = \alpha_4}{a: \alpha_2 \vdash a: \alpha_4} \;\;\;\;\;\; a: \alpha_2 \vdash \text{true}: \text{bool}}{a: \alpha_2 \vdash a\ \text{true}: \alpha_3}}{\vdash \lambda a.\ a\ \text{true}: \alpha_1}\]
77
\end{beispiel}
78
\footnotetext{Dieses Beispiel stammt aus der Klausur vom WS2013/2014}
79
80
\section{Typsystem}
81
\begin{definition}[Typsystem $\Gamma \vdash t: T$\footnotemark]\label{def:typsystem-t1}\xindex{Typregel}\xindex{Typsystem}\xindex{APP@$\APP$}\xindex{ABS@$\ABS$}\xindex{VAR@$\VAR$}\xindex{CONST@$\CONST$}%
82
Ein Typsystem besteht aus einem Typkontext $\Gamma$ und folgenden Regeln:
83
84
\begin{align*}
85
\CONST:&\frac{c \in \text{Const}}{\Gamma \vdash c: \tau_c}\\
86
&\\
87
\VAR: &\frac{\Gamma(x) = \tau}{\Gamma \vdash x: \tau}\\
88
&\\
89
\ABS: &\frac{\Gamma, x: \tau_1 \vdash t: \tau_2}{\Gamma \vdash \lambda x. t: \tau_1 \rightarrow \tau_2}\\
90
&\\
91
\APP: &\frac{\Gamma \vdash t_1: \tau_2 \rightarrow \tau\;\;\; \Gamma \vdash t_2: \tau_2}{\Gamma \vdash t_1 t_2: \tau} \\
92
\end{align*}
93
94
wobei $t_1, t_2$ immer $\lambda$-Terme bezeichnet.
95
\end{definition}
96
\footnotetext{WS 2013 / 2014, Folie 192}
97
98
99
Dabei ist der lange Strich kein Bruchstrich, sondern ein Symbol der Logik das als
100
\textbf{Schlussstrich}\xindex{Schlussstrich} bezeichnet wird. Dabei ist der
101
Zähler als Voraussetzung und der Nenner als Schlussfolgerung zu verstehen.
102
103
\begin{definition}[Typsubstituition]\xindex{Typsubstituition}%
104
Eine \textit{Typsubstituition} ist eine endliche Abbildung von Typvariablen auf
105
Typen.
106
\end{definition}
107
108
Für eine Menge von Typsubsitutionen wird überlicherweise $\sigma$ als Symbol
109
verwendet. Man schreibt also beispielsweise:
110
\[\sigma = [\alpha_1 \text{\pointer} \text{\texttt{bool}}, \alpha_2 \text{\pointer} \alpha_1 \rightarrow \alpha_1]\]
111
112
\begin{definition}[Lösung eines Typkontextes]
113
Sei $t$ eine beliebige freie Variable, $\tau = \tau(t)$ ein beliebiger Typ
114
$\sigma$ eine Menge von Typsubstitutionen und $\Gamma$ ein Typkontext.
115
116
$(\sigma, \tau)$ heißt eine Lösung für $(\Gamma, t)$, falls gilt:
117
\[\sigma \Gamma \vdash t : \tau\]
118
\end{definition}
119
120
\begin{beispiel}[Typisierungsregel]\xindex{Typisierungsregel}%
121
Das Folgende nennt man eine Typisierungsregel:\footnote{Klausur WS 2010 / 2011}
122
\[\frac{\Gamma \vdash b: \text{\texttt{bool}}\;\;\; \Gamma \vdash x: \tau \;\;\; \Gamma \vdash y: \tau }{\Gamma \vdash \text{\textbf{if} b \textbf{then} x \textbf{else} y} : \tau}\]
123
\end{beispiel}
124
125
\section{Constraint-Mengen}
126
Die Konstraint-Mengen ergeben sich direkt aus den Typisierungsregeln:
127
128
\begin{align*}
129
\CONST:&\text{z.~B.} \CONST \frac{2 \in \text{Const}}{\Gamma \vdash 2 : \alpha_5} \text{ ergibt } \alpha_5 = \text{\texttt{int}}\\
130
&\\
131
\VAR: &\\
132
&\\
133
\ABS: &\frac{\alpha_2 \vdash \alpha_3}{\alpha_1} \text{ ergibt } \alpha_1 = \alpha_2 \rightarrow \alpha_3\\
134
&\\
135
\APP: &\frac{\vdash \alpha_2 \;\;\; \vdash \alpha_3}{\alpha_1} \text{ ergibt } \alpha_2 = \alpha_3 \rightarrow \alpha_1\\
136
\end{align*}
137
138
\section{Let-Polymorphismus}\xindex{let-Polymorphismus}\footnote{WS 2013 / 2014, Folie 205ff}%
139
Das Programm $P = \text{let } f = \lambda x.\ 2 \text{ in } f\ (f\ \text{\texttt{true}})$
140
ist eine polymorphe Hilfsfunktion, da sie beliebige Werte auf 2 Abbildet.
141
Auch solche Ausdrücke sollen typisierbar sein.
142
143
Die Kodierung
144
\[\text{let } x = t_1 \text{ in } t_2\]
145
ist bedeutungsgleich mit
146
\[(\lambda x.\ t_2) t_1\]
147
148
Das Problem ist, dass
149
\[P = \lambda f. \ f (f\ \text{\texttt{true}})\ (\lambda x.\ 2)\]
150
so nicht typisierbar ist, da in
151
\[\ABS \frac{f: \tau_f \vdash f\ (f\ \text{\texttt{true}}): \dots}{\vdash \lambda f.\ f\ (f\ \text{\texttt{true}}): \dots}\]
152
müsste
153
\[\tau_f = \text{bool} \rightarrow \text{int}\]
154
und zugleich
155
\[\tau_f = \text{int} \rightarrow \text{int}\]
156
in den Typkontext eingetragen werden. Dies ist jedoch nicht möglich. Stattdessen
157
wird
158
\[\text{let} x = t_1 \text{ in } t_2\]
159
als neues Konstrukt im $\lambda$-Kalkül erlaubt.
160
161
Der Term
162
\[\text{let } x = t_1 \text{ in } t_2\]
163
ist bedeutungsgleich zu
164
\[\lambda x.\ (t_2)\ t_1\]
165
166
\begin{definition}[Typschema]\xindex{Typschema}%
167
Ein Typ der Gestalt $\forall \alpha_1.\ \forall \alpha_2.\ \dots\ \forall \alpha_n. \tau$
168
heißt \textbf{Typschema}. Es bindet freie Variablen $\alpha_1, \dots, \alpha_n$
169
in $\tau$.
170
\end{definition}
171
172
\begin{beispiel}[Typschema]
173
Das Typschema $\forall \alpha.\ \alpha \rightarrow \alpha$ steht für unendlich
174
viele Typen und insbesondere für folgende:
175
\begin{bspenum}
176
\item int $\rightarrow$ int, bool $\rightarrow$ bool, \dots
177
\item (int $\rightarrow$ int) $\rightarrow$ (int $\rightarrow$ int), \dots
178
\item \dots
179
\end{bspenum}
180
\end{beispiel}
181
182
\begin{definition}[Typschemainstanziierung]\xindex{Typschemainstanziierung}%
183
Sei $\tau_2$ ein Nicht-Schema-Typ. Dann heißt der Typ
184
\[\tau[\alpha \mapsto \tau_2]\]
185
eine \textbf{Instanziierung} vom Typschema $\forall \alpha.\ \tau$
186
und man schreibt:
187
\[(\forall \alpha.\ \tau) \succeq \tau [\alpha \mapsto \tau_2]\]
188
\end{definition}
189
190
\begin{beispiel}[Typschemainstanziierung]
191
Folgendes sind Beispiele für Typschemainstanziierungen:
192
\begin{bspenum}
193
\item $\forall \alpha.\ \alpha \rightarrow \alpha \succeq \text{int} \rightarrow \text{int}$
194
\item $\forall \alpha.\ \alpha \rightarrow \alpha \succeq (\text{int} \rightarrow \text{int}) \rightarrow (\text{int} \rightarrow \text{int})$
195
\item $\text{int} \succeq \text{int}$
196
\end{bspenum}
197
198
Folgendes sind keine Typschemainstanziierungen:
199
\begin{bspenum}
200
\item $\alpha \rightarrow \alpha \nsucceq \text{int} \rightarrow \text{int}$
201
\item $\alpha \nsucceq \text{bool}$
202
\item $\forall \alpha.\ \alpha \rightarrow \alpha \nsucceq \text{bool}$
203
\end{bspenum}
204
\end{beispiel}
205
206
Zu Typschemata gibt es angepasste Regeln:\xindex{Typregel!mit Typabstraktionen}%
207
208
\[\VAR \frac{\Gamma(x)= \tau' \;\;\; \tau' \succeq \tau}{\gamma \vdash x: \tau}\]
209
210
und
211
212
\[\ABS \frac{\Gamma, x: \tau_1 \vdash t: \tau_2 \;\;\; \tau_1 \text{ kein Typschema}}{\Gamma \vdash \lambda x. t: \tau_1 \rightarrow \tau_2}\]
213
214
\todo[inline]{Folie 208ff}
215
216
\section{Beispiele}
217
Im Folgenden wird die Typinferenz für einige $\lambda$-Funktionen durchgeführt.
218
219
\subsection[$\lambda x.\ \lambda y.\ x\ y$]{$\lambda x.\ \lambda y.\ x\ y$\footnote{Lösung von Übungsblatt 6, WS 2013 / 2014}}
220
Gesucht ist ein Typ $\tau$, sodass sich $\vdash \lambda x.\ \lambda y.\ x\ y: \tau$
221
mit einem Ableitungsbaum nachweisen lässt. Es gibt mehrere solche $\tau$, aber
222
wir suchen das allgemeinste. Die Regeln unseres Typsystems (siehe \cpageref{def:typsystem-t1})
223
sind \textit{syntaxgerichtet}, d.~h. zu jedem $\lambda$-(Teil)-Term gibt es genau
224
eine passende Regel.
225
226
Für $\lambda x.\ \lambda y.\ x\ y$ wissen wir also schon, dass jeder Ableitungsbaum\xindex{Ableitungsbaum}
227
von folgender Gestalt ist. Dabei sind $\alpha_i$ Platzhalter:
228
229
\[\ABS \frac{\ABS\frac{\textstyle\APP \frac{\textstyle\VAR \frac{(x: \alpha_2, y: \alpha_4)\ (x) = \alpha_6}{x: \alpha_2, y: \alpha_4 \vdash x: \alpha_6}\ \ \VAR \frac{(x:\alpha_2, y: \alpha_4)\ (y) = \alpha_7}{x: \alpha_2, y: \alpha_4 \vdash y : \alpha_7}}{\textstyle x: \alpha_2, y: \alpha_4 \vdash x\ y: \alpha_5}}{x:\alpha_2 \vdash \lambda y.\ x\ y\ :\ \alpha_3}}{\vdash \lambda x.\ \lambda \ y.\ x\ y: \alpha_1}\]
230
231
Das was wir haben wollen steht am Ende, also unter dem unterstem Schlussstrich.
232
Dann bedeutet die letzte Zeile
233
\[\vdash \lambda x.\ \lambda \ y.\ x\ y: \alpha_1\]
234
235
Ohne (weitere) Voraussetzungen lässt sich sagen, dass der Term
236
\[\lambda x.\ \lambda \ y.\ x\ y\]
237
vom Typ $\alpha_1$ ist.
238
239
Links der Schlussstriche steht jeweils die Regel, die wir anwenden. Also entweder
240
$\ABS$, $\VAR$, $\CONST$ oder $\APP$.
241
242
Nun gehen wir eine Zeile höher:
243
244
\[x:\alpha_2 \vdash \lambda y.\ x\ y\ :\ \alpha_3\]
245
246
Diese Zeile ist so zu lesen: Mit der Voraussetzung, dass $x$ vom Typ $\alpha_2$
247
ist, lässt sich syntaktisch Folgern, dass der Term $\lambda y.\ x\ y$ vom
248
Typ $\alpha_3$ ist.
249
250
\underline{Hinweis:} Alles was in Zeile $i$ dem $\vdash$ steht, steht auch in
251
jedem \enquote{Nenner} in Zeile $j < i$ vor jedem einzelnen $\vdash$.
252
253
Folgende Typgleichungen $C$ lassen sich aus dem Ableitungsbaum ablesen:
254
255
\begin{align*}
256
C &= \Set{\alpha_1 = \alpha_2 \rightarrow \alpha_3}\\
257
&\cup \Set{\alpha_3 = \alpha_4 \rightarrow \alpha_5}\\
258
&\cup \Set{\alpha_6 = \alpha_7 \rightarrow \alpha_5}\\
259
&\cup \Set{\alpha_6 = \alpha_2}\\
260
&\cup \Set{\alpha_7 = \alpha_4}
261
\end{align*}
262
263
Diese Bedingungen (engl. \textit{Constraints})\xindex{Constraints} haben eine
264
allgemeinste Lösung mit einem allgemeinsten Unifikator $\sigma_C$:
265
266
\begin{align*}
267
\sigma_C = [&\alpha_1 \Parr (\alpha_4 \rightarrow \alpha_5) \rightarrow \alpha_4 \rightarrow \alpha_5,\\
268
&\alpha_2 \Parr \alpha_4 \rightarrow \alpha_5,\\
269
&\alpha_3 \Parr \alpha_4 \rightarrow \alpha_5,\\
270
&\alpha_6 \Parr \alpha_4 \rightarrow \alpha_5,\\
271
&\alpha_7 \Parr \alpha_4]
272
\end{align*}
273
274
\underline{Hinweis:} Es gilt $(\alpha_4 \rightarrow \alpha_5) \rightarrow \alpha_4 \rightarrow \alpha_5 = (\alpha_4 \rightarrow \alpha_5) \rightarrow (\alpha_4 \rightarrow \alpha_5)$
275
276
Also gilt: Der allgemeinste Typ von $\lambda x.\ \lambda y.\ x\ y$ ist $\sigma_C (\alpha_1) = (\alpha_4 \rightarrow \alpha_5) \rightarrow \alpha_4 \rightarrow \alpha_5$.
277
278
\subsection[Selbstapplikation]{Selbstapplikation\footnote{Lösung von Übungsblatt 6, WS 2013 / 2014}}\xindex{Selbstapplikation}
279
Im Folgenden wird eine Typinferenz für die Selbstapplikation, also
280
\[\lambda x.\ x\ x\]
281
durchgeführt.
282
283
Zuerst erstellt man den Ableitungsbaum:
284
285
\[\ABS\frac{\APP \frac{\VAR \frac{(x:\alpha_2)\ (x) = \alpha_5}{x:\alpha_2 \vdash x: \alpha_5} \;\;\; \VAR \frac{(x:\alpha_2)\ (x) = \alpha_4}{x:\alpha_2 \vdash x:\alpha_4}}{x: \alpha_2 \vdash x\ x\ :\ \alpha_3}}{\vdash \lambda x.\ x\ x: \alpha_1}\]
286
287
Dies ergibt die Constraint-Menge
288
\begin{align}
289
C&= \Set{\alpha_1 = \alpha_2 \rightarrow \alpha_3} &\text{$\ABS$-Regel}\label{eq:bsp2.c1}\\
290
&\cup \Set{\alpha_5 = \alpha_4 \rightarrow \alpha_3} &\text{$\APP$-Regel}\label{eq:bsp2.c2}\\
291
&\cup \Set{\alpha_5 = \alpha_2} &\text{Linke $\VAR$-Regel}\label{eq:bsp2.c3}\\
292
&\cup \Set{\alpha_4 = \alpha_2} &\text{Rechte $\VAR$-Regel}\label{eq:bsp2.c4}
293
\end{align}
294
295
Aus \cref{eq:bsp2.c3} und \cref{eq:bsp2.c4} folgt:
296
\[\alpha_2 = \alpha_4 = \alpha_5\]
297
298
Also lässt sich \cref{eq:bsp2.c2} umformulieren:
299
\[\alpha_2 = \alpha_2 \rightarrow \alpha_3\]
300
301
Offensichtlich ist diese Bedingung nicht erfüllbar. Daher ist ist die Selbstapplikation
302
nicht typisierbar. Dies würde im Unifikationsalgorithmus
303
(vgl. \cref{alg:klassischer-unifikationsalgorithmus})
304
durch den \textit{occur check} festgestellt werden.
305