EvolvingObjects
|
00001 // -*- mode: c++; c-indent-level: 4; c++-member-init-indent: 8; comment-column: 35; -*- 00002 //----------------------------------------------------------------------------- 00003 // eoOrderXover.h 00004 //----------------------------------------------------------------------------- 00005 00006 #ifndef eoOrderXover_h 00007 #define eoOrderXover_h 00008 00009 //----------------------------------------------------------------------------- 00010 00011 #include <algorithm> 00012 #include <utils/eoRNG.h> 00013 #include <eoInit.h> 00014 00026 template<class Chrom> class eoOrderXover: public eoQuadOp<Chrom> 00027 { 00028 public: 00030 virtual std::string className() const { return "eoOrderXover"; } 00031 00037 bool operator()(Chrom& _chrom1, Chrom& _chrom2){ 00038 00039 char direction=eo::rng.flip()? 1 : -1; 00040 unsigned cut2= 1 + eo::rng.random(_chrom1.size()); 00041 unsigned cut1= eo::rng.random(cut2); 00042 Chrom tmp1= _chrom1; 00043 Chrom tmp2= _chrom2; 00044 00045 cross(tmp1, tmp2, _chrom1, direction, cut1, cut2); 00046 cross(tmp2, tmp1, _chrom2, direction, cut1, cut2); 00047 00048 _chrom1.invalidate(); 00049 _chrom2.invalidate(); 00050 00051 return true; 00052 } 00053 00054 private: 00055 00064 void cross(Chrom& _chrom1, Chrom& _chrom2, Chrom& _child, char _direction, unsigned _cut1, unsigned _cut2){ 00065 00066 unsigned size, id=0, from=0; 00067 size= _chrom1.size(); 00068 00069 std::vector<bool> verif(size, false); 00070 00071 for(unsigned i= _cut1; i<_cut2; i++){ 00072 _child[id++]= _chrom1[i]; 00073 verif[_chrom1[i] % size] = true; 00074 } 00075 00076 while(_chrom2[from] != _child[_cut2 - 1]) 00077 from++; 00078 00079 for(unsigned i=0; i<size; i++){ 00080 unsigned j= (_direction*i + from + size) % size; 00081 if(!verif[_chrom2[j] % size]){ 00082 _child[id++]=_chrom2[j]; 00083 verif[_chrom2[j]%size]=true; 00084 } 00085 } 00086 } 00087 00088 }; 00092 #endif