ruby中的哈希数据类型中的“默认值是同一个对象”
参见英文答案 >
Strange,unexpected behavior (disappearing/changing values) when using Hash default value,e.g. Hash.new([])????????????????????????????????????4个
我是Ruby新手并且运行Ruby Koans.在Ruby Koans的about_hashes.rb文件中,有一个为散列分配默认值的示例. hash = Hash.new([]) hash[:one] << "uno" hash[:two] << "dos" puts hash[:one] # this is ["uno","dos"] 哈希[:one]& hash [:two]或任何键如hash [:three](非现有键)都具有值[“uno”和“dos”]我不明白“<<”在这里使用.此外,当我尝试提取键和&哈希值,或打印键/值,它是空的. puts (hash.values.size) # size is 0 here puts (hash.keys.size) # size is 0 puts hash.values # nothing gets printed puts hash.keys #nothing gets printed. 那么这里发生了什么?存储的值在哪里,如果它们没有作为键或值存储在散列中. 在下一个例子中,当Hash被定义为 hash = Hash.new {|hash,key| hash[key] = [] } hash[:one] << "uno" hash[:two] << "dos" puts hash[:one] #this is "uno" puts hash[:two] #this is "dos" puts hash[:three] # this is undefined. 我想在第二个例子中,hash正在使用空白数组初始化所有键.因此当“<<”时,“uno”会被附加到空数组中使用此运算符?我对这两个例子感到困惑.我不知道他们俩发生了什么.我也无法在谷歌中找到关于这个例子的更多信息.如果有人可以帮我解释这两个例子,那将会很有帮助.提前致谢 解决方法
hash = Hash.new([])
此语句创建一个空哈希,其默认值为空数组.如果散列没有密钥k,则hash [k]返回默认值[].这很重要:只返回默认值不会修改哈希值. 当你写: hash[:one] << "uno" #=> ["uno"] 在hash有一个键之前:一,hash [:one]被默认值替换,所以我们有: [] << "uno" #=> ["uno"] 这解释了为什么散列没有改变: hash #=> {} 现在写: hash[:two] << "dos" #=> ["uno","dos"] hash #=> {} 为了了解为什么我们得到这个结果,让我们重写上面的内容如下: hash = Hash.new([]) #=> {} hash.default #=> [] hash.default.object_id #=> 70209931469620 a = (hash[:one] << "uno") #=> ["uno"] a.object_id #=> 70209931469620 hash.default #=> ["uno"] b = (hash[:two] << "dos") #=> ["uno","dos"] b.object_id #=> 70209931469620 hash.default #=> ["uno","dos"] 因此,您可以看到object_id为70209931469620的默认数组是附加“uno”和“dos”的单个数组. 如果我们写了: hash[:one] = hash[:one] << "uno" #=> hash[:one] = [] << "uno" => ["uno"] hash #=> { :one=>"uno" } 我们得到了我们希望的东西,但不是那么快: hash[:two] = hash[:two] << "dos" #=> ["uno","dos"] hash #=> {:one=>["uno","dos"],:two=>["uno","dos"]} 这仍然不是我们想要的,因为两个键的值都是相同的数组. hash = Hash.new {| hash,key | hash [key] = []} 当哈希没有密钥时,此语句会导致执行块.这确实通过添加键值pair1来更改哈希值. 所以现在: hash[:one] << "uno" 导致阻止: { |h,k| h[k] = [] } 做出任务: hash[:one] = [] 之后: hash[:one] << "uno" 将“uno”附加到一个空数组,该数组是键的值:one,我们可以验证: hash #=> { :one=>"uno" } 这与写作效果相同: hash[:one] = (hash[:one] || []) << "uno" (当没有默认值时,(hash [:one] || = [])<<“uno”的扩展版本. 同样的, hash[:two] << "dos" #=> ["dos"] hash #=> {:one=>["uno"],:two=>["dos"]} 这通常是我们想要的结果. 1但是,块不需要更改哈希值.该块可以包含任何代码,例如,{puts“Have a nice day”}. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |