Frage

Ich bin neu in ocaml und tryin eine Fortsetzung vorbei Style-Funktion zu schreiben, aber ganz verwirrt, welchen Wert ich in zusätzliches Argument übergeben müssen auf k

zum Beispiel, kann ich eine rekursive Funktion schreiben, die true zurückgibt, wenn alle Elemente der Liste selbst ist, sonst false.

so sein wie

let rec even list = .... 

auf CPS, ich weiß, ich brauche ein Argument hinzufügen Funktion zu übergeben so wie

let rec evenk list k = .... 

aber ich habe keine Ahnung, wie man mit dieser k umgehen und wie funktioniert das genau Arbeit

zum Beispiel für diese Funktion auch, Umgebung sieht aus wie

val evenk : int list -> (bool -> ’a) -> ’a = <fun>

evenk [4; 2; 12; 5; 6] (fun x -> x)  (* output should give false *)
War es hilfreich?

Lösung

Die Fortsetzung k ist eine Funktion, die das Ergebnis von evenk und führt „der Rest der Berechnung“ nimmt und die „Antwort“. Was die Frage beantworten hat und was Sie unter „dem Rest der Berechnung“ hängt davon ab, was Sie verwenden CPS für . CPS ist in der Regel kein Selbstzweck, sondern ist mit einem Zweck im Auge getan. Zum Beispiel in CPS Form ist es sehr einfach Bekämpfer oder zu optimieren Endrekursion zu implementieren. Ohne zu wissen, was Sie versuchen zu erreichen, ist es schwer, Ihre Frage zu beantworten.

Für das, was ist es wert, wenn Sie versuchen einfach, von den direkten Stil Fortsetzung Umgehung Stil zu konvertieren, und alles, was Sie über Pflege ist der Wert der Antwort, vorbei an die Identitätsfunktion als die Fortsetzung über rechts ist.

Ein guter nächster Schritt wäre evenk zu implementieren CPS verwenden. Ich werde ein einfacheres Beispiel tun. Wenn ich die direkte Stil Funktion

let muladd x i n = x + i * n

und wenn ich CPS Primitiven mulk und addk annehmen, kann ich schreiben

let muladdk x i n k =
  let k' product = addk x product k in
  mulk i n k'

Und Sie werden sehen, dass die mulptiplication zuerst getan wird, dann ist es „fährt fort“ mit k', die das Add tut, und schließlich, dass continues mit k, die Rückkehr an den Anrufer. Die Schlüsselidee ist, dass ich im Körper muladdk eine frische Fortsetzung k' zugeordnet, die in der Multiply-Add-Funktion für einen Zwischenpunkt steht. Um Ihre evenk Arbeit machen Sie mindestens eine solche Fortsetzung zuweisen müssen.

Ich hoffe, das hilft.

Andere Tipps

Jedes Mal, wenn ich mit CPS gespielt habe, die Sache auf die Fortsetzung vergangen ist genau das, was Sie in der Regel an den Anrufer zurückkommen würden. In diesem einfachen Fall eine schöne „Intuition Schmiermittel“ ist die Fortsetzung „Rückkehr“ zu nennen.

let rec even list return =
  if List.length list = 0
    then return true
    else if List.hd list mod 2 = 1
      then return false
      else even (List.tl list) return;;

let id = fun x -> x;;

Beispiel Nutzung:. "Even [2; 4; 6; 8] id ;;"

Da Sie den Aufruf von evenk korrekt (mit der Identitätsfunktion -, dass die Fortsetzung-Passing-Stil wieder in dem normalen Stil Umwandlung) haben, gehe ich davon aus, dass die Schwierigkeit bei der Definition evenk ist

.

k ist die Fortsetzungsfunktion den Rest der Berechnung darstellt, und einen Endwert Herstellung, wie Norman gesagt. Also, was Sie tun müssen, ist das Ergebnis der v von even zu berechnen und das Ergebnis an k passieren, Rückkehr k v anstatt nur v.

Sie mögen das Ergebnis Ihrer Funktion als Input geben, als ob es nicht mit Fortsetzung vorbei Stil geschrieben wurde.

Hier ist Ihre Funktion, die prüft, ob eine Liste nur noch ganze Zahlen hat:

(* val even_list : int list -> bool *)
let even_list input = List.for_all (fun x -> x mod 2=0) input

Nun wollen wir schreiben es mit einer Fortsetzung cont:

(* val evenk : int list -> (bool -> 'a) -> 'a *)
let evenk input cont =
  let result = even_list input in
  (cont result)

Sie berechnen das Ergebnis Ihrer Funktion und übergeben resultto die Fortsetzung ...

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