[~/local/src/ruby/LPP/rspec_examples/rpcalculator(master)]$ cat lib/math/rpcalc.rb
module Math
class RPCalc
attr_accessor :stack
def initialize()
@stack = []
end
def calc(expr)
@stack = []
expr.split(/\s+/).each do |x|
case x
when '+', '*', '-', '/'
op2 = @stack.pop or raise SyntaxError, "No first argument for '#{x}'"
op1 = @stack.pop or raise SyntaxError, "No second argument for '#{x}'"
@stack.push eval "(#{op1} #{x} #{op2})"
when /^-?\s*\d+(\.\d+)?([eE][+-]?\d+)?\s*$/
@stack.push x
else
raise SyntaxError, "Error. found '#{x}'. Expected number or operator"
end
end
@stack.pop
end
end # class RPCalc
end # Math
[~/local/src/ruby/LPP/rspec_examples/rpcalculator(master)]$ cat spec/math/rpcalc_spec.rb
#require File.join(File.dirname(__FILE__), "/../spec_helper")
require "spec_helper"
module Math
describe RPCalc do
before :each do
@c = Math::RPCalc.new
end
context "When an erroneous input is given" do
context "not numeric input" do
before :each do
@e = proc { @c.calc('a') }
end
it "must raise an exception for not numeric input" do
expect { @e[] }.to raise_error(SyntaxError)
expect { @e[] }.to raise_error("Error. found 'a'. Expected number or operator")
end
end
context "not enough operands" do
it "must raise an exception when not enough operands" do
expect { @c.calc('2 3 + *') }.to raise_error(SyntaxError)
expect { @c.calc('2 3 + *') }.to raise_error("No second argument for '*'")
end
end
end
context "When a correct input is given" do
it "must give the correct answer for integer expressions" do
r = @c.calc('2 3 + 4 *')
r.should eq 20
@c.stack.should eq []
end
it "must give the correct answer for float expressions" do
r = @c.calc('4 3 + 2.5 3.5 +')
r.should be_within(0.01).of(6.0)
@c.stack.should eq [ 7 ]
end
end
end # RPCalc
end # Math
[~/local/src/ruby/LPP/rspec_examples/rpcalculator(master)]$ rake spec
rspec -Ilib -Ispec spec/math/rpcalc_spec.rb
Math::RPCalc
When an erroneous input is given
not numeric input
must raise an exception for not numeric input
not enough operands
must raise an exception when not enough operands
When a correct input is given
must give the correct answer for integer expressions
must give the correct answer for float expressions
Finished in 0.00526 seconds
4 examples, 0 failures