Algorithm Alley by Girish Keshav Palshikar Listing One // max. no. of neighboring states for a given state #define MAX_NEIGHBOUR 100 // external functions assumed (specific to each problem domain) extern double Cost(STATE *pS); // returns the cost of given state extern int Solution(STATE *pS); // 1 if given state is a solution; else 0 // generate neighbor states of given state; return no. of neighbor states extern int GetNeighbours(STATE *pS, STATE Next[MAX_NEIGHBOUR]); // hopefully find and return the lowest cost state // STATE is a problem-specific representation of the structure of a state // pS0 and pS are pointers to given initial state and low cost state found. int HillClimbing(STATE *pS0, STATE *pS) { STATE Next[MAX_NEIGHBOUR]; int i, n, index; double c0, c, c1; if ( Solution(pS0) ) // found { CopyState(pS,pS0); return(1); } CopyState(pS, pS0); // initialize c0 = Cost(pS0); // cost of initial state while ( (n = GetNeighbours(pS,Next)) > 0 ) // get neighbours of s { index = 0; // index (in Next) of lowest cost neighbour c = Cost(&Next[0]); for(i = 0; i < n; i++) // do for each neighbour state { if ( Solution(&Next[i]) ) // found { CopyState(pS,&Next[i]); return(1); } if ( (c1 = Cost(&Next[i])) < c ) { index = i; c = c1; } } // end for if ( c < c0 ) // found a lower cost neighbour { CopyState(pS, &Next[index]); c0 = c; } else // reached local maximum break; } // end while return(0); // global solution not found; S contains low cost state found } Listing Two /* Module: Simulated Annealing * Programmer: Girish Keshav Palshikar */ #include #include #include #include "simann.h" #include "sim_app.h" // problem-specific information needed by SA // function prototypes int NextTemp(TEMP *pt); BOOL Boltzmann(ENERGY e1, ENERGY e2, TEMP t); BOOL CoolEnough(TEMP t); // problem-specific functions assumed extern BOOL NeighbourState(STATE *pS, STATE *pNew); extern BOOL IsSolution(STATE *pS); // TRUE if state is an acceptable solution extern ENERGY Energy(STATE *pS); // compute & return cost/energy of state extern int CopyState(STATE *pDest, STATE *pSrc); // s0 is the initial state and t0 is the initial temperature // Limit is the no. of attempts to explore neighbourhoods at a given temp. BOOL SimAnneal(STATE *pInit, TEMP t0, int Limit, STATE *pDest) { STATE s; // current state TEMP t; // current temp. ENERGY e, e_new; // energy of current and new state BOOL success = FALSE; int i; CopyState(&s, pInit); // make current state = initial state e = Energy(&s); // compute current energy t = t0; CopyState(pDest, pInit); // copy initial state into pDest while ( !CoolEnough(t) ) { if ( IsSolution(&s) ) // done { success = TRUE; break; } for ( i = 0, success = FALSE; i < Limit; i++ ) { if ( !NeighbourState(&s, pDest) ) // generate new state in pDest break; // no more states in the neighbourhood if ( IsSolution(pDest) ) // done { success = TRUE; break; } e_new = Energy(pDest); printf("temp = %lf i = %d e = %lf e_new = %lf\n", t, i, e, e_new); if ( Boltzmann(e, e_new, t) ) // make pDest new current state? { CopyState(&s, pDest); e = e_new; } } // end for NextTemp(&t); // get the next lower temperature } // end while CopyState(pDest, &s); // copy last state into pDest return(success); } BOOL Boltzmann(ENERGY e1, ENERGY e2, TEMP t) { double x; if ( e2 < e1 ) return(TRUE); x = exp( (-(e2 - e1)) / t ); if ( x <= 1.0 && rand() < x ) return(TRUE); if ( rand() < (x - floor(x)) ) // x > 1, so check decimal fraction of x return(TRUE); return(FALSE); } // implement cooling schedule; return the next lower temp int NextTemp(TEMP *pt) { TEMP t1 = (*pt); (*pt) = t1 * TEMP_FACTOR; return(0); } // true if given temp < a fixed threshold; stop condition for SA BOOL CoolEnough(TEMP t) { if ( t < MIN_TEMP ) return(TRUE); return(FALSE); } Listing Three /* Module: Simulated Annealing * File: simann.h * Programmer: Girish Keshav Palshikar */ #ifndef SIMANN_H #define SIMANN_H typedef double TEMP; typedef double ENERGY; typedef enum { FALSE = 0, TRUE = 1 } BOOL; #define MAX_TEMP 5000.0 #define MIN_TEMP 1.0 #define BOLTZMANN_CONSTANT 1.0 #define TEMP_FACTOR 0.5 #endif 3