配列のコピー

C:\DATA\Java2\Dos>java Copy2
ABCDEFG
[0]=X  [3]=Y
XBCYEFG
charArray1 ?
XBCYEFG
 -- Press any key to exit (Input "c" to continue) --
配列のコピーに付いて検証してみました。

前田稔の超初心者のプログラム入門

要素を一個ずつコピー

  1. ネットで見かけたシャローコピー(shallow copy)とディープコピー(deep copy)のプログラムが怪しいので検証してみました。
    シャローコピーとはコピー先のオブジェクトに対し、そのオブジェクトの参照情報のみ複写する方法です。
    つまりコピー元、コピー先とも同じオブジェクトを参照しています。
    シャローコピーを行った場合は、コピー先のオブジェクトの値を変更するとコピー元のオブジェクトの値も変更されます。
    ディープコピーとはコピー先のオブジェクトに対し、参照情報だけでなくオブジェクトの実体も複写する方法です。
  2. メモ帳などでタイプして Copy1.java の名前で保存して下さい。
    // 要素を一個ずつコピー    前田 稔
    public class Copy1
    {   public static void main(String[] args)
        {   char[] charArray1 = {'A', 'B', 'C', 'D', 'E', 'F', 'G'};
            char[] charArray2 = new char[charArray1.length];
    
            // charArray1 ⇒ charArray2
            for(int i=0; i<charArray1.length; i++)
            {   charArray2[i] = charArray1[i];  }
            for(int i=0; i<charArray2.length; i++)
            {   System.out.print(charArray2[i]);  }
    
            // コピー先の charArray2 を変更
            charArray2[0]= 'X';
            charArray2[3]= 'Y';
            System.out.println("\n[0]=X  [3]=Y");
            for(int i=0; i<charArray2.length; i++)
            {   System.out.print(charArray2[i]);  }
    
            // コピー元の charArray1 を確認
            System.out.println("\ncharArray1 ?");
            for(int i=0; i<charArray1.length; i++)
            {   System.out.print(charArray1[i]);  }
            System.out.println();
        }
    }
    
  3. Copy1.java の説明です。
    charArray1 から charArray2 に for ループで要素を一個ずつコピーします。
    charArray1 と charArray2 は別々に領域が確保され、charArray2 を修正しても charArray1 は不変です。

直接代入

  1. メモ帳などでタイプして Copy2.java の名前で保存して下さい。
    // 直接代入    前田 稔
    public class Copy2
    {   public static void main(String[] args)
        {   char[] charArray1 = {'A', 'B', 'C', 'D', 'E', 'F', 'G'};
            char[] charArray2;
    
            // charArray1 ⇒ charArray2
            charArray2= charArray1;
            for(int i=0; i<charArray2.length; i++)
            {   System.out.print(charArray2[i]);  }
    
            // コピー先の charArray2 を変更
            charArray2[0]= 'X';
            charArray2[3]= 'Y';
            System.out.println("\n[0]=X  [3]=Y");
            for(int i=0; i<charArray2.length; i++)
            {   System.out.print(charArray2[i]);  }
    
            // コピー元の charArray1 を確認
            System.out.println("\ncharArray1 ?");
            for(int i=0; i<charArray1.length; i++)
            {   System.out.print(charArray1[i]);  }
            System.out.println();
        }
    }
    
  2. Copy2.java の説明です。
    charArray2 = charArray1 で直接代入します。
    このとき代入されるのは「領域のポインタ」です。
    charArray1 と charArray2 は同一の領域を指し示すので、charArray2 を修正すると charArray1 も変化します。
    このページの先頭に実行結果を表示しています。
    配列をパラメータとして渡したときも同様で、受け取った配列を修正すると元の値も変化します。

clone() でコピー

  1. メモ帳などでタイプして Copy3.java の名前で保存して下さい。
    // clone() でコピー    前田 稔
    public class Copy3
    {   public static void main(String[] args)
        {   char[] charArray1 = {'A', 'B', 'C', 'D', 'E', 'F', 'G'};
    
            // クローンを作成
            char[] charArray2 = (char[])charArray1.clone();
            for(int i=0; i<charArray2.length; i++)
            {   System.out.print(charArray2[i]);  }
    
            // クローンの charArray2 を変更
            charArray2[0]= 'X';
            charArray2[3]= 'Y';
            System.out.println("\n[0]=X  [3]=Y");
            for(int i=0; i<charArray2.length; i++)
            {   System.out.print(charArray2[i]);  }
    
            // コピー元の charArray1 を確認
            System.out.println("\ncharArray1 ?");
            for(int i=0; i<charArray1.length; i++)
            {   System.out.print(charArray1[i]);  }
            System.out.println();
        }
    }
    
  2. Copy3.java の説明です。
    charArray1 から clone() メソッドで charArray2 を作成します。
    charArray1 と charArray2 は別々に領域が確保されるようで、charArray2 を修正しても charArray1 は不変です。

arraycopy() でコピー

  1. メモ帳などでタイプして Copy4.java の名前で保存して下さい。
    // arraycopy() でコピー    前田 稔
    public class Copy4
    {   public static void main(String[] args)
        {   char[] charArray1 = {'A', 'B', 'C', 'D', 'E', 'F', 'G'};
            char[] charArray2 = new char[7];
    
            // charArray1(1番目から) ⇒ charArray2(3番目から4文字分)
            System.arraycopy(charArray1,1,charArray2,3,4);
            for(int i=0; i<charArray2.length; i++)
            {   System.out.print(charArray2[i]);  }
    
            // コピー先の charArray2 を変更
            charArray2[0]= 'X';
            charArray2[3]= 'Y';
            System.out.println("\n[0]=X  [3]=Y");
            for(int i=0; i<charArray2.length; i++)
            {   System.out.print(charArray2[i]);  }
    
            // コピー元の charArray1 を確認
            System.out.println("\ncharArray1 ?");
            for(int i=0; i<charArray1.length; i++)
            {   System.out.print(charArray1[i]);  }
            System.out.println();
        }
    }
    
  2. Copy4.java の説明です。
    charArray1 を arraycopy() メソッドで charArray2 にコピーします。
    charArray1 と charArray2 は別々に領域が確保されるようで、charArray2 を修正しても charArray1 は不変です。

超初心者のプログラム入門(Java2)