def cross_indvidual_random(ind1: Individual, ind2: Individual) -> Individual:
    '''
    :param ind1:
    :param ind2:
    :return: new individual cross of ind1 and ind2
    '''
    random.seed(datetime.now())
    pos = random.randint(0, ind1.street_order.shape[0] - 1)
    il_el = random.randint(1, min(ind1.street_order.shape[0] - pos, 10))
    part1 = ind1.street_order[pos:pos + il_el].copy()
    new = ind2.street_order.copy()
    for i in range(0, len(part1)):
        j = 0
        while j < len(new):
            if part1[i] == new[j]:
                new = np.delete(new, j)
                break
            j += 1
    new = np.array(new)
    part1 = np.array(part1)
    child = Individual()
    pos2 = random.randint(0, len(new))
    tmp = np.concatenate((new[0:pos2], part1, new[pos2:len(new)]), axis=None)
    child.street_order = tmp
    child.genesis = combine_stats(stat1=ind1.genesis, stat2=ind2.genesis)
    child.genesis.cross_indvidual_random_counter += 1
    child.max_number_of_cars = ind1.max_number_of_cars
    child.number_of_cars = np.count_nonzero(child.street_order == -1)
    return child
def cross_indvidual_longest_common(ind1: Individual, ind2: Individual) -> Individual:
    '''
    :param ind1:
    :param ind2:
    :return: new individual cross of ind1 and ind2
    '''
    child = Individual()
    child.street_order = create_cross_table(np.copy(ind1.street_order), np.copy(ind2.street_order))
    child.genesis = combine_stats(stat1=ind1.genesis, stat2=ind2.genesis)

    child.genesis.cross_indvidual_longest_common_counter += 1
    child.max_number_of_cars = ind1.max_number_of_cars
    child.number_of_cars = np.count_nonzero(child.street_order == -1)
    return child