初始化ArrayList<CheckBox>时触发ConcurrentModificationException原因解析
为什么设置setOnCheckedChangeListener会触发ConcurrentModificationException?
核心原因
ConcurrentModificationException 是ArrayList的快速失败(fail-fast)机制触发的——当你在遍历集合的过程中,集合的结构被修改(比如添加、删除元素),迭代器会检测到集合的修改次数(modCount)和迭代器初始化时的预期次数不一致,直接抛出异常。
结合你的场景分析
最初写法触发异常的逻辑
你先给每个CheckBox设置setOnCheckedChangeListener,随后遍历repeatDays修改对应CheckBox的isChecked状态。此时修改isChecked会立即触发监听器的回调方法:- 如果你的监听器回调里包含对
ArrayList<CheckBox>的结构修改操作(比如选中时往列表里加元素、取消时移除元素),那在遍历过程中,集合的modCount会被修改。 - 迭代器检测到
modCount变化,就会抛出ConcurrentModificationException。
- 如果你的监听器回调里包含对
调整顺序后异常消失的原因
把设置监听器的逻辑移到修改isChecked之后,遍历修改状态的过程中没有监听器存在,不会触发任何集合结构修改的操作。遍历完成后再设置监听器,后续的状态变更触发回调时,遍历已经结束,自然不会触发快速失败机制。
示例验证
假设你的监听器逻辑类似下面这样,就会直接触发问题:
// 监听器里修改集合结构 checkBox.setOnCheckedChangeListener((buttonView, isChecked) -> { if (isChecked) { checkBoxList.add(buttonView); } else { checkBoxList.remove(buttonView); } });
当你遍历checkBoxList修改isChecked时,每修改一个就触发回调修改集合,导致遍历过程中modCount异常,抛出错误。
内容的提问来源于stack exchange,提问作者neo
相关产品推荐
相关产品推荐

