问题描述
我有这种方法
def method1
{
headers: { 'Content-Type' => 'application/json' }
}
end
和另一个方法,用于将另一个键和值合并到此method1哈希中,所以
def merge_hash
method1.merge!(body: { params: 123 }
end
所以当我再次调用method1时,我希望他返回一个变形的身体,而我的问题是为什么不发生这种情况或我该怎么做?
解决方法
每次调用method1
都会返回一个新对象:
> method1.object_id
=> 47220476550040
> method1.object_id
=> 47220476543700
要实现所需的功能,您可以在第一次通话后记住它:
def method1
@method1 ||= {
headers: { 'Content-Type' => 'application/json' }
}
end
> method1.object_id
=> 47220477154400
> method1.object_id
=> 47220477154400
我建议不要以这种方式对哈希进行变异,因为它会导致错误。
,当然method1
的返回值不会更改,因为您尚未更改方法本身。
您可以使用称为别名方法链的古老技术。
# Define a new method `method1_without_body`
# whose implementation is exactly the same
# as `method1` at this moment.
alias method1_without_body method1
# Define a new method that calls `method1_without_body`.
# Make sure that it does NOT call `method1`,# or you'll get a stack overflow.
def method1_with_body
method1_without_body.merge!(body: { params: 123 })
end
# Define a new method `method1`
# whose implementation is exactly the same
# as `method1_with_body`.
# This method shadows the previous implementation of `method1`.
alias method1 method1_with_body
或者如果您使用的是Rails
def method1_with_body
method1_without_body.merge!(body: { params: 123 })
end
alias_method_chain :method1,:body
然后,当您调用method1
时,它将返回带有标头和正文的哈希。
顺便说一句,从Rails 5开始不推荐使用此技术,后来又将其完全删除(我忘记了哪个次要版本)。
,也许这与您所看的很接近:
class MyClass
attr_reader :method1
def initialize
@method1 = { headers: { 'Content-Type' => 'application/json' } }
end
def merge_hash
@method1.merge!(body: { params: 123 }
end
end
因此,如果您有
o = MyClass.new
第一个o.method1
将返回初始哈希值,但是在a
o.merge_hash
o.method1
将返回修改后的哈希。