2013-10-23 96 views
-1

这里是我无法理解的代码的简化版本:是否有可能使一个常数不可改变?

1.9.3p448 :004 > a = {a: 1, b: 2} 
=> {:a=>1, :b=>2} 
1.9.3p448 :005 > b = a 
=> {:a=>1, :b=>2} 
1.9.3p448 :006 > b[:c] = 3 
=> 3 
1.9.3p448 :007 > a 
=> {:a=>1, :b=>2, :c=>3} 
1.9.3p448 :008 > 

我不明白为什么a变化。 只想改变b,并保持与a其原始值。

回答

0

编辑︰ 再次看看这个问题,它来到我为什么这是发生在第一个地方: 你实际上只分配一个引用到你的本地变量。然后在本地更改值也会更改原始散列内的值。您可能想尝试.dup以获取值的副本。 虽然它只是一个浅的副本,所以取决于你可能在那里的物体,它可能不完全工作。

原文:

您可以使用freeze以防止它被改变。如果应用了更改,则会引发RuntimeError。它仍然没有100%的保护,但它会保持意外的变化发生。

CONSTANT = {:key1 => 'some value', :key2 => 'some other value'}.freeze 

在这里看到的文档: http://www.ruby-doc.org/core-2.0.0/Object.html#method-i-freeze

而且随着限制的咆哮在这里: http://m.onkey.org/ruby-i-don-t-like-3-object-freeze

+0

是的,你说得对。 'dup'解决了它。然而,这个问题对我来说似乎仍然很奇怪 –

+1

请注意,'freeze'也很浅,因此可以防止mod到主对象,但不会引用包含的对象。 'H = {A 1,B:2,C:[1,2]}。冻结; h2 = h' h2 [:a] = 11'或'h2 [:d] = 4'会引发RuntimeError,但h2 [:c] << 4'会修改引用的数组:=>'{ :a => 1,:b => 2,:c => [1,2,4]} – dbenhur

相关问题