剛用LUA寫了AGSO算法,效果奇差無比. 可能寫錯了..下面這個蜂群算法.效果很好.跳出局部最優的能力比較強!
1 -- 人工蜂群算法 ABC 2 3 4 -- lua 相關簡易操作 5 sin = math.sin 6 cos = math.cos 7 sqrt = math.sqrt 8 pi = math.pi 9 random = math.random 10 exp = math.exp 11 int = math.floor 12 13 14 -- 獲得不同的隨機序列 15 math.randomseed(os.time()) 16 17 18 -- ==============================求解函數============================== 19 dim = 2 -- 解的維數 20 domx = { -- 定義域 21 { { -1, 2 }, { -1, 2 } }, 22 { { 2, 4 }, { -1, 1 } }, 23 { { 0, 4 }, { 0, 4 } }, 24 } 25 maxfun = { -- 求解函數 26 function(x) return 4 - (x[1] * sin( 4 * pi * x[1]) - x[2] * sin(4 * pi * x[2] + pi + 1)) end , 27 function(x) return exp(x[1] - x[2] * x[2]) / (x[1] * x[1] - x[2]) + (x[1] - 3) ^ 2 end , 28 function(x) return 2 + (x[1] * x[1] + x[2] * x[2]) / 10 - (cos(2 * pi * x[1]) + cos(2 * pi * x[2])) end , 29 } 30 funidx = 0 31 -- ==================================================================== 32 33 34 -- ================================定義================================ 35 foodnum = 10 -- 食物數量 36 employednum = foodnum -- 雇佣兵等於食物數量, 每個雇佣兵負責更新一下食物 37 onlookernum = foodnum -- 觀察蜂也設置為食物數量, 理論上每個食物都有機會提高 38 foods = {} -- 食物, 即可行解 還包含了,函數值,適應度,最優次數 39 gbest = 0 -- 當前全局最優 40 optmaxtime = 20 -- 局部最優最大值 41 itermax = 100 -- 迭代次數 42 -- ==================================================================== 43 44 45 -- ==============================工具函數============================== 46 -- 適應度函數, 此處全設為Y值 47 function getfitness(y) return y end 48 49 -- 食物初始化, 並選出最佳 50 function foodinit() 51 for i = 1, foodnum do 52 foods[i] = {} 53 for j = 1, dim do 54 foods[i][j] = domx[funidx][j][1] + (domx[funidx][j][2] - domx[funidx][j][1]) * random() 55 end 56 foods[i].y = maxfun[funidx](foods[i]) 57 foods[i].fitness = getfitness(foods[i].y) 58 foods[i].opttimes = 0 59 end 60 61 gbest = 1 62 for i = 2, foodnum do 63 if foods[i].fitness > foods[gbest].fitness then gbest = i end 64 end 65 end 66 67 -- 單個食物重新初始化 68 function sfoodinit(idx) 69 for i = 1, dim do 70 foods[idx][i] = domx[funidx][i][1] + (domx[funidx][i][2] - domx[funidx][i][1]) * random() 71 end 72 foods[idx].y = maxfun[funidx](foods[idx]) 73 foods[idx].fitness = getfitness(foods[idx].y) 74 foods[idx].opttimes = 0 75 76 if idx == gbest then 77 gbest = 1 78 for i = 2, foodnum do 79 if foods[i].fitness > foods[gbest].fitness then gbest = i end 80 end 81 --print("去掉一個全局最優") 82 else 83 if foods[idx].fitness > foods[gbest].fitness then gbest = idx end 84 --print("去掉一個局部最優") 85 end 86 end 87 88 89 -- 更新食物 90 function updatefood(idx) 91 dimi = int(random() * dim) + 1 92 93 idx1 = int(random() * foodnum) + 1 94 while idx1 == idx do 95 idx1 = int(random() * foodnum) + 1 96 end 97 98 tmpfood = {} 99 for i = 1, dim do 100 tmpfood[i] = foods[idx][i] 101 end 102 103 tmpfood[dimi] = tmpfood[dimi] + (foods[idx1][dimi] - tmpfood[dimi]) * (random() - 0.5) * 2 104 if tmpfood[dimi] < domx[funidx][dimi][1] then 105 tmpfood[dimi] = domx[funidx][dimi][1] 106 elseif tmpfood[dimi] > domx[funidx][dimi][2] then 107 tmpfood[dimi] = domx[funidx][dimi][2] 108 end 109 110 tmpfood.y = maxfun[funidx](tmpfood) 111 tmpfood.fitness = getfitness(tmpfood.y) 112 113 if tmpfood.fitness > foods[idx].fitness then 114 foods[idx].y = tmpfood.y 115 foods[idx].fitness = tmpfood.fitness 116 foods[idx].opttimes = 0 117 for i = 1, dim do foods[idx][i] = tmpfood[i] end 118 119 if foods[idx].fitness > foods[gbest].fitness then gbest = idx end 120 else 121 foods[idx].opttimes = foods[idx].opttimes + 1 122 end 123 124 end 125 -- ==================================================================== 126 127 128 -- ===============================主函數=============================== 129 function main(idx) 130 -- 功能選取 131 funidx = idx 132 -- 系統初始化 133 foodinit() 134 135 -- 開始迭代 136 for iter = 1, itermax do 137 -- 雇佣蜂 138 for i = 1, employednum do 139 updatefood(i) 140 end 141 142 -- 觀察蜂, 非輪盤賭 143 fitsum = {} 144 for i = 1, foodnum do 145 fitsum[i] = ( 0.9 * ( foods[i].fitness / foods[gbest].fitness ) ) + 0.1 146 end 147 148 cnt = 0 149 while cnt < onlookernum do 150 for i = 1, foodnum do 151 if random() < fitsum[i] then 152 updatefood(i) 153 cnt = cnt + 1 154 if cnt >= onlookernum then break end 155 end 156 end 157 end 158 159 -- 偵查蜂 160 maxoptidx = 1 161 for i = 2, foodnum do 162 if foods[i].opttimes > foods[maxoptidx].opttimes then maxoptidx = i end 163 end 164 165 if foods[maxoptidx].opttimes > optmaxtime then sfoodinit(maxoptidx) end 166 end 167 end 168 -- ==================================================================== 169 170 t1 = os.clock() 171 172 main(1) 173 print(string.format("函數值為: %.8f \t解為: (%.3f, %.3f)", foods[gbest].y, foods[gbest][1], foods[gbest][2])) 174 main(2) 175 print(string.format("函數值為: %.8f \t解為: (%.3f, %.3f)", foods[gbest].y, foods[gbest][1], foods[gbest][2])) 176 main(3) 177 print(string.format("函數值為: %.8f \t解為: (%.3f, %.3f)", foods[gbest].y, foods[gbest][1], foods[gbest][2])) 178 179 t2 = os.clock() 180 181 print("times: ", 1000 * (t2 - t1))
1 /* 人工蜂群算法 ABC C語言 */ 2 #include <stdio.h> 3 #include <stdlib.h> 4 #include <string.h> 5 #include <time.h> 6 #include <math.h> 7 #include <windows.h> 8 9 #define PI 3.1415926f 10 #define X_DIM 2 11 #define RND ((float)rand() / (RAND_MAX + 1)) 12 13 float domx[2][2] = 14 { 15 { -1.0f, 2.0f}, { -1.0f, 2.0f} 16 }; 17 18 typedef struct tag_food 19 { 20 float x[X_DIM]; 21 float y; 22 int opttimes; 23 } food_t; 24 25 const int foodnum = 30; /*食物數量*/ 26 const int employednum = foodnum; /*雇佣兵等於食物數量, 每個雇佣兵負責更新一個食物*/ 27 const int onlookernum = foodnum; /*觀察蜂也設置為食物數量, 理論上每個食物都有機會提高*/ 28 food_t foods[foodnum]; /*食物, 即可行解 還包含了,函數值,適應度,最優次數*/ 29 const int maxopttimes = 20; /*局部最優最大值*/ 30 const int itermax = 100; /*迭代次數*/ 31 32 int gbest; 33 34 35 float func_y( float* x ) 36 { 37 return 4 - ( x[0] * sin( 4 * PI * x[0] ) - x[1] * sin( 4 * PI * x[1] + PI + 1 ) ); 38 } 39 40 41 void foods_init() 42 { 43 register int i, j; 44 45 for ( i = 0; i < foodnum; i ++ ) 46 { 47 for ( j = 0; j < X_DIM; j ++ ) 48 { 49 foods[i].x[j] = domx[j][0] + ( domx[j][1] - domx[j][0] ) * RND; 50 } 51 52 foods[i].y = func_y( foods[i].x ); 53 foods[i].opttimes = 0; 54 } 55 56 gbest = 0; 57 for ( i = 1; i < foodnum; i ++ ) 58 { 59 if ( foods[i].y > foods[gbest].y ) 60 { 61 gbest = i; 62 } 63 } 64 } 65 66 void food_init_s( int idx ) 67 { 68 register int i; 69 70 for ( i = 0; i < X_DIM; i ++ ) 71 { 72 foods[idx].x[i] = domx[i][0] + ( domx[i][1] - domx[i][0] ) * RND; 73 } 74 75 foods[idx].y = func_y( foods[idx].x ); 76 foods[idx].opttimes = 0; 77 78 if ( idx != gbest ) 79 { 80 if ( foods[idx].y > foods[gbest].y ) 81 { 82 gbest = idx; 83 } 84 } 85 else 86 { 87 gbest = 0; 88 for ( i = 1; i < foodnum; i ++ ) 89 { 90 if ( foods[i].y > foods[gbest].y ) 91 { 92 gbest = i; 93 } 94 } 95 } 96 } 97 98 void food_update( int idx ) 99 { 100 food_t tmpfood; 101 int idx1, dimi; 102 103 while ( ( idx1 = ( int )( RND * foodnum ) ) == idx ); 104 105 dimi = ( int )( RND * X_DIM ); 106 107 memcpy( tmpfood.x, foods[idx].x, sizeof( foods[idx].x ) ); 108 109 tmpfood.x[dimi] += ( foods[idx1].x[dimi] - tmpfood.x[dimi] ) * ( RND - 0.5f ) * 2; 110 111 if ( tmpfood.x[dimi] < domx[dimi][0] ) 112 { 113 tmpfood.x[dimi] = domx[dimi][0]; 114 } 115 else if ( tmpfood.x[dimi] > domx[dimi][1] ) 116 { 117 tmpfood.x[dimi] = domx[dimi][1]; 118 } 119 120 tmpfood.y = func_y( tmpfood.x ); 121 122 if ( tmpfood.y > foods[idx].y ) 123 { 124 memcpy( foods + idx, &tmpfood, sizeof( food_t ) ); 125 if ( foods[idx].y > foods[gbest].y ) 126 { 127 gbest = idx; 128 } 129 } 130 else 131 { 132 foods[idx].opttimes ++; 133 } 134 } 135 136 137 int main() 138 { 139 DWORD dwT1, dwT2; 140 int iter, cnt, optidx; 141 register int i; 142 float fit; 143 144 srand( ( unsigned int )time( NULL ) ); 145 146 147 dwT1 = GetTickCount(); 148 149 foods_init(); 150 151 for ( iter = 0; iter < itermax; iter ++ ) 152 { 153 for ( i = 0; i < employednum; i ++ ) 154 { 155 food_update( ( ( ( int )( RND * 10 ) ) * i ) % foodnum ); 156 } 157 158 cnt = 0; 159 while ( cnt < onlookernum ) 160 { 161 for ( i = 0; i < foodnum; i ++ ) 162 { 163 fit = ( 0.6f * ( foods[i].y / foods[gbest].y ) ) + 0.1f; 164 if ( RND < fit ) 165 { 166 food_update( i ); 167 if ( ++ cnt == onlookernum ) 168 { 169 break; 170 } 171 } 172 } 173 } 174 175 optidx = 0; 176 for ( i = 1; i < foodnum; i ++ ) 177 { 178 if ( foods[i].opttimes > foods[optidx].opttimes ) 179 { 180 optidx = i; 181 } 182 } 183 184 if ( foods[optidx].opttimes > maxopttimes ) 185 { 186 food_init_s( optidx ); 187 } 188 } 189 190 dwT2 = GetTickCount() - dwT1; 191 192 fprintf( stdout, "函數值為: %.8f\t解為: (%.3f, %.3f)\t時間: %d", \ 193 foods[gbest].y, foods[gbest].x[0], foods[gbest].x[1], dwT2 ); 194 195 return 0; 196 }
1 // 人工蜂群算法 ABC 2 3 // 獲得不同的隨機序列 4 // math.randomseed(os.time()) 5 6 7 // ==============================求解函數============================== 8 var dim = 2; // 解的維數 9 var domx = [ // 定義域 10 [ [ -1, 2 ], [ -1, 2 ] ], 11 [ [ 2, 4 ], [ -1, 1 ] ], 12 [ [ 0, 4 ], [ 0, 4 ] ], 13 ]; 14 var maxfun = [ // 求解函數 15 function( x ) 16 { 17 return 4 - ( x[0] * Math.sin( 4 * Math.PI * x[0] ) - x[1] * Math.sin( 4 * Math.PI * x[1] + Math.PI + 1 ) ); 18 }, 19 function( x ) 20 { 21 return Math.exp( x[0] - x[1] * x[1] ) / ( x[0] * x[0] - x[1] ) + Math.pow( x[0] - 3, 2); 22 }, 23 function( x ) 24 { 25 return 2 + ( x[0] * x[0] + x[1] * x[1] ) / 10 - ( Math.cos( 2 * Math.PI * x[0] ) + Math.cos( 2 * Math.PI * x[1] ) ); 26 } 27 ]; 28 var funidx = 0; 29 // ==================================================================== 30 31 32 // ================================定義================================ 33 var foodnum = 10; // 食物數量 34 var employednum = foodnum; // 雇佣兵等於食物數量, 每個雇佣兵負責更新一下食物 35 var onlookernum = foodnum; // 觀察蜂也設置為食物數量, 理論上每個食物都有機會提高 36 var foods = new Object( foodnum ); // 食物, 即可行解 還包含了,函數值,適應度,最優次數 37 var gbest = 0; // 當前全局最優 38 var optmaxtime = 20; // 局部最優最大值 39 var itermax = 100; // 迭代次數 40 // ==================================================================== 41 42 43 // ==============================工具函數============================== 44 // 適應度函數, 此處全設為Y值 45 function getfitness( y ) 46 { 47 return y; 48 } 49 50 // 食物初始化, 並選出最佳 51 function foodinit() 52 { 53 var i, j; 54 55 for ( i = 0; i < foodnum; i ++ ) 56 { 57 foods[i] = {x:new Array(dim)}; 58 for ( j = 0; j < dim; j ++ ) 59 { 60 foods[i].x[j] = domx[funidx][j][0] + ( domx[funidx][j][1] - domx[funidx][j][0] ) * Math.random(); 61 } 62 foods[i].y = maxfun[funidx]( foods[i].x ); 63 foods[i].fitness = getfitness( foods[i].y ); 64 foods[i].opttimes = 0; 65 } 66 67 gbest = 0; 68 for ( i = 1; i < foodnum; i ++ ) 69 { 70 if ( foods[i].fitness > foods[gbest].fitness ) 71 { 72 gbest = i; 73 } 74 } 75 } 76 77 78 // 單個食物重新初始化 79 function sfoodinit( idx ) 80 { 81 var i; 82 83 for ( i = 0; i < dim; i ++ ) 84 { 85 foods[idx].x[i] = domx[funidx][i][0] + ( domx[funidx][i][1] - domx[funidx][i][0] ) * Math.random(); 86 } 87 foods[idx].y = maxfun[funidx]( foods[idx].x ); 88 foods[idx].fitness = getfitness( foods[idx].y ); 89 foods[idx].opttimes = 0; 90 91 if ( idx == gbest ) 92 { 93 gbest = 0; 94 for ( i = 1; i < foodnum; i ++ ) 95 { 96 if ( foods[i].fitness > foods[gbest].fitness ) 97 { 98 gbest = i; 99 } 100 } 101 } 102 else 103 { 104 if ( foods[idx].fitness > foods[gbest].fitness ) 105 { 106 gbest = idx; 107 } 108 } 109 } 110 111 112 113 // 更新食物 114 function updatefood( idx ) 115 { 116 var dimi, idx1; 117 var tmpfood; 118 119 dimi = Math.floor( Math.random() * dim ); 120 121 while ( ( idx1 = Math.floor( Math.random() * foodnum ) ) == idx ); 122 123 tmpfood = new Object(); 124 tmpfood.x = foods[idx].x.concat(); 125 126 tmpfood.x[dimi] = tmpfood.x[dimi] + ( foods[idx1].x[dimi] - tmpfood.x[dimi] ) * ( Math.random() - 0.5 ) * 2; 127 if ( tmpfood.x[dimi] < domx[funidx][dimi][0] ) 128 { 129 tmpfood.x[dimi] = domx[funidx][dimi][0]; 130 } 131 else if ( tmpfood.x[dimi] > domx[funidx][dimi][1] ) 132 { 133 tmpfood.x[dimi] = domx[funidx][dimi][1]; 134 } 135 136 137 tmpfood.y = maxfun[funidx]( tmpfood.x ); 138 tmpfood.fitness = getfitness( tmpfood.y ); 139 tmpfood.opttimes = 0; 140 141 if ( tmpfood.fitness > foods[idx].fitness ) 142 { 143 foods[idx] = tmpfood; 144 145 if ( foods[idx].fitness > foods[gbest].fitness ) 146 { 147 gbest = idx; 148 } 149 } 150 else 151 { 152 foods[idx].opttimes ++; 153 } 154 } 155 // ==================================================================== 156 157 158 // ===============================主函數=============================== 159 function main( idx ) 160 { 161 162 var iter; 163 var fitsum; 164 var cnt, maxoptidx; 165 166 // 功能選取 167 funidx = idx; 168 // 系統初始化 169 foodinit(); 170 171 // 中間數組 172 fitsum = new Array(); 173 174 // 開始迭代 175 for ( iter = 0; iter < itermax; iter ++ ) 176 { 177 // 雇佣蜂 178 for ( i = 0; i < employednum; i ++ ) 179 { 180 updatefood( i ); 181 } 182 183 // 觀察蜂, 非輪盤賭 184 for ( i = 0; i < foodnum; i ++ ) 185 { 186 fitsum[i] = ( 0.9 * ( foods[i].fitness / foods[gbest].fitness ) ) + 0.1; 187 } 188 189 cnt = 0; 190 while ( cnt < onlookernum ) 191 { 192 for ( i = 0; i < foodnum; i ++ ) 193 { 194 if ( Math.random() < fitsum[i] ) 195 { 196 updatefood( i ); 197 if ( ++ cnt >= onlookernum ) break; 198 } 199 } 200 } 201 202 // 偵查蜂 203 maxoptidx = 0; 204 for ( i = 1; i < foodnum; i ++ ) 205 { 206 if ( foods[i].opttimes > foods[maxoptidx].opttimes ) 207 { 208 maxoptidx = i; 209 } 210 } 211 212 if ( foods[maxoptidx].opttimes > optmaxtime ) 213 { 214 sfoodinit( maxoptidx ); 215 } 216 } 217 } 218 // ==================================================================== 219 220 var t1 = new Date(); 221 222 main( 0 ); 223 document.write( "函數值為: ", foods[gbest].y, " \t解為: (", foods[gbest].x[0], ", ", foods[gbest].x[1], ")<br>\n"); 224 main( 1 ); 225 document.write( "函數值為: ", foods[gbest].y, " \t解為: (", foods[gbest].x[0], ", ", foods[gbest].x[1], ")<br>\n"); 226 main( 2 ); 227 document.write( "函數值為: ", foods[gbest].y, " \t解為: (", foods[gbest].x[0], ", ", foods[gbest].x[1], ")<br>\n"); 228 229 document.write( "times: ", new Date() - t1 );