user7090887 user7090887 - 27 days ago 14
Android Question

Getting weird number of location objects from onLocationMethod and outofmemory exception

I am trying to update

ArrayList
of Locations as per below logic in a service, running in background thread through Runnable.I have edited code to show only relevant code. I was getting
ConcurrentModificationException
but resolved it by implementing changes instructed here. But problem of weird results still continues.

public static ArrayList<Location> locationPoints;


ArrayList<Location> alnew = new ArrayList<Location>();

@Override
public void onLocationChanged(final Location location) {
//Log.i(TAG, "onLocationChanged: " + location);
Log.i(TAG, "onLocationChanged: " + locationPoints.size());


if(!locationPoints.isEmpty()){
for(Location l:locationPoints){
if(location.distanceTo(l)<=200.0f){
alnew.add(l);
}else{
alnew.add(location);
}
}
}else{
alnew.add(location);
}
locationPoints.addAll(alnew);
alnew.removeAll(alnew);

sendLocationsToActivity(locationPoints);
}


I want location objects going one after the other, but i see location objects increasing exponentially.

Result from Log in
onLocationChanged
is as below.

onLocationChanged: 0
onLocationChanged:1
onLocationChanged:2
onLocationChanged:4
onLocationChanged:8
onLocationChanged:16
onLocationChanged:32


But if I delete all the
ArrayList
logic from
onLocationChanged
and simply add location objects to
ArrayList
, the results are the way I want

onLocationChanged: 0
onLocationChanged:1
onLocationChanged:2
onLocationChanged:3
onLocationChanged:4
onLocationChanged:5

Answer

ConcurrentModificationException occurs when you modify the list (adding or removing elements) while traversing a list with Iterator. The for-each loop is nothing but syntactic sugar for java.util.Iterator. So here the logic is like:

for() {
     if(someCondition) {
         locationPoints.add(sth);
   }
}

Rather than that you can try sth like:

for() {
         if(someCondition) {
             someOtherArrayList.add(sth);
       }
    }

And once out of the loop and all then:

locationPoints.addAll(someOtherArrayList);