public double SolveBasic(int branchLimit) { // Objective Console.WriteLine(); Console.WriteLine(" ! ----------------------------------------------------------------------------"); Console.WriteLine(" ! Minimizing total cost"); Console.WriteLine(" ! ----------------------------------------------------------------------------"); IIntExpr costExpr = cp.IntExpr(); int nbMachines = machines.Length; int nbJobs = machines[0].Length; for (int i = 0; i < nbJobs; i++) { for (int j = 0; j < nbMachines; j++) { costExpr = cp.Sum(costExpr, cp.Prod(costs[j][i], cp.PresenceOf(machines[j][i]))); } } IObjective obj = cp.Minimize(costExpr); cp.Add(obj); cp.SetParameter(CP.IntParam.LogPeriod, 600000); cp.SetParameter(CP.IntParam.BranchLimit, branchLimit); cp.SetParameter(CP.IntParam.NoOverlapInferenceLevel, CP.ParameterValues.Extended); cp.Solve(); double cost = cp.ObjValue; return(cost); }
private Cplex initCplex(VariabilityModel vm) { Cplex cplex = new Cplex(); one = cplex.Constant(1); initializeBinaryVariables(cplex, vm); return(cplex); }
private void BuildModel() { // Create the decision variables, cost, and the model scene = new IIntVar[numScenes]; for (int s = 0; s < numScenes; s++) { scene[s] = cp.IntVar(0, numScenes - 1); } // Expression representing the global cost idleCost = cp.IntExpr(); // Make the slot-based secondary model IIntVar[] slot = new IIntVar[numScenes]; for (int s = 0; s < numScenes; s++) { slot[s] = cp.IntVar(0, numScenes - 1); } cp.Add(cp.Inverse(scene, slot)); // Loop over all actors, building cost for (int a = 0; a < numActors; a++) { // Expression for the waiting time for this actor IIntExpr actorWait = cp.IntExpr(); // Calculate the first and last slots where this actor plays List <IIntVar> position = new List <IIntVar>(); System.Collections.IEnumerator en = actorInScene[a].GetEnumerator(); while (en.MoveNext()) { position.Add(slot[(int)en.Current]); } IIntExpr firstSlot = cp.Min(position.ToArray()); IIntExpr lastSlot = cp.Max(position.ToArray()); // If an actor is not in a scene, he waits // if he is on set when the scene is filmed for (int s = 0; s < numScenes; s++) { if (!actorInScene[a].Contains(s)) { // not in scene IIntExpr wait = cp.And(cp.Le(firstSlot, slot[s]), cp.Le( slot[s], lastSlot)); actorWait = cp.Sum(actorWait, cp.Prod(sceneDuration[s], wait)); } } // Accumulate the cost of waiting time for this actor idleCost = cp.Sum(idleCost, cp.Prod(actorPay[a], actorWait)); } cp.Add(cp.Minimize(idleCost)); }
public static IIntExpr MakeScenarioSubmodel(CP cp, int nbJobs, int nbMachines, int[][] machines, int[][] durations, IIntervalSequenceVar[] sequences) { List <IIntervalVar>[] machinesOps = new List <IIntervalVar> [nbMachines]; String name; int i, j; for (j = 0; j < nbMachines; j++) { machinesOps[j] = new List <IIntervalVar>(); } IIntExpr[] ends = new IIntExpr[nbJobs]; for (i = 0; i < nbJobs; i++) { IIntervalVar prec = cp.IntervalVar(); for (j = 0; j < nbMachines; j++) { name = "J" + i + "_O" + j; IIntervalVar ti = cp.IntervalVar(durations[i][j], name); machinesOps[machines[i][j]].Add(ti); if (j > 0) { cp.Add(cp.EndBeforeStart(prec, ti)); } prec = ti; } ends[i] = cp.EndOf(prec); } for (j = 0; j < nbMachines; j++) { name = "M" + j; sequences[j] = cp.IntervalSequenceVar(machinesOps[j].ToArray(), name); cp.Add(cp.NoOverlap(sequences[j])); } return(cp.Max(ends)); }
static void Main(string[] args) { CP cp = new CP(); int weightSum = 0; for (int o = 0; o < nbOrders; o++) { weightSum += weight[o]; } IIntVar[] where = new IIntVar[nbOrders]; for (int o = 0; o < nbOrders; o++) { where[o] = cp.IntVar(0, nbSlabs - 1); } IIntVar[] load = new IIntVar[nbSlabs]; for (int m = 0; m < nbSlabs; m++) { load[m] = cp.IntVar(0, weightSum); } // Pack constraint cp.Add(cp.Pack(load, where, weight)); // Color constraints for (int m = 0; m < nbSlabs; m++) { IIntExpr[] colorExpArray = new IIntExpr[nbColors]; for (int c = 0; c < nbColors; c++) { IConstraint orCt = cp.FalseConstraint(); for (int o = 0; o < nbOrders; o++) { if (colors[o] == c) { orCt = cp.Or(orCt, cp.Eq(where[o], m)); } } colorExpArray[c] = cp.IntExpr(orCt); } cp.Add(cp.Le(cp.Sum(colorExpArray), 2)); } // Objective function int sizeLossValues = capacities[capacities.Length - 1] - capacities[0] + 1; int[] lossValues = new int[sizeLossValues]; lossValues[0] = 0; int indexValue = 1; for (int q = 1; q < capacities.Length; q++) { for (int p = capacities[q - 1] + 1; p <= capacities[q]; p++) { lossValues[indexValue] = capacities[q] - p; indexValue++; } } IIntExpr obj = cp.Constant(0); for (int m = 0; m < nbSlabs; m++) { obj = cp.Sum(obj, cp.Element(lossValues, load[m])); } cp.Add(cp.Minimize(obj)); // - A symmetry breaking constraint that is useful for small instances for (int m = 1; m < nbSlabs; m++) { cp.Add(cp.Ge(load[m - 1], load[m])); } if (cp.Solve()) { Console.WriteLine("Optimal value: " + cp.GetValue(obj)); for (int m = 0; m < nbSlabs; m++) { int p = 0; for (int o = 0; o < nbOrders; o++) { if (cp.GetValue(where[o]) == m) { ++p; } } if (p == 0) { continue; } Console.Write("Slab " + m + " is used for order"); if (p > 1) { Console.Write("s"); } Console.Write(" :"); for (int o = 0; o < nbOrders; o++) { if (cp.GetValue(where[o]) == m) { Console.Write(" " + o); } } Console.WriteLine(); } } }
static void Main(string[] args) { String filename; if (args.Length > 0) { filename = args[0]; } else { filename = "../../../../examples/data/facility.data"; } CP cp = new CP(); int i, j; DataReader data = new DataReader(filename); int nbLocations = data.Next(); int nbStores = data.Next(); int[] capacity = new int[nbLocations]; int[] fixedCost = new int[nbLocations]; int[][] cost = new int[nbStores][]; for (i = 0; i < nbStores; i++) { cost[i] = new int[nbLocations]; } for (j = 0; j < nbLocations; j++) { capacity[j] = data.Next(); } for (j = 0; j < nbLocations; j++) { fixedCost[j] = data.Next(); } for (i = 0; i < nbStores; i++) { for (j = 0; j < nbLocations; j++) { cost[i][j] = data.Next(); } } IIntVar[] supplier = cp.IntVarArray(nbStores, 0, nbLocations - 1); IIntVar[] open = cp.IntVarArray(nbLocations, 0, 1); for (i = 0; i < nbStores; i++) { cp.Add(cp.Eq(cp.Element(open, supplier[i]), 1)); } for (j = 0; j < nbLocations; j++) { cp.Add(cp.Le(cp.Count(supplier, j), capacity[j])); } IIntExpr obj = cp.ScalProd(open, fixedCost); for (i = 0; i < nbStores; i++) { obj = cp.Sum(obj, cp.Element(cost[i], supplier[i])); } cp.Add(cp.Minimize(obj)); cp.SetParameter(CP.IntParam.Workers, 1); cp.SetParameter(CP.IntParam.SearchType, CP.ParameterValues.DepthFirst); cp.SetParameter(CP.IntParam.LogPeriod, 1); cp.SetParameter(CP.IntParam.LogSearchTags, CP.ParameterValues.On); cp.Solve(); cp.ClearExplanations(); cp.ExplainFailure(15); cp.ExplainFailure(20); int[] failureArray = { 3, 10, 11, 12 }; cp.ExplainFailure(failureArray); cp.Solve(); cp.ClearExplanations(); cp.ExplainFailure(1); cp.Solve(); Console.WriteLine(); Console.WriteLine("Optimal value: " + cp.GetValue(obj)); for (j = 0; j < nbLocations; j++) { if (cp.GetValue(open[j]) == 1) { Console.Write("Facility " + j + " is open, it serves stores "); for (i = 0; i < nbStores; i++) { if (cp.GetValue(supplier[i]) == j) { Console.Write(i + " "); } } Console.WriteLine(); } } }
public static void Main(String[] args) { try { CP cp = new CP(); ITransitionDistance setup1 = cp.TransitionDistance(NbTypes); ITransitionDistance setup2 = cp.TransitionDistance(NbTypes); int i, j; for (i = 0; i < NbTypes; ++i) { for (j = 0; j < NbTypes; ++j) { int d1 = SetupM1[NbTypes * i + j]; if (d1 < 0) d1 = CP.IntervalMax; // Forbidden transition setup1.SetValue(i, j, d1); int d2 = SetupM2[NbTypes * i + j]; if (d2 < 0) d2 = CP.IntervalMax; // Forbidden transition setup2.SetValue(i, j, d2); } } int[] tp = new int[NbTasks]; IIntervalVar[] a = new IIntervalVar[NbTasks]; IIntervalVar[] a1 = new IIntervalVar[NbTasks]; IIntervalVar[] a2 = new IIntervalVar[NbTasks]; IIntExpr[] ends = new IIntExpr[NbTasks]; String name; for (i = 0; i < NbTasks; ++i) { int type = TaskType[i]; int d1 = TaskDurM1[i]; int d2 = TaskDurM2[i]; tp[i] = type; name = "A" + i + "_TP" + type; a[i] = cp.IntervalVar(name); IIntervalVar[] alt = new IIntervalVar[2]; name = "A" + i + "_M1_TP" + type; a1[i] = cp.IntervalVar(d1, name); a1[i].SetOptional(); alt[0] = a1[i]; name = "A" + i + "_M2_TP" + type; a2[i] = cp.IntervalVar(d2, name); a2[i].SetOptional(); alt[1] = a2[i]; cp.Add(cp.Alternative(a[i], alt)); ends[i] = cp.EndOf(a[i]); } IIntervalSequenceVar s1 = cp.IntervalSequenceVar(a1, tp); IIntervalSequenceVar s2 = cp.IntervalSequenceVar(a2, tp); cp.Add(cp.NoOverlap(s1, setup1, true)); cp.Add(cp.NoOverlap(s2, setup2, true)); cp.Add(cp.Minimize(cp.Max(ends))); cp.SetParameter(CP.IntParam.FailLimit, 100000); cp.SetParameter(CP.IntParam.LogPeriod, 10000); if (cp.Solve()) { Console.WriteLine("Machine 1: "); IIntervalVar x; for (x = cp.GetFirst(s1); !x.Equals(cp.GetLast(s1)); x = cp.GetNext(s1, x)) Console.WriteLine(cp.GetDomain(x)); Console.WriteLine(cp.GetDomain(x)); Console.WriteLine("Machine 2: "); for (x = cp.GetFirst(s2); !x.Equals(cp.GetLast(s2)); x = cp.GetNext(s2, x)) Console.WriteLine(cp.GetDomain(x)); Console.WriteLine(cp.GetDomain(x)); Console.WriteLine("Makespan \t: " + cp.ObjValue); } else { Console.WriteLine("No solution found."); } } catch (IloException e) { Console.WriteLine("Error: " + e); } }
static void Main(string[] args) { CP cp = new CP(); int weightSum=0; for (int o = 0; o < nbOrders; o++) weightSum += weight[o]; IIntVar[] where = new IIntVar[nbOrders]; for(int o = 0; o < nbOrders; o++) where[o] = cp.IntVar(0, nbSlabs-1); IIntVar[] load = new IIntVar[nbSlabs]; for(int m = 0; m < nbSlabs; m++) load[m] = cp.IntVar(0, weightSum); // Pack constraint cp.Add(cp.Pack(load, where, weight)); // Color constraints for(int m = 0; m < nbSlabs; m++) { IIntExpr[] colorExpArray = new IIntExpr[nbColors]; for(int c = 0; c < nbColors; c++) { IConstraint orCt = cp.FalseConstraint(); for(int o = 0; o < nbOrders; o++){ if (colors[o] == c){ orCt = cp.Or(orCt, cp.Eq(where[o], m)); } } colorExpArray[c] = cp.IntExpr(orCt); } cp.Add(cp.Le(cp.Sum(colorExpArray), 2)); } // Objective function int sizeLossValues = capacities[capacities.Length-1] - capacities[0] + 1; int[] lossValues = new int[sizeLossValues]; lossValues[0]= 0; int indexValue= 1; for(int q = 1; q < capacities.Length; q++){ for(int p = capacities[q-1] + 1; p <= capacities[q]; p++){ lossValues[indexValue] = capacities[q] - p; indexValue++; } } IIntExpr obj = cp.Constant(0); for(int m = 0; m < nbSlabs; m++){ obj = cp.Sum(obj, cp.Element(lossValues, load[m])); } cp.Add(cp.Minimize(obj)); // - A symmetry breaking constraint that is useful for small instances for(int m = 1; m < nbSlabs; m++){ cp.Add(cp.Ge(load[m-1],load[m])); } if (cp.Solve()){ Console.WriteLine("Optimal value: " + cp.GetValue(obj)); for (int m = 0; m < nbSlabs; m++) { int p = 0; for (int o = 0; o < nbOrders; o++) if (cp.GetValue(where[o]) == m) ++p; if (p == 0) continue; Console.Write("Slab " + m + " is used for order"); if (p > 1) Console.Write("s"); Console.Write(" :"); for (int o = 0; o < nbOrders; o++) { if (cp.GetValue(where[o]) == m) Console.Write(" " + o); } Console.WriteLine(); } } }
static void Main(string[] args) { String filename; if (args.Length > 0) { filename = args[0]; } else { filename = "../../../../examples/data/facility.data"; } CP cp = new CP(); int i, j; DataReader data = new DataReader(filename); int nbLocations = data.Next(); int nbStores = data.Next(); int[] capacity = new int[nbLocations]; int[] fixedCost = new int[nbLocations]; int[][] cost = new int[nbStores][]; for (i = 0; i < nbStores; i++) { cost[i] = new int[nbLocations]; } for (j = 0; j < nbLocations; j++) { capacity[j] = data.Next(); } for (j = 0; j < nbLocations; j++) { fixedCost[j] = data.Next(); } for (i = 0; i < nbStores; i++) { for (j = 0; j < nbLocations; j++) { cost[i][j] = data.Next(); } } IIntVar[] supplier = cp.IntVarArray(nbStores, 0, nbLocations - 1); IIntVar[] open = cp.IntVarArray(nbLocations, 0, 1); for (i = 0; i < nbStores; i++) { cp.Add(cp.Eq(cp.Element(open, supplier[i]), 1)); } for (j = 0; j < nbLocations; j++) { cp.Add(cp.Le(cp.Count(supplier, j), capacity[j])); } IIntExpr obj = cp.ScalProd(open, fixedCost); for (i = 0; i < nbStores; i++) { obj = cp.Sum(obj, cp.Element(cost[i], supplier[i])); } cp.Add(cp.Minimize(obj)); cp.Solve(); Console.WriteLine(); Console.WriteLine("Optimal value: " + cp.GetValue(obj)); for (j = 0; j < nbLocations; j++) { if (cp.GetValue(open[j]) == 1) { Console.Write("Facility " + j + " is open, it serves stores "); for (i = 0; i < nbStores; i++) { if (cp.GetValue(supplier[i]) == j) { Console.Write(i + " "); } } Console.WriteLine(); } } }
public static void Main(String[] args) { String filename = "../../../../examples/data/rcpspmm_default.data"; int failLimit = 30000; int nbTasks, nbRenewable, nbNonRenewable; if (args.Length > 0) { filename = args[0]; } if (args.Length > 1) { failLimit = Convert.ToInt32(args[1]); } CP cp = new CP(); DataReader data = new DataReader(filename); nbTasks = data.Next(); nbRenewable = data.Next(); nbNonRenewable = data.Next(); ICumulFunctionExpr[] renewables = new ICumulFunctionExpr[nbRenewable]; IIntExpr[] nonRenewables = new IIntExpr[nbNonRenewable]; int[] capRenewables = new int[nbRenewable]; int[] capNonRenewables = new int[nbNonRenewable]; for (int j = 0; j < nbRenewable; j++) { renewables[j] = cp.CumulFunctionExpr(); capRenewables[j] = data.Next(); } for (int j = 0; j < nbNonRenewable; j++) { nonRenewables[j] = cp.IntExpr(); capNonRenewables[j] = data.Next(); } IIntervalVar[] tasks = new IIntervalVar[nbTasks]; List <IIntervalVar>[] modes = new List <IIntervalVar> [nbTasks]; for (int i = 0; i < nbTasks; i++) { tasks[i] = cp.IntervalVar(); modes[i] = new List <IIntervalVar>(); } List <IIntExpr> ends = new List <IIntExpr>(); for (int i = 0; i < nbTasks; i++) { IIntervalVar task = tasks[i]; int d = data.Next(); int nbModes = data.Next(); int nbSucc = data.Next(); for (int k = 0; k < nbModes; k++) { IIntervalVar alt = cp.IntervalVar(); alt.SetOptional(); modes[i].Add(alt); } cp.Add(cp.Alternative(task, modes[i].ToArray())); ends.Add(cp.EndOf(task)); for (int s = 0; s < nbSucc; s++) { int succ = data.Next(); cp.Add(cp.EndBeforeStart(task, tasks[succ])); } } for (int i = 0; i < nbTasks; i++) { IIntervalVar task = tasks[i]; List <IIntervalVar> imodes = modes[i]; for (int k = 0; k < imodes.Count; k++) { int taskId = data.Next(); int modeId = data.Next(); int d = data.Next(); imodes[k].SizeMin = d; imodes[k].SizeMax = d; int q; for (int j = 0; j < nbNonRenewable; j++) { q = data.Next(); if (0 < q) { renewables[j].Add(cp.Pulse(imodes[k], q)); } } for (int j = 0; j < nbNonRenewable; j++) { q = data.Next(); if (0 < q) { nonRenewables[j] = cp.Sum(nonRenewables[j], cp.Prod(q, cp.PresenceOf(imodes[k]))); } } } } for (int j = 0; j < nbRenewable; j++) { cp.Add(cp.Le(renewables[j], capRenewables[j])); } for (int j = 0; j < nbRenewable; j++) { cp.Add(cp.Le(nonRenewables[j], capNonRenewables[j])); } IObjective objective = cp.Minimize(cp.Max(ends.ToArray())); cp.Add(objective); cp.SetParameter(CP.IntParam.FailLimit, failLimit); Console.WriteLine("Instance \t: " + filename); if (cp.Solve()) { Console.WriteLine("Makespan \t: " + cp.ObjValue); } else { Console.WriteLine("No solution found."); } }
public static void Main(String[] args) { String filename = "../../../../examples/data/learningeffect_default.data"; int failLimit = 10000; int nbJobs, nbMachines; if (args.Length > 0) filename = args[0]; if (args.Length > 1) failLimit = Convert.ToInt32(args[1]); CP cp = new CP(); DataReader data = new DataReader(filename); nbJobs = data.Next(); nbMachines = data.Next(); IIntExpr[] ends = new IIntExpr[nbJobs]; IIntervalVar[][] machines = new IIntervalVar[nbMachines][]; int[][] sizes = new int[nbMachines][]; for (int j = 0; j < nbMachines; j++) { machines[j] = new IIntervalVar[nbJobs]; sizes[j] = new int[nbJobs]; } for (int i = 0; i < nbJobs; i++) { IIntervalVar prec = cp.IntervalVar(); for (int j = 0; j < nbMachines; j++) { int m, d; m = data.Next(); d = data.Next(); IIntervalVar ti = cp.IntervalVar(0, d); machines[m][i] = ti; sizes[m][i] = d; if (j > 0) { cp.Add(cp.EndBeforeStart(prec, ti)); } prec = ti; } ends[i] = cp.EndOf(prec); } for (int j = 0; j < nbMachines; j++) { double alpha = data.Next() / ((double) 100); IIntervalVar[] chain = new IIntervalVar[nbJobs]; IIntervalVar prec = cp.IntervalVar(); IIntExpr[] indices = new IIntExpr[nbJobs]; for (int i = 0; i < nbJobs; i++) { IIntervalVar syncti = cp.IntervalVar(); if (i > 0) { cp.Add(cp.EndBeforeStart(prec, syncti)); } prec = syncti; chain[i] = syncti; IIntExpr index = cp.IntVar(0, nbJobs -1); indices[i] = index; // Learning effect captured by the decreasing function // of the position (0 <= alpha <= 1). // At first position, in the sequence index = 0; there is no // learning effect and duration of the task is its nominal duration cp.Add(cp.Eq(cp.SizeOf(machines[j][i]), cp.Floor(cp.Prod(sizes[j][i], cp.Power(alpha, index))))); } cp.Add(cp.Isomorphism(chain, machines[j], indices, nbJobs)); // The no-overlap is a redundant constraint in this quite // simple model - it is used only to provide stronger inference. cp.Add(cp.NoOverlap(machines[j])); } IObjective objective = cp.Minimize(cp.Max(ends)); cp.Add(objective); cp.SetParameter(CP.IntParam.FailLimit, failLimit); Console.WriteLine("Instance \t: " + filename); if (cp.Solve()) { Console.WriteLine("Makespan \t: " + cp.ObjValue); } else { Console.WriteLine("No solution found."); } }
public static void Main(String[] args) { String filename = "../../../../examples/data/stochastic_jobshop_default.data"; int failLimit = 250000; if (args.Length > 0) { filename = args[0]; } if (args.Length > 1) { failLimit = Convert.ToInt32(args[1]); } // Data reading DataReader data = new DataReader(filename); int nbJobs, nbMachines, nbScenarios; nbJobs = data.Next(); nbMachines = data.Next(); nbScenarios = data.Next(); int i, j, k; // machines[i][j]: machine used by jth operation of job i int[][] machines = new int[nbJobs][]; for (i = 0; i < nbJobs; i++) { machines[i] = new int[nbMachines]; for (j = 0; j < nbMachines; j++) { machines[i][j] = data.Next(); } } // durations[k][i][j]: duration of jth operation of job i in scenario k int[][][] durations = new int[nbScenarios][][]; for (k = 0; k < nbScenarios; k++) { durations[k] = new int[nbJobs][]; for (i = 0; i < nbJobs; i++) { durations[k][i] = new int[nbMachines]; for (j = 0; j < nbMachines; j++) { durations[k][i][j] = data.Next(); } } } CP cp = new CP(); IIntervalSequenceVar[] refSequences = new IIntervalSequenceVar[nbMachines]; IIntExpr sumMakespan = cp.IntExpr(); for (k = 0; k < nbScenarios; k++) { IIntervalSequenceVar[] scenarioSequences = new IIntervalSequenceVar[nbMachines]; IIntExpr scenarioMakespan = MakeScenarioSubmodel(cp, nbJobs, nbMachines, machines, durations[k], scenarioSequences); // Objective function is aggregated sumMakespan = cp.Sum(sumMakespan, scenarioMakespan); // For each machine, a sameSequence constraint is posted across all scenarios if (0 == k) { refSequences = scenarioSequences; } else { for (j = 0; j < nbMachines; j++) { cp.Add(cp.SameSequence(refSequences[j], scenarioSequences[j])); } } } // Objective function is expected makespan INumExpr expectedMakespan = cp.Quot(sumMakespan, nbScenarios); IObjective objective = cp.Minimize(expectedMakespan); cp.Add(objective); cp.SetParameter(CP.IntParam.FailLimit, failLimit); cp.SetParameter(CP.IntParam.LogPeriod, 1000000); Console.WriteLine("Instance \t: " + filename); if (cp.Solve()) { Console.WriteLine("Expected makespan \t: " + cp.ObjValue); for (j = 0; j < nbMachines; ++j) { IIntervalSequenceVar s = refSequences[j]; Console.Write(s.Name + ":\t"); IIntervalVar op = cp.GetFirst(s); for (; !op.Equals(cp.GetLast(s)); op = cp.GetNext(s, op)) { Console.Write(op.Name + "\t"); } Console.WriteLine(op.Name + "\t"); } } else { Console.WriteLine("No solution found."); } }
public static void Main(String[] args) { try { CP cp = new CP(); ITransitionDistance setup1 = cp.TransitionDistance(NbTypes); ITransitionDistance setup2 = cp.TransitionDistance(NbTypes); int i, j; for (i = 0; i < NbTypes; ++i) { for (j = 0; j < NbTypes; ++j) { setup1.SetValue(i, j, SetupM1[NbTypes * i + j]); setup2.SetValue(i, j, SetupM2[NbTypes * i + j]); } } int[] tp = new int[NbTasks]; IIntervalVar[] a = new IIntervalVar[NbTasks]; IIntervalVar[] a1 = new IIntervalVar[NbTasks]; IIntervalVar[] a2 = new IIntervalVar[NbTasks]; String name; for (i = 0; i < NbTasks; ++i) { int type = TaskType[i]; int d = TaskDur[i]; tp[i] = type; name = "A" + i + "_TP" + type; a[i] = cp.IntervalVar(d, name); IIntervalVar[] alt = new IIntervalVar[2]; name = "A" + i + "_M1_TP" + type; a1[i] = cp.IntervalVar(name); a1[i].SetOptional(); alt[0] = a1[i]; name = "A" + i + "_M2_TP" + type; a2[i] = cp.IntervalVar(name); a2[i].SetOptional(); alt[1] = a2[i]; cp.Add(cp.Alternative(a[i], alt)); } IIntervalSequenceVar s1 = cp.IntervalSequenceVar(a1, tp); IIntervalSequenceVar s2 = cp.IntervalSequenceVar(a2, tp); cp.Add(cp.NoOverlap(s1, setup1, true)); cp.Add(cp.NoOverlap(s2, setup2, true)); IIntExpr nbLongSetups = cp.IntExpr(); for (i = 0; i < NbTasks; ++i) { int tpi = TaskType[i]; int[] isLongSetup1 = new int[NbTypes + 1]; int[] isLongSetup2 = new int[NbTypes + 1]; for (j = 0; j < NbTypes; ++j) { isLongSetup1[j] = (30 <= SetupM1[NbTypes * tpi + j]) ? 1 : 0; isLongSetup2[j] = (30 <= SetupM2[NbTypes * tpi + j]) ? 1 : 0; } isLongSetup1[NbTypes] = 0; // Last on resource or resource not selected isLongSetup2[NbTypes] = 0; // Last on resource or resource not selected nbLongSetups = cp.Sum(nbLongSetups, cp.Element(isLongSetup1, cp.TypeOfNext(s1, a1[i], NbTypes, NbTypes))); nbLongSetups = cp.Sum(nbLongSetups, cp.Element(isLongSetup2, cp.TypeOfNext(s2, a2[i], NbTypes, NbTypes))); } cp.Add(cp.Minimize(nbLongSetups)); cp.SetParameter(CP.IntParam.FailLimit, 100000); cp.SetParameter(CP.IntParam.LogPeriod, 10000); if (cp.Solve()) { Console.WriteLine("Machine 1: "); IIntervalVar x; for (x = cp.GetFirst(s1); !x.Equals(cp.GetLast(s1)); x = cp.GetNext(s1, x)) { Console.WriteLine(cp.GetDomain(x)); } Console.WriteLine(cp.GetDomain(x)); Console.WriteLine("Machine 2: "); for (x = cp.GetFirst(s2); !x.Equals(cp.GetLast(s2)); x = cp.GetNext(s2, x)) { Console.WriteLine(cp.GetDomain(x)); } Console.WriteLine(cp.GetDomain(x)); Console.WriteLine("Number of long transition times \t: " + cp.ObjValue); } else { Console.WriteLine("No solution found."); } } catch (IloException e) { Console.WriteLine("Error: " + e); } }
public static void Main(String[] args) { try { CP cp = new CP(); ITransitionDistance setup1 = cp.TransitionDistance(NbTypes); ITransitionDistance setup2 = cp.TransitionDistance(NbTypes); int i, j; for (i = 0; i < NbTypes; ++i) { for (j = 0; j < NbTypes; ++j) { int d1 = SetupM1[NbTypes * i + j]; if (d1 < 0) { d1 = CP.IntervalMax; // Forbidden transition } setup1.SetValue(i, j, d1); int d2 = SetupM2[NbTypes * i + j]; if (d2 < 0) { d2 = CP.IntervalMax; // Forbidden transition } setup2.SetValue(i, j, d2); } } int[] tp = new int[NbTasks]; IIntervalVar[] a = new IIntervalVar[NbTasks]; IIntervalVar[] a1 = new IIntervalVar[NbTasks]; IIntervalVar[] a2 = new IIntervalVar[NbTasks]; IIntExpr[] ends = new IIntExpr[NbTasks]; String name; for (i = 0; i < NbTasks; ++i) { int type = TaskType[i]; int d1 = TaskDurM1[i]; int d2 = TaskDurM2[i]; tp[i] = type; name = "A" + i + "_TP" + type; a[i] = cp.IntervalVar(name); IIntervalVar[] alt = new IIntervalVar[2]; name = "A" + i + "_M1_TP" + type; a1[i] = cp.IntervalVar(d1, name); a1[i].SetOptional(); alt[0] = a1[i]; name = "A" + i + "_M2_TP" + type; a2[i] = cp.IntervalVar(d2, name); a2[i].SetOptional(); alt[1] = a2[i]; cp.Add(cp.Alternative(a[i], alt)); ends[i] = cp.EndOf(a[i]); } IIntervalSequenceVar s1 = cp.IntervalSequenceVar(a1, tp); IIntervalSequenceVar s2 = cp.IntervalSequenceVar(a2, tp); cp.Add(cp.NoOverlap(s1, setup1, true)); cp.Add(cp.NoOverlap(s2, setup2, true)); cp.Add(cp.Minimize(cp.Max(ends))); cp.SetParameter(CP.IntParam.FailLimit, 100000); cp.SetParameter(CP.IntParam.LogPeriod, 10000); if (cp.Solve()) { Console.WriteLine("Machine 1: "); IIntervalVar x; for (x = cp.GetFirst(s1); !x.Equals(cp.GetLast(s1)); x = cp.GetNext(s1, x)) { Console.WriteLine(cp.GetDomain(x)); } Console.WriteLine(cp.GetDomain(x)); Console.WriteLine("Machine 2: "); for (x = cp.GetFirst(s2); !x.Equals(cp.GetLast(s2)); x = cp.GetNext(s2, x)) { Console.WriteLine(cp.GetDomain(x)); } Console.WriteLine(cp.GetDomain(x)); Console.WriteLine("Makespan \t: " + cp.ObjValue); } else { Console.WriteLine("No solution found."); } } catch (IloException e) { Console.WriteLine("Error: " + e); } }
static void Main(string[] args) { int D = 5; int W = 5; int H = 3; int G = 2; int T = 12; int[] k_g = new int[] { 2, 2 }; int ALLK = 4; int[] cc_d = new int[] { 2, 1, 2, 1, 2 }; int[] ave = new int[] { 1, 0, 0, 1, 0, 0, 1, 1, 1, 1, 1, 1 }; int[] dur = new int[] { 1, 2, 1, 1, 2 }; int[] prf_D = new int[] { 2, 1, 1, 1, 100 }; int[] indexg_d = new int[] { 0, 1, 1, 1, 0 }; CP roster = new CP(); // intern availbility INumToNumStepFunction resource_AveIntern = roster.NumToNumStepFunction(0, T, 100, "AvailibilityOfIntern"); for (int t = 0; t < T; t++) { if (ave[t] == 0) { resource_AveIntern.SetValue(t, t + 1, 0); } } // discipline IIntervalVar[] discipline_d = new IIntervalVar[D]; ICumulFunctionExpr hospitalNotRR = roster.CumulFunctionExpr(); for (int d = 0; d < D; d++) { discipline_d[d] = roster.IntervalVar(); discipline_d[d].EndMax = T; discipline_d[d].EndMin = dur[d]; discipline_d[d].LengthMax = dur[d]; discipline_d[d].LengthMin = dur[d]; discipline_d[d].SizeMax = dur[d]; discipline_d[d].SizeMin = dur[d]; discipline_d[d].StartMax = T; discipline_d[d].StartMin = 0; discipline_d[d].SetIntensity(resource_AveIntern, 100); hospitalNotRR.Add(roster.Pulse(discipline_d[d], 1)); discipline_d[d].SetOptional(); } IIntervalSequenceVar dis = roster.IntervalSequenceVar(discipline_d); roster.Add(roster.Ge(roster.PresenceOf(discipline_d[1]), roster.PresenceOf(discipline_d[4]))); roster.Add(roster.Before(dis, discipline_d[1], discipline_d[4])); roster.Add(roster.NoOverlap(discipline_d)); // desciplien for not renewable resources IIntVar[] height_t = new IIntVar[T]; for (int t = 0; t < T; t++) { height_t[t] = roster.IntVar(0, 1); } INumToNumSegmentFunction piecewise = roster.NumToNumSegmentFunction(new double[] { 0, 0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 7, 7, 8, 8, 9, 9, 10, 10, 11, 11 }, new double[] { 10, 0, 10, 1, 10, 2, 10, 3, 10, 4, 10, 5, 10, 6, 10, 7, 10, 8, 10, 9, 10, 10, 10, 11 }); INumExpr rc = roster.NumExpr(); for (int d = 0; d < D; d++) { rc = roster.Sum(rc, roster.StartEval(discipline_d[d], piecewise, 0)); } for (int t = 0; t < T; t++) { } IIntervalVar[] disciplineNR_d = new IIntervalVar[D]; for (int d = 0; d < D; d++) { disciplineNR_d[d] = roster.IntervalVar(); disciplineNR_d[d].EndMax = T; disciplineNR_d[d].EndMin = T; disciplineNR_d[d].LengthMax = T; disciplineNR_d[d].LengthMin = T; disciplineNR_d[d].SizeMax = T; disciplineNR_d[d].SizeMin = T; disciplineNR_d[d].StartMax = T; disciplineNR_d[d].StartMin = 0; disciplineNR_d[d].SetOptional(); roster.IfThen(roster.PresenceOf(discipline_d[d]), roster.PresenceOf(disciplineNR_d[d])); } //roster.Add(roster.IfThen(roster.PresenceOf(discipline_d[4]), roster.And(roster.Le(roster.EndOf(discipline_d[4]), roster.StartOf(discipline_d[0])),roster.PresenceOf(discipline_d[0])))); //roster.Add(roster.StartBeforeEnd(discipline_d[4],discipline_d[0])); // hospital changes //ICumulFunctionExpr[] hospital //for (int d = 0; d < D; d++) //{ // roster.IfThen(roster.PresenceOf(disciplineNR_d[d]),); //} // hospital assignment IIntervalVar[][] Hospital_dh = new IIntervalVar[D][]; for (int d = 0; d < D; d++) { Hospital_dh[d] = new IIntervalVar[H]; for (int h = 0; h < H; h++) { Hospital_dh[d][h] = roster.IntervalVar(); Hospital_dh[d][h].EndMax = T; Hospital_dh[d][h].EndMin = dur[d]; Hospital_dh[d][h].LengthMax = dur[d]; Hospital_dh[d][h].LengthMin = dur[d]; Hospital_dh[d][h].SizeMax = dur[d]; Hospital_dh[d][h].SizeMin = dur[d]; Hospital_dh[d][h].StartMax = T; Hospital_dh[d][h].StartMin = 0; Hospital_dh[d][h].SetOptional(); if (h == 0 && (d != 4)) { Hospital_dh[d][h].SetAbsent(); } if (h == 1 && (d == 4)) { Hospital_dh[d][h].SetAbsent(); } if (h == 2 && (d == 4)) { Hospital_dh[d][h].SetAbsent(); } } roster.Add(roster.Alternative(discipline_d[d], Hospital_dh[d])); } IIntervalVar[] disHospSetUp_dh = new IIntervalVar[D * H]; int[] type = new int[D * H]; for (int dh = 0; dh < D * H; dh++) { int dIndex = dh % D; int hIndex = dh / D; disHospSetUp_dh[dh] = roster.IntervalVar("DsiHosp" + "[" + dIndex + "][" + hIndex + "]"); type[dh] = hIndex; disHospSetUp_dh[dh].SetOptional(); disHospSetUp_dh[dh] = Hospital_dh[dIndex][hIndex]; } // changes IIntervalSequenceVar cc = roster.IntervalSequenceVar(disHospSetUp_dh, type); roster.NoOverlap(cc); IIntVar[][] change_dD = new IIntVar[D][]; for (int d = 0; d < D; d++) { change_dD[d] = new IIntVar[D]; for (int dd = 0; dd < D; dd++) { change_dD[d][dd] = roster.IntVar(0, 1, "change_dD[" + d + "][" + dd + "]"); } } IIntVar[] change_d = new IIntVar[D]; for (int d = 0; d < D; d++) { change_d[d] = roster.IntVar(0, 1, "change_d[" + d + "]"); } for (int dh = 0; dh < D * H; dh++) { int dIndex = dh % D; int hIndex = dh / D; IIntExpr chngD = roster.IntExpr(); chngD = roster.Sum(chngD, change_d[dIndex]); roster.Add(roster.IfThen(roster.And(roster.PresenceOf(disHospSetUp_dh[dh]), roster.Neq(roster.TypeOfNext(cc, disHospSetUp_dh[dh], hIndex, hIndex), hIndex)), roster.Eq(chngD, 1))); for (int ddh = 0; ddh < D * H; ddh++) { int ddIndex = ddh % D; int hhIndex = ddh / D; if (hhIndex == hIndex || dIndex == ddIndex) { continue; } } } //IIntVar[][] y_dD = new IIntVar[D][]; //for (int d = 0; d < D; d++) //{ // y_dD[d] = new IIntVar[D]; // for (int dd= 0; dd < D; dd++) // { // y_dD[d][dd] = roster.IntVar(0,1); // if (d == dd) // { // y_dD[d][dd] = roster.IntVar(0, 0); // } // } //} //for (int d = 0; d < D; d++) //{ // for (int dd = 0; dd < D; dd++) // { // if (d != dd) // { // for (int h = 0; h < H; h++) // { // for (int hh = 0; hh < H; hh++) // { // if (d != dd && h != hh && true) // { // IIntExpr yyy = roster.IntExpr(); // yyy = roster.Sum(yyy,roster.Prod(T,y_dD[d][dd])); // yyy = roster.Sum(yyy, roster.Prod(1, roster.EndOf(Hospital_dh[dd][hh]))); // yyy = roster.Sum(yyy, roster.Prod(-1, roster.StartOf(Hospital_dh[d][h]))); // roster.Add( roster.IfThen(roster.And(roster.PresenceOf(Hospital_dh[d][h]), roster.PresenceOf(Hospital_dh[dd][hh])), roster.AddGe(yyy, 0))); // } // } // } // } // } //} //for (int d = 0; d < D; d++) //{ // for (int dd = 0; dd < D; dd++) // { // if (d == dd) // { // continue; // } // IIntExpr change = roster.IntExpr(); // change = roster.Sum(change, change_dD[dd][d]); // change = roster.Sum(change, roster.Prod(-1, y_dD[dd][d])); // for (int ddd = 0; ddd < D; ddd++) // { // if (ddd == d || ddd == dd) // { // continue; // } // change = roster.Sum(change, change_dD[dd][ddd]); // } // roster.Add(roster.IfThen(roster.And(roster.PresenceOf(discipline_d[d]), roster.PresenceOf(discipline_d[dd])), roster.AddEq(change, 0))); // } //} // all group assignment IIntExpr allPossibleCourses = roster.IntExpr(); for (int d = 0; d < D; d++) { allPossibleCourses = roster.Sum(allPossibleCourses, roster.Prod(cc_d[d], roster.PresenceOf(discipline_d[d]))); } roster.AddEq(allPossibleCourses, ALLK); // group assignment for (int g = 0; g < G; g++) { IIntExpr groupedCours_g = roster.IntExpr(); for (int d = 0; d < D; d++) { if (indexg_d[d] == g) { groupedCours_g = roster.Sum(groupedCours_g, roster.Prod(cc_d[d], roster.PresenceOf(discipline_d[d]))); } } roster.AddGe(groupedCours_g, k_g[g]); } // stay in one hospital // objective function INumExpr objExp = roster.NumExpr(); // discipline desire for (int d = 0; d < D; d++) { objExp = roster.Sum(objExp, roster.Prod(prf_D[d], roster.PresenceOf(discipline_d[d]))); for (int dd = 0; dd < D; dd++) { objExp = roster.Sum(objExp, roster.Prod(-1, change_d[d])); } } objExp = roster.Sum(objExp, rc); IIntExpr makespan = roster.IntExpr(); for (int d = 0; d < D; d++) { makespan = roster.Max(makespan, roster.EndOf(discipline_d[d])); } IIntVar wait = roster.IntVar(0, T); IIntExpr waitConst = roster.IntExpr(); waitConst = roster.Sum(waitConst, wait); waitConst = roster.Sum(waitConst, roster.Prod(-1, makespan)); for (int d = 0; d < D; d++) { waitConst = roster.Sum(waitConst, roster.Prod(dur[d], roster.PresenceOf(discipline_d[d]))); } roster.AddEq(waitConst, 0); roster.AddMaximize(objExp); roster.ExportModel("Roster.cpo"); roster.SetParameter(CP.IntParam.TimeMode, CP.ParameterValues.ElapsedTime); roster.SetParameter(CP.IntParam.LogVerbosity, CP.ParameterValues.Quiet); roster.SetParameter(CP.IntParam.SolutionLimit, 10); // solve it now if (roster.Solve()) { Console.WriteLine("this is the cost of the CP column {0}", roster.ObjValue); for (int d = 0; d < D; d++) { if (roster.IsPresent(discipline_d[d])) { Console.WriteLine("Discipline {0} with CC {1} and Dur {2} and Prf {3} started at time {4} and finished at time {5}", d, cc_d[d], dur[d], prf_D[d], roster.GetStart(discipline_d[d]), roster.GetEnd(discipline_d[d])); } } for (int d = 0; d < D; d++) { for (int h = 0; h < H; h++) { if (roster.IsPresent(Hospital_dh[d][h])) { Console.WriteLine("Discipline {0} with CC {1} and Dur {2} and Prf {3} started at time {4} and finished at time {5} at Hospitail {6}", d, cc_d[d], dur[d], prf_D[d], roster.GetStart(Hospital_dh[d][h]), roster.GetEnd(Hospital_dh[d][h]), h); } } } for (int d = 0; d < D * H; d++) { int dIndex = d % D; int hIndex = d / D; if (roster.IsPresent(disHospSetUp_dh[d])) { Console.WriteLine("discpline " + dIndex + " in hospital " + hIndex); } } for (int d = 0; d < D; d++) { if (roster.GetValue(change_d[d]) > 0.5) { Console.WriteLine("We have change for discipline {0}", d); } for (int dd = 0; dd < D; dd++) { if (d == dd) { continue; } } } Console.WriteLine("========================================="); Console.WriteLine("Wainting time {0}", roster.GetValue(wait)); } }
public static IIntExpr Game(CP cp, IIntExpr h, IIntExpr a, int n) { return cp.Diff(cp.Sum(cp.Prod(h, n - 1), a), cp.Gt(a, h)); }
public static void Main(String[] args) { String filename = "../../../../examples/data/learningeffect_default.data"; int nbJobs, nbMachines; if (args.Length > 0) { filename = args[0]; } CP cp = new CP(); DataReader data = new DataReader(filename); nbJobs = data.Next(); nbMachines = data.Next(); IIntExpr[] ends = new IIntExpr[nbJobs]; IIntervalVar[][] machines = new IIntervalVar[nbMachines][]; int[][] sizes = new int[nbMachines][]; for (int j = 0; j < nbMachines; j++) { machines[j] = new IIntervalVar[nbJobs]; sizes[j] = new int[nbJobs]; } for (int i = 0; i < nbJobs; i++) { IIntervalVar prec = cp.IntervalVar(); for (int j = 0; j < nbMachines; j++) { int m, d; m = data.Next(); d = data.Next(); IIntervalVar ti = cp.IntervalVar(0, d); machines[m][i] = ti; sizes[m][i] = d; if (j > 0) { cp.Add(cp.EndBeforeStart(prec, ti)); } prec = ti; } ends[i] = cp.EndOf(prec); } for (int j = 0; j < nbMachines; j++) { double alpha = data.Next() / ((double)100); IIntervalVar[] chain = new IIntervalVar[nbJobs]; IIntervalVar prec = cp.IntervalVar(); IIntExpr[] indices = new IIntExpr[nbJobs]; for (int i = 0; i < nbJobs; i++) { IIntervalVar syncti = cp.IntervalVar(); if (i > 0) { cp.Add(cp.EndBeforeStart(prec, syncti)); } prec = syncti; chain[i] = syncti; IIntExpr index = cp.IntVar(0, nbJobs - 1); indices[i] = index; // Learning effect captured by the decreasing function // of the position (0 <= alpha <= 1). // At first position, in the sequence index = 0; there is no // learning effect and duration of the task is its nominal duration INumExpr floatDur = cp.Prod(sizes[j][i], cp.Power(alpha, index)); cp.Add(cp.Le( cp.Abs(cp.Diff(floatDur, cp.SizeOf(machines[j][i]))), 0.5) ); } cp.Add(cp.Isomorphism(chain, machines[j], indices, nbJobs)); // The no-overlap is a redundant constraint in this quite // simple model - it is used only to provide stronger inference. cp.Add(cp.NoOverlap(machines[j])); } IObjective objective = cp.Minimize(cp.Max(ends)); cp.Add(objective); cp.SetParameter(CP.IntParam.LogPeriod, 10000); Console.WriteLine("Instance \t: " + filename); if (cp.Solve()) { Console.WriteLine("Makespan \t: " + cp.ObjValue); } else { Console.WriteLine("No solution found."); } }
public static IIntExpr Game(CP cp, IIntExpr h, IIntExpr a, int n) { return(cp.Diff(cp.Sum(cp.Prod(h, n - 1), a), cp.Gt(a, h))); }
static void Main(string[] args) { String filename; if (args.Length > 0) { filename = args[0]; } else { filename = "../../../../examples/data/plant_location.data"; } DataReader data = new DataReader(filename); int nbCustomer = data.Next(); int nbLocation = data.Next(); int[][] cost = new int[nbCustomer][]; for (int c = 0; c < nbCustomer; c++) { cost[c] = new int[nbLocation]; for (int l = 0; l < nbLocation; l++) { cost[c][l] = data.Next(); } } int[] demand = new int[nbCustomer]; int totalDemand = 0; for (int c = 0; c < nbCustomer; c++) { demand[c] = data.Next(); totalDemand += demand[c]; } int[] fixedCost = new int[nbLocation]; for (int l = 0; l < nbLocation; l++) { fixedCost[l] = data.Next(); } int[] capacity = new int[nbLocation]; for (int l = 0; l < nbLocation; l++) { capacity[l] = data.Next(); } CP cp = new CP(); IIntVar[] cust = new IIntVar[nbCustomer]; for (int c = 0; c < nbCustomer; c++) { cust[c] = cp.IntVar(0, nbLocation - 1); } IIntVar[] open = new IIntVar[nbLocation]; IIntVar[] load = new IIntVar[nbLocation]; for (int l = 0; l < nbLocation; l++) { open[l] = cp.IntVar(0, 1); load[l] = cp.IntVar(0, capacity[l]); } for (int l = 0; l < nbLocation; l++) { cp.Add(cp.Eq(open[l], cp.Gt(load[l], 0))); } cp.Add(cp.Pack(load, cust, demand)); IIntExpr obj = cp.Prod(open, fixedCost); for (int c = 0; c < nbCustomer; c++) { obj = cp.Sum(obj, cp.Element(cost[c], cust[c])); } cp.Add(cp.Minimize(obj)); cp.AddKPI(cp.Quot(totalDemand, cp.ScalProd(open, capacity)), "Mean occupancy"); INumExpr[] usage = new INumExpr[nbLocation]; for (int w = 0; w < nbLocation; w++) { usage[w] = cp.Sum(cp.Quot(load[w], capacity[w]), cp.Diff(1, open[w])); } cp.AddKPI(cp.Min(usage), "Min occupancy"); int[] custValues = { 19, 0, 11, 8, 29, 9, 29, 28, 17, 15, 7, 9, 18, 15, 1, 17, 25, 18, 17, 27, 22, 1, 26, 3, 22, 2, 20, 27, 2, 16, 1, 16, 12, 28, 19, 2, 20, 14, 13, 27, 3, 9, 18, 0, 13, 19, 27, 14, 12, 1, 15, 14, 17, 0, 7, 12, 11, 0, 25, 16, 22, 13, 16, 8, 18, 27, 19, 23, 26, 13, 11, 11, 19, 22, 28, 26, 23, 3, 18, 23, 26, 14, 29, 18, 9, 7, 12, 27, 8, 20 }; ISolution sol = cp.Solution(); for (int c = 0; c < nbCustomer; c++) { sol.SetValue(cust[c], custValues[c]); } cp.SetStartingPoint(sol); cp.SetParameter(CP.DoubleParam.TimeLimit, 10); cp.SetParameter(CP.IntParam.LogPeriod, 10000); cp.Solve(); }
public static void Main(String[] args) { CP cp = new CP(); dist[0] = new int[] { 16, 1, 1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 2, 1, 1, 0, 0, 0, 2, 2, 1, 1, 1 }; dist[1] = new int[] { 1, 16, 2, 0, 0, 0, 0, 0, 2, 2, 1, 1, 1, 2, 2, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0 }; dist[2] = new int[] { 1, 2, 16, 0, 0, 0, 0, 0, 2, 2, 1, 1, 1, 2, 2, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0 }; dist[3] = new int[] { 0, 0, 0, 16, 2, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 1, 1 }; dist[4] = new int[] { 0, 0, 0, 2, 16, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 1, 1 }; dist[5] = new int[] { 0, 0, 0, 2, 2, 16, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 0, 0, 1, 1 }; dist[6] = new int[] { 0, 0, 0, 0, 0, 0, 16, 2, 0, 0, 1, 1, 1, 0, 0, 1, 1, 1, 1, 2, 0, 0, 0, 1, 1 }; dist[7] = new int[] { 0, 0, 0, 0, 0, 0, 2, 16, 0, 0, 1, 1, 1, 0, 0, 1, 1, 1, 1, 2, 0, 0, 0, 1, 1 }; dist[8] = new int[] { 1, 2, 2, 0, 0, 0, 0, 0, 16, 2, 2, 2, 2, 2, 2, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1 }; dist[9] = new int[] { 1, 2, 2, 0, 0, 0, 0, 0, 2, 16, 2, 2, 2, 2, 2, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1 }; dist[10] = new int[] { 1, 1, 1, 0, 0, 0, 1, 1, 2, 2, 16, 2, 2, 2, 2, 2, 2, 1, 1, 2, 1, 1, 0, 1, 1 }; dist[11] = new int[] { 1, 1, 1, 0, 0, 0, 1, 1, 2, 2, 2, 16, 2, 2, 2, 2, 2, 1, 1, 2, 1, 1, 0, 1, 1 }; dist[12] = new int[] { 1, 1, 1, 0, 0, 0, 1, 1, 2, 2, 2, 2, 16, 2, 2, 2, 2, 1, 1, 2, 1, 1, 0, 1, 1 }; dist[13] = new int[] { 2, 2, 2, 0, 0, 0, 0, 0, 2, 2, 2, 2, 2, 16, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }; dist[14] = new int[] { 2, 2, 2, 0, 0, 0, 0, 0, 2, 2, 2, 2, 2, 2, 16, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }; dist[15] = new int[] { 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 1, 1, 16, 2, 2, 2, 1, 2, 2, 1, 2, 2 }; dist[16] = new int[] { 1, 1, 1, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 1, 1, 2, 16, 2, 2, 1, 2, 2, 1, 2, 2 }; dist[17] = new int[] { 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 16, 2, 2, 1, 1, 0, 2, 2 }; dist[18] = new int[] { 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 16, 2, 1, 1, 0, 2, 2 }; dist[19] = new int[] { 0, 0, 0, 1, 1, 1, 2, 2, 1, 1, 2, 2, 2, 1, 1, 1, 1, 2, 2, 16, 1, 1, 0, 1, 1 }; dist[20] = new int[] { 2, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 2, 2, 1, 1, 1, 16, 2, 1, 2, 2 }; dist[21] = new int[] { 2, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 2, 2, 1, 1, 1, 2, 16, 1, 2, 2 }; dist[22] = new int[] { 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 1, 1, 16, 1, 1 }; dist[23] = new int[] { 1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 1, 2, 2, 1, 16, 2 }; dist[24] = new int[] { 1, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 1, 2, 2, 1, 2, 16 }; int nbTransmitters = getTransmitterIndex(nbCell, 0); IIntVar[] freq = cp.IntVarArray(nbTransmitters, 0, nbAvailFreq - 1, "freq"); for (int cell = 0; cell < nbCell; cell++) { for (int channel1 = 0; channel1 < nbChannel[cell]; channel1++) { for (int channel2 = channel1 + 1; channel2 < nbChannel[cell]; channel2++) { cp.Add(cp.Ge(cp.Abs(cp.Diff(freq[getTransmitterIndex(cell, channel1)], freq[getTransmitterIndex(cell, channel2)])), 16)); } } } for (int cell1 = 0; cell1 < nbCell; cell1++) { for (int cell2 = cell1 + 1; cell2 < nbCell; cell2++) { if (dist[cell1][cell2] > 0) { for (int channel1 = 0; channel1 < nbChannel[cell1]; channel1++) { for (int channel2 = 0; channel2 < nbChannel[cell2]; channel2++) { cp.Add(cp.Ge(cp.Abs(cp.Diff(freq[getTransmitterIndex(cell1, channel1)], freq[getTransmitterIndex(cell2, channel2)])), dist[cell1][cell2])); } } } } } // Minimizing the total number of frequencies IIntExpr nbFreq = cp.CountDifferent(freq); cp.Add(cp.Minimize(nbFreq)); cp.SetParameter(CP.IntParam.CountDifferentInferenceLevel, CP.ParameterValues.Extended); cp.SetParameter(CP.IntParam.FailLimit, 40000); cp.SetParameter(CP.IntParam.LogPeriod, 100000); if (cp.Solve()) { for (int cell = 0; cell < nbCell; cell++) { for (int channel = 0; channel < nbChannel[cell]; channel++) { Console.Write(cp.GetIntValue(freq[getTransmitterIndex(cell, channel)]) + " "); } Console.WriteLine(); } Console.WriteLine("Total # of sites " + nbTransmitters); Console.WriteLine("Total # of frequencies " + cp.GetValue(nbFreq)); } else { Console.WriteLine("No solution"); } cp.End(); }
static public void Main(string[] args) { int numPeriods = 6; if (args.Length > 0) { numPeriods = Int32.Parse(args[0]); } CP cp = new CP(); // // Variables // // Host boat choice IIntVar[] host = new IIntVar[numBoats]; for (int j = 0; j < numBoats; j++) { host[j] = cp.IntVar(0, 1, String.Format("H{0}", j)); } // Who is where each time period (time- and boat-based views) IIntVar[][] timePeriod = new IIntVar[numPeriods][]; for (int i = 0; i < numPeriods; i++) { timePeriod[i] = new IIntVar[numBoats]; for (int j = 0; j < numBoats; j++) { timePeriod[i][j] = cp.IntVar(0, numBoats - 1, String.Format("T{0},{1}", i, j)); } } IIntVar[][] visits = Transpose(timePeriod); // // Objective // IIntVar numHosts = cp.IntVar(numPeriods, numBoats); cp.Add(cp.Eq(numHosts, cp.Sum(host))); cp.Add(cp.Minimize(numHosts)); // // Constraints // // Stay in my boat (host) or only visit other boats (guest) for (int i = 0; i < numBoats; i++) { cp.Add(cp.Eq(cp.Count(visits[i], i), cp.Prod(host[i], numPeriods))); } // Capacity constraints: only hosts have capacity for (int p = 0; p < numPeriods; p++) { IIntVar[] load = new IIntVar[numBoats]; for (int j = 0; j < numBoats; j++) { load[j] = cp.IntVar(0, boatSize[j], String.Format("L{0},{1}", p, j)); cp.Add(cp.Le(load[j], cp.Prod(host[j], boatSize[j]))); } cp.Add(cp.Pack(load, timePeriod[p], crewSize, numHosts)); } // No two crews meet more than once for (int i = 0; i < numBoats; i++) { for (int j = i + 1; j < numBoats; j++) { IIntExpr timesMet = cp.Constant(0); for (int p = 0; p < numPeriods; p++) { timesMet = cp.Sum(timesMet, cp.Eq(visits[i][p], visits[j][p])); } cp.Add(cp.Le(timesMet, 1)); } } // Host and guest boat constraints: given in problem spec cp.Add(cp.Eq(host[0], 1)); cp.Add(cp.Eq(host[1], 1)); cp.Add(cp.Eq(host[2], 1)); cp.Add(cp.Eq(host[39], 0)); cp.Add(cp.Eq(host[40], 0)); cp.Add(cp.Eq(host[41], 0)); // // Solving // if (cp.Solve()) { Console.WriteLine("Solution at cost = {0}", cp.GetValue(numHosts)); Console.Write("Hosts: "); for (int i = 0; i < numBoats; i++) { Console.Write(cp.GetValue(host[i])); } Console.WriteLine(); for (int p = 0; p < numPeriods; p++) { Console.WriteLine("Period {0}", p); for (int h = 0; h < numBoats; h++) { if (cp.GetValue(host[h]) > 0) { Console.Write("\tHost {0} : ", h); int load = 0; for (int i = 0; i < numBoats; i++) { if (cp.GetValue(visits[i][p]) == h) { load += crewSize[i]; Console.Write("{0} ({1}) ", i, crewSize[i]); } } Console.WriteLine(" --- {0} / {1}", load, boatSize[h]); } } } Console.WriteLine(); } }
/* * MakeTeamTuples return a IIntTupleSet containing all the possible configurations of a team. * The team members in a tuple are ordered to break symmetry. */ public static IIntTupleSet MakeTeamTuples(CP mainCP) { CP cp = new CP(); int i; int[] newEmployee = new int[nbPersons]; int[] service = new int[nbPersons]; for (i = 0; i < nbPersons; i++) { if ((i % 2) == 0) { newEmployee[i] = 1; } else { newEmployee[i] = 0; } if (i < 20) { service[i] = 0; } else if (i < 40) { service[i] = 1; } else if (i < 45) { service[i] = 2; } else if (i < 50) { service[i] = 3; } else if (i < 55) { service[i] = 4; } else { service[i] = 5; } } IIntTupleSet ts = mainCP.IntTable(teamSize); IIntVar[] teamMembers = cp.IntVarArray(teamSize, 0, nbPersons - 1); //number of new employees among the teamMembers = number of teamMembers / 2 IIntExpr nbNewEmployees = cp.Constant(0); for (i = 0; i < teamSize; i++) { nbNewEmployees = cp.Sum(nbNewEmployees, cp.Element(newEmployee, teamMembers[i])); } cp.Add(cp.Eq(nbNewEmployees, teamSize / 2)); //a new employee and his coach must be in the same team for (i = 0; i < 60; i += 2) { if (coaching[i] >= 0) { cp.Add(cp.Eq(cp.Count(teamMembers, i), cp.Count(teamMembers, coaching[i]))); } } IIntVar[] serviceVar = cp.IntVarArray(teamSize, 0, numServices - 1); for (i = 0; i < teamSize; i++) { cp.Add(cp.Eq(serviceVar[i], cp.Element(service, teamMembers[i]))); } // at most 4 people of the same service for (i = 0; i < numServices; i++) { cp.Add(cp.Le(cp.Count(serviceVar, i), 4)); } //Persons of Services A and B cannot be in the same team //Persons of Services E and F cannot be in the same team cp.Add(cp.Or(cp.Eq(cp.Count(serviceVar, 0), 0), cp.Eq(cp.Count(serviceVar, 1), 0))); cp.Add(cp.Or(cp.Eq(cp.Count(serviceVar, 4), 0), cp.Eq(cp.Count(serviceVar, 5), 0))); // order the teamMembers to break symmetry for (i = 0; i < teamSize - 1; i++) { cp.Add(cp.Lt(teamMembers[i], teamMembers[i + 1])); } int[] tuple = new int[teamSize]; cp.SetParameter(CP.IntParam.LogVerbosity, CP.ParameterValues.Quiet); cp.SetParameter(CP.IntParam.SearchType, CP.ParameterValues.DepthFirst); cp.StartNewSearch(); while (cp.Next()) { for (i = 0; i < teamSize; i++) { tuple[i] = (int)cp.GetValue(teamMembers[i]); } cp.AddTuple(ts, tuple); } return(ts); }
public static void Main(String[] args) { String filename = "../../../../examples/data/rcpspmm_default.data"; int failLimit = 30000; int nbTasks, nbRenewable, nbNonRenewable; if (args.Length > 0) filename = args[0]; if (args.Length > 1) failLimit = Convert.ToInt32(args[1]); CP cp = new CP(); DataReader data = new DataReader(filename); nbTasks = data.Next(); nbRenewable = data.Next(); nbNonRenewable = data.Next(); ICumulFunctionExpr[] renewables = new ICumulFunctionExpr[nbRenewable]; IIntExpr[] nonRenewables = new IIntExpr[nbNonRenewable]; int[] capRenewables = new int[nbRenewable]; int[] capNonRenewables = new int[nbNonRenewable]; for (int j = 0; j < nbRenewable; j++) { renewables[j] = cp.CumulFunctionExpr(); capRenewables[j] = data.Next(); } for (int j = 0; j < nbNonRenewable; j++) { nonRenewables[j] = cp.IntExpr(); capNonRenewables[j] = data.Next(); } IIntervalVar[] tasks = new IIntervalVar[nbTasks]; List<IIntervalVar>[] modes = new List<IIntervalVar>[nbTasks]; for (int i = 0; i < nbTasks; i++) { tasks[i] = cp.IntervalVar(); modes[i] = new List<IIntervalVar>(); } List<IIntExpr> ends = new List<IIntExpr>(); for (int i = 0; i < nbTasks; i++) { IIntervalVar task = tasks[i]; int d = data.Next(); int nbModes = data.Next(); int nbSucc = data.Next(); for (int k = 0; k < nbModes; k++) { IIntervalVar alt = cp.IntervalVar(); alt.SetOptional(); modes[i].Add(alt); } cp.Add(cp.Alternative(task, modes[i].ToArray())); ends.Add(cp.EndOf(task)); for (int s = 0; s < nbSucc; s++) { int succ = data.Next(); cp.Add(cp.EndBeforeStart(task, tasks[succ])); } } for (int i = 0; i < nbTasks; i++) { IIntervalVar task = tasks[i]; List<IIntervalVar> imodes = modes[i]; for (int k = 0; k < imodes.Count; k++) { int taskId = data.Next(); int modeId = data.Next(); int d = data.Next(); imodes[k].SizeMin = d; imodes[k].SizeMax = d; int q; for (int j = 0; j < nbNonRenewable; j++) { q = data.Next(); if (0 < q) { renewables[j].Add(cp.Pulse(imodes[k], q)); } } for (int j = 0; j < nbNonRenewable; j++) { q = data.Next(); if (0 < q) { nonRenewables[j] = cp.Sum(nonRenewables[j], cp.Prod(q, cp.PresenceOf(imodes[k]))); } } } } for (int j = 0; j < nbRenewable; j++) { cp.Add(cp.Le(renewables[j], capRenewables[j])); } for (int j = 0; j < nbRenewable; j++) { cp.Add(cp.Le(nonRenewables[j], capNonRenewables[j])); } IObjective objective = cp.Minimize(cp.Max(ends.ToArray())); cp.Add(objective); cp.SetParameter(CP.IntParam.FailLimit, failLimit); Console.WriteLine("Instance \t: " + filename); if (cp.Solve()) { Console.WriteLine("Makespan \t: " + cp.ObjValue); } else { Console.WriteLine("No solution found."); } }
private void BuildModel() { // Create the decision variables, cost, and the model scene = new IIntVar[numScenes]; for (int s = 0; s < numScenes; s++) scene[s] = cp.IntVar(0, numScenes - 1); // Expression representing the global cost idleCost = cp.IntExpr(); // Make the slot-based secondary model IIntVar[] slot = new IIntVar[numScenes]; for (int s = 0; s < numScenes; s++) slot[s] = cp.IntVar(0, numScenes - 1); cp.Add(cp.Inverse(scene, slot)); // Loop over all actors, building cost for (int a = 0; a < numActors; a++) { // Expression for the waiting time for this actor IIntExpr actorWait = cp.IntExpr(); // Calculate the first and last slots where this actor plays List<IIntVar> position = new List<IIntVar>(); System.Collections.IEnumerator en = actorInScene[a].GetEnumerator(); while (en.MoveNext()) position.Add(slot[(int)en.Current]); IIntExpr firstSlot = cp.Min(position.ToArray()); IIntExpr lastSlot = cp.Max(position.ToArray()); // If an actor is not in a scene, he waits // if he is on set when the scene is filmed for (int s = 0; s < numScenes; s++) { if (!actorInScene[a].Contains(s)) { // not in scene IIntExpr wait = cp.And(cp.Le(firstSlot, slot[s]), cp.Le( slot[s], lastSlot)); actorWait = cp.Sum(actorWait, cp.Prod(sceneDuration[s], wait)); } } // Accumulate the cost of waiting time for this actor idleCost = cp.Sum(idleCost, cp.Prod(actorPay[a], actorWait)); } cp.Add(cp.Minimize(idleCost)); }
static public void Main(string[] args) { CP cp = new CP(); int nbTruckConfigs = 7; // number of possible configurations for the truck int nbOrders = 21; int nbCustomers = 3; int nbTrucks = 15; //max number of travels of the truck int[] maxTruckConfigLoad = //Capacity of the truck depends on its config { 11, 11, 11, 11, 10, 10, 10 }; int maxLoad = Max(maxTruckConfigLoad); int[] customerOfOrder = { 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 2 }; int[] volumes = { 3, 4, 3, 2, 5, 4, 11, 4, 5, 2, 4, 7, 3, 5, 2, 5, 6, 11, 1, 6, 3 }; int[] colors = { 1, 2, 0, 1, 1, 1, 0, 0, 0, 0, 2, 2, 2, 0, 2, 1, 0, 2, 0, 0, 0 }; int[] truckCost = //cost for loading a truck of a given config { 2, 2, 2, 3, 3, 3, 4 }; //Decision variables IIntVar[] truckConfigs = cp.IntVarArray(nbTrucks, 0, nbTruckConfigs - 1); //configuration of the truck IIntVar[] where = cp.IntVarArray(nbOrders, 0, nbTrucks - 1); //In which truck is an order IIntVar[] load = cp.IntVarArray(nbTrucks, 0, maxLoad); //load of a truck IIntVar numUsed = cp.IntVar(0, nbTrucks); // number of trucks used IIntVar[] customerOfTruck = cp.IntVarArray(nbTrucks, 0, nbCustomers); // transition costs between trucks IIntTupleSet costTuples = cp.IntTable(3); cp.AddTuple(costTuples, new int[] { 0, 0, 0 }); cp.AddTuple(costTuples, new int[] { 0, 1, 0 }); cp.AddTuple(costTuples, new int[] { 0, 2, 0 }); cp.AddTuple(costTuples, new int[] { 0, 3, 10 }); cp.AddTuple(costTuples, new int[] { 0, 4, 10 }); cp.AddTuple(costTuples, new int[] { 0, 5, 10 }); cp.AddTuple(costTuples, new int[] { 0, 6, 15 }); cp.AddTuple(costTuples, new int[] { 1, 0, 0 }); cp.AddTuple(costTuples, new int[] { 1, 1, 0 }); cp.AddTuple(costTuples, new int[] { 1, 2, 0 }); cp.AddTuple(costTuples, new int[] { 1, 3, 10 }); cp.AddTuple(costTuples, new int[] { 1, 4, 10 }); cp.AddTuple(costTuples, new int[] { 1, 5, 10 }); cp.AddTuple(costTuples, new int[] { 1, 6, 15 }); cp.AddTuple(costTuples, new int[] { 2, 0, 0 }); cp.AddTuple(costTuples, new int[] { 2, 1, 0 }); cp.AddTuple(costTuples, new int[] { 2, 2, 0 }); cp.AddTuple(costTuples, new int[] { 2, 3, 10 }); cp.AddTuple(costTuples, new int[] { 2, 4, 10 }); cp.AddTuple(costTuples, new int[] { 2, 5, 10 }); cp.AddTuple(costTuples, new int[] { 2, 6, 15 }); cp.AddTuple(costTuples, new int[] { 3, 0, 3 }); cp.AddTuple(costTuples, new int[] { 3, 1, 3 }); cp.AddTuple(costTuples, new int[] { 3, 2, 3 }); cp.AddTuple(costTuples, new int[] { 3, 3, 0 }); cp.AddTuple(costTuples, new int[] { 3, 4, 10 }); cp.AddTuple(costTuples, new int[] { 3, 5, 10 }); cp.AddTuple(costTuples, new int[] { 3, 6, 15 }); cp.AddTuple(costTuples, new int[] { 4, 0, 3 }); cp.AddTuple(costTuples, new int[] { 4, 1, 3 }); cp.AddTuple(costTuples, new int[] { 4, 2, 3 }); cp.AddTuple(costTuples, new int[] { 4, 3, 10 }); cp.AddTuple(costTuples, new int[] { 4, 4, 0 }); cp.AddTuple(costTuples, new int[] { 4, 5, 10 }); cp.AddTuple(costTuples, new int[] { 4, 6, 15 }); cp.AddTuple(costTuples, new int[] { 5, 0, 3 }); cp.AddTuple(costTuples, new int[] { 5, 1, 3 }); cp.AddTuple(costTuples, new int[] { 5, 2, 3 }); cp.AddTuple(costTuples, new int[] { 5, 3, 10 }); cp.AddTuple(costTuples, new int[] { 5, 4, 10 }); cp.AddTuple(costTuples, new int[] { 5, 5, 0 }); cp.AddTuple(costTuples, new int[] { 5, 6, 15 }); cp.AddTuple(costTuples, new int[] { 6, 0, 3 }); cp.AddTuple(costTuples, new int[] { 6, 1, 3 }); cp.AddTuple(costTuples, new int[] { 6, 2, 3 }); cp.AddTuple(costTuples, new int[] { 6, 3, 10 }); cp.AddTuple(costTuples, new int[] { 6, 4, 10 }); cp.AddTuple(costTuples, new int[] { 6, 5, 10 }); cp.AddTuple(costTuples, new int[] { 6, 6, 0 }); IIntVar[] transitionCost = cp.IntVarArray(nbTrucks - 1, 0, 1000); for (int i = 1; i < nbTrucks; i++) { IIntVar[] auxVars = new IIntVar[3]; auxVars[0] = truckConfigs[i - 1]; auxVars[1] = truckConfigs[i]; auxVars[2] = transitionCost[i - 1]; cp.Add(cp.AllowedAssignments(auxVars, costTuples)); } // constrain the volume of the orders in each truck cp.Add(cp.Pack(load, where, volumes, numUsed)); for (int i = 0; i < nbTrucks; i++) { cp.Add(cp.Le(load[i], cp.Element(maxTruckConfigLoad, truckConfigs[i]))); } // compatibility between the colors of an order and the configuration of its truck int[][] allowedContainerConfigs = new int[3][]; allowedContainerConfigs[0] = new int[] { 0, 3, 4, 6 }; allowedContainerConfigs[1] = new int[] { 1, 3, 5, 6 }; allowedContainerConfigs[2] = new int[] { 2, 4, 5, 6 }; for (int j = 0; j < nbOrders; j++) { IIntVar configOfContainer = cp.IntVar(allowedContainerConfigs[colors[j]]); cp.Add(cp.Eq(configOfContainer, cp.Element(truckConfigs, where[j]))); } // only one customer per truck for (int j = 0; j < nbOrders; j++) { cp.Add(cp.Eq(cp.Element(customerOfTruck, where[j]), customerOfOrder[j])); } // non used trucks are at the end for (int j = 1; j < nbTrucks; j++) { cp.Add(cp.Or(cp.Gt(load[j - 1], 0), cp.Eq(load[j], 0))); } // Dominance: the non used trucks keep the last used configuration cp.Add(cp.Gt(load[0], 0)); for (int i = 1; i < nbTrucks; i++) { cp.Add(cp.Or(cp.Gt(load[i], 0), cp.Eq(truckConfigs[i], truckConfigs[i - 1]))); } //Dominance: regroup deliveries with same configuration for (int i = nbTrucks - 2; i > 0; i--) { IConstraint Ct = cp.TrueConstraint(); for (int p = i + 1; p < nbTrucks; p++) { Ct = cp.And(cp.Neq(truckConfigs[p], truckConfigs[i - 1]), Ct); } cp.Add(cp.Or(cp.Eq(truckConfigs[i], truckConfigs[i - 1]), Ct)); } // Objective: first criterion for minimizing the cost for configuring and loading trucks // second criterion for minimizing the number of trucks IIntExpr obj1 = cp.Constant(0); for (int i = 0; i < nbTrucks; i++) { obj1 = cp.Sum(obj1, cp.Prod(cp.Element(truckCost, truckConfigs[i]), cp.Neq(load[i], 0))); } obj1 = cp.Sum(obj1, cp.Sum(transitionCost)); IIntExpr obj2 = numUsed; // Multicriteria lexicographic optimization cp.Add(cp.Minimize(cp.StaticLex(obj1, obj2))); cp.SetParameter(CP.DoubleParam.TimeLimit, 20); cp.SetParameter(CP.IntParam.LogPeriod, 50000); cp.Solve(); double[] obj = cp.GetObjValues(); Console.WriteLine("Configuration cost: " + (int)obj[0] + " Number of Trucks: " + (int)obj[1]); for (int i = 0; i < nbTrucks; i++) { if (cp.GetValue(load[i]) > 0) { Console.Write("Truck " + i + ": Config=" + cp.GetIntValue(truckConfigs[i]) + " Items= "); for (int j = 0; j < nbOrders; j++) { if (cp.GetValue(where[j]) == i) { Console.Write("<" + j + "," + colors[j] + "," + volumes[j] + "> "); } } Console.WriteLine(); } } }
public double SolveGoalProgramming(int branchLimit) { // Objective 1 Console.WriteLine(); Console.WriteLine(" ! ----------------------------------------------------------------------------"); Console.WriteLine(" ! STEP 1: Minimizing usage of expensive resources"); Console.WriteLine(" ! ----------------------------------------------------------------------------"); IIntExpr costExpr = cp.IntExpr(); for (int i = 0; i < nbJobs; i++) { for (int j = 0; j < nbMachines; j++) { if (costs[j][i] >= 1000) { costExpr = cp.Sum(costExpr, cp.Prod(costs[j][i], cp.PresenceOf(machines[j][i]))); } } } IObjective obj1 = cp.Minimize(costExpr); cp.Add(obj1); cp.SetParameter(CP.IntParam.LogPeriod, 600000); cp.SetParameter(CP.IntParam.BranchLimit, 2 * branchLimit / 3); cp.SetParameter(CP.IntParam.NoOverlapInferenceLevel, CP.ParameterValues.Extended); cp.Solve(); ISolution startSol = cp.Solution(); for (int i = 0; i < nbJobs; i++) { for (int j = 0; j < nbMachines; j++) { if (cp.IsPresent(machines[j][i])) { startSol.SetPresent(machines[j][i]); startSol.SetStart(machines[j][i], cp.GetStart(machines[j][i])); } } } // Objective 2 Console.WriteLine(); Console.WriteLine(" ! ----------------------------------------------------------------------------"); Console.WriteLine(" ! STEP 2: Minimizing total cost"); Console.WriteLine(" ! ----------------------------------------------------------------------------"); cp.Remove(obj1); IIntExpr costExpr2 = cp.IntExpr(); for (int i = 0; i < nbJobs; i++) { for (int j = 0; j < nbMachines; j++) { costExpr2 = cp.Sum(costExpr2, cp.Prod(costs[j][i], cp.PresenceOf(machines[j][i]))); } } IObjective obj2 = cp.Minimize(costExpr2); cp.Add(obj2); cp.SetParameter(CP.IntParam.BranchLimit, branchLimit / 3); cp.SetStartingPoint(startSol); cp.Solve(); double cost = cp.ObjValue; return(cost); }
static void Main(string[] args) { try { int n = 10; if (args.Length > 0) { n = Int32.Parse(args[0]); } if ((n % 2) == 1) { n++; } Console.WriteLine("Finding schedule for {0} teams", n); int nbWeeks = 2 * (n - 1); int nbGamesPerWeek = n / 2; int nbGames = n * (n - 1); CP cp = new CP(); IIntVar[][] games = new IIntVar[nbWeeks][]; IIntVar[][] home = new IIntVar[nbWeeks][]; IIntVar[][] away = new IIntVar[nbWeeks][]; for (int i = 0; i < nbWeeks; i++) { home[i] = cp.IntVarArray(nbGamesPerWeek, 0, n - 1); away[i] = cp.IntVarArray(nbGamesPerWeek, 0, n - 1); games[i] = cp.IntVarArray(nbGamesPerWeek, 0, nbGames - 1); } // // For each play slot, set up correspondance between game id, // home team, and away team // IIntTupleSet gha = cp.IntTable(3); int[] tuple = new int[3]; for (int i = 0; i < n; i++) { tuple[0] = i; for (int j = 0; j < n; j++) { if (i != j) { tuple[1] = j; tuple[2] = Game(i, j, n); cp.AddTuple(gha, tuple); } } } for (int i = 0; i < nbWeeks; i++) { for (int j = 0; j < nbGamesPerWeek; j++) { IIntVar[] vars = cp.IntVarArray(3); vars[0] = home[i][j]; vars[1] = away[i][j]; vars[2] = games[i][j]; cp.Add(cp.AllowedAssignments(vars, gha)); } } // // All teams play each week // for (int i = 0; i < nbWeeks; i++) { IIntVar[] teamsThisWeek = cp.IntVarArray(n); for (int j = 0; j < nbGamesPerWeek; j++) { teamsThisWeek[j] = home[i][j]; teamsThisWeek[nbGamesPerWeek + j] = away[i][j]; } cp.Add(cp.AllDiff(teamsThisWeek)); } // // Dual representation: for each game id, the play slot is maintained // IIntVar[] weekOfGame = cp.IntVarArray(nbGames, 0, nbWeeks - 1); IIntVar[] allGames = cp.IntVarArray(nbGames); IIntVar[] allSlots = cp.IntVarArray(nbGames, 0, nbGames - 1); for (int i = 0; i < nbWeeks; i++) { for (int j = 0; j < nbGamesPerWeek; j++) { allGames[i * nbGamesPerWeek + j] = games[i][j]; } } cp.Add(cp.Inverse(allGames, allSlots)); for (int i = 0; i < nbGames; i++) { cp.Add(cp.Eq(weekOfGame[i], cp.Div(allSlots[i], nbGamesPerWeek))); } // // Two half schedules. Cannot play the same pair twice in the same half. // Plus, impose a minimum number of weeks between two games involving // the same teams (up to six weeks) // int mid = nbWeeks / 2; int overlap = 0; if (n >= 6) { overlap = min(n / 2, 6); } for (int i = 0; i < n; i++) { for (int j = i + 1; j < n; j++) { int g1 = Game(i, j, n); int g2 = Game(j, i, n); cp.Add(cp.Equiv(cp.Ge(weekOfGame[g1], mid), cp.Lt(weekOfGame[g2], mid))); // Six week difference... if (overlap != 0) { cp.Add(cp.Ge(cp.Abs(cp.Diff(weekOfGame[g1], weekOfGame[g2])), overlap)); } } } // // Can't have three homes or three aways in a row. // IIntVar[][] playHome = new IIntVar[n][]; for (int i = 0; i < n; i++) { playHome[i] = cp.IntVarArray(nbWeeks, 0, 1); for (int j = 0; j < nbWeeks; j++) { cp.Add(cp.Eq(playHome[i][j], cp.Count(home[j], i))); } for (int j = 0; j < nbWeeks - 3; j++) { IIntVar[] window = cp.IntVarArray(3); for (int k = j; k < j + 3; k++) { window[k - j] = playHome[i][k]; } IIntExpr windowSum = cp.Sum(window); cp.Add(cp.Le(1, windowSum)); cp.Add(cp.Le(windowSum, 2)); } } // // If we start the season home, we finish away and vice versa. // for (int i = 0; i < n; i++) { cp.Add(cp.Neq(playHome[i][0], playHome[i][nbWeeks - 1])); } // // Objective: minimize the number of `breaks'. A break is // two consecutive home or away matches for a // particular team IIntVar[] teamBreaks = cp.IntVarArray(n, 0, nbWeeks / 2); for (int i = 0; i < n; i++) { IIntExpr nbreaks = cp.Constant(0); for (int j = 1; j < nbWeeks; j++) { nbreaks = cp.Sum(nbreaks, cp.IntExpr(cp.Eq(playHome[i][j - 1], playHome[i][j]))); } cp.Add(cp.Eq(teamBreaks[i], nbreaks)); } IIntVar breaks = cp.IntVar(n - 2, n * (nbWeeks / 2)); cp.Add(cp.Eq(breaks, cp.Sum(teamBreaks))); cp.Add(cp.Minimize(breaks)); // // Catalyzing constraints // // Each team plays home the same number of times as away for (int i = 0; i < n; i++) { cp.Add(cp.Eq(cp.Sum(playHome[i]), nbWeeks / 2)); } // Breaks must be even for each team for (int i = 0; i < n; i++) { cp.Add(cp.Eq(cp.Modulo(teamBreaks[i], 2), 0)); } // // Symmetry breaking constraints // // Teams are interchangeable. Fix first week. // Also breaks reflection symmetry of the whole schedule. for (int i = 0; i < nbGamesPerWeek; i++) { cp.Add(cp.Eq(home[0][i], i * 2)); cp.Add(cp.Eq(away[0][i], i * 2 + 1)); } // Order of games in each week is arbitrary. // Break symmetry by forcing an order. for (int i = 0; i < nbWeeks; i++) { for (int j = 1; j < nbGamesPerWeek; j++) { cp.Add(cp.Gt(games[i][j], games[i][j - 1])); } } cp.SetParameter(CP.DoubleParam.TimeLimit, 20); cp.SetParameter(CP.IntParam.LogPeriod, 10000); IVarSelector varSel = cp.SelectSmallest(cp.VarIndex(allGames));; IValueSelector valSel = cp.SelectRandomValue(); ISearchPhase phase = cp.SearchPhase(allGames, cp.IntVarChooser(varSel), cp.IntValueChooser(valSel)); cp.SetSearchPhases(phase); cp.StartNewSearch(); while (cp.Next()) { Console.WriteLine("Solution at {0}", cp.GetValue(breaks)); } cp.EndSearch(); } catch (ILOG.Concert.Exception e) { Console.WriteLine("Error {0}", e); } }
public static IIntExpr MakeScenarioSubmodel(CP cp, int nbJobs, int nbMachines, int[][] machines, int[][] durations, IIntervalSequenceVar[] sequences) { List<IIntervalVar>[] machinesOps = new List<IIntervalVar>[nbMachines]; String name; int i,j; for (j = 0; j < nbMachines; j++) machinesOps[j] = new List<IIntervalVar>(); IIntExpr[] ends = new IIntExpr[nbJobs]; for (i = 0; i < nbJobs; i++) { IIntervalVar prec = cp.IntervalVar(); for (j = 0; j < nbMachines; j++) { name = "J" + i + "_O" + j; IIntervalVar ti = cp.IntervalVar(durations[i][j], name); machinesOps[machines[i][j]].Add(ti); if (j > 0) cp.Add(cp.EndBeforeStart(prec, ti)); prec = ti; } ends[i] = cp.EndOf(prec); } for (j = 0; j < nbMachines; j++) { name = "M" + j; sequences[j] = cp.IntervalSequenceVar(machinesOps[j].ToArray(), name); cp.Add(cp.NoOverlap(sequences[j])); } return cp.Max(ends); }