Entschuldigung im Voraus, wenn ich hier die falsche Terminologie verwende.
Was ist der idiomatische Weg in Haskell, um zwei oder mehr Typen zu verallgemeinern, so dass Sie Pattern-Matching gegen sie verschieben können, während Sie den Standardcode vermeiden?
Um ein konkretes Beispiel zu geben: In meiner Anwendung möchte ich mögliche Fehler, die während der Ausführung auftreten können, weitergeben. Diese Fehler stammen von einem anderen Modul, daher kontrolliere ich sie nicht direkt:
%Vor%Nun möchte ich eine Art Supertyp dieser Fehlerkategorien übergeben, damit ich sie so behandeln kann:
%Vor%Ist das möglich?
Ich kam am nächsten, indem ich einen Wrapper-Typ wie diesen erstellte:
%Vor%Dadurch kann ich alle Fehler leicht umbrechen, wie in
handleError $ wrap $ WTFError "Woopsie"
aber ich müsste handleError
ändern, damit es mit CatA (WTFError s)
etc.
Gibt es einen einfacheren oder eher idiomatischen Umgang mit einem solchen Szenario?
Angenommen, Sie haben die Ausnahmetypen
%Vor%Und Sie wollten jeden einzelnen, aber generisch behandeln. Anstatt einen Summen-Typ um sie herum als
zu schreiben %Vor%Was Sie wirklich wollen, ist jede Ausnahme zu behandeln. Warum also nicht einfach das tun? Schreiben Sie die Funktionen
%Vor%Schreiben Sie dann eine Klasse
%Vor%Mit
%Vor% Und verwenden Sie handleError
wo nötig. Es ist nicht wirklich anders als das, was Sie haben, aber jetzt ist die Logik für die Behandlung einer Art von Fehler nicht mit der Logik für die Behandlung einer anderen Art von Fehler vermischt. Denken Sie nur an die Klassenstufe handleError
und an Ihre handleError . wrap
.
Ich würde mit dem Erstellen einer Typklasse gehen:
%Vor%und sinnvolle -Instanzen dafür bereitstellen:
%Vor%und benutze es wie:
%Vor% Natürlich ist die GError
Instanz vollständig anpassbar. Sie können jedes Verhalten von ErrorCatA
und ErrorCatB
in Ihren spezifischen Kontext einschließen.
Dieses Papier erklärt, wie Kontrolle.Exception ist implementiert. Ich denke, es kann als erweiterbarer Summen-Typ bezeichnet werden (ein Top-Typ für eine beliebige Familie von (Unter-) Typen, also "Super-Typ", während ein einfacher Summen-Typ wie Either a b
nicht erweiterbar ist, aber trotzdem ein Super-Typ für a
und b
, eine feste Familie von Subtypen). Prism
s aus der lens
-Bibliothek sind verwandt, siehe Kontrolle. Lens.Prism und Control.Exception.Lens zur Verwendung mit Ausnahmen.
Beispiel mit Ausnahmen:
%Vor% oder Sie können Exception
schreiben ähnliche Klasse mit SomeException
ähnlichen Wrappern für den eigenen Gebrauch (Prismen können auch hinzugefügt werden).