You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Timefold能否生成多个调度方案?如何配置实现多提案输出

如何用Timefold获取多个调度方案而非仅最优解

你的现有模型无需修改核心结构,只需要通过求解器配置或API即可收集多个可行/次优解,以下是具体实现方式:

方法一:通过事件监听收集多个不同解

利用求解器的事件监听机制,捕获每次最优解更新的事件,筛选并收集不同的调度方案,直到凑够5个:

// 构建求解器
SolverFactory<PlanningSolution> solverFactory = SolverFactory.createFromXmlResource("solverConfig.xml");
Solver<PlanningSolution> solver = solverFactory.buildSolver();

// 用于存储候选方案的列表
List<PlanningSolution> candidateSolutions = new ArrayList<>(5);

// 添加最优解变更监听器
solver.addEventListener(event -> {
    if (event instanceof BestSolutionChangedEvent<PlanningSolution> bestEvent) {
        PlanningSolution newSolution = bestEvent.getNewBestSolution();
        // 判断当前解是否与已收集的解唯一(避免重复的分配方案)
        boolean isUnique = candidateSolutions.stream()
            .noneMatch(existing -> {
                // 先比较分数,再比较订单的配送分配细节
                if (!existing.getScore().equals(newSolution.getScore())) {
                    return false;
                }
                // 逐订单检查配送分配是否完全一致
                for (int i = 0; i < existing.getOrders().size(); i++) {
                    Order existingOrder = existing.getOrders().get(i);
                    Order newOrder = newSolution.getOrders().get(i);
                    if (!Objects.equals(existingOrder.getAssignedDelivery(), newOrder.getAssignedDelivery())) {
                        return false;
                    }
                }
                return true;
            });

        if (isUnique) {
            // 克隆解,避免求解器后续修改实例
            candidateSolutions.add(solver.createClone(newSolution));
            // 收集够5个就提前终止求解
            if (candidateSolutions.size() >= 5) {
                solver.terminateEarly();
            }
        }
    }
});

// 启动求解
solver.solve(initialPlanningSolution);

// candidateSolutions 中即为最多5个不同的调度方案

方法二:收集Pareto最优解(多目标场景)

如果你的调度需求涉及多个优化目标(如最小化配送成本、最短配送时间),可以启用Pareto最优解模式,收集非支配的最优解集合,再从中选取前5个:

  1. 在求解器配置文件solverConfig.xml中添加以下配置:
<solver>
    <!-- 其他基础配置(如求解终止条件、启发式算法) -->
    <scoreDirectorFactory>
        <!-- 根据你的目标设置分数类型,比如HARD_SOFT对应多目标 -->
        <scoreDefinitionType>HARD_SOFT</scoreDefinitionType>
    </scoreDirectorFactory>
    <!-- 启用Pareto解模式 -->
    <paretoSolutionMode>ENABLED</paretoSolutionMode>
    <!-- 限制收集的Pareto解数量为5 -->
    <termination>
        <bestSolutionCountLimit>5</bestSolutionCountLimit>
    </termination>
</solver>
  1. 求解完成后获取解集合:
Solver<PlanningSolution> solver = solverFactory.buildSolver();
solver.solve(initialPlanningSolution);
// 获取所有Pareto最优解,最多5个
Collection<PlanningSolution> paretoSolutions = solver.getBestSolutions();

关键注意事项

  • 你的PlanningSolution类缺少@PlanningScore字段,这是Timefold评估解优劣的核心,必须添加:
    @PlanningScore
    private HardSoftScore score; // 可根据实际需求选择分数类型(如SimpleScore、HardMediumSoftScore)
    
  • 保存解时必须调用solver.createClone(),因为求解器内部会复用同一个解决方案实例,直接添加会导致后续修改覆盖已收集的解。
  • 仅通过分数判断解的唯一性不可靠,不同的配送分配可能得到相同分数,因此需要额外检查订单的配送分配细节。

内容的提问来源于stack exchange,提问作者R S

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.03 12:30:26