Simplifying swap. Also allowed the chaining of dictionary definitions.

This commit is contained in:
fogus 2010-09-09 15:19:52 -04:00
parent 1812c15dbc
commit 38214e1544

View file

@ -7,10 +7,12 @@ class Dictionary
def word( name, &block ) def word( name, &block )
@entries[name] = { :name => name, :block => block, :immediate => false } @entries[name] = { :name => name, :block => block, :immediate => false }
self
end end
def immediate_word( name, &block ) def immediate_word( name, &block )
@entries[name] = { :name => name, :block => block, :immediate => true } @entries[name] = { :name => name, :block => block, :immediate => true }
self
end end
def []( name ) def []( name )
@ -28,55 +30,40 @@ class RForth
end end
def initial_dictionary def initial_dictionary
d = Dictionary.new Dictionary.new
.word('dup') { @stack << @stack.last }
# stack management .word('?dup') { @stack << @stack.last unless @stack.last == 0 }
d.word('dup') { @stack << @stack.last } .word('drop') { @stack.pop }
d.word('?dup') { @stack << @stack.last unless @stack.last == 0 } .word('swap') { @stack += [@stack.pop, @stack.pop] }
d.word('drop') { @stack.pop } .word('over') do
d.word('swap') do
a = @stack.pop
b = @stack.pop
@stack << a << b
end
d.word('over') do
a = @stack.pop a = @stack.pop
b = @stack.pop b = @stack.pop
@stack << b << a << b @stack << b << a << b
end end
d.word('rot') do .word('rot') do
a = @stack.pop a = @stack.pop
b = @stack.pop b = @stack.pop
c = @stack.pop c = @stack.pop
@stack << b << a << c @stack << b << a << c
end end
.word(':') { define_word }
# functions .word('+') { @stack << (@stack.pop + @stack.pop) }
d.word(':') { define_word } .word('*') { @stack << (@stack.pop * @stack.pop) }
.word('-') do
# math
d.word('+') { @stack << (@stack.pop + @stack.pop) }
d.word('*') { @stack << (@stack.pop * @stack.pop) }
d.word('-') do
a = @stack.pop a = @stack.pop
b = @stack.pop b = @stack.pop
@stack << b - a @stack << b - a
end end
.word('/') do
d.word('/') do
a = @stack.pop a = @stack.pop
b = @stack.pop b = @stack.pop
@stack << b / a @stack << b / a
end end
.word('.') { @s_out.print( "#{@stack.pop}\n" ) }
# aux words .word('.S') { @s_out.print( "#{@stack}\n" ) }
d.word('.') { @s_out.print( "#{@stack.pop}\n" ) } .word('.D') { pp @dictionary }
d.word('.S') { @s_out.print( "#{@stack}\n" ) } .word('cr') { @s_out.puts }
d.word('.D') { pp @dictionary } .word('bye') { exit }
d.word('cr') { @s_out.puts }
d.word('bye') { exit }
d
end end
def define_word def define_word