JDK 1.5前,ArrayList的底层实现
class A{
}
class B{
}
class MyArrayList{
int size;
int capacity;
Object [] array;
public MyArrayList(int capacity){
array = new Object[capacity];
size = 0;
this.capacity = capacity;
}
void add(Object e)
{
// 检测容量
array[size++] = e;
}
int size()
{
return size;
}
Object get(int index)
{
// 检测index不能越界
return array[index];
}
boolean isEmpty()
{
return 0 == size;
}
}
将对象添加到Object类型的数组中去,因为所有类的基类都是Object,所以将元素类型定义成 Object 类型,这样Object 类型的引用可以指向其他类型的对象了。
但是这样是不安全的:
public class Test{
public static void main(String[] args) {
MyArrayList list1=new MyArrayList(10);
list1.add(new A());
list1.add(new B());
A a=(A)list1.get(1);
}
}
A a=(A)list1.get(1);这一句看似没有问题,但是在运行时就会报出错误
list1的一号元素中存储的是B类型的对象,通过get(1)得到的是指向B对象的Object类型引用,所以要进行向下转型,要将其转为A类型,在编译时期这样的错误不会提示,只会到运行时抛出异常。
所以这样实现泛型的方法是不安全的。
在JDK1.5后,是这样实现泛型的。
class MyArrayList<E>{
int size;
int capacity;
E[] array;
public MyArrayList(int capacity){
array = (E[]) new Object[capacity];
size = 0;
this.capacity = capacity;
}
void add(E e)
{
// 检测容量
array[size++] = e;
}
int size()
{
return size;
}
E get(int index)
{
// 检测index不能越界
return (E)array[index];
}
boolean isEmpty()
{
return 0 == size;
}
}
在类名后增加了,这代表你要在其中添加E类型的元素。
public class Test{
public static void main(String[] args) {
MyArrayList<A> list1=new MyArrayList(10);
list1.add(new A());
list1.add(new B());
A a=(A)list1.get(1);
}
}
这时已经提前设定list1中元素为A类型,再添加B类型直接提示错误,编译时期就不通过。
注意: 泛型是作用在编译期间的一种机制,即运行期间没有泛型的概念
总结:
- 泛型是为了解决某些容器、算法等代码的通用性而引入,并且能在编译期间做类型检查。
- 泛型利用的是 Object 是所有类的祖先类,并且父类的引用可以指向子类对象的特定而工作。
- 泛型是一种编译期间的机制,即 MyArrayList 和 MyArrayList 在运行期间是一个类型。称为类型擦除。
- 泛型是 java 中的一种合法语法,标志就是尖括号 <>
来源:CSDN
作者:珠穆朗玛峰上的珠穆朗玛峰
链接:https://blog.csdn.net/qq_44267206/article/details/103753168