• Main Page
  • Modules
  • Classes
  • Files
  • File List

D:/Projekt/ECF_trunk/ECF/AlgEvolutionStrategy.cpp

00001 #include "ECF_base.h"
00002 #include "ECF_macro.h"
00003 #include "AlgEvolutionStrategy.h"
00004 #include "SelBestOp.h"
00005 #include "SelRandomOp.h"
00006 #include <algorithm>
00007 
00008 
00009 EvolutionStrategy::EvolutionStrategy()
00010 {
00011     // define algorithm name
00012     name_ = "EvolutionStrategy";
00013 
00014     // create selection operators needed
00015     selBestOp_ = static_cast<SelectionOperatorP> (new SelBestOp);
00016     selRandomOp_ = static_cast<SelectionOperatorP> (new SelRandomOp);
00017 }
00018 
00019 
00020 void EvolutionStrategy::registerParameters(StateP state)
00021 {
00022     registerParameter(state, "lambda", (voidP) new uint(4), ECF::UINT, 
00023         "number of offspring created in each iteration (default: 4)");
00024     registerParameter(state, "rho", (voidP) new uint(1), ECF::UINT, 
00025         "number of parents used to create an offspring; may be 1 or 2 (default: 1)");
00026     registerParameter(state, "mu", (voidP) new uint(1), ECF::UINT, 
00027         "the size of parent population (default: 1)");
00028     registerParameter(state, "selection", (voidP) new std::string("plus"), ECF::STRING, 
00029         "selection scheme: \"plus\", uses both parents and offspring) or \"comma\", uses just offspring (default: plus)");
00030 }
00031 
00032 
00033 bool EvolutionStrategy::initialize(StateP state)
00034 {
00035     // initialize all operators
00036     selBestOp_->initialize(state);
00037     selRandomOp_->initialize(state);
00038 
00039     // read parameter values
00040     voidP sizep = getParameterValue(state, "lambda");
00041     lambda_ = *((uint*) sizep.get());
00042 
00043     voidP rhop = getParameterValue(state, "rho");
00044     rho_ = *((uint*) rhop.get());
00045 
00046     if(rho_ < 1 || rho_ > 2) {
00047         ECF_LOG_ERROR(state, "Error: number of parents to create an offspring in EvolutionStrategy can only be 1 or 2!");
00048         throw "";
00049     }
00050 
00051     voidP mup = getParameterValue(state, "mu");
00052     mu_ = *((uint*) mup.get());
00053 
00054     if(mu_ < rho_) {
00055         ECF_LOG_ERROR(state, "Error: size of parent population in EvolutionStrategy must be greater than number of parents to create an offspring!");
00056         throw "";
00057     }
00058 
00059 
00060     voidP sptr = state->getRegistry()->getEntry("population.size");
00061     uint demeSize = *((uint*) sptr.get());
00062     if(demeSize % mu_ != 0 || mu_ < 1) {
00063         ECF_LOG_ERROR(state, "Error: \"population.size\" parameter must be a multiple of size of parent population (mu) in EvolutionStrategy algorithm!");
00064         throw "";
00065     }
00066 
00067     voidP selp = getParameterValue(state, "selection");
00068     std::string sels = *((std::string*) selp.get());
00069     if(sels == "plus")
00070         plusSelection_ = true;
00071     else if(sels == "comma")
00072         plusSelection_ = false;
00073     else {
00074         ECF_LOG_ERROR(state, "Error: selection type in EvolutionStrategy can only be \"plus\" or \"comma\"!");
00075         throw "";
00076     }
00077 
00078     if(plusSelection_ == false && lambda_ <= mu_) {
00079         ECF_LOG_ERROR(state, "Error: offspring number (lambda) in comma EvolutionStrategy must be greater than the number of parents (mu)!");
00080         throw "";
00081     }
00082 
00083     return true;
00084 }
00085 
00086 
00087 bool EvolutionStrategy::advanceGeneration(StateP state, DemeP deme)
00088 {
00089     subPopulations_ = (uint) deme->size() / mu_;
00090 
00091     // repeat the same ES for each parent subpopulation
00092     for(uint subPopulation = 0; subPopulation < subPopulations_; subPopulation++) {
00093 
00094         // use appropriate portion of the deme
00095         uint firstInd = subPopulation * mu_;
00096         uint lastInd = (subPopulation + 1) * mu_;
00097 
00098         // construct parent pool
00099         std::vector<IndividualP> parents;
00100         for(uint ind = firstInd; ind < lastInd; ind++)
00101             parents.push_back(deme->at(ind));
00102 
00103         // create offspring pool
00104         std::vector<IndividualP> offspring;
00105         for(uint iChild = 0; iChild < lambda_; iChild++) {
00106             // randomly select rho parents, create one child
00107             IndividualP child;
00108             // use mutation
00109             if(rho_ == 1) {
00110                 IndividualP parent = selRandomOp_->select(parents);
00111                 child = copy(parent);
00112                 mutation_->mutate(child);
00113             }
00114             // use crossover
00115             else if(rho_ == 2) {
00116                 IndividualP p1 = selRandomOp_->select(parents);
00117                 IndividualP p2 = p1;
00118                 while(p1 == p2)
00119                     p2 = selRandomOp_->select(parents);
00120                 child = copy(p1);
00121                 mate(p1, p2, child);
00122             }
00123             offspring.push_back(child);
00124             // evaluate offspring
00125             evaluate(child);
00126         }
00127 
00128         // construct selection pool for new generation parents
00129         std::vector<IndividualP> selPool;
00130         if(plusSelection_) {
00131             // arrange selection pool from both best parents and offspring
00132             selPool = parents;
00133             selPool.insert(selPool.end(), offspring.begin(), offspring.end());
00134         }
00135         else
00136             // select from offspring only
00137             selPool = offspring;
00138 
00139         // sort by fitness (best first)
00140         std::sort(selPool.begin(), selPool.end(), &EvolutionStrategy::compare);
00141 
00142         // replace new generation in deme
00143         uint selected = 0;
00144         for(uint ind = firstInd; ind < lastInd; ind++, selected++)
00145             replaceWith(ind, selPool[selected]);
00146     }
00147 
00148     return true;
00149 }

Generated on Tue Nov 4 2014 13:04:30 for ECF by  doxygen 1.7.1