泛型
JDK1.5以后出现的机制
概述
泛型是一种特殊的类型,它把指定类型的工作推迟到客户端代码声明并实例化类或方法的时候进行。
也被成为参数化类型,可以把类型当做参数一样传递过来,在传递过来之前我不明确,但是在使用的时候我就用明确了
为什么会有泛型呢?
早期的Object类型可以接收任意的对象类型,但是在实际的使用中,会有类型转换的问题。也就存在这种隐患,所以java提供了泛型来解决这个安全问题
优点
1、提高了程序的安全性
2、将运行期遇到的问题转移到了编译器
3、省去了类型强转的麻烦
应用
泛型类
把泛型定义在类上
格式:public class 类名<泛型类型1,...>
注意:泛型类型必须是引用类型
泛型方法
把泛型定义在方法上
格式:public <泛型类型> 返回类型 方法名(泛型类型 变量名)
该方法在调用时可以接收不同类型的参数,根据传递给泛型方法的参数类型,编辑器适当地处理每一个方法调用
泛型接口
把泛型定义在接口上
格式:public interface 接口名<泛型类型1...>
泛型高级(通配符)
泛型通配符<?>
任意类型,如果没有明确,那么就是Object以及任意的java类了
? extends E
向下限定,E以及其子类
? super E
向上限定,E以及其父类
增强for循环
概述
简化数组和Collection集合的遍历
格式
for(元素数据类型 变量:数组或者Collection集合){
使用变量即可,该变量就是集合元素
}
优点
简化遍历
注意事项
1、增强for的目标要判断是否为null
2、增强for本质还是iterator迭代器,循环内不能对集合进行操作
3、public inerface Iterable<T> 实现这个接口允许对象成为“foreach”语句的目标
数组集合相互转换
集合转数组
<T> T[] toArray(T[] a);
ArrayList<Integer> arr01 = new ArrayList<>();
arr01.add(1);
arr01.add(2);
arr01.add(3);
Integer[] arr0101=arr01.toArray(new Integer[arr01.size()]);
数组转集合
1、Arrays.asList()
注意该方法的返回值是java.util.Arrays类中一个私有静态内部类java.util.Arrays.ArrayList, 它并非java.util.ArrayList类。 java.util.Arrays.ArrayList类具有set(),get(),contains()等方法, 但是不支持添加add()或删除remove()方法,调用这些方法会报错。
解决方法是新建一个List对象, 并且在构造方法加入返回的strList, 然后再add新元素:
Integer[] int01={1,2,2,3};
List<Integer> integers = Arrays.asList(int01);
2、Collections.addAll()
String[] array={"1","2","3"};
List<String> resultList = new ArrayList<>();
Collections.addAll(resultList,array);
3、List.of()
此方法是Java9新增方法,定义在List接口内,并且为静态方法,因此可直接通过类名调用
String[] array={"1","2","3"};
List<String> resultList=List.of(array);
静态导入
概述
格式:import static 包名...类名.方法名;
可以直接导入到方法的级别
注意事项
1、方法必须是静态的
2、如果测试类内也有同名的静态类,则默认优先使用本类内;若想使用导入的静态方法,则需要输入前缀(包名...类名.方法名)
3、如果有多个同名的静态方法,容易不知道使用谁。这个时候要使用,必须加前缀。由此可见,意义不大,所以一般不用,但是要能看懂
可变参数
概述
定义方法的时候不知道该定义多少个参数
格式
修饰符 返回值类型 方法名(数据类型... 变量名){}
注意:
这里的变量其实是一个数组
如果一个方法有可变参数,并且有多个参数,那么,可变参数肯定是最后一个
举例:public static <T> List<T> asList(T.. a)(Arrays工具类中的一个方法)
HashSet类
继承自Set接口(一个不包括重复元素的collection)
概述
线程不安全,效率高
元素唯一性
不保证set的迭代顺序(特别是它不保证该顺序恒久不变)
HashSet如何保证元素唯一性
底层数据结构是哈希表(元素是链表的数组)
哈希表依赖于哈希值存储
添加功能底层依赖两个方法:
int hashCode()
boolean equals(Object obj)
通过观察源码发现,
要想知道是否将元素插入到集合,先看元素的HashCode()值是否相同
如果相同,,继续判断equals()方法
返回true,说明元素的内容一样,重复了,就不添加
返回false,说明元素的呃内容不重复,只是哈希值一样,就会添加集合中
如果连哈希值都不一样,就直接添加到集合中
LinkedHashSet类
底层是哈希表和链表组成
概述
线程不安全
元素有序唯一
由链表保证元素有序
由哈希表保证元素唯一