From c2577a665818b14adb7b0a0c1eaf326144d4447d Mon Sep 17 00:00:00 2001 From: Eduardo Julian Date: Sun, 15 Sep 2019 23:17:55 -0400 Subject: Added the ":let" macro to enable reuse of type fragments in larger types. --- lux-mode/lux-mode.el | 3 ++- stdlib/source/lux.lux | 23 +++++++++++++++++++---- stdlib/source/lux/control/function/memo.lux | 3 ++- 3 files changed, 23 insertions(+), 6 deletions(-) diff --git a/lux-mode/lux-mode.el b/lux-mode/lux-mode.el index 8f66e2717..ca8178c6a 100644 --- a/lux-mode/lux-mode.el +++ b/lux-mode/lux-mode.el @@ -245,7 +245,7 @@ Called by `imenu--generic-function'." (control//contract (altRE "pre" "post")) ;; Type (type//syntax (altRE "|" "&" "->" "All" "Ex" "Rec" "primitive" "\\$" "type")) - (type//checking (altRE ":" ":coerce" ":~" ":assume" ":of" ":cast" ":share" ":by-example" ":hole")) + (type//checking (altRE ":" ":coerce" ":let" ":~" ":assume" ":of" ":cast" ":share" ":by-example" ":hole")) (type//abstract (altRE "abstract:" ":abstraction" ":representation" ":transmutation" "\\^:representation")) (type//unit (altRE "unit:" "scale:")) (type//poly (altRE "poly:" "derived:")) @@ -433,6 +433,7 @@ This function also returns nil meaning don't specify the indentation." (define-lux-indent (function 'defun) (let 'defun) + (:let 'defun) (case 'defun) (do 'defun) (exec 'defun) diff --git a/stdlib/source/lux.lux b/stdlib/source/lux.lux index 9cc2254b2..6042457fe 100644 --- a/stdlib/source/lux.lux +++ b/stdlib/source/lux.lux @@ -1618,7 +1618,7 @@ (wrap (#Cons y ys)))} xs))) -(def:''' (monad/fold m f y xs) +(def:''' (monad@fold m f y xs) #Nil ## (All [m a b] ## (-> (Monad m) (-> a b (m b)) b (List a) (m b))) @@ -1635,7 +1635,7 @@ (#Cons x xs') (do m [y' (f x y)] - (monad/fold m f y' xs'))} + (monad@fold m f y' xs'))} xs))) (macro:' #export (if tokens) @@ -1770,7 +1770,7 @@ [lastO (untemplate lastI)] (wrap (form$ (list (tag$ ["lux" "Cons"]) (tuple$ (list lastO (tag$ ["lux" "Nil"])))))))} lastI)] - (monad/fold meta-monad + (monad@fold meta-monad (function' [leftI rightO] ({[_ (#Form (#Cons [[_ (#Identifier ["" "~+"])] (#Cons [spliced #Nil])]))] (let' [[[_module-name _ _] _] spliced] @@ -4259,7 +4259,7 @@ tags) pattern (tuple$ (list@map identifier$ locals))] (do meta-monad - [enhanced-target (monad/fold meta-monad + [enhanced-target (monad@fold meta-monad (function (_ [m-local m-type] enhanced-target) (do meta-monad [m-structure (resolve-type-tags m-type)] @@ -5881,3 +5881,18 @@ [no yes] [off on] ) + +(macro: #export (:let tokens) + (case tokens + (^ (list [_ (#Tuple bindings)] bodyT)) + (if (multiple? 2 (list@size bindings)) + (return (list (` (..with-expansions [(~+ (|> bindings + ..as-pairs + (list@map (function (_ [localT valueT]) + (list localT (` (..as-is (~ valueT)))))) + (list@fold list@compose (list))))] + (~ bodyT))))) + (..fail ":let requires an even number of parts")) + + _ + (..fail "Wrong syntax for :let"))) diff --git a/stdlib/source/lux/control/function/memo.lux b/stdlib/source/lux/control/function/memo.lux index 975d03148..253506508 100644 --- a/stdlib/source/lux/control/function/memo.lux +++ b/stdlib/source/lux/control/function/memo.lux @@ -38,7 +38,8 @@ (def: #export (open memo) {#.doc (doc "Memoization where the memoized results can be re-used accross invocations.")} (All [i o] - (-> (Memo i o) (-> [(Dictionary i o) i] [(Dictionary i o) o]))) + (:let [Memory (Dictionary i o)] + (-> (Memo i o) (-> [Memory i] [Memory o])))) (let [memo (//.mixin (//.inherit ..memoization (//.from-recursive memo)))] (function (_ [memory input]) (|> input memo (state.run memory))))) -- cgit v1.2.3