diff options
Diffstat (limited to 'ps/step3_env.ps')
| -rw-r--r-- | ps/step3_env.ps | 42 |
1 files changed, 24 insertions, 18 deletions
diff --git a/ps/step3_env.ps b/ps/step3_env.ps index 49d37c4..e94f92c 100644 --- a/ps/step3_env.ps +++ b/ps/step3_env.ps @@ -19,15 +19,21 @@ %(eval_ast: ) print ast == ast _symbol? { %if symbol env ast env_get - }{ ast _list? { %elseif list + }{ ast _sequential? { %elseif list or vector [ - ast { + ast /data get { %forall items env EVAL } forall - ] + ] ast _list? { _list_from_array }{ _vector_from_array } ifelse + }{ ast _hash_map? { %elseif list or vector + << + ast /data get { %forall entries + env EVAL + } forall + >> _hash_map_from_dict }{ % else ast - } ifelse } ifelse + } ifelse } ifelse } ifelse end } def /EVAL { 8 dict begin @@ -38,20 +44,20 @@ end } def ast _list? not { %if not a list ast env eval_ast }{ %else apply the list - /a0 ast 0 get def + /a0 ast 0 _nth def /def! a0 eq { %if def! - /a1 ast 1 get def - /a2 ast 2 get def + /a1 ast 1 _nth def + /a2 ast 2 _nth def env a1 a2 env EVAL env_set }{ /let* a0 eq { %if let* - /a1 ast 1 get def - /a2 ast 2 get def - /let_env env [ ] [ ] env_new def - 0 2 a1 length 1 sub { %for each pair + /a1 ast 1 _nth def + /a2 ast 2 _nth def + /let_env env null null env_new def + 0 2 a1 _count 1 sub { %for each pair /idx exch def let_env - a1 idx get - a1 idx 1 add get let_env EVAL + a1 idx _nth + a1 idx 1 add _nth let_env EVAL env_set pop % discard the return value } for @@ -72,15 +78,15 @@ end } def % repl -/repl_env null [ ] [ ] env_new def +/repl_env null null null env_new def /REP { READ repl_env EVAL PRINT } def /_ref { repl_env 3 1 roll env_set pop } def -(+) { dup 0 get exch 1 get add } _ref -(-) { dup 0 get exch 1 get sub } _ref -(*) { dup 0 get exch 1 get mul } _ref -(/) { dup 0 get exch 1 get idiv } _ref +(+) { dup 0 _nth exch 1 _nth add } _ref +(-) { dup 0 _nth exch 1 _nth sub } _ref +(*) { dup 0 _nth exch 1 _nth mul } _ref +(/) { dup 0 _nth exch 1 _nth idiv } _ref { % loop (user> ) _readline |
