web-dev-qa-db-ja.com

Rubyの文字列は変更可能ですか?

次のコードについて考えてみます。

$ 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)

新しい文字列を作成せずに、個々の文字を変更できるようです。ただし、文字列に追加すると、明らかに新しい文字列が作成されます。

文字列はRuby可変ですか?

35
SundayMonday

はい、Pythonとは異なり、Rubyの文字列は変更可能です。

s += "hello"not"hello"sに追加します-まったく新しい文字列オブジェクトが作成されます。文字列「インプレース」に追加するには、次のように<<を使用します。

s = "hello"
s << "   world"
s # hello world
45
Marek Příhoda
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 

したがって、文字列は変更可能ですが、+=演算子は新しい文字列を作成します。 <<古いまま

13
zed_0xff

Ruby String に追加するのは+=ではなく、<<です。

したがって、+=<<に変更すると、質問は自動的に解決されます

8
Oleg Mikheev

Rubyの文字列は変更可能ですが、フリーズして変更できます。

irb(main):001:0> s = "foo".freeze
=> "foo"
irb(main):002:0> s << "bar"
RuntimeError: can't modify frozen String
7
hipertracker

Ruby文字列は変更可能です。ただし、連結には+ではなく<<を使用する必要があります。
実際、文字列をと連結する
+ operator(immutable)新しい文字列オブジェクトを作成するため。
<< operator(mutable)同じオブジェクト内で変更されるため。

3
Faruk Hossen

このプルリクエスト で作成できることから、Ruby 3.0では、すべての文字列を作成する「魔法のコメント」を追加できるようになります不変 、変更可能ではなく。

このコメントを明示的に追加する必要があるように思われるため、「文字列は変更可能ですデフォルト?」という答えのようです。それでも「はい」になりますが、一種の条件付き「はい」は、スクリプトに魔法のコメントを書き込んだかどうかによって異なります。

[〜#〜]編集[〜#〜]

私はこれを指摘しました Ruby-Lang.orgのバグ/問題 これはsome Ruby3.0の文字列のタイプは実際には不変であると明確に述べていますデフォルトでは。

1
sameers