existential-type

___ tag123haskell ___ Haskell ist eine funktionale Programmiersprache mit starker statischer Typisierung, verzögerungsfreier Auswertung, umfangreicher Parallelitäts- und Parallelitätsunterstützung und einzigartigen Abstraktionsfunktionen. ___ tag123existentialtyp ___ Existentialtypen sind Typen, die eine Sammlung von Operationen bereitstellen, die auf einen nicht angegebenen oder abstrakten Typ angewendet werden. Sie erfassen somit in einer typentheoretischen Einstellung Begriffe von Interface und Abstraktion. ___ qstntxt ___

Ist es möglich, eine Haskell-Funktion zu schreiben, die einen parametrisierten Typ liefert, in dem der genaue Typparameter verborgen ist? I.e. etwas wie %code% ? Der naheliegende Versuch:

%Vor%

kann nicht mit:

kompiliert werden %Vor%

Ich weiß, dass dies ein künstliches Beispiel ist, aber ich bin neugierig, ob es GHC gelingt, den exakten Typ, mit dem %code% parametrisiert ist, nicht zu interessieren, ohne einen weiteren existenziellen Wrapper-Typ für das Ergebnis einzuführen von %code% .

Zur Klarstellung möchte ich Sicherheit schreiben, möchte aber auch eine Funktion %code% anwenden können, die %code% nicht interessiert (zB weil sie einfach ein String-Feld aus %code% extrahiert) Ergebnis von %code% . Ich weiß, dass es andere Wege gibt, um das zu erreichen (z. B. %code% definieren), aber ich bin mehr daran interessiert, ob es einen fundamentalen Grund dafür gibt, warum solch ein Verstecken unter Existenziellen nicht erlaubt ist.

    
___ qstnhdr ___ Haskell-Funktion, die den existentiellen Typ zurückgibt ___ answer33064175 ___

Ja, Sie können GHC davon überzeugen, dass Sie sich nicht um den genauen Typ kümmern, mit dem %code% parametrisiert ist. Nur, es ist eine schreckliche Idee.

%Vor%

Das passiert, wenn ich dieses einfache Programm ausführe:

usw., bis der Speicherverbrauch das System zum Absturz bringt.

Typen sind wichtig! Wenn Sie das Typsystem umgehen, umgehen Sie die Vorhersehbarkeit Ihres Programms (dh alles kann passieren, einschließlich thermonuklearer Krieg oder der berühmte Dämonen fliegen aus deiner Nase ).

Sie dachten offensichtlich, dass Typen irgendwie anders funktionieren. In dynamischen Sprachen wie Python und auch in OO-Sprachen wie Java ist ein Typ gewissermaßen eine Eigenschaft , die ein Wert haben kann. Die (Referenz-) Werte enthalten also nicht nur die Informationen, die zur Unterscheidung verschiedener Werte eines einzelnen Typs benötigt werden, sondern auch Informationen zur Unterscheidung verschiedener (Unter-) Typen. Das ist in vielerlei Hinsicht ziemlich ineffizient - es ist ein Hauptgrund, warum Python so langsam ist und Java eine so große VM braucht.

In Haskell gibt es zur Laufzeit nicht . Eine Funktion weiß nie, mit welchem ​​Typ die Werte arbeiten. Nur weil der Compiler alles über die Typen weiß, die er haben wird, braucht die Funktion kein solches Wissen - der Compiler hat es bereits fest programmiert! (Das heißt, es sei denn, Sie umgehen es mit %code% , was, wie ich gezeigt habe, genauso unsicher ist, wie es sich anhört.)

Wenn Sie den Typ als "Eigenschaft" an einen Wert anhängen möchten, müssen Sie dies explizit tun, und dafür gibt es diese existenziellen Wrapper. Es gibt jedoch normalerweise bessere Möglichkeiten, dies in einer funktionalen Sprache zu tun. Für was ist wirklich die Anwendung, für die Sie das wollten?

Vielleicht ist es auch hilfreich, sich daran zu erinnern, was eine Signatur mit polymorphem Ergebnis bedeutet. %code% bedeutet nicht "das Ergebnis ist einige %code% ... und der Aufrufer kümmert sich nicht mehr um den %code% used". Das wäre in Java der Fall, aber in Haskell wäre es ziemlich nutzlos, weil man mit einem Wert unbekannten Typs nichts anfangen kann.

Stattdessen bedeutet es: für was auch immer Typ %code% der Aufrufer anfordert, diese Funktion kann einen geeigneten %code% -Wert liefern. Natürlich ist das schwierig zu liefern - ohne zusätzliche Informationen ist es genauso unmöglich wie irgendetwas mit einem unbekannten Wert zu tun. Aber wenn in den Argumenten bereits %code% -Werte vorhanden sind oder %code% irgendwie auf eine Typklasse beschränkt ist (z. B. %code% , dann ist das durchaus möglich und sehr nützlich.

Um ein %code% -Feld zu erhalten - unabhängig vom Parameter %code% - können Sie direkt mit dem umbrochenen Wert arbeiten:

%Vor%

Um solche Funktionen auf %code% allgemeiner zu schreiben (mit jedem "Label-Accessor, der sich nicht um %code% kümmert"), verwenden Sie Rank2-Polymorphismus, wie in der Antwort von n.m. gezeigt.

    
___ answer33064451 ___

Ja, das geht, aber nicht direkt.

%Vor%

Sie können keine %code% von Ihrer Funktion zurückgeben, aber Sie können sie extrahieren und sofort an eine andere Funktion übergeben, die %code% akzeptiert, wie gezeigt.

    
___
1
Antwort

Skolemisierung existentiell typisierter Ausdrücke

In Scala löst der folgende Ausdruck einen Typfehler aus: %Vor% Wie in SI-9899 und diesem Antwort , das ist korrekt nach der Spezifikation:    Ich denke, das funktioniert nach SLS 6.1: "Das Folgende   Skolemisierungsregel wird universel...
23.08.2016, 21:10
4
Antworten

Haskell: Heterogene Liste für Daten mit Phantomvariablen

Ich lerne gerade über existenzielle Quantifizierung, Phantomtypen und GADTs. Wie gehe ich vor, um eine heterogene Liste eines Datentyps mit einer Phantomvariablen zu erstellen? Zum Beispiel: %Vor% Funktionen wie unten sind OK: %Vor% Ich...
10.02.2015, 17:30
1
Antwort

Haskell Existential Typen

Ich versuche mein Gehirn um Haskells existenzielle Typen zu wickeln, und mein erstes Beispiel ist eine heterogene Liste von Dingen, die gezeigt werden können: %Vor% Nun scheint es mir, dass ich das nächste, was ich tun möchte Showable eine I...
13.08.2011, 13:59
2
Antworten

GADT vs Existentiell quantifizierte Typen (* forall *)

Man kann GADT verwenden, um Existentiell quantifizierte Typen auszudrücken. Ich sehe, dass GADT generischer ist - Datentyperweiterungen , Abschnitt Abschnitt 7.4.7 Wenn es besser ist Existentiell quantifizierte Typen zu verwenden,...
03.08.2014, 10:36
2
Antworten

Scala gibt Rückschlüsse auf existentielle Typen und Typmitglieder

Der folgende Codeabschnitt wird nicht kompiliert: %Vor% Es gibt den folgenden Kompilierungsfehler zurück: %Vor% Der folgende Code entspricht jedoch genau: %Vor% Ich habe hier zwei Fragen: Ich erwarte, dass das erste Stück Code k...
21.02.2015, 18:02
3
Antworten

Testen der Gleichheit zwischen zwei heterogenen Werten

Ich verwende die Erweiterung -XExistentialQuantification GHC, um einen heterogenen Container für Werte einer bestimmten Typklasse ( Shape ) zu erstellen: %Vor% Wenn alle Instanzen von Shape auch Instanzen von Eq sind, gibt es eine...
22.10.2012, 16:45
2
Antworten

Haskell-Funktion, die den existentiellen Typ zurückgibt

Ist es möglich, eine Haskell-Funktion zu schreiben, die einen parametrisierten Typ liefert, in dem der genaue Typparameter verborgen ist? I.e. etwas wie f :: T -> (exists a. U a) ? Der naheliegende Versuch: %Vor% kann nicht mit: kompil...
11.10.2015, 10:15