Sample program of Differential Evolution

// Sample source code of Differential Evolution
//
// Coded by T.Takahama

#include <stdio.h>
#include <stdlib.h>

/* Random number generator in [0, 1] */
#define Rand()		((double)rand()/RAND_MAX)
/* Random integer generator in [0, n-1] */
#define RandInt(n)	((int)(rand()/(RAND_MAX+1.0)*(n)))

/* Structure of an individual */
typedef struct {
	double *x;	/* genes */
	double f;	/* fitness value */
} IndividualRec, *Individual;

/*
	Parameters for DE
*/

/* Number of individuals */
#define Nindividuals	50
/* Maximum number of iterations */
#define T_MAX		1000
/* parameters for crossover */
#define CR		0.9
#define F		0.7

/*
	Definitions for a problem
*/

/* Number of variables: problem dependent */
#define Nvariables	5
#define LOWER		-5.12
#define UPPER		5.12

/* Objective function for minimization: problem dependent */
#define better(y1, y2)	(y1<y2)

/* The following is the function of Sum_i (x_i-1)^2 */
void Evaluate(Individual P)
{
	int i;

	P->f=0.0;
	for(i=0; i<Nvariables; i++)
		P->f+=(P->x[i]-1)*(P->x[i]-1);
}

/* Initialization of individuals: problem dependent */
/* The function returns the index of the best individual */
int Initialize(Individual P, int n)
{
	int i, j;
	int best;		/* the index of the best individual */

	best=0;
	for(i=0; i<n; i++) {
		/* problem dependent */
		for(j=0; j<Nvariables; j++)
			P[i].x[j]=LOWER+Rand()*(UPPER-LOWER);
		Evaluate(&P[i]);
		if(better(P[i].f, P[best].f)) best=i;
	}
	return best;
}

/*
	Definitions for DE
*/

/* allocate new data structures */
#define New(type, n, msg)	(type *)NewCell(sizeof(type), n, msg)

void *NewCell(int size, int n, char *msg)
{
	void *new;

	if((new=malloc(size*n))==NULL) {
		fprintf(stderr, "Cannot allocate memory for %d %s\n", n, msg);
		exit(1);
	}
	return new;
}

/* allocate "n" new individuals */
Individual NewIndividuals(int n)
{
	int i;
	Individual P;

	P=New(IndividualRec, n, "individuals");
	for(i=0; i<n; i++) {
		P[i].x=New(double, Nvariables, "x");
	}
	return P;
}

/* Copy an individual */
void CopyIndividual(Individual dest, Individual src)
{
	int j;

	for(j=0; j<Nvariables; j++)
		dest->x[j]=src->x[j];
	dest->f=src->f;
}

/* Print an individual */
void Print(Individual P)
{
	int j;

	for(j=0; j<Nvariables; j++)
		printf("%f ", P->x[j]);
	printf(" = %g\n", P->f);
}

/* crossover & mutation */
void DEoperation(Individual New, Individual Old, int i)
{
	int p1, p2, p3, j, l;

	do {
		p1=RandInt(Nindividuals);
	} while(p1==i);
	do {
		p2=RandInt(Nindividuals);
	} while(p2==i || p2==p1);
	do {
		p3=RandInt(Nindividuals);
	} while(p3==i || p3==p1 || p3==p2);
#ifdef BINARY
/* DE/rand/1/bin */
	j=RandInt(Nvariables);
	for(l=0; l<Nvariables; l++) {
		if(l==0 || Rand()<CR)
			New[i].x[j]=Old[p1].x[j]+F*(Old[p2].x[j]-Old[p3].x[j]);
		else
			New[i].x[j]=Old[i].x[j];
		j=(j+1)%Nvariables;
	}
#else
/* DE/rand/1/exp */
	CopyIndividual(&New[i], &Old[i]);
	j=RandInt(Nvariables);
	l=0;
	do {
		New[i].x[j]=Old[p1].x[j]+F*(Old[p2].x[j]-Old[p3].x[j]);
		j=(j+1)%Nvariables;
		l++;
	}
	while(l<Nvariables && Rand()<CR);
#endif
}

/* Differential Evolution */
main()
{
	int t, i;
	Individual Old, New, Temp;
	Individual Best;
	int best;

	Old=NewIndividuals(Nindividuals);
	New=NewIndividuals(Nindividuals);
	Best=NewIndividuals(1);
	best=Initialize(Old, Nindividuals);
	CopyIndividual(Best, &Old[best]);
	for(t=1; t<=T_MAX; t++) {
		for(i=0; i<Nindividuals; i++) {
			DEoperation(New, Old, i);
			Evaluate(&New[i]);
			if(better(Old[i].f, New[i].f)) /* new is worse than old */
				CopyIndividual(&New[i], &Old[i]);
			else if(better(New[i].f, Best->f))
				CopyIndividual(Best, &New[i]);
		}
		Temp=Old; Old=New; New=Temp;
		printf("%4d: ", t); Print(Best);
	}
}