一、泛型方法
1、声明语法
传递方法的泛型参数:调用的时候传递泛型参数
变量.< 实际的泛型类型>方法名();
方法中声明的泛型只能在当前方法中使用
类声明的泛型在整个类中都能用
每次调用方法都可以确定不一样的类型
二、声明受限制的泛型
受限泛型类
class 类名< T extends 类型>
{
}
受限泛型方法
public < T extends 类型> 返回值 方法名称(){
}
传递泛型参数的时候T必须是父类型或者是它的子类型
三、泛型通配符
在声明范型类的变量时可以使用通配符,在创建对象中不可以使用通配符。
1、声明的时候直接写?
2、使用通配符限制上界:<? extends 上界类型>
示例: 右边的<>中的类型必须是Number或者Number的子类型
List<? extends Number> list=new ArrayList();
List<? extends Object> list=new ArrayList();
不可以调用传递范型参数的方法。
调用带泛型返回值的方法,返回值按照上界类型对待
在声明变量的时候使用,可以对该变量接收的对象的类型中的泛型信息做一些限制,但是又有一定灵活性
3、<? super 下界类型>
右边的<>中的类型必须是Number或者Number的父类型或者实现的接口类型
可以调用传递范型参数的方法,参数按照下界类型来对待了
调用带泛型返回值的方法,返回值全部按照Object对待了
四、泛型擦除
1、概念 Java的泛型是伪泛型,这是因为Java在编译期间,类中声明的、接口中声明的、方法中声明的所
有的泛型信息都会被擦掉,在这些类生成的字节码文件中的正文中是不包含泛型信息,这个过程成为泛
型擦除,泛型擦除之后,原来在源文件中使用泛型类型的地方在字节码文件中会替换为Object,如果声
明的时候声明的受限制的泛型,那么字节码文件中会替换为限制类型。
2、泛型擦除的时间点:发生在编译期间
编译器首先检查类型安全—————————》进行编译擦除泛型信息———————-》字节码文件中
就没有泛型信息(Object)
3、泛型擦除的一些问题
1)因为存在泛型擦除,所以反射机制可以破坏泛型的特性。,比如创建Person类型对象的时候确定了
Person类的T为String.,使用反射机制调用setPersonId方法缺可以放置其它类型,因为字节码文件中的
setPersonId方法的参数为Object类型
2)因为存在泛型擦除,所以方法重写的时候会有冲突,但是JAVA语言已经想办法解决这个冲突,就是
使用桥方会在子类或者实现类的字节码文件中生成一个和父类同名同参的桥方法,在此桥方法中,调用
了我们自己在源文件中重写的方法
3)传递泛型参数的时候不能传递八中基本数据类型
4)Instanceof运算符后面的类型不能传递泛型参数,只能写原始类型、
五、泛型使用注意事项
1、不能将静态属性声明为泛型类型
2、不能在静态方法中使用类声明的泛型类型
3、不能创建泛型数组:new T[10],写法错误
4、使用Instanceof运算符比较的时候,类型不能包含泛型信息,因为有泛型擦除
5、传递泛型参数的时候不能使用8种基本数据类型
六、层次结构
1、Collection:以单个元素为单位进行存放
List:有序集合,每个元素都有一个和存入顺序吻合的索引编号,并且,我们可以依靠位置编号对
集合中的元素进行操作
ArrayList:实现类
LinkedList
Vector
Set:无序集合,每个元素没有位置编号,程序员也不能用位置编号对集合中的元素进行操作,不
能存入重复值
HashSet
LinkedHashSet
TreeSet
2、Map:以键值对为单位进行存放HashMap
LinkedHashMap
TreeMap
Hashtable
七、Collection
存放若干个独立元素
增加操作
•boolean add(Object element) :增加一个元素
•boolean addAll(Collection collection) :将集合中的所有元素进行增加
移除操作
•boolean remove(Object element) :移除一个元素,依靠equals方法进行 比对。注意。你的元素类型
有没有重写equals方法,如果有重写,那就调用重写过的equals,没有重写,调用Object类的equals
void clear() :清空所有元素
•void removeAll(Collection collection):将在集合中的元素移除, 依靠equals方法进行 比对
•void retainAll(Collection collection) :将不在集合中的元素移除, 依靠equals方法进行 比对
查询操作:
•int size() :集合实际元素的个数
•boolean isEmpty() :判断集合是否为空
•boolean contains(Object element) :判断集合中有没有包含一个元素
•boolean containsAll(Collection collection) :判断集合中有没有包含另一个集合中的元素
•Iterator iterator() :得到迭代器
八、List
数据结构:
逻辑存储结构
线性的:每个元素有0或者1个前驱元素,有0个或者1个后继元素
树结构:每个元素有一个或0个前驱元素,有0个多个后继元素
图结构:每个元素有多个或0个前驱元素,有0个多个后继元素
物理存储结构
线性存储:元素在内存中是连续存放的
链式存储:元素在内存中不是连续存放的
List: 有序集合,可以放入重复(equals进行判断)元素,会按照存入的顺序给每个元素编号,遍历的
时候也可以依靠编号进行遍历
示例:
1、ArrayList
常用API
构造方法
底层:底层是一个Object类型的数组,初始的默认长度10,也可以指定长度,初始长度如果满了,
底层进行自动扩容,扩容为原来的1.5倍oldCapacity + (oldCapacity >> 1)。10—->15—->22,如
果对集合中的元素个数可以预估,那么建议预先指定一个合适的初始容量,可以减少扩容的次数
List l =new ArrayList();
线程不安全,性能高。
优点:查找效率高,向末尾添加、删除元素也可以
缺点:增加 、删除牵扯到数组的扩容和移动,效率低
2、LinkedList:
常用API:
构造方法
LinkedList():无参数
LinkedList(Collection c):带集合类型的参数
其他方法(实现类独有的方法)
addFirst:给链表头添加元素
addLast:给链表末尾添加元素
底层是一个链表(双向)结构,添加的元素和前后元素的地址信息会封装成一个Node类型的对
象,放到集合中,不是线性存储,内存中是链式存储,不连续的空间。
优点:增加、删除效率高
缺点:查找效率低