遗传算法(GA)

找一个好的fitness方程 

所有的遗传算法 (Genetic Algorithm), 后面都简称 GA, 我们都需要一个评估好坏的方程, 这个方程通常被称为 fitness. 在今天的问题中, 我们找到下面这个曲线(y=sin(10*x)*x + cos(2*x)*x )当中的最高点. 那么这个 fitness 方程就很好定, 越高的点, fitness 越高.

如果这个曲线上任一点的 y 值是 pred 的话, 我们的 fitness 就是下面这样:

def get_fitness(pred):
    return pred

DNA 编码 

在 GA 中有基因, 为了方便, 我们直接就称为 DNA 吧. GA 中第二重要的就是这 DNA 了, 如何编码和解码 DNA, 就是你使用 GA 首先要想到的问题. 传统的 GA 中, DNA 我们能用一串二进制来表示, 比如:

DNA1 = [1, 1, 0, 1, 0, 0, 1]
DNA2 = [1, 0, 1, 1, 0, 1, 1]

为什么会要用二进制编码, 我们之后在下面的内容中详细说明这样编码的好处. 但是长成这样的 DNA 并不好使用. 如果要将它解码, 我们可以将二进制转换成十进制, 比如二进制的 11 就是十进制的 3. 这种转换的步骤在程序中很好执行. 但是有时候我们会需要精确到小数, 其实也很简单, 只要再将十进制的数浓缩一下就好. 比如我有 1111 这么长的 DNA, 我们产生的十进制数范围是 [0, 15], 而我需要的范围是 [0, 5], 我们就将 [0, 15] 缩放到 [0,5] 这个范围就好.

def translateDNA(pop):
    return pop.dot(2 ** np.arange(DNA_SIZE)[::-1]) / float(2**DNA_SIZE-1) * X_BOUND[1]

注意, 这里的 pop 是一个储存二进制 DNA 的矩阵, 他的 shape 是这样 (pop_size, DNA_size).

进化啦 

进化分三步:

  • 适者生存 (selection)
  • DNA 交叉配对 (crossover)
  • DNA 变异 (mutation)

我们用 python 的三个功能, 一个循环表示:

# 种群 DNA
pop = np.random.randint(2, size=(POP_SIZE, DNA_SIZE))

F_values = F(translateDNA(pop))
fitness = get_fitness(F_values)
pop = select(pop, fitness)      # 按适应度选 pop
pop_copy = pop.copy()           # 备个份
for parent in pop:
    child = croseeover(parent, pop_copy)
    child = mutate(child)
    parent[:] = child           # 宝宝变大人

适者生存的 select() 很简单, 我们只要按照适应程度 fitness 来选 pop 中的 parent 就好.fitness 越大, 越有可能被选到.

def select(pop, fitness):
    idx = np.random.choice(np.arange(POP_SIZE), size=POP_SIZE, replace=True,
                           p=fitness/fitness.sum()) # p 就是选它的比例
    return pop[idx]

接下来进行交叉配对. 方式很简单. 比如这两个 DNA, Y 的点我们取 DNA1 中的元素, N 的点取 DNA2 中的. 生成的 DNA3 就有来自父母的基因了.

DNA1 = [1, 1, 0, 1, 0, 0, 1]
       [Y, N, Y, N, N, Y, N]
DNA2 = [1, 0, 1, 1, 0, 1, 1]

DNA3 = [1, 0, 0, 1, 0, 0, 1]

而 python 写出来也很方便, 从 pop_copy 中随便选一个当另一个父辈 和 parent 进行随机的 crossover:

def crossover(parent, pop):
    if np.random.rand() < CROSS_RATE:
        i_ = np.random.randint(0, POP_SIZE, size=1)  # select another individual from pop
        cross_points = np.random.randint(0, 2, DNA_SIZE).astype(np.bool)  # choose crossover points
        parent[cross_points] = pop[i_, cross_points]  # mating and produce one child
    return parent

mutation 就更好写了, 将某些 DNA 中的 0 变成 11 变成 0.

def mutate(child):
    for point in range(DNA_SIZE):
        if np.random.rand() < MUTATION_RATE:
            child[point] = 1 if child[point] == 0 else 0
    return child

总结如下:

1. 选择的作用:优胜劣汰,适者生存;

2. 交叉的作用:保证种群的稳定性,朝着最优解的方向进化;

3. 变异的作用:保证种群的多样性,避免交叉可能产生的局部收敛。

全部流程如下:

for _ in range(N_GENERATIONS):
    F_values = F(translateDNA(pop))    # compute function value by extracting DNA

    # something about plotting
    if 'sca' in globals(): sca.remove()
    sca = plt.scatter(translateDNA(pop), F_values, s=200, lw=0, c='red', alpha=0.5); plt.pause(0.05)

    # GA part (evolution)
    fitness = get_fitness(F_values)
    print("Most fitted DNA: ", pop[np.argmax(fitness), :])
    pop = select(pop, fitness)
    pop_copy = pop.copy()
    for parent in pop:
        child = crossover(parent, pop_copy)
        child = mutate(child)
        parent[:] = child       # parent is replaced by its child
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
在MATLAB中,遗传算法可以通过ga函数来实现。这个函数主要用于解决优化问题,特别是在求解Bin Packing问题中,可以利用遗传算法来进行求解。 在使用ga函数时,可以通过设置一些参数来控制算法的行为。例如,可以使用gaoptimset函数来设置迭代次数、种群大小、是否并行以及函数是否向量化等参数。例如,可以设置迭代次数为200,种群大小为50,是否并行为true,并指定函数是否向量化为'on'。 另外,在使用遗传算法求解问题时,可以使用fprintf函数将结果输出到文件中。例如,可以使用fprintf函数将变量x的数值按照一定的格式输出到文件中。这样可以方便地查看求解结果。 综上所述,遗传算法ga函数是MATLAB中用于求解优化问题的一个函数,可以通过设置参数来控制算法的行为,并使用fprintf函数将结果输出到文件中。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* [利用遗传算法(GA)、粒子群算法(PSO)、萤火虫算法(FA)和入侵杂草优化(IWO)求解Bin Packing问题的MATLA](https://download.csdn.net/download/weixin_39168167/88251667)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 33.333333333333336%"] - *2* [matlab 遗传算法 ga函数实现并行](https://download.csdn.net/download/weixin_38751177/14885265)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 33.333333333333336%"] - *3* [matlab遗传算法ga函数](https://blog.csdn.net/weixin_39789792/article/details/116158890)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 33.333333333333336%"] [ .reference_list ]
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值