예제 #1
0
파일: init.py 프로젝트: chopper6/GitEvoNet
def build_advice(net, configs):
    if (configs['advice_creation'] == 'once'):
        #assumes no growth
        advice_upon = configs['advice_upon']
        biased = util.boool(configs['biased'])
        bias_on = str(configs['bias_on'])
        pressure = math.ceil((float(configs['PT_pairs_dict'][1][0]) / 100.0))
        samples, sample_size = None, None

        if (advice_upon == 'nodes'):
            samples = net.nodes()
            sample_size = int(pressure * len(net.nodes()))
        elif (advice_upon == 'edges'):
            samples = [[str(node_i), str(node_j)] for node_i in net.nodes()
                       for node_j in net.nodes()]  # all possible edges
            #samples = net.edges()
            sample_size = int(
                pressure *
                len(net.edges()))  #sample size based on all existing edges
        advice = util.advice(net, util.sample_p_elements(samples, sample_size),
                             biased, advice_upon, bias_on)
    else:
        advice = None  #will generate during reduction each time instead

    return advice
예제 #2
0
def distrib_workers(population, gen, worker_pop_size, num_survive, advice, BD_table, biases, configs):
    num_workers = int(configs['number_of_workers'])
    output_dir = configs['output_directory']
    debug = util.boool(configs['debug'])

    if (debug == True):  # sequential debug
        for w in range(1, num_workers + 1):
            dump_file = output_dir + "to_workers/" + str(gen) + "/" + str(w)
            seed = population[0].copy()
            randSeeds = os.urandom(sysRand().randint(0, 1000000))
            worker_args = [w, seed, worker_pop_size, min(worker_pop_size, num_survive), randSeeds, advice, BD_table, biases, configs]
            with open(dump_file, 'wb') as file:
                pickle.dump(worker_args, file)
            # pool.map_async(minion.evolve_minion, (dump_file,))
            minion.evolve_minion(dump_file, gen, w, output_dir)
            sleep(.0001)

    else:
        for w in range(1, num_workers + 1):
            dump_file = output_dir + "/to_workers/" + str(gen) + "/" + str(w)
            seed = population[w % num_survive].copy()
            randSeeds = os.urandom(sysRand().randint(0, 1000000))
            assert (seed != population[w % num_survive])
            worker_args = [w, seed, worker_pop_size, min(worker_pop_size, num_survive), randSeeds, advice, BD_table, biases, configs]
            with open(dump_file, 'wb') as file:
                pickle.dump(worker_args, file)

    del population
    if (debug == True): util.cluster_print(output_dir, "debug is ON")
예제 #3
0
def add_this_edge(net,
                  configs,
                  node1=None,
                  node2=None,
                  sign=None,
                  random_direction=False,
                  given_bias=None):

    reverse_allowed = util.boool(configs['reverse_edges_allowed'])
    bias_on = configs['bias_on']

    node1_set, node2_set = node1, node2  #to save their states

    if not sign:
        sign = rd.randint(0, 1)
        if (sign == 0): sign = -1

    pre_size = post_size = len(net.edges())
    i = 0
    while (pre_size == post_size):  # ensure that net adds

        if not node1_set and node1_set != 0:
            node = rd.sample(net.nodes(), 1)
            node1 = node[0]

        if not node2_set and node2_set != 0:
            node2 = node1
            while (node2 == node1):
                node2 = rd.sample(net.nodes(), 1)
                node2 = node2[0]

        if random_direction:  #chance to swap nodes 1 & 2
            if (rd.random() < .5):
                node3 = node2
                node2 = node1
                node1 = node3

        if reverse_allowed:
            if not net.has_edge(node1, node2):
                net.add_edge(node1, node2, sign=sign)
        else:
            if not net.has_edge(node1, node2) and not net.has_edge(
                    node2, node1):
                net.add_edge(node1, node2, sign=sign)

        post_size = len(net.edges())

        i += 1
        if (i == 10000000):
            util.cluster_print(
                configs['output_directory'],
                "\n\n\nWARNING mutate.add_this_edge() is looping a lot.\nNode1 = "
                + str(node1_set) + ", Node2 = " + str(node2_set) + "\n\n\n")

    if (bias and bias_on == 'edges'):
        bias.assign_an_edge_bias(net, [node1, node2],
                                 configs['bias_distribution'],
                                 given_bias=given_bias)
예제 #4
0
def add_edges(net, num_add, configs, biases=None):

    #if (num_add == 0): print("WARNING in mutate(): 0 nodes added in add_nodes\n")

    if (biases):
        assert (len(biases) == num_add)
        assert (
            util.boool(configs['biased'])
        )  # note that the converse may not be true: net_generator will mutate first and add biases later

    for j in range(num_add):
        if (biases): add_this_edge(net, configs, given_bias=biases[j])
        else: add_this_edge(net, configs)

    if util.boool(configs['single_cc']):
        net_undir = net.to_undirected()
        num_cc = nx.number_connected_components(net_undir)
        if (num_cc != 1): ensure_single_cc(net, configs)
예제 #5
0
def final_master_info(population, gen, configs):
    output_dir = configs['output_directory']

    nx.write_edgelist(population[0].net, output_dir+"/nets/"+str(gen))
    pickle_file = output_dir + "/pickle_nets/" + str(gen) + "_pickle"
    with open(pickle_file, 'wb') as file: pickle.dump(population[0].net, file)
    popn_data(population, output_dir, gen)
    #draw_nets.basic(population, output_dir, total_gens)

    if util.boool(configs['biased']):
        util.cluster_print(output_dir,"Pickling biases.")
        bias.pickle_bias(population[0].net, output_dir+"/bias", configs['bias_on'])
예제 #6
0
def rewire(net, num_rewire, bias, bias_on, dirr, configs):

    single_cc = util.boool(configs['single_cc'])
    edge_node_ratio = float(configs['edge_to_node_ratio'])

    for i in range(num_rewire):

        assert (edge_node_ratio != 1 or not single_cc)
        # this is an unlikely scenario, but bias tracking requires rm, then add
        # which triggers multiple connected components if edge_node_ratio = 1

        orig_biases = rm_edges(net, 1, configs)
        add_this_edge(net, configs, given_bias=orig_biases[0])
예제 #7
0
def ensure_single_cc(net,
                     configs,
                     node1=None,
                     node2=None,
                     sign_orig=None,
                     bias_orig=None):
    #rewires [node1, node2] at the expense of a random, non deg1 edge

    single_cc = util.boool(configs['single_cc'])

    if single_cc:

        if node1 or node1 == 0: assert (node2 or node2 == 0)
        elif not node1: assert not (node2)

        net_undir = net.to_undirected()
        num_cc = nx.number_connected_components(net_undir)

        if (num_cc !=
                1):  #rm_edge() will recursively check #COULD CAUSE AN ERR
            if not node1 and node1 != 0:
                components = list(nx.connected_components(net_undir))
                c1 = components[0]
                node1 = rd.sample(c1, 1)
                node1 = node1[0]

            if not node2 and node2 != 0:
                c2 = components[1]
                node2 = rd.sample(c2, 1)
                node2 = node2[0]

            if not sign_orig:
                sign_orig = rd.randint(0, 1)
                if (sign_orig == 0): sign_orig = -1

            add_this_edge(net,
                          configs,
                          node1=node1,
                          node2=node2,
                          sign=sign_orig,
                          given_bias=bias_orig)
            rm_edges(net, 1, configs)  #calls ensure_single_cc() at end

        net_undir = net.to_undirected()
        num_cc = nx.number_connected_components(net_undir)
        assert (num_cc == 1)
예제 #8
0
def add_nodes(net, num_add, configs, biases=None):

    biased = util.boool(configs['biased'])
    bias_on = configs['bias_on']

    if biases: assert (biased)
    # note that the converse may not be true: net_generator will mutate first and add biases later

    # ADD NODE
    for i in range(num_add):
        pre_size = post_size = len(net.nodes())
        while (pre_size == post_size):
            new_node = rd.randint(
                0,
                len(net.nodes()) *
                1000)  # hope to hit number that doesn't already exist
            if new_node not in net.nodes():  #could be slowing things down...
                net.add_node(new_node)
                post_size = len(net.nodes())
                assert (pre_size < post_size)

        if biases and bias_on == 'nodes':
            bias.assign_a_node_bias(net,
                                    new_node,
                                    configs['bias_distribution'],
                                    given_bias=biases[i])

        # ADD EDGE TO NEW NODE TO KEEP CONNECTED
        if biases and bias_on == 'edges':
            add_this_edge(net,
                          configs,
                          node1=new_node,
                          random_direction=True,
                          given_bias=biases[i])
        else:
            add_this_edge(net, configs, node1=new_node, random_direction=True)

    # MAINTAIN NODE_EDGE RATIO
    num_edge_add = int(
        num_add * float(configs['edge_to_node_ratio'])) - num_add
    if biases and bias_on == 'edges':
        assert (len(biases) == num_edge_add + num_add)
        add_edges(net, num_edge_add, configs, biases=biases[num_add:])
    else:
        add_edges(net, num_edge_add, configs)
예제 #9
0
def rm_edges(net, num_rm, configs):
    # constraints: doesn't leave 0 deg edges or mult connected components

    biased = util.boool(configs['biased'])
    bias_on = configs['bias_on']
    orig_biases = []

    for j in range(num_rm):
        pre_size = post_size = len(net.edges())
        i = 0
        while (pre_size == post_size):
            edge = rd.sample(net.edges(), 1)
            edge = edge[0]

            # don't allow 0 deg edges
            while ((net.in_degree(edge[0]) + net.out_degree(edge[0]) == 1)
                   or (net.in_degree(edge[1]) + net.out_degree(edge[1]) == 1)):
                edge = rd.sample(net.edges(), 1)
                edge = edge[0]

            sign_orig = net[edge[0]][edge[1]]['sign']
            if biased and bias_on == 'edges':
                bias_orig = net[edge[0]][edge[1]]['bias']
            else:
                bias_orig = None
            orig_biases.append(bias_orig)

            net.remove_edge(edge[0], edge[1])

            post_size = len(net.edges())
            i += 1

            if (i == 10000000):
                util.cluster_print(
                    configs['output_directory'],
                    "WARNING mutate.rm_edges() is looping a lot.\n")

        ensure_single_cc(net,
                         configs,
                         node1=edge[0],
                         node2=edge[1],
                         sign_orig=sign_orig,
                         bias_orig=bias_orig)

    return orig_biases
예제 #10
0
def evolve_master(configs):
    # get configs
    num_workers = int(configs['number_of_workers'])
    output_dir = configs['output_directory']
    worker_pop_size = int(configs['num_worker_nets'])
    fitness_direction = str(configs['fitness_direction'])
    biased = util.boool(configs['biased'])
    num_sims = int(configs['num_sims'])

    run_data = init_run(configs)
    if not run_data: return #for ex if run already finished

    population, gen, size, advice, BD_table, num_survive, keep_running = run_data

    while keep_running:
        t_start = time.time()
        pop_size, num_survive = curr_gen_params(size, num_survive, configs)
        output.master_info(population, gen, size, pop_size, num_survive, advice, BD_table, configs)
        write_mpi_info(output_dir, gen)

        if biased: biases = bias.gen_biases(configs) #all nets must have same bias to have comparable fitness
        else: biases = None

        distrib_workers(population, gen, worker_pop_size, num_survive, advice, BD_table, biases, configs)

        report_timing(t_start, gen, output_dir)
        population = watch(configs, gen, num_workers, output_dir, num_survive, fitness_direction)

        size = len(population[0].net.nodes())
        gen += 1

        keep_running = util.test_stop_condition(size, gen, configs)

    with open(output_dir + "/progress.txt", 'w') as out: out.write("Done")
    output.final_master_info(population, gen, configs)
    del_mpi_dirs(output_dir)

    util.cluster_print(output_dir,"Evolution finished, generating images.")
    if (num_sims == 1): plot_nets.single_run_plots(output_dir)

    util.cluster_print(output_dir,"Master finished config file.\n")
예제 #11
0
def init_population(init_type, start_size, pop_size, configs):
    sign_edges_needed = True
    edge_node_ratio = float(configs['edge_to_node_ratio'])
    num_edges = int(start_size*edge_node_ratio)
    #print("net_generator.init_population(): num edges = " + str(num_edges))

    if (init_type == 'shell'):
        population = [Net(nx.DiGraph(), i) for i in range(pop_size)] #change to generate, based on start_size

    elif (init_type == 'erdos-renyi'):
        num_cc = 2
        num_tries = 0
        while(num_cc != 1):
            num_tries += 1
            init_net = (nx.erdos_renyi_graph(start_size,.035, directed=True, seed=None))
            num_added = 0
            for node in init_net.nodes():
                if (init_net.degree(node) == 0):
                    pre_edges = len(init_net.edges())
                    num_added += 1
                    sign = sysRand().randint(0, 1)
                    if (sign == 0):     sign = -1
                    node2 = node
                    while (node2 == node):
                        node2 = sysRand().sample(init_net.nodes(), 1)
                        node2 = node2[0]
                    if (sysRand().random() < .5): init_net.add_edge(node, node2, sign=sign)
                    else: init_net.add_edge(node2, node, sign=sign)
                    assert (len(init_net.edges()) > pre_edges)
                else:
                    if (init_net.in_edges(node) + init_net.out_edges(node) == 0): print("ERROR in net_generator(): hit a 0 deg node that is unrecognized.")

            net_undir = init_net.to_undirected()
            num_cc = nx.number_connected_components(net_undir)

        print("Number of added edges to avoid 0 degree = " + str(num_added) + ", num attempts to create suitable net = " + str(num_cc) + ".\n")
        population = [Net(init_net.copy(), i) for i in range(pop_size)]

    elif (init_type == 'empty'):
        population = [Net(nx.empty_graph(start_size, create_using=nx.DiGraph()), i) for i in range(pop_size)]

    elif (init_type == 'complete'):
        #crazy high run time due to about n^n edges
        population = [Net(nx.complete_graph(start_size, create_using=nx.DiGraph()), i) for i in range(pop_size)]

    elif (init_type == 'cycle'):
        population = [Net(nx.cycle_graph(start_size, create_using=nx.DiGraph()), i) for i in range(pop_size)]

    elif (init_type == 'star'):
        population = [Net(nx.star_graph(start_size-1), i) for i in range(pop_size)]
        custom_to_directed(population)

    elif (init_type == 'v sparse erdos-renyi'):
        num_cc = 2
        num_tries = 0
        while(num_cc != 1):
            num_tries += 1
            init_net = (nx.erdos_renyi_graph(start_size,.002, directed=True, seed=None))
            num_added = 0
            for node in init_net.nodes():
                if (init_net.degree(node) == 0):
                    pre_edges = len(init_net.edges())
                    num_added += 1
                    sign = sysRand().randint(0, 1)
                    if (sign == 0):     sign = -1
                    node2 = node
                    while (node2 == node):
                        node2 = sysRand().sample(init_net.nodes(), 1)
                        node2 = node2[0]
                    if (sysRand().random() < .5): init_net.add_edge(node, node2, sign=sign)
                    else: init_net.add_edge(node2, node, sign=sign)
                    assert (len(init_net.edges()) > pre_edges)
                else:
                    if (init_net.in_edges(node) + init_net.out_edges(node) == 0): print("ERROR in net_generator(): hit a 0 deg node that is unrecognized.")

            net_undir = init_net.to_undirected()
            num_cc = nx.number_connected_components(net_undir)

        print("Number of added edges to avoid 0 degree = " + str(num_added) + ", num attempts to create suitable net = " + str(num_cc) + ".\n")
        population = [Net(init_net.copy(), i) for i in range(pop_size)]


    elif (init_type == 'scale-free'):  # curr does not work, since can't go to undirected for output
        population = [Net(nx.scale_free_graph(start_size, beta=.7, gamma=.15, alpha=.15),i) for i in range(pop_size)]
    elif (init_type == 'barabasi-albert 2'):
        population = [Net(nx.barabasi_albert_graph(start_size, 2),i) for i in range(pop_size)]
        custom_to_directed(population)
    elif (init_type == 'barabasi-albert 1'):
        population = [Net(nx.barabasi_albert_graph(start_size, 1),i) for i in range(pop_size)]
        custom_to_directed(population)

    elif (init_type == 'double cycle'): #double cycle
        population = [Net(nx.cycle_graph(start_size, create_using=nx.DiGraph()), i) for i in range(pop_size)]
        double_edges(population)

    elif (init_type == 'double star'): #double star
        population = [Net(nx.star_graph(start_size-1), i) for i in range(pop_size)]
        custom_to_directed(population)
        double_edges(population)

    elif (init_type == 'exponential'): #may be a bit slow
        init_net = Net(nx.cycle_graph(start_size, create_using=nx.DiGraph()),0)
        double_edges([init_net])
        sign_edges([init_net])
        sign_edges_needed = False
        num_rewire = start_size*10
        mutate.rewire(init_net.net, num_rewire)

        population = [Net(init_net.net.copy(), i) for i in range(pop_size)]
        assert(population[0] != population[1] and population[0].net != population[1].net)

    elif (init_type == "vinayagam"):
        population = [Net(init.load_network(configs), i) for i in range(pop_size)]

    elif (init_type == "load"):
        population = [Net(nx.read_edgelist(configs['network_file'], nodetype=int,create_using=nx.DiGraph()), i) for i in range(pop_size)]

    elif (init_type == "pickle load"):
        pickled_net = pickle.load(configs['network_file'])
        population = [Net(pickled_net.copy(), i) for i in range(pop_size)]
        sign_edges_needed=False

    elif (init_type == 'All Leaves'):
        population = [Net(nx.configuration_model([1 for e in range(start_size)]),i) for i in range(pop_size)]

    elif (init_type == 'All 2s'):
        population = [Net(nx.configuration_model([2 for e in range(start_size)]),i) for i in range(pop_size)]

    elif (init_type == 'All 3s'):
        population = [Net(nx.configuration_model([3 for e in range(start_size)]),i) for i in range(pop_size)]

    elif (init_type == 'random'):

        if (start_size <= 20):
            init_net = nx.empty_graph(start_size, create_using=nx.DiGraph())
            num_add = int(edge_node_ratio*start_size)
            mutate.add_edges(init_net, num_add, configs)

        else: #otherwise rewire till connected is intractable, grow without selection instead
            init_net = nx.empty_graph(8, create_using=nx.DiGraph())
            num_add = int(edge_node_ratio*8)
            mutate.add_edges(init_net, num_add, configs)
            mutate.add_nodes(init_net, start_size-8, configs)
            if (len(init_net.edges()) == num_edges+1): mutate.rm_edges(init_net, 1, configs)

        mutate.ensure_single_cc(init_net, configs)
        assert(len(init_net.edges()) == num_edges)
        assert(len(init_net.nodes()) == start_size)

        population = [Net(init_net.copy(), i) for i in range(pop_size)]


    else:
        print("ERROR in master.gen_init_population(): unknown init_type.")
        return

    if (sign_edges_needed == True): sign_edges(population)
    if util.boool(configs['biased']):
        if (configs['bias_on'] == 'nodes'): bias.assign_node_bias(population, configs['bias_distribution'])
        elif (configs['bias_on'] == 'edges'): bias.assign_edge_bias(population, configs['bias_distribution'])
        else: print("ERROR in net_generator(): unknown bias_on: " + str (configs['bias_on']))
    return population
예제 #12
0
def pressurize(configs, Net, instance_file_name, advice, BD_table):
    # configs:
    pressure = math.ceil((float(configs['pressure']) / 100.0))
    sampling_rounds_multiplier = float(configs['sampling_rounds_multiplier']
                                       )  #FRACTION of curr number of EDGES
    if (util.is_it_none(configs['sampling_rounds_max']) == None):
        max_sampling_rounds = None
    else:
        max_sampling_rounds = int(configs['sampling_rounds_max'])
    knapsack_solver = cdll.LoadLibrary(configs['KP_solver_binary'])
    advice_upon = configs['advice_upon']
    use_kp = util.boool(configs['use_knapsack'])
    leaf_metric = str(configs['leaf_metric'])
    leaf_pow = float(configs['leaf_power'])
    hub_metric = str(configs['hub_metric'])
    fitness_operator = str(configs['fitness_operation'])
    edge_state = str(configs['edge_state'])
    biased = util.boool(configs['biased'])

    scale_node_fitness = util.boool(configs['scale_node_fitness'])

    net = Net.net  #not great syntax, but Net is an individual in a population, whereas net is it's graph representation

    #num_samples_relative = min(max_sampling_rounds, len(net.nodes()) * sampling_rounds)
    num_samples_relative = max(
        1, int(len(net.edges()) * sampling_rounds_multiplier))
    if (max_sampling_rounds):
        num_samples_relative = min(num_samples_relative, max_sampling_rounds)

    if (advice_upon == 'nodes'):
        pressure_relative = int(pressure * len(net.nodes()))
    elif (advice_upon == 'edges'):
        pressure_relative = int(pressure * len(net.edges()))
    else:
        print("ERROR in pressurize(): unknown advice_upon: " +
              str(advice_upon))
        return

    if (use_kp == 'True' or use_kp == True):
        leaf_fitness, hub_fitness, solo_fitness = 0, 0, 0
        node_data.reset_fitness(net)  #not actually used when kp = True
        node_data.reset_BDs(net)

        kp_instances = reducer.reverse_reduction(net, pressure_relative,
                                                 num_samples_relative, advice,
                                                 configs)

        if (instance_file_name != None): open(instance_file_name, 'w')

        for kp in kp_instances:
            a_result = solver.solve_knapsack(kp, knapsack_solver)
            inst_solo_fitness, inst_leaf_fitness, inst_hub_fitness = fitness.kp_instance_properties(
                a_result, leaf_metric, leaf_pow, hub_metric, fitness_operator,
                net, instance_file_name)
            leaf_fitness += inst_leaf_fitness
            hub_fitness += inst_hub_fitness
            solo_fitness += inst_solo_fitness

        leaf_fitness /= num_samples_relative
        hub_fitness /= num_samples_relative
        solo_fitness /= num_samples_relative

        Net.fitness, Net.leaf_fitness, Net.hub_fitness = solo_fitness, leaf_fitness, hub_fitness

    elif (use_kp == 'False' or use_kp == False):
        #  assumes 100% pressure

        if (edge_state == 'probabilistic'):
            assert (not biased or not configs['bias_on'] == 'nodes')
            fitness_score = probabilistic_entropy.calc_fitness(
                net, BD_table, configs)

        elif (edge_state == 'experience'):
            node_data.reset_fitness(net)
            for i in range(num_samples_relative):
                node_data.reset_BDs(net)
                reducer.exp_BDs(net, configs)
                fitness.node_fitness(net, leaf_metric)

            fitness.node_normz(net, num_samples_relative)
            fitness_score = fitness.node_product(net, scale_node_fitness)

        else:
            print("ERROR in pressurize: Unknown edge state " + str(edge_state))
            return

        Net.fitness = fitness_score

    else:
        print("ERROR in pressurize(): unknown use_knapsack config: " +
              str(use_kp))
예제 #13
0
def calc_fitness(net, BD_table, configs):
    # also uses log-likelihood normz

    biased = util.boool(configs['biased'])
    bias_on = configs['bias_on']
    leaf_metric = configs['leaf_metric']
    bias_distrib = configs['bias_distribution']
    directed = util.boool(configs['directed'])

    pressure = float(float(configs['pressure']) / float(100))
    pressure_on = configs['pressure_on']

    auto_self_loops = util.boool(configs['auto_self_loops'])

    assert (not biased
            or not bias_distrib)  #not ready to handle local bias on edges

    # fitness_score = 1
    fitness_score = 0

    if not directed:  #not biased or not bias_distrib: #ie no local bias

        if False:  #pressure is curr handled in BD_table building, before: not pressure==1

            if pressure_on == 'edges':
                pressure_relative = int(len(net.edges()) * pressure)
                all_edges = net.edges()
                rd.shuffle(all_edges)
                pressured_edges = all_edges[:pressure_relative]
                for node in net.nodes():
                    effective_node_deg = 1
                    assert (len(net.edges(node)) == net.in_degree(node) +
                            net.out_degree(node))
                    for edge in net.edges(node):
                        if edge in pressured_edges:
                            effective_node_deg += 1
                    deg_fitness = BD_table[effective_node_deg]
                    if (deg_fitness != 0): fitness_score += deg_fitness

            else:
                assert (pressure_on == 'nodes')

                # either only pressurized nodes are evaluated in fitness function
                # or only edges between two pressurized nodes are evaluated
                # curr the later

                pressure_relative = int(len(net.nodes()) * pressure)
                all_nodes = net.nodes()
                rd.shuffle(all_nodes)
                pressured_nodes = all_nodes[:pressure_relative]
                for node in pressured_nodes:
                    effective_node_deg = 1
                    assert (len(net.edges(node)) == net.in_degree(node) +
                            net.out_degree(node))
                    for edge in net.edges(node):
                        if (edge[0] == node and edge[1] in pressured_nodes
                            ) or (edge[1] == node
                                  and edge[0] in pressured_nodes):
                            effective_node_deg += 1
                    deg_fitness = BD_table[effective_node_deg]
                    if (deg_fitness != 0): fitness_score += deg_fitness

        else:

            #degrees = list(net.degree().values())
            if auto_self_loops:
                degrees = [
                    net.in_degree(node) + net.out_degree(node) + 1
                    for node in net.nodes()
                ]  #making sure...
            else:
                degrees = [
                    net.in_degree(node) + net.out_degree(node)
                    for node in net.nodes()
                ]  # making sure...
            degs, freqs = np.unique(degrees, return_counts=True)
            tot = float(sum(freqs))
            #freqs = [(f / tot) * 100 for f in freqs]

            for i in range(len(degs)):
                deg = degs[i]
                deg_fitness = BD_table[deg]  #already log-scaled
                # fitness_score *= math.pow(deg_fitness,freqs[i]) #as per node product rule
                if (deg_fitness != 0): fitness_score += freqs[i] * deg_fitness

    else:
        assert (pressure == 1 and not auto_self_loops)  #not ready yet
        node_degs = [[net.in_degree(node),
                      net.out_degree(node)] for node in net.nodes()]
        for node_deg in node_degs:
            in_deg, out_deg = node_deg[0], node_deg[1]
            fitness_score += BD_table[in_deg][out_deg]
    '''
    else: #TODO: fix dis later
        for n in net.nodes():
            deg = net.in_degree(n) + net.out_degree(n)
            p = net.node[n]['bias']
            node_fitness = 0
            for B in range(deg+1):
                D = deg - B
                prBD = (math.factorial(B + D) / (math.factorial(B) * math.factorial(D))) * math.pow(p, B) * math.pow(1 - p, D)
                assert (prBD >= 0 and prBD <= 1)
                fitBD = l_fitness.node_score(leaf_metric, B, D)
                node_fitness += prBD * fitBD
            if (node_fitness != 0): node_fitness = math.log(node_fitness, 2)  #log likelihood normz

            fitness_score += node_fitness
    '''

    return fitness_score
예제 #14
0
def build_BD_table(configs, max_deg=100):
    # assumes no conservation score and bernouille pr distribution
    # incld log-normz
    directed = util.boool(configs['directed'])
    leaf_metric = configs['leaf_metric']
    biased = util.boool(configs['biased'])
    global_edge_bias = float(configs['global_edge_bias'])

    pressure = float(float(configs['pressure']) / float(100))
    pressure_on = configs['pressure_on']

    if biased:
        global_edge_bias = float(global_edge_bias)
        p = .5 + global_edge_bias
        assert (p > 0 and p < 1)
    else:
        p = .5

    if not directed:

        if pressure == 1:
            BD_table = [None for d in range(max_deg)]
            for d in range(max_deg):
                deg_fitness = 0
                for B in range(d + 1):
                    D = d - B
                    prBD = bin_pr(B + D, B, p)
                    assert (prBD >= 0 and prBD <= 1)

                    fitBD = l_fitness.node_score(leaf_metric, B, D)
                    deg_fitness += prBD * fitBD
                if (deg_fitness != 0):
                    deg_fitness = math.log(deg_fitness,
                                           2)  #log likelihood normz
                BD_table[d] = deg_fitness

        else:
            #first build BD_table as if pressure==1
            assert (pressure_on == 'edges'
                    )  #otherwise not sure how to implement

            base_BD_table = [None for d in range(max_deg)]
            for d in range(max_deg):
                deg_fitness = 0
                for B in range(d + 1):
                    D = d - B
                    prBD = bin_pr(B + D, B, p)
                    assert (prBD >= 0 and prBD <= 1)

                    fitBD = l_fitness.node_score(leaf_metric, B, D)
                    deg_fitness += prBD * fitBD
                if (deg_fitness != 0):
                    deg_fitness = math.log(deg_fitness,
                                           2)  # log likelihood normz
                base_BD_table[d] = deg_fitness

            BD_table = [0 for d in range(max_deg)]
            for d in range(max_deg):
                for d_pressured in range(d + 1):
                    pr_d_pressured = bin_pr(d, d_pressured, pressure)
                    BD_table[d] += pr_d_pressured * base_BD_table[d_pressured]

    else:  #DIRECTED
        assert (pressure == 1)  #not ready yet

        BD_table = [[0 for i in range(max_deg)] for j in range(max_deg)]
        for in_deg in range(max_deg):
            for out_deg in range(max_deg):
                for Bin in range(in_deg + 1):
                    Din = in_deg - Bin
                    prBDin = (math.factorial(Bin + Din) /
                              (math.factorial(Bin) * math.factorial(Din))
                              ) * math.pow(p, Bin) * math.pow(1 - p, Din)
                    assert (prBDin >= 0 and prBDin <= 1)
                    for Bout in range(out_deg + 1):
                        Dout = out_deg - Bout

                        prBDout = (math.factorial(Bout + Dout) /
                                   (math.factorial(Bout) *
                                    math.factorial(Dout))) * math.pow(
                                        p, Bout) * math.pow(1 - p, Dout)
                        assert (prBDout >= 0 and prBDout <= 1)

                        fitBD = l_fitness.directed_node_score(
                            leaf_metric, Bin, Bout, Din, Dout)
                        BD_table[in_deg][
                            out_deg] += prBDin * prBDout * fitBD  #i think...

        for i in range(max_deg):
            for o in range(max_deg):
                if (BD_table[i][o] > 0):
                    BD_table[i][o] = math.log(BD_table[i][o],
                                              2)  # log likelihood normz
                else:
                    assert (BD_table[i][o] > -.2)  #allow rounding diff
                    BD_table[i][o] = 0

    return BD_table