Les chaînes sont-elles mutables dans Ruby? Selon la documentation faire
str = "hello"
str = str + " world"
crée un nouvel objet de chaîne avec la valeur "hello world"
mais quand nous faisons
str = "hello"
str << " world"
Il ne mentionne pas qu'il crée un nouvel objet, il est donc muté l'objet str
, qui aura maintenant la valeur "hello world"
?
Oui, <<
Mutte le même objet, et +
crée une nouvelle. Manifestation:
irb(main):011:0> str = "hello"
=> "hello"
irb(main):012:0> str.object_id
=> 22269036
irb(main):013:0> str << " world"
=> "hello world"
irb(main):014:0> str.object_id
=> 22269036
irb(main):015:0> str = str + " world"
=> "hello world world"
irb(main):016:0> str.object_id
=> 21462360
irb(main):017:0>
Juste pour compléter, une implication de cette mutabilité semble-t-elle ci-dessous:
Ruby-1.9.2-p0 :001 > str = "foo"
=> "foo"
Ruby-1.9.2-p0 :002 > ref = str
=> "foo"
Ruby-1.9.2-p0 :003 > str = str + "bar"
=> "foobar"
Ruby-1.9.2-p0 :004 > str
=> "foobar"
Ruby-1.9.2-p0 :005 > ref
=> "foo"
et
Ruby-1.9.2-p0 :001 > str = "foo"
=> "foo"
Ruby-1.9.2-p0 :002 > ref = str
=> "foo"
Ruby-1.9.2-p0 :003 > str << "bar"
=> "foobar"
Ruby-1.9.2-p0 :004 > str
=> "foobar"
Ruby-1.9.2-p0 :005 > ref
=> "foobar"
Donc, vous devez choisir judicieusement les méthodes que vous utilisez avec des chaînes afin d'éviter un comportement inattendu.
De plus, si vous voulez quelque chose d'immuable et unique dans votre application, vous devriez aller avec des symboles:
Ruby-1.9.2-p0 :001 > "foo" == "foo"
=> true
Ruby-1.9.2-p0 :002 > "foo".object_id == "foo".object_id
=> false
Ruby-1.9.2-p0 :003 > :foo == :foo
=> true
Ruby-1.9.2-p0 :004 > :foo.object_id == :foo.object_id
=> true