implement IFTE and IFT
This commit is contained in:
parent
a26c059394
commit
b7d748ac5d
4 changed files with 53 additions and 4 deletions
|
@ -1,5 +1,6 @@
|
|||
require 'bigdecimal/math'
|
||||
|
||||
require_relative './language/branch'
|
||||
require_relative './language/general'
|
||||
require_relative './language/mode'
|
||||
require_relative './language/operations'
|
||||
|
|
|
@ -101,8 +101,8 @@ module Rpl
|
|||
add( 'xor', proc { |stack| Rpl::Core.xor( stack ) } )
|
||||
add( 'not', proc { |stack| Rpl::Core.not( stack ) } )
|
||||
add( 'same', proc { |stack| Rpl::Core.same( stack ) } )
|
||||
add( 'true', proc { |stack| Rpl::Core.true( stack ) } )
|
||||
add( 'false', proc { |stack| Rpl::Core.false( stack ) } )
|
||||
add( 'true', proc { |stack| Rpl::Core.true( stack ) } ) # specific
|
||||
add( 'false', proc { |stack| Rpl::Core.false( stack ) } ) # specific
|
||||
|
||||
# STRING
|
||||
add( '->str', proc { |stack| Rpl::Core.to_string( stack ) } )
|
||||
|
@ -124,8 +124,8 @@ module Rpl
|
|||
add( 'for', proc { |stack| Rpl::Core.__todo( stack ) } ) # <start> <end> for <variable> <instructions> next|<step> step
|
||||
add( 'next', proc { |stack| Rpl::Core.__todo( stack ) } ) # used with start and for
|
||||
add( 'step', proc { |stack| Rpl::Core.__todo( stack ) } ) # used with start and for
|
||||
add( 'ift', proc { |stack| Rpl::Core.__todo( stack ) } ) # similar to if-then-end, <test-instruction> <true-instruction> ift
|
||||
add( 'ifte', proc { |stack| Rpl::Core.__todo( stack ) } ) # similar to if-then-else-end, <test-instruction> <true-instruction> <false-instruction> ifte
|
||||
add( 'ift', proc { |stack| Rpl::Core.ift( stack, self ) } )
|
||||
add( 'ifte', proc { |stack| Rpl::Core.ifte( stack, self ) } )
|
||||
add( 'do', proc { |stack| Rpl::Core.__todo( stack ) } ) # do <instructions> until <condition> end
|
||||
add( 'until', proc { |stack| Rpl::Core.__todo( stack ) } ) # used with do
|
||||
add( 'while', proc { |stack| Rpl::Core.__todo( stack ) } ) # while <test-instruction> repeat <loop-instructions> end
|
||||
|
|
19
lib/language/branch.rb
Normal file
19
lib/language/branch.rb
Normal file
|
@ -0,0 +1,19 @@
|
|||
module Rpl
|
||||
module Core
|
||||
module_function
|
||||
|
||||
# similar to if-then-end, <test-instruction> <true-instruction> ift
|
||||
def ift( stack, dictionary )
|
||||
ifte( stack << { type: :word, value: 'nop' }, dictionary )
|
||||
end
|
||||
|
||||
# similar to if-then-else-end, <test-instruction> <true-instruction> <false-instruction> ifte
|
||||
def ifte( stack, dictionary )
|
||||
stack, args = Rpl::Core.stack_extract( stack, [%i[program word], %i[program word], %i[boolean]] )
|
||||
|
||||
stack << args[ args[2][:value] ? 1 : 0 ]
|
||||
|
||||
Rpl::Core.eval( stack, dictionary )
|
||||
end
|
||||
end
|
||||
end
|
29
spec/language_branch_spec.rb
Normal file
29
spec/language_branch_spec.rb
Normal file
|
@ -0,0 +1,29 @@
|
|||
# coding: utf-8
|
||||
# frozen_string_literal: true
|
||||
|
||||
require 'test/unit'
|
||||
|
||||
require_relative '../lib/core'
|
||||
require_relative '../lib/dictionary'
|
||||
require_relative '../lib/parser'
|
||||
require_relative '../lib/runner'
|
||||
|
||||
class TestLanguageBranch < Test::Unit::TestCase
|
||||
def test_ifte
|
||||
stack = Rpl::Core.ifte( [{ type: :boolean, value: true },
|
||||
{ type: :program, value: '« 2 3 + »' },
|
||||
{ type: :program, value: '« 2 3 - »' }],
|
||||
Rpl::Dictionary.new )
|
||||
|
||||
assert_equal [{ value: 5, type: :numeric, base: 10 }],
|
||||
stack
|
||||
|
||||
stack = Rpl::Core.ifte( [{ type: :boolean, value: false },
|
||||
{ type: :program, value: '« 2 3 + »' },
|
||||
{ type: :program, value: '« 2 3 - »' }],
|
||||
Rpl::Dictionary.new )
|
||||
|
||||
assert_equal [{ value: -1, type: :numeric, base: 10 }],
|
||||
stack
|
||||
end
|
||||
end
|
Loading…
Add table
Reference in a new issue