Code created last time https://qiita.com/nmat0031785/items/ceea6f78ab71e9956fce
The previously used algorithms.eaSimple
can only leave statistics for each generation.
Improve so that the design variables and fitness of all individuals can be retained.
First, the fitness is calculated only for the initial individual. After that, the design variable, fitness, generation (0 because it is the initial generation), and individual number are saved in pd.DataFrame.
sample_GA.py
#Generate an early population
pop = toolbox.population_guess()
#Evaluation of fitness of early individuals
fitnesses = toolbox.map(toolbox.evaluate, pop)
for ind, fit in zip(pop, fitnesses):
ind.fitness.values = fit
fits = [ind.fitness.values[0] for ind in pop]
#Store initial individuals in logbook
logbook = pd.DataFrame([])
t1 = pd.DataFrame(pop)
t1.columns = ["x1", "x2"]
t1 = t1.assign(fits=fits, generation=0, ids=range(len(pop)))
logbook = logbook.append(t1)
Enter the evolution loop. With offspring = toolbox.select (pop, POP_SIZE)
, the individuals for POP_SIZE``` are reselected from the initial population
pop```. This makes it possible to change the number of initial populations and evolutionary loop populations. Random numbers are given to individuals of each generation by for minutes, and individuals caught in ``
CX_PB and `` `MUT_PB
are crossed and targeted for mutation. After that, the fitness is re-evaluated for the new individual and added to pd.DataFrame.
sample_GA.py
#Parameters
N_GEN = 20 #Number of repeating generations
POP_SIZE = 100 #Population in the population
CX_PB = 0.8 #Crossing probability
MUT_PB = 0.05 #Mutation probability
#Evolution loop start
g = 0
while g < N_GEN:
g = g + 1
#Selection and replication of next-generation individuals
offspring = toolbox.select(pop, POP_SIZE)
offspring = list(map(toolbox.clone, offspring))
#Crossing
for child1, child2 in zip(offspring[::2], offspring[1::2]):
#Select individuals to cross
if random.random() < CX_PB:
toolbox.mate(child1, child2)
#Crossed individuals remove fitness
del child1.fitness.values
del child2.fitness.values
#Mutation
for mutant in offspring:
#Select an individual to mutate
if random.random() < MUT_PB:
toolbox.mutate(mutant)
#Mutant individuals remove fitness
del mutant.fitness.values
#Reassess the fitness of individuals whose fitness has been removed
invalid_ind = [ind for ind in offspring if not ind.fitness.valid]
fitnesses = map(toolbox.evaluate, invalid_ind)
for ind, fit in zip(invalid_ind, fitnesses):
ind.fitness.values = fit
#Update population with new generation population
pop[:] = offspring
#Extraction of fitness of all new generation individuals
fits = [ind.fitness.values[0] for ind in pop]
#Store in logbook
t1 = pd.DataFrame(pop)
t1.columns = ["x1", "x2"]
t1 = t1.assign(fits=fits, generation=g, ids=range(POP_SIZE))
logbook = logbook.append(t1)
#debug
print(t1)
terminal
・
・
・
-- Generation 20 --
x1 x2 fits generation ids
0 -1.582142 -3.130247 -106.764537 20 0
1 -1.582142 -3.130247 -106.764537 20 1
2 -1.582142 -3.130247 -106.764537 20 2
3 -1.582142 -3.130247 -106.764537 20 3
4 -1.582142 -3.130247 -106.764537 20 4
.. ... ... ... ... ...
95 -1.582142 -3.130247 -106.764537 20 95
96 -1.582142 -3.130247 -106.764537 20 96
97 -1.582142 -3.130247 -106.764537 20 97
98 -1.582142 -3.130247 -106.764537 20 98
99 -1.582142 -3.130247 -106.764537 20 99
[100 rows x 5 columns]
Save the result as CSV.
sample_GA.py
logbook.to_csv("result.csv", sep=",", index=None, header=None)
Output of design variables and fitness of each individual. Next time until the visualization of the results.
Recommended Posts