DEAP是一个新颖的进化计算框架,用于快速原型设计和测试。它旨在使算法清楚和数据结构透明。 它可以在并行机制之间完美协调,例如多处理和SCOOP(简单并发性面向对象程序设计)。
DEAP包括以下特征:
- (1)在遗传算法中可以使用任何你能想到的表示,例如:列表 List,数组Array,集合 Set,字典 Dictionary,树 Tree,Numpy Array 等等。
- (2)基因编程使用前缀树:Loosely typed, Strongly typed(理解为稀疏类型和紧凑类型);自定义函数;
- (3)进化策略(包括CMA-ES):Covariance Matrix Adaptation Evolutionary Strategies的缩写,中文名称是协方差矩阵自适应进化策略
- (4)多目标优化:包括 NSGA-II, SPEA2, MO-CMA-ES;
- (5)多种群(多人口)共同进化;
- (6)评估的并行化(和更多);
- (7)名人堂,居住在人群中最好的人物;
- (8)检查点定期拍摄系统的快照;
- (9)基准模块包含最常用的测试功能;
- (10)进化的家谱(与NetworkX兼容)
- (11)其他算法的例子:PSO,差分演化,分布算法估计;
Core 核心模块:
- : 基本结构。包含Toolbox(存储自定的EA运行所需的对象和操作), Fitness(个体的适应度的基类)等。
- : 允许通过动态添加属性或函数来创建符合问题需求的类,常用来创建个体。
- :包含多种选择(selection)操作函数,遗传算子操作函数(多种crossover, mutation)等。
单目标优化:
- 在创建单目标优化问题时, 用来指示最大化和最小化。此处 即代表问题是一个最小化问题,对于最大化,应将 改为正数,如 。
- 另外即使是单目标优化, 也需要是一个 ,以保证单目标和多目标优化时数据结构的统一。
- 对于单目标优化问题,weights 的绝对值没有意义,只要符号选择正确即可。
- 多目标优化:
- 对于多目标优化问题, 用来指示多个优化目标之间的相对重要程度以及最大化最小化。如示例中给出的 代表对第一个目标函数取最小值,对第二个目标函数取最大值。
直接用实数对变量进行编码。优点是不用解码,基因表达非常简洁,而且能对应连续区间。但是实数编码后搜索区间连续,因此容易陷入局部最优
来产生随机数,如果喜欢 numpy 的,也可以用 np.random.rand 代替,DEAP 的灵活性还是很强的。
以随机生成一个长度为 10 的二进制编码为例,本身 DEAP 库中没有内置的 Binary encoding,可以借助 Scipy 模块中的伯努利分布来生成一个二进制序列。
通常在求解顺序问题时用到,例如TSP问题。序列编码中的每个染色体都是一个序列。
一般种群的 DEAP 实现:
以二进制编码为例,以下代码可以生成由10个长度为5的随机二进制编码个体组成的一般种群:
评价部分是根据任务的特性高度定制的,DEAP 库中并没有预置的评价函数模版。
❗️ 在使用 DEAP 时,需要注意的是,无论是单目标还是多目标优化,评价函数的返回值必须是一个 类型。
zip 函数详解:
环境选择也就是重插入(Reinsertion),在选择、交叉和突变之后,得到的育种后代族群规模与父代相比可能增加或减少。为保持族群规模,需要将育种后代插入到父代中,替换父代种群的一部分个体,或者丢弃一部分育种个体。
- 重插入分为全局重插入(Global reinsertion)和本地重插入(Local reinsertion)两种,后者只有在使用含有本地邻域的算法时使用。常见的全局重插入操作有以下四种:
- 完全重插入(Pure reinsertion): 产生与父代个体数量相当的配种个体,直接用配种个体生成新一代族群。
- 均匀重插入(Uniform reinsertion): 产生比父代个体少的配种个体,用配种个体随机均匀地替换父代个体。
- 精英重插入(Elitist reinsertion): 产生比父代个体少的配种个体,选取配种后代中适应度最好的一些个体,插入父代中,取代适应度较低的父代个体。
- 精英保留重插入(Fitness-based reinsertion): 产生比父代个体多的配种个体,选取其中适应度最大的配种个体形成新一代族群。
通常来说后两种方式由于精英保留的缘故,收敛速度较快,因此比较推荐。
DEAP 中没有设定专门的 操作,可以用选择操作选择中的 来对育种族群和父代族群进行操作。
通常情况下,想要在优化过程中编辑数据。Statistic 模块 可以在任何设计好的目标上改变一些本不可改变的数据。为了达到这个目的,需要使用与工具箱中完全相同的语法在静态数据中注册统计函数。
- 使用 的第一个参数作为统计对象。这个 必须支持一个可以在之后被应用到数据上的函数从而得到统计结果。上面的例子使用了 中每一个元素的属性。
- 这些统计函数现在被注册了。 函数希望 作为第一个属性以及一个在向量上操作的函数 作为第二个属性。在调用时,任何在后面的元素都会传到函数上。统计目标的创建已经完成。
当使用一个预定义的算法时,例如 ,之前创建的统计目标可以作为算法的属性。
统计将会在每一次迭代中自动的进行计算。详细参数在优化过程中会打印在屏幕上。一旦算法返回,最终的种群和一个 将会返回。在下面可以看到更详细的信息。
- 当编写自己的算法时,包含统计是十分简单的。只用在需要的目标上编写统计。例如,在一个给定种群 上编写统计需要调用 方法完成。
- 用于编辑函数的属性必须在一个迭代元素中,这样这些 才会被调用。
- 这里,种群包含了许多个体。统计目标将会在每一个个体上调用 函数获取 属性的值。这个结果数组的值最终会给到每一个统计函数并且将结果输入到 字典中,每一个 都会与相应的函数相关联。
- 在 main 函数中把这个命令放在更新种群之后就可以得到一系列的统计值:标准差-最大值-平均值-最小值。
正如统计可以通过 函数直接进行计算,所有的目标将会通过默认 的属性联合在一起。接下来,一个需要明确的事情是每一个 的操作。这会通过给予 一个额外的属性作为注册函数达成。
计算种群个体的不同属性也是可以的。例如,在遗传程序设计中除了对适应度统计之外,对表达式树的高度统计也是常见的。一个可以使用多元 目标的函数是 。

两个统计目标使用与之前相同的方式被创建。第二个目标将会通过调用 获取每一个个体的长度。一旦创建完成,统计目标将会被给到 函数中,这里地元素都是使用 来定义的。这些 将会提供不同统计量的定义。这些统计函数仅仅可以在 被注册一次
多元统计目标可以给到一个算法当中,或者他们可以以相似的形式运用到单一统计中
在这种情况下, 就是一个字典的字典类型 (嵌套)。第一个等级包括一些统计信息的关键字,第二个等级包括一些预制件相似的简单统计目标
- 方法采用可变数字作为参数,每一个参数作为数据都会被记录。
- 在最后一个例子中,保存了一代,结果的数量和任何包含在 中的东西都会通过这个方法产生统计学目标。所有的记录都会被保存在 中,直到它被销毁。在一些列的记录之后,可能会想去调用 中的信息
方法提供了一种方法去调用所有的与 中 相关的信息。这个方法采取了可变数量的字符串元素,就是在 或者 中的 。这里,我们调用代数和平均适应度,使用一个单独的 进行调用。一个 是一个可选择的目标(只要插入数据是可选择的),它可以提供一种很好的方法去存储演化过程中的统计参数。
- 注意: 每一个算法返回的 包含着每一代的信息和适应度在整个进化过程中的数目。
一个 可以打印在屏幕或者文档中。它的 方法在第一个 中返回每一个 的头,同时使用这些 完成 。按照行插入的时间顺序排列,而列将处于未定义的顺序。指定顺序的最简单方法是将 属性设置为指定列顺序的字符串列表。
结果为:
每一个列名包含了没有明确记录的列名,它将会被空着,就像 一样。
一个 同样包含尚未打印的条目的流属性。
可以与字典类型合作,返回 目标。事实上,它将在 中为每一个包含在字典中的子字典记录数据,接下来,一个 multi 可以被看做一个
与列排序不同的一点是,当我们明确 的顺序时,它们的内容如下
(看起来就是 包含 也包含这些,然后它们的输出就都分别包含这些)
这些数据的调用同样也可以通过 进行调用
- 迭代次数、最小适应度和平均尺寸就可以按照时间顺序获得了。如果一些数据不可用,一个 会出现在向量中。
在优化过程中最常用的操作就是在图中显示进化过程。 可以有效地执行这一操作。使用选择方法,我们可以调用需要的数据并且使用 去绘制图形。
DEAP 官方文档给出的一个简单GP例子 (符号回归问题):Symbolic Regression Problem: Introduction to GP
令期望曲线为:
并在 [-1, 1] 区间设置 20 个等分点来评估适应度(fitness),来寻找一个 GP 生成的最拟合的表达式。
以下是对它的讲解,代码部分的 comment 当中也加入了对代码过程和操作的解读。
- 注: Primitive set 为 function set 和 terminal set 的并集。primitives 不是指 functions + terminals,primitives 仅仅指 functions
- 不指定节点的输入和输出类型(type)。常用于较为单一处理类型的问题,比如我们现在看的这个只用到浮点数 float 的符号回归。
创建 primitive set 使用 gp.PrimitiveSet(名称, inputs数量, prefix=‘ARG’)
添加函数节点:gp.addPrimitive(函数, 参数数量, name=None)
添加终止符: gp.addTerminal(终止符, name=None)
- 指定每一个节点输入和输出的类型 (它真的很严格 ! )。在Srong Typed GP的随机过程中,如果一个下层节点的输出类型和它连接的一个上层节点输入类型不一致,那么存在这种连接的树会被丢弃。
创建 primitive set 使用 gp.PrimitiveSetTyped(名称, 输入types, 返回/输出type,prefix=‘ARG’)
添加函数节点: addPrimitive(函数, 输入types, 返回/输出type, name=None)
添加终止符: addTerminal(终止符, 返回/输出type, name=None)
gp 模块方法官方文档:https://deap.readthedocs.io/en/master/api/gp.html
2.1 Primitive Set 参数说明
- pset.arguments:自变量列表
- pset.primitives:存储树中所有的函数节点,node
- pset.terminals:存储树中所有的终端节点
- node.ret:节点类型
- node.args:节点参数
允许我们动态添加函数、属性来创建自己的自定类型。
- 中,至少需要用 创建两个类型:个体类和它对应的适应度的类。个体类表现为一个 ,适应度表现为 base 模块中的 Fitness 基类。
- 我们一会用到的 fitness function 使用均方误差来评估个体适应度,越小的值表明个体越优良,所以我们想要一个 minimizing fitness。
creator 模块方法官方文档: https://deap.readthedocs.io/en/master/api/creator.html
base 模块官方文档: https://deap.readthedocs.io/en/master/api/base.html

“注册一些工具”:使用 将自定函数填充到工具箱 (base.Toolbox()) 当中,在之后的算法部分可以通过 toolbox.name 调用 ☆☆☆。算法部分,暨遗传迭代的实行部分,可以自定、也可使用 algorithms 模块中提供的算法方法。使用 algorithms 模块中的方法时,工具箱注册的函数名称固定,如适应度评估必须注册为 , 遗传操作交叉注册为 ,变异注册为 等。
对于 register 的过程理解,我们来体会一下在代码段中的两个注册例子:
Example 1 :
过程解读: 将 函数命名为 “mate”,放入工具箱中。可以看成一个 重命名的过程。
执行时,调用工具箱的 “mate” 即通过调用 ,便会直接调用 ,进行交叉。
注意: 现在这句里只有两个参数,名称和被注册函数,但并不代表不需要给 gp.cxOnePoint 这个被注册函数某些参数。 中包含一个偏函数,可以让我们在之后再以字典方式传入参数。下面的例句同样验证了这一点。
Example 2 :
过程解读: 这是种群列表的注册,注册名称 “”, 为被注册函数,后面紧跟的 为 的参数。 还应该接收一个数量 为参数才能正常执行,可以看到这行语句没有任何参数 ,但在 6. Launching 部分(本文后面) 的语句 中,参数 以字典形式传入了注册函数 population中。 执行 时, 被调用,它会进行 300 次调用 并将返回的结果填入 结构的操作 (toolbox.population() 返回一个list)。同理, 调用 ,将 返回值填充入 类型。
后面使用的 evolutionary algorithms 会抽调这些注册的操作。
tools模块方法官方文档: https://deap.readthedocs.io/en/master/api/tools.html
设置统计项,注册到统计容器 中,在后面能够通过 观察运行过程中每一代的数据。
初始化、运行。
存储最适合的个体,传入参数为 1 则其包含一个最适合的个体。
这里使用 模块的 ,一个最基础的算法。传入参数分别为种群对象,toolbox 工具箱,crossover 概率,mutate 概率,演化多少代,统计容器,名人堂,verbose=true 设置显示 statistics。
算法会自动抽调传入的 里注册过的工具, 中必须按特定名称注册对应操作的工具,如 “mate”, “mutate”, “select”, “evaluate” 这些一定要有,不能随意起名字…
可以在运行结束后通过查看名人堂 来找到 生成的表达式。如下直接打印出来:
之前设置名人堂数量为 1,所以直接找 hof.items[0] 就可以。将打印出的语法树转为表达式为
,GP 找到的最优解即为我们的期望曲线。
algorithms 模块方法官方文档:https://deap.readthedocs.io/en/master/api/algo.html
(1)首先创建 primitive set:函数集 + 终点集
(2)根据上述 primitive set 创建表达式
- 注意:步骤(2)只是创建一个gp表达式、编译表达式的示例,实际使用deap库时,直接进行步骤(3)即可。
(3)创建个体(individual)
[1] 【遗传编程/基因规划】python DEAP框架学习笔记
github 源码: https://gitcode.net/mirrors/DEAP/deap?utm_source=csdn_github_accelerator
DEAP 文档: http://deap.gel.ulaval.ca/doc/dev/index.html
DEAP 中文介绍: https://www.jianshu.com/p/8fa044ed9267
Poli, Riccardo, et al. A Field Guide to Genetic Programming. Lulu Press, 2008.

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容,请联系我们,一经查实,本站将立刻删除。
如需转载请保留出处:https://51itzy.com/kjqy/158557.html