java - 在 Java DIY 中克隆对象及其内部数组

标签 java arrays matrix clone

我正在尝试在不使用任何库的情况下克隆对象。 该对象中有其他对象/数组/矩阵。 所以我也开发了一些方法来克隆它们。

当我克隆不在对象内部的数组/矩阵时,它们工作正常。 这些是方法:

public static int[] cloneArray(int[] array){
    int i = 0;
    int[] clone = new int[array.length];
    while (i < array.length){
        clone[i] = array[i];
        i++;
    }
    return clone;
}

public static int[][] cloneMatrix(int[][] matrix){
    int[][] clone = new int[matrix.length][matrix[0].length];
    for (int i = 0;i<matrix.length;i++)
        for(int j = 0;j<matrix[0].length;j++)
            clone[i][j] = matrix[i][j];
    return clone;
}

但是,当我想克隆一个对象时,数组/矩阵的引用保持不变,因为您可以在帖子底部查看输出。 这是我的构造函数:

    public State(int parentStateID, int stateID, int[][] board, int[] pieces, int points, int acquiredPoints){
       State.parentStateID = parentStateID;
       State.stateID = stateID;
       State.currentBoard = cloneMatrix(board); //here takes place the matrix cloning
       State.currentPieces = cloneArray(pieces); //here takes place the array cloning
       State.totalPoints = points;
       State.acquiredPoints = acquiredPoints;
   }

这是克隆方法:

    public static State cloneState(State state){
    int[][] currentBoard = state.getCurrentBoard();
    int[] currentPieces = state.getCurrentPieces();
    int totalPoints = state.getTotalPoints();
    int acquiredPoints = state.getAcquiredPoints();
    int parentStateID = state.getParentStateID();
    int stateID = state.getStateID();
    State clone = new State(parentStateID, 
            stateID,
            currentBoard, 
            currentPieces, 
            totalPoints, 
            acquiredPoints);
    return clone;
}

为了更好地可视化输出,这里是数组和矩阵:

public static int piecesList[] = {1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1};
public static int piecesList2[] = {2,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1};
public static int piecesList3[] = {3,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1};
private static int[][] map = {{0,1,2,3,4},{5,6,7,8,9},{10,11,12,13,14},{15,16,17,18,19},{20,21,22,23,24}};

验证码如下:

    int[][] state2 = cloneMatrix(map);
    state2[0][0] = 1;
    System.out.println("map.original " + map[0][0]);
    System.out.println("map.clone " + state2[0][0]);

    System.out.println("");
    System.out.println("");

    int[] pc = cloneArray(piecesList);
    pc[24] = 1;
    System.out.println("pieces.original " + piecesList[24]);
    System.out.println("pieces.clone " + pc[24]);

    System.out.println("");
    System.out.println("");
    State newState = setFirstState();
    State clonedState = cloneState(newState);
    clonedState.setCurrentPieces(piecesList2);
    System.out.println("newState.pieceslist: "+newState.getCurrentPieces()[0]);
    System.out.println("clonedState.pieceslist: "+clonedState.getCurrentPieces()[0]);
    System.out.println("piecesList.original: "+piecesList[0]);
    System.out.println("");
    newState.setCurrentPieces(piecesList3);
    System.out.println("newState.pieceslist: "+newState.getCurrentPieces()[0]);
    System.out.println("clonedState.pieceslist: "+clonedState.getCurrentPieces()[0]);
    System.out.println("piecesList.original: "+piecesList[0]);

这是输出:

map.original 0
map.clone 1


pieces.original -1
pieces.clone 1

//as you can check in the next two cases, the change takes effect in both the original state, and the cloned state
newState.pieceslist: 2
clonedState.pieceslist: 2
piecesList.array variable: 1

newState.pieceslist: 3
clonedState.pieceslist: 3
piecesList.array variable: 1

尝试解决此问题已超过 12 个小时,但没有取得太大成功... 我尝试过库和序列化但没有成功...... 非常感谢您的帮助!

最佳答案

您的代码的问题在于,字段(未显示)显然是静态,从您的构造函数可以看出:

public State(int parentStateID, int stateID, int[][] board, int[] pieces, int points, int acquiredPoints){
    State.parentStateID = parentStateID;
    State.stateID = stateID;
    State.currentBoard = cloneMatrix(board); //here takes place the matrix cloning
    State.currentPieces = cloneArray(pieces); //here takes place the array cloning
    State.totalPoints = points;
    State.acquiredPoints = acquiredPoints;
}

构造函数应该这样写:

public State(int parentStateID, int stateID, int[][] board, int[] pieces, int points, int acquiredPoints){
    this.parentStateID = parentStateID;
    this.stateID = stateID;
    this.currentBoard = cloneMatrix(board); //here takes place the matrix cloning
    this.currentPieces = cloneArray(pieces); //here takes place the array cloning
    this.totalPoints = points;
    this.acquiredPoints = acquiredPoints;
}

静态字段每个类仅存在一次。每个从该类(或任何子类)构造的对象都存在一个非静态字段。因此,您实际上创建了空对象,以及您认为要存储在实际存储在类中的对象中的任何内容,从而在所有对象之间共享相同的数据。

根据经验,您通常不希望类中出现任何staticfinal 字段。异常(exception)情况也适用,但它们很少见,而且大多仅限于框架中的一些微小的 Bootstrap 。

关于java - 在 Java DIY 中克隆对象及其内部数组,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27580278/

相关文章:

java - 从表名中获取主键的值

java - JAVA 中的 StringTokenizer

javascript - Bootstrap 轮播TypeError : f[0] is undefined

python - 如何在 python 中使用电子表格或等效项来存储列表?

c++ - 如何使用 opencv 库将 3D 矩阵的元素置零?

java - Android Studio : NavigationDrawer displaying a black screen

java - Gradle - 如何从 GitHub 创建和获取简单的类

c - 为什么我不能为该指针数组元素分配 NULL 值?

r - 在 R 中创建一个双模式频率矩阵

matlab - 将向量附加到空的MATLAB矩阵