如何以编程方式向对象添加属性?

Jos*_*ech 0 ruby openstruct

我有一个哈希数组,我宁愿把它变成一个对象数组,其中的属性以编程方式添加到这些对象中.

我现在正试试这个

obj = OpenStruct.new

resulthash["users"].collect { |u|
  u.each do |k,v|
    obj.send("#{k}=#{v}");
  end
}
Run Code Online (Sandbox Code Playgroud)

回顾一下我正在尝试做的事

obj.foo = "bar"
obj.hello = "world"
Run Code Online (Sandbox Code Playgroud)

但是以编程方式,例如对于数组/哈希看起来喜欢这个

{"users"=>[{"foo"=>"bar","hello"=>"world"}]}
Run Code Online (Sandbox Code Playgroud)

Dom*_*nef 5

Object#send 将方法名称作为第一个参数,并将可选参数作为剩余参数传递给方法.

因此,obj.send("#{k}=#{v}")实际上尝试调用名为like的方法"foo=bar",这foo=与使用参数调用不同"bar".

所以对于一个人来说,正确的方式是

resulthash["users"].each { |u|
  u.each do |k,v|
    obj.send("#{k}=", v)
  end
}
Run Code Online (Sandbox Code Playgroud)

请注意,我正在使用#each而不是#collect因为我们不想转换哈希.

此外,如果您的示例反映了将Hashes数组转换为单个OpenStruct的最终目标,则可以将所有Hashes合并为一个并将其传递给OpenStruct.new:

h = resulthash["users"].inject({}) { |acc, v| acc.merge(v) }
obj = OpenStruct.new(h)
Run Code Online (Sandbox Code Playgroud)