I am implementing Genetic Algorithm (GA).
There are 43 numbers [Ambulance Locations] to choose from (1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39) , I choose 3 places since I have 3 ambulances.
I can only put my ambulance in 3 locations among 1-39 locations (Restriction).
A chromosome sample: [000010000000000000100000000000100000000]. This represents that I want to put my Ambulance on the 5th, 19th, and 31 positions. The bits against positions 5th, 19th, and 31 are 1 and rest positions are 0. In other words, I am turning on 5-bit, 19-bit, and 31-bit.
Let's say
Parent1 (111000000000000000000000000000000000000)
and
Parent2 (000000000000000000000000000000000000111)
After a cross-over, I am getting this:
('111000000000000000000000000000000000111', '000000000000000000000000000000000000000')
In the first off-spring, I have six 1's and in the second off-spring, I have Zero 1's. These generated off-springs are illegal for me since I need off-springs string with three 1's only.
I am using one-point cross-over. This is my code:
from typing import Union
import random
Parent 1 ="111000000000000000000000000000000000000"
Parent 2 ="000000000000000000000000000000000000111"
def crossover(cs1: str, cs2: str) -> Union[str, str]:
index: int = random.randint(0, len(cs1))
return cs1[:index] + cs2[index:], cs2[:index] + cs1[index:]
crossover(Cs1,Cs2)
What can be a good approach to perform cross-over while keeping3 bits among 1-39 bits?
IIUC, you want to mix the two parents randomly, keeping exactly 3 '1's?
You can get the indices of the 1s in each parent and select them randomly:
If you want to give more weight to a position that is 1 in both strings, you can modify the above to use a
Counterin place of a set:shuffle the bits between two offsprings:
using set operations
example output: