7

rubyのsendメソッドに慣れてきたのですが、なぜかこんなことができません

a = 4
a.send(:+=, 1)

何らかの理由でこれは機能しません。それから私は次のようなことを試しました

a.send(:=, a.send(:+, 1))

しかし、これもうまくいきません。「送信」を介してプラスイコールを起動する適切な方法は何ですか?

4

5 に答える 5

6

基本的なオプションは次のとおりだと思います。

a = a.send(:+, 1)

これは、sendオブジェクトへのメッセージのためです。割り当ては、オブジェクトではなく変数を変更します。


いくつかのメタプログラミングを使用して変数に直接割り当てることは可能ですが、コードは複雑です。これまでのところ、私が見つけることができる最高のものは次のとおりです。

a = 1
var_name = :a
eval "#{var_name} = #{var_name}.send(:+, 1)"
puts a  # 2

またはインスタンス変数を使用します。

@a = 2
var_name = :@a
instance_variable_set( var_name, instance_variable_get( var_name ).send(:+, 1) )
puts @a  # 3
于 2013-08-12T09:52:13.960 に答える
1

以下を参照してください。

p 4.respond_to?(:"+=") #  false
p 4.respond_to?(:"=")  #  false
p 4.respond_to?(:"+")  #  true

a+=1のシンタックスシュガーですa = a+1。しかし、直接的な方法はありません+==メソッドではなく代入演算子です。一方Object#send、引数としてメソッド名を取ります。したがって、あなたのコードは、あなたが探している方法では機能しません。

于 2013-08-12T09:57:51.433 に答える
0

=Rubyにはメソッドがないからです。Ruby=では C/C++ のようには機能しませんが、変数に新しい値を割り当てるのではなく、新しいオブジェクト参照を変数に割り当てます。

于 2013-08-12T09:57:32.353 に答える
0

これは少し的外れかもしれませんが、私はこれaを実際にオブジェクトで動的に呼び出されるメソッドで行おうとしていました。たとえば、added_countand updated_countfor のような属性を使用しImporterて、次のように書きました

class Importer
  attr_accessor :added_count, :updated_count

  def increment(method)
    send("#{method}=", (send(method) + 1))
  end

end

だから私は使用することができimporter.increment(:added_count)ますimporter.increment(:updated_count)

これら 2 つの異なるカウンターしかない場合、これはばかげているように見えるかもしれませんが、場合によっては、半ダース以上のカウンターと、attr を増加させるさまざまな条件があるため、便利です。

于 2018-10-11T20:00:24.203 に答える