CodeGym /Java 博客 /随机的 /Java 中的并发修改异常
John Squirrels
第 41 级
San Francisco

Java 中的并发修改异常

已在 随机的 群组中发布

Java中的ConcurrentModificationException是什么?

“当在没有修改权限的情况下修改资源时,会发生 ConcurrentModificationException。”
换句话说,Java ConcurrentModificationException(顾名思义)是由于并发问题而发生的。在继续操作之前,假定您已具备线程多线程 的先验知识。Java 中的某些类(如 Collection 类)不允许一个线程在另一个线程迭代元素时修改该元素。如果执行修改操作(添加、删除等),程序将抛出ConcurrentModificationException。这并不是发生此异常的唯一情况。然而,更深入的挖掘超出了本文的范围。

例子

让我们看一个例子来说明这个异常是如何发生的。
import java.util.List;
import java.util.Iterator;
import java.util.ArrayList;

//Test driver for ConcurrentModificationException
public class ConcurrentModificationExceptionTestDriver1 {

	public static void main(String[] args) {
		List<String> businessDays = new ArrayList<>();

		businessDays.add("Monday");
		businessDays.add("Tuesday");
		businessDays.add("Wednesday");
		businessDays.add("Thursday");
		businessDays.add("Friday");
		businessDays.add("Saturday");
		businessDays.add("Sunday");

		Iterator<String> iterator = businessDays.iterator();
		while (iterator.hasNext()) {
			String day = iterator.next();
			if (day.equals("Sunday")) {
				// removing a list item while iterating
				// leading to java.util.ConcurrentModificationException
				businessDays.remove(day);
			}
		}
	}
}

输出

线程“main”中的异常 java.util.ConcurrentModificationException 在 java.base/java.util.ArrayList$Itr.checkForComodification(ArrayList.java:1042) 在 java.base/java.util.ArrayList$Itr.next(ArrayList.java :996)在milestone.thirty.seven.ConcurrentModificationExceptionTestDriver1.main(ConcurrentModificationExceptionTestDriver1.java:22)

Java中如何避免ConcurrentModificationException?

ConcurrentModificationException有不同的解决方法。这里列出了一些。您可以根据您的需要选择任何人。
  1. 避免迭代时修改。
  2. 使用传统循环进行同时迭代和修改。
  3. 创建要在使用迭代器时修改的值的副本。迭代结束后更新值。

例子

以下是如何避免ConcurrentModificationException的示例。
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

//Test driver for ConcurrentModificationException
public class ConcurrentModificationExceptionTestDriver2 {

	public static void main(String[] args) {

		List<String> businessDays = new ArrayList<>();

		businessDays.add("Monday");
		businessDays.add("Tuesday");
		businessDays.add("Wednesday");
		businessDays.add("Thursday");
		businessDays.add("Friday");
		businessDays.add("Saturday");
		businessDays.add("Sunday");

		System.out.println("Initial Business Days: " + businessDays);

		// Method II - Using traditional for loop
		for (int i = 0; i < businessDays.size(); i++) {
			if (businessDays.get(i).equals("Sunday")) {
				businessDays.remove(i);
			}
		}

		Iterator<String> iterator = businessDays.iterator();
		List<String> businessDaysToBeRemoved = new ArrayList<>();

		// Method III - Creating a copy of elements
		while (iterator.hasNext()) {
			String day = iterator.next();
			if (day.equals("Saturday")) {
				// Add values to be removed in the list
				businessDaysToBeRemoved.add(day);
			}
		}
		businessDays.removeAll(businessDaysToBeRemoved);
		System.out.println("Final Business Days: " + businessDays);
	}
}

输出

初始工作日:[周一、周二、周三、周四、周五、周六、周日] 最终工作日:[周一、周二、周三、周四、周五]

结论

这是处理Java 中的ConcurrentModificationException的快速方法。每当您感到卡住时,请随时跳上来。一如既往,前进的关键是练习和耐心。在那之前,继续学习并不断成长。
评论
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION