nydp 0.2.3 → 0.2.5
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/bin/nydp +1 -1
- data/lib/lisp/core-000.nydp +1 -0
- data/lib/lisp/core-010-precompile.nydp +15 -15
- data/lib/lisp/core-012-utils.nydp +6 -5
- data/lib/lisp/core-020-utils.nydp +20 -6
- data/lib/lisp/core-030-syntax.nydp +14 -16
- data/lib/lisp/core-035-flow-control.nydp +26 -8
- data/lib/lisp/core-040-utils.nydp +4 -15
- data/lib/lisp/core-041-string-utils.nydp +3 -3
- data/lib/lisp/core-043-list-utils.nydp +81 -16
- data/lib/lisp/core-045-dox-utils.nydp +2 -2
- data/lib/lisp/core-060-benchmarking.nydp +92 -27
- data/lib/lisp/tests/all-examples.nydp +20 -0
- data/lib/lisp/tests/any-examples.nydp +28 -0
- data/lib/lisp/tests/builtin-tests.nydp +3 -1
- data/lib/lisp/tests/collect-tests.nydp +10 -0
- data/lib/lisp/tests/curry-tests.nydp +7 -2
- data/lib/lisp/tests/error-tests.nydp +11 -0
- data/lib/lisp/tests/foundation-test.nydp +66 -0
- data/lib/lisp/tests/len-examples.nydp +1 -0
- data/lib/lisp/tests/list-gsub-examples.nydp +25 -0
- data/lib/lisp/tests/list-match-examples.nydp +40 -0
- data/lib/lisp/tests/list-tests.nydp +13 -0
- data/lib/lisp/tests/none-examples.nydp +16 -0
- data/lib/lisp/tests/parser-tests.nydp +4 -5
- data/lib/lisp/tests/quasiquote-examples.nydp +2 -0
- data/lib/lisp/tests/syntax-tests.nydp +3 -2
- data/lib/lisp/tests/tuples-examples.nydp +2 -2
- data/lib/nydp.rb +50 -18
- data/lib/nydp/assignment.rb +3 -1
- data/lib/nydp/builtin.rb +15 -13
- data/lib/nydp/builtin/error.rb +1 -1
- data/lib/nydp/builtin/handle_error.rb +8 -2
- data/lib/nydp/builtin/parse_in_string.rb +1 -1
- data/lib/nydp/builtin/plus.rb +4 -4
- data/lib/nydp/closure.rb +5 -1
- data/lib/nydp/compiler.rb +2 -3
- data/lib/nydp/cond.rb +134 -13
- data/lib/nydp/context_symbol.rb +4 -1
- data/lib/nydp/error.rb +8 -0
- data/lib/nydp/function_invocation.rb +46 -48
- data/lib/nydp/helper.rb +15 -0
- data/lib/nydp/interpreted_function.rb +10 -14
- data/lib/nydp/lexical_context.rb +13 -2
- data/lib/nydp/lexical_context_builder.rb +28 -13
- data/lib/nydp/pair.rb +35 -36
- data/lib/nydp/parser.rb +3 -0
- data/lib/nydp/runner.rb +4 -32
- data/lib/nydp/string_atom.rb +3 -2
- data/lib/nydp/symbol.rb +1 -1
- data/lib/nydp/symbol_lookup.rb +9 -1
- data/lib/nydp/truth.rb +1 -1
- data/lib/nydp/version.rb +1 -1
- data/lib/nydp/vm.rb +2 -2
- data/nydp.gemspec +1 -1
- data/spec/error_spec.rb +14 -4
- data/spec/hash_non_hash_behaviour_spec.rb +19 -12
- data/spec/hash_spec.rb +0 -13
- data/spec/pair_spec.rb +17 -3
- data/spec/spec_helper.rb +13 -1
- data/spec/symbol_spec.rb +1 -1
- metadata +9 -4
@@ -0,0 +1,16 @@
|
|
1
|
+
(examples-for none?
|
2
|
+
("nil when any items match"
|
3
|
+
(none? num? '(1 nil nil 4))
|
4
|
+
nil)
|
5
|
+
|
6
|
+
("nil for a non-nil atom"
|
7
|
+
(and (none? string? "really, all") t)
|
8
|
+
nil)
|
9
|
+
|
10
|
+
("t for nil"
|
11
|
+
(none? x1 nil)
|
12
|
+
t)
|
13
|
+
|
14
|
+
("t when all items are nil"
|
15
|
+
(and (none? x1 '(nil nil nil nil)) t)
|
16
|
+
t))
|
@@ -36,10 +36,9 @@
|
|
36
36
|
(parse "$this.that.zozo")
|
37
37
|
((dot-syntax (dollar-syntax || this) that zozo)))
|
38
38
|
|
39
|
-
|
40
|
-
("parses an expression"
|
39
|
+
("parses a list of expressions"
|
41
40
|
(parse "(foo bar \"hello, String\") 1 2 (3 t nil) nil")
|
42
|
-
((foo bar "hello, String") 1 2 (3 t nil))))
|
41
|
+
((foo bar "hello, String") 1 2 (3 t nil) nil)))
|
43
42
|
|
44
43
|
(examples-for parse-in-string
|
45
44
|
("parses a plain string"
|
@@ -67,5 +66,5 @@
|
|
67
66
|
13)
|
68
67
|
|
69
68
|
("reports parse errors gracefully"
|
70
|
-
(on-err "CAUGHT: ~
|
71
|
-
"CAUGHT: parse error: \"unterminated string\" in\n blah ~~(\"stri
|
69
|
+
(on-err "CAUGHT: ~(joinstr "\n" errors)" (parse-in-string (joinstr "" "blah ~~(\"stri...")))
|
70
|
+
"CAUGHT: parse error: \"unterminated string\" in\n blah ~~(\"stri...\nunterminated string" ))
|
@@ -4,7 +4,9 @@
|
|
4
4
|
("substitutes single variables" (let b 10 `(a ,b c)) (a 10 c))
|
5
5
|
("substitutes a list" (let b '(1 2 3) `(a ,@b c)) (a 1 2 3 c))
|
6
6
|
("substitutes a list at the end of a given list" (let b '(1 2 3) `(a ,b ,@b)) (a (1 2 3) 1 2 3))
|
7
|
+
("unquotes an improper tail" (let c 42 `(a b . ,c)) (a b . 42))
|
7
8
|
("more complicated substitution example" (with (d '(1 2 3) g '(x y z)) `(a (b c ,d (e f ,@g)))) (a (b c (1 2 3) (e f x y z))))
|
8
9
|
("peeks inside nested quotes" `(a b '(c ,(+ 1 2))) (a b '(c 3)))
|
9
10
|
("handles nested unquote-splicing" ``(a ,,@(list '+ 1 2) b) `((a ,(+ 1 2) b)))
|
11
|
+
("unquote-splices an improper tail" (let c '(1 2 3) `(a b . ,@c)) (a b 1 2 3))
|
10
12
|
("returns nested quasiquotes" `(a b `(c d ,(+ 1 2) ,,(+ 3 4))) (a b `(c d ,(+ 1 2) ,7))))
|
@@ -8,8 +8,9 @@
|
|
8
8
|
b)
|
9
9
|
|
10
10
|
("dislikes no-prefix"
|
11
|
-
(on-err
|
12
|
-
|
11
|
+
(on-err (joinstr "\n" errors)
|
12
|
+
(pre-compile '(:foo 1 2 3)))
|
13
|
+
"\"Irregular ': syntax: got (|| foo) : not prefix-syntax : in :foo\""))
|
13
14
|
|
14
15
|
(examples-for prefix-list
|
15
16
|
("one argument"
|
@@ -5,7 +5,7 @@
|
|
5
5
|
|
6
6
|
("returns single list for fewer than n items"
|
7
7
|
(tuples 4 '(a b) )
|
8
|
-
((a b
|
8
|
+
((a b)))
|
9
9
|
|
10
10
|
("returns exactly one list for exactly n items"
|
11
11
|
(tuples 5 '(a b c d e) )
|
@@ -13,4 +13,4 @@
|
|
13
13
|
|
14
14
|
("returns the given list split into sublist each having n items"
|
15
15
|
(tuples 3 '(a b c d e f g) )
|
16
|
-
((a b c) (d e f) (g
|
16
|
+
((a b c) (d e f) (g))))
|
data/lib/nydp.rb
CHANGED
@@ -4,6 +4,7 @@ require 'set'
|
|
4
4
|
module Nydp
|
5
5
|
class Namespace < Hash
|
6
6
|
end
|
7
|
+
|
7
8
|
def self.apply_function ns, function_name, *args
|
8
9
|
function = r2n(function_name.to_sym, ns).value
|
9
10
|
args = r2n args, ns
|
@@ -15,32 +16,63 @@ module Nydp
|
|
15
16
|
|
16
17
|
def self.reader txt ; Nydp::StringReader.new txt ; end
|
17
18
|
def self.eval_src ns, src_txt, name=nil ; eval_with Nydp::Runner, ns, src_txt, name ; end
|
18
|
-
def self.eval_src! ns, src_txt, name=nil ; eval_with Nydp::ExplodeRunner, ns, src_txt, name ; end
|
19
19
|
def self.eval_with runner, ns, src_txt, name ; runner.new(VM.new(ns), ns, reader(src_txt), nil, name).run ; end
|
20
20
|
def self.ms t1, t0 ; ((t1 - t0) * 1000).to_i ; end
|
21
21
|
|
22
|
+
def self.indent_message indent, msg
|
23
|
+
msg.split(/\n/).map { |line| "#{indent}#{line}" }.join("\n")
|
24
|
+
end
|
25
|
+
|
26
|
+
def self.handle_run_error e, indent=""
|
27
|
+
puts "#{indent}#{e.class.name}"
|
28
|
+
puts "#{indent_message indent, e.message}"
|
29
|
+
if e.cause
|
30
|
+
puts "#{indent}#{e.backtrace.first}"
|
31
|
+
puts "\n#{indent}Caused by:"
|
32
|
+
handle_run_error e.cause, "#{indent} "
|
33
|
+
else
|
34
|
+
e.backtrace.each do |b|
|
35
|
+
puts "#{indent}#{b}"
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
def self.toplevel
|
41
|
+
begin
|
42
|
+
yield
|
43
|
+
rescue StandardError => e
|
44
|
+
handle_run_error e
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
22
48
|
def self.repl options={ }
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
49
|
+
toplevel do
|
50
|
+
silent = options[:silent]
|
51
|
+
launch_time = Time.now
|
52
|
+
last_script_time = Time.now
|
53
|
+
puts "welcome to nydp #{options.inspect}" unless silent
|
54
|
+
reader = Nydp::ReadlineReader.new $stdin, "nydp > "
|
55
|
+
ns = build_nydp do |script|
|
56
|
+
this_script_time = Time.now
|
57
|
+
puts "script #{script} time #{ms this_script_time, last_script_time}ms" if options[:verbose]
|
58
|
+
last_script_time = this_script_time
|
59
|
+
end
|
60
|
+
load_time = Time.now
|
61
|
+
puts "nydp v#{Nydp::VERSION} repl ready in #{ms(load_time, launch_time)}ms" unless silent
|
62
|
+
puts "^D to exit" unless silent
|
63
|
+
return if options[:exit]
|
64
|
+
Nydp::Runner.new(VM.new(ns), ns, reader, $stdout, "<stdin>").run
|
31
65
|
end
|
32
|
-
load_time = Time.now
|
33
|
-
puts "repl ready in #{ms(load_time, launch_time)}ms"
|
34
|
-
puts "^D to exit"
|
35
|
-
Nydp::Runner.new(VM.new(ns), ns, reader, $stdout, "<stdin>").run
|
36
66
|
end
|
37
67
|
|
38
68
|
def self.tests *options
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
69
|
+
toplevel do
|
70
|
+
verbose = options.include?(:verbose) ? "t" : "nil"
|
71
|
+
puts "welcome to nydp : running tests"
|
72
|
+
reader = Nydp::StringReader.new "(run-all-tests #{verbose})"
|
73
|
+
ns = build_nydp
|
74
|
+
Nydp::Runner.new(VM.new(ns), ns, reader, nil, "<test-runner>").run
|
75
|
+
end
|
44
76
|
end
|
45
77
|
end
|
46
78
|
|
data/lib/nydp/assignment.rb
CHANGED
@@ -1,5 +1,7 @@
|
|
1
1
|
module Nydp
|
2
2
|
class AssignmentInstruction
|
3
|
+
attr_accessor :name
|
4
|
+
|
3
5
|
def initialize name
|
4
6
|
@name = name
|
5
7
|
end
|
@@ -30,7 +32,7 @@ module Nydp
|
|
30
32
|
end
|
31
33
|
|
32
34
|
def to_s
|
33
|
-
"
|
35
|
+
"(assign #{@instructions.cdr.car.name} #{@value_src.inspect})"
|
34
36
|
end
|
35
37
|
|
36
38
|
def inspect; to_s ; end
|
data/lib/nydp/builtin.rb
CHANGED
@@ -10,41 +10,43 @@ module Nydp::Builtin
|
|
10
10
|
|
11
11
|
def invoke_1 vm
|
12
12
|
builtin_invoke_1 vm
|
13
|
-
rescue
|
14
|
-
handle_error e
|
13
|
+
rescue StandardError => e
|
14
|
+
handle_error e
|
15
15
|
end
|
16
16
|
|
17
17
|
def invoke_2 vm, arg
|
18
18
|
builtin_invoke_2 vm, arg
|
19
|
-
rescue
|
20
|
-
handle_error e,
|
19
|
+
rescue StandardError => e
|
20
|
+
handle_error e, arg
|
21
21
|
end
|
22
22
|
|
23
23
|
def invoke_3 vm, arg_0, arg_1
|
24
24
|
builtin_invoke_3 vm, arg_0, arg_1
|
25
|
-
rescue
|
26
|
-
handle_error e,
|
25
|
+
rescue StandardError => e
|
26
|
+
handle_error e, arg_0, arg_1
|
27
27
|
end
|
28
28
|
|
29
29
|
def invoke_4 vm, arg_0, arg_1, arg_2
|
30
30
|
builtin_invoke_4 vm, arg_0, arg_1, arg_2
|
31
|
-
rescue
|
32
|
-
handle_error e,
|
31
|
+
rescue StandardError => e
|
32
|
+
handle_error e, arg_0, arg_1, arg_2
|
33
33
|
end
|
34
34
|
|
35
35
|
def invoke vm, args
|
36
36
|
builtin_invoke vm, args
|
37
|
-
rescue
|
38
|
-
handle_error e, args
|
37
|
+
rescue StandardError => e
|
38
|
+
handle_error e, *(args.to_a)
|
39
39
|
end
|
40
40
|
|
41
|
-
|
41
|
+
|
42
|
+
def handle_error e, *args
|
42
43
|
case e
|
43
44
|
when Nydp::Error
|
44
45
|
raise e
|
45
46
|
else
|
46
|
-
|
47
|
-
|
47
|
+
arg_msg = args.map { |a| " #{a.inspect}"}.join("\n")
|
48
|
+
new_msg = "Called #{self.inspect}\nwith args\n#{arg_msg}"
|
49
|
+
raise new_msg
|
48
50
|
end
|
49
51
|
end
|
50
52
|
|
data/lib/nydp/builtin/error.rb
CHANGED
@@ -4,6 +4,6 @@ class Nydp::Builtin::Error
|
|
4
4
|
# override #invoke on nydp/builtin/base because
|
5
5
|
# we don't want to inherit error handling
|
6
6
|
def builtin_invoke vm, args
|
7
|
-
raise Nydp::Error.new(args.inspect)
|
7
|
+
raise Nydp::Error.new(args.to_a.map(&:inspect).join("\n"), vm.last_error)
|
8
8
|
end
|
9
9
|
end
|
@@ -13,13 +13,19 @@ class Nydp::Builtin::HandleError
|
|
13
13
|
end
|
14
14
|
|
15
15
|
def execute vm
|
16
|
-
e = vm.unhandled_error
|
16
|
+
e = vm.last_error = vm.unhandled_error
|
17
17
|
vm.unhandled_error = nil
|
18
18
|
return unless e
|
19
19
|
|
20
20
|
vm.args = vm.args[0...vm_arg_array_size]
|
21
21
|
|
22
|
-
|
22
|
+
msgs = []
|
23
|
+
while e
|
24
|
+
msgs << e.message
|
25
|
+
e = e.cause
|
26
|
+
end
|
27
|
+
|
28
|
+
handler.invoke_2 vm, vm.r2n(msgs)
|
23
29
|
end
|
24
30
|
|
25
31
|
def to_s
|
@@ -7,7 +7,7 @@ class Nydp::Builtin::ParseInString
|
|
7
7
|
tokens = Nydp::Tokeniser.new Nydp::StringReader.new parsable
|
8
8
|
expr = parser.string(tokens, "", :eof)
|
9
9
|
vm.push_arg expr
|
10
|
-
rescue
|
10
|
+
rescue StandardError => e
|
11
11
|
new_msg = "parse error: #{e.message.inspect} in\n#{Nydp.indent_text parsable}"
|
12
12
|
raise Nydp::Error.new new_msg
|
13
13
|
end
|
data/lib/nydp/builtin/plus.rb
CHANGED
@@ -18,11 +18,11 @@ class Nydp::Builtin::Plus
|
|
18
18
|
end
|
19
19
|
|
20
20
|
def sum args, accum
|
21
|
-
|
22
|
-
accum
|
23
|
-
|
24
|
-
sum(args.cdr, (accum + args.car))
|
21
|
+
while args && !Nydp::NIL.is?(args)
|
22
|
+
accum += args.car
|
23
|
+
args = args.cdr
|
25
24
|
end
|
25
|
+
accum
|
26
26
|
end
|
27
27
|
|
28
28
|
def name ; "+" ; end
|
data/lib/nydp/closure.rb
CHANGED
@@ -4,6 +4,9 @@ module Nydp
|
|
4
4
|
|
5
5
|
def initialize ifn, context
|
6
6
|
@ifn, @context = ifn, context
|
7
|
+
# TODO don't create a closure where it's not needed (zero_arg functions), use parent context instead
|
8
|
+
# TODO see SymbolLookup for how to ensure variable references stay on track
|
9
|
+
# TODO see InterpretedFunction for where to not instantiate new LexicalContext
|
7
10
|
end
|
8
11
|
|
9
12
|
def invoke_1 vm
|
@@ -28,7 +31,8 @@ module Nydp
|
|
28
31
|
|
29
32
|
def nydp_type ; "fn" ; end
|
30
33
|
def to_s
|
31
|
-
"(closure #{context.
|
34
|
+
"(closure #{context.to_s} : #{ifn.to_s})"
|
32
35
|
end
|
36
|
+
def inspect ; to_s ; end
|
33
37
|
end
|
34
38
|
end
|
data/lib/nydp/compiler.rb
CHANGED
@@ -9,9 +9,8 @@ module Nydp
|
|
9
9
|
|
10
10
|
def self.compile expression, bindings
|
11
11
|
compile_expr expression, bindings
|
12
|
-
rescue
|
13
|
-
|
14
|
-
raise $!, new_msg, $!.backtrace
|
12
|
+
rescue StandardError => e
|
13
|
+
raise Nydp::Error.new "failed to compile expression:\n#{expression.inspect}"
|
15
14
|
end
|
16
15
|
|
17
16
|
def self.compile_expr expression, bindings
|
data/lib/nydp/cond.rb
CHANGED
@@ -1,23 +1,20 @@
|
|
1
1
|
module Nydp
|
2
2
|
class ExecuteConditionalInstruction
|
3
3
|
extend Helper
|
4
|
-
attr_reader :when_true, :when_false
|
5
4
|
|
6
5
|
def initialize when_true, when_false
|
7
6
|
@when_true, @when_false = when_true, when_false
|
8
7
|
end
|
9
8
|
|
10
9
|
def execute vm
|
11
|
-
|
12
|
-
vm.instructions.push (truth ? when_true : when_false)
|
13
|
-
vm.contexts.push vm.current_context
|
10
|
+
(Nydp::NIL.is?(vm.args.pop) ? @when_false : @when_true).execute vm
|
14
11
|
end
|
15
12
|
|
16
13
|
def inspect
|
17
|
-
"when_true:#{when_true.inspect}:when_false:#{when_false.inspect}"
|
14
|
+
"when_true:#{@when_true.inspect}:when_false:#{@when_false.inspect}"
|
18
15
|
end
|
19
16
|
def to_s
|
20
|
-
"#{when_true.
|
17
|
+
"#{@when_true.to_s} #{@when_false.to_s}"
|
21
18
|
end
|
22
19
|
end
|
23
20
|
|
@@ -33,26 +30,150 @@ module Nydp
|
|
33
30
|
def execute vm
|
34
31
|
vm.instructions.push conditional
|
35
32
|
vm.contexts.push vm.current_context
|
36
|
-
|
37
|
-
vm.contexts.push vm.current_context
|
33
|
+
condition.execute vm
|
38
34
|
end
|
39
35
|
|
40
36
|
def inspect
|
41
37
|
"cond:#{condition.inspect}:#{conditional.inspect}"
|
42
38
|
end
|
43
39
|
def to_s
|
44
|
-
"(cond #{condition.
|
40
|
+
"(cond #{condition.to_s} #{conditional.to_s})"
|
45
41
|
end
|
46
42
|
|
47
43
|
def self.build expressions, bindings
|
48
44
|
if expressions.is_a? Nydp::Pair
|
49
|
-
cond =
|
50
|
-
when_true =
|
51
|
-
when_false =
|
52
|
-
|
45
|
+
cond = Compiler.compile expressions.car, bindings
|
46
|
+
when_true = Compiler.compile expressions.cdr.car, bindings
|
47
|
+
when_false = Compiler.compile expressions.cdr.cdr.car, bindings
|
48
|
+
csig = sig(cond)
|
49
|
+
# puts cond_sig
|
50
|
+
# TODO : handle literal nil explicitly (if x y) -> #when_false is literal nil, we can hardcode that
|
51
|
+
# todo : handle "OR" explicitly -> (if x x y) -> when #cond equals #when_true, hardcode this case
|
52
|
+
case csig
|
53
|
+
when "LEX"
|
54
|
+
Cond_LEX.build(cond, when_true, when_false)
|
55
|
+
when "SYM"
|
56
|
+
Cond_SYM.new(cond, cons(when_true), cons(when_false))
|
57
|
+
else
|
58
|
+
new(cond, when_true, when_false)
|
59
|
+
end
|
53
60
|
else
|
54
61
|
raise "can't compile Cond: #{expr.inspect}"
|
55
62
|
end
|
56
63
|
end
|
57
64
|
end
|
65
|
+
|
66
|
+
class CondBase
|
67
|
+
extend Helper
|
68
|
+
include Helper
|
69
|
+
|
70
|
+
def initialize cond, when_true, when_false
|
71
|
+
@condition, @when_true, @when_false = cond, when_true, when_false
|
72
|
+
end
|
73
|
+
|
74
|
+
def inspect ; "cond:#{@condition.inspect}:#{@when_true.inspect}:#{@when_false.inspect}" ; end
|
75
|
+
def to_s ; "(cond #{@condition.to_s} #{@when_true.to_s} #{@when_false.to_s})" ; end
|
76
|
+
end
|
77
|
+
|
78
|
+
class Cond_LEX < CondBase
|
79
|
+
def execute vm
|
80
|
+
truth = !Nydp::NIL.is?(@condition.value vm.current_context)
|
81
|
+
vm.instructions.push (truth ? @when_true : @when_false)
|
82
|
+
vm.contexts.push vm.current_context
|
83
|
+
end
|
84
|
+
|
85
|
+
def self.build cond, when_true, when_false
|
86
|
+
tsig = sig(when_true)
|
87
|
+
fsig = sig(when_false)
|
88
|
+
cond_sig = "#{tsig}_#{fsig}"
|
89
|
+
|
90
|
+
# if (cond == when_true)
|
91
|
+
# OR_LEX.build cond, when_false
|
92
|
+
|
93
|
+
if (cond == when_true) && (fsig == "LIT")
|
94
|
+
OR_LEX_LIT.new cond, nil, when_false
|
95
|
+
elsif (cond == when_true) && (fsig == "LEX")
|
96
|
+
OR_LEX_LEX.new cond, nil, when_false
|
97
|
+
else
|
98
|
+
case cond_sig
|
99
|
+
when "LIT_LIT"
|
100
|
+
Nydp::Cond_LEX_LIT_LIT.new(cond, when_true.expression, when_false.expression)
|
101
|
+
when "LEX_LIT"
|
102
|
+
Nydp::Cond_LEX_LEX_LIT.new(cond, when_true, when_false.expression)
|
103
|
+
when "CND_LIT"
|
104
|
+
Nydp::Cond_LEX_CND_LIT.new(cond, when_true, when_false.expression)
|
105
|
+
else
|
106
|
+
Nydp::Cond_LEX.new(cond, cons(when_true), cons(when_false))
|
107
|
+
end
|
108
|
+
end
|
109
|
+
end
|
110
|
+
end
|
111
|
+
|
112
|
+
class OR_LEX_LIT < CondBase
|
113
|
+
def execute vm
|
114
|
+
value = @condition.value vm.current_context
|
115
|
+
vm.push_arg(!Nydp::NIL.is?(value) ? value : @when_false)
|
116
|
+
end
|
117
|
+
end
|
118
|
+
|
119
|
+
class OR_LEX_LEX < CondBase
|
120
|
+
def execute vm
|
121
|
+
value = @condition.value vm.current_context
|
122
|
+
vm.push_arg(!Nydp::NIL.is?(value) ? value : (@when_false.value vm.current_context))
|
123
|
+
end
|
124
|
+
end
|
125
|
+
|
126
|
+
# class OR_LEX < CondBase
|
127
|
+
# def execute vm
|
128
|
+
# value = @condition.value vm.current_context
|
129
|
+
# if !Nydp::NIL.is?(value)
|
130
|
+
# vm.push_arg value
|
131
|
+
# else
|
132
|
+
# @when_false.execute vm
|
133
|
+
# end
|
134
|
+
# end
|
135
|
+
|
136
|
+
# def self.build cond, when_false
|
137
|
+
# case sig(when_false)
|
138
|
+
# when "LIT"
|
139
|
+
# OR_LEX_LIT.new(cond, nil, when_false)
|
140
|
+
# when "LEX"
|
141
|
+
# OR_LEX_LEX.new(cond, nil, when_false)
|
142
|
+
# else
|
143
|
+
# OR_LEX.new(cond, nil, when_false)
|
144
|
+
# end
|
145
|
+
# end
|
146
|
+
# end
|
147
|
+
|
148
|
+
class Cond_LEX_LIT_LIT < CondBase # (def no (arg) (cond arg nil t))
|
149
|
+
def execute vm
|
150
|
+
truth = !Nydp::NIL.is?(@condition.value vm.current_context)
|
151
|
+
vm.push_arg(truth ? @when_true : @when_false)
|
152
|
+
end
|
153
|
+
end
|
154
|
+
|
155
|
+
class Cond_LEX_LEX_LIT < CondBase
|
156
|
+
def execute vm
|
157
|
+
truth = !Nydp::NIL.is?(@condition.value vm.current_context)
|
158
|
+
vm.push_arg(truth ? (@when_true.value vm.current_context) : @when_false)
|
159
|
+
end
|
160
|
+
end
|
161
|
+
|
162
|
+
class Cond_LEX_CND_LIT < CondBase
|
163
|
+
def execute vm
|
164
|
+
if !Nydp::NIL.is?(@condition.value vm.current_context)
|
165
|
+
@when_true.execute vm
|
166
|
+
else
|
167
|
+
vm.push_arg @when_false
|
168
|
+
end
|
169
|
+
end
|
170
|
+
end
|
171
|
+
|
172
|
+
class Cond_SYM < CondBase
|
173
|
+
def execute vm
|
174
|
+
truth = !Nydp::NIL.is?(@condition.value)
|
175
|
+
vm.instructions.push (truth ? @when_true : @when_false)
|
176
|
+
vm.contexts.push vm.current_context
|
177
|
+
end
|
178
|
+
end
|
58
179
|
end
|