I definiert eine einfache Liste Typ:`Instanz` für Betontyp anstelle von Typklasse?
data MyList a = End
|Entry a (MyList a)
Statt deriving (Show)
implementiert ich, dass explizit mich für alle MyList a
wo a
eine Instanz von Show
ist.
instance Show a => Show (MyList a)
where show End = ""
show (Entry a l) = (show a) ++","++(show l)
Das funktioniert einwandfrei. Nun wollte ich ändern, dass, so dass nur MyList String
ist eine Instanz von Show
und zu tun, so schrieb ich
instance Show (MyList String)
where show End = ""
show (Entry a l) = a ++","++(show l)
Aber dies zu einem Fehler geführt hat, dass ich nicht verstehe:
Illegal instance declaration for `Show (MyList String)'
(All instance types must be of the form (T a1 ... an)
where a1 ... an are *distinct type variables*,
and each type variable appears at most once in the instance head.
Use FlexibleInstances if you want to disable this.)
In the instance declaration for `Show (MyList String)'
Jeder kann erklären, warum das nicht funktioniert und was dieser Fehler mir sagt?
Also ohne 'FlexibleInstances' zu aktivieren kann ich nur' show' für ganze typeclasses, aber nicht für bestimmte Typen? – flawr
Für einen Typkonstruktor (zB Ihre 'MyList :: * -> *') können Sie nur Klassen (zB 'Show') nur für die ganze" Typenfamilie "der Form' MyList a' gleichzeitig implementieren, nicht für bestimmte Personen wie 'MyList String' oder' MyList Bool'. – kirelagin
Das ist übrigens genau der Grund, warum 'Show' den Hacky [' showList'] hat (https://hackage.haskell.org/package/base-4.9.1.0/docs/Prelude.html#v:showList) Methode. Sie möchten Listen von 'Char' anders als die Listen aller anderen Typen anzeigen, aber Sie können nicht einfach eine separate' Show [Char] '- Instanz in Standard-Haskell implementieren. – kirelagin