IBM ILOG Scheduler User's Manual > Advanced Concepts > Using Transition Times and Costs > Complete Program

You can see the entire program tcost.cpp here or view it online in the standard distribution.

#include <ilsched/iloscheduler.h>
 
ILOSTLBEGIN
 
const IloInt Horizon = 10000;
const IloInt NumberOfJobs = 6;
const IloInt NumberOfResources = 6;
const IloInt NumberOfWorkers = 5;
const IloInt NumberOfTypes = 4;
 
IloInt ResourceNumbers [] = {2, 0, 1, 3, 5, 4,
                             1, 2, 4, 5, 0, 3,
                             2, 3, 5, 0, 1, 4,
                             1, 0, 2, 3, 4, 5,
                             2, 1, 4, 5, 0, 3,
                             1, 3, 5, 0, 4, 2};
 
IloInt ProcessingTimes [] = { 10,  30,  60,  70,  30,  60,
                        80,  50, 100, 100, 100,  40,
                        50,  40,  80,  90,  10,  70,
                        50,  50,  50,  30,  80,  90,
                        90,  30,  50,  40,  30,  10,
                        30,  30,  90, 100,  40,  10};
IloInt Types [] = { 0, 1, 2, 2, 0, 3,
                    1, 3, 2, 3, 3, 0,
                    2, 3, 1, 1, 0, 1,
                    2, 1, 0, 0, 1, 1,
                    3, 3, 2, 0, 1, 1,
                    3, 1, 2, 0, 3, 3};
IloInt TableDurations [] = { 0, 16, 14, 19,
                             12, 0, 8, 15,
                             15, 10, 0, 14,
                             16, 15, 17, 0};
 
IloInt SetupDurations [] = { 7, 0, 6, 7};
IloInt TableCapacities [] = { 0, 2, 3, 1,
                              2, 0, 4, 2,
                              3, 3, 0, 2,
                              1, 2, 3, 0};
 
IloInt SetupCapacities [] = { 2, 1, 1, 1};
///////////////////////////////////////////////////////////////////////////////
//
// PROBLEM DEFINITION
//
///////////////////////////////////////////////////////////////////////////////
/* CREATION OF A MACHINE WITH ITS TRANSITION TIME AND COSTS. */
IloUnaryResource
MakeMachine(IloModel model,
            IloTransitionParam durTransParam,
            IloTransitionParam enrTransParam,
            IloNumVar cost,
            const char* name) {
  IloUnaryResource machine(model.getEnv(), name);
  IloTransitionTime durTrans(machine, durTransParam);
  IloTransitionCost enrTrans(machine, enrTransParam);
  model.add(enrTrans.getCostSumVar() <= cost);
  return machine;
}
/* CREATION OF A TASK */
IloActivity
MakeTask(IloModel model,
         IloUnaryResource machine,
         IloInt type,
         IloInt procTime,
         IloInt setupTime,
         const char* name) {
  IloActivity task(model.getEnv(), procTime, type, name);
  task.setStartMin(setupTime);
  model.add(task.requires(machine));
  return task;
}
void
DefineProblem(IloModel model,
              IloInt horizon,
              IloInt numberOfJobs,
              IloInt numberOfResources,
              IloInt numberOfWorkers,
              IloInt numberOfTypes,
              IloInt* resourceNumbers,
              IloInt* processingTimes,
              IloInt* types,
              IloInt* tableDurations,
              IloInt* tableCapacities,
              IloInt* setupDurations,
              IloInt* setupCapacities,
              IloNumVar& makespan,
              IloNumVar& cost,
              IloTransitionParam& enrTransParam) {
  /* CREATE THE MAKESPAN VARIABLE. */
  IloEnv env = model.getEnv();
  makespan = IloNumVar(env, 0, horizon, IloNumVar::Int);
  /* CREATE THE COST VARIABLE. */
  IloInt maxEnergy = horizon * numberOfWorkers;
  cost = IloNumVar(env, 0, maxEnergy, IloNumVar::Int);
  char buffer[128];
  IloInt i, j, k;
  /* CREATE THE TRANSITION FUNCTIONS. */
  enrTransParam = IloTransitionParam(env, numberOfTypes, IloFalse);
  IloTransitionParam durTransParam(env, numberOfTypes, IloFalse);
  for(i = 0; i < numberOfTypes; ++i) {
    enrTransParam.setSetup(i, setupDurations[i] * setupCapacities[i]);
    IloInt index = i * numberOfTypes;
    for(j = 0 ; j < numberOfTypes; ++j) {
      durTransParam.setValue(i, j, tableDurations[index]);
      enrTransParam.setValue(i, j,
                       (tableDurations[index] * tableCapacities[index]));
      ++index;
    }
  }
  /* CREATE THE RESOURCES. */
  IloUnaryResource* resources =
    new (env) IloUnaryResource[numberOfResources];
  for (j = 0; j < numberOfResources; j++) {
    sprintf(buffer, "Machine%ld", j);
    resources[j] = MakeMachine(model, durTransParam, enrTransParam,
                               cost, buffer);
  }
  /* CREATE THE ACTIVITIES AND THE TEMPORAL CONSTRAINTS. */
  k = 0;
  for (i = 0; i < numberOfJobs; i++) {
    IloActivity previousTask;
    for (j = 0; j < numberOfResources; j++) {
      IloInt number = resourceNumbers[k];
      sprintf(buffer, "J%ldS%ldR%ldT%ld", i, j, number, types[k]);
      IloActivity task = MakeTask(model,
                                  resources[number],
                                  types[k],
                                  processingTimes[k],
                                  setupDurations[types[k]],
                                  buffer);
      if (j != OL)
        model.add(task.startsAfterEnd(previousTask));
      previousTask = task;
      k++;
    }
    model.add(previousTask.endsBefore(makespan));
  }
}
 
///////////////////////////////////////////////////////////////////////////////
//
// PRINTING OF SOLUTIONS
//
///////////////////////////////////////////////////////////////////////////////
 
void PrintSolution(IloSolver& solver) {
  IlcScheduler schedule(solver);
  for(IlcUnaryResourceIterator iter(schedule); iter.ok(); ++iter) {
    IlcUnaryResource machine = *iter;
    solver.out() << endl << "Machine : " << machine << endl;
    IloInt index = machine.getSetupVar().getValue();
    IloInt sink = machine.getTeardownIndex();
    while(index != sink) {
      IlcResourceConstraint task = machine.getSequenceRC(index);
      solver.out() << "\t" << task.getActivity() << endl;
      index = task.getNextVar().getValue();
    }
  }
}
 
int main() {
  try {    
    IloEnv env;
    IloModel model(env);
    IloNumVar makespan;
    IloNumVar cost;
    IloTransitionParam enrTransParam;
    DefineProblem(model,
                  Horizon,
                  NumberOfJobs,
                  NumberOfResources,
                  NumberOfWorkers,
                  NumberOfTypes,
                  ResourceNumbers,
                  ProcessingTimes,
                  Types,
                  TableDurations,
                  TableCapacities,
                  SetupDurations,
                  SetupCapacities,
                  makespan,
                  cost,
                  enrTransParam);
 
    IloSolver solver(model); 
    IloGoal goal = IloSequenceForward(env, cost, enrTransParam) &&
      IloInstantiate(env, makespan) &&
      IloSetTimesForward(env);
    
    if (solver.solve(goal)) {
      env.out() << " Solution with " << endl
                << "\tenergy : " << solver.getIntVar(cost) << endl
                << "\tmakespan : " << solver.getIntVar(makespan) << endl;
      PrintSolution(solver);
    }
    else
      solver.out() << "No Solution" << endl;
    env.end();
  } catch (IloException& exc) {
    cout << exc << endl;
  }
  return 0;
}
 
///////////////////////////////////////////////////////////////////////////////
//
// RESULTS
//
///////////////////////////////////////////////////////////////////////////////
 
/* tcost
  Solution with 
        energy : [168]
        makespan : [971]
 
  Machine : Machine4 [1]
        J4S2R4T2 [450 -- 50 --> 500]
        J1S2R4T2 [500 -- 100 --> 600]
        J3S4R4T1 [610 -- 80 --> 690]
        J2S5R4T1 [756 -- 70 --> 826]
        J5S4R4T3 [841 -- 40 --> 881]
        J0S5R4T3 [881 -- 60 --> 941]
 
  Machine : Machine5 [1]
        J5S2R5T2 [450 -- 90 --> 540]
        J2S2R5T1 [550 -- 80 --> 630]
        J0S4R5T0 [642 -- 30 --> 672]
        J4S3R5T0 [672 -- 40 --> 712]
        J1S3R5T3 [731 -- 100 --> 831]
        J3S5R5T1 [846 -- 90 --> 936]
 
  Machine : Machine3 [1]
        J2S1R3T3 [56 -- 40 --> 96]
        J0S3R3T2 [326 -- 70 --> 396]
        J5S1R3T1 [420 -- 30 --> 450]
        J3S3R3T0 [476 -- 30 --> 506]
        J4S5R3T1 [776 -- 10 --> 786]
        J1S5R3T0 [931 -- 40 --> 971]
 
  Machine : Machine1 [1]
        J1S0R1T1 [0 -- 80 --> 80]
        J0S2R1T2 [266 -- 60 --> 326]
        J3S0R1T2 [326 -- 50 --> 376]
        J5S0R1T3 [390 -- 30 --> 420]
        J4S1R1T3 [420 -- 30 --> 450]
        J2S4R1T0 [746 -- 10 --> 756]
 
  Machine : Machine0 [1]
        J0S1R0T1 [236 -- 30 --> 266]
        J3S1R0T1 [376 -- 50 --> 426]
        J5S3R0T0 [540 -- 100 --> 640]
        J2S3R0T1 [656 -- 90 --> 746]
        J4S4R0T1 [746 -- 30 --> 776]
        J1S4R0T3 [831 -- 100 --> 931]
 
  Machine : Machine2 [1]
        J2S0R2T2 [6 -- 50 --> 56]
        J4S0R2T3 [70 -- 90 --> 160]
        J1S1R2T3 [160 -- 50 --> 210]
        J0S0R2T0 [226 -- 10 --> 236]
        J3S2R2T0 [426 -- 50 --> 476]
        J5S5R2T3 [881 -- 10 --> 891]
*/