Skip to content

集合之 Set

面试题 Java Set

List 和 Set 的区别?

List,Set 都是继承自 Collection 接口。都是用来存储一组相同类型的元素的。

List 特点:元素有放入顺序,元素可重复 。

有顺序,即先放入的元素排在前面。

Set 特点:元素无放入顺序,元素不可重复。

无顺序,即先放入的元素不一定排在前面。不可重复,即相同元素在 set 中只会保留一份。所以,有些场景下,set 可以用来去重。

注意:set 在元素插入时是要有一定的方法来判断元素是否重复的。这个方法很重要,决定了 set 中可以保存哪些元素。

Set 如何保证元素不重复?

在 Java 的 Set 体系中,根据实现方式不同主要分为两大类。HashSet 和 TreeSet。

1、TreeSet 是二叉树实现的,Treeset 中的数据是自动排好序的,不允许放入 null 值
2、HashSet 是哈希表实现的,HashSet 中的数据是无序的,可以放入 null,但只能放入一个 null,两者中的值都不能重复,就如数据库中唯一约束

在 HashSet 中,基本的操作都是有 HashMap 底层实现的,因为 HashSet 底层是用 HashMap 存储数据的。当向 HashSet 中添加元素的时候,首先计算元素的 hashcode 值,然后通过扰动计算和按位与的方式计算出这个元素的存储位置,如果这个位置位空,就将元素添加进去;如果不为空,则用 equals 方法比较元素是否相等,相等就不添加,否则找一个空位添加。

TreeSet 的底层是 TreeMap 的 keySet(),而 TreeMap 是基于红黑树实现的,红黑树是一种平衡二叉查找树,它能保证任何一个节点的左右子树的高度差不会超过较矮的那棵的一倍。

TreeMap 是按 key 排序的,元素在插入 TreeSet 时 compareTo() 方法要被调用,所以 TreeSet 中的元素要实现 Comparable 接口。TreeSet 作为一种 Set,它不允许出现重复元素。TreeSet 是用 compareTo() 来判断重复元素的。

HashSet 实现原理?

1.基于 HashMap 实现的,默认构造函数是构建一个初始容量为 16,负载因子为 0.75 的 HashMap。封装了一个 HashMap 对象来存储所有的集合元素,所有放入 HashSet 中的集合元素实际上由 HashMap 的 key 来保存,而 HashMap 的 value 则存储了一个 PRESENT,它是一个静态的 Object 对象。

2.当试图把某个类的对象当成 HashMap 的 key,或试图将这个类的对象放入 HashSet 中保存时,重写该类的 equals(Object obj) 方法和 hashCode() 方法,而且这两个方法的返回值必须保持一致:当该类的两个的 hashCode() 返回值相同时,它们通过 equals() 方法比较也应该返回 true。
通常来说,所有参与计算 hashCode() 返回值的关键属性,都应该用于作为 equals() 比较的标准。

3.HashSet 的其他操作都是基于 HashMap 的。

如何取到 Set 集合中的第一个元素 ?

java
public static void main(String[] args) {
    Set set = new HashSet();
    set.add("tracy");
    set.add("hcx");
    set.add(123);
    set.add(4.5);
    System.out.println(set);//[4.5, hcx, tracy, 123]
    //第一种方法
    if(!set.isEmpty()){
        System.out.println(set.iterator().next());// 4.5
    }
    //第二种方法:将set集合转换成list集合 取第一个
    List list = new ArrayList(set);
    System.out.println(list.get(0));// 4.5
}

TreeMap 和 TreeSet 在排序时如何比较元素?

TreeSet 要求存放的对象所属的类必须是实现 Comparable 接口,该接口提供了比较元素的 compareTo 方法,当插入元素时会调该方法比较元素的大小.TreeMap 要求存放的键值对映射的键必须实现 Comparable 接口,从而根据键对元素进行排序。

Collection 工具类中的 sort 方法如何比较元素?

Collections 工具类的 sort 方法有两种重载的形式,
第一种要求传入的待排序容器中存放的对象比较实现 Comparable 接口以实现元素的比较,
第二种不强制性的要求容器中的元素必须可比较但是要求第二个参数,参数是 Comparator 接口的子类型(需要重写 compare 方法实现元素的比较)相当一个临时定义的排序规则,其实就是通过接口注入比较元素大小的算法,也是对回调模式的应用。

更新: 2020-09-25 14:18:01
原文: <https://www.yuque.com/fcant/notes/mhbmlv&gt;

最近更新