best for now RMSE: 30.937

This commit is contained in:
2025-11-07 00:08:08 +03:00
parent cb2b031e9c
commit cfae423f11
4 changed files with 140 additions and 10 deletions

View File

@@ -37,3 +37,62 @@ def grow_mutation(chromosome: Chromosome, max_depth: int) -> Chromosome:
chromosome.root = subtree
return chromosome
def node_replacement_mutation(chromosome: Chromosome) -> Chromosome:
"""Мутация замены операции (Node Replacement Mutation).
Выбирает случайный узел с операцией (arity > 0) и заменяет его
на случайную другую операцию той же арности, сохраняя поддеревья.
Если подходящей альтернативы нет — возвращает копию без изменений.
"""
chromosome = chromosome.copy()
operation_nodes = [n for n in chromosome.root.list_nodes() if n.value.arity > 0]
if not operation_nodes:
return chromosome
target_node = random.choice(operation_nodes)
current_arity = target_node.value.arity
same_arity_ops = [
op
for op in chromosome.operations
if op.arity == current_arity and op != target_node.value
]
if not same_arity_ops:
return chromosome
new_operation = random.choice(same_arity_ops)
target_node.value = new_operation
return chromosome
def hoist_mutation(chromosome: Chromosome) -> Chromosome:
"""Hoist-мутация (анти-bloat).
Выбирает случайное поддерево, затем внутри него — случайное поддерево меньшей глубины,
и заменяет исходное поддерево на это внутреннее.
В результате дерево становится короче, сохраняя часть структуры.
"""
chromosome = chromosome.copy()
operation_nodes = [n for n in chromosome.root.list_nodes() if n.value.arity > 0]
if not operation_nodes:
return chromosome
outer_subtree = random.choice(operation_nodes)
outer_nodes = outer_subtree.list_nodes()[1:] # исключаем корень
inner_subtree = random.choice(outer_nodes).copy_subtree()
if outer_subtree.parent:
outer_subtree.parent.replace_child(outer_subtree, inner_subtree)
else:
chromosome.root = inner_subtree
return chromosome