通过引用/复制字符串分配?

谁能解释这种行为

情景1

str = "hello" str1 = str puts str #=> hello puts str1 #=> hello str1 = "hi" puts str1 #=> hi puts str #=> hello 

在这里,改变str1的值对str的值没有影响。

方案2

 str = "hello" str1 = str str1.gsub! "hello", "whoa!" puts str1 #=> whoa puts str #=> whoa 

不是gsub! 只影响str1 ? 为什么要改变str ? 如果str1只保存对str的引用,那么为什么在Scenario-1中值不会改变?

仔细看下面:

情景1

 str = "hello" str1 = str puts str #=> hello puts str1 #=> hello p str.object_id #=>15852348 p str1.object_id #=> 15852348 

在上面的情况下, strstr1保持对object_idcertificate的相同对象的引用。 现在,在下面的情况下使用局部变量str1来保存一个新对象"hi" ,这也是由两个不同的object_idcertificate的。

 str1 = "hi" puts str1 #=> hi puts str #=> hello p str.object_id #=> 15852348 p str1.object_id #=> 15852300 

方案2

`字符串#GSUB! 说:

如果没有执行替换,则执行String#gsub的替换,返回str或nil。 如果没有给出块和没有替换,则返回枚举器。

 str = "hello" str1 = str str1.gsub! "hello", "whoa!" puts str1 #=> whoa puts str #=> whoa p str.object_id #=>16245792 p str1.object_id #=>16245792 

在变量赋值中,它是否存在具有相同名称的变量无效,如果是,则它是什么值。 在方案-1中, str最终被赋予str1 = "hi" ,并且在此之前发生的任何事情都是无关紧要的。 场景-1与没有str1 = str的以下内容相同。

 str = "hello" str1 = "hi" 

在场景-2中, strstr指的是相同的字符串。 如果通过指向该字符串的其中一个变量进行更改,那么当您通过另一个变量调用它时,它会引用相同的更改字符串。