java—遍历一个列表并允许它同时删除一个项(不是迭代器)

ki0zmccv  于 2021-07-09  发布在  Java
关注(0)|答案(3)|浏览(360)

注意:我不知道剂量测定是否能去除元素。这是我的数据结构需要处理的一个例外情况。
我的问题很简单:

int size = list.size();
for(int i = 0; i < size; i++) {
   MyObj mo = list.get(i);
   mo.doSomething();
}

如果dosomething()从列表中删除mo,我最终会得到一个arrayindexoutofbounds,因为列表现在已经缩小了。
我应该使用什么样的数据结构来允许有删除可能性的迭代?我不能在这里使用迭代器,换句话说,我不能让dosomething返回布尔值并调用iterator.remove()。数据结构必须以某种方式处理这种情况,并继续遍历仍然存在的其余元素。
编辑:我不知道dosomething是否会删除元素。这是我的数据结构需要处理的一个例外情况。
第二部分=>制作一个智能侦听器通知程序,以避免代码到处重复

zpjtge22

zpjtge221#

我觉得你应该改变自己 doSomething() . 如果 mo.doSomething() 可以删除 mol ,你 mo 一定知道你的 l .
您可以这样更改代码:
在myobj中创建一个有效的标志。只有有效的时候才听。

while(list.hasNext()) {
   MyObj mo = list.next()
   if(mo.isValid()){
       mo.doSomething();
   } else {
       list.remove();
   }
}
vmdwslir

vmdwslir2#

我应该使用什么样的数据结构来允许有删除可能性的迭代?
最简单的方法是复制列表并迭代:

List<MyObj> copy = new ArrayList<MyObj>(list);
for (MyObj mo : copy) {
    mo.doSomething();
}

现在,不管是否有任何东西从原来的列表中删除了一个想法,这都不会改变列表的副本。
另一种选择是使用 CopyOnWriteArrayList . 然后您可以随意迭代和删除或添加项:
“快照”样式的迭代器方法使用对创建迭代器时数组状态的引用。此数组在迭代器的生存期内从不更改,因此不可能发生干扰,并且迭代器保证不会抛出concurrentmodificationexception。自从创建迭代器以来,迭代器不会反映对列表的添加、删除或更改。

ct3nt3jp

ct3nt3jp3#

你可以使用 ArrayList ,例如,只要在删除某些内容时更新索引和大小。

List<MyObj> list = new ArrayList<MyObj>();
int size = list.size();
for(int i = 0; i < size; i++) {
    MyObj mo = list.get(i);
    mo.doSomething();
    if (size > list.size()) {
        size = list.size();
        i--;
    }
}

这只在移除的项目是最后一个检查的项目时有效。对于列表的其他更改,您必须有更复杂的逻辑。

相关问题