I came across this code of firefly algorithm and need to use it in my major. If any of you could explain the working of the functions, it would be of great help to me. Thanks in advance.

``````#include<iostream>
#include<stdio.h>
#include<stdlib.h>
#include<math.h>
#include<time.h>
#include<string.h>
#include<memory.h>

#defineDUMP 1
#defineMAX_FFA  1000
#defineMAX_D    1000

usingnamespacestd;

int D = 1000;           // dimension of the problem
int n = 20;         // number of fireflies
intMaxGeneration;       // number of iterations
intNumEval;         // number of evaluations
int Index[MAX_FFA];     // sort of fireflies according to fitness values

doubleffa[MAX_FFA][MAX_D];  // firefly agents
doubleffa_tmp[MAX_FFA][MAX_D]; // intermediate population
double f[MAX_FFA];      // fitness values
double I[MAX_FFA];      // light intensity
doublenbest[MAX_FFA];          // the best solution found so far
doublelb[MAX_D];        // upper bound
doubleub[MAX_D];        // lower bound

double alpha = 0.5;     // alpha parameter
doublebetamin = 0.2;           // beta parameter
doublegama = 1.0;       // gamma parameter

doublefbest;            // the best objective function

typedefdouble (*FunctionCallback)(double sol[MAX_D]);

/*benchmark functions */
doublecost(double sol[MAX_D]);
doublesphere(double sol[MAX_D]);

/*Write your own objective function */
FunctionCallback function = &cost;

// optionally recalculate the new alpha value
doublealpha_new(double alpha, intNGen)
{
double delta;           // delta parameter
delta = 1.0-pow((pow(10.0, -4.0)/0.9), 1.0/(double) NGen);
return (1-delta)*alpha;
}

// initialize the firefly population
voidinit_ffa()
{
inti, j;
double r;

// initialize upper and lower bounds
for (i=0;i<D;i++)
{
lb[i] = 0.0;
ub[i] = 2.0;
}

for (i=0;i<n;i++)
{
for (j=0;j<D;j++)
{
r = (   (double)rand() / ((double)(RAND_MAX)+(double)(1)) );
ffa[i][j]=r*(ub[i]-lb[i])+lb[i];
}
f[i] = 1.0;         // initialize attractiveness
I[i] = f[i];
}
}

// implementation of bubble sort
voidsort_ffa()
{
inti, j;

// initialization of indexes
for(i=0;i<n;i++)
Index[i] = i;

// Bubble sort
for(i=0;i<n-1;i++)
{
for(j=i+1;j<n;j++)
{
if(I[i] > I[j])
{
double z = I[i];    // exchange attractiveness
I[i] = I[j];
I[j] = z;
z = f[i];           // exchange fitness
f[i] = f[j];
f[j] = z;
int k = Index[i];   // exchange indexes
Index[i] = Index[j];
Index[j] = k;
}
}
}
}

// replace the old population according the new Index values
voidreplace_ffa()
{
inti, j;

// copy original population to temporary area
for(i=0;i<n;i++)
{
for(j=0;j<D;j++)
{
ffa_tmp[i][j] = ffa[i][j];
}
}

// generational selection in sense of EA
for(i=0;i<n;i++)
{
for(j=0;j<D;j++)
{
ffa[i][j] = ffa_tmp[Index[i]][j];
}
}
}

voidfindlimits(int k)
{
inti;

for(i=0;i<D;i++)
{
if(ffa[k][i] <lb[i])
ffa[k][i] = lb[i];
if(ffa[k][i] >ub[i])
ffa[k][i] = ub[i];
}
}

voidmove_ffa()
{
inti, j, k;
double scale;
double r, beta;

for(i=0;i<n;i++)
{
scale = abs(ub[i]-lb[i]);
for(j=0;j<n;j++)
{
r = 0.0;
for(k=0;k<D;k++)
{
r += (ffa[i][k]-ffa[j][k])*(ffa[i][k]-ffa[j][k]);
}
r = sqrt(r);
if(I[i] > I[j]) // brighter and more attractive
{
double beta0 = 1.0;
beta = (beta0-betamin)*exp(-gama*pow(r, 2.0))+betamin;
for(k=0;k<D;k++)
{
r = (   (double)rand() / ((double)(RAND_MAX)+(double)(1)) );
doubletmpf = alpha*(r-0.5)*scale;
ffa[i][k] = ffa[i][k]*(1.0-beta)+ffa_tmp[j][k]*beta+tmpf;
}
}
}
findlimits(i);
}
}

voiddump_ffa(int gen)
{
cout<<"Dump at gen= "<< gen <<" best= "<<fbest<<endl;
}

/* display syntax messages */
voidhelp()
{
cout<<"Syntax:"<<endl;
cout<<"  Firefly [-h|-?] [-l] [-p] [-c] [-k] [-s] [-t]"<<endl;
cout<<"    Parameters: -h|-? = command syntax"<<endl;
cout<<"                -n = number of fireflies"<<endl;
cout<<"                -d = problem dimension"<<endl;
cout<<"                -g = number of generations"<<endl;
cout<<"                -a = alpha parameter"<<endl;
cout<<"                -b = beta0 parameter"<<endl;
cout<<"                -c = gamma parameter"<<endl;
}

intmain(intargc, char* argv[])
{
inti;
int t = 1;      // generation  counter

// interactive parameters handling
for(inti=1;i<argc;i++)
{
if((strncmp(argv[i], "-h", 2) == 0) || (strncmp(argv[i], "-?", 2) == 0))
{
help();
return0;
}
elseif(strncmp(argv[i], "-n", 2) == 0)         // number of fireflies
{
n = atoi(&argv[i][2]);
}
elseif(strncmp(argv[i], "-d", 2) == 0)      // problem dimension
{
D = atoi(&argv[i][2]);
}
elseif(strncmp(argv[i], "-g", 2) == 0)      // number of generations
{
MaxGeneration = atoi(&argv[i][2]);
}
elseif(strncmp(argv[i], "-a", 2) == 0)      // alpha parameter
{
alpha = atof(&argv[i][2]);
}
elseif(strncmp(argv[i], "-b", 2) == 0)      // beta parameter
{
betamin = atof(&argv[i][2]);
}
elseif(strncmp(argv[i], "-c", 2) == 0)      // gamma parameter
{
gama = atof(&argv[i][2]);
}
else
{
cerr<<"Fatal error: invalid parameter: "<<argv[i] <<endl;
return -1;
}
}

// firefly algorithm optimization loop
// determine the starting point of random generator
srand(1);

// generating the initial locations of n fireflies
init_ffa();
#ifdef DUMP
dump_ffa(t);
#endif

while(t <= MaxGeneration)
{
// this line of reducing alpha is optional
alpha = alpha_new(alpha, MaxGeneration);

// evaluate new solutions
for(i=0;i<n;i++)
{
f[i] = function(ffa[i]);                        // obtain fitness of solution
I[i] = f[i];                    // initialize attractiveness
}

// ranking fireflies by their light intensity
sort_ffa();
// replace old population
replace_ffa();

// find the current best
for(i=0;i<D;i++)
nbest[i] = ffa[0][i];
fbest = I[0];

// move all fireflies to the better locations
move_ffa();
#ifdef DUMP
dump_ffa(t);
#endif
t++;
}

cout<<"End of optimization: fbest = "<<fbest<<endl;

return0;
}

// FF test function
doublecost(double* sol)
{
double sum = 0.0;

for(inti=0;i<D;i++)
sum += (sol[i]-1)*(sol[i]-1);

return sum;
}

doublesphere(double* sol) {
int j;
double top = 0;
for (j = 0; j < D; j++) {
top = top + sol[j] * sol[j];
}
}
``````

Well, to begin with, this is a C++ program, not a C program, and a poorly written one at that. The header formats indicate that it probably dates back to the late 1990s, when the then-new C++ standard was still being formalized - either that, or the programmer didn't understand the standard correctly. Several critical values are hard-coded in rather than parameterized, making the implementation brittle. The choice of bubblesort for the sorting algorithm is questionable at best, though with the small range it probably isn't very performance-critical. Finally, the code is pretty badly mangled, with the return types running into the function names and so forth, which means that without many fixes it wouldn't compile cleanly.

While it could fairly easily be re-written in C, you would be a lot better off writing a new implementation of the algorithm yourself. You would waste more time trying to fix this than you would starting over from scratch.

Thanks for the early reply Schol-R-LEA. Also I wanted to know, seeing a source code how can you tell if it's C or C++ when they are so similar ? I might get down votes on this weird question but I really want to know. It would be of great help if you could find me as easily understandable code for the same.

Well, the first thing to look at is the headers, both the names and the format of them. A C program will have headers in the form of `foo.h`, whereas in (modern) C++, the standard library headers will be `foo` without the extension. Now, this isn't a foolproof method, as there's a lot of pre-standard C++ code floating around, but if you see a header without an extension, it is presumably C++.

Also, in C++, the C library headers should be prepended with a `c`, making (for example) `<stdio.h>` into `<cstdio>`. Again, a lot of older code doesn't match this standard, and even some current code isn't correct in this regard, but if it is like that, it is definitely C++ rather than C.

Next, the headers used may be different; C++ adds a large number of new libraries which use the C++ facilities that don't exist in C. The main ones to look for are `<iostream>`, `<fstream>`, `<string>`, `<vector>` and `<algorithm>`.

Fourth, C++ has namespaces, but C does not; so, if you see a reference to `using namespace foo;`, it will be C++. The same goes for the scoping operator, `::`, which is used to indicate membership in either a class or a namespace.

Finally, if it uses `cin` and `cout` for input and output, it is going to be C++.

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.