Frage

Ich habe irgendwo gelesen, wo Rich Hickey sagte:

"Ich denke, dass Kontinuationen theoretisch ordentlich sein könnten, aber nicht in der Praxis"

Ich bin mit Clojure nicht vertraut.
1. Hat Clojure Kontinuationen?
2. Wenn nein, brauchen Sie keine Kontinuationen? Ich habe viele gute Beispiele gesehen, insbesondere von dieser Typ. Was ist die Alternative?
3. Wenn ja, gibt es eine Dokumentation?

War es hilfreich?

Lösung

Wenn Sie über Kontinuationen sprechen, müssen Sie zwischen zwei verschiedenen Arten von ihnen unterscheiden:

  • Erstklassige Kontinuationen-Fortsetzungsunterstützung, die tief in die Sprache (Schema oder Rubin) integriert ist. Clojure unterstützt erstklassige Kontinuationen nicht.

  • CPS-Passing-Stil (CPS)-CPS ist nur ein Codierungsstil, und jede Sprache, die anonyme Funktionen unterstützt, ermöglicht diesen Stil (der auch für Clojure gilt).

Beispiele:

-- Standard function
double :: Int -> Int
double x = 2 * x

-- CPS-function – We pass the continuation explicitly
doubleCPS :: Int -> (Int -> res) -> res
doubleCPS x cont = cont (2 * x)
; Call
print (double 2)

; Call CPS: Continue execution with specified anonymous function
double 2 (\res -> print res)

Lesen Fortsetzung auf Wikipedia.

Ich denke nicht, dass Kontinuationen für eine gute Sprache notwendig sind, aber insbesondere erstklassige Kontinuationen und CPs in funktionalen Sprachen wie Haskell können sehr nützlich sein (nützlich (Intelligentes Backtracking -Beispiel).

Andere Tipps

Ich habe einen Clojure-Port von CL-Cont geschrieben, der Common Lisp-Kontinuationen verleiht.

https://github.com/swannodette/delimc

Ist die Fortsetzung ein notwendiges Merkmal in einer Sprache?

Nein, viele Sprachen haben keine Fortschritte.

Wenn nein, brauchen Sie keine Fortschritte? Ich habe viele gute Beispiele gesehen, besonders von diesem Kerl. Was ist die Alternative?

Ein Anrufstack

Abstrakte Kontinuationen

Kontinuationen sind ein abstrakter Begriff, der zur Beschreibung der Kontrollflusssemantik verwendet wird. In diesem Sinne existieren beide und existieren nicht (denken Sie daran, sie sind abstrakt) in jeder Sprache, die Kontrollbetreiber (wie jede vollständige Sprache muss), auf die gleiche Weise, die sowohl Zahlen (als abstrakt existieren nicht (als konkrete Einheiten).

Kontinuationen beschreiben Kontrolleffekte wie Funktionsaufruf/Rückgabe, Ausnahmebehandlung und sogar Gotos. Eine gut gegründete Sprache wird unter anderem mit Abstraktionen entwickelt, die auf Kontinuationen (z. B. Ausnahmen) basieren. (Das heißt, eine begründete Sprache besteht aus Kontrollbetreibern, die mit Berücksichtigung von Kontinuationen entworfen wurden nur Steuern Sie die Abstraktion, sodass Benutzer ihre eigenen Abstraktionen oben erstellen können.)

First -Class -Kontinuationen

Wenn der Begriff einer Fortsetzung ist umgewaltet Als erstklassiges Objekt in einer Sprache haben wir dann ein Tool, auf dem alle Arten von Kontrolleffekten erstellt werden können. Wenn beispielsweise eine Sprache erstklassige Kontinuationen, aber keine Ausnahmen hat, können wir Ausnahmen zusätzlich zu den Kontinuationen konstruieren.

Probleme mit erstklassigen Kontinuationen

Während erstklassige Kontinuationen in vielen Fällen ein leistungsstarkes und nützliches Instrument sind, gibt es auch einige Nachteile, um sie in einer Sprache aufzudecken:

  • Unterschiedliche Abstraktionen, die auf den Kontinuationen aufgebaut sind, können bei Zusammensetzung zu unerwartetem / unintuitivem Verhalten führen. Zum Beispiel a finally Block kann übersprungen werden, wenn ich eine Fortsetzung verwende, um eine Berechnung abzubrechen.
  • Wenn die aktuelle Fortsetzung jederzeit angefordert werden kann, muss die Sprachlaufzeit so strukturiert sein, dass die aktuelle Fortsetzung der Datenstruktur jederzeit eine Datenstrukturdarstellung erzeugt werden kann. Dies stellt die Laufzeit für ein Merkmal ein, das zum Guten oder Schlechten oft als "exotisch" angesehen wird. Wenn die Sprache gehostet wird (z. B. Clojure wird auf der JVM gehostet), muss diese Darstellung in das von der Hosting -Plattform bereitgestellte Framework passen können. Es kann auch andere Merkmale geben, die eine Sprache beibehalten möchte (z. B. C -Interop), die den Lösungsraum einschränken. Probleme wie diese erhöhen das Potenzial einer "Behinderung Nichtübereinstimmung" und können die Entwicklung einer Performantenlösung stark erschweren.

Hinzufügen von erstklassigen Kontinuationen zu einer Sprache

Durch die Metaprogrammierung ist es möglich, eine Sprache zu unterstützen. Im Allgemeinen beinhaltet dieser Ansatz die Umwandlung des Code in den CPS (Continuation-Passing-Stil), bei dem die aktuelle Fortsetzung als explizites Argument für jede Funktion weitergegeben wird.

Zum Beispiel David Nolen's Abgrenzung Die Bibliothek implementiert abgrenzte Kontinuationen von Teilen eines Clojure -Programms durch eine Reihe von Makro -Transformationen. In ähnlicher Weise habe ich verfasst Riemenscheibe.cps, Dies ist ein Makro-Compiler, der Code in CPS umwandelt, zusammen mit einer Laufzeitbibliothek, um mehr Kern-Clojure-Funktionen (z. B. Ausnahmeregelung) sowie mit dem nativen Clojure-Code zu unterstützen.

Ein Problem mit diesem Ansatz ist, wie Sie mit der Grenze zwischen dem nativen Code (Clojure) und dem transformierten (CPS) Code umgehen. Insbesondere, da Sie die Fortsetzung des nativen Code nicht erfassen können, müssen Sie entweder mit der Basissprache unterhalten (oder irgendwie einschränken) oder den Benutzer belasten, um sicherzustellen, dass der Kontext eine Fortsetzung ermöglicht, die sie erfassen möchten, tatsächlich zu erfassen. gefangen genommen werden.

Pulley.cps tendiert zu letzterem, obwohl einige Versuche unternommen wurden, um dem Benutzer dies zu ermöglichen, dies zu verwalten. Beispielsweise ist es möglich, CPS -Code zu verhindern, um in nativen Code aufzurufen. Darüber hinaus wird ein Mechanismus zur Verfügung gestellt, um CPS -Versionen bestehender nativer Funktionen zu liefern.

In einer Sprache mit einem ausreichend starken Typsystem (z. B. Haskell) ist es möglich, das Typsystem zu verwenden, um Berechnungen zu verkörpern, die Kontrollvorgänge (dh Kontinuationen) aus funktionell reinem Code verwenden können.

Zusammenfassung

Wir haben jetzt die Informationen, die erforderlich sind, um Ihre drei Fragen direkt zu beantworten:

  1. Clojure unterstützt aufgrund praktischer Überlegungen keine erstklassigen Kontinuationen.
  2. Alle Sprachen basieren auf Kontinuationen im theoretischen Sinne, aber nur wenige Sprachen enthüllen Kontinuationen als erstklassige Objekte. Es ist jedoch möglich, jede Sprache über, z. B. eine Transformation in CPS zu verleihen.
  3. Schauen Sie sich die Dokumentation an Abgrenzung und/oder Riemenscheibe.cps.

Eine häufige Verwendung von Kontinuationen besteht in der Implementierung von Kontrollstrukturen für: Rückkehr aus einer Funktion, Ausbruch aus einer Schleife, Ausnahmebehandlung usw. Die meisten Sprachen (wie Java, C ++ usw.) liefern diese Funktionen als Teil der Kernsprache. Einige Sprachen nicht (zB: Schema). Stattdessen enthüllen diese Sprachen Kontinuatiionen als erstklassige Objekte und lassen den Programmierer neue Kontrollstrukturen definieren. Somit sollte das Schema als Programmiersprache angesehen werden, nicht als eine vollständige Sprache für sich.

In Clojure müssen wir fast nie direkte Kontinuationen verwenden, da fast alle Kontrollstrukturen durch die Sprach-/VM -Kombination bereitgestellt werden. Dennoch können First -Class -Kontinuationen ein leistungsstarkes Werkzeug in den Händen des zuständigen Programmierers sein. Insbesondere im Schema sind Kontinuationen besser als die äquivalenten Gegenstücke in anderen Sprachen (wie das SETJMP/LONGJMP -Paar in C). Dies Artikel enthält weitere Details dazu.

Übrigens wird es interessant sein zu wissen, wie reich an Hickey seine Meinung über Fortsetzung rechtfertigt. Irgendwelche Links dafür?

Clojure (oder besser gesagt clojure.contrib.monads) hat eine fortlaufende Monate; Hier ist ein Artikel, der seine Verwendung und Motivation beschreibt.

Nun ... Clojure's -> implementiert, was Sie suchen ... aber stattdessen mit einem Makro

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top