zoukankan      html  css  js  c++  java
  • 遗传算法学习笔记

    遗传算法的定义,摘自维基百科:

    遗传算法英语:genetic algorithm (GA) )是计算数学中用于解决最佳化的搜索算法,是进化算法的一种。进化算法最初是借鉴了进化生物学中的一些现象而发展起来的,这些现象包括遗传突变自然选择以及杂交等。

    具体怎么实现呢?其实也很好理解,给每个对象一个属性(也就是所谓的基因),再建立一套评判标准,来决定这种基因是好还是坏。为了得到更优化的结果,需要进行若干次进化。每一轮进化,会选中一些对象来杂交(一般使用轮盘选择,以保证性质优良的对象有更大概率杂交繁衍,但性质较为不良的也可以得到杂交的机会),再选中一些对象进行突变,以保证属性的多样性,最后再淘汰掉一些性质不良的对象,完成一次进化。

    本质上和模拟退火这类随机化算法是类似的,也就是玄学。也就是利用科学化的随机来逼近问题的最优解。对于不同的问题,需要调整不同的随机化参数以得到更好的结果。

    下面就一个具体的问题来说明一下代码的编写:

    借鉴的是:遗传算法实例-求解函数极值,感觉我只是把他翻译了一下emmmmmm…

    f(x)=x+10sin(5x)+7cos(4x)

    以上那个函数,求其在区间[-10,10]之间的最大值,不妨先画一下图:

    emmm,抖啊老哥。

    代码如下:

    #include<math.h>
    #include<string.h>
    #include<iostream>
    #include<stdio.h>
    #include<time.h>
    #include<algorithm>
    #include<sstream> //istringstream stm(string); stm >> x;
    #include<vector>
    #define INF 2139062143
    #define inf -2139062144
    #define ll long long
    #define Num 500
    #define Step 5000
    using namespace std;
    
    // double随机数生成函数
    double doubleram(double a,double b) {
        double temp = (double)(rand()%101)/101;
        return temp * (b - a) + a;
    }
    
    // 整形随机数生成函数
    int intram(int a,int b) {
        return (rand() % (b-a+1))+ a;
    }
    
    // 个体类
    struct indivdual {
        double x = 0.0,fitness = 0.0;
    };
    bool cmp(indivdual p1, indivdual p2) {
        return p1.fitness > p2.fitness;
    }
    vector<indivdual> indi;
    
    // 适应度函数
    double fitness(double x) {
        return x + 10.0 * sin(5.0 * x) + 7.0 * cos(4.0 * x);
    }
    
    // 初始化种群
    void initPopulation() {
        indi.clear();
        indivdual temp;
        for(int i = 0; i < Num; i++) {
            temp.x = doubleram(-10.0,10.0);
            temp.fitness = fitness(temp.x);
            indi.push_back(temp);
        }
    }
    
    // 杂交过程
    void crossover() {
        int t1 = intram(0,Num-1);
        int t2 = intram(0,Num-1);
        
        indivdual tempvec[4];
        tempvec[0] = indi[t1];
        tempvec[1] = indi[t2];
    
        indivdual child1,child2;
        child1.x = indi[t1].x * 0.9 + indi[t2].x * 0.1;
    //    if(child1.x >= 10.0 || child1.x <= -10.0)    printf("%llf
    ",child1.x);
        child1.fitness = fitness(child1.x);
        
        child2.x = indi[t1].x * 0.1 + indi[t2].x * 0.9;
    //    if(child2.x >= 10.0 || child2.x <= -10.0)    printf("%llf
    ",child2.x);
        child2.fitness = fitness(child2.x);
    
        tempvec[2] = child1;
        tempvec[3] = child2;
    
        sort(tempvec,tempvec + 4,cmp);
    
        indi[t1] = tempvec[0];
        indi[t2] = tempvec[1];
    
    }
    
    // 变异过程
    void mut() {
        int ind = intram(0,Num - 1);
        indi[ind].x = doubleram(-10.0,10.0);
        indi[ind].x = fitness(indi[ind].x);
    }
    
    int main() {
        srand((unsigned)time(NULL));
    //    for(int i = 0;i < 10;i++)
    //        printf("%llf
    ",ram(-10.0,10.0));
        initPopulation();
        int t = Step;
        while(t--) {
            double x = doubleram(0.0,1.0);
            if(x < 0.1) {
                mut();
                continue;
            }
            if(x < 0.75) {
                crossover();
                continue;
            }
        }
        
        sort(indi.begin(),indi.end(),cmp); 
        
        for(int i = 0;i < 5;i++){
            printf("    %llf    %llf
    ",indi[i].x,indi[i].fitness);
        } 
        
        return 0;
    }
  • 相关阅读:
    java内存模型
    类、对象和接口
    Python--数据存储:pickle模块的使用讲解
    Python--常用的内置函数
    Python--迭代器和生成器的定义和案例
    Python--作业2--对员工信息文件,实现增删改查操作
    Python--文本基本操作
    Python--字符串基本操作
    Python--字典基本操作
    Python--作业1--购物车程序
  • 原文地址:https://www.cnblogs.com/zinyy/p/9139147.html
Copyright © 2011-2022 走看看