#include #include #include "Exam28.h" // 5 December 2002 // corrected a bug in Dispatcher encoding of JSP: time windows for a visit! //Keep it in case. This version is //okay for working with VRPs etc up until pure JSPs (inclusive). //In subsequent versions we will be updating //the VRP opt criterion to work with pure JSPs //and a VRP-like criterion (needed for symmetric experiments //with swapped optim criteria in the area of pure JSPs. ILOSTLBEGIN const IloInt MaxSize = 400; const IloNum VehicleUsagePenalty = 0.0; const IloInt StartUserTime = 10000; IloInt MoveLimit; IloBool TypeOfMethod;//0-LS,1-GLS; IloInt nbOfJobs; IloNum TimeLimit; IloInt nbOfVisits; IloInt nbOfTrucks; IloInt capacity; IloInt UserTime; IloInt Step; IloBool firstAccept; IloNum Speed; IloBool Redo; //char TypeOfProblem[3]; bool activateAltVRPCriterion = false; IloNum PenaltyFactor; IloInt TabuTenure; IloInt DiffNb,SameNb, PrecedenceNb; IloBool VRPFlag = IloFalse; IloNum openTime; IloNum closeTime; IloNum** DistMatr; IloNum** VrpData; IloNum* durations; IloInt* resourceNumbers; IloInt* DiffArr; IloInt* SameArr; IloInt* PrecedenceArr; IloVisit ChooseCheapestVisit(IloDispatcher dispatcher, IloVehicle vehicle, IloVisit visit) { IloInt vehIndex = dispatcher.getIndex(vehicle); IlcIntVar nextVar = dispatcher.getNextVar(visit); IloVisit bestVisit; IloNum bestCost = IloInfinity; for (IlcIntExpIterator iter(nextVar); iter.ok();++iter) { IloVisit v = dispatcher.getVisit(*iter); IloNum cost = dispatcher.getCost(visit,v,vehicle); IlcIntVar vehicleVar = dispatcher.getVehicleVar(v); if (cost < bestCost && !v.isFirstVisit() && !v.isLastVisit() && vehicleVar.isInDomain(vehIndex)) { bestVisit = v; bestCost = cost; break; } } return bestVisit; } ILCGOAL3 (AddArcTestGoal, IloVisit&, visit1, IloVisit&, visit2, IloVehicle&, vehicle) { IloSolver solver = getSolver(); IloDispatcher dispatcher(solver); dispatcher.setNext(visit1,visit2); return IloLimitSearch(solver, IloGenerateRoute(solver,vehicle), IloFailLimit(solver,100)); } ILCGOAL1(VehicleAdditionGenerate,IloVehicle,vehicle) { IloSolver solver = getSolver(); IloDispatcher dispatcher(solver); IloVisit visit1 = vehicle.getFirstVisit(); IloVisit visit2 = ChooseCheapestVisit(dispatcher, vehicle, visit1); IlcGoal testGoal = AddArcTestGoal(solver,visit1, visit2, vehicle); while (visit2.getImpl() != 0) { if (solver.solve(testGoal,IloTrue)) { dispatcher.setNext(visit1,visit2); visit1 = visit2; } else { solver.add(dispatcher.getNextVar(visit1) != dispatcher.getIndex(visit2)); } visit2 = ChooseCheapestVisit(dispatcher,vehicle,visit1); } solver.solve(IloGenerateRoute(solver,vehicle)); return 0; } IloVehicle ChooseCheapestVehicle(IloDispatcher dispatcher, IloDimension dim) { IloEnv env = dispatcher.getEnv(); IloVehicle bestVehicle; IloNum bestCostCoef = IloInfinity; for (IloIterator vehIter(env);vehIter.ok();++vehIter) { IloVehicle vehicle = *vehIter; IloNum coef = vehicle.getCost(dim); if (coef < bestCostCoef && !dispatcher.isRouteComplete(vehicle)) { bestVehicle = vehicle; bestCostCoef = coef; break; } } return bestVehicle; } ILCGOAL0 (UnperformVisits) { IloSolver solver = getSolver(); IloDispatcher dispatcher(solver); IloEnv env = dispatcher.getEnv(); for (IloIterator visIter(env);visIter.ok();++visIter) { IloVisit visit = *visIter; if (!dispatcher.getVehicleVar(visit).isBound()) solver.add(dispatcher.unperformed(visit)); } return 0; } ILCGOAL1(AdditionGenerate, IloDimension, dim) { IloSolver solver = getSolver(); IloDispatcher dispatcher(solver); dispatcher.setFilterLevel(IlcBasic); IloVehicle vehicle = ChooseCheapestVehicle(dispatcher,dim); if (vehicle.getImpl() == 0) return UnperformVisits(solver); return IlcAnd(VehicleAdditionGenerate(solver,vehicle), this); } ILOCPGOALWRAPPER1(MyAdditionGenerate,solver,IloDimension,dim) { return AdditionGenerate(solver,dim); } inline int myRound(double x) { return (int) (x+0.5); } class MyDistanceI: public IloDistanceI { public: MyDistanceI(IloEnv env); virtual IloNum computeDistance (IloNode node1, IloNode node2, IloVehicle vehicle) const; IloEnv _env; IloNum** _distanceMatrix; void getDistanceMatrix(IloNum** DistanceMatrixExternal); }; MyDistanceI::MyDistanceI(IloEnv env) : IloDistanceI(env) { _env = env; } void MyDistanceI::getDistanceMatrix(IloNum** DistanceMatrixExternal){ int i,j; _distanceMatrix = new IloNum* [nbOfVisits+1]; for (i=0;imakespan) { makespan = solver.getFloatVar(DepotTimeArr[i]).getMin(); } } } void Info(IloDispatcher dispatcher, char*& problem, ofstream& fout, ofstream& fout1, ofstream& fout2, IloDimension time, IloNumVarArray DepotTimeArr, IloInt nbOfTrucks, IloInt depotDropTime, IloBool statisticsFlag) { IloSolver solver = dispatcher.getSolver(); IloEnv env = solver.getEnv(); IloInt makespan; GetMakespan(solver,DepotTimeArr,makespan); fout<< "===============" << endl << "Makespan : "< wi(env); wi.ok(); ++wi) { IloVehicle vehicle = *wi; if (dispatcher.getRouteSize(vehicle) != 0) { fout2< wi(env); wi.ok(); ++wi) { IloVehicle vehicle = *wi; if (dispatcher.getRouteSize(vehicle) != 0) { fout1<= tStart + 600 && time <= tStart + 1200 && !isIntermediateOutputPoint1Reached) { isIntermediateOutputPoint1Reached = true; fout1 << dispatcher.getNbOfVehiclesUsed()<<" "<= tStart + 1200 && time <= tStart + 1800 && !isIntermediateOutputPoint2Reached) { isIntermediateOutputPoint2Reached = true; fout1 << dispatcher.getNbOfVehiclesUsed()<<" "<= tStart + 1800 && time <= tStart + 2400 && !isIntermediateOutputPoint3Reached) { isIntermediateOutputPoint3Reached = true; fout1 << dispatcher.getNbOfVehiclesUsed()<<" "<= tStart + 2400 && time <= tStart + 3000 && !isIntermediateOutputPoint4Reached) { isIntermediateOutputPoint4Reached = true; fout1 << dispatcher.getNbOfVehiclesUsed()<<" "<TimeLimit) { KILL_PROC_BY_NAME(nameOfProcess); } return 0; } int main(int argc, char* argv[]) { IloEnv env; try { /////////////////////////////////////////////////////////////////////// // // Reading in data // /////////////////////////////////////////////////////////////////////// int i,j; FILE* infile; ofstream outfile, outfile1, outfile2; TimeLimit = 0; IloBool StartFlag; char * problem; char * output; char * output1; char * output2; if (argc == 9) { problem = argv[1]; output = argv[2]; output1 = argv[3]; output2 = argv[4]; PenaltyFactor = atof(argv[5]); TimeLimit=atoi(argv[6]); StartFlag = atoi(argv[7]); Redo = (IloBool) atoi(argv[8]); } else { env.out() <<"Usage: .exe \n"; env.out() <<" \n"; env.out() <<" GLSPenalty TimeLimitValue StartFlag Redo\n"; return 0; } if ((infile=fopen(argv[1],"r"))==NULL) { cout<<"Couldn't open "<= openTime); mdl.add(first.getDelayVar(time) == depotDropTime); //may be non-zero (after transformation) IloVisit last(depot, "Depot"); mdl.add(last.getCumulVar(time) <= closeTime-depotDropTime); //!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! mdl.add(last.getDelayVar(time) == depotDropTime); //may be non-zero (after transformation) char name[16]; sprintf(name, "%d", j+1); IloVehicle vehicle(first, last, name); if (!activateAltVRPCriterion) { vehicle.setCost(length, 1.0); } else { vehicle.setCost(time, 1.0); } //setting a fixed cost on a vehicle, thus it will tend to minimise the //number of used vehicles; //vehicle.setCost(VehicleUsagePenalty); fscanf(infile,"%d",&id); fscanf(infile,"%Ld",&capacity); vehicle.setCapacity(weight, capacity); vehicles[j] = vehicle; mdl.add(vehicle); } IloExpr expr(env); char buf1[30]; for (i=0;i<3;i++) { if (i==0) { strcpy(buf1,"Diff"); ReadInSideConstraints((char *) buf1, DiffArr,DiffNb,infile,outfile); } if (i==1) { strcpy(buf1,"Same"); ReadInSideConstraints((char *) buf1, SameArr,SameNb,infile,outfile); } if (i==2) { strcpy(buf1,"Precedence"); ReadInSideConstraints((char *) buf1, PrecedenceArr,PrecedenceNb,infile,outfile); } } ImposeVehicleVisitConstraints(mdl,time,nbOfTrucks,arrayOfAllowedVehicles,vehicles, visits,outfile); fclose(infile); IloSolver solver(mdl); IloDispatcher dispatcher(solver); IloRoutingSolution solution(mdl); //////////////////////////////////////////////// // // constructing the 1st solution with savings // //////////////////////////////////////////////// IloGoal instantiateCost = IloDichotomize(env, dispatcher.getCostVar(), IloFalse); IloGoal restoreSolution = IloRestoreSolution(env, solution); IloGoal goal = IloSavingsGenerate(env) && instantiateCost; // IloGoal goal = IloInsertionGenerate(env) && instantiateCost; // IloGoal goal = IloDispatcherGenerate(env) && instantiateCost; clock_t tStart = clock()/CLK_TCK, clocktime = tStart; IloGoal goalAdd = MyAdditionGenerate(env,length) && instantiateCost; if (!Redo) { //by default we generate a first solution by savings; cout<<"TimeLimit = "<0) { improveWithGLS_TimeLimitVersion(dispatcher,solution,nhood,outfile, outfile1); } /////////////////////////////////////////// // // outputting the improved solution // /////////////////////////////////////////// outfile2.open(output2, ios::out); Info(dispatcher,outfile,outfile2,problem); outfile2.close(); trueCost = dispatcher.getTotalCost() - dispatcher.getNbOfVehiclesUsed()*VehicleUsagePenalty; cout<<"Last Solution: "<= openTime); mdl.add(first.getDelayVar(time) == depotDropTime); //may be non-zero (after transformation) mdl.add(first.getTransitVar(tardiness) == 0); IloVisit last(depot, "Depot"); IloNumVar tard(env,0,IloInfinity,ILOINT); mdl.add(tard >= last.getCumulVar(time) - softDeadline); mdl.add(last.getTransitVar(tardiness) == tard); mdl.add(DepotTimeArr[j]==last.getCumulVar(time)); char name[16]; sprintf(name, "%d", j+1); IloVehicle vehicle(first, last, name); vehicles[j]=vehicle; vehicle.setCost(tardiness, 1.0); // vehicle.setCost(length,0.001); fscanf(infile,"%d",&id); fscanf(infile,"%Ld",&capacity); // outfile<= minTime); ////////////////////////////////////////// //outfile<<"i = "< quit if (!solver.solve(IloLimitSearch(env,goal,IloTimeLimit(env,TimeLimit)))) { solver.out() << "Couldn't generate first solution! Try and change your deadline value"; outfile2<<"0"<