Aşağıdaki Shift/Reset öğreticisini inceliyorum: http://www.is.ocha.ac.jp/~asai/cw2011tutorial/main-e.pdf.Scala devamlılık eklentisi iç içe kaymayı destekliyor mu?
Şu ana kadar, OchaCaml örneklerini Scala'ya çevirirken oldukça iyi sonuçlar aldım (2.11 numaralı bölüme kadar). Ama şimdi bir duvara çarpmış gibiyim. Bir lambda ifade A-normalleştirmek için
(* a_normal : term_t => term_t *)
let rec a_normal term = match term with
Var (x) -> Var (x)
| Lam (x, t) -> Lam (x, reset (fun() -> a_normal t))
| App (t1, t2) ->
shift (fun k ->
let t = gensym() in (* generate fresh variable *)
App (Lam (t, (* let expression *)
k (Var (t))), (* continue with new variable *)
App (a_normal t1, a_normal t2))) ;;
işlevi beklenir: - (Bence bu OchaCaml olan) Asai/KISELYOV kağıt kod aşağıdaki özyinelemeli işlevi tanımlar.
// section 2.11
object ShiftReset extends App {
sealed trait Term
case class Var(x: String) extends Term
case class Lam(x: String, t: Term) extends Term
case class App(t1: Term, t2: Term) extends Term
val gensym = {
var i = 0
() => { i += 1; "t" + i }
}
def a_normal(t: Term): [email protected][Term] = t match {
case Var(x) => Var(x)
case Lam(x, t) => Lam(x, reset(a_normal(t)))
case App(t1, t2) => shift{ (k:Term=>Term) =>
val t = gensym()
val u = Lam(t, k(Var(t)))
val v = App(a_normal(t1), a_normal(t2))
App(u, v): Term
}
}
}
aşağıdaki derleme hatası alıyorum: Bu benim Scala çevirisidir Eklenti iç içe shift
başa çıkamaz bana anlatıyor düşünüyorum
found : ShiftReset.Term @scala.util.continuations.cpsSynth
@scala.util.continuations.cpsParam[ShiftReset.Term,ShiftReset.Term]
required: ShiftReset.Term
case App(t1, t2) => shift{ (k:Term=>Term) =>
^
one error found
... bir yolu var mı kodu derlemek (gözden kaçan temel bir hata mı yoksa bazı geçici çözümler mi)? Desen eşlemesini eğer/else if/else değerine çevirmeyi ve daha fazla yerel değişkenleri tanıtmayı denedim ama aynı hatayı aldım.
Alternatif olarak, ben daha fazla şans Haskell ve Kont monad (+ shift/here reset) kullanarak ya da orada yuvalanmış vardiya ile sınırlama aynı tip olacak olurdu? Haskell etiketini de ekliyorum, çünkü öğreticinin geri kalanından geçmek için Haskell'e geçmem.
Düzenleme: Sürdürme eklentisinin hangi çizgiyle başa çıkamayacağını ve nasıl düzeltileceğini anlayan James'e teşekkürler. (Ben devamı aslında yönetir henüz nasıl kavramak da) kağıt telaffuz edilmesi çıktısını almak
def format(t: Term): String = t match {
case Var(x) => s"$x"
case Lam(x, t) => s"\\$x.${format(t)}"
case App(Lam(x, t1), t2) => s"let $x = ${format(t2)} in ${format(t1)}"
case App(Var(x), Var(y)) => s"$x$y"
case App(Var(x), t2) => s"$x (${format(t2)})"
case App(t1, t2) => s"(${format(t1)}) (${format(t2)})"
}
:
sCombinator:
\x.\y.\z.(xz) (yz)
reset{a_normal(sCombinator)}:
\x.\y.\z.let t1 = xz in let t2 = yz in let t3 = t1t2 in t3
İlginç, koduma geri dönmem gerekecek ve sadece App çıkışı çekip çıkarmayacağımı kontrol etmem gerekiyor. – huynhjl
Teşekkür ederim, şimdi çalışıyor! Şimdi bu zihin bükme kodunun gerçekten ne yaptığını düşünmek zorundayım. – huynhjl