Android 2.1 GoogleMaps ItemizedOverlay ConcurrentModificationException
我无法弄清楚 ConcurrentModificationException 的来源。在我的 activity
中,我正在调用 updateMapOverlay()
。我还在定期调用的另一个线程(TimerTask
)内调用 updateMapOverlay()
。从两个线程调用 updateMapOverlay()
时,我会采取适当的锁定。导致此问题的原因是我从非 UI 线程(即 TimerTask
)内部调用 updateMapOverlay
吗?还有其他人遇到过类似的问题吗?
<代码> private void updateMapOverlay() {
this.itemizedOverlay.refreshItems(createOverlayItemsList());
List<Overlay> overlays = mapView.getOverlays();
overlays.clear();
overlays.add(cotItemizedOverlay);
this.mapview.invalidate();
}
谢谢。
例外:
W/dalvikvm(10641): threadid=3: thread exiting with uncaught exception (group=0x4001b180)
E/AndroidRuntime(10641): Uncaught handler: thread main exiting due to uncaught exception
E/AndroidRuntime(10641): java.util.ConcurrentModificationException
E/AndroidRuntime(10641): at java.util.AbstractList$SimpleListIterator.next(AbstractList.java:64)
E/AndroidRuntime(10641): at com.google.android.maps.OverlayBundle.draw(OverlayBundle.java:41)
E/AndroidRuntime(10641): at com.google.android.maps.MapView.onDraw(MapView.java:494)
E/AndroidRuntime(10641): at android.view.View.draw(View.java:6535)
E/AndroidRuntime(10641): at android.view.ViewGroup.drawChild(ViewGroup.java:1531)
E/AndroidRuntime(10641): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1258)
E/AndroidRuntime(10641): at android.view.ViewGroup.drawChild(ViewGroup.java:1529)
E/AndroidRuntime(10641): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1258)
E/AndroidRuntime(10641): at android.view.View.draw(View.java:6538)
E/AndroidRuntime(10641): at android.widget.FrameLayout.draw(FrameLayout.java:352)
E/AndroidRuntime(10641): at android.view.ViewGroup.drawChild(ViewGroup.java:1531)
E/AndroidRuntime(10641): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1258)
E/AndroidRuntime(10641): at android.view.ViewGroup.drawChild(ViewGroup.java:1529)
E/AndroidRuntime(10641): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1258)
E/AndroidRuntime(10641): at android.view.View.draw(View.java:6538)
E/AndroidRuntime(10641): at android.widget.FrameLayout.draw(FrameLayout.java:352)
E/AndroidRuntime(10641): at com.android.internal.policy.impl.PhoneWindow$DecorView.draw(PhoneWindow.java:1830)
E/AndroidRuntime(10641): at android.view.ViewRoot.draw(ViewRoot.java:1349)
E/AndroidRuntime(10641): at android.view.ViewRoot.performTraversals(ViewRoot.java:1114)
E/AndroidRuntime(10641): at android.view.ViewRoot.handleMessage(ViewRoot.java:1633)
E/AndroidRuntime(10641): at android.os.Handler.dispatchMessage(Handler.java:99)
E/AndroidRuntime(10641): at android.os.Looper.loop(Looper.java:123)
E/AndroidRuntime(10641): at android.app.ActivityThread.main(ActivityThread.java:4363)
E/AndroidRuntime(10641): at java.lang.reflect.Method.invokeNative(Native Method)
E/AndroidRuntime(10641): at java.lang.reflect.Method.invoke(Method.java:521)
E/AndroidRuntime(10641): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:860)
E/AndroidRuntime(10641): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:618)
E/AndroidRuntime(10641): at dalvik.system.NativeStart.main(Native Method)
I/Process ( 95): Sending signal. PID: 10641 SIG: 3
I cannot figure out the origin of the ConcurrentModificationException
. In my activity
I'm callingupdateMapOverlay()
. I'm also calling updateMapOverlay()
inside another Thread (a TimerTask
) that is invoked on regular intervals. I'm taking the appropriate locks when invoking updateMapOverlay()
from both the threads. Is this problem being caused because I'm invoking updateMapOverlay
from inside a non-UI thread (i.e., TimerTask
). Has anyone else faced a similar issue ?
private void updateMapOverlay() {
this.itemizedOverlay.refreshItems(createOverlayItemsList());
List<Overlay> overlays = mapView.getOverlays();
overlays.clear();
overlays.add(cotItemizedOverlay);
this.mapview.invalidate();
}
Thanks.
Exception:
W/dalvikvm(10641): threadid=3: thread exiting with uncaught exception (group=0x4001b180)
E/AndroidRuntime(10641): Uncaught handler: thread main exiting due to uncaught exception
E/AndroidRuntime(10641): java.util.ConcurrentModificationException
E/AndroidRuntime(10641): at java.util.AbstractList$SimpleListIterator.next(AbstractList.java:64)
E/AndroidRuntime(10641): at com.google.android.maps.OverlayBundle.draw(OverlayBundle.java:41)
E/AndroidRuntime(10641): at com.google.android.maps.MapView.onDraw(MapView.java:494)
E/AndroidRuntime(10641): at android.view.View.draw(View.java:6535)
E/AndroidRuntime(10641): at android.view.ViewGroup.drawChild(ViewGroup.java:1531)
E/AndroidRuntime(10641): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1258)
E/AndroidRuntime(10641): at android.view.ViewGroup.drawChild(ViewGroup.java:1529)
E/AndroidRuntime(10641): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1258)
E/AndroidRuntime(10641): at android.view.View.draw(View.java:6538)
E/AndroidRuntime(10641): at android.widget.FrameLayout.draw(FrameLayout.java:352)
E/AndroidRuntime(10641): at android.view.ViewGroup.drawChild(ViewGroup.java:1531)
E/AndroidRuntime(10641): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1258)
E/AndroidRuntime(10641): at android.view.ViewGroup.drawChild(ViewGroup.java:1529)
E/AndroidRuntime(10641): at android.view.ViewGroup.dispatchDraw(ViewGroup.java:1258)
E/AndroidRuntime(10641): at android.view.View.draw(View.java:6538)
E/AndroidRuntime(10641): at android.widget.FrameLayout.draw(FrameLayout.java:352)
E/AndroidRuntime(10641): at com.android.internal.policy.impl.PhoneWindow$DecorView.draw(PhoneWindow.java:1830)
E/AndroidRuntime(10641): at android.view.ViewRoot.draw(ViewRoot.java:1349)
E/AndroidRuntime(10641): at android.view.ViewRoot.performTraversals(ViewRoot.java:1114)
E/AndroidRuntime(10641): at android.view.ViewRoot.handleMessage(ViewRoot.java:1633)
E/AndroidRuntime(10641): at android.os.Handler.dispatchMessage(Handler.java:99)
E/AndroidRuntime(10641): at android.os.Looper.loop(Looper.java:123)
E/AndroidRuntime(10641): at android.app.ActivityThread.main(ActivityThread.java:4363)
E/AndroidRuntime(10641): at java.lang.reflect.Method.invokeNative(Native Method)
E/AndroidRuntime(10641): at java.lang.reflect.Method.invoke(Method.java:521)
E/AndroidRuntime(10641): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:860)
E/AndroidRuntime(10641): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:618)
E/AndroidRuntime(10641): at dalvik.system.NativeStart.main(Native Method)
I/Process ( 95): Sending signal. PID: 10641 SIG: 3
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
是的。
为什么要不断删除和添加覆盖层?只需更新覆盖并使其失效即可。请参阅此处了解异步更新叠加层的示例。
Yes.
Why are you removing and adding an overlay constantly? Just update the overlay and invalidate. See here for an example of updating an overlay asynchronously.
感谢您的回复。
但是,在您的代码中,您不是在执行类似的操作 (
map.getOverlays().remove(sites);
和map.getOverlays().add(sites);
)?<代码>
类 OverlayTask 扩展 AsyncTask {
@覆盖
公共无效onPreExecute(){
if (站点!=null) {
map.getOverlays().remove(sites);
地图.invalidate();
站点=空;
}
}
}
Thank you for your response.
However, in your code aren't you doing something similar (
map.getOverlays().remove(sites);
andmap.getOverlays().add(sites);
)?class OverlayTask extends AsyncTask {
@Override
public void onPreExecute() {
if (sites!=null) {
map.getOverlays().remove(sites);
map.invalidate();
sites=null;
}
}
}
一般来说,只要您只在 UI 线程上修改 ItemizedOverlay 的支持列表/地图,您就应该是安全的。
正如 Mark 指出的,AsyncTask 的:
始终在 UI 线程上执行,因此此处的修改是安全的。
Generally speaking you should be safe as long as you only modify your ItemizedOverlay's backing List/Map on the UI thread.
As Mark pointed out, AsyncTask's:
is always executed on the UI thread, so modifications are safe here.
我也有同样的问题。为了回答您关于“为什么要不断删除和添加覆盖层?”的问题,我这样做是因为我的一些覆盖层项目可能不再存在,或者可能会出现新的覆盖层项目,而现有的覆盖层项目可能会改变位置,具体取决于我的特定应用程序的其余部分发生了什么。另外,我发现无法在不扩展 OverlayItem 的情况下更改其位置,以便我可以这样做。
此外,更改逐项覆盖中的项目是否也会导致并发修改异常?
I'm having the same problem. To answer your question as to "why are you removing and adding an overlay constantly?", I'm doing it because some of my overlay items might no longer exist, or new ones might appear, and existing ones may change location, depending on what's happening in the rest of my particular application. Also, I've found no way of changing the location of an OverlayItem without extending it so that I can do so.
Besides, wouldn't changing what items are in the itemized overlay also cause a concurrent modification exception?