优化算法相关 实时绘制训练过程中损失和准确率的变化趋势
安装optproblems 和 fastprogress
1.pip install optproblems
https://ls11-www.cs.tu-dortmund.de/people/swessing/optproblems/doc/
该软件包包含一些用于黑盒优化的常见基准测试问题。
包含的测试问题:
二进制问题OneMax,LeadingOnes和LeadingOnesTrailingZeros以及用于多模式问题的三个实例生成器
CEC 2005单目标问题集
CEC 2007多目标问题集
Dixon-Szegö系列进行全局优化
DTLZ问题1-7
多峰模型2
步行鱼小组(WFG)工具包
ZDT集合用于多目标优化
- Binary problems OneMax, LeadingOnes, and LeadingOnesTrailingZeros and three instance generators for multimodal problems
- CEC 2005 collection of single-objective problems
- CEC 2007 collection of multiobjective problems
- Dixon-Szegö collection for global optimization
- DTLZ problems 1-7
- Multiple-Peaks Model 2
- Walking Fish Group (WFG) toolkit
- ZDT collection for multiobjective optimization
此程序包的基础结构还可用于将您自己的(实际)优化问题包装在问题基类中。这样做的原因可能是以下功能:
支持单目标和多目标问题
通常,不对搜索空间做任何假设
评估自动计数
可以通过multiprocessing(.dummy)使用真正的并行性或并发性
提供用于检查绑定约束并修复连续优化中违反约束的功能
可选:检测并随后避免重复评估
还包括一些实际问题。(在测试问题上配置梯度法,超立方体中点的均匀性优化)
依存关系
此程序包的某些模块对第三方程序包具有其他依赖性。但是,在安装过程中不会强制执行这些操作,以免妨碍基本模块的使用,而基本模块将始终没有依赖性。
2. pip install liveloseplot
这款工具用于实时绘制训练时的损失和准确率,方便好用,不需要自己另外再写 plot 函数。Keras
和 PyTorch
中都可以使用
from livelossplot import PlotLossesKeras
model.fit(X_train, Y_train,
epochs=10,
validation_data=(X_test, Y_test),
callbacks=[PlotLossesKeras()],
verbose=0)
3. pip install fastprogress
from fastprogress import master_bar, progress_bar
from time import sleep
mb = master_bar(range(10))
for i in mb:
for j in progress_bar(range(100), parent=mb):
sleep(0.01)
mb.child.comment = f'second bar stat'
mb.first_bar.comment = f'first bar stat'
mb.write(f'Finished loop {i}.')
#mb.update_graph(graphs, x_bounds, y_bounds)
一个例子:
from optproblems import *
from optproblems import cec2005
import numpy as np
import random
import bisect
import matplotlib.pyplot as plt
from fastprogress import progress_bar
def get_best_possible_fitness(problem):
optimal_solutions = problem.get_optimal_solutions()
an_optimal_solution = optimal_solutions[0]
problem.evaluate(an_optimal_solution)
return an_optimal_solution.objective_values
class GA:
"""
An implementation of Genetic Algorithm, pioneered by John Holland.
The population consists of fixed length vectors of real numbers and is initialised
using a uniform distribution of random numbers. It uses two point crossover, tournament
selection and Gaussian convolution for mutation.
Attributes
----------
problem : obj
The cec2005 problem to be attempted
pop_size : int
The size of the population
vector_length : int
The dimensions of the problem, should be the same used when creating the problem object
tournament_size: int, optional
The number of individuals competing in each tournament
mutation_rate: float, optional
The likelyhood of mutation for each child
mutation_scale: int, optional
The size of the mutation used. i.e the standard deviation of the gaussian
Public Methods
-------
evolve(num_iterations)
Evoles the population for a number of given iterations
"""
def __init__(self, problem, pop_size, vector_length, tournament_size=2, mutation_rate=0.3, mutation_scale=12):
self.problem = problem
self.vector_length = vector_length
self.pop_size = pop_size
self.tournament_size = tournament_size
self.mutation_rate = mutation_rate
self.mutation_scale = mutation_scale
self.current_population = np.random.rand(self.pop_size, self.vector_length)
def evolve(self, num_iterations=200):
"""Evolves the population for a given number of iterations
Parameters
----------
num_iterations : int, optional
The number of generations before stopping evolving
Returns
-------
results : list
A list of the best fitness at each generation
found_global_min_at : int
The position at which the global min was found at, return -1 if not found
"""
results = []
found_global_min_at = -1
best_possible_fitness = get_best_possible_fitness(self.problem)
for i in range(num_iterations):
best_index, fitnesses = self.find_current_best(self.current_population)
results.append(fitnesses[best_index])
if math.isclose(best_possible_fitness, fitnesses[best_index], rel_tol=1e-1):
if found_global_min_at == -1:
found_global_min_at = i
self.current_population = self.update_population(fitnesses)
return results, found_global_min_at
def update_population(self, fitnesses):
"""Performs one generational update of Genetic Algorithm"""
next_population = np.empty((self.pop_size, self.vector_length))
for i in range(int(self.pop_size / 2)):
parent_a = self.tournament_select_with_replacement(self.current_population)
parent_b = self.tournament_select_with_replacement(self.current_population)
child_a, child_b = self.crossover(parent_a, parent_b)
next_population[i] = self.mutate(child_a)
position_child_b = i + (self.pop_size / 2)
next_population[int(position_child_b)] = self.mutate(child_b)
next_population = np.clip(next_population, self.problem.min_bounds, self.problem.max_bounds)
return next_population
def assess_fitness(self, individual):
"""Determines the fitness of an individual using the given problem"""
solution = Individual(individual)
self.problem.evaluate(solution)
return solution.objective_values
def find_current_best(self, population):
"""Evaluates a given population and returns the fittest individual"""
fitnesses = [self.assess_fitness(x) for x in population]
best_value = min(fitnesses)
best_index = fitnesses.index(best_value)
return best_index, fitnesses
def tournament_select_with_replacement(self, population):
"""Competes a number of challengers and returns the fittest one"""
challengers_indexes = np.random.choice(population.shape[0], self.tournament_size, replace=True)
challengers = population[challengers_indexes]
best_index, _ = self.find_current_best(challengers)
return challengers[best_index]
def crossover(self, parent_a, parent_b):
"""Performs two point crossover on two parents"""
l = parent_a.shape[0]
c, d = random.randint(0, l), random.randint(0, l)
# Flip if c greater than d
if (c > d): d, c = c, d
if (c == d): d += 1
temp = np.copy(parent_a)
child_a = np.concatenate([parent_a[0:c], parent_b[c:d], parent_a[d:]])
child_b = np.concatenate([parent_b[0:c], temp[c:d], parent_b[d:]])
return child_a, child_b
def mutate(self, child):
"""May mutate a child using Gaussian convolution"""
if self.mutation_rate >= random.uniform(0, 1):
size = self.current_population.shape[1]
mutation_value = np.random.normal(0, self.mutation_scale, size)
child = child + mutation_value
return child
def get_mean(tests):
return np.mean(np.array(tests), axis=0)
##################################
def test():
size, num_iterations = 50, 200
vector_length = 10
problem = cec2005.F1(vector_length)
pso_fitnesses = []
pso_found_global_best_results = []
ga_fitnesses = []
ga_found_global_best_results = []
for j in progress_bar(range(10)):
pso = PSO(problem, size, vector_length)
fitness, pso_found_global_best = pso.improve(num_iterations)
pso_found_global_best_results.append(pso_found_global_best)
pso_fitnesses.append(fitness)
ga = GA(problem, size, vector_length)
fitness, ga_found_global_best = ga.evolve(num_iterations)
ga_found_global_best_results.append(ga_found_global_best)
ga_fitnesses.append(fitness)
pso_mean_fitnesses = get_mean(pso_fitnesses)
ga_mean_fitnesses = get_mean(ga_fitnesses)
best_possible_fitness = get_best_possible_fitness(problem)
best_fitnesses = np.full_like(pso_mean_fitnesses, best_possible_fitness)
fig, ax = plt.subplots()
ax.plot(best_fitnesses, label="Global best")
ax.plot(pso_mean_fitnesses, label="PSO")
ax.plot(ga_mean_fitnesses, label="GA")
title = 'F1'
# ax.set_yscale('log')
plt.title(f'Mean fitness for CEC2005 Function {title}')
legend = ax.legend(loc='upper center', shadow=True)
# plt.ylim(0,1)
plt.ylabel('Fitness')
plt.xlabel('Iterations')
plt.show()
3 CEC2005问题
这套25个测试问题是为2005年9月2日至5日在英国爱丁堡举行的进化计算大会(CEC)上的实参优化特别会议而编写的。数学定义在[Suganthan2005]中给出。 此外,还为参与者提供了C,Java和Matlab的实现。 该代码是纯Python中Java代码的重新实现。
已用原始代码分发的测试数据验证了此实现的正确性。 根据特别会议的指南,对于此数据,对于参考目标值y和此处计算的值
[Suganthan2005] | (1, 2) P. N. Suganthan, N. Hansen, J. J. Liang, K. Deb, Y.-P. Chen, A. Auger, and S. Tiwari. Problem Definitions and Evaluation Criteria for the CEC 2005 Special Session on Real-Parameter Optimization. Technical Report, Nanyang Technological University, Singapore, May 2005 and KanGAL Report #2005005, IIT Kanpur, India. http://web.mysites.ntu.edu.sg/epnsugan/PublicSite/Shared%20Documents/CEC2005/Tech-Report-May-30-05.pdf |