Android 我在这里遇到一个并发修改异常。请建议如何解决

Android 我在这里遇到一个并发修改异常。请建议如何解决,android,exception,concurrency,Android,Exception,Concurrency,@凌驾 protected FilterResults performFiltering(CharSequence constraint) { if(constraint != null) { suggestions.clear(); for (DrugsInfo customer : itemsAll) { if(customer.getDRUGNAME().toLowerCase().st

@凌驾

    protected FilterResults performFiltering(CharSequence constraint) {
        if(constraint != null) {
            suggestions.clear();
            for (DrugsInfo customer : itemsAll) {
                if(customer.getDRUGNAME().toLowerCase().startsWith(constraint.toString().toLowerCase())){
                    suggestions.add(customer);
                }
            }
            FilterResults filterResults = new FilterResults();
            filterResults.values = suggestions;
            filterResults.count = suggestions.size();
            return filterResults;
        } else {
            return new FilterResults();
        }
    }


    @Override
    protected void publishResults(CharSequence constraint, FilterResults results) {
        ArrayList<DrugsInfo> filteredList = (ArrayList<DrugsInfo>) results.values;
        if(results != null && results.count > 0) {
            clear();
            for (DrugsInfo c : filteredList) {
                add(c);
            }
            notifyDataSetChanged();
        }
    }
};
protectedfilterResults性能过滤(字符序列约束){
if(约束!=null){
建议。清晰();
对于(药品信息客户:itemsAll){
if(customer.getDRUGNAME().toLowerCase().startsWith(constraint.toString().toLowerCase())){
建议。添加(客户);
}
}
FilterResults FilterResults=新的FilterResults();
filterResults.values=建议;
filterResults.count=建议.size();
返回过滤器结果;
}否则{
返回新的FilterResults();
}
}
@凌驾
受保护的void publishResults(CharSequence约束、FilterResults结果){
ArrayList filteredList=(ArrayList)results.values;
if(results!=null&&results.count>0){
清除();
用于(药品信息c:过滤器列表){
添加(c);
}
notifyDataSetChanged();
}
}
};
我在这里遇到一个并发修改异常。请建议如何解决


此行中针对(DrugsInfo c:filteredList){的错误我正在查看以下代码:

            suggestions.clear();
            for (DrugsInfo customer : itemsAll) {
                if(customer.getDRUGNAME().toLowerCase().startsWith(constraint.toString().toLowerCase())){
                    suggestions.add(customer);
                }
            }
注意,您正在清除一个现有列表(这显然是一个类属性,而不是一个局部变量),而不是在此处创建一个新的空列表。我敢打赌,您的
建议
列表就是支持适配器的实际列表。如果我是对的,那么下面就是发生的情况:

  • performFiltering()
    中,您将
    建议
    分配给
    filterResults.values
    。现在
    filterResults.values
    。现在
    filterResults.values
    保存对适配器源列表的引用
  • publishResults()
    中,将
    results.values
    (来自
    filterResults.values
    )分配给
    filteredList
    。现在
    filteredList
    保存对适配器源列表的引用
  • 接下来,通过在列表上运行for-each循环来创建一个迭代器。因此,现在支持列表上有了一个迭代器。迭代器工作时不能修改列表(因此,
    ConcurrentModificationException
    ;不能与活动迭代器同时修改列表)
  • 然后调用
    add(c)
    ,使适配器添加到适配器源代码列表中——您知道,就是您现在正在迭代的那个列表
  • 迭代器现在注意到列表已被修改,并抛出异常
我从Android开发中了解到,在将列表分配给其他列表变量时必须非常小心。很容易忘记其他变量实际上是同一个列表

您应该能够通过将上面的代码段更改为:

            ArrayList<DrugsInfo> tempList = new ArrayList<>();
            for (DrugsInfo customer : itemsAll) {
                if(customer.getDRUGNAME().toLowerCase().startsWith(constraint.toString().toLowerCase())){
                    tempList.add(customer);
                }
            }
            FilterResults filterResults = new FilterResults();
            filterResults.values = tempList;
            filterResults.count = tempList.size();


我正在查看以下代码:

            suggestions.clear();
            for (DrugsInfo customer : itemsAll) {
                if(customer.getDRUGNAME().toLowerCase().startsWith(constraint.toString().toLowerCase())){
                    suggestions.add(customer);
                }
            }
注意,您正在清除一个现有列表(这显然是一个类属性,而不是一个局部变量),而不是在此处创建一个新的空列表。我敢打赌,您的
建议
列表就是支持适配器的实际列表。如果我是对的,那么下面就是发生的情况:

  • performFiltering()
    中,您将
    建议
    分配给
    filterResults.values
    。现在
    filterResults.values
    。现在
    filterResults.values
    保存对适配器源列表的引用
  • publishResults()
    中,将
    results.values
    (来自
    filterResults.values
    )分配给
    filteredList
    。现在
    filteredList
    保存对适配器源列表的引用
  • 接下来,通过在列表上运行for-each循环来创建一个迭代器。因此,现在支持列表上有了一个迭代器。迭代器工作时不能修改列表(因此,
    ConcurrentModificationException
    ;不能与活动迭代器同时修改列表)
  • 然后调用
    add(c)
    ,使适配器添加到适配器源代码列表中——您知道,就是您现在正在迭代的那个列表
  • 迭代器现在注意到列表已被修改,并抛出异常
我从Android开发中了解到,在将列表分配给其他列表变量时必须非常小心。很容易忘记其他变量实际上是同一个列表

您应该能够通过将上面的代码段更改为:

            ArrayList<DrugsInfo> tempList = new ArrayList<>();
            for (DrugsInfo customer : itemsAll) {
                if(customer.getDRUGNAME().toLowerCase().startsWith(constraint.toString().toLowerCase())){
                    tempList.add(customer);
                }
            }
            FilterResults filterResults = new FilterResults();
            filterResults.values = tempList;
            filterResults.count = tempList.size();


这里没有足够的代码可以确定。该错误意味着您有多个线程试图同时读取/写入集合。这里没有足够的代码可以确定。该错误意味着您有多个线程试图同时读取/写入集合。