Java 创建泛型数组
原文:https://www.studytonight.com/java-examples/creating-generic-array-in-java
数组用于存储相似类型数据的集合。用 Java 创建一个通用数组可能有点复杂。数组在运行时使用其元素的类型信息来分配内存。但是在泛型的情况下,由于类型擦除,该信息不可用。
泛型在编译时检查类型信息,在运行时没有信息可用。
对于数组,类型信息在运行时被检查,因为它们是协变的。这意味着我们可以将子类型数组赋给父类型(就像字符串[]赋给对象[])。
String[] strArr = new String[5];
Object[] objArr = strArr; //No Error
上述代码不会返回任何编译时错误。我们还可以向上面的数组添加不同的对象,而不用担心任何编译错误。但是对所有元素的类型检查是在运行时对数组进行的。如果在运行时发现任何差异,那么我们将得到ArrayStoreException
。
public class Demo
{
public static void main(String[] args)
{
String[] strArr = new String[5];
Object[] objArr = strArr; //No Error
objArr[0] = new Object();
objArr[1] = new Exception();
}
}
线程“main”Java . lang . arraystorexception:Java . lang . object 在 Demo.main(Demo.java:7)出现异常
建议使用像列表这样的集合框架,而不是通用数组。但是,如果我们在编译时有关于类型的一些信息,我们可以创建一个泛型数组。让我们学习如何在 Java 中创建一个泛型数组。
使用对象数组创建通用数组
我们可以创建一个带有对象数组的泛型类来模仿泛型数组。我们将在本课中使用一个get()
方法和一个set()
方法。get()方法将使用显式强制转换。
import java.util.Arrays;
class GenericArray<T>
{
private Object[] genericArr;
GenericArray(int size)
{
genericArr = new Object[size];
}
public T get(int index)
{
return (T) genericArr[index];
}
public void set(int index, T element)
{
genericArr[index] = element;
}
@Override
public String toString()
{
return Arrays.toString(genericArr);
}
}
public class Demo
{
public static void main(String[] args)
{
GenericArray<String> strArr = new GenericArray(3);
strArr.set(0, "five");
strArr.set(1, "ten");
strArr.set(2, "twenty");
GenericArray<Integer> intArr = new GenericArray(3);
intArr.set(0, 5);
intArr.set(1, 10);
intArr.set(2, 20);
GenericArray<Double> doubleArr = new GenericArray(3);
doubleArr.set(0, 5.0);
doubleArr.set(1, 10.0);
doubleArr.set(2, 20.0);
System.out.println("Integer Array: " + intArr);
System.out.println("String Array: " + strArr);
System.out.println("Double Array: " + doubleArr);
}
}
整数数组:[5,10,20] 字符串数组:[5,10,20] 双数组:[5.0,10.0,20.0]
如果我们只使用 get()和 set()方法,而不为用户提供对对象数组的直接访问,那么上述方法可以很好地工作。这里需要注意的一点是,即使是ArrayList
也使用对象数组来存储元素。ArrayList
不提供对此对象数组的直接访问。
使用反射创建通用数组
这种方法类似于上一节讨论的方法。唯一不同的是构造器会取类型信息,然后我们会用Array.newInstance()
方法初始化我们的数组。完整的实现如下所示。
import java.lang.reflect.Array;
import java.util.Arrays;
class GenericArray<T>
{
private T[] genericArr;
GenericArray(Class<T> classType, int size)
{
genericArr = (T[]) Array.newInstance(classType, size);
}
public T get(int index)
{
return genericArr[index];
}
public void set(int index, T element)
{
genericArr[index] = element;
}
@Override
public String toString()
{
return Arrays.toString(genericArr);
}
}
public class Demo
{
public static void main(String[] args)
{
GenericArray<String> strArr = new GenericArray(String.class, 3);
strArr.set(0, "five");
strArr.set(1, "ten");
strArr.set(2, "twenty");
GenericArray<Integer> intArr = new GenericArray(Integer.class, 3);
intArr.set(0, 5);
intArr.set(1, 10);
intArr.set(2, 20);
GenericArray<Double> doubleArr = new GenericArray(Double.class, 3);
doubleArr.set(0, 5.0);
doubleArr.set(1, 10.0);
doubleArr.set(2, 20.0);
System.out.println("Integer Array: " + intArr);
System.out.println("String Array: " + strArr);
System.out.println("Double Array: " + doubleArr);
}
}
整数数组:[5,10,20] 字符串数组:[5,10,20] 双数组:[5.0,10.0,20.0]
摘要
我们可以借助泛型类在 Java 中实现泛型数组。我们可以使用对象数组和适当的方法让用户与这个通用数组交互。ArrayList
类也使用了对象数组的概念。我们还可以使用 Array.newInstance()方法,让用户将类型信息传递给构造器。一些集合的泛型方法也使用类似的方法,如 LinkedList。总的来说,建议使用ArrayList
或LinkedList
来代替创建我们自己的通用列表。