Dobra, chodźmy jeden po drugim.
Wartości
Wartości to konkretne dane, które programy oceniają i żonglują. Nic szczególnego, niektóre przykłady mogą być
1
true
"fizz buzz foo bar"
Rodzaje
Dobrym opisem typu jest „klasyfikator wartości”. Typ to trochę informacji o tym, jaka będzie ta wartość w czasie wykonywania, ale wskazany w czasie kompilacji.
Na przykład, jeśli powiesz mi to e : bool
w czasie kompilacji, a ja będę wiedział, że e
jest to true
albo w false
czasie wykonywania, nic więcej! Ponieważ typy tak ładnie klasyfikują wartości, możemy wykorzystać te informacje do określenia podstawowych właściwości Twojego programu.
Na przykład, jeśli kiedykolwiek zobaczę, jak dodajesz e
i e'
kiedy e : int
i e' : String
, to wiem, że coś jest nie tak! W rzeczywistości mogę to oflagować i zgłosić błąd w czasie kompilacji, mówiąc: „Hej, to nie ma żadnego sensu!”.
Bardziej wydajny system typów pozwala na bardziej interesujące typy, które klasyfikują bardziej interesujące wartości. Rozważmy na przykład jakąś funkcję
f = fun x -> x
To całkiem jasne f : Something -> Something
, ale co to powinno Something
być? W systemie typu nudnego musielibyśmy określić coś arbitralnego Something = int
. W bardziej elastycznym systemie typów można by powiedzieć
f : forall a. a -> a
To znaczy „dla każdego a
, f
odwzorowuje a
na a
”. Wykorzystajmy to f
bardziej ogólnie i piszmy ciekawsze programy.
Co więcej, kompilator sprawdzi, czy rzeczywiście spełnia on podany przez nas klasyfikator, jeśli f = fun x -> true
wtedy wystąpi błąd, a kompilator to powie!
Więc jako tldr; typ jest ograniczeniem czasowym kompilacji wartości, jakie wyrażenie może mieć w czasie wykonywania.
Typ Konstruktor
Niektóre typy są powiązane. Na przykład lista liczb całkowitych jest bardzo podobna do listy ciągów znaków. To prawie tak, jak sort
dla liczb całkowitych jest prawie jak sort
dla ciągów. Możemy wyobrazić sobie rodzaj fabryki, która buduje te prawie te same typy, uogólniając ich różnice i budując je na żądanie. Taki jest konstruktor typów. To trochę jak funkcja od typów do typów, ale trochę bardziej ograniczona.
Klasycznym przykładem jest ogólna lista. Konstruktor typów dla to tylko ogólna definicja
data List a = Cons a (List a) | Nil
Teraz List
jest funkcja, która mapuje typ a
na listę wartości tego typu! Wydaje mi się, że w Javie są to „klasy ogólne”
Parametry typu
Parametr typu to typ przekazywany do konstruktora typu (lub funkcji). Podobnie jak na poziomie wartości, powiedzielibyśmy, że foo(a)
ma parametr a
tak jak List a
parametr typu a
.
Rodzaje
Rodzaje są trochę trudne. Podstawową ideą jest to, że niektóre typy są podobne. Na przykład, mamy wszystkie prymitywne typy w Javie int
, char
, float
..., które zachowują się tak, jakby one mają taką samą „typem”. Z wyjątkiem sytuacji, gdy mówimy o klasyfikatorach dla samych typów, nazywamy je klasyfikatorami. Więc int : Prim
, String : Box
, List : Boxed -> Boxed
.
Ten system podaje ładne konkretne reguły dotyczące tego, jakiego rodzaju typów możemy używać, podobnie jak typy rządzą wartościami. Bez wątpienia byłoby to nonsensowne
List<List>
lub
List<int>
W Javie List
musi być zastosowany do konkretnego typu, aby mógł być używany w ten sposób! Jeśli spojrzymy na ich rodzaje List : Boxed -> Boxed
i odtąd Boxed -> Boxed /= Boxed
, powyższy jest miłym błędem!
Przez większość czasu tak naprawdę nie myślimy o rodzajach i po prostu traktujemy je jako „zdrowy rozsądek”, ale w przypadku bardziej wyszukanych systemów typów warto o tym pomyśleć.
Mała ilustracja tego, co mówiłem do tej pory
value : type : kind : ...
true : bool : Prim : ...
new F() : Foo : Boxed : ...
Lepsze czytanie niż Wikipedia
Jeśli jesteś zainteresowany tego typu rzeczami, zdecydowanie polecam zainwestowanie dobrego podręcznika. Teoria typów i ogólnie PLT są dość rozległe i bez spójnej bazy wiedzy, którą ty (lub przynajmniej ja) możesz wędrować bez dostania się gdzieś przez miesiące.
Dwie z moich ulubionych książek to
- Rodzaje i język programowania - Ben Pierce
- Praktyczne podstawy języków programowania - Bob Harper
Obie są doskonałymi książkami, które przedstawiają to, o czym właśnie mówiłem, i wiele więcej w pięknych, dobrze wyjaśnionych szczegółach.