rubylisp 1.0.2 → 1.0.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/rubylisp/builtins.rb +7 -0
- data/lib/rubylisp/cons_cell.rb +1 -0
- data/lib/rubylisp/prim_special_forms.rb +35 -2
- metadata +1 -1
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 766ad09a55015bc092208b72f53402b9d937449a
|
4
|
+
data.tar.gz: 3861fd772f1f62324bf636387c5cc8ba73ce89a6
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: ec857ef3a5c1c82446acf3dffd9a0a90c2b355bf528b2c50e8aeb879b6eeeffd14566fa28bdbcedd272da3de746da3da6f503fecaa831fa08169330ad07c634c
|
7
|
+
data.tar.gz: cebd6a7be2904d8f7390d5bd05162b5d92e7092fba83ee73e76945042c493674704af1f4aaad734fb215f78b2b72f7ad948e44d5cb12f9f8d31436ab5d4d7dea
|
data/lib/rubylisp/builtins.rb
CHANGED
data/lib/rubylisp/cons_cell.rb
CHANGED
@@ -348,9 +348,9 @@ module Lisp
|
|
348
348
|
end
|
349
349
|
|
350
350
|
|
351
|
-
def self.
|
351
|
+
def self.common_let_impl(args, env)
|
352
352
|
bindings = args.car || Lisp::ConsCell.new
|
353
|
-
return Lisp::Debug.process_error("let requires a list of bindings as it's
|
353
|
+
return Lisp::Debug.process_error("let requires a list of bindings as it's first argument", env) unless bindings.list?
|
354
354
|
local_frame = EnvironmentFrame.extending(env, "let")
|
355
355
|
local_frame.previous = env
|
356
356
|
do_let_bindings(bindings, env, local_frame)
|
@@ -358,6 +358,39 @@ module Lisp
|
|
358
358
|
end
|
359
359
|
|
360
360
|
|
361
|
+
def self.named_let_impl(args, env)
|
362
|
+
name = args.car
|
363
|
+
bindings = args.cadr || Lisp::ConsCell.new
|
364
|
+
binding_names = bindings.to_a.map {|b| b.car}
|
365
|
+
return Lisp::Debug.process_error("named let requires a list of bindings as it's second argument", env) unless bindings.list?
|
366
|
+
body = args.cddr
|
367
|
+
local_frame = EnvironmentFrame.extending(env, "let-#{name.to_s}")
|
368
|
+
local_frame.previous = env
|
369
|
+
do_let_bindings(bindings, env, local_frame)
|
370
|
+
Lisp.named_let_stack.push(name)
|
371
|
+
while true
|
372
|
+
new_values = catch :named_let_application do
|
373
|
+
result = body.evaluate_each(local_frame)
|
374
|
+
Lisp.named_let_stack.pop
|
375
|
+
return result
|
376
|
+
end
|
377
|
+
return Lisp::Debug.process_error("named let call requires the same number of values as bindings", env) unless binding_names.length == new_values.length
|
378
|
+
binding_names.zip(new_values) do |binding_pair|
|
379
|
+
local_frame.bind_locally(binding_pair[0], binding_pair[1])
|
380
|
+
end
|
381
|
+
end
|
382
|
+
end
|
383
|
+
|
384
|
+
|
385
|
+
def self.let_impl(args, env)
|
386
|
+
if args.car.symbol?
|
387
|
+
named_let_impl(args, env)
|
388
|
+
else
|
389
|
+
common_let_impl(args, env)
|
390
|
+
end
|
391
|
+
end
|
392
|
+
|
393
|
+
|
361
394
|
def self.letstar_impl(args, env)
|
362
395
|
bindings = args.car || Lisp::ConsCell.new
|
363
396
|
return Lisp::Debug.process_error("let requires a list of bindings as it's firest argument", env) unless bindings.list?
|