私はそれを浅くコピーしたいので、これを行うことはできません:
int[] 浅い = 元;
それは本当に浅いコピーではありません。コピーとは、オリジナルに似ているが、オリジナルのアイテムではない個別のエンティティです。あなたの例では、実際に持っているのは、同じオブジェクトを指している 2 つの参照です。コピーを作成すると、元のオブジェクトとコピーの 2 つのオブジェクトが作成されます。
ここでは、両方が同じオブジェクトを指しているため、変更することはすべてshallow
同様に行われます。orig
比較しているオブジェクトがその中に他のオブジェクトへの参照を持っている場合、「浅さ」が作用します。たとえば、整数の配列があり、コピーを作成すると、同じ整数値を含む 2 つの配列が作成されます。
Original Array
[0]
[1]
[2]
[3]
After copying:
[0] <--- Original [0]
[1] [1]
[3] [2]
[4] Copy ---> [3]
objArr1
しかし、オブジェクト ( ととしましょうobjArr2
) で構成される配列がある場合はどうなるでしょうか。浅いコピーを行うと、2 つの新しい配列オブジェクトが作成されますが、2 つの配列間の対応する各エントリは同じオブジェクトを指します (オブジェクト自体はコピーされておらず、参照だけがコピーされているため)。
Original Array:
[0:]----> [object 0]
[1:]----> [object 1]
[2:]----> [object 2]
[3:]----> [object 3]
コピー後 (対応する場所が同じインスタンスを指していることに注意してください):
Original -> [0:]----> [object 0] <----[:0] <- Copy
[1:]----> [object 1] <----[:1]
[2:]----> [object 2] <----[:2]
[3:]----> [object 3] <----[:3]
objArr1
エントリを置き換えたり、エントリを削除したりして変更しても、同じことがobjArr2
. ただし、 でオブジェクトを変更すると、それらの場所が同じオブジェクトを指しているため、 にもobjArr1[0]
反映されます。したがって、この場合、コンテナー オブジェクト自体は別個のものですが、それらに含まれるものは同じオブジェクトへの参照です。objArr2[0]
ディープ コピーを実行すると、対応する各場所が異なるインスタンスを指す 2 つの新しい配列が作成されます。したがって、基本的には、オブジェクトのコピーをずっと下に作成します。
私の教授は、プリミティブの場合、配列の各インデックスをコピーする必要があるという点で、浅いコピーと深いコピーは本質的に同じであると言いました。
重要な違いは、プリミティブの配列をコピーする場合、値を正確にコピーすることです。新しいプリミティブを取得するたびに。ただし、オブジェクトの配列がある場合、実際にあるのはオブジェクトへの参照の配列です。したがって、コピーを作成するときは、元の配列の参照のコピーを持つ新しい配列を作成するだけです。ただし、これらの参照の新しいコピーは、依然として同じ対応するオブジェクトを指しています。これは、浅いコピーとして知られているものです。配列をディープコピーすると、個々の場所が参照するオブジェクトもコピーされます。したがって、次のように表示されます。
Original -> [0:]----> [object 0] Copy -> [0:]----> [copy of object 0]
[1:]----> [object 1] [1:]----> [copy of object 1]
[2:]----> [object 2] [2:]----> [copy of object 2]
[3:]----> [object 3] [3:]----> [copy of object 3]
しかし、配列全体を別の配列と等しく設定すると、同じことが起こりますよね?
いいえ、違います。ここで行っているのは、既存の配列への新しい参照を作成することだけです。
arr1 -> [0, 1, 2, 3, 4]
では、したとしましょうarr2 = arr1
。あなたが持っているものは次のとおりです。
arr1 -> [0, 1, 2, 3, 4] <- arr2
したがって、ここではarr1
との両方arr2
が同じ配列を指しています。したがって、同じ配列を見ているため、使用して実行した変更は、使用しarr1
て配列にアクセスすると反映されます。arr2
これは、コピーを作成する場合には発生しません。