У меня есть два многомерных массива (ну, на самом деле они всего лишь 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); выдает ложный результат. Почему? : |




Возможно, вы захотите проверить методы java.util.Arrays.deepEquals и java.util.Arrays.equals.
Я боюсь, что метод equals для объектов массива выполняет неглубокое сравнение и неправильно (по крайней мере, в этом случае) сравнивает внутренние массивы Character.
Метод equals () для массивов - это метод, объявленный в классе Object. Это означает, что он вернет истину только в том случае, если объекты такие же. То же самое означает не то же самое в СОДЕРЖАНИЕ, но то же самое в ПАМЯТИ. Таким образом, equals () в ваших массивах никогда не вернет true, поскольку вы дублируете структуру в памяти.
A test for equality original.equals(clone); spits out a false. Why? :|
это потому, что вы создаете новый массив с new Character[original.length][];.
Arrays.deepEquals(original,clone) должен вернуть истину.
Я нашел этот ответ для клонирования многомерных массивов на 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();
/**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;
}
То же, что и решение @Barak (Serialize и Deserialize) с примерами (поскольку некоторые люди не могли понять и проголосовали против)
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]]]
Этот метод работает для многомерных массивов. Просто используйте
arrayвместоthis