第一次调用后,删除迭代器的方法不起作用

时间:2012-06-27 13:00:37

标签: java iterator

我正在尝试将一些集合分成不相交的集合。例如,如果我有这5套:

  

[[1,3],[2],[1,5],[6,8],[1,7]]

我希望得到这样的结果:

  

[[2],[6,8],[1,3,5,7]]

以下是代码:

import java.util.*;

public class SetTest {

public static void main(String[] args) {
    // ---- Initialisation
    Set<Set<Integer>> groups = new LinkedHashSet<Set<Integer>>();
    for (int[] set : new int[][] { {1, 3 }, {2 }, {1, 5 }, {6, 8 }, {1, 7} }) {
        Set<Integer> group = new TreeSet<Integer>();
        for (int i : set) {
            group.add(i);
        }
        groups.add(group);
    }
    System.out.println(groups);
    // ---- Grouping values in disjoint sets
    for (Iterator<Set<Integer>> iterator = groups.iterator(); iterator.hasNext();) {
        Set<Integer> group = iterator.next();
        System.out.println(String.format(" + Checking %20s in \t %s", group, groups));
        for (Set<Integer> other : groups) {
            if (!group.equals(other) && !Collections.disjoint(group, other)) {
                other.addAll(group);
                iterator.remove();
                System.out.println(String.format(" - Removed  %20s -> \t %s", group, groups));
                break;
            }
        }
    }
    System.out.println(groups);
}
}

我在集合上使用迭代器,我想将2个集合在一起,删除其中一个。但是,我遇到了Iterator.remove()方法的问题 这个程序打印的是:

[[1, 3], [2], [1, 5], [6, 8], [1, 7]]
 + Checking               [1, 3] in      [[1, 3], [2], [1, 5], [6, 8], [1, 7]]
 - Removed                [1, 3] ->      [[2], [1, 3, 5], [6, 8], [1, 7]]
 + Checking                  [2] in      [[2], [1, 3, 5], [6, 8], [1, 7]]
 + Checking            [1, 3, 5] in      [[2], [1, 3, 5], [6, 8], [1, 7]]
 - Removed             [1, 3, 5] ->      [[2], [1, 3, 5], [6, 8], [1, 3, 5, 7]]
 + Checking               [6, 8] in      [[2], [1, 3, 5], [6, 8], [1, 3, 5, 7]]
 + Checking         [1, 3, 5, 7] in      [[2], [1, 3, 5], [6, 8], [1, 3, 5, 7]]
 - Removed          [1, 3, 5, 7] ->      [[2], [1, 3, 5, 7], [6, 8], [1, 3, 5, 7]]
[[2], [1, 3, 5, 7], [6, 8], [1, 3, 5, 7]]

第一次删除[1, 3]按预期工作,但其余时间,它不会删除该项目。我认为这是因为我使用addAll(),但为什么呢?因为我没有在groups中进行更改;我只更改其中的元素(other) - 并且引用是相同的,对吧?

1 个答案:

答案 0 :(得分:2)

HashSet的元素应该具有稳定的hashCode,但是当您迭代外部集合时,您正在改变它们。这在不可预测但有记录的方式上失败了。

TreeSet中,通过变异更改元素的排序顺序也可能存在问题。