LoginSignup
32
14

More than 5 years have passed since last update.

Ruby 参照、浅いコピー、深いコピー

Last updated at Posted at 2017-07-23

配列に対しての参照渡し、浅いコピー、深いコピーについてのメモ。

参照渡し

=を使用して配列の複製を行う。

参照
a1 = "ruby java python".split
#参照渡し
a2 = a1
puts "a1:#{a1}"
puts "a2:#{a2}"
#配列オブジェクトが同じか確認
p a1.equal?(a2)
p a1.object_id
p a2.object_id
p a1[0].equal?(a2[0])
p a1[0].object_id
p a2[0].object_id
#配列に対して変更
a1.sort!
#配列内容の確認
puts "a1:#{a1}"
puts "a2:#{a2}"
#要素の値に対して変更
a1[0].capitalize!
#配列内容の確認
puts "a1:#{a1}"
puts "a2:#{a2}"
実行結果
a1:["ruby", "java", "python"]
a2:["ruby", "java", "python"]
true
70328621736780
70328621736780
true
70328621736740
70328621736740
a1:["java", "python", "ruby"]
a2:["java", "python", "ruby"]
a1:["Java", "python", "ruby"]
a2:["Java", "python", "ruby"]

配列もその中の要素も元のa1と変わらないことがわかる。
配列に対してsortを実行するとa2にも影響を受け
a1の要素0に対してcapitalizeを実行するとa2にも影響している。

refBf.jpg

↓↓↓ 処理実行後 ↓↓↓

refAf.jpg

浅いコピー

dupを使用して配列の複製を行う。

浅いコピー
a1 = "ruby java python".split
#浅いコピー
a2 = a1.dup
puts "a1:#{a1}"
puts "a2:#{a2}"
#配列オブジェクトが同じか確認
p a1.equal?(a2)
p a1.object_id
p a2.object_id
p a1[0].equal?(a2[0])
p a1[0].object_id
p a2[0].object_id
#配列に対して変更
a1.sort!
#配列内容の確認
puts "a1:#{a1}"
puts "a2:#{a2}"
#要素の値に対して変更
a1[0].capitalize!
#配列内容の確認
puts "a1:#{a1}"
puts "a2:#{a2}"
実行結果
a1:["ruby", "java", "python"]
a2:["ruby", "java", "python"]
false
70363447026880
70363447026740
true
70363447026860
70363447026860
a1:["java", "python", "ruby"]
a2:["ruby", "java", "python"]
a1:["Java", "python", "ruby"]
a2:["ruby", "Java", "python"]

配列のオブジェクトが違うことがわかる。
そのためソートを実行するとa2には影響がない。
ただし要素の値に関しては同一のものを参照しているため
capitalizeを実行するとa2も値が変更されている。

shallowCopyBf.jpg

↓↓↓ 処理実行後 ↓↓↓

shallowCopyAf.jpg

深いコピー

Marshalを使用して配列の複製を行う。

深いコピー
a1 = "ruby java python".split
#深いコピー
a2 = Marshal.load(Marshal.dump(a1))
puts "a1:#{a1}"
puts "a2:#{a2}"
#配列オブジェクトが同じか確認
p a1.equal?(a2)
p a1.object_id
p a2.object_id
p a1[0].equal?(a2[0])
p a1[0].object_id
p a2[0].object_id
#配列に対して変更
a1.sort!
#配列内容の確認
puts "a1:#{a1}"
puts "a2:#{a2}"
#要素の値に対して変更
a1[0].capitalize!
#配列内容の確認
puts "a1:#{a1}"
puts "a2:#{a2}"
実行結果
a1:["ruby", "java", "python"]
a2:["ruby", "java", "python"]
false
70194731237460
70194731242700
false
70194731241740
70194731242800
a1:["java", "python", "ruby"]
a2:["ruby", "java", "python"]
a1:["Java", "python", "ruby"]
a2:["ruby", "java", "python"]

配列とその要素いずれも同一でないことがわかる。
よってsortcapitalizeのどちらの実行もa2に影響がない。

deepCopyBf.jpg

↓↓↓ 処理実行後 ↓↓↓

deepCopyAf.jpg

32
14
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
32
14