为什么'transform_keys'方法未定义?

时间:2017-09-25 20:50:59

标签: ruby

此示例直接来自Ruby 2.4.1 documentation,我可以确认我正在运行2.4.1:

({a: 1, b: 2, c: 3}).transform_keys {|k| k.to_s}

当我执行它时,我收到以下错误:

NoMethodError: undefined method `transform_keys' for {:a=>1, :b=>2, :c=>3}:Hash

为什么没有定义transform_keys方法?

3 个答案:

答案 0 :(得分:5)

正如在another question中观察到的那样,http://ruby-doc.org目前(错误地)基于Ruby主干而不是实际发布的2.4.1版本生成Ruby 2.4.1的文档。

不幸的是,Hash#transform_keys方法尚未作为任何2.4版本的一部分发布。它是用Feature #13583开发并配置到Ruby主干的,但是还没有(还)向后移植到稳定的2.4分支。

作为解决方法,您可以改用此方法:

def transform_keys(hash)
  result = {}
  hash.each_pair do |key, value|
    result[yield(key)] = value
  end
  result
end

等同地(即:有点短,但也有点慢)你cpuld使用这个:

def transform_keys(hash)
  hash.keys.each_with_object({}) do |key, result|
    result[(yield(key)] = hash[value]
  end
end

如果您是大胆的,可以将其作为Hash课程的核心修补程序,然后您只需将hash的所有提及替换为self

请注意,ActiveSupport(即Rails)带来了一个核心补丁,使用这种精确的方法,因为它永远存在。他们使用两种实现的混合。

答案 1 :(得分:0)

感谢Holger,你激励我。

这适用于将键从字符串转换为符号以及嵌套哈希,如我所需:

class Hash

  def keys_to_sym
    result = {}
    self.each_pair do |key, value|
       value = value.keys_to_sym if value.class == Hash
       result[key.to_sym] = value
    end
  result
  end

end

所以你可以改变这个:

h = {
  "key1"=>"value1",
  "key2"=>"value2",
  "key3"=>{"key4"=>"value4", "key5"=>"value5"},
  "key6"=>{"key7"=>"value7", "key8"=>{"key9"=>"value9"}}
}

进入这个:

h_transformed = {
  :key1=>"value1",
  :key2=>"value2",
  :key3=>{:key4=>"value4", :key5=>"value5"},
  :key6=>{:key7=>"value7", :key8=>{:key9=>"value9"}}
}

答案 2 :(得分:0)

好吧,看来您是在ruby shell中尝试此代码。(irb)

但是它在Rails中可用。

> (irb): ({a: 1, b: 2, c: 3}).transform_keys {|k| k.to_s} 
  NoMethodError: undefined method `transform_keys' for {:a=>1, :b=>2, :c=>3}:Hash    
  from (irb):1
  from /home/chitresh/.rvm/rubies/ruby-2.2.10/bin/irb:11:in `<main>'

通过命令rails consolerails c使用Rails控制台

> ({a: 1, b: 2, c: 3}).transform_keys {|k| k.to_s}
 => {"a"=>1, "b"=>2, "c"=>3}