public static Fitness Constraint(Position x, int functCode, double epsConstr) { // ff[0] is defined in perf() // Variables specific to Coil compressing spring const double fmax = 1000.0; const double fp = 300; double Cf; double K; double sp; double lf; const double S = 189000.0; const double lmax = 14.0; const double spm = 6.0; const double sw = 1.25; const double G = 11500000; Fitness ff = new Fitness(Constants.DMax) {size = 1}; switch (functCode) { case 7: ff.size = 4; ff.f[1] = 0.0193 * x.x[2] - x.x[0]; ff.f[2] = 0.00954 * x.x[2] - x.x[1]; ff.f[3] = 750 * 1728 - Math.PI * x.x[2] * x.x[2] * (x.x[3] + (4.0 / 3) * x.x[2]); break; case 8: ff.size = 5; Cf = 1 + 0.75 * x.x[2] / (x.x[1] - x.x[2]) + 0.615 * x.x[2] / x.x[1]; K = 0.125 * G * Math.Pow(x.x[2], 4) / (x.x[0] * x.x[1] * x.x[1] * x.x[1]); sp = fp / K; lf = fmax / K + 1.05 * (x.x[0] + 2) * x.x[2]; ff.f[1] = 8 * Cf * fmax * x.x[1] / (Math.PI * x.x[2] * x.x[2] * x.x[2]) - S; ff.f[2] = lf - lmax; ff.f[3] = sp - spm; ff.f[4] = sw - (fmax - fp) / K; break; case 15: ff.size = 4; ff.f[1] = Math.Abs(x.x[0] * x.x[0] + x.x[1] * x.x[1] + x.x[2] * x.x[2] + x.x[3] * x.x[3] + x.x[4] * x.x[4] - 10) - epsConstr; // Constraint h1<=eps ff.f[2] = Math.Abs(x.x[1] * x.x[2] - 5 * x.x[3] * x.x[4]) - epsConstr; // Constraint h2<=eps; ff.f[3] = Math.Abs(Math.Pow(x.x[0], 3) + Math.Pow(x.x[1], 3) + 1) - epsConstr; // Constraint h3<=eps break; } return ff; }
public void memSave(Position P) { // Save a position // Is useful to generate a new particle in a promising area // The memPos list is a global variable M[Rank] = P; if (Size < M.Length - 1) { Size = Size + 1; Rank = Rank + 1; } else Rank = 0; // We re-use the memory cyclically }
public Position InitializeFar(IProblem pb) { // Try to find a new position that is "far" from all the memorised ones //Note: memPos is a global variable double[] coord = new double[Constants.MMax]; double[] interv = new double[2]; var xFar = new Position(Constants.DMax) { size = pb.SwarmSize.D }; for (int d = 0; d < pb.SwarmSize.D; d++) // For each dimension { for (int n = 0; n < this.Size; n++) coord[n] = this.M[n].x[d]; // All the coordinates on // this dimension Array.Sort(coord); // Sort them // by increasing order // Find the biggest intervall interv[0] = coord[0]; interv[1] = coord[1]; double delta = interv[1] - interv[0]; for (int n = 1; n < this.Size - 1; n++) { if (coord[n + 1] - coord[n] < delta) continue; interv[0] = coord[n]; interv[1] = coord[n + 1]; delta = interv[1] - interv[0]; } // Particular case, xMax if (pb.SwarmSize.max[d] - coord[this.Size - 1] > delta) { xFar.x[d] = pb.SwarmSize.max[d]; delta = pb.SwarmSize.max[d] - coord[this.Size - 1]; } // Particular case, xMin if (coord[0] - pb.SwarmSize.min[d] > delta) xFar.x[d] = pb.SwarmSize.min[d]; else xFar.x[d] = 0.5 * (interv[1] + interv[0]);// Take the middle } xFar = Position.Discrete(xFar, pb); xFar.f = pb.Evaluate(xFar); return xFar; }
public static double distanceL(Position x1, Position x2, double L) { // Distance between two positions // L = 2 => Euclidean int d; double n; n = 0; for (d = 0; d < x1.size; d++) n = n + Math.Pow(Math.Abs(x1.x[d] - x2.x[d]), L); n = Math.Pow(n, 1 / L); return n; }
public static Velocity Initialize(Position pos, SwarmSize swarmSize) { int d; var vel = new Velocity(Constants.DMax) {Size = pos.size}; // Half-diff 0.5*(alea-x) for (d = 0; d < vel.Size; d++) { vel.V[d] = (Alea.NextDouble(swarmSize.min[d], swarmSize.max[d]) - pos.x[d]) / 2; } return vel; }
public void Confinement( Problem.IProblem pb) { // Confinement and evaluation // Note: the two are together, for depending on the clamping option // there may be no evaluation at all // Set to the bounds, and v to zero for (int d = 0; d < pb.SwarmSize.D; d++) { if (x.x[d] < pb.SwarmSize.minS[d]) { x.x[d] = pb.SwarmSize.minS[d]; v.V[d] = 0; } if (x.x[d] > pb.SwarmSize.maxS[d]) { x.x[d] = pb.SwarmSize.maxS[d]; v.V[d] = 0; } } if (pb.Constraint != 0) { Fitness ff = Position.Constraint(x, pb); for (int i = 1; i < ff.size; i++) { if (ff.f[i] <= 0) continue; // If a constraint is not respected the velocity is decreased // and the position moved accordingly in th HOPE that the new position will be OK // (but we don't check it) for (int d = 0; d < pb.SwarmSize.D; d++) { v.V[d] = v.V[d]/2; x.x[d] = x.x[d] - v.V[d]; } } } x = Position.Quantis(x, pb.SwarmSize); // Evaluation x.f = pb.Evaluate(x); }
//================================================ //================================================= public static double lennard_jones(Position x) { /* This is for black-box optimisation. Therefore, we are not supposed to know that there are some symmetries. That is why the dimension of the problem is 3*nb_of_atoms, as it could be 3*nb_of_atoms-6 */ int d; int dim = 3; double dist; double f; int i, j; int nPoints = x.size / dim; Position x1 = new Position(Constants.DMax); Position x2 = new Position(Constants.DMax); double zz; x1.size = dim; x2.size = dim; f = 0; for (i = 0; i < nPoints - 1; i++) { for (d = 0; d < dim; d++) x1.x[d] = x.x[3 * i + d]; for (j = i + 1; j < nPoints; j++) { for (d = 0; d < dim; d++) x2.x[d] = x.x[3 * j + d]; dist = Tools.distanceL(x1, x2, 2); zz = Math.Pow(dist, -6); f = f + zz * (zz - 1); } } f = 4 * f; //printf("\n %f",f); return f; }
public XV() { x=new Position(Constants.DMax); v=new Velocity(Constants.DMax); }
//============================================================ static double potentiel(Position X, Archive list) { double dist; int n; double pot = 0; for (n = 0; n < list.Size; n++) { dist = Tools.distanceL(X, list.M[n], 2); if (dist > Constants.Zero) pot = pot + 1.0 / dist; else return Constants.Infinity; } return pot; }
// For Cutting stock // http://en.wikipedia.org/wiki/Cutting_stock_problem static void Main(string[] args) { Position bestBest = new Position(Constants.DMax); double convRateMean; int d; // Current dimension double error; // Current error double errorMean; // Average error double errorMin = Constants.Infinity; // Best result over all runs double[] errorMeanBest = new double[Constants.RMax]; double evalMean; // Mean number of evaluations int functionCode; int n; int nFailure; // Number of unsuccessful runs double logProgressMean = 0; Parameters parameters = new Parameters(); ProblemBase pb; int runMax; Result result; double successRate; double variance; // ----------------------------------------------- PROBLEM functionCode = 102; //TODO: Something seems wrong with Rosenbrockf6 /* (see problemDef, cellular_phone, cec2005pb for precise definitions) 0 Parabola (Sphere) 1 Griewank 2 Rosenbrock (Banana) 3 Rastrigin 4 Tripod (dimension 2) 5 Ackley 6 Center-bias test function 7 Pressure vessel (penalty method) 1007 " (confinement method) 8 Compression spring 1008 " (confinement method) 9 Gear train 10 Cellular phone 12 Schwefel 13 Cutting stock 14 convex small polygon, 4 edges, smallest perimeter 15 constrained problem g13 (penalty method) 16 constrained problem g3 (penalty method) 17 Lennard-Jones problem 1015 " (confinement method) CEC 2005 benchmark (no more than 30D. See cec2005data.c) 100 F1 (shifted Parabola/Sphere) 102 F6 (shifted Rosenbrock) 103 F9 (shifted Rastrigin) 104 F2 Schwefel 105 F7 Griewank (NOT rotated) 106 F8 Ackley (NOT rotated) 99 Test */ runMax = 100; // Numbers of runs // =========================================================== pb = new CEC2005F1Circle();//Problem.Problem.problemDef(functionCode, null);//fLandscape); fLandscape is for when the landscape is read from a file. /* ----------------------------------------------------- PARAMETERS and OPTIONS */ parameters.formula = 1; // Which formula to use to compute the number of // iterations between two checks. See SpreadIter() parameters.spreadProba = 1; //1; // We want that the probability for a particle to be // informed my any other one after T time steps // is at least spreadProba. Then T is automatically // computed. // Particular case: set to zero => T=1 // Suggested values: // formula spreadProba // 1 1.0 // 2, 3 0.9 // with PSO_B, formula=1 and spredProba=0.55 // -------------------------------------------------------------AUTOMATIC VALUES // You may modify them, if you really want to ... parameters.S = (int)(40 + 2 * Math.Sqrt(pb.SwarmSize.D)); // Initial swarm size //Parameters.S=pb.SwarmSize.D+1; // According to Clerc's Stagnation Analysis parameters.w = 1 / (2 * Math.Log((double)2)); // 0.721 parameters.c1 = 0.5 + Math.Log((double)2); // 1.193 parameters.c2 = parameters.c1; //---------------------------------------------------------- WARNINGS and ERRORS if (runMax > Constants.RMax) // Maximum number of runs { runMax = Constants.RMax; Console.WriteLine("WARNING. No more than {0} runs", Constants.RMax); } if (parameters.S > Constants.SMax) { parameters.S = Constants.SMax; Console.WriteLine("WARNING. The swarm size can not be bigger than {0}", Constants.SMax); } if (parameters.spreadProba > 1) { throw new ArgumentException("Parameters.spreadProba must be smaller than 1"); } // Display information about the problem and the parameters // Some information //--------------- convRateMean = 0; errorMean = 0; evalMean = 0; nFailure = 0; //------------------------------------- RUNS for (run = 0; run < runMax; run++) { //printf("\n run %i/%i",run+1,runMax); // For some options, positions must be memorised as much a possible //fprintf(f_swarm,"run %i\n",run); result = PSO(parameters, pb, 0); error = result.error.errorFC(); convRateMean = convRateMean + result.convRate; if (error > pb.Epsilon) // Failure { nFailure = nFailure + 1; } // Result display //printf("\nmean %1.2e", errorMean/(run+1)); // Temporary error mean //printf(", %0.0f %% ", (double)100*(run+1-nFailure)/(run+1)); // Temporary success rate //printf (" %i/%i. Eval %f. Error %f ", run+1,runMax, result.nEval, error); //printf(" x(0)= %f",(double)result.SW.P[result.SW.best].x[0]); // Save result //fprintf( f_run, "\n%i %f %e ", run, result.nEval, error ); //for ( d = 0; d < pb.SwarmSize.D; d++ ) // fprintf( f_run, " %0.20f", (double)result.SW.P[result.SW.best].x[d] ); // Compute/store some statistical information if (run == 0) { errorMin = error; bestBest = result.SW.P[result.SW.best]; } else if (error < errorMin) { errorMin = error; bestBest = result.SW.P[result.SW.best]; } evalMean = evalMean + result.nEval; errorMean = errorMean + error; errorMeanBest[run] = error; logProgressMean = logProgressMean - Math.Log(error); } // End loop on "run" // Display statistical information // Means convRateMean = convRateMean / (double)runMax; evalMean = evalMean / (double)runMax; errorMean = errorMean / (double)runMax; logProgressMean = logProgressMean / (double)runMax; Console.WriteLine("Conv. rate (mean)= {0}", convRateMean); Console.WriteLine("Eval. (mean)= {0}", evalMean); Console.WriteLine("Error (mean) = {0}, {1}", errorMean, errorMean); // Variance variance = 0; for (run = 0; run < runMax; run++) variance = variance + Math.Pow(errorMeanBest[run] - errorMean, 2); variance = Math.Sqrt(variance / runMax); Console.WriteLine("Std. dev. {0}", variance); Console.WriteLine("Log_progress (mean) = {0}", logProgressMean); // Success rate and minimum value Console.WriteLine("Failure(s) {0}", nFailure); successRate = 1 - nFailure / (double)runMax; Console.WriteLine("Success rate = {0}%", 100 * successRate); //if (run > 1) Console.WriteLine("Best min value = {0}", bestBest.f.f[0]); if (pb.Constraint > 0) { Console.WriteLine("{0} constraints (should be negative): ", pb.Constraint); for (n = 0; n < pb.Constraint; n++) Console.WriteLine("{0} ", bestBest.f.f[n + 1]); } // Display the best position Console.WriteLine("Position: "); for (d = 0; d < pb.SwarmSize.D; d++) Console.WriteLine(" {0}", (double)bestBest.x[d]); // Save /* fprintf(f_synth,"\n"); for (d=0;d<SwarmSize.D;d++) fprintf(f_synth,"%f ", pb.offset[d]); fprintf(f_synth," %f %f %f %.0f%% %f",errorMean,variance,errorMin, successRate,evalMean); fprintf( f_synth, "\n%f %f %f %f %.0f%% %f ", shift, errorMean, variance, errorMin, successRate, evalMean ); */ //fprintf (f_synth, "%f %f %.0f%% %f ", // errorMean, variance, 100*successRate, evalMean); // Save the best result //fprintf(f_synth,"\n "); //for(n=0;n<pb.constraint+1;n++) fprintf( f_synth, "%f ", bestBest.f.f[n]); //fprintf(f_synth," X"); //for ( d = 0; d < pb.SwarmSize.D; d++ ) fprintf( f_synth, " %f", (double) bestBest.x[d] ); //----------------------------------------------------- // Repeat some information Console.WriteLine("Function {0}", functionCode); Console.WriteLine("Dimension {0}", pb.SwarmSize.D); Console.ReadLine(); return; // End of main program }
public static Position Discrete(Position pos0, IProblem pb) { if (pb.SwarmSize.valueNb > 0) // The search space is a list of values { return ValueAccept(pos0, pb.SwarmSize.valueNb); } // Quantisation Position pos = Quantis(pos0, pb.SwarmSize); return pos; }
public static Fitness Constraint(Position x, IProblem pb) { throw new NotImplementedException(); }
public Position Clone() { var retVal = new Position(x.Length); retVal.size = size; retVal.f = f.Clone(); x.CopyTo(retVal.x,0); return retVal; }
public static Position ValueAccept(Position x, int valueNb) { // valueList[] is a global variable (see main.h) // Move the position to the nearest acceptable value, // for each dimension independently int d; int i; Position xv; xv = x; for (d = 0; d < x.size; d++) { if (x.x[d] <= Constants.valueList[0]) { xv.x[d] = Constants.valueList[0]; continue; } if (x.x[d] >= Constants.valueList[valueNb - 1]) { xv.x[d] = Constants.valueList[valueNb - 1]; continue; } for (i = 1; i < valueNb; i++) { if (x.x[d] >= Constants.valueList[i - 1] && x.x[d] <= Constants.valueList[i]) { if (x.x[d] - Constants.valueList[i - 1] < Constants.valueList[i] - x.x[d]) xv.x[d] = Constants.valueList[i - 1]; else xv.x[d] = Constants.valueList[i]; break; } } } return xv; }
public static Position Quantis(Position x, SwarmSize swarmSize) { /* Quantisatition of a position Only values like x+k*q (k integer) are admissible */ Position quantx = x.Clone(); for (int d = 0; d < x.size; d++) { if (swarmSize.q.Q[d] > Constants.Zero) // Note that qd can't be < 0 { quantx.x[d] = swarmSize.q.Q[d] * Math.Floor(0.5 + x.x[d] / swarmSize.q.Q[d]); } } return quantx; }
/// <summary> /// Initialise a position /// Note: possible constraints are not checked here. /// The position may be unfeasible /// </summary> public static Position Initialize(SwarmSize swarmSize) { int d; var pos = new Position(Constants.DMax) {size = swarmSize.D}; // Random uniform for (d = 0; d < pos.size; d++) { pos.x[d] = Alea.NextDouble(swarmSize.min[d], swarmSize.max[d]); } if (swarmSize.valueNb > 0) // If only some values are acceptable pos = ValueAccept(pos, swarmSize.valueNb); return pos; }