I am using ortools to model a VRP with pickup and delivery constraints, where pickups can be done at different nodes. For example, if node A has a demand, it must be picked at node B or C.
Here is how I do this:
# data["pickups_deliveries"] is a dict with keys delivery_nodes and values a list of possible pickup nodes # example : data["pickups_deliveries"][a] = [b,c] for delivery_node in self.data["pickups_deliveries"]: # choose one node among all pickup options all_pickups = [ self.manager.NodeToIndex(p) for p in self.data["pickups_deliveries"][delivery_node] ] self.routing.AddDisjunction(all_pickups, 0) # same vehicle for pickup and delivery delivery_index = self.manager.NodeToIndex(delivery_node) self.routing.solver().Add( sum( self.routing.ActiveVar(p) * self.routing.VehicleVar(p) for p in all_pickups ) == self.routing.VehicleVar(delivery_index) ) # precedence constraint time_dimension = self.routing.GetDimensionOrDie("Time") self.routing.solver().Add( sum( self.routing.ActiveVar(p) * time_dimension.CumulVar(p) for p in all_pickups ) <= time_dimension.CumulVar(delivery_index) )
This works if everything fits into 1 vehicle. But if capacity constraints require more than 1 vehicle, the solver does not find a solution after a few minutes (solver status 3).
I suspect something is wrong with the constraints imposing that the same vehicle is used for the pickup and delivery, but I am not sure. I have also tried using the following code (from here), but it does not help:
pickup_vehicles = [self.routing.VehicleVar(i) for i in all_pickups] deliver_vehicle = [self.routing.VehicleVar(delivery_index)] self.routing.solver().AddConstraint( self.routing.solver().Max(pickup_vehicles)== self.routing.solver().Max(deliver_vehicle))
Can someone help ? Thanks!
Note : I have cross posted on ortools mailing list.