由于意外修改而导致 java.util.ConcurrentModificationException

标签 java

我正在实现 A* 算法,将给定数量的出租车分配给给定数量的客户:

public SearchNode AStarSearch(List<Car> allCars, List<Customer> allCustomers) {

    // creates first node
    SearchNode firstNode = createFirstNode(allCars, allCustomers);
    open.add(firstNode);

    SearchNode currentNode;

    while(true) {
        currentNode = open.poll();   //error thrown here
        if (currentNode.allCustomers.isEmpty()) break;

        closed.add(currentNode);

        SearchNode temp;

        Iterator<Customer> itrCus = currentNode.allCustomers.iterator();
        Iterator<Car> itrCar = currentNode.allCars.iterator();

        while (itrCus.hasNext()) {
            Customer currentCustomer = itrCus.next();
            while (itrCar.hasNext()) {
                Car currentCar = itrCar.next();
                temp = new SearchNode(currentNode, currentCar, currentCustomer);
                openUpdate(currentNode, temp);
            }
        }
    }
    return currentNode;
}

现在,对于子 SearchNode,我想删除它已服务的客户。但这应该只发生在搜索节点内部。

这就是 SearchNode 类中发生的情况:

public class SearchNode implements Comparable<SearchNode> {

List<Car> allCars;
List<Customer> allCustomers;
SearchNode parent;

public SearchNode(SearchNode parent, Car currentCar, Customer currentCustomer) {
    // inheriting values from parent search node
    this.allCars = parent.allCars; 
    this.allCustomers = parent.allCustomers;
    this.parent = parent;

    // now updating this node's values
    this.allCustomers.remove(currentCustomer);
}

我检查了一些打印件,并在 while(itrCar.hasNext()) 的第二次迭代中进行了检查。 , parent 的allCustomer列表缺少 currentCustomer .

编辑:我更应该问:有人可以告诉我为什么我更改了父节点的值吗?这可能是因为我还没有理解整个java实际上是按引用传递的。

最佳答案

您应该创建要从中本地删除客户的 List 副本:

public SearchNode(SearchNode parent, Car currentCar, Customer currentCustomer) {
    // inheriting values from parent search node
    this.allCars = parent.allCars; // consider making a copy here too
                                   // if required
    this.allCustomers = new ArrayList<>(parent.allCustomers); // make a 
                                                              // copy
    this.parent = parent;

    // now updating this node's values
    this.allCustomers.remove(currentCustomer); // now you can safely 
                                               // remove currentCustomer
                                               // without affecting 
                                               // parent.allCustomers
}

关于由于意外修改而导致 java.util.ConcurrentModificationException,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55236421/

相关文章:

java - 这段 Python 代码与 Java 代码等价吗?

java - 使用正则表达式解析地址

java - 覆盖 @autowired/@Inject Map<String,Object> 的键字符串?

java - 屏幕上鼠标位置周围区域的缩放框

javax包包含两个不同项目中的不同包

java - 使用 JSON 参数简化 REST URL

java - ByteArrayInputStream 不复制字节数组?

java - Spring Boot 单元测试 - 缺少 bean 运行测试

java - 给定一个类路径资源,有没有办法获取拥有/包含它的 java.io.File 对象?

使用 lambda 表达式时 Java 8 泛型 + 异常编译时错误