Exemplo n.º 1
0
def force_tsp(population_size,
              generations,
              circle,
              dist_matrix_path,
              topology,
              noise_type,
              noise_amplitude,
              load_population,
              load_initial_conditions,
              save_data):

    start_time = time.time()

    # load distance matrix
    dist_matrix = np.genfromtxt(dist_matrix_path, delimiter=';', dtype=int)
    n_cities = dist_matrix.shape[0]

    eval_length = int(eval_T/dt)

    # store data
    signal_matrix = np.empty([population_size, generations + 1], dtype=list)
    aligned_signal_matrix = np.empty([population_size, generations + 1], dtype=list)
    initial_fourier_signals = np.empty(population_size, dtype=list)
    cost = np.empty([population_size, generations + 1], dtype=float)
    permutations = np.empty([population_size, generations + 1], dtype=list)
    best_signals = np.empty(generations + 1, dtype=list)
    best_aligned_signals = np.empty(generations + 1, dtype=list)

    # Load or generate population of reservoirs
    if load_population != False:
        population_file = np.load(load_population, allow_pickle=True)
        population = population_file['best_units']
        for reservoir in population:
            reservoir[4] = np.empty(generations, dtype=list)

        print("population loaded from file ", load_population)

    else:
        population = generate_population(population_size, generations)
        # reservoir = [M, w_feedback, w_output, state, [[teacher,res], noise_power] ]

    # Topology map
    if topology == '1D':
        interaction_map = interaction_map_1d(population_size)
    elif topology == '2D_square':
        interaction_map = interaction_map_2d_square(population_size)
    else:
        assert False, "invalid topology" + topology

    # print model parameters
    print("Population size= ", population_size)
    print("Generations= ", generations)
    print("Number of cities= ", n_cities)
    print("Topology: ", topology)
    print("Noise type: ", noise_type)
    print("Noise amplitude: ", noise_amplitude)


    # initializing signals
    print()
    print("initializing signals...")
    print()

    if load_initial_conditions != False:
        for network in range(population_size):
            coefficients = np.load(load_initial_conditions, allow_pickle=True)
            initial_fourier_signals[network] = fourier_series_from_coeffs(coefficients[network], signal_T, dt,
                                                                          period_fourier)

        print("initial conditions loaded from file", load_initial_conditions)
        print()

    else:
        for network in range(population_size):
            initial_fourier_signals[network] = generate_fourier_signal(n_fourier, period_fourier, signal_T, dt)

    for reservoir in range(population_size):
        [w_out, state] = force(population[reservoir],initial_fourier_signals[reservoir][0], alpha, training_T, dt)
        population[reservoir][2] = w_out
        population[reservoir][3] = state

    learners_list = []

    print("Elapsed time:", int(round(time.time() - start_time)/60), "min")


    for generation in range(generations + 1):

        print("Generation:", generation)

        # Generate signals and evaluate fitness
        for reservoir in range(population_size):
            signal, state = generate_signal(population[reservoir], signal_T, dt)
            signal_matrix[reservoir, generation] = signal
            population[reservoir][3] = state

            # add noise to learners signal (ie noisy copying)
            if reservoir in learners_list:
                if noise_type == "white":
                    noise_function = gen_white_noise(noise_amplitude, int(signal_T / dt))
                elif noise_type == "fourier":
                    noise_function = gen_fourier_noise(noise_amplitude, signal_T, dt, n_fourier, period_fourier)
                else:
                    noise_function = np.zeros(int(signal_T / dt))
                signal_matrix[reservoir, generation] += noise_function

            if align:
                signal_for_eval, eval_start_index = align_signal(signal_matrix[reservoir, generation], eval_length, timebin=0)


            else:
                eval_start = 0
                signal_for_eval = signal_matrix[network, generation][eval_start: eval_start + eval_length]


            # if learner: calculate power of the evaluated part of the noise function, and save it
            if reservoir in learners_list:
                power = noise_power(noise_function[eval_start_index:eval_start_index + eval_length])
                population[network][4][generation - 1].append(power)

            # save aligned signal
            aligned_signal_matrix[reservoir, generation] = signal_for_eval

            perm = signal_to_permutation(signal_for_eval, n_cities)
            permutations[reservoir, generation] = np.array(list(perm), dtype=int)
            cost[reservoir, generation] = evaluate_permutation(dist_matrix, perm, circle)


        print("Min cost = ", min(cost[:, generation]))
        # save current best signal
        best_signals[generation] = signal_matrix[np.argmin(cost[:, generation]), generation]
        best_aligned_signals[generation] = aligned_signal_matrix[np.argmin(cost[:, generation]), generation]

        # quit before training at last cycle
        if generation == generations:
            break

        # teacher -  learner pairs based on topology
        teacher_learner = interactor((-1) * cost[:, generation], interaction_map)

        # learner's list, in next cycles's signal generation we will add noise to these reservoirs' signals
        learners_list = np.empty(population_size, dtype=int)
        copy_id = 0

        # teaching / copying
        for pair in teacher_learner:
            teacher = pair[0]
            learner = pair[1]
            if learner != teacher:
                [w_out, state] = force(population[learner], signal_matrix[teacher, generation], alpha, training_T, dt)
                population[learner][2] = w_out
                population[learner][3] = state

                learners_list[copy_id] = learner
                copy_id += 1

            # store the copying event:
            population[learner][4][generation] = pair

        learners_list = learners_list[:copy_id]

        # print runtime of cycle
        print("Elapsed time:", int(round(time.time() - start_time)/60), "min")



    # save data to file (filename = current date and time in MMDD-HHMM format)

    simulation_params = [population_size, generations, signal_T, eval_T, n_cities, nk_mapping, topology, n_fourier,
                         alpha, align]
    noise_params = [noise_type, noise_amplitude]

    copying_events = np.empty(population_size, dtype=list)
    for network in range(population_size):
        copying_events[network] = population[network][4]

    if save_data:
        outfile = "TSP" + "-" + str(population_size) + "-" + str(generations) + "-" + datetime.datetime.now().strftime(
            "%m%d-%H%M")

        np.savez(outfile, sim_params=simulation_params,
                          noise_params=noise_params,
                          distance_matrix=dist_matrix,
                          permutations=permutations,
                          cost=cost,
                          copying_events=copying_events,
                          best_signals=best_signals,
                          best_aligned_signals=best_aligned_signals)

        print(outfile," saved")

    print("Total time:", int(round(time.time() - start_time)/60), "min")

    return simulation_params, noise_params, dist_matrix, permutations, cost, copying_events, best_signals, best_aligned_signals
Exemplo n.º 2
0
# signal_to_load = 'aligned_signal.npy'

save_signal = False

N = 10

signal_length = int(signal_T / dt)
eval_length = int(eval_T / dt)
timebin = int(eval_length / N)

if load_signal:
    aligned_signal = np.load(signal_to_load)
else:
    signal = generate_fourier_signal(n_fourier, period_fourier, signal_T,
                                     dt)[0]
    aligned_signal = align_signal(signal, eval_length, timebin)[0]

# map the signal to binary
bitstring = signal_to_bitstring_center(aligned_signal, timebin, threshold=0)
binary_string = np.array(list(bitstring), dtype=int)

# map the signal to permutation
permutation = signal_to_permutation_a(aligned_signal, N)

# plot

fig, ax = plt.subplots(tight_layout=True)
fig.set_size_inches(9, 8)
# plt.gcf().subplots_adjust(bottom=0.15)

ax.plot(aligned_signal, 'red', linewidth=3)
Exemplo n.º 3
0
def sample_permutations(n_samples, n_sample_points, N, save_to_npz=True):

    ls_points = np.logspace(0, 7, num=n_sample_points).astype(int)

    numbers = np.arange(1, N + 1)

    n_unique_random = np.zeros(n_samples, dtype=int)
    n_unique_fourier = np.zeros(n_samples, dtype=int)
    occ_distribution = np.zeros(n_samples, dtype=int)

    eval_length = int(eval_T / dt)
    timebin = eval_length / N

    start_time = time.time()

    # random sample from permutation space
    random_permutations = np.empty(n_samples, dtype='S10')
    # Fourier signal -> permutation
    fourier_permutations = np.empty(n_samples, dtype='S10')

    # initialize
    random_permutations[0] = "".join(map(str, np.random.permutation(numbers)))

    signal = generate_fourier_signal(n_fourier, period_fourier, signal_T,
                                     dt)[0]
    aligned_signal = align_signal(signal, eval_length, timebin)[0]
    fourier_permutations[0] = "".join(
        map(str, signal_to_permutation(aligned_signal, N)))

    n_unique_random[0] = 1
    n_unique_fourier[0] = 1

    for sample in range(1, n_samples):

        if sample % 100000 == 0:
            print("Elapsed time:", int(round(time.time() - start_time) / 60),
                  "min")
            print("Sample", sample)

        # sample random permutation
        random_permutations[sample] = "".join(
            map(str, np.random.permutation(numbers)))

        # permutation from signal with method a
        signal = generate_fourier_signal(n_fourier, period_fourier)[0]
        aligned_signal = align_signal(signal, eval_length, timebin)[0]
        fourier_permutations[sample] = "".join(
            map(str, signal_to_permutation_a(aligned_signal, N)))

        if sample in ls_points:
            n_unique_random[sample] = len(
                np.unique(random_permutations[:sample + 1]))
            n_unique_fourier[sample] = len(
                np.unique(fourier_permutations[:sample + 1]))

        else:
            n_unique_random[sample] = n_unique_random[sample - 1]
            n_unique_fourier[sample] = n_unique_fourier[sample - 1]

    occurences = np.unique(fourier_permutations, return_counts=True)[1]
    for item in occurences:
        occ_distribution[item] = occ_distribution[item] + 1

    logspace_points = ls_points.astype(int)

    print("Elapsed time:", int(round(time.time() - start_time) / 60), "min")

    if save_to_npz:
        # save results
        outfile = "Perm-gen-" + str(n_samples) + "-" + str(N) + "-" + str(
            n_sample_points) + "-" + datetime.datetime.now().strftime(
                "%m%d-%H%M")
        np.savez(outfile,
                 sim_parameters=[n_samples, N],
                 random=n_unique_random,
                 fourier=n_unique_fourier,
                 fourier_distribution=occ_distribution,
                 logspace_points=logspace_points)

        print(outfile, "saved")

    print("Total time:", int(round(time.time() - start_time) / 60), "min")

    return n_unique_random, n_unique_fourier, occ_distribution, logspace_points
Exemplo n.º 4
0
def force_nk(population_size, generations, N, K, nk_mapping, topology,
             noise_type, noise_amplitude, load_population,
             load_initial_conditions, load_landscape, save_information_measure,
             save_data, outfilename_format):

    start_time = time.time()

    eval_length = int(eval_T / dt)
    timebin = eval_length / N

    # store data
    signal_matrix = np.empty([population_size, generations + 1], dtype=list)
    initial_fourier_signals = np.empty(population_size, dtype=list)
    fitness = np.empty([population_size, generations + 1], dtype=float)
    binary_strings = np.empty([population_size, generations + 1], dtype=list)

    # Load or generate population of reservoirs
    if load_population != False:
        population_file = np.load(load_population, allow_pickle=True)
        population = population_file['best_units']
        for reservoir in population:
            reservoir[4] = np.empty(generations, dtype=list)

        print("population loaded from file ", load_population)

    else:
        population = generate_population(population_size, generations)
        # reservoir = [M, w_feedback, w_output, state, [[teacher,res], noise_power] ]

    # Load or generate NK landscape
    if load_landscape != False:
        landscape_file = np.load(load_landscape, allow_pickle=True)
        landscape = landscape_file["nk_landscape"]
        N = landscape_file["N"]
        K = landscape_file["K"]

        print("NK-landscape loaded from file ", load_landscape)
        print()

    else:
        landscape = generate_nklandscape(N, K)

    if nk_mapping == 'neighbour':
        nk_map = neighbourmap(N, K)
    elif nk_mapping == 'random':
        nk_map = randommap(N, K, f=None)
    else:
        assert False, "invalid nk mapping method" + nk_mapping

    # Topology map
    if topology == '1D':
        interaction_map = interaction_map_1d(population_size)
    elif topology == '2D_square':
        interaction_map = interaction_map_2d_square(population_size)
    else:
        assert False, "invalid topology map method" + topology

    # print model parameters
    print("Population size= ", population_size)
    print("Generations= ", generations)
    print("N= ", N, " K= ", K)
    print("NK landscape mapping: ", nk_mapping)
    print("Topology mapping: ", topology)
    print("Noise type: ", noise_type)
    print("Noise amplitude: ", noise_amplitude)

    # initializing signals
    print()
    print("initializing signals...")
    print()

    if load_initial_conditions != False:
        for network in range(population_size):
            coefficients = np.load(load_initial_conditions, allow_pickle=True)
            initial_fourier_signals[network] = fourier_series_from_coeffs(
                coefficients[network], signal_T, dt, period_fourier)

        print("initial conditions loaded from file", load_initial_conditions)
        print()

    else:
        for network in range(population_size):
            initial_fourier_signals[network] = generate_fourier_signal(
                n_fourier, period_fourier, signal_T, dt)

    for reservoir in range(population_size):
        [w_out, state] = force(population[reservoir],
                               initial_fourier_signals[reservoir][0], alpha,
                               training_T, dt)
        population[reservoir][2] = w_out
        population[reservoir][3] = state

    learners_list = []

    print("Elapsed time:", int(round(time.time() - start_time) / 60), "min")

    # simulation
    for generation in range(generations + 1):

        print("Generation:", generation)

        # Generate signals and evaluate fitness
        for reservoir in range(population_size):
            signal, state = generate_signal(population[reservoir], signal_T,
                                            dt)
            signal_matrix[reservoir, generation] = signal
            population[reservoir][3] = state

            # add noise to learners signal (ie noisy copying)
            if reservoir in learners_list:
                if noise_type == "white":
                    noise_function = gen_white_noise(noise_amplitude,
                                                     int(signal_T / dt))
                elif noise_type == "fourier":
                    noise_function = gen_fourier_noise(noise_amplitude,
                                                       signal_T, dt, n_fourier,
                                                       period_fourier)
                else:
                    noise_function = np.zeros(int(signal_T / dt))
                signal_matrix[reservoir, generation] += noise_function

            if align:
                aligned_signal, eval_start_index = align_signal(
                    signal_matrix[reservoir, generation], eval_length, timebin)
                bitstring = signal_to_bitstring_center(aligned_signal,
                                                       timebin,
                                                       threshold=0)

            else:
                eval_start_index = timebin
                bitstring = signal_to_bitstring_center(
                    signal_matrix[reservoir,
                                  generation][timebin:timebin + eval_length],
                    timebin,
                    threshold=0)

            # if learner: calculate power of the evaluated part of the noise function, and save it
            if reservoir in learners_list:
                power = noise_power(
                    noise_function[eval_start_index:eval_start_index +
                                   eval_length])
                population[reservoir][4][generation - 1].append(power)

            # save binary strings
            binary_strings[reservoir, generation] = np.array(list(bitstring),
                                                             dtype=int)

            # evaluate fitness
            fitness[reservoir,
                    generation] = bitstring_to_fitness(bitstring, landscape,
                                                       nk_map, N, K)

        # quit before training at last cycle
        if generation == generations:
            break

        # teacher - learner pairs based on topology
        teacher_learner = interactor(fitness[:, generation], interaction_map)

        # learner's list - in next cycles's signal generation noise is added to these reservoirs' signals
        learners_list = np.empty(population_size, dtype=int)
        copy_id = 0

        # signal copying
        for pair in teacher_learner:
            teacher = pair[0]
            learner = pair[1]
            if learner != teacher:
                [w_out, state] = force(population[learner],
                                       signal_matrix[teacher, generation],
                                       alpha, training_T, dt)
                population[learner][2] = w_out
                population[learner][3] = state

                learners_list[copy_id] = learner
                copy_id += 1

            # store the copying event:
            population[learner][4][generation] = pair

        learners_list = learners_list[:copy_id]

        print(fitness)

        # print runtime of cycle
        print("Elapsed time:", int(round(time.time() - start_time) / 60),
              "min")

    print("Total time:", int(round(time.time() - start_time) / 60), "min")

    if outfilename_format == "datetime":
        # filename = current date and time in population_size-generations-N-K-MMDD-HHMM format
        outfile = str(population_size) + "-" + str(generations) + "-" + str(N) + "-" + str(K) + "-" + \
                  datetime.datetime.now().strftime("%m%d-%H%M")

    elif outfilename_format == "fig3d":
        # filename for fig 3d runs
        outfile = str(N) + "-" + str(K) + "-" + str(
            load_initial_conditions) + "-" + str(topology_mapping)

    elif outfilename_format == "fig4":
        # filename: noise type - amplitude noise analysis runs
        outfile = str(noise_type) + "-" + str(
            noise_amplitude) + "-" + datetime.datetime.now().strftime(
                "%m%d-%H%M")

    else:
        outfile = str(population_size) + "-" + str(generations) + "-" + str(
            N) + "-" + str(K)

    simulation_params = [
        population_size, generations, signal_T, eval_T, N, K, nk_mapping,
        topology_mapping, n_fourier, alpha, align
    ]
    noise_params = [noise_type, noise_amplitude]

    nk_landscape = landscape
    binary_strings = binary_strings
    fitness = fitness
    copying_events = np.empty(population_size, dtype=list)
    for network in range(population_size):
        copying_events[network] = population[network][4]

    if save_information_measure:
        fitness_absolute = fitness
        landscape_values = all_values_of_landscape(nk_landscape,
                                                   return_sorted=True)
        fitness_measure = compute_infomeasure(fitness_absolute,
                                              landscape_values)

        if save_data:
            outfile += "_i"
            np.savez(outfile,
                     sim_params=simulation_params,
                     noise_params=noise_params,
                     nk_landscape=nk_landscape,
                     binary_strings=binary_strings,
                     fitness_abs=fitness_absolute,
                     fitness_measure=fitness_measure,
                     copying_events=copying_events)

            print(outfile, "saved")

            return simulation_params, noise_params, nk_landscape, binary_strings, fitness_absolute, fitness_measure, copying_events

    else:
        if save_data:
            np.savez(outfile,
                     sim_params=simulation_params,
                     noise_params=noise_params,
                     nk_landscape=nk_landscape,
                     binary_strings=binary_strings,
                     fitness=fitness,
                     copying_events=copying_events)

            print(outfile, "saved")

            return simulation_params, noise_params, nk_landscape, binary_strings, fitness, copying_events

    print()
Exemplo n.º 5
0
def sample_binaries(n_samples, N, save_to_npz=True):
    """
    Generates samples of N-long binary strings, 1) drawn uniformly, 2) mapped from randomly generated Fourier signals.

    Parameters
    ----------
    n_samples
    N
    save_to_npz

    Returns
    -------
    n_unique_random - the number of different binaries generated drawn uniformly over time
    n_unique_fourier - the number of different binaries mapped from Fourier-signals over time
    occ_distribution - array containing how many binary string were sampled n times using method 2)

    optionally an npz file containing the simulation data

    """
    n_unique_random = np.empty(n_samples, dtype=int)
    n_unique_fourier = np.empty(n_samples, dtype=int)

    occ_distribution = np.zeros(n_samples, dtype=int)

    eval_length = int(eval_T / dt)
    timebin = eval_length / N

    start_time = time.time()

    # random sample from binary space
    random_binaries = np.empty(n_samples, dtype=list)

    unique_random = []

    # Fourier signal -> binary
    fourier_binaries = np.empty(n_samples, dtype=list)

    unique_fourier = []

    for sample in range(n_samples):

        if sample % 10000 == 0:
            print("Elapsed time:", int(round(time.time() - start_time) / 60),
                  "min")
            print("Sample", sample)

        random_binaries[sample] = [random.randint(0, 1) for j in range(N)]

        if random_binaries[sample] not in unique_random:
            unique_random.append(random_binaries[sample])

        n_unique_random[sample] = len(unique_random)

        signal = generate_fourier_signal(n_fourier, period_fourier, signal_T,
                                         dt)[0]
        aligned_signal = align_signal(signal, eval_length, timebin)[0]
        fourier_binaries[sample] = signal_to_bitstring_center(aligned_signal,
                                                              timebin,
                                                              threshold=0)

        if fourier_binaries[sample] not in unique_fourier:
            unique_fourier.append(fourier_binaries[sample])

        n_unique_fourier[sample] = len(unique_fourier)

    occurences = np.unique(fourier_binaries, return_counts=True)[1]
    for item in occurences:
        occ_distribution[item] = occ_distribution[item] + 1

    print("Elapsed time:", int(round(time.time() - start_time) / 60), "min")

    print(n_unique_random)
    print(n_unique_fourier)

    if save_to_npz:
        # save results
        outfile = "Binary-gen-" + str(n_samples) + "-" + str(
            N) + "-" + datetime.datetime.now().strftime("%m%d-%H%M")
        np.savez(outfile,
                 sim_parameters=[n_samples, N],
                 random=n_unique_random,
                 fourier=n_unique_fourier,
                 fourier_distribution=occ_distribution)

        print(outfile, "saved")

    print("Total time:", int(round(time.time() - start_time) / 60), "min")

    return n_unique_random, n_unique_fourier, occ_distribution