Ich versuche, den Quellcode für das Haskell-Paket Data.List.Class zu lesen. (Liste-0.4.2). Aber ich bin mit einigen der Syntax fest.
Gleich zu Beginn heißt es:
%Vor% Ich bin nicht vertraut mit der Syntax der 3. Zeile. Ich denke, dass diese letzte Zeile Cons a (l a)
?? entspricht. Aber ich bin mir nicht wirklich sicher. Ich habe bemerkt, dass der Header der Datei sagt: {-# LANGUAGE FlexibleContexts, TypeFamilies #-}
.
Dann, wenn ich weitermache, gibt es eine seltsame Verwendung der type
Anweisung: type ItemM l :: * -> *
, die ich nicht verstehen konnte.
Kann jemand erklären, was diese bedeuten? Ich habe ein perfektes Verständnis von Data.List, aber diese Typklasse Sache ist mir nicht wirklich klar. Außerdem habe ich nach Wikis, Beispielen und / oder Tutorials für die Verwendung von Data.List gesucht. {Class, Tree}, aber es scheint keine zu geben, außer den Kommentaren, die mit dem Code kommen. Irgendwelche Hinweise hier?
Danke.
- Aktualisierung -
Die erste Antwort (@Chris) hat mir geholfen, die Kind-Signatur und die Record-Syntax zu verstehen, was sehr hilfreich ist. Dennoch kann ich aus dem Code insgesamt keinen Sinn ziehen, wie er das Verhalten einer Liste erfasst und definiert, und welchen Wert sie den bekannten Data.List-Definitionen hinzufügt. Hier sind einige weitere Details, wo es nur zwei Instanzanweisungen gibt. Der Identity
-Term stammt auch von import Data.Functor.Identity (Identity(..))
. Können Sie mir bitte erklären, was das für eine Typklasse ist, um die Eigenschaften einer Liste zu erfassen, wie wir sie normalerweise kennen? Wieder habe ich online gesucht, aber es gibt wirklich keine Dokumentation für Data.List.Class außer dem Code selbst. Weiß jemand?
Gibt es ein weiteres Beispiel für die Verwendung der type
-Anweisung in der typeclass-Einschränkung, ähnlich wie in diesem Beispiel? Ich suchte learnyouahaskell.com/ (@Landei) aber konnte solch ein Beispiel nicht finden. Ich nehme an, dass die Verwendung von type
hier ähnlich ist, wie Sie typedef
in C ++ - Vorlagen verwenden würden, um "Funktionen auf Typen" zu definieren, richtig?
Nochmals vielen Dank.
%Vor%Dies
%Vor%heißt Datensatzsyntax . Sie haben Recht, wenn Sie vermuten, dass die Struktur die gleiche ist wie bei der Eingabe von
%Vor%Sie erhalten jedoch auch die zwei Accessor-Funktionen:
%Vor%Record Syntax ist syntaktischer Zucker - hier spart es Ihnen rund 4 Zeilen Code. Sie können eine Musterübereinstimmung auf die normale Weise erstellen, wie im Code direkt über diesem Absatz, oder Sie können die Datensatzsyntax in der Musterübereinstimmung verwenden:
%Vor%Auch dies wird in den Standard-Mustervergleich übernommen.
Dies
%Vor%ist eine type family -Deklaration. Die Zeile
%Vor% ist eine Art-Signatur . Wenn wir sagen, dass etwas eine Art *
hat, meinen wir, dass es ein Basistyp ist, wie Int
oder Float
. Zu sagen, dass etwas eine Art * -> *
hat, bedeutet, dass es ein Typkonstruktor ist, d. H. Es nimmt einen Typ und gibt einen anderen Typ zurück.
Der Konstruktor Maybe
hat diese Art von Signatur:
Denken Sie daran, dass Maybe
allein kein Typ ist. Es muss ein Typ angegeben werden, und dann wird ein Typ zurückgegeben. Gib es Int
und du bekommst Maybe Int
. Gib es Double
und du bekommst Maybe Double
.
Der Typkonstruktor ItemM l
nimmt einen Typparameter (vom Typ *
) und gibt etwas vom Typ *
zurück. Beachten Sie, dass, da l
vom Typ *
ist, Sie
d. ItemM
verwendet zwei Typen und gibt einen Typ zurück (entspricht einem Typ und gibt einen unären Typkonstruktor zurück).
Wenn Sie die Typdeklaration in die Klasse aufnehmen, erzwingen Sie die Einschränkung, dass in allen Fällen der Klasse l
in ItemM l
mit der l
in List l
übereinstimmen muss. Es ist unmöglich, eine Instanz der Klasse zu erstellen, in der diese nicht übereinstimmen.