Reputation: 12592
Im trying to delete item from a ArrayList
. Some times it pops an exception, java.util.ConcurrentModificationException
.
First I tried to remove them by array_list_name.remove(i)
, but it failed and some people were asked to use Iterator instead. So my current code is as follows:
for (Iterator<Collectable> iter = array_list_name.iterator(); iter.hasNext();) {
Collectable s = iter.next();
if (s.equals(array_list_name.get(id))){
iter.remove();
return true;
}
}
And I call array_list_name
inside onDraw()
function in view. My view is a SurfaceView
. Can anyone suggest me how to delete items from ArrayList
without getting this error?
Upvotes: 10
Views: 16833
Reputation: 2179
Have you ever thought to use Vector List ? If you need a thread-safe implementation, you should use Vector
instead of ArrayList
.
Vector
list's usage is same with ArrayList
. Just change its type with Vector
.
Unsafe usage
ArrayList<FutureTask> futureTasks;
Change with
Vector<FutureTask> futureTasks;
That's all.
Upvotes: 1
Reputation: 530
Try using java.util.concurrent.CopyOnWriteArrayList
instead of ArrayList
Upvotes: 11
Reputation: 30128
Seems from the comments that your ArrayList<Collectable>
is accessed from the onDraw()
method in one thread, by the UI, concurrently with you removing items from it in another thread.
So, why not just wrap both accessors in a
synchronized(array_list_name)
{
// UI access code or item removal code
}
Note that this might make your UI laggy if removing items takes a long time. If this is the case, consider making a list of all item indexes to be removed, and remove them in a tight synchronized loop after iterating over the whole list.
Update
It seems to me your whole code snippet could be simplified to just:
synchronized(array_list_name)
return array_list_name.remove(id);
Upvotes: 8
Reputation: 63794
You could create a defensive copy of the list like so:
List copy = new ArrayList(array_list_name);
for (Iterator<Collectable> iter = copy.iterator(); iter.hasNext();) {
Collectable s = iter.next();
if (s.equals(copy.get(id))){
iter.remove();
return true;
}
}
Upvotes: 0