def estimate_SI_continuous(cls, underlying: Network, theta: float, outcome: dict, initials: set, immunes: set = set(), tmax=1000.0): time = .0 my_outcome = outcome.copy() susceptible = set(underlying.nodes_ids) loglikelyhood = .0 infected = set() infected |= initials susceptible -= immunes | infected prev_time = .0 for newinf_id, inf_time in my_outcome.items(): dt = inf_time - prev_time prev_time = inf_time neighbors = underlying.get_in_neighbors_for_node(newinf_id) n_infected = len(neighbors & infected) loglikelyhood += math.log(n_infected * theta) for sus_id in susceptible: sus_neighbors = underlying.get_in_neighbors_for_node(sus_id) sus_n_infected = len(sus_neighbors & infected) if sus_n_infected: loglikelyhood += sus_n_infected*theta*dt infected.add(newinf_id) if newinf_id in susceptible: susceptible.remove(newinf_id) return loglikelyhood
def make_cascades_summary(self, cascade_networks, logweight=True): new_nodes = {} new_links = {} self.cascades_network = Network() for cascade in cascade_networks: for node_id in cascade.network.nodes_ids: if new_nodes.get(node_id) is None: new_nodes[node_id] = 0 new_nodes[node_id] += 1 for from_id, to_id in cascade.network.links.keys(): if new_links.get((from_id, to_id)) is None: new_links[(from_id, to_id)] = 0 new_links[(from_id, to_id)] += 1 self.cascades_network.nodes_attributes.append({'id': 'w', 'title': 'LogWeight', 'type': 'float'}) for node_id, quantity in new_nodes.items(): self.cascades_network.add_node(node_id) if logweight: w = math.log(quantity) + 1 else: w = quantity self.cascades_network.add_meta_for_node(node_id, {'w': w}) for link, quantity in new_links.items(): if logweight: w = math.log(quantity) + 1 else: w = quantity self.cascades_network.add_link(link[0], link[1], mutual=False, weighted=True, weight=w)
def make_underlying_summary(self, underlyings): if len(underlyings) == 1: self.underlying = underlyings[0].network else: self.underlying = Network(optimisation=NetworkOptimisation.id_only) for underlying in underlyings: for node_id, neighbors in underlying.network.nodes.items(): self.underlying.add_node(node_id) self.underlying.nodes[node_id].update(neighbors)
def make_test_network_traingle(): ntw = Network(optimisation=NetworkOptimisation.id_only) for i in range(3): ntw.add_node(i + 1) ntw.add_link(1, 2) ntw.add_link(1, 3) ntw.add_link(2, 3) return ntw
def estimate_SI(cls, underlying: Network, theta: float, outcome: dict, initials: set, immunes: set = set(), tmax=1000.0, dt=1): time = .0 my_outcome = outcome.copy() susceptible = set(underlying.nodes_ids) probability = 1. infected = set() infected |= initials susceptible -= immunes | infected while time < tmax: time += dt new_infected = set() for node_id in susceptible: neighbors = underlying.get_in_neighbors_for_node(node_id) n_infected = len(neighbors & infected) if n_infected > 0 or (node_id in my_outcome.keys() and my_outcome[node_id] < time): p_not_infected = (1. - theta * dt) ** n_infected if node_id in my_outcome.keys() and my_outcome[node_id] <= time: probability *= 1.0 - p_not_infected new_infected.add(node_id) else: probability *= p_not_infected for node_id in new_infected: my_outcome.pop(node_id) susceptible -= new_infected infected |= new_infected # print(str(probability) + ' ' + str(infected)) return probability
def __init__(self, net=Network(), name='', base_dir=''): super().__init__(net, name, base_dir) self.post_meta = {} self.posters = {} self.hiddens = set() self.likers = set() self.timestamp = datetime.datetime.now()
def __init__(self, net=Network(optimisation=NetworkOptimisation.id_only), name='', base_dir=''): super().__init__(net, name, base_dir) self.nodes_meta = {} self.crawled_nodes = set() self.counters_meta = {}
def simulate_SIR(cls, underlying: Network, theta: float, infected: set = None, immunes: set = None, immune_p=.0, initial_p=.0, tmax=1000.0, dt=.1, recover_rate=.0, recover_time=.0): susceptible = set(underlying.nodes_ids) outcome_infected = {} outcome_recovered = {} time = .0 rec_const = False if recover_time > 0: rec_const = True if infected is None: infected = set() if immunes is None: immunes = set() if len(infected) == 0 and initial_p > 0: for node_id in susceptible: if node_id not in immunes and random.uniform(0, 1.) < initial_p: infected.add(node_id) outcome_infected[node_id] = time if len(immunes) == 0 and immune_p > 0: for node_id in susceptible: if node_id not in infected and random.uniform(0, 1.) < immune_p: immunes.add(node_id) susceptible -= immunes | infected while time < tmax: time += dt new_infected = set() new_recover = set() for node_id in susceptible: neighbors = underlying.get_in_neighbors_for_node(node_id) n_infected = len(neighbors & infected) if n_infected > 0: if random.uniform(0, 1.) < (1. - (1. - theta*dt) ** n_infected): new_infected.add(node_id) outcome_infected[node_id] = time for node_id in infected: inf_time = outcome_infected[node_id] if rec_const: if time - inf_time >= recover_time: new_recover.add(node_id) outcome_recovered[node_id] = (inf_time, time) outcome_infected.pop(node_id) else: if random.uniform(0, 1.) < recover_rate: new_recover.add(node_id) outcome_recovered[node_id] = (inf_time, time) outcome_infected.pop(node_id) infected |= new_infected susceptible -= new_infected infected -= new_recover for node_id, inf_time in outcome_infected: outcome_recovered[node_id] = (inf_time, -1) return outcome_recovered
def make_test_network_chain(n=31): ntw = Network(optimisation=NetworkOptimisation.id_only) for i in range(n): ntw.add_node(i + 1) for i in range(n - 1): ntw.add_link(i + 1, i + 2) return ntw
def make_test_network_star(): ntw = Network(optimisation=NetworkOptimisation.id_only) for i in range(31): ntw.add_node(i + 1) for i in range(30): ntw.add_link(1, i + 2) return ntw
def simulate_SI_halflife(cls, underlying: Network, theta: float, halflife: float, infected: set = None, immunes: set = None, immune_p=.0, initial_p=.0, tmax=1000.0, dt=1): susceptible = set(underlying.nodes_ids) outcome_infected = {} time = .0 probability = 1. my_infected = infected.copy() if my_infected is None: my_infected = set() if immunes is None: immunes = set() if len(my_infected) == 0 and initial_p > 0: for node_id in susceptible: if node_id not in immunes and random.uniform(0, 1.) < initial_p: my_infected.add(node_id) outcome_infected[node_id] = time if len(immunes) == 0 and immune_p > 0: for node_id in susceptible: if node_id not in my_infected and random.uniform(0, 1.) < immune_p: immunes.add(node_id) susceptible -= immunes | my_infected while time < tmax: time += dt new_infected = set() for node_id in susceptible: neighbors = underlying.get_in_neighbors_for_node(node_id) infected_nbrs = neighbors & my_infected if len(infected_nbrs) > 0: p_not_infected = 1. for neighbor_id in infected_nbrs: time_gone = outcome_infected.get(neighbor_id) if time_gone: time_gone = time - time_gone else: # initialy infected time_gone = time theta_r = theta t = time_gone - halflife while t > 0: theta_r /= 2 t -= halflife p_not_infected *= 1. - theta_r * dt if random.uniform(0, 1.) < (1. - p_not_infected): new_infected.add(node_id) outcome_infected[node_id] = time probability *= 1. - p_not_infected else: probability *= p_not_infected my_infected |= new_infected susceptible -= new_infected #print(str(probability) + ' ' + str(my_infected) + ' ' + str(time)) return {'outcome': outcome_infected, 'p': probability}
def make_test_network_connected(): ntw = Network(optimisation=NetworkOptimisation.id_only) for i in range(31): ntw.add_node(i + 1) for i in range(30): for j in range(i + 1, 31): ntw.add_link(i + 1, j + 1) return ntw
def simulate_SI_confirm(cls, underlying: Network, theta: float, confirm: float, infected: set = None, immunes: set = None, immune_p=.0, initial_p=.0, tmax=1000.0, dt=1): susceptible = set(underlying.nodes_ids) outcome_infected = {} time = .0 probability = 1. my_infected = infected.copy() if my_infected is None: my_infected = set() if immunes is None: immunes = set() if len(my_infected) == 0 and initial_p > 0: for node_id in susceptible: if node_id not in immunes and random.uniform(0, 1.) < initial_p: my_infected.add(node_id) outcome_infected[node_id] = time if len(immunes) == 0 and immune_p > 0: for node_id in susceptible: if node_id not in my_infected and random.uniform(0, 1.) < immune_p: immunes.add(node_id) susceptible -= immunes | my_infected while time < tmax: time += dt new_infected = set() for node_id in susceptible: neighbors = underlying.get_in_neighbors_for_node(node_id) n_infected = len(neighbors & my_infected) if n_infected > 0: if confirm >= .0: if n_infected / len(neighbors) >= confirm: p_not_infected = (1. - theta * dt) ** n_infected else: p_not_infected = (1. - theta / 10. * dt) ** n_infected elif confirm < .0: if n_infected / len(neighbors) < -confirm: p_not_infected = (1. - theta * dt) ** n_infected else: p_not_infected = (1. - theta / 10. * dt) ** n_infected # p_not_infected = (1. - theta * dt) ** (n_infected ** (confirm+1)) if random.uniform(0, 1.) < (1. - p_not_infected): new_infected.add(node_id) outcome_infected[node_id] = time probability *= 1. - p_not_infected else: probability *= p_not_infected my_infected |= new_infected susceptible -= new_infected # print(str(probability) + ' ' + str(infected)) return {'outcome': outcome_infected, 'p': probability}
def simulate_ICM(cls, underlying: Network, theta: float, relic: float = .0, infected: set = None, immunes: set = None, immune_p=.0, initial_p=.0): susceptible = set(underlying.nodes_ids) outcome_infected = {} time = .0 probability = 1. my_infected = infected.copy() if my_infected is None: my_infected = set() if immunes is None: immunes = set() if len(my_infected) == 0 and initial_p > 0: for node_id in susceptible: if node_id not in immunes and random.uniform(0, 1.) < initial_p: my_infected.add(node_id) outcome_infected[node_id] = time if len(immunes) == 0 and immune_p > 0: for node_id in susceptible: if node_id not in my_infected and random.uniform(0, 1.) < immune_p: immunes.add(node_id) susceptible -= immunes | my_infected fresh_infected = my_infected.copy() while len(fresh_infected): new_infected = set() time = time + 1. for node_id in susceptible: neighbors = underlying.get_in_neighbors_for_node(node_id) n_infected = len(neighbors & fresh_infected) if n_infected > 0: p_not_infected = (1. - theta) ** n_infected * (1. - relic) ** len(fresh_infected) if random.uniform(0, 1.) < (1. - p_not_infected): new_infected.add(node_id) outcome_infected[node_id] = time probability *= 1. - p_not_infected else: probability *= p_not_infected my_infected |= new_infected fresh_infected = new_infected susceptible -= new_infected # print(str(probability) + ' ' + str(infected)) return {'outcome': outcome_infected, 'p': probability}
def estimate_SI_halflife(cls, underlying: Network, theta: float, halflife: float, outcome: dict, initials: set, immunes: set = set(), tmax=1000.0, dt=1): time = .0 my_outcome = outcome.copy() susceptible = set(underlying.nodes_ids) probability = 1. infected = set() infected |= initials susceptible -= immunes | infected while time < tmax: time += dt new_infected = set() for node_id in susceptible: neighbors = underlying.get_in_neighbors_for_node(node_id) infected_nbrs = neighbors & infected if len(infected_nbrs) > 0 or (node_id in my_outcome.keys() and my_outcome[node_id] == time): p_not_infected = 1. for neighbor_id in infected_nbrs: time_gone = my_outcome.get(neighbor_id) if time_gone: time_gone = time - time_gone else: # initialy infected time_gone = time theta_r = theta t = time_gone - halflife while t > 0: theta_r /= 2 t -= halflife p_not_infected *= 1. - theta_r * dt if node_id in my_outcome.keys() and my_outcome[node_id] <= time: probability *= 1.0 - p_not_infected new_infected.add(node_id) else: probability *= p_not_infected #for node_id in new_infected: # my_outcome.pop(node_id) susceptible -= new_infected infected |= new_infected #print(str(probability) + ' ' + str(infected) + ' ' + str(time)) return probability
def simulate_SI_decay_confirm_relicexp_hetero(cls, underlying: Network, theta: float, decay: float, confirm: float, relic: float, thetas: dict = None, infected: set = None, immunes: set = None, immune_p=.0, initial_p=.0, tmax=1000.0, dt=1, echo=False): susceptible = set(underlying.nodes_ids) outcome_infected = {} time = .0 probability = 1. my_infected = infected.copy() if my_infected is None: my_infected = set() if immunes is None: immunes = set() if len(my_infected) == 0 and initial_p > 0: for node_id in susceptible: if node_id not in immunes and random.uniform(0, 1.) < initial_p: my_infected.add(node_id) outcome_infected[node_id] = time if len(immunes) == 0 and immune_p > 0: for node_id in susceptible: if node_id not in my_infected and random.uniform(0, 1.) < immune_p: immunes.add(node_id) susceptible -= immunes | my_infected while time < tmax: time += dt new_infected = set() for node_id in susceptible: neighbors = underlying.get_in_neighbors_for_node(node_id) infected_nbrs = neighbors & my_infected p_not_infected = 1. relic_total = .0 for infected_id in my_infected: if outcome_infected.get(infected_id): relic_total += math.exp(-decay * (time - outcome_infected[infected_id])) else: relic_total += math.exp(-decay * time) relic_total *= relic if len(infected_nbrs) > 0: for neighbor_id in infected_nbrs: time_gone = outcome_infected.get(neighbor_id) if time_gone: time_gone = time - time_gone else: # initialy infected time_gone = time if thetas and thetas.get(neighbor_id): p_not_infected *= (1. - thetas[neighbor_id] * dt * (math.exp(-time_gone * decay))) else: p_not_infected *= (1. - theta * dt * (math.exp(-time_gone * decay))) p_not_infected *= (1. - relic_total * dt) if random.uniform(0, 1.) < (1. - p_not_infected): new_infected.add(node_id) outcome_infected[node_id] = time probability *= 1. - p_not_infected else: probability *= p_not_infected my_infected |= new_infected susceptible -= new_infected if echo: print(str(time) + ' ' + str(probability) + ' ' + str(my_infected)) return {'outcome': outcome_infected, 'p': probability}
def remake_network(self, possible_links: dict, uselikes=True, usehiddens=True, dynamic=True, logdyn=False, start_from_zero=False): # print('This method updates network from post_meta, hiddens, likers etc.') self.network = Network() if dynamic: self.network.nodes_attributes.append({ 'id': 'start', 'title': 'start', 'type': 'float' }) self.network.nodes_attributes.append({ 'id': 'n', 'title': 'Underlying_degree', 'type': 'integer' }) self.network.nodes_attributes.append({ 'id': 'g', 'title': 'Is_group', 'type': 'boolean' }) self.network.links_attributes.append({ 'id': 'start', 'title': 'start', 'type': 'float' }) self.network.links_attributes.append({ 'id': 'delay', 'title': 'delay', 'type': 'float' }) if usehiddens: for node_id in self.hiddens: self.network.add_node(node_id) if uselikes: for node_id in self.likers: self.network.add_node(node_id) nodes = self.posters.keys() min_date = float("inf") if start_from_zero: for node_id in nodes: date = self.posters[node_id]['date'] if date < min_date: min_date = date for node_id in nodes: self.network.add_node(node_id) if node_id > 0: self.network.add_meta_for_node(node_id, {'g': "False"}) else: self.network.add_meta_for_node(node_id, {'g': "True"}) date = self.posters[node_id]['date'] neighs_set = possible_links.get(node_id) if neighs_set: self.network.add_meta_for_node(node_id, {'n': len(neighs_set)}) else: self.network.add_meta_for_node(node_id, {'n': 0}) if start_from_zero: date -= min_date if dynamic: if logdyn: self.network.add_meta_for_node( node_id, {'start': math.log(date + 1)}) else: self.network.add_meta_for_node(node_id, {'start': date}) for node2_id in nodes: if node2_id != node_id: date2 = self.posters[node2_id]['date'] if start_from_zero: date2 -= min_date if date < date2: if neighs_set and node2_id in neighs_set: self.network.add_link(node_id, node2_id, mutual=False) self.network.add_meta_for_link( node_id, node2_id, {'delay': date2 - date}) if dynamic: if logdyn: self.network.add_meta_for_link( node_id, node2_id, {'start': math.log(date2 + 1)}) else: self.network.add_meta_for_link( node_id, node2_id, {'start': date2})
def estimate_SI_relic_decay_confirm_continuous(cls, underlying: Network, theta: float, relic: float, decay: float, confirm: .0, confirm_drop: 0.1, outcome: dict, initials: set, immunes: set = set(), tmax=1000.0, echo=False, leafs_degrees={}): time = .0 my_outcome = [] for key, value in outcome.items(): my_outcome.append((key, value)) my_outcome.sort(key=lambda x: x[1]) susceptible = set(underlying.nodes_ids) loglikelyhood = .0 infected = set() infected |= initials susceptible -= immunes | infected leafs_dict = {} n_no_inf_neighbors = 0 virulences = {} for inf_id in infected: virulences[inf_id] = [0, .0, theta] #[start time, integrated, last point] nn = 0 for node_id in underlying.nodes_ids: # make separate storage for leafs never infected (>99% of all nodes) neighbors = underlying.get_in_neighbors_for_node(node_id) if len(neighbors) == 1 and node_id not in outcome.keys(): for n in neighbors: if n in (outcome.keys() | initials): if n not in leafs_dict.keys(): leafs_dict[n] = 0 leafs_dict[n] += 1 else: n_no_inf_neighbors += 1 # leafs having no infected neighbors (>80% of all nodes) nn += 1 if node_id in susceptible: susceptible.remove(node_id) break prev_time = .0 for newinf_id, inf_time in my_outcome: if inf_time == 0.0: continue # calculating integrated infection rates for inf_id, value in virulences.items(): value[1] = theta/decay*(math.exp(decay*(value[0] - prev_time)) - math.exp(decay*(value[0] - inf_time))) value[2] = theta*math.exp(decay*(value[0] - inf_time)) dt = inf_time - prev_time prev_time = inf_time # calculating multipliers for no infection time for sus_id in susceptible: sus_neighbors = underlying.get_in_neighbors_for_node(sus_id) sus_inf_neighbors = sus_neighbors & infected if len(sus_inf_neighbors) > 0: inf_rate = 0 cd = 1. n_neighbors = len(sus_neighbors) if sus_id in leafs_degrees.keys(): n_neighbors = leafs_degrees[sus_id] if n_neighbors == 0: n_neighbors = 100 else: n_neighbors = len(sus_neighbors) if confirm > .0: if len(sus_inf_neighbors)/n_neighbors < confirm: cd = confirm_drop elif confirm < .0: if len(sus_inf_neighbors)/n_neighbors > 1. + confirm: cd = confirm_drop for inf_id in sus_inf_neighbors: # calculate total infection rate inf_rate += virulences[inf_id][1] loglikelyhood -= cd * inf_rate + relic * dt else: loglikelyhood -= relic * dt for nonleaf_id, n_leafs in leafs_dict.items(): if nonleaf_id in infected: #assume that all leafs have enough uninfected friends to not beat the treshold cd = 1. if confirm != 0: cd = confirm_drop loglikelyhood -= n_leafs * (cd * virulences[nonleaf_id][1] + relic * dt) else: loglikelyhood -= n_leafs * relic * dt loglikelyhood -= n_no_inf_neighbors * relic * dt # calculating multiplier for infection neighbors = underlying.get_in_neighbors_for_node(newinf_id) infected_nbrs = neighbors & infected inf_rate = 0 cd = 1. if confirm > .0: if len(infected_nbrs) / len(neighbors) < confirm: cd = confirm_drop elif confirm < .0: if len(infected_nbrs) / len(neighbors) > -confirm: cd = confirm_drop for inf_id in infected_nbrs: # calculate total infection rate inf_rate += virulences[inf_id][2] loglikelyhood += math.log(cd * inf_rate + relic) infected.add(newinf_id) virulences[newinf_id] = [inf_time, .0, theta] if newinf_id in susceptible: susceptible.remove(newinf_id) if echo: print(str(time) + ' ' + str(loglikelyhood)) return loglikelyhood
class InformationConductivity(object): def __init__(self): self.cascades_network = Network() self.underlying = Network() pass def make_cascades_summary(self, cascade_networks, logweight=True): new_nodes = {} new_links = {} self.cascades_network = Network() for cascade in cascade_networks: for node_id in cascade.network.nodes_ids: if new_nodes.get(node_id) is None: new_nodes[node_id] = 0 new_nodes[node_id] += 1 for from_id, to_id in cascade.network.links.keys(): if new_links.get((from_id, to_id)) is None: new_links[(from_id, to_id)] = 0 new_links[(from_id, to_id)] += 1 self.cascades_network.nodes_attributes.append({'id': 'w', 'title': 'LogWeight', 'type': 'float'}) for node_id, quantity in new_nodes.items(): self.cascades_network.add_node(node_id) if logweight: w = math.log(quantity) + 1 else: w = quantity self.cascades_network.add_meta_for_node(node_id, {'w': w}) for link, quantity in new_links.items(): if logweight: w = math.log(quantity) + 1 else: w = quantity self.cascades_network.add_link(link[0], link[1], mutual=False, weighted=True, weight=w) def make_underlying_summary(self, underlyings): if len(underlyings) == 1: self.underlying = underlyings[0].network else: self.underlying = Network(optimisation=NetworkOptimisation.id_only) for underlying in underlyings: for node_id, neighbors in underlying.network.nodes.items(): self.underlying.add_node(node_id) self.underlying.nodes[node_id].update(neighbors) def nodes_summary(self): summary = {'in': [], 'out': [], 'in_w': [], 'out_w': [], 'degree': [], 'w': []} for node_id, node_data in self.cascades_network.nodes.items(): degrees = self.cascades_network.node_degree(node_id) weights = self.cascades_network.node_weighted_degree(node_id) summary['in'].append(degrees['in']) summary['out'].append(degrees['out']) summary['in_w'].append(weights['in']) summary['out_w'].append(weights['out']) summary['degree'].append(self.underlying.node_degree(node_id)['inout']) summary['w'].append(self.cascades_network.meta_for_node(node_id, 'w')) return summary
def estimate_SI_relic_halflife_continuous(cls, underlying: Network, theta: float, relic: float, halflife: float, outcome: dict, initials: set, immunes: set = set(), tmax=1000.0, echo=False): time = .0 my_outcome = [] for key, value in outcome.items(): my_outcome.append((key, value)) my_outcome.sort(key=lambda x: x[1]) susceptible = set(underlying.nodes_ids) loglikelyhood = .0 infected = set() infected |= initials susceptible -= immunes | infected leafs_dict = {} n_no_inf_neighbors = 0 virulences = {} for inf_id in infected: virulences[inf_id] = [halflife, theta, 0.] nn = 0 for node_id in underlying.nodes_ids: # make separate storage for leafs never infected (>99% of all nodes) neighbors = underlying.get_in_neighbors_for_node(node_id) if len(neighbors) == 1 and node_id not in outcome.keys(): for n in neighbors: if n in (outcome.keys() | initials): if n not in leafs_dict.keys(): leafs_dict[n] = 0 leafs_dict[n] += 1 else: n_no_inf_neighbors += 1 #leafs having no infected neighbors (>80% of all nodes) nn += 1 if node_id in susceptible: susceptible.remove(node_id) break prev_time = .0 for newinf_id, inf_time in my_outcome: if inf_time == 0.0: continue dt = inf_time - prev_time prev_time = inf_time #calculating integrated infection rates for inf_id, value in virulences.items(): if dt > value[0]: #dt * theta value[2] = value[0] * value[1] else: value[2] = dt * value[1] value[0] -= dt while value[0] < .0: value[1] /= 2 # halflifing value[0] += halflife if value[0] < .0: value[2] += value[1] * halflife else: value[2] += value[1] * (halflife - value[0]) #calculating multipliers for no infection time for sus_id in susceptible: sus_neighbors = underlying.get_in_neighbors_for_node(sus_id) sus_inf_neighbors = sus_neighbors & infected if len(sus_inf_neighbors) > 0: inf_rate = 0 for inf_id in sus_inf_neighbors: # calculate total infection rate inf_rate += virulences[inf_id][2] loglikelyhood -= inf_rate + relic * dt else: loglikelyhood -= relic * dt for nonleaf_id, n_leafs in leafs_dict.items(): if nonleaf_id in infected: loglikelyhood -= n_leafs * (virulences[nonleaf_id][2] + relic * dt) else: loglikelyhood -= n_leafs * relic * dt loglikelyhood -= n_no_inf_neighbors * relic * dt #calculating multiplier for infection neighbors = underlying.get_in_neighbors_for_node(newinf_id) inf_rate = 0 for inf_id in neighbors & infected: #calculate total infection rate inf_rate += virulences[inf_id][1] loglikelyhood += math.log(inf_rate + relic) infected.add(newinf_id) virulences[newinf_id] = [halflife, theta, 0.] if newinf_id in susceptible: susceptible.remove(newinf_id) if echo: print(str(time) + ' ' + str(loglikelyhood)) return loglikelyhood
def estimate_SI_relic_continuous(cls, underlying: Network, theta: float, relic: float, outcome: dict, initials: set, immunes: set = set(), tmax=1000.0, echo = False): time = .0 my_outcome = [] for key, value in outcome.items(): my_outcome.append((key, value)) my_outcome.sort(key=lambda x: x[1]) susceptible = set(underlying.nodes_ids) loglikelyhood = .0 infected = set() infected |= initials susceptible -= immunes | infected leafs_dict = {} n_no_inf_neighbors = 0 nn = 0 for node_id in underlying.nodes_ids: #make separate storage for leafs never infected (>99% of al nodes) neighbors = underlying.get_in_neighbors_for_node(node_id) if len(neighbors) == 1 and node_id not in outcome.keys(): for n in neighbors: if n in (outcome.keys() | initials): if n not in leafs_dict.keys(): leafs_dict[n] = 0 leafs_dict[n] += 1 else: n_no_inf_neighbors += 1 #leafs having no infected neighbors (>80% of all nodes) nn += 1 if node_id in susceptible: susceptible.remove(node_id) break prev_time = .0 for newinf_id, inf_time in my_outcome: # print('PyNInfTot: ' + str(len(infected))) if inf_time == 0.0: continue dt = inf_time - prev_time prev_time = inf_time neighbors = underlying.get_in_neighbors_for_node(newinf_id) n_infected = len(neighbors & infected) loglikelyhood += math.log(n_infected * theta + len(infected) * relic) for sus_id in susceptible: sus_neighbors = underlying.get_in_neighbors_for_node(sus_id) sus_n_infected = len(sus_neighbors & infected) if sus_n_infected > 0: loglikelyhood -= (sus_n_infected * theta + len(infected) * relic) * dt else: loglikelyhood -= len(infected) * relic * dt for nonleaf_id, n_leafs in leafs_dict.items(): if nonleaf_id in infected: loglikelyhood -= n_leafs * (theta + len(infected) * relic) * dt else: loglikelyhood -= n_leafs * len(infected) * relic * dt loglikelyhood -= n_no_inf_neighbors * len(infected) * relic * dt infected.add(newinf_id) if newinf_id in susceptible: susceptible.remove(newinf_id) if echo: print(str(prev_time) + ' ' + str(loglikelyhood)) return loglikelyhood
class ICNetworkManager(NetworkManager): def __init__(self, net=Network(), name='', base_dir=''): super().__init__(net, name, base_dir) self.post_meta = {} self.posters = {} self.hiddens = set() self.likers = set() self.timestamp = datetime.datetime.now() def get_data_dict(self): data_dict = super().get_data_dict() data_dict['post_meta'] = self.post_meta data_dict['posters'] = self.posters data_dict['hiddens'] = self.hiddens data_dict['likers'] = self.likers data_dict['timestamp'] = self.timestamp return data_dict def set_data_dict(self, data_dict): super().set_data_dict(data_dict) self.post_meta = data_dict['post_meta'] self.posters = data_dict['posters'] self.hiddens = data_dict['hiddens'] self.likers = data_dict['likers'] self.timestamp = data_dict['timestamp'] def crawl_next(self): if len(self.crawl_plan) == 0: # print('Crawl plan is length of zero') return 0 crawler = self.crawl_plan[0] result = self.crawl_post(crawler) if result == 'empty': self.crawl_plan.pop(0) if result != 'error': return 1 else: return -1 def crawl_post(self, crawler): if crawler['stage'] == 0: source_id = crawler['source_id'] post_id = crawler['post_id'] meta = crlr.get_root_post_for_wall_with_meta(source_id, post_id) if vk.is_error(meta): if vk.error_code( meta) != 666: #666 is the code if no root post found print('Error: ' + str(meta['error']['error_code']) + ' ' + meta['error']['error_msg']) return 'error' return 'empty' self.post_meta = meta self.posters[source_id] = self.post_meta['postinfo'] if self.posters[source_id].get('likes') is not None: crawler['likes_to_process'] |= self.posters[source_id]['likes'] crawler['stage'] = 1 return 'done' return 'empty' elif crawler['stage'] == 1: source_id = crawler['source_id'] post_id = crawler['post_id'] likes_to_process = crawler['likes_to_process'] likes_processed = crawler['likes_processed'] if len(likes_to_process) == 0: return 'empty' user_id = likes_to_process.pop() content_md5 = self.post_meta['md5'] search_string = self.post_meta['search_string'] source_date = self.post_meta['postinfo']['date'] new_post_info = crlr.find_post_on_wall( user_id, content_md5, search_string, source_id, source_date, use_cache=True, cache_date_utc=(self.timestamp.timestamp() - 25200), original_id=post_id) if vk.is_error(new_post_info): likes_to_process.add(user_id) print('Error: ' + str(new_post_info['error']['error_code']) + ' ' + new_post_info['error']['error_msg']) return 'error' if new_post_info['type'] == 'poster': print(new_post_info) if vk.is_error(new_post_info['likes']): if vk.error_code(new_post_info['likes']) == 15: new_post_info['likes'] = set() self.posters[user_id] = new_post_info likes_processed.add(user_id) if len(new_post_info['likes']): likes_to_process |= new_post_info['likes'] - likes_processed if len(new_post_info['copy_history']): for copy_case in new_post_info['copy_history']: if copy_case['owner_id'] not in likes_processed: likes_to_process.add(copy_case['owner_id']) if copy_case['from_id'] not in likes_processed: likes_to_process.add(copy_case['from_id']) elif new_post_info['type'] == 'hidden': self.hiddens.add(user_id) elif new_post_info['type'] == 'liker': self.likers.add(user_id) def schedule_crawl_post_from_source(self, source_id, post_id): self.post_meta = {} self.posters = {} self.hiddens = set() self.likers = set() crawler = { 'type': 'post', 'stage': 0, 'source_id': source_id, 'post_id': post_id, 'likes_to_process': set(), 'likes_processed': set() } self.crawl_plan.append(crawler) def remake_network(self, possible_links: dict, uselikes=True, usehiddens=True, dynamic=True, logdyn=False, start_from_zero=False): # print('This method updates network from post_meta, hiddens, likers etc.') self.network = Network() if dynamic: self.network.nodes_attributes.append({ 'id': 'start', 'title': 'start', 'type': 'float' }) self.network.nodes_attributes.append({ 'id': 'n', 'title': 'Underlying_degree', 'type': 'integer' }) self.network.nodes_attributes.append({ 'id': 'g', 'title': 'Is_group', 'type': 'boolean' }) self.network.links_attributes.append({ 'id': 'start', 'title': 'start', 'type': 'float' }) self.network.links_attributes.append({ 'id': 'delay', 'title': 'delay', 'type': 'float' }) if usehiddens: for node_id in self.hiddens: self.network.add_node(node_id) if uselikes: for node_id in self.likers: self.network.add_node(node_id) nodes = self.posters.keys() min_date = float("inf") if start_from_zero: for node_id in nodes: date = self.posters[node_id]['date'] if date < min_date: min_date = date for node_id in nodes: self.network.add_node(node_id) if node_id > 0: self.network.add_meta_for_node(node_id, {'g': "False"}) else: self.network.add_meta_for_node(node_id, {'g': "True"}) date = self.posters[node_id]['date'] neighs_set = possible_links.get(node_id) if neighs_set: self.network.add_meta_for_node(node_id, {'n': len(neighs_set)}) else: self.network.add_meta_for_node(node_id, {'n': 0}) if start_from_zero: date -= min_date if dynamic: if logdyn: self.network.add_meta_for_node( node_id, {'start': math.log(date + 1)}) else: self.network.add_meta_for_node(node_id, {'start': date}) for node2_id in nodes: if node2_id != node_id: date2 = self.posters[node2_id]['date'] if start_from_zero: date2 -= min_date if date < date2: if neighs_set and node2_id in neighs_set: self.network.add_link(node_id, node2_id, mutual=False) self.network.add_meta_for_link( node_id, node2_id, {'delay': date2 - date}) if dynamic: if logdyn: self.network.add_meta_for_link( node_id, node2_id, {'start': math.log(date2 + 1)}) else: self.network.add_meta_for_link( node_id, node2_id, {'start': date2}) # print('Link: ' + str(node_id) + ' -> ' + str(node2_id)) # print(str(node_id) + ' : ' + str(self.posters[node_id])) def get_minimum_delay(self): min_delay = float('inf') for link_key in self.network.links.keys(): delay = self.network.meta_for_link(link_key[0], link_key[1], 'delay') if delay < min_delay: min_delay = delay return min_delay def get_outcome(self, normalization_factor=1.0): min_date = float("inf") outcome = {} for node_id, node_data in self.posters.items(): date = node_data['date'] if date < min_date: min_date = date for node_id, node_data in self.posters.items(): outcome[node_id] = (node_data['date'] - min_date) / normalization_factor return outcome def get_outcome_connected_only(self, possible_links: dict, normalization_factor=1.0): outcome = self.get_outcome(normalization_factor) self.remake_network(possible_links) connected_nodes = set() border = set() for node_id, time in outcome.items(): if time <= .0: border.add(node_id) while len(border): new_border = set() for node_id in border: node = self.network.nodes.get(node_id) print(node) if node: if len(node['out']): new_border |= set(node['out']) connected_nodes |= border new_border -= connected_nodes border = new_border new_outcome = {} for node_id, time in outcome.items(): if node_id in connected_nodes: new_outcome[node_id] = time return new_outcome
def __init__(self): self.cascades_network = Network() self.underlying = Network() pass
def make_test_network(): ntw = Network(optimisation=NetworkOptimisation.id_only) for i in range(31): ntw.add_node(i + 1) ntw.add_link(1, 2) ntw.add_link(1, 3) ntw.add_link(2, 3) ntw.add_link(3, 4) ntw.add_link(4, 5) ntw.add_link(4, 6) ntw.add_link(5, 6) ntw.add_link(4, 7) ntw.add_link(7, 8) ntw.add_link(7, 9) ntw.add_link(7, 10) ntw.add_link(8, 10) ntw.add_link(9, 10) ntw.add_link(9, 11) ntw.add_link(11, 12) ntw.add_link(11, 13) ntw.add_link(12, 13) ntw.add_link(13, 14) ntw.add_link(8, 15) ntw.add_link(3, 16) ntw.add_link(16, 17) ntw.add_link(17, 18) ntw.add_link(18, 19) ntw.add_link(19, 20) ntw.add_link(15, 20) ntw.add_link(1, 21) ntw.add_link(1, 22) ntw.add_link(1, 23) ntw.add_link(1, 24) ntw.add_link(1, 25) ntw.add_link(1, 26) ntw.add_link(2, 21) ntw.add_link(2, 22) ntw.add_link(2, 23) ntw.add_link(2, 24) ntw.add_link(2, 25) ntw.add_link(2, 26) ntw.add_link(3, 21) ntw.add_link(3, 22) ntw.add_link(3, 23) ntw.add_link(3, 24) ntw.add_link(3, 25) ntw.add_link(3, 26) return ntw
def estimate_SI_decay_confirm_relicexp_hetero(cls, underlying: Network, theta: float, decay: float, confirm: float, relic: float, outcome: dict, thetas: dict = None, initials: set = None, immunes: set = set(), immune_p=.0, initial_p=.0, tmax=1000.0, dt=1, echo=False): time = .0 my_outcome = outcome.copy() susceptible = set(underlying.nodes_ids) probability = 1. infected = set() infected |= initials susceptible -= immunes | infected i = 0 dprob_not = 1. while time < tmax and len(susceptible) > 0: time += dt new_infected = set() dprob_inf = 1. totrel=0 for node_id in susceptible: neighbors = underlying.get_in_neighbors_for_node(node_id) infected_nbrs = neighbors & infected p_not_infected = 1. relic_total = .0 for infected_id in infected: if outcome.get(infected_id): relic_total += math.exp(-decay * (time - outcome[infected_id])) else: relic_total += math.exp(-decay * time) relic_total *= relic totrel = relic_total if len(infected_nbrs) > 0: for neighbor_id in infected_nbrs: time_gone = outcome.get(neighbor_id) if time_gone: time_gone = time - time_gone else: # initialy infected time_gone = time if thetas and thetas.get(neighbor_id): p_not_infected *= (1. - thetas[neighbor_id] * dt * (math.exp(-time_gone * decay))) else: p_not_infected *= (1. - theta * dt * (math.exp(-time_gone * decay))) p_not_infected *= (1. - relic_total * dt) if node_id in my_outcome.keys() and my_outcome[node_id] <= time: probability *= 1.0 - p_not_infected dprob_inf *= 1.0 - p_not_infected new_infected.add(node_id) else: probability *= p_not_infected dprob_not *= p_not_infected for node_id in new_infected: my_outcome.pop(node_id) susceptible -= new_infected infected |= new_infected # print(str(probability) + ' ' + str(infected)) if echo and len(new_infected): #print(str(list(new_infected)[0]) + ' ' + str(time) + ' ' + str(math.log(probability/(dt**(len(outcome)-1))))) #print(str(list(new_infected)[0]) + ' ' + str(time) + ' ' + str(math.log(dprob_inf / dt))) print(str(list(new_infected)[0]) + ' ' + str(time) + ' ' + str(math.log(dprob_not)) + ' ' + str(math.log(dprob_inf / dt)) + ' ' + str(math.log(probability/(dt**(len(infected-initials)))))) print('nr'+str(len(susceptible|new_infected)) + ' ' + str(totrel)) dprob_not = 1. #print('tail ' + str(time) + ' ' + str(math.log(dprob_not)) + ' ' + str(math.log(probability/(dt**(len(infected-initials)))))) #print(time) return probability
def __init__(self, net=Network(), name='', base_dir=''): self.network = net self.name = name self.base_dir = base_dir self.source = NetworkSource.vkontakte self.crawl_plan = []