Home > Software design >  Is there a way to declare a 2 dimensional array of List in a type safe manner in Java? [duplicate]
Is there a way to declare a 2 dimensional array of List in a type safe manner in Java? [duplicate]

Time:09-17

Here is the code I have that works but with a type safety warning when I size and instantiate the array:

import java.util.ArrayList;
import java.util.List;

public class Test {

    private static final int MAX_ROWS = 2;
    private static final int MAX_COLS = 5;
    
    private List<String> _stringSets[][];
    
    public Test() {
        _stringSets = new List[MAX_ROWS][MAX_COLS];
        
        for(int row = 0; row < MAX_ROWS; row  ) {
            for(int col = 0; col < MAX_COLS; col  ) {
                _stringSets[row][col] = new ArrayList<String>();
            }
        }
    }
}

I tried

_stringSets = new List<String>[MAX_ROWS][MAX_COLS];

but this won't work...

CodePudding user response:

Lists are unidimensional and would be declared something like this:

List<String> myList = new ArrayList<>()

When you seem to be looking for a 2-dimensional arrays, which are declared something like this:

String[][] myArray = new String[n1][n2]

So what you want is probably something along those lines:

public class Test {

    private static final int MAX_ROWS = 2;
    private static final int MAX_COLS = 5;

    private String[][] stringSets;

    public Test() {
        stringSets = new String[MAX_ROWS][MAX_COLS];

        for(int row = 0; row < MAX_ROWS; row  ) {
            for(int col = 0; col < MAX_COLS; col  ) {
                stringSets[row][col] = row "-" col;
            }
        }
    }
}

CodePudding user response:

Never mind... Here's the correct answer...

https://docs.oracle.com/javase/tutorial/java/generics/restrictions.html#createArrays

Cannot Create Arrays of Parameterized Types You cannot create arrays of parameterized types. For example, the following code does not compile:

List<Integer>[] arrayOfLists = new List<Integer>[2];  // compile-time error

The following code illustrates what happens when different types are inserted into an array:

Object[] strings = new String[2];
strings[0] = "hi";   // OK
strings[1] = 100;    // An ArrayStoreException is thrown.

If you try the same thing with a generic list, there would be a problem:

Object[] stringLists = new List<String>[2];  // compiler error, but pretend it's allowed
stringLists[0] = new ArrayList<String>();   // OK
stringLists[1] = new ArrayList<Integer>();  // An ArrayStoreException should be thrown,
                                        // but the runtime can't detect it.

If arrays of parameterized lists were allowed, the previous code would fail to throw the desired ArrayStoreException.

CodePudding user response:

Generally not recommended to mix Arrays and Lists in this way. May want to consider using other data structures to achieve a similar effect instead. For example, you could create a Map that uses Position coordinates to achieve similar results.

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Objects;

public class MapList {

  private static Map<Position, List<Integer>> mapList;
  
  public static void main(String[] args) {
    final int MAX_X = 5;
    final int MAX_Y = 6;
    
    mapList = new HashMap<>();
    
    for(int i = 0; i < MAX_X; i  ) {
      for(int j = 0; j < MAX_Y; j  ) {
        mapList.put(new Position(i, j), new ArrayList<>());
        for(int k = 0; k < 5; k  ) {
          mapList.get(new Position(i, j)).add(k);
        }
      }
    }
    
    for(Position p : mapList.keySet())
      System.out.println(p.toString()   mapList.get(p));
  }
  
  private static class Position {
    private Integer x;
    private Integer y;
    
    public Position(Integer x, Integer y) {
      this.x = x;
      this.y = y;
    }
    
    @Override
    public boolean equals(Object o) {
      if(this == o)
        return true;
      if(o == null)
        return false;
      if(getClass() != o.getClass())
        return false;
      Position other = (Position) o;
      return x == other.x && y == other.y;
    }
    
    @Override
    public int hashCode() {
      return Objects.hash(x, y);
    }
    
    
    @Override
    public String toString() {
      return "(x:"   x   ", y:"   y   ")";
    }
  }
}
  • Related