Java集合:在一个循环中比较集合中的元素并删除

4

假设我有一组地理位置(格式为国家 > 地区 [ > 城镇 [ > 区域]]),我想要移除重叠的位置(例如,欧洲 > 德国欧洲 > 德国 > 德累斯顿欧洲 > 德国 > 汉堡 重叠,因此后两个必须被移除)。我发现需要使用两个迭代器实例来实现这样的功能:

final Iterator<Location> outerIterator = locations.newIterator();
while (outerIterator.hasNext()) {
    final Location outer = outerIterator.next();
    final Iterator<Location> innerIterator = locations.newIterator();
    while (innerIterator.hasNext()) {            
        final Location inner = innerIterator.next();
        if (!inner.equals(outer)) {
            if (inner.overlaps(outer)) outerIterator.remove();
            else if (outer.overlaps(inner)) innerIterator.remove();
        }
    }
}

但是我无法为同一集合获取新的Iterator。我的算法是否有误或者有正确的方法可以实现?


最终代码使用提供的答案Carl Smotricz的建议,看起来像这样:
final Iterator<JobLocation> outerIterator = locations.iterator();
while (outerIterator.hasNext()) {
    final JobLocation outer = outerIterator.next();         
    final Iterator<JobLocation> innerIterator = locations.iterator();
    while (innerIterator.hasNext()) {
        final JobLocation inner = innerIterator.next();
        if (!inner.equals(outer) && inner.overlaps(outer)) {
            outerIterator.remove();
            break;
        }
    }
}

你应该考虑使用更好的数据结构,比如层次结构,比如树。这会让你的生活变得更加轻松。事情会更容易管理、阅读、更快等等。 - polygenelubricants
这段代码是为GWT编写的,而且已经有点复杂了。实际上,层次树是保存在服务器端的,我只是通过RPC获取客户端已经计算好的实例。 - shaman.sir
3个回答

3

你确定你想在内部循环中增加outerIterator吗?


2

如果你从外部迭代器中删除一个对象,那么你需要立即跳出内部循环。我不确定这是否完全解决了你的问题,但它可能会让你更进一步。

如果仍然有问题,请展示错误信息和/或异常!


我需要移除几个元素,所以我不能在这里终止。在示例代码中,我经常遇到“ConcurrentModificationException”异常情况,这遵循集合的逻辑,但并不是我的问题的答案。 - shaman.sir
1
如果您刚刚删除了外部循环所指向的对象,则继续比较元素与最近死亡的“outer”毫无意义。我主张退出内部循环,而不是两者都退出。好好想想! - Carl Smotricz
是的,你说得完全正确,我会在问题中添加最终代码。 - shaman.sir

2
我认为你应该选择一种不同的结构来表示你的区域,比如一棵树,其中每个位置都有包含在它内部的子位置。这样,你可以通过简单的查找排除所有与其他位置重叠的区域,而无需进行嵌套迭代。
如果没有任何位置可以与两个位置重叠,那么这将更容易实现。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接