Fix closure bug.
This commit is contained in:
parent
a5914076b0
commit
3b5e91c1bb
|
@ -5,6 +5,7 @@
|
||||||
[ludus.ast :as ast]
|
[ludus.ast :as ast]
|
||||||
[ludus.prelude :as prelude]
|
[ludus.prelude :as prelude]
|
||||||
[ludus.data :as data]
|
[ludus.data :as data]
|
||||||
|
[ludus.show :as show]
|
||||||
[clojure.pprint :as pp]))
|
[clojure.pprint :as pp]))
|
||||||
|
|
||||||
;; right now this is not very efficient:
|
;; right now this is not very efficient:
|
||||||
|
@ -155,20 +156,21 @@
|
||||||
(= (::data/type lfn) ::data/clj) (apply (:body lfn) (next tuple))
|
(= (::data/type lfn) ::data/clj) (apply (:body lfn) (next tuple))
|
||||||
|
|
||||||
(= (::data/type lfn) ::data/fn)
|
(= (::data/type lfn) ::data/fn)
|
||||||
(let [clauses (:clauses lfn)]
|
(let [clauses (:clauses lfn)
|
||||||
|
closed-over (:ctx lfn)]
|
||||||
(loop [clause (first clauses)
|
(loop [clause (first clauses)
|
||||||
clauses (rest clauses)]
|
clauses (rest clauses)]
|
||||||
(if clause
|
(if clause
|
||||||
(let [pattern (:pattern clause)
|
(let [pattern (:pattern clause)
|
||||||
body (:body clause)
|
body (:body clause)
|
||||||
new-ctx (volatile! {::parent ctx})
|
fn-ctx (volatile! {::parent closed-over})
|
||||||
match? (match pattern tuple new-ctx)
|
match? (match pattern tuple fn-ctx)
|
||||||
success (:success match?)
|
success (:success match?)
|
||||||
clause-ctx (:ctx match?)]
|
clause-ctx (:ctx match?)]
|
||||||
(if success
|
(if success
|
||||||
(do
|
(do
|
||||||
(vswap! new-ctx #(merge % clause-ctx))
|
(vswap! fn-ctx #(merge % clause-ctx))
|
||||||
(interpret-ast body new-ctx))
|
(interpret-ast body fn-ctx))
|
||||||
(recur (first clauses) (rest clauses))))
|
(recur (first clauses) (rest clauses))))
|
||||||
|
|
||||||
(throw (ex-info "Match Error: No match found" {:fn-name (:name lfn)})))))
|
(throw (ex-info "Match Error: No match found" {:fn-name (:name lfn)})))))
|
||||||
|
@ -218,10 +220,12 @@
|
||||||
(if (= name ::ast/anon)
|
(if (= name ::ast/anon)
|
||||||
{::data/type ::data/fn
|
{::data/type ::data/fn
|
||||||
:name name
|
:name name
|
||||||
:clauses clauses}
|
:clauses clauses
|
||||||
|
:ctx ctx}
|
||||||
(let [fn {::data/type ::data/fn
|
(let [fn {::data/type ::data/fn
|
||||||
:name name
|
:name name
|
||||||
:clauses clauses}]
|
:clauses clauses
|
||||||
|
:ctx ctx}]
|
||||||
(if (contains? @ctx name)
|
(if (contains? @ctx name)
|
||||||
(throw (ex-info (str "Name " name " is already bound") {}))
|
(throw (ex-info (str "Name " name " is already bound") {}))
|
||||||
(do
|
(do
|
||||||
|
@ -397,10 +401,18 @@
|
||||||
(println (ex-message e))
|
(println (ex-message e))
|
||||||
(pp/pprint (ex-data e)))))
|
(pp/pprint (ex-data e)))))
|
||||||
|
|
||||||
(comment
|
(do
|
||||||
|
|
||||||
(def source "
|
(def source "
|
||||||
|
|
||||||
|
let foo = {
|
||||||
|
let x = :f00
|
||||||
|
|
||||||
|
fn foo () -> x
|
||||||
|
}
|
||||||
|
|
||||||
|
foo ()
|
||||||
|
|
||||||
")
|
")
|
||||||
|
|
||||||
(println "")
|
(println "")
|
||||||
|
@ -412,7 +424,8 @@
|
||||||
(scanner/scan)
|
(scanner/scan)
|
||||||
(parser/parse)
|
(parser/parse)
|
||||||
(interpret-safe)
|
(interpret-safe)
|
||||||
(pp/pprint)))
|
(show/show)
|
||||||
|
(println)))
|
||||||
|
|
||||||
(comment "
|
(comment "
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue
Block a user