1

If you add a int[][] to a list, it will not add the value of the array, but the location of the array. How can I add the value of an array to a list. This is the code (This is just an example and might have small errors in it):

public class Main {
    int[][] matrix = new int[2][2];
    List<int[2][2]> matrixList = new ArrayList<>();

    public static void main(String[] args) {
        for(int i = 0; i < 4; i++){
            matrixList.add(matrix);
            matrix = matrixCalc(matrix);
        }       

        for(int i = 0; i < 4; i++) {
            System.out.println(Arrays.deepToString(matrixList.get(i)));
        }
      public int[][] matrixCalc(int[][] m){
        //do various calculations with m
        ...

        return m;
      }
   }
}

I want the output to have different matrixes that are calculated by the calculate method.

example of out put i want to get:

{{0,1}{5,7}}
{{2,0}{2,4}}
{{8,1}{4,8}}
{{3,3}{7,9}}

output I would get this way (WRONG!)

  {{3,3}{7,9}}
  {{3,3}{7,9}}
  {{3,3}{7,9}}
  {{3,3}{7,9}}
Jongware
  • 22,200
  • 8
  • 54
  • 100
  • in matrixCalc you are changing the same array instance, not a new one, so you are adding to the list the same instance 4 time. – fantarama Mar 08 '16 at 14:52
  • `List matrixList = new ArrayList<>()` - mindblowingly complicated structure! – NickJ Mar 08 '16 at 14:52
  • Have a look at [SO40480](https://stackoverflow.com/questions/40480/is-java-pass-by-reference-or-pass-by-value). Your list only contains multiple references to one object. – blafasel Mar 08 '16 at 14:57
  • @fantarama I get why its working this way, but I want to add the value of matrix to a list while keeping the variable matrix the same. Do you know how I can accomplish that? –  Mar 08 '16 at 21:36

3 Answers3

1

EDIT: After OP's comment I removed my entire answer (you can still find a screenshot of it here; or look in the history of the edits).

If I'm not mistaken, you send an empty Array to the method matrixCalc? For the calculations method I need a matrix with the same value as I just put on top of the stack.

In that case it's a bit different, although the problem is still having the same reference to matrix, so we'll have to change this. To copy the data from one 2D-array to a new one (with a new reference), we should make a separate copy-method. In Java there is the Arrays.copyOf-method (or alternatively System.arraycopy) for a 1D-array, but for a 2D-array you should make a method yourself. So your code becomes something like this:

public class Main {
    int[][] previousMatrix = new int[2][2];
    List<int[2][2]> matrixList = new ArrayList<>();

    public static void main(String[] args) {
        for(int i = 0; i < 4; i++){
            int[][] matrix = matrixCalc(previousMatrix);
            matrixList.add(matrix);
            previousMatrix = copy2dArray(matrix);
        }       

        for(int i = 0; i < 4; i++) {
            System.out.println(Arrays.deepToString(matrixList.get(i)));
        }
    }

    public int[][] matrixCalc(int[][] m){
        //do various calculations with m
        ...

        return m;
    }

    private int[][] copy2dArray(int[][] original){
        int[][] copy = new int[original.length][];
        for(int i = 0; i < original.length; i++){
            copy[i] = Arrays.copyOf(original[i], original[i].length);
        }
        return copy;
    }
}

Alternatively, you could make a new 2D array at the start of your matrixCalc method and fill and return that, instead of the parameter given. But, since I didn't knew what kind of calculations you are doing in your matrixCalc method I can't really give an example of this. It will look something like this:

public int[][] matrixCalc(int[][] m){
    int[][] n = new int[2][2];
    //do various calculations with m,
    //but save the result in n
    ...

    return n;
}
Kevin Cruijssen
  • 9,153
  • 9
  • 61
  • 135
  • Thx for your reply. If I'm not mistaken, you send an empty Array to the method matrixCalc? For the calculations method I need a matrix with the same value as I just put on top of the stack. –  Mar 08 '16 at 21:43
  • I think this might be the solution! I'll add it to my code and hope for the best ;) –  Mar 09 '16 at 13:10
0

Try with:

public class Main {
    int[][] matrix = new int[2][2];
    List<int[2][2]> matrixList = new ArrayList<>();

    public static void main(String[] args) {
        for(int i = 0; i < 4; i++){
            matrixList.add(matrixCalc(matrix));
        }       

        for(int i = 0; i < 4; i++) {
            System.out.println(Arrays.deepToString(matrixList.get(i)));
        }
      public int[][] matrixCalc(int[][] m){
        int[][] newMatrix = new int[2][2];

        ... do calc then put results on newMatrix

        return newMatrix;
      }
   }
}
fantarama
  • 862
  • 6
  • 14
  • matrix = new int[2][2]; clears the matrix and adds {{0,0}{0,0}} to the matrixList. I have also tried to put that after the matrixList.add(matrix), but then it clears the matrix and every matrix inside the list aswell. –  Mar 08 '16 at 21:33
  • I've edited the code, use the matrix variable to hold the state, but matrixCalc must return a new matrix – fantarama Mar 09 '16 at 10:07
  • I dont want to keep calculating with the same matrix, the output of matrixCalc should be the next matrix I calculate with. For exampel: matrix = 3 --> MatrixList.add(3) --> matrixCalc(3) --> matrix = 5 --> MatrixList.add(5) --> matrixCalc(5) --> matrix = 2 --> matrixList.add(2) -- matrixCalc(2). It is a recursive method that saves every output of matrixCalc to a list and then cals matrixCalc with the matrix returned from matrixCalc –  Mar 09 '16 at 13:04
  • so post the matrixCalc real code, otherwise how we could understand that is a recursive function? However the problem is still the same, you need to add to the list new instances. – fantarama Mar 09 '16 at 14:17
0

Some background info: The programm I'm writing uses backtracking. I need to save boardstates into an stack and also add stuff to the board. Here [matrix] stands for the board and [matrixList] for the saved boardstates. When I do calculations I need to have the current board then after I changed something. I need to add the new board on top of the stack and continue changing the new board.