TreeMap - 基于密钥的动态排序元素

时间:2014-05-20 10:28:20

标签: java collections

我想使用HashMap和元素排序。所以我选择了TreeMap。下面的代码给了我奇怪的答案,而不是我的预期

public class MapTest {

  public static class Key implements Comparable<Key>{
    private String key;
    private int count;

    public Key(String key, int count){
      this.key = key;
      this.count = count;
    }

    @Override
    public int hashCode() {
      return key.hashCode();
    }

    @Override
    public boolean equals(Object obj) {
      return key.equals(obj);
    }

    @Override
    public int compareTo(Key o) {
      return count - o.count;
    }
  }

  public static void main(String[] args) {
    Map<Key, Integer> map = new TreeMap<>();

    Key c = new Key("c", 4);

    map.put(new Key("a", 6), 1);
    map.put(new Key("b", 8), 1);
    map.put(c, 1);
    map.put(new Key("d", 2), 1);

    for(Map.Entry<Key, Integer> entry : map.entrySet()){
      System.out.println(entry.getKey().key);
    }

    //map.remove(c);
    map.put(c, null);
    c.count = 0;
    map.put(c, 1);

    for(Map.Entry<Key, Integer> entry : map.entrySet()){
      System.out.println(entry.getKey().key);
    }

  }
}

如果我使用map.remove()并添加元素,则会对其进行排序。否则,它总是按顺序返回元素 d c a b

为什么上面的代码不起作用? put(key,null)应该删除该值,如果插入了新值,则必须对其进行排序吗?

1 个答案:

答案 0 :(得分:2)

put(key, null)不会从地图中删除密钥。它仍然在地图中,只是映射到null。您想要remove(key)

在Map中用作键的对象应该是不可变的。在将密钥放入地图后,您正在修改密钥 - 但是地图没有机制来检测密钥并移动密钥,以便您意识到密钥最终位于无效位置。

这可能会使Map混淆到它根本不认为密钥存在于地图中的那一点,因为它会在它应该的位置查找它并且它不是&#39;那里。