如何将数学运算(例如+, - ,*,/)作为参数传递给方法

时间:2016-06-07 19:38:18

标签: ruby

我正在写一个反向波兰表示法(RPN)计算器,到目前为止,它看起来像这样:

class RPNCalculator
  attr_accessor :numbers, :value
  def initialize
    @numbers = []
    @value = nil
  end

  def push(number)
    @numbers.push(number)
  end

  def plus
    if value.nil?
      number1=@numbers.pop
      number2=@numbers.pop
      @value = number1 + number2
    else
      @value += @numbers.pop
    end
  end

  # minus_proc = Proc.new {|a,b| a - b}

  def minus
    number1=@numbers.pop
    number2=@numbers.pop
    @value = number2 - number1
    # operate_on_two_numbers(minus_proc)
  end

  def operate_on_two_numbers(&prc)
    number1=@numbers.pop
    number2=@numbers.pop
    @value = prc.call(number1,number2)
  end

end

例如,以下命令

calculator=RPNCalculator.new
calculator.push(5)
calculator.push(8)
calculator.plus
p calculator.value

产生数字“13”。

这应该是如何工作的,但代码中似乎有很多重复。例如,“加”和“减”函数大致相同;代码中只有“+”和“ - ”不同。

我想尝试定义一个(私有)方法,该方法接受一个操作两个数字的操作作为参数,例如“+”,“ - ”,“*”或“/”。像快捷方式.inject(:+)一样使用“快捷符号”会很不错。

我已尝试使用注释掉的行和方法operate_on_two_numbers,但当我在行中注释时,我收到错误“未定义的局部变量或方法'minus_proc'”。

2 个答案:

答案 0 :(得分:3)

你可以在这里以同样的方式使用任何arithmetic operator

def operate_on_two_numbers(a, b, op)
  a.send(op, b)
end

operate_on_two_numbers(1, 2, :+)
#=> 3
operate_on_two_numbers(1, 2, :-)
#=> -1

以下是您的完整代码的样子

class RPNCalculator
  attr_accessor :numbers, :value
  def initialize
    @numbers = []
    @value = nil
  end

  def push(number)
    @numbers.push(number)
  end

  def plus
    operate_on_two_numbers(:+)
  end

  def minus
    operate_on_two_numbers(:-)
  end

  private

  def operate_on_two_numbers(op)
    number1=@numbers.pop
    number2=@numbers.pop
    @value = number1.send(op, number2)
  end
end

calculator=RPNCalculator.new
#=> #<RPNCalculator:0x00000002efe460 @numbers=[], @value=nil>
calculator.push(5)
#=> [5]
calculator.push(8)
#=> [5, 8]
calculator.plus
#=> 13
calculator.value
#=> 13

答案 1 :(得分:0)

虽然我会接受&#34; .send&#34;方法就像我最初寻找的那样,最后我使用了一个接受块作为参数的方法,因为对于除法(&#34;除法&#34;方法)我需要更多的操作(即转换为浮点数)在分裂之前)。更新的RPN计算器如下所示。

 {
     "id": "58027708919_10153766074838920",
     "type": "link",
     "created_time": "2016-06-07T12:00:00+0000",
     "link": "http://po.st/Piscine",
     "message": "La natation pour optimiser vos entra\u00eenements?!? Pourquoi? Comment?\nNos 6 mani\u00e8res de l'inclure dans vos programmes !! \ud83c\udf0a \ud83d\udcaa  \ud83c\udfc3",
     "picture": "https://external.xx.fbcdn.net/safe_image.php?d=AQDSc30G8WnJJrnb&w=130&h=130&url=fbstaging\u00253A\u00252F\u00252Fgraph.facebook.com\u00252Fstaging_resources\u00252FMDExMDE1Mzc2NjA2Njc4ODkyMDoyMTMwMzk2MjE4&cfs=1",
     "full_picture": "https://external.xx.fbcdn.net/safe_image.php?d=AQAKv_-jfO40xDvY&url=fbstaging\u00253A\u00252F\u00252Fgraph.facebook.com\u00252Fstaging_resources\u00252FMDExMDE1Mzc2NjA2Njc4ODkyMDoyMTMwMzk2MjE4"
  },

请注意&#34;加&#34;,&#34;减去&#34;等现在是单行方法,并且大部分复杂性已经转移到私有&#34; operate_on_two_numbers&#34 ;方法