题目描述:
运用遗传算法求解图中函数的最大值(约为38.8503…)
解决步骤:
1.确定编码方案——二进制编码,长度33位。
2.初始化种群:使用计算机在0~1之间产生随机数K,并按照数K的 值初始化基因位: 0≤K<0.5,基因为置为1,0.5≤K≤1,基因为置为0。得到33位的01序列字符串。
3.计算个体适应度,以maxf(x1,x2)为适应度函数,因所需求的值为最大值,适应度函数值越大表示适应度越高,个体越优良。
4.轮盘赌算法
1)计算适应度比例,即每个个体的选择概率。
(2)计算每个个体的累积概率(适应度越大累积概率越高),相当于转盘上的“跨度”,“跨度”越大越容易选到。即每个个体之前所有个体的选择概率之和,相当于概率论中的概率分布函数
(3)生成0-1随机数,挑选在跨度之间的个体(累积概率越高被选中的概率越大)。
5.根据交叉概率pc=0.6对选出的个体进行交 叉,将两点交叉作为交叉算子,记产生的后代个体的集合为O1。
5.设定变异概率Pm=0.01(变异概率0.01表示O1中平均有1%个基因发生变异)对交叉产生的个体 进行变异,将单点变异作为变异算子,记产生 的后代个体的集合为O2。
6.计算所有后代个体的适应度,选出最好的 E=2个个体直接保留到下一代种群。 然后,根据轮盘赌选择N-E=8个个体进入下一 代种群。
7.若进化代数t=1000,则终止算法,输出适应度最大的个体作为问题的最优解。否则, 令t=t+1,转入第三步。
遗传算法根据对个体的优良选培及适当的交叉变异,逐步逼近最优解。
显然进化代数越高,解的精度和可信度越高,但是计算时间和算力要求更高。
源代码语言:java
package ai;
import java.util.ArrayList;
import java.util.Random;
import static java.lang.Math.*;
public class AIWork {
public static final int RANDOMMAX = 32767;
public static final double PI = 3.14159265358979323;
//
public ArrayList<String> pop = new ArrayList<>();
//种群规模
public static final int NUMBER = 20;
//交叉概率
private double pc = 0.6;
//变异概率
private double pm = 0.01;
//
String maxString;
//代数
private int t;
public void incre_t(){
t++;
}
public int getT() {
return t;
}
public void setT(int t) {
this.t = t;
}
public static void main(String[] args) {
AIWork aiWork = new AIWork();
Individual Max = new Individual();
aiWork.init();
int j = 0;
double MAX = 0;
while (aiWork.getT() < 200000){
double max1 = 0;
double max2 = 0;
String s1 = null;
String s2 = null;
Individual max;
ArrayList<String> pop1,pop2,popNew,pop3 = new ArrayList<>();
pop1 = aiWork.choose(aiWork.pop,NUMBER);
pop2 = aiWork.crossover(pop1);
for (int i = 0; i < pop2.size(); i++) {
String s = aiWork.mutation(pop2.get(i));
pop3.add(s);
double d = aiWork.fitness(pop2.get(i)).getFit();
if (d > max1){
s1 = pop2.get(i);
max1 = d;
}
}
for