16

これはおそらく自宅で試すべきものではありませんが、何らかの理由で、Rubyでメソッドの配列を作成しようとしました。

私は2つの方法を定義することから始めました。

irb(main):001:0> def test1
irb(main):002:1>   puts "test!"
irb(main):003:1> end
=> nil
irb(main):004:0> def test2
irb(main):005:1>   puts "test2!"
irb(main):006:1> end
=> nil

それを実際の配列に入れようとすると、奇妙なことが起こります。両方のメソッドを実行しているようです。

irb(main):007:0> array = [test1, test2]
test!
test2!
=> [nil, nil]

その後、配列は空になります。

irb(main):008:0> puts array


=> nil

誰かがメソッドを実行する理由を私に説明できますか?それ以外は、エクササイズ全体が真剣にエクソシストを必要としていますか?

4

6 に答える 6

26

配列に格納しているのは、メソッド自体ではなく、メソッドを呼び出した結果です。

def test1
  puts "foo!"
end

def test2
  puts "bar!"
end

次のように、実際のメソッドへの参照を保存できます。

> arr = [method(:test1), method(:test2)]
# => [#<Method: Object#test1>, #<Method: Object#test2>] 

後で、次のように参照されるメソッドを呼び出すことができます。

> arr.each {|m| m.call }
foo!
bar!
于 2012-12-19T10:11:12.807 に答える
9

@alestanisはその理由をよく説明しました。メソッドを保存しようとした場合は、Lars Haugsethの言うことを実行するか、次のことを実行できます。

test1 = Proc.new { puts "test!" }
test2 = Proc.new { puts "test2!" }
a = [test1, test2]

これにより、コードがはるかに読みやすくなる可能性があります。

これがirbの実行です。

1.9.3p194 :009 > test1 = Proc.new { puts "test!" }
 => #<Proc:0x00000002798a90@(irb):9> 
1.9.3p194 :010 > test2 = Proc.new { puts "test2!" }
 => #<Proc:0x00000002792988@(irb):10> 
1.9.3p194 :011 > a = [test1, test2]
 => [#<Proc:0x00000002798a90@(irb):9>, #<Proc:0x00000002792988@(irb):10>] 
于 2012-12-19T10:21:29.147 に答える
1

squareメソッドがあり、2と4の2乗値を持つ配列を作成したい場合は、次のように記述します。

array = [square(2), square(4)]

ここでは、テストメソッドが何も返さないことを除いて、まったく同じことを行っています。そのため、finalarrayは空に見えます(実際には、が含まれています[nil, nil])。

于 2012-12-19T09:16:16.217 に答える
1

配列に2つのnil値以外のものが含まれることはありません。評価するときに文字列を入れてあなたをだまします。ただし、各関数の戻り値はまだnilです。

于 2012-12-19T09:16:54.557 に答える
1

「test1」と「test2」と言うときに実際にメソッドを呼び出しているため、コードは2つのメソッドを実行します。括弧はrubyメソッド呼び出しではオプションです。

どちらのメソッドにもnilを返す「puts」が含まれているため、結果の配列は2つのnilの配列になります。

于 2012-12-19T09:17:48.890 に答える
-1

これが私の2ペニーの価値です。すでに投稿されているソリューションに基づいて、これは実際の例の例です。ここで便利なのは、メソッドの引数と、self(インスタンス化されたときにPromotionalRulesクラスのインスタンスを参照する)の使用とシンボルの配列が含まれていることです。これは、Rubyのドキュメントから入手したものです。ここで#sendメソッド。これが誰かに役立つことを願っています!

class PromotionalRules
  PROMOTIONS = [:lavender_heart_promotion, :ten_percent_discount]

  def apply_promotions total, basket
    @total = total

    if PROMOTIONS.count > 0
      PROMOTIONS.each { |promotion| @total = self.send promotion, @total, basket }
    end

    @total.round(2)
  end

  def lavender_heart_promotion total, basket
    if two_or_more_lavender_hearts? basket
      basket.map { |item| total -= 0.75 if item == 001 }
    end
    total
  end

  def two_or_more_lavender_hearts? basket
    n = 0
    basket.each do |item|
      n += 1 if item == 001
    end
    n >= 2
  end

  def ten_percent_discount total, *arg
    if total > 60.00
      total = total - total/10
    end
    total
  end
end

みんなの助けに感謝します。私はコーディングのオープンソースの性質が大好きです-人々がお互いのソリューションを繰り返すにつれて、スレッドはどんどん良くなっていきます!

于 2015-12-28T22:53:10.747 に答える