Docs
  • Solver
  • Models
    • Field Service Routing
    • Employee Shift Scheduling
    • Pick-up and Delivery Routing
    • Task Scheduling
  • Platform
Try models
  • Timefold Solver SNAPSHOT
  • Responding to change
  • Non-disruptive replanning
  • Edit this Page

Timefold Solver SNAPSHOT

    • Introduction
    • Getting started
      • Overview
      • Build as a service
      • Embed as a library
        • Hello World guide
        • Quarkus guide
        • Spring Boot guide
    • Domain modeling
      • Guide
      • Building blocks
      • Common patterns
    • Constraints and score
      • Overview
      • Score calculation
      • Understanding the score
      • Load balancing and fairness
      • Performance tips and tricks
    • Running the Solver
      • Overview
      • As a service
        • REST API
        • Model Enrichment
        • Constraint weights
        • Demo data
        • Exposing metrics
      • As a library
        • Configuring Timefold Solver
        • Constraint weights
        • Quarkus integration
        • Spring Boot integration
        • JPA/JAXB/JSON integration
    • Diagnosing the Solver
      • Benchmarking
      • Solver diagnostics
    • Optimization algorithms
      • Overview
      • Construction heuristics
      • Local search
      • Exhaustive search
      • Custom moves
        • Neighborhoods API
        • Move Selector reference
    • Responding to change
      • Continuous planning
      • Real-time planning
      • Non-disruptive replanning
      • Assignment Recommendation API
    • Example use cases
      • Vehicle routing (guide)
      • More examples on GitHub
    • FAQ
    • New and noteworthy
    • Upgrading Timefold Solver
      • Upgrading Timefold Solver: Overview
      • Upgrade from Timefold Solver 1.x to 2.x
      • Upgrading from OptaPlanner
      • Backwards compatibility
      • Migration guides
        • Variable Listeners to Custom Shadow Variables
        • Chained planning variable to planning list variable
    • Commercial editions
      • Overview
      • Installation
      • Performance improvements
      • Score analysis
      • Recommendation API
      • Nearby selection
      • Multithreaded solving
      • Partitioned search
      • Constraint profiling
      • Multistage moves
      • Throttling best solution events

Non-disruptive replanning

Replanning an existing plan can be very disruptive. If the plan affects humans (such as employees, drivers, …​), very disruptive changes are often undesirable.

There are two ways to limit disruption:

  • Pinning — completely prevent specific assignments from changing. Use @PlanningPin to lock individual entities to their current values, or @PlanningPinToIndex to lock only the first portion of a planning list variable. This is appropriate when certain assignments are already confirmed or published and must not move under any circumstances.

  • Non-disruptive replanning — allow changes, but make the solver justify them. The gain of changing an assignment must outweigh the disruption cost. This is usually implemented by taxing all planning entities that change, and is the approach described on this page.

nonDisruptiveReplanning

In conference scheduling, the entity has both a planning variable timeslot and its original value publishedTimeslot:

  • Java

@PlanningEntity
public class Talk {

    ...

    @PlanningVariable
    private Timeslot timeslot;

    private Timeslot publishedTimeslot;

    ...
}

During planning, the planning variable timeslot changes. By writing a constraint comparing it with the publishedTimeslot, a change in plan can be penalized:

  • Java

    Constraint publishedTimeslot(ConstraintFactory factory) {
        return factory.forEach(Talk.class)
                .filter(talk -> talk.getPublishedTimeslot() != null
                        && talk.getTimeslot() != talk.getPublishedTimeslot())
                .penalize(HardSoftScore.ofSoft(1000))
                .asConstraint("Published timeslot");
    }

By configuring a penalty weight of -1000 we can express that a solution will only be accepted if it improves the soft score for at least 1000 points per variable changed (or if it improves the hard score).

  • © 2026 Timefold BV
  • Timefold.ai
  • Documentation
  • Changelog
  • Send feedback
  • Privacy
  • Legal
    • Light mode
    • Dark mode
    • System default