前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >TreeSet集合的add()方法的源码解析

TreeSet集合的add()方法的源码解析

作者头像
黑泽君
发布2018-10-12 10:08:11
5900
发布2018-10-12 10:08:11
举报
文章被收录于专栏:黑泽君的专栏黑泽君的专栏

用TreeSet存储Integer类型数据并遍历

  20,18,23,22,17,24,19,18,24

代码语言:javascript
复制
 1 package cn.itcast_05;
 2 
 3 import java.util.TreeSet;
 4 
 5 /*
 6  * TreeSet:能够对元素按照某种规则进行排序。
 7  *         排序有两种方式(具体那种方式取决于使用TreeSet的构造方法)
 8  *             A:自然排序
 9  *             B:比较器排序
10  * 
11  * TreeSet集合的特点:排序和唯一
12  * 
13  * 通过观察TreeSet的add()方法,我们知道最终要看TreeMap的put()方法。
14  */
15 public class TreeSetDemo {
16     public static void main(String[] args) {
17         // 创建集合对象
18         // TreeSet的无参构造:自然顺序进行排序
19         TreeSet<Integer> ts = new TreeSet<Integer>();
20 
21         // 创建元素并添加进集合
22         // 20,18,23,22,17,24,19,18,24
23         // Integer i1 = new Integer(200);
24         // ts.add(i1);
25         ts.add(20); // 自动装箱
26         ts.add(18);
27         ts.add(23);
28         ts.add(22);
29         ts.add(17);
30         ts.add(24);
31         ts.add(19);
32         ts.add(18);
33         ts.add(24);
34 
35         // 遍历集合
36         for (Integer i : ts) {
37             System.out.println(i);
38         }
39     }
40 }

TreeSet集合的add()方法的源码

代码语言:javascript
复制
---------------------------------------
interface Collection {
    ...
}

interface Set extends Collection {
    ...
}
---------------------------------------
class TreeSet implements Set {
    ...
    private static final Object PRESENT = new Object();
    private transient NavigableMap<E,Object> m;
    
    public TreeSet() {
         this(new TreeMap<E,Object>());
    }

    public boolean add(E e) {
        return m.put(e, PRESENT)==null;
    }
    ...
}
---------------------------------------
class TreeMap implements NavigableMap {
    ...
    public V put(K key, V value) {
       Entry<K,V> t = root; // 先造根,TreeSet集合底层数据结构是红黑树(是一个自平衡的二叉树)
       if (t == null) {
           compare(key, key); // type (and possibly null) check

           root = new Entry<>(key, value, null);
           size = 1;
           modCount++;
           return null;
       }
       
       int cmp;
       Entry<K,V> parent;
       // split comparator and comparable paths
       Comparator<? super K> cpr = comparator; // 因为用的是TreeSet的无参构造方法,是自然排序,没有用到comparator比较器
       if (cpr != null) {                      // 所以此时的comparator = null,则程序执行else里面的代码
           do {
               parent = t;
               cmp = cpr.compare(key, t.key);
               if (cmp < 0)
                   t = t.left;
               else if (cmp > 0)
                   t = t.right;
               else
                   return t.setValue(value);
           } while (t != null);
       } else {
           if (key == null)
               throw new NullPointerException();
           Comparable<? super K> k = (Comparable<? super K>) key; // 此接口Comparable强行对实现它的每个类的对象进行整体排序。这种排序被称为类的自然排序,类的 compareTo 方法被称为它的自然比较方法。。
           do {                                                   // 举例中我们使用的是包装类Intrger,而Integer类实现了Comparable接口。此例子是向上转型。
               parent = t;
               cmp = k.compareTo(t.key); // 类的 compareTo 方法被称为它的自然比较方法。
               if (cmp < 0)              // int compareTo(T o) 比较此对象与指定对象的顺序。如果该对象小于、等于或大于指定对象,则分别返回负整数、零或正整数。 
                   t = t.left;
               else if (cmp > 0)
                   t = t.right;
               else
                   return t.setValue(value);
           } while (t != null);
       }
       
       Entry<K,V> e = new Entry<>(key, value, parent);
       if (cmp < 0)
           parent.left = e;
       else
           parent.right = e;
       fixAfterInsertion(e);
       size++;
       modCount++;
       return null;
   }
   ...
}
---------------------------------------
    由上可知:真正的比较是依赖于元素的compareTo()方法,而这个方法compareTo()是定义在 Comparable接口里面的(抽象方法)。
    所以,你要想重写该方法,就必须是先实现 Comparable接口。这个接口表示的就是自然排序。
---------------------------------------
本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2018-03-27 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档