1. Problem
Java does not allow you to create arrays of generic classes:
Set<String>[] sets = new Set<String>[5];
2. Workaround 1: Raw types
@SuppressWarnings("unchecked")
Set<String>[] sets = new Set[5];
3. Workaround 2: Use a List instead
List<Set<String>> sets = new ArrayList<>();
4. Workaround 3: Non-generic subclass
You can create a non-generic subclass (local if you like) that extends the generic class:
class StringHashSet extends HashSet<String> {}
Set<String>[] sets = new StringHashSet[5];
5. What’s the reason for this limitation?
Let’s illustrate what could happen with an example:
// Suppose this was allowed
Set<String>[] arr = new Set<String>[5];
// Arrays are covariant:
Object[] oa = arr;
// Putting a Set<Integer> in arr!
oa[0] = Collections.singleton(3);
// Looks type safe but isn't!
String s = arr[0].iterator().next();
Arrays actually have the same problem. This program does in fact even compile:
String[] arr = new String[5];
Object[] oa = arr;
oa[0] = 5; // Eeek! An Integer in a String[]?
String s = arr[0];
Here however, oa[0] = 5
throws an ArrayStoreException
in runtime. In other words, when generics were introduced the designers traded some expressiveness for some added compile time type safety.