【问题标题】:HashSet.clear() not working as expected [duplicate]HashSet.clear()没有按预期工作[重复]
【发布时间】:2017-04-13 23:45:01
【问题描述】:

我有一个哈希图,它有一个字符串哈希集作为值。我制定了一个测试代码 - 如下所示:

 public static void main(String args[]) {

    HashMap<String, HashSet<String>> hmap = new HashMap<String, HashSet<String>>();

    HashSet<String> set = new HashSet<String>();
    set.add("a");
    set.add("b");
    set.add("c");
    set.add("d");

    hmap.put("a", set);

    set.clear();// = new HashSet<String>();
    set.add("a");
    set.add("b");

    hmap.put("c", set);

    set.clear();// = new HashSet<String>();
    set.add("a");
    set.add("b");
    set.add("c");

    hmap.put("b", set);

    for (Entry<String, HashSet<String>> entry : hmap.entrySet())
    {
        System.out.println(entry.getKey() + " - " + entry.getValue());
    }
  }

我正在重用相同的哈希集来填充哈希图中的值。但我看到 hashset.clear() 没有按预期清除值。

上述代码我得到的代码是-

b - [b, c, a]
c - [b, c, a]
a - [b, c, a]

所以,所有的值都被最后一个 HashSet 覆盖了。我阅读了 clear() 的 javadoc,预期的行为是在调用 clear 时删除了 hashset 的元素。

当我使用 new HashSet 而不是 hashset.clear() 时的输出

b - [b, c, a]
c - [b, a]
a - [d, b, c, a]

这是我期待的输出。

我不想每次都使用set = new HashSet&lt;String&gt;的原因是我不想创建太多的hashset(hashmap的大小预计会很大)。我错过了什么吗?

感谢您的帮助。

【问题讨论】:

  • 您使用的是 same 集,因此您将获得的只是最后一次“清除”之后的最新值
  • 地图的每个值都是相同的集合对象
  • "我不想每次都使用 set = new HashSet 的原因是我不想创建太多的哈希集" - 但是你需要多个哈希集.一个还不够!
  • 如今写得好的问题通常很少见 :) 你有一个测试用例,你得到了什么,你期望什么,所以不能要求更多!
  • @maddie : 未来的 2 个提示 — 1) 使用 Java diamond operator 来简化泛型...这个 HashMap&lt;String, HashSet&lt;String&gt;&gt; hmap = new HashMap&lt;String, HashSet&lt;String&gt;&gt;(); 变成这个 HashMap&lt;String, HashSet&lt;String&gt;&gt; hmap = new HashMap&lt;&gt;(); 编译器可以在右边找出所需的类型-手边。 2)在声明中使用接口,创建实例时的类:Map&lt;String, Set&lt;String&gt;&gt; hmap = new HashMap&lt;&gt;();/Set&lt;String&gt; set = new HashSet&lt;&gt;();

标签: java hashmap hashset


【解决方案1】:

如果你打印 HashMap 的地址或者调试它,你可以看到所有的 Objects 都在引用同一个地址。

如果你使用的是eclipse或者netbeans,可以下断点,查看每一步的地址和状态。

祝你好运

【讨论】:

    【解决方案2】:

    事实上,您正在修改同一个 set 对象,即所有 3 个键(在 Map 内)都持有对同一个 set 对象的引用。

    因此,如果您想单独清除和处理每个 set,只需为 Map 内的每个键使用新的 set 对象:

    set = new HashSet<String>();
    

    【讨论】:

      猜你喜欢
      • 2014-12-17
      • 2012-11-01
      • 2011-12-01
      • 2021-08-14
      • 2013-03-25
      • 2021-01-16
      • 2015-10-16
      • 2017-12-22
      • 1970-01-01
      相关资源
      最近更新 更多