import random from gausse.components.database import ComponentDatabase from gausse.optim.objective import compute_cost_rub, decoded_summary, evaluate from gausse.optim.search_space import SearchBounds, decode, sample_genome DB = ComponentDatabase.load() BOUNDS = SearchBounds() def test_evaluate_feasible_genome_has_fitness_equal_efficiency(): rng = random.Random(2) found_feasible = False for _ in range(50): genome = sample_genome(DB, BOUNDS, rng) result = evaluate(genome, DB, BOUNDS) if result.feasible: found_feasible = True assert result.fitness == result.efficiency # КПД <= 1 всегда; может быть СЛЕГКА отрицательным: трение о трубку # за время разряда может съесть больше, чем слабая катушка добавила assert -0.01 <= result.efficiency <= 1.0 assert result.cost_rub > 0 break assert found_feasible, "ни один из 50 случайных геномов не оказался реализуемым" def test_evaluate_infeasible_genome_has_negative_fitness_and_reason(): rng = random.Random(9) genome = sample_genome(DB, BOUNDS, rng) # индукционный датчик требует скорости >= порог/чувствительность = 5 м/с, # а старт по умолчанию 3 м/с -- первая ступень обязана провалиться inductive_idx = next(i for i, s in enumerate(DB.sensors) if s.kind == "inductive") genome.stages[0].sensor_idx = inductive_idx result = evaluate(genome, DB, BOUNDS) assert not result.feasible assert result.fitness < 0 assert result.reason is not None assert result.failed_stage_index == 0 def test_compute_cost_rub_is_positive_and_scales_with_stage_count(): rng = random.Random(4) genome = sample_genome(DB, BOUNDS, rng) config, _, _ = decode(genome, DB, BOUNDS) cost = compute_cost_rub(config, DB) assert cost > 0 genome.stages.append(genome.stages[0]) genome.inter_stage_gaps_m.append(0.05) config2, _, _ = decode(genome, DB, BOUNDS) cost2 = compute_cost_rub(config2, DB) assert cost2 > cost def test_decoded_summary_uses_real_part_numbers(): rng = random.Random(6) genome = sample_genome(DB, BOUNDS, rng) summary = decoded_summary(genome, DB) assert len(summary["stages"]) == len(genome.stages) real_wire_ids = {w.part_id for w in DB.wires} assert all(s["wire"] in real_wire_ids for s in summary["stages"])