Since we have two neighborhoods (one for swapping and one for relocating), we first create an abstract neighborhood class that inherits from IloNHoodI
and which contains the functionality that is common to both concrete neighborhoods. In this case, the MyNHoodI
class contains private and protected methods and data to manage the current solution, the set of possible moves, and the recalculation of the critical path and the previous pointers.
private:
void resetCache() { _cp->needsRecomputing(); }
protected:
IloSchedulerSolution _solution;
CriticalPath *_cp;
IloArray<LSMove*> _moves;
IloInt _nbMoves;
void realAddMove(LSMove *m) {
if (_nbMoves < _moves.getSize()) _moves[_nbMoves] = m;
else _moves.add(m);
_nbMoves++;
}
|
The virtual methods inherited from IloNHoodI
are also redefined. The start
method stores the new solution and recalculates the previous pointers.
void start(IloSolver, IloSolution soln) {
_solution = IloSchedulerSolution(soln);
_nbMoves = 0;
}
|
The define
and getSize
methods are identical to what was implemented in the previous chapter as the LSMove
subclass creates the delta solution and the size of the neighborhood is stored in the _nbMoves
data member.
IloSolution define(IloSolver solver, IloInt i) {
return (_moves[i])->createDelta(solver.getEnv(), _solution);
}
IloInt getSize(IloSolver) const { return _nbMoves; }
|
Finally, the set of methods for maintaining the state of the neighborhood make use of the resetCache
method described above.
void notify(IloSolver, IloInt) { resetCache(); }
void notifyOther (IloSolver, IloSolution) { resetCache(); }
void reset() { _solution = 0; _nbMoves = 0; resetCache(); }
|