一、Collection 集合
- 概述
- 集合是java中提供的一种容器,可以用来存储多个数据。
- 集合和数组既然都是容器,它们有啥区别呢?
-
- 数组的长度是固定的。集合的长度是可变的。
- 数组中存储的是同一类型的元素,可以存储基本数据类型值。集合存储的都是对象。而且对象的类型可以不一致。在开发中一般当对象多的时候,使用集合进行存储。
-
- 集合框架
-
- 任意的单列集合都可以使用 Collection 接口中的方法
- public boolean add(E e)
- 把给定的对象添加到当前集合中 。
- public void clear()
- 清空集合中所有的元素。
- public boolean remove(E e)
- 把给定的对象在当前集合中删除
- public boolean contains(E e)
- 判断当前集合中是否包含给定的对象。
- public boolean isEmpty()
- 判断当前集合是否为空。
- public int size()
- 返回集合中元素的个数。
- public Object[] toArray()
- 把集合中的元素,存储到数组中。
- public boolean add(E e)
- 任意的单列集合都可以使用 Collection 接口中的方法
二、Iterator 迭代器
- Iterator 接口
- 作用
- 可以在类或方法中预支地使用未知的类型。
- 好处
- 避免了类型转换的麻烦,存储的是什么类型,取出的就是什么类型。
- 把运行期异常(代码运行之后会抛出的异常),提升到了编译期(写代码的时候会报错)。
- 弊端
- 泛型是什么类型,只能存储什么类型的数据。
- 泛型不存在继承关系。
- 创建集合对象,不使用泛型
- 好处
- 集合不使用泛型,默认的类型就是 Object 类型,可以存储任意类型的数据。
- 弊端
- 不安全,会引发异常。
- 发生转换异常。
- 不安全,会引发异常。
- 好处
- 泛型,用来灵活地将数据类型应用到不同的类、方法、接口当中。将数据类型作为参数进行传递。
- 类
- 格式
- 修饰符 class 类名<代表泛型的变量> { }
- 创建对象的时候确定泛型的数据类型。
- 举例
- public class GenericClass<E>{
- private E name;
- get/set方法;
- }
- 创建对象
- 创建 GenericClass 对象,泛型使用 Integer 类型。
- GenericClass<Integer> gc = new GenericClass<>();
- 创建 GenericClass 对象,泛型使用 String 类型。
- GenericClass<String> gc2 = new GenericClass<>();
- 创建 GenericClass 对象,泛型使用 Integer 类型。
- public class GenericClass<E>{
- 格式
- 方法
- 定义含有泛型的方法:泛型定义在方法的修饰符和返回值类型之间。
- 格式
- 修饰符 <泛型> 返回值类型 方法名(参数列表(使用泛型)) {
- 方法体
- } 含有泛型的方法,在调用方法的时候确定泛型的数据类型。
- 传递什么类型的参数,泛型就是什么类型。
- 修饰符 <泛型> 返回值类型 方法名(参数列表(使用泛型)) {
- 举例
- public class GenericMethod {
- //定义一个含有泛型的方法
- public <M> void method01(M m){}
- //定义一个含有泛型的静态方法
- public static <S> void method02(S s){}
- }
- 使用
- GenericMethod gm = new GenericMethod();
- gm.method01(10);
- gm.method01("abc");
- 传递什么类型,泛型就是什么类型。
- GenericMethod.method02("静态方法");
- 不建议创建对象使用,通过类名.方法名(参数)可以直接使用。
- public class GenericMethod {
- 格式
- 定义含有泛型的方法:泛型定义在方法的修饰符和返回值类型之间。
- 接口
- 第一种使用方式
- 定义接口的实现类,实现接口,指定接口的泛型。
- 举例
- Scanner 类实现了 Iterator 接口,并指定接口的泛型为String,所以重写的 next() 方法泛型默认就是 String。
- public interface Iterator<E> {
- E next();
- }
- public final class Scanner implements Iterator<String>{
- public String next() {}
- public interface Iterator<E> {
- Scanner 类实现了 Iterator 接口,并指定接口的泛型为String,所以重写的 next() 方法泛型默认就是 String。
- 举例
- 定义接口的实现类,实现接口,指定接口的泛型。
- 第二种使用方式
- 接口使用什么泛型,实现类就使用什么泛型,类跟着接口走。
- 就相当于定义了一个含有泛型的类,创建对象的时候确定泛型的类型。
- public interface List<E>{
- boolean add(E e);
- E get(int index);
- }
- public class ArrayList<E> implements List<E>{
- public boolean add(E e) {}
- public E get(int index) {}
- }
- public interface List<E>{
- 就相当于定义了一个含有泛型的类,创建对象的时候确定泛型的类型。
- 接口使用什么泛型,实现类就使用什么泛型,类跟着接口走。
- 第一种使用方式
- 类
- 泛型通配符
- 当使用泛型类或者接口时,传递的数据中,泛型类型不确定,可以通过通配符 <?> 表示。但是一旦使用泛型的通配符后,只能使用Object类中的共性方法,集合中元素自身方法无法使用。
- 通配符的基本使用
- 不知道使用什么类型来接收的时候,此时可以使用 ?
- ?表示未知通配符。
- 此时只能接受数据,不能往该集合中存储数据。
- 不知道使用什么类型来接收的时候,此时可以使用 ?
- 通配符的高级使用
-
- List 接口的特点
五、LinkedList 集合
- 集合数据存储的结构是链表结构。
- LinkedList 集合的特点
- 底层是一个链表结构。
- 查询慢,增删快。
- 里边包含了大量操作首尾元素的方法
- 注意:使用 LinkedList 集合特有的方法,不能使用多态。
- 底层是一个链表结构。
- 常用方法
- public void addFirst(E e)
- 将指定元素插入此列表的开头。
- public void addLast(E e)
- 将指定元素添加到此列表的结尾。
- public void push(E e)
- 将元素推入此列表所表示的堆栈。
- 此方法等效于 addFirst(E)。
- 将元素推入此列表所表示的堆栈。
- public E getFirst()
- 返回此列表的第一个元素。
- public E getLast()
- 返回此列表的最后一个元素。
- 此方法等效于 add()
- 返回此列表的最后一个元素。
- public E removeFirst()
- 移除并返回此列表的第一个元素。
- public E removeLast()
- 移除并返回此列表的最后一个元素。
- public E pop()
- 移除并返回此列表的最后一个元素。
- 此方法相当于 removeFirst
- 移除并返回此列表的最后一个元素。
- public boolean isEmpty()
- 如果列表不包含元素,则返回true。
- public void addFirst(E e)
六、Set 接口
-
- HashSet 存储自定义类型元素
- 必须重写 hashCode 方法和 equals 方法。
- HashSet 存储自定义类型元素
- LinkedHashSet
- 保证了元素唯一。
- 保证元素有序。
- 特点
- 底层是一个哈希表(数组+链表/红黑树) + 链表。
- 多了一条链表(记录元素的存储顺序),保证元素有序。
- 底层是一个哈希表(数组+链表/红黑树) + 链表。
- 哈希值
- 是一个十进制的整数,由系统随机给出。
- 就是对象的地址值,是一个逻辑地址,是模拟出来得到地址,不是数据实际存储的物理地址。
- 在Object类有一个方法,可以获取对象的哈希值。
- int hashCode()
- 返回该对象的哈希码值。
- int hashCode()
- 在Object类有一个方法,可以获取对象的哈希值。
- 就是对象的地址值,是一个逻辑地址,是模拟出来得到地址,不是数据实际存储的物理地址。
- 是一个十进制的整数,由系统随机给出。
- 可变参数
- 使用前提
- 当方法的参数列表数据类型已经确定,但是参数的个数不确定,就可以使用可变参数。
- 格式
- 修饰符 返回值类型 方法名(数据类型...变量名){}
- 原理
- 可变参数底层就是一个数组,根据传递参数个数不同,会创建不同长度的数组,来存储这些参数。
- 传递的参数个数,可以是0个(不传递),1,2...多个。
- 可变参数底层就是一个数组,根据传递参数个数不同,会创建不同长度的数组,来存储这些参数。
- 注意事项
- .一个方法的参数列表,只能有一个可变参数。
- 如果方法的参数有多个,那么可变参数必须写在参数列表的末尾。
- 使用前提
七、Collentions
- 集合工具类,用来对集合进行操作。
- 常用方法
- public static <T> boolean addAll(Collection<T> c, T... elements)
- 往集合中添加一些元素。
- public static void shuffle(List<?> list)
- 打乱顺序:打乱集合顺序。
- public static <T> void sort(List<T> list)
- 将集合中元素按照默认规则排序。
- 默认升序
- 使用前提
- 被排序的集合里边存储的元素,必须实现 Comparable,重写接口中的方法 compareTo() 定义排序的规则。
- Comparable接口的排序规则
- 自己(this)-参数
- 升序
- 自己(this)-参数
- 将集合中元素按照默认规则排序。
- public static <T> void sort(List<T> list,Comparator<? super T> )
- 将集合中元素按照指定规则排序。
- 排序规则
- o1-o2:升序
- Comparator 和 Comparable 的区别
- Comparable:自己(this)和别人(参数)比较,自己需要实现 Comparable 接口,重写比较的规则 compareTo()方法。
- 强行对实现它的每个类的对象进行整体排序。这种排序被称为类的自然排序,类的 compareTo 方法被称为它的自然比较方法。只能在类中实现compareTo() 一次,不能经常修改类的代码实现自己想要的排序。实现此接口的对象列表(和数组)可以通过 Collections.sort(和Arrays.sort)进行自动排序,对象可以用作有序映射中的键或有序集合中的元素,无需指定比较器。
- Comparator:相当于找一个第三方的裁判,比较两个。
- 强行对某个对象进行整体排序。可以将Comparator 传递给 sort 方法(如 Collections.sort 或 Arrays.sort),从而允许在排序顺序上实现精确控制。还可以使用 Comparator 来控制某些数据结构(如有序 set 或有序映射)的顺序,或者为那些没有自然顺序的对象 collection 提供排序。
- Comparable:自己(this)和别人(参数)比较,自己需要实现 Comparable 接口,重写比较的规则 compareTo()方法。
- public static <T> boolean addAll(Collection<T> c, T... elements)
- 常用方法
八、Map
- 概述
- 现实生活中,我们常会看到这样的一种集合:IP地址与主机名,身份证号与个人。这种一一对应的关系,就叫做映射。
- 必须复写对象的 hashCode 和 equals 方法。
- 对 List接口,Set接口,Map接口
- 里边增加了一个静态的方法 of,可以给集合一次性添加多个元素。
- 格式
- static <E> List<E> of(E... elements)
- 适用前提
- 当集合中存储的元素的个数已经确定了,不在改变时使用。
- 注意事项
- of 方法只适用于 List 接口,Set 接口, Map 接口,不适用子接口的实现类。
- of 方法的返回值是一个不能改变的集合,集合不能再使用 add,put 方法添加元素,会抛出异常。
- Set 接口和 Map 接口在调用 of 方法的时候,不能有重复的元素,否则会抛出异常。
- 格式
- 里边增加了一个静态的方法 of,可以给集合一次性添加多个元素。
十、集合完结。