android studio java.util.ConcurrentModificationException

android studio java.util.ConcurrentModificationException,android,firebase,Android,Firebase,我一直从Firebase收到ConcurrentModificationException 我已经多次更改代码(例如在循环外使用“addAll”等),但仍然会遇到错误。现在我不知道我能改变什么来解决这个问题。 这是我目前的代码: 以及更扩展的代码段: 公共类ChatFragment扩展了片段{ private RecyclerView recyclerView; private UserAdapter userAdapter; private List<User>mUsers;

我一直从Firebase收到ConcurrentModificationException

我已经多次更改代码(例如在循环外使用“addAll”等),但仍然会遇到错误。现在我不知道我能改变什么来解决这个问题。 这是我目前的代码:

以及更扩展的代码段:

公共类ChatFragment扩展了片段{

private RecyclerView recyclerView;

private UserAdapter userAdapter;
private List<User>mUsers;

private FirebaseUser fuser;
private DatabaseReference reference;

private List<String>userlist;

@Override
public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {

    View view = inflater.inflate(R.layout.fragment_chat,container,false);

    recyclerView = view.findViewById(R.id.recycler_view);
    recyclerView.setHasFixedSize(true);
    recyclerView.setLayoutManager(new LinearLayoutManager(getContext()));

    fuser = FirebaseAuth.getInstance().getCurrentUser();

    userlist = new ArrayList<>();

    reference = FirebaseDatabase.getInstance().getReference("Chats");
    reference.addValueEventListener(new ValueEventListener() {
        @Override
        public void onDataChange(@NonNull DataSnapshot dataSnapshot) {
            userlist.clear();

            for (DataSnapshot snapshot :dataSnapshot.getChildren()){
                Chat chat = snapshot.getValue(Chat.class);

                if(chat.getSender().equals(fuser.getUid())){
                    userlist.add(chat.getReceiver());

                }
                if (chat.getReceiver().equals(fuser.getUid())){
                    userlist.add(chat.getSender());
                }
            }

            readChat();
        }

        @Override
        public void onCancelled(@NonNull DatabaseError databaseError) {

        }
    });



    return view;




}

private void readChat(){
    mUsers = new ArrayList<>();

    reference = FirebaseDatabase.getInstance().getReference("Users");
    reference.addValueEventListener(new ValueEventListener() {
        @Override
        public void onDataChange(@NonNull DataSnapshot dataSnapshot) {
            mUsers.clear();

            for (DataSnapshot snapshot : dataSnapshot.getChildren()){
                User user = snapshot.getValue(User.class);

                //display 1 users from chat
                for (String id : userlist){
                    if (user.getId().equals(id)){
                        if (mUsers.size()!=0){
                            for (User user1 : mUsers){
                                if(!user.equals(user1.getId())){
                                    mUsers.add(user);

                                }
                            }
                        }else{
                            mUsers.add(user);

                               }
                    }
                }

            }

            userAdapter = new UserAdapter(getContext(),mUsers);
            recyclerView.setAdapter(userAdapter);
        }

        @Override
        public void onCancelled(@NonNull DatabaseError databaseError) {
            Toast.makeText(getContext(), "database error", Toast.LENGTH_SHORT).show();
        }
    });
}
私有回收视图回收视图;
私有用户适配器;
私人博物馆;
专用FirebaseUser fuser;
私人数据库参考;
私有列表用户列表;
@凌驾
创建视图时的公共视图(@NonNull layoutiner flater flatter,ViewGroup container,
Bundle savedInstanceState){
视图=充气机。充气(R.layout.fragment\u chat,容器,false);
recyclerView=view.findViewById(R.id.recycler\u视图);
recyclerView.setHasFixedSize(true);
setLayoutManager(新的LinearLayoutManager(getContext());
fuser=FirebaseAuth.getInstance().getCurrentUser();
userlist=newarraylist();
reference=FirebaseDatabase.getInstance().getReference(“聊天”);
addValueEventListener(新的ValueEventListener(){
@凌驾
public void onDataChange(@NonNull DataSnapshot DataSnapshot){
userlist.clear();
对于(DataSnapshot快照:DataSnapshot.getChildren()){
Chat Chat=snapshot.getValue(Chat.class);
if(chat.getSender().equals(fuser.getUid())){
添加(chat.getReceiver());
}
if(chat.getReceiver().equals(fuser.getUid())){
添加(chat.getSender());
}
}
readChat();
}
@凌驾
已取消的公共void(@NonNull DatabaseError DatabaseError){
}
});
返回视图;
}
私有void readChat(){
mUsers=newarraylist();
reference=FirebaseDatabase.getInstance().getReference(“用户”);
addValueEventListener(新的ValueEventListener(){
@凌驾
public void onDataChange(@NonNull DataSnapshot DataSnapshot){
mUsers.clear();
对于(DataSnapshot快照:DataSnapshot.getChildren()){
User=snapshot.getValue(User.class);
//显示聊天室中的1个用户
for(字符串id:userlist){
if(user.getId().equals(id)){
如果(mUsers.size()!=0){
for(用户1:mUsers){
如果(!user.equals(user1.getId())){
添加(用户);
}
}
}否则{
添加(用户);
}
}
}
}
userAdapter=newuseradapter(getContext(),mUsers);
recyclerView.setAdapter(userAdapter);
}
@凌驾
已取消的公共void(@NonNull DatabaseError DatabaseError){
Toast.makeText(getContext(),“数据库错误”,Toast.LENGTH_SHORT.show();
}
});
}
}

根据OracleDocs for

此类的迭代器和listIterator返回的迭代器 方法是快速失败的:如果列表在任何时候进行了结构修改 创建迭代器后的时间,以任何方式,除了通过 迭代器自己的remove或add方法,迭代器将抛出 ConcurrentModificationException。因此,面对同时发生的冲突, 修改后,迭代器会快速、干净地失败,而不是 在不确定的时间内冒任意、不确定行为的风险 将来

为了解决这个问题,我遵循了这个,它对解决这样的异常有很好的解释

我们如何避免:

  • 如果您使用的是JDK1.5或更高版本,那么可以使用ConcurrentHashMap 和CopyOnWriteArrayList类。这是推荐的方法 避免并发修改异常(我采用了这种方法)
  • 避免多线程系统中的ConcurrentModificationException 您可以将列表转换为数组,然后进行迭代 阵列。这种方法适用于中小型列表 但是如果列表很大,则会对性能产生很大影响
  • 您可以在迭代时通过将列表放入 同步块。不建议使用此方法,因为它会 停止多线程的好处

  • 是的,您找到了问题点-为了避免ConcurrentModificationException-

    可以使用迭代器从基础集合对象中删除/添加对象。但在这种情况下,您可以从列表中删除同一对象,而不是任何其他对象

        Iterator<String> iterator = mUsers.iterator();
        while (iterator.hasNext()) {
        String value = iterator.next();
            mUsers.add("user1");
            mUsers.add("user2");
        }
    
    Iterator Iterator=mUsers.Iterator();
    while(iterator.hasNext()){
    字符串值=迭代器.next();
    添加(“用户1”);
    添加(“用户2”);
    }
    
    希望这对你有帮助

                                    for (User user1 : mUsers){
                                    if(!user.equals(user1.getId())){
                                        mUsers.add(user);
    
                                    }
                                }
    
    private RecyclerView recyclerView;
    
    private UserAdapter userAdapter;
    private List<User>mUsers;
    
    private FirebaseUser fuser;
    private DatabaseReference reference;
    
    private List<String>userlist;
    
    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
    
        View view = inflater.inflate(R.layout.fragment_chat,container,false);
    
        recyclerView = view.findViewById(R.id.recycler_view);
        recyclerView.setHasFixedSize(true);
        recyclerView.setLayoutManager(new LinearLayoutManager(getContext()));
    
        fuser = FirebaseAuth.getInstance().getCurrentUser();
    
        userlist = new ArrayList<>();
    
        reference = FirebaseDatabase.getInstance().getReference("Chats");
        reference.addValueEventListener(new ValueEventListener() {
            @Override
            public void onDataChange(@NonNull DataSnapshot dataSnapshot) {
                userlist.clear();
    
                for (DataSnapshot snapshot :dataSnapshot.getChildren()){
                    Chat chat = snapshot.getValue(Chat.class);
    
                    if(chat.getSender().equals(fuser.getUid())){
                        userlist.add(chat.getReceiver());
    
                    }
                    if (chat.getReceiver().equals(fuser.getUid())){
                        userlist.add(chat.getSender());
                    }
                }
    
                readChat();
            }
    
            @Override
            public void onCancelled(@NonNull DatabaseError databaseError) {
    
            }
        });
    
    
    
        return view;
    
    
    
    
    }
    
    private void readChat(){
        mUsers = new ArrayList<>();
    
        reference = FirebaseDatabase.getInstance().getReference("Users");
        reference.addValueEventListener(new ValueEventListener() {
            @Override
            public void onDataChange(@NonNull DataSnapshot dataSnapshot) {
                mUsers.clear();
    
                for (DataSnapshot snapshot : dataSnapshot.getChildren()){
                    User user = snapshot.getValue(User.class);
    
                    //display 1 users from chat
                    for (String id : userlist){
                        if (user.getId().equals(id)){
                            if (mUsers.size()!=0){
                                for (User user1 : mUsers){
                                    if(!user.equals(user1.getId())){
                                        mUsers.add(user);
    
                                    }
                                }
                            }else{
                                mUsers.add(user);
    
                                   }
                        }
                    }
    
                }
    
                userAdapter = new UserAdapter(getContext(),mUsers);
                recyclerView.setAdapter(userAdapter);
            }
    
            @Override
            public void onCancelled(@NonNull DatabaseError databaseError) {
                Toast.makeText(getContext(), "database error", Toast.LENGTH_SHORT).show();
            }
        });
    }
    
        Iterator<String> iterator = mUsers.iterator();
        while (iterator.hasNext()) {
        String value = iterator.next();
            mUsers.add("user1");
            mUsers.add("user2");
        }