Java中如何进行多维数组的深度克隆?

9

我有两个多维数组(实际上只有2D),它们具有推断大小。如何深度克隆它们?这是我到目前为止的代码:

public foo(Character[][] original){
    clone = new Character[original.length][];
    for(int i = 0; i < original.length; i++)
          clone[i] = (Character[]) original[i].clone();
}

一个判断相等的测试original.equals(clone);返回了false。为什么? :|

6个回答

13
/**Creates an independent copy(clone) of the boolean array.
 * @param array The array to be cloned.
 * @return An independent 'deep' structure clone of the array.
 */
public static boolean[][] clone2DArray(boolean[][] array) {
    int rows=array.length ;
    //int rowIs=array[0].length ;

    //clone the 'shallow' structure of array
    boolean[][] newArray =(boolean[][]) array.clone();
    //clone the 'deep' structure of array
    for(int row=0;row<rows;row++){
        newArray[row]=(boolean[]) array[row].clone();
    }

    return newArray;
}

3

3

equals()方法适用于数组,是在Object类中声明的。这意味着它只有在对象相同的情况下才会返回true。所谓相同并不是指内容相同,而是指内存中相同。因此,如果您在内存中复制结构,则数组上的equals()永远不会返回true。


1
一个相等性测试,original.equals(clone)输出false。为什么? :|
这是因为你正在使用new Character[original.length][];创建一个新数组。
Arrays.deepEquals(original,clone)应该返回true。

0

与@Barak的解决方案相同(序列化和反序列化),并提供示例(因为有些人可能无法理解并对此进行了负面评价)

public static <T extends Serializable> T deepCopy(T obj)
{
    ByteArrayOutputStream baos = new ByteArrayOutputStream();
    try
    {
        ObjectOutputStream oos = new ObjectOutputStream(baos);

        // Beware, this can throw java.io.NotSerializableException 
        // if any object inside obj is not Serializable
        oos.writeObject(obj);  
        ObjectInputStream ois = new ObjectInputStream(
                                    new ByteArrayInputStream(baos.toByteArray()));
        return (T) ois.readObject();
    }
    catch (  ClassNotFoundException /* Not sure */
           | IOException /* Never happens as we are not writing to disc */ e)
    {
        throw new RuntimeException(e); // Your own custom exception
    }
}

使用方法:

    int[][] intArr = { { 1 } };
    System.out.println(Arrays.deepToString(intArr)); // prints: [[1]]
    int[][] intDc = deepCopy(intArr);
    intDc[0][0] = 2;
    System.out.println(Arrays.deepToString(intArr)); // prints: [[1]]
    System.out.println(Arrays.deepToString(intDc)); // prints: [[2]]
    int[][] intClone = intArr.clone();
    intClone[0][0] = 4;

    // original array modified because builtin cloning is shallow 
    System.out.println(Arrays.deepToString(intArr)); // prints: [[4]]
    System.out.println(Arrays.deepToString(intClone)); // prints: [[4]]

    short[][][] shortArr = { { { 2 } } };
    System.out.println(Arrays.deepToString(shortArr)); // prints: [[[2]]]

    // deepCopy() works for any type of array of any dimension
    short[][][] shortDc = deepCopy(shortArr);
    shortDc[0][0][0] = 4;
    System.out.println(Arrays.deepToString(shortArr)); // prints: [[[2]]]
    System.out.println(Arrays.deepToString(shortDc)); // prints: [[[4]]]

-1

我在jGuru上找到了关于克隆多维数组的答案:

ByteArrayOutputStream baos = new ByteArrayOutputStream();
ObjectOutputStream oos = new ObjectOutputStream(baos);
oos.writeObject(this);
ByteArrayInputStream bais = new ByteArrayInputStream(baos.toByteArray());
ObjectInputStream ois = new ObjectInputStream(bais);
Object deepCopy = ois.readObject();

这种技术适用于多维数组。只需使用“array”代替“this”。 - Venkata Raju

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接