# Total of weights must be greater than zero #python

I'm tried to follow a tutorial of making a genetic algorithm in python, but when I run the code below, i get the following errors: Traceback (most recent call last): File "C:\Users\Dani\PycharmProjects\FirstProject\main.py", line 343, in population, generations = run_evolution( File "C:\Users\Dani\PycharmProjects\FirstProject\main.py", line 325, in run_evolution parents = selection_func(population, fitness_func) File "C:\Users\Dani\PycharmProjects\FirstProject\main.py", line 274, in selection_pair return choices( File "C:\Users\Dani\AppData\Local\Programs\Python\Python39\lib\random.py", line 495, in choices raise ValueError('Total of weights must be greater than zero') ValueError: Total of weights must be greater than zero

The last one is the one that's bothering me the most because I don't really know what should I do in order to solve it.

Here is the code (sorry for the hardcoded part):

# Genetic Algorithm

``````Genome = List[int] # this is line 98
Population = List[Genome]
FitnessFunc = Callable[[Genome], int]
PopulateFunc = Callable[[], Population]
SelectionFunc = Callable[[Population, FitnessFunc], Tuple[Genome, Genome]]
CrossoverFunc = Callable[[Genome, Genome], Tuple[Genome, Genome]]
MutationFunc = Callable[[Genome], Genome]

Champion = namedtuple('Champion', ['name', 'value', 'limit'])
champions = [
Champion('Annie', 50, 1),
Champion('Olaf', 47, 1),
Champion('Galio', 46, 1),
Champion('TwistedFate', 51, 1),
Champion('XinZhao', 51, 1),
Champion('Urgot', 48, 1),
Champion('Leblanc', 46, 1),
Champion('Fiddlesticks', 49, 1),
Champion('Kayle', 50, 1),
Champion('MasterYi', 50, 1),
Champion('Alistar', 49, 1),
Champion('Ryze', 40, 1),
Champion('Sion', 49, 1),
Champion('Sivir', 50, 1),
Champion('Soraka', 52, 1),
Champion('Teemo', 51, 1),
Champion('Tristana', 51, 1),
Champion('Warwick', 51, 1),
Champion('Nunu', 49, 1),
Champion('Ashe', 47, 1),
Champion('Tryndamere', 52, 1),
Champion('Jax', 50, 1),
Champion('Morgana', 47, 1),
Champion('Zilean', 49, 1),
Champion('Singed', 53, 1),
Champion('Evelynn', 47, 1),
Champion('Twitch', 52, 1),
Champion('Karthus', 51, 1),
Champion('Anivia', 53, 1),
Champion('Shaco', 49, 1),
Champion('DrMundo', 49, 1),
Champion('Sona', 54, 1),
Champion('Irelia', 50, 1),
Champion('Janna', 55, 1),
Champion('Gangplank', 49, 1),
Champion('Corki', 46, 1),
Champion('Karma', 45, 1),
Champion('Taric', 52, 1),
Champion('Veigar', 49, 1),
Champion('Trundle', 47, 1),
Champion('Swain', 53, 1),
Champion('Caitlyn', 46, 1),
Champion('Blitzcrank', 51, 1),
Champion('Malphite', 50, 1),
Champion('Katarina', 50, 1),
Champion('Nocturne', 51, 1),
Champion('Maokai', 51, 1),
Champion('Renekton', 50, 1),
Champion('JarvanIV', 52, 1),
Champion('Elise', 49, 1),
Champion('Orianna', 50, 1),
Champion('Wukong', 52, 1),
Champion('Brand', 51, 1),
Champion('LeeSin', 45, 1),
Champion('Vayne', 51, 1),
Champion('Rumble', 49, 1),
Champion('Cassiopeia', 48, 1),
Champion('Skarner', 48, 1),
Champion('Heimerdinger', 48, 1),
Champion('Nasus', 50, 1),
Champion('Nidalee', 46, 1),
Champion('Udyr', 49, 1),
Champion('Poppy', 45, 1),
Champion('Gragas', 49, 1),
Champion('Pantheon', 50, 1),
Champion('Ezreal', 46, 1),
Champion('Mordekaiser', 51, 1),
Champion('Yorick', 53, 1),
Champion('Akali', 50, 1),
Champion('Kennen', 47, 1),
Champion('Garen', 53, 1),
Champion('Leona', 51, 1),
Champion('Malzahar', 52, 1),
Champion('Talon', 50, 1),
Champion('Riven', 49, 1),
Champion('KogMaw', 50, 1),
Champion('Shen', 48, 1),
Champion('Lux', 49, 1),
Champion('Xerath', 52, 1),
Champion('Shyvana', 53, 1),
Champion('Ahri', 52, 1),
Champion('Graves', 47, 1),
Champion('Fizz', 48, 1),
Champion('Volibear', 49, 1),
Champion('Rengar', 48, 1),
Champion('Varus', 49, 1),
Champion('Nautilus', 48, 1),
Champion('Viktor', 47, 1),
Champion('Sejuani', 53, 1),
Champion('Fiora', 49, 1),
Champion('Ziggs', 51, 1),
Champion('Lulu', 50, 1),
Champion('Draven', 50, 1),
Champion('Hecarim', 50, 1),
Champion('Khazix', 48, 1),
Champion('Darius', 51, 1),
Champion('Jayce', 50, 1),
Champion('Lissandra', 46, 1),
Champion('Diana', 51, 1),
Champion('Quinn', 50, 1),
Champion('Syndra', 46, 1),
Champion('AurelionSol', 52, 1),
Champion('Kayn', 48, 1),
Champion('Zyra', 49, 1),
Champion('Gnar', 49, 1),
Champion('Zac', 49, 1),
Champion('Yasuo', 50, 1),
Champion('Velkoz', 51, 1),
Champion('Taliyah', 47, 1),
Champion('Camille', 48, 1),
Champion('Braum', 51, 1),
Champion('Jhin', 48, 1),
Champion('Kindred', 48, 1),
Champion('Jinx', 51, 1),
Champion('TahmKench', 46, 1),
Champion('Lucian', 47, 1),
Champion('Zed', 49, 1),
Champion('Kled', 51, 1),
Champion('Ekko', 49, 1),
Champion('Vi', 50, 1),
Champion('Aatrox', 47, 1),
Champion('Nami', 51, 1),
Champion('Azir', 43, 1),
Champion('Thresh', 47, 1),
Champion('Illaoi', 48, 1),
Champion('RekSai', 48, 1),
Champion('Ivern', 46, 1),
Champion('Kalista', 47, 1),
Champion('Bard', 47, 1),
Champion('Rakan', 50, 1),
Champion('Xayah', 49, 1),
Champion('Ornn', 41, 1),
]

def gen_genome(length: int) -> Genome:
return choices([0, 1], k=length)

def gen_population(size: int, genome_length: int) -> Population:
return [gen_genome(genome_length) for _ in range(size)]

def fitness(genome: Genome, champions: [Champion], team_limit: int) -> int:
if len(genome) != len(champions):
raise ValueError("Genome and champions must be of the same length")

limit = 0
value = 0

for z, champion in enumerate(champions):
if genome[z] == 1:
limit += champion.limit
value += champion.value

if limit > team_limit:
return 0

return value
``````

# This is the problematic function

``````**def selection_pair(population: Population, fitness_func: FitnessFunc) -> Population:
return choices(
population=population,
# limits=[fitness_func(gene) for gene in population],
weights=[fitness_func(gene) for gene in population],
k=2
)**
``````

# Rest of the code

``````def single_point_crossover(a: Genome, b: Genome) -> Tuple[Genome, Genome]:
if len(a) != len(b):
raise ValueError("Genomes a and b must be of same length")

length = len(a)
if length < 2:
return a, b

p = randint(1, length -1)
return a[0:p] + b[p:], b[0:p] + a[p:]

def mutation(genome: Genome, num: int = 1, probability: float = 0.5) -> Genome:
for _ in range(num):
index = randrange(len(genome))
genome[index] = genome[index] if random() > probability else abs(genome[index] - 1)
return genome

def run_evolution(
populate_func: PopulateFunc,
fitness_func: FitnessFunc,
fitness_limit: int,
selection_func: SelectionFunc = selection_pair,
crossover_func: CrossoverFunc = single_point_crossover,
mutation_func: MutationFunc = mutation,
generation_limit: int = 100
) -> Tuple[Population, int]:
population = populate_func()

for r in range(generation_limit):
population = sorted(
population,
key=lambda genome: fitness_func(genome),
reverse=True
)

if fitness_func(population[0]) >= fitness_limit:
break

next_generation = population[0:2]

for z in range(int(len(population) / 2) - 1):
parents = selection_func(population, fitness_func)
offspring_a, offspring_b = crossover_func(parents[0], parents[1])
offspring_a = mutation_func(offspring_a)
offspring_b = mutation_func(offspring_b)
next_generation += [offspring_a, offspring_b]

population = next_generation

population = sorted(
population,
key=lambda genome: fitness_func(genome),
reverse=True
)

return population, r

start = time.time()
population, generations = run_evolution(
populate_func=partial(
gen_population, size=10, genome_length=len(champions)
),
fitness_func=partial(
fitness, champions=champions, team_limit=5
),
fitness_limit=300,
generation_limit=100
)
end = time.time()

def genome_to_champions(genome: Genome, champions: [Champion]) -> [Champion]:
result = []
for z, champion in enumerate(champions):
if genome[z] == 1:
result += [champion.name]

return result

print(f"number of generations: {generations}")
print(f"time: {end - start}s")
print(f"best solution: {genome_to_champions(population[0], champions)}")
``````

The lines until 98 are just some for and if's, not affecting the algorithm The imports are:

``````import csv
import time
from collections import namedtuple
from functools import partial
from random import choices, randint, random, randrange
from typing import List, Callable, Tuple
``````