Haskell Language
Herschrijfregels (GHC)
Zoeken…
Herschrijfregels gebruiken voor overbelaste functies
In deze vraag vroeg @Viclib over het gebruik van herschrijfregels om typeklassewetten te gebruiken om een aantal overbelaste functie-aanroepen te elimineren:
Let op de volgende les:
class ListIsomorphic l where toList :: l a -> [a] fromList :: [a] -> l a
Ik eis dat
toList . fromList == id
. Hoe schrijf ik herschrijfregels om GHC te vertellen die vervanging te doen?
Dit is een ietwat lastige use case voor het herschrijfregelsmechanisme van GHC, omdat overbelaste functies worden herschreven in hun specifieke instantiemethoden door regels die impliciet achter de schermen worden gecreëerd door GHC (dus zoiets als fromList :: Seq a -> [a]
zou zijn herschreven in Seq$fromList
etc.).
Door echter eerst toList
en fromList
herschrijven naar niet-ingevoerde methoden zonder typeklasse, kunnen we ze beschermen tegen voortijdig herschrijven en behouden totdat de regel voor de compositie kan worden geactiveerd:
{-# RULES
"protect toList" toList = toList';
"protect fromList" fromList = fromList';
"fromList/toList" forall x . fromList' (toList' x) = x; #-}
{-# NOINLINE [0] fromList' #-}
fromList' :: (ListIsomorphic l) => [a] -> l a
fromList' = fromList
{-# NOINLINE [0] toList' #-}
toList' :: (ListIsomorphic l) => l a -> [a]
toList' = toList