代码
import random
class GeneticAlgorithm:
def __init__(self, population_size, chromosome_length, mutation_rate, generations):
"""
初始化遗传算法参数
:param population_size: 种群大小
:param chromosome_length: 染色体长度(二进制编码位数)
:param mutation_rate: 变异概率
:param generations: 迭代次数
"""
self.pop_size = population_size
self.chromo_len = chromosome_length
self.mutation_rate = mutation_rate
self.generations = generations
self.population = []
# 初始化种群
self.initialize_population()
def initialize_population(self):
"""生成随机的二进制编码种群"""
self.population = [
''.join(random.choice('01') for _ in range(self.chromo_len))
for _ in range(self.pop_size)
]
@staticmethod
def decode(binary_str, search_min=0, search_max=15):
"""将二进制字符串解码为实际数值"""
int_val = int(binary_str, 2)
return search_min + (int_val / (2 ** len(binary_str) - 1)) * (search_max - search_min)
def fitness_function(self, x):
"""适应度函数(值越小越好,这里取倒数)"""
return 1 / (x ** 2 + 1e-6) # 避免除以0
def tournament_selection(self, tournament_size=3):
"""锦标赛选择"""
selected = []
for _ in range(self.pop_size):
# 随机选择 tournament_size 个个体进行竞争
competitors = random.sample(list(zip(self.population, self.fitness_scores)), tournament_size)
# 选择适应度最高的(因为我们的适应度函数是倒数)
winner = max(competitors, key=lambda x: x[1])[0]
selected.append(winner)
return selected
def crossover(self, parent1, parent2):
"""单点交叉"""
point = random.randint(1, self.chromo_len - 1)
child1 = parent1[:point] + parent2[point:]
child2 = parent2[:point] + parent1[point:]
return child1, child2
def mutate(self, individual):
"""按位变异"""
mutated = list(individual)
for i in range(len(mutated)):
if random.random() < self.mutation_rate:
mutated[i] = '0' if mutated[i] == '1' else '1'
return ''.join(mutated)
def run(self):
"""执行遗传算法"""
for gen in range(self.generations):
# 计算适应度
self.fitness_scores = [
self.fitness_function(self.decode(ind))
for ind in self.population
]
# 选择
selected = self.tournament_selection()
# 交叉生成新种群
new_population = []
for i in range(0, self.pop_size, 2):
parent1 = selected[i]
parent2 = selected[i + 1] if i + 1 < self.pop_size else selected[0]
child1, child2 = self.crossover(parent1, parent2)
new_population.extend([child1, child2])
# 变异
self.population = [self.mutate(ind) for ind in new_population[:self.pop_size]]
# 跟踪最佳解
best_ind = max(zip(self.population, self.fitness_scores), key=lambda x: x[1])
best_x = self.decode(best_ind[0])
print(f"Generation {gen + 1}: Best x = {best_x:.4f}, f(x) = {best_x ** 2:.4f}")
# 返回最终结果
best_ind = max(zip(self.population, self.fitness_scores), key=lambda x: x[1])
return self.decode(best_ind[0])
# 参数设置
ga = GeneticAlgorithm(
population_size=20, # 种群大小
chromosome_length=8, # 二进制编码位数(精度更高)
mutation_rate=0.01, # 变异概率
generations=30 # 迭代次数
)
# 运行算法
best_solution = ga.run()
print(f"\nOptimal Solution: x = {best_solution:.4f}, f(x) = {best_solution ** 2:.4f}")
输出示例
Generation 1: Best x = 1.4118, f(x) = 1.9931
Generation 2: Best x = 3.7647, f(x) = 14.1730
Generation 3: Best x = 0.5294, f(x) = 0.2803
Generation 4: Best x = 0.2941, f(x) = 0.0865
Generation 5: Best x = 0.1765, f(x) = 0.0311
Generation 6: Best x = 0.0000, f(x) = 0.0000
Generation 7: Best x = 0.0000, f(x) = 0.0000
Generation 8: Best x = 0.0000, f(x) = 0.0000
Generation 9: Best x = 3.7647, f(x) = 14.1730
Generation 10: Best x = 0.0000, f(x) = 0.0000
Generation 11: Best x = 0.0000, f(x) = 0.0000
Generation 12: Best x = 0.0000, f(x) = 0.0000
Generation 13: Best x = 0.0000, f(x) = 0.0000
Generation 14: Best x = 7.5294, f(x) = 56.6920
Generation 15: Best x = 0.0000, f(x) = 0.0000
Generation 16: Best x = 0.0000, f(x) = 0.0000
Generation 17: Best x = 0.1176, f(x) = 0.0138
Generation 18: Best x = 0.0000, f(x) = 0.0000
Generation 19: Best x = 0.0000, f(x) = 0.0000
Generation 20: Best x = 0.0000, f(x) = 0.0000
Generation 21: Best x = 0.0000, f(x) = 0.0000
Generation 22: Best x = 0.0000, f(x) = 0.0000
Generation 23: Best x = 0.0000, f(x) = 0.0000
Generation 24: Best x = 0.0000, f(x) = 0.0000
Generation 25: Best x = 0.0000, f(x) = 0.0000
Generation 26: Best x = 0.0000, f(x) = 0.0000
Generation 27: Best x = 0.0000, f(x) = 0.0000
Generation 28: Best x = 0.0000, f(x) = 0.0000
Generation 29: Best x = 0.0000, f(x) = 0.0000
Generation 30: Best x = 0.0000, f(x) = 0.0000
Optimal Solution: x = 0.0000, f(x) = 0.0000