TreeSet去重问题,这种情况为何无法去重?

1,这种情况是compare方法里面用equals比较,无法去重,控制台比较次数为6,应该是少了一次“规模指标”比“规模指标”的,不知道为啥。
image.png

image.png

2,这种compare方法里面用了compareTo可以去重,但是只比较了4次。
image.png

3,求大佬指出为何一种可以另一种不可以呢?为什么一个是6次一个是4次呢?

阅读 5.4k
1 个回答

因为你的Comparator实现的不对,TreeSet是使用TreeMap来判断重复的,你这里只要不相等就返回一个比0大的数,意味着你在告诉程序:规模指标<效益指标<资产质量指标<规模指标。所以就不会去重的,判断次数不一样也是这个原因,可以去了解下红黑树

因为你的Comparator实现的不对,TreeSet是使用TreeMap来判断重复的,你这里只要不相等就返回一个比0大的数,意味着你在告诉程序:规模指标<效益指标<资产质量指标<规模指标。所以就不会去重的,判断次数不一样也是这个原因,可以去了解下红黑树。

附上TreeMap里面比较节点是否相等的代码:

public V put(K key, V value) {
    ...
    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);
    ...
}

举个例子:
假如你写入的数据分别是:A、B、C、A

  1. 插入A:树没有节点,所以A作为根节点
  2. 插入B:存在根节点A,compare方法返回1,表示B比A大,所以B作为A的右节点
  3. 插入C:比较A和C,C比A大,继续跟A的右节点(比A大的值)比较,最终插到B的右节点。然后,红黑树调整,B作为根节点,A在B的左边的子节点,C在B的右边的子节点
  4. 插入A,这时会先跟根节点B比较,A比B大,所以继续跟B右侧的子节点比较(第一次写入的A在B的左侧,所以新写入的A不会再跟原来的A作比较),最终A作为C的右侧子节点
撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题