mirror of
https://github.com/graphhopper/jsprit.git
synced 2020-01-24 07:45:05 +01:00
added soft constraints and tests
This commit is contained in:
parent
86c168e428
commit
9a471a58be
11 changed files with 159 additions and 22 deletions
|
|
@ -253,7 +253,7 @@ class CalculatorBuilder {
|
|||
}
|
||||
|
||||
ShipmentInsertionCalculator shipmentInsertion = new ShipmentInsertionCalculator(vrp.getTransportCosts(), actInsertionCalc, constraintManager, constraintManager);
|
||||
ServiceInsertionCalculator serviceInsertion = new ServiceInsertionCalculator(vrp.getTransportCosts(), constraintManager);
|
||||
ServiceInsertionCalculator serviceInsertion = new ServiceInsertionCalculator(vrp.getTransportCosts(), actInsertionCalc, constraintManager);
|
||||
|
||||
JobCalculatorSwitcher switcher = new JobCalculatorSwitcher();
|
||||
switcher.put(Shipment.class, shipmentInsertion);
|
||||
|
|
|
|||
|
|
@ -16,6 +16,7 @@
|
|||
******************************************************************************/
|
||||
package jsprit.core.algorithm.recreate;
|
||||
|
||||
import jsprit.core.algorithm.recreate.ActivityInsertionCostsCalculator.ActivityInsertionCosts;
|
||||
import jsprit.core.problem.constraint.ConstraintManager;
|
||||
import jsprit.core.problem.constraint.HardActivityStateLevelConstraint;
|
||||
import jsprit.core.problem.constraint.HardActivityStateLevelConstraint.ConstraintsStatus;
|
||||
|
|
@ -59,15 +60,18 @@ final class ServiceInsertionCalculator implements JobInsertionCostsCalculator{
|
|||
|
||||
private VehicleRoutingTransportCosts transportCosts;
|
||||
|
||||
private ActivityInsertionCostsCalculator additionalTransportCostsCalculator;
|
||||
|
||||
private TourActivityFactory activityFactory;
|
||||
|
||||
public ServiceInsertionCalculator(VehicleRoutingTransportCosts routingCosts, ConstraintManager constraintManager) {
|
||||
public ServiceInsertionCalculator(VehicleRoutingTransportCosts routingCosts, ActivityInsertionCostsCalculator additionalTransportCostsCalculator, ConstraintManager constraintManager) {
|
||||
super();
|
||||
this.transportCosts = routingCosts;
|
||||
hardRouteLevelConstraint = constraintManager;
|
||||
hardActivityLevelConstraint = constraintManager;
|
||||
softActivityConstraint = constraintManager;
|
||||
softRouteConstraint = constraintManager;
|
||||
this.additionalTransportCostsCalculator = additionalTransportCostsCalculator;
|
||||
activityFactory = new DefaultTourActivityFactory();
|
||||
logger.info("initialise " + this);
|
||||
}
|
||||
|
|
@ -95,7 +99,7 @@ final class ServiceInsertionCalculator implements JobInsertionCostsCalculator{
|
|||
double bestCost = bestKnownCosts;
|
||||
|
||||
//from job2insert induced costs at route level
|
||||
double routeICosts = softRouteConstraint.getCosts(insertionContext);
|
||||
double additionalICostsAtRouteLevel = softRouteConstraint.getCosts(insertionContext);
|
||||
|
||||
Service service = (Service)jobToInsert;
|
||||
int insertionIndex = InsertionData.NO_INDEX;
|
||||
|
|
@ -114,9 +118,10 @@ final class ServiceInsertionCalculator implements JobInsertionCostsCalculator{
|
|||
ConstraintsStatus status = hardActivityLevelConstraint.fulfilled(insertionContext, prevAct, deliveryAct2Insert, nextAct, prevActStartTime);
|
||||
if(status.equals(ConstraintsStatus.FULFILLED)){
|
||||
//from job2insert induced costs at activity level
|
||||
double activityICosts = softActivityConstraint.getCosts(insertionContext, prevAct, deliveryAct2Insert, nextAct, prevActStartTime);
|
||||
if(routeICosts + activityICosts < bestCost){
|
||||
bestCost = routeICosts + activityICosts;
|
||||
double additionalICostsAtActLevel = softActivityConstraint.getCosts(insertionContext, prevAct, deliveryAct2Insert, nextAct, prevActStartTime);
|
||||
ActivityInsertionCosts additionalTransportationCosts = additionalTransportCostsCalculator.getCosts(insertionContext, prevAct, nextAct, deliveryAct2Insert, prevActStartTime);
|
||||
if(additionalICostsAtRouteLevel + additionalICostsAtActLevel + additionalTransportationCosts.getAdditionalCosts() < bestCost){
|
||||
bestCost = additionalICostsAtRouteLevel + additionalICostsAtActLevel + additionalTransportationCosts.getAdditionalCosts();
|
||||
insertionIndex = actIndex;
|
||||
}
|
||||
}
|
||||
|
|
@ -134,9 +139,10 @@ final class ServiceInsertionCalculator implements JobInsertionCostsCalculator{
|
|||
if(!loopBroken){
|
||||
ConstraintsStatus status = hardActivityLevelConstraint.fulfilled(insertionContext, prevAct, deliveryAct2Insert, nextAct, prevActStartTime);
|
||||
if(status.equals(ConstraintsStatus.FULFILLED)){
|
||||
double activityICosts = softActivityConstraint.getCosts(insertionContext, prevAct, deliveryAct2Insert, nextAct, prevActStartTime);
|
||||
if(routeICosts + activityICosts < bestCost){
|
||||
bestCost = routeICosts + activityICosts;
|
||||
double additionalICostsAtActLevel = softActivityConstraint.getCosts(insertionContext, prevAct, deliveryAct2Insert, nextAct, prevActStartTime);
|
||||
ActivityInsertionCosts additionalTransportationCosts = additionalTransportCostsCalculator.getCosts(insertionContext, prevAct, nextAct, deliveryAct2Insert, prevActStartTime);
|
||||
if(additionalICostsAtRouteLevel + additionalICostsAtActLevel + additionalTransportationCosts.getAdditionalCosts() < bestCost){
|
||||
bestCost = additionalICostsAtRouteLevel + additionalICostsAtActLevel + additionalTransportationCosts.getAdditionalCosts();
|
||||
insertionIndex = actIndex;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ import jsprit.core.util.CalculationUtils;
|
|||
* @author schroeder
|
||||
*
|
||||
*/
|
||||
public class AdditionalTransportationCosts implements SoftActivityConstraint{
|
||||
class AdditionalTransportationCosts implements SoftActivityConstraint{
|
||||
|
||||
private VehicleRoutingTransportCosts routingCosts;
|
||||
|
||||
|
|
|
|||
|
|
@ -32,7 +32,6 @@ import jsprit.core.algorithm.selector.SelectBest;
|
|||
import jsprit.core.algorithm.state.StateManager;
|
||||
import jsprit.core.algorithm.state.UpdateVariableCosts;
|
||||
import jsprit.core.problem.VehicleRoutingProblem;
|
||||
import jsprit.core.problem.constraint.AdditionalTransportationCosts;
|
||||
import jsprit.core.problem.constraint.ConstraintManager;
|
||||
import jsprit.core.problem.io.VrpXMLReader;
|
||||
import jsprit.core.problem.solution.SolutionCostCalculator;
|
||||
|
|
@ -68,7 +67,7 @@ public class BuildCVRPAlgoFromScratch_IT {
|
|||
ConstraintManager cManager = new ConstraintManager(vrp, stateManager);
|
||||
cManager.addLoadConstraint();
|
||||
cManager.addTimeWindowConstraint();
|
||||
cManager.addConstraint(new AdditionalTransportationCosts(vrp.getTransportCosts()));
|
||||
|
||||
|
||||
VehicleFleetManager fleetManager = new InfiniteFleetManagerFactory(vrp.getVehicles()).createFleetManager();
|
||||
|
||||
|
|
|
|||
|
|
@ -136,7 +136,7 @@ public class ServiceInsertionAndLoadConstraintsTest {
|
|||
stateManager.informInsertionStarts(Arrays.asList(route), null);
|
||||
|
||||
JobCalculatorSwitcher switcher = new JobCalculatorSwitcher();
|
||||
ServiceInsertionCalculator serviceInsertionCalc = new ServiceInsertionCalculator(routingCosts, constraintManager);
|
||||
ServiceInsertionCalculator serviceInsertionCalc = new ServiceInsertionCalculator(routingCosts, activityInsertionCostsCalculator, constraintManager);
|
||||
ShipmentInsertionCalculator insertionCalculator = new ShipmentInsertionCalculator(routingCosts, activityInsertionCostsCalculator, hardRouteLevelConstraint, constraintManager);
|
||||
switcher.put(Pickup.class, serviceInsertionCalc);
|
||||
switcher.put(Delivery.class, serviceInsertionCalc);
|
||||
|
|
|
|||
|
|
@ -240,7 +240,7 @@ public class ShipmentInsertionCalculatorTest {
|
|||
stateManager.informInsertionStarts(Arrays.asList(route), null);
|
||||
|
||||
JobCalculatorSwitcher switcher = new JobCalculatorSwitcher();
|
||||
ServiceInsertionCalculator serviceInsertionCalc = new ServiceInsertionCalculator(routingCosts, constraintManager);
|
||||
ServiceInsertionCalculator serviceInsertionCalc = new ServiceInsertionCalculator(routingCosts, activityInsertionCostsCalculator, constraintManager);
|
||||
ShipmentInsertionCalculator insertionCalculator = new ShipmentInsertionCalculator(routingCosts, activityInsertionCostsCalculator, hardRouteLevelConstraint, constraintManager);
|
||||
switcher.put(Pickup.class, serviceInsertionCalc);
|
||||
switcher.put(Shipment.class, insertionCalculator);
|
||||
|
|
|
|||
|
|
@ -24,11 +24,10 @@ import java.util.ArrayList;
|
|||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
|
||||
import jsprit.core.algorithm.ExampleActivityCostFunction;
|
||||
import jsprit.core.algorithm.state.StateManager;
|
||||
import jsprit.core.problem.VehicleRoutingProblem;
|
||||
import jsprit.core.problem.constraint.AdditionalTransportationCosts;
|
||||
import jsprit.core.problem.constraint.ConstraintManager;
|
||||
import jsprit.core.problem.cost.VehicleRoutingActivityCosts;
|
||||
import jsprit.core.problem.cost.VehicleRoutingTransportCosts;
|
||||
import jsprit.core.problem.driver.DriverImpl;
|
||||
import jsprit.core.problem.driver.DriverImpl.NoDriver;
|
||||
|
|
@ -166,12 +165,10 @@ public class TestCalculatesServiceInsertion {
|
|||
ConstraintManager cManager = new ConstraintManager(vrp,states);
|
||||
cManager.addLoadConstraint();
|
||||
cManager.addTimeWindowConstraint();
|
||||
cManager.addConstraint(new AdditionalTransportationCosts(costs));
|
||||
|
||||
serviceInsertion = new ServiceInsertionCalculator(costs, cManager);
|
||||
|
||||
VehicleRoutingActivityCosts actCosts = mock(VehicleRoutingActivityCosts.class);
|
||||
|
||||
// stateUpdater = new UpdateStates(states, costs, activityCosts);
|
||||
serviceInsertion = new ServiceInsertionCalculator(costs, new LocalActivityInsertionCostsCalculator(costs, actCosts), cManager);
|
||||
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -0,0 +1,50 @@
|
|||
package jsprit.core.problem.constraint;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.mockito.Mockito.mock;
|
||||
import static org.mockito.Mockito.when;
|
||||
import jsprit.core.problem.misc.JobInsertionContext;
|
||||
import jsprit.core.problem.solution.route.activity.TourActivity;
|
||||
|
||||
import org.junit.Test;
|
||||
|
||||
public class SoftActivityConstraintManagerTest {
|
||||
|
||||
@Test
|
||||
public void whenAddingSoftConstraint_managerShouldHaveIt(){
|
||||
SoftActivityConstraint c = mock(SoftActivityConstraint.class);
|
||||
SoftActivityConstraintManager man = new SoftActivityConstraintManager();
|
||||
assertEquals(0,man.getConstraints().size());
|
||||
man.addConstraint(c);
|
||||
assertEquals(1,man.getConstraints().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenAddingTwoSoftConstraints_managerShouldHaveIt(){
|
||||
SoftActivityConstraint c1 = mock(SoftActivityConstraint.class);
|
||||
SoftActivityConstraint c2 = mock(SoftActivityConstraint.class);
|
||||
SoftActivityConstraintManager man = new SoftActivityConstraintManager();
|
||||
assertEquals(0,man.getConstraints().size());
|
||||
man.addConstraint(c1);
|
||||
man.addConstraint(c2);
|
||||
assertEquals(2,man.getConstraints().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenAddingTwoSoftConstrainta_managerShouldSumCostsCorrectly(){
|
||||
SoftActivityConstraint c1 = mock(SoftActivityConstraint.class);
|
||||
JobInsertionContext iContext = mock(JobInsertionContext.class);
|
||||
TourActivity act_i = mock(TourActivity.class);
|
||||
TourActivity act_k = mock(TourActivity.class);
|
||||
TourActivity act_j = mock(TourActivity.class);
|
||||
when(c1.getCosts(iContext,act_i,act_k,act_j,0.0)).thenReturn(1.0);
|
||||
SoftActivityConstraint c2 = mock(SoftActivityConstraint.class);
|
||||
when(c2.getCosts(iContext,act_i,act_k,act_j,0.0)).thenReturn(2.0);
|
||||
|
||||
SoftActivityConstraintManager man = new SoftActivityConstraintManager();
|
||||
|
||||
man.addConstraint(c1);
|
||||
man.addConstraint(c2);
|
||||
assertEquals(3.0,man.getCosts(iContext,act_i,act_k,act_j,0.0),0.01);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,46 @@
|
|||
package jsprit.core.problem.constraint;
|
||||
|
||||
import jsprit.core.problem.misc.JobInsertionContext;
|
||||
|
||||
import org.junit.Test;
|
||||
|
||||
import static org.junit.Assert.*;
|
||||
import static org.mockito.Mockito.mock;
|
||||
import static org.mockito.Mockito.when;
|
||||
|
||||
public class SoftRouteConstraintManagerTest {
|
||||
|
||||
@Test
|
||||
public void whenAddingSoftRouteConstraint_managerShouldHaveIt(){
|
||||
SoftRouteConstraint c = mock(SoftRouteConstraint.class);
|
||||
SoftRouteConstraintManager man = new SoftRouteConstraintManager();
|
||||
assertEquals(0,man.getConstraints().size());
|
||||
man.addConstraint(c);
|
||||
assertEquals(1,man.getConstraints().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenAddingTwoSoftRouteConstraint_managerShouldHaveIt(){
|
||||
SoftRouteConstraint c1 = mock(SoftRouteConstraint.class);
|
||||
SoftRouteConstraint c2 = mock(SoftRouteConstraint.class);
|
||||
SoftRouteConstraintManager man = new SoftRouteConstraintManager();
|
||||
assertEquals(0,man.getConstraints().size());
|
||||
man.addConstraint(c1);
|
||||
man.addConstraint(c2);
|
||||
assertEquals(2,man.getConstraints().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenAddingTwoSoftRouteConstraint_managerShouldSumCostsCorrectly(){
|
||||
SoftRouteConstraint c1 = mock(SoftRouteConstraint.class);
|
||||
JobInsertionContext iContext = mock(JobInsertionContext.class);
|
||||
when(c1.getCosts(iContext)).thenReturn(1.0);
|
||||
SoftRouteConstraint c2 = mock(SoftRouteConstraint.class);
|
||||
when(c2.getCosts(iContext)).thenReturn(2.0);
|
||||
SoftRouteConstraintManager man = new SoftRouteConstraintManager();
|
||||
|
||||
man.addConstraint(c1);
|
||||
man.addConstraint(c2);
|
||||
assertEquals(3.0,man.getCosts(iContext),0.01);
|
||||
}
|
||||
}
|
||||
|
|
@ -1,6 +1,6 @@
|
|||
package jsprit.core.problem.constraint;
|
||||
|
||||
import static org.junit.Assert.*;
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.mockito.Mockito.mock;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
|
@ -30,5 +30,45 @@ public class TestConstraintManager {
|
|||
ConstraintManager cManager = new ConstraintManager(mock(VehicleRoutingProblem.class),mock(RouteAndActivityStateGetter.class),constraints);
|
||||
assertEquals(1,cManager.getConstraints().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenAddingSoftRouteConstraint_managerShouldHaveIt(){
|
||||
SoftRouteConstraint c = mock(SoftRouteConstraint.class);
|
||||
ConstraintManager man = new ConstraintManager(mock(VehicleRoutingProblem.class),mock(RouteAndActivityStateGetter.class));
|
||||
assertEquals(0,man.getConstraints().size());
|
||||
man.addConstraint(c);
|
||||
assertEquals(1,man.getConstraints().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenAddingTwoSoftRouteConstraint_managerShouldHaveIt(){
|
||||
SoftRouteConstraint c1 = mock(SoftRouteConstraint.class);
|
||||
SoftRouteConstraint c2 = mock(SoftRouteConstraint.class);
|
||||
ConstraintManager man = new ConstraintManager(mock(VehicleRoutingProblem.class),mock(RouteAndActivityStateGetter.class));
|
||||
assertEquals(0,man.getConstraints().size());
|
||||
man.addConstraint(c1);
|
||||
man.addConstraint(c2);
|
||||
assertEquals(2,man.getConstraints().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenAddingSoftActivityConstraint_managerShouldHaveIt(){
|
||||
SoftActivityConstraint c = mock(SoftActivityConstraint.class);
|
||||
ConstraintManager man = new ConstraintManager(mock(VehicleRoutingProblem.class),mock(RouteAndActivityStateGetter.class));
|
||||
assertEquals(0,man.getConstraints().size());
|
||||
man.addConstraint(c);
|
||||
assertEquals(1,man.getConstraints().size());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void whenAddingTwoSoftActivityConstraints_managerShouldHaveIt(){
|
||||
SoftActivityConstraint c1 = mock(SoftActivityConstraint.class);
|
||||
SoftActivityConstraint c2 = mock(SoftActivityConstraint.class);
|
||||
ConstraintManager man = new ConstraintManager(mock(VehicleRoutingProblem.class),mock(RouteAndActivityStateGetter.class));
|
||||
assertEquals(0,man.getConstraints().size());
|
||||
man.addConstraint(c1);
|
||||
man.addConstraint(c2);
|
||||
assertEquals(2,man.getConstraints().size());
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue