Are strings in Ruby mutable? [duplicate]

2019-01-17 09:39发布

This question already has an answer here:

Consider the following code:

$ irb
> s = "asd"
> s.object_id   # prints 2171223360
> s[0] = ?z     # s is now "zsd"
> s.object_id   # prints 2171223360 (same as before)
> s += "hello"  # s is now "zsdhello"
> s.object_id   # prints 2171224560 (now it's different)

Seems like individual characters can be changed w/o creating a new string. However appending to the string apparently creates a new string.

Are strings in Ruby mutable?

6条回答
女痞
2楼-- · 2019-01-17 10:21

Appending in Ruby String is not +=, it is <<

So if you change += to << your question gets addressed by itself

查看更多
唯我独甜
3楼-- · 2019-01-17 10:23

Ruby Strings are mutable. But you need to use << for concatenation rather than +.
In fact concatenating string with
+ operator(immutable) because it creates new string object.
<< operator(mutable) because it changes in the same object.

查看更多
一纸荒年 Trace。
4楼-- · 2019-01-17 10:23

From what I can make of this pull request, it will become possible in Ruby 3.0 to add a "magic comment" that will make all string immutable, rather than mutable.

Because it seems you have to explicitly add this comment, it seems like the answer to "are string mutable by default?" will still be yes, but a sort of conditional yes - depends on whether you wrote the magic comment into your script or not.

EDIT

I was pointed to this bug/issue on Ruby-Lang.org that definitively states that some type of strings in Ruby 3.0 will in fact be immutable by default.

查看更多
戒情不戒烟
5楼-- · 2019-01-17 10:34

Yes, strings in Ruby, unlike in Python, are mutable.

s += "hello" is not appending "hello" to s - an entirely new string object gets created. To append to a string 'in place', use <<, like in:

s = "hello"
s << "   world"
s # hello world
查看更多
Ridiculous、
6楼-- · 2019-01-17 10:42

Strings in Ruby are mutable, but you can change it with freezing.

irb(main):001:0> s = "foo".freeze
=> "foo"
irb(main):002:0> s << "bar"
RuntimeError: can't modify frozen String
查看更多
爷、活的狠高调
7楼-- · 2019-01-17 10:45
ruby-1.9.3-p0 :026 > s="foo"
 => "foo" 
ruby-1.9.3-p0 :027 > s.object_id
 => 70120944881780 
ruby-1.9.3-p0 :028 > s<<"bar"
 => "foobar" 
ruby-1.9.3-p0 :029 > s.object_id
 => 70120944881780 
ruby-1.9.3-p0 :031 > s+="xxx"
 => "foobarxxx" 
ruby-1.9.3-p0 :032 > s.object_id
 => 70120961479860 

so, Strings are mutable, but += operator creates a new String. << keeps old

查看更多
登录 后发表回答