Exemplo n.º 1
0
def GetTemporalClosenessInstantaneous(t, start_t=0, delta=1):
    """Calculates the temporal closeness values of 
    all nodes for a given start time start_t in a temporal network t.
    This function returns a numpy array of (temporal) closeness centrality values. 
    The ordering of these values corresponds to the ordering of nodes in the vertex 
    sequence of the igraph first order time-aggregated network. A mapping between node names
    and array indices can be found in Utilities.firstOrderNameMap().
    
    @param t: the temporal network for which temporal closeness centralities will be computed
    @param start_t: the start time for which to consider time-respecting paths (default 0). This is 
        important, since any unambigious definition of a shortest time-respecting path between
        two nodes must include the time range to be considered (c.f. Holme and Saramäki, Phys. Rep., 2012)
    @param delta: the maximum time difference time used in the time-respecting path definition (default 1)
        Note that this parameter is independent from the delta used internally for the extraction of two-paths
        by the class TemporalNetwork.
    """
    
    closeness = np.array([0.]*len(t.nodes))

    # Calculate all shortest time-respecting paths
    D, paths = Paths.GetTemporalDistanceMatrix(t, start_t, delta, collect_paths=False)

    # Get a mapping between node names and matrix indices
    name_map = Utilities.firstOrderNameMap( t )

    # Calculate closeness for each node u, by summing the reciprocal of its 
    # distances to all other nodes. Note that this definition of closeness centrality 
    # is required for directed networks that are not strongly connected. 
    for u in t.nodes:
        for v in t.nodes:
            if u!=v:
                closeness[name_map[u]] += 1./D[name_map[v], name_map[u]]

    return closeness
Exemplo n.º 2
0
def GetStaticEigenvectorCentrality(t, model='SECOND'):
    """Computes eigenvector centralities of nodes in the second-order aggregate network, 
    and aggregates eigenvector centralities to obtain the eigenvector centrality of nodes in the 
    first-order network.
    
    @param t: The temporalnetwork instance to work on
    @param model: either C{"SECOND"} or C{"NULL"}, where C{"SECOND"} is the 
      the default value."""

    if (model is "SECOND" or "NULL") == False:
        raise ValueError("model must be one of \"SECOND\" or \"NULL\"")

    name_map = Utilities.firstOrderNameMap(t)

    if model == 'SECOND':
        g2 = t.igraphSecondOrder()
    else:
        g2 = t.igraphSecondOrderNull()

    # Compute eigenvector centrality in second-order network
    A = Utilities.getSparseAdjacencyMatrix(g2,
                                           attribute="weight",
                                           transposed=True)
    evcent_2 = Utilities.StationaryDistribution(A, False)

    # Aggregate to obtain first-order eigenvector centrality
    evcent_1 = np.zeros(len(name_map))
    sep = t.separator
    for i in range(len(evcent_2)):
        # Get name of target node
        target = g2.vs()[i]["name"].split(sep)[1]
        evcent_1[name_map[target]] += np.real(evcent_2[i])

    return np.real(evcent_1 / sum(evcent_1))
Exemplo n.º 3
0
def GetStaticEigenvectorCentrality(t, model='SECOND'):
    """Computes eigenvector centralities of nodes in the second-order aggregate network, 
    and aggregates eigenvector centralities to obtain the eigenvector centrality of nodes in the 
    first-order network.
    
    @param t: The temporalnetwork instance to work on
    @param model: either C{"SECOND"} or C{"NULL"}, where C{"SECOND"} is the 
      the default value."""

    if (model is "SECOND" or "NULL") == False:
        raise ValueError("model must be one of \"SECOND\" or \"NULL\"")

    name_map = Utilities.firstOrderNameMap(t)
    
    if model == 'SECOND':
        g2 = t.igraphSecondOrder()
    else:
        g2 = t.igraphSecondOrderNull()
    
    # Compute eigenvector centrality in second-order network
    A = Utilities.getSparseAdjacencyMatrix( g2, attribute="weight", transposed=True )
    evcent_2 = Utilities.StationaryDistribution( A, False )
    
    # Aggregate to obtain first-order eigenvector centrality
    evcent_1 = np.zeros(len(name_map))
    sep = t.separator
    for i in range(len(evcent_2)):
        # Get name of target node
        target = g2.vs()[i]["name"].split(sep)[1]
        evcent_1[name_map[target]] += np.real(evcent_2[i])
    
    return np.real(evcent_1/sum(evcent_1))
Exemplo n.º 4
0
def GetTemporalBetweenness(t, delta=1, normalized=False):
    """Calculates the temporal betweenness centralities of all nodes 
    in a temporal network t based on the shortest time-respecting paths with a 
    maximum waiting time of delta. This function returns a numpy array of temporal betweenness centrality values of 
    nodes. The ordering of these values corresponds to the ordering of nodes in the vertex sequence 
    of the igraph first order time-aggregated network. A mapping between node names and array 
    indices can be found in  Utilities.firstOrderNameMap().
    
    @param t: the temporal network for which temporal closeness centralities will be computed    
    @param delta: the maximum time difference used in the time-respecting path definition (default 1).
        Note that this parameter is independent from the delta used internally for the extraction of two-paths
        by the class TemporalNetwork
    @param normalized: whether or not to normalize centralities by dividing each value byt the total number 
        of shortest time-respecting paths.
    """

    bw = np.array([0] * len(t.nodes))
    S = 0

    name_map = Utilities.firstOrderNameMap(t)

    minD, minPaths = Paths.GetMinTemporalDistance(t,
                                                  delta=1,
                                                  collect_paths=True)

    for v in t.nodes:
        for w in t.nodes:
            for p in minPaths[v][w]:
                for i in range(1, len(p) - 1):
                    bw[name_map[p[i][0]]] += 1
                    S += 1
    return bw
Exemplo n.º 5
0
def GetFirstOrderDistanceMatrix(t):
    """Calculates a matrix D containing the shortest path lengths between all
    pairs of nodes calculated based on the topology of the *first-order* aggregate network. 
    The ordering of rows/columns corresponds to the ordering of nodes in the vertex sequence of 
    the igraph first order time-aggregated network. A mapping between nodes and indices can be 
    found in Utilities.firstOrderNameMap().    
    
    @param t: the temporal network to calculate shortest path lengths for based on a first-order
        aggregate representation    
    """

    # This way of generating the first-order time-aggregated network makes sure that
    # links are not omitted even if they do not contribute to any time-respecting path
    g1 = t.igraphFirstOrder(all_links=False, force=True)

    name_map = Utilities.firstOrderNameMap(t)

    D = np.zeros(shape=(len(t.nodes), len(t.nodes)))
    D.fill(np.inf)
    np.fill_diagonal(D, 0)

    for v in g1.vs()["name"]:
        for w in g1.vs()["name"]:
            # Compute all shortest paths using igraph
            X = g1.get_shortest_paths(v, w)
            for p in X:
                if len(p) > 0:
                    D[name_map[v], name_map[w]] = len(p) - 1
    return D
Exemplo n.º 6
0
def GetStaticPageRank(t, model='SECOND'):
    """Computes PageRank of nodes based on the second-order aggregate network, 
    and aggregates PageRank values to obtain the PageRank of nodes in the
    first-order network.
    
    @param t: The temporalnetwork instance to work on
    @param model: either C{"SECOND"} or C{"NULL"}, where C{"SECOND"} is the 
      the default value.
    """

    if (model is "SECOND" or "NULL") == False:
        raise ValueError("model must be one of \"SECOND\" or \"NULL\"")

    name_map = Utilities.firstOrderNameMap( t )

    if model == 'SECOND':
        g2 = t.igraphSecondOrder()
    else:
        g2 = t.igraphSecondOrderNull()    

    # Compute betweenness centrality in second-order network
    pagerank_2 = np.array(g2.pagerank(weights=g2.es()['weight'], directed=True))
    
    # Aggregate to obtain first-order eigenvector centrality
    pagerank_1 = np.zeros(len(name_map))
    sep = t.separator
    for i in range(len(pagerank_2)):
        # Get name of target node
        target = g2.vs()[i]["name"].split(sep)[1]
        pagerank_1[name_map[target]] += pagerank_2[i]
    
    return pagerank_1/sum(pagerank_1)
Exemplo n.º 7
0
def GetStaticCloseness(t, model='SECOND'):
    """Computes closeness centralities of nodes based on the first- or second-order time-aggregated network.
    
    @param t: The temporal network instance for which closeness centralities will be computed
    @param model: either C{"FIRST"}, C{"SECOND"} or C{"SECONDNULL"}, where C{"SECOND"} is the 
      the default value.
    """

    if model =='FIRST':
        D = Paths.GetFirstOrderDistanceMatrix(t)
    else:
        D = Paths.GetSecondOrderDistanceMatrix(t, model)

    name_map = Utilities.firstOrderNameMap( t )

    closeness = np.zeros(len(name_map))

    # Calculate closeness for each node u, by summing the reciprocal of its 
    # distances to all other nodes. Note that this definition of closeness centrality 
    # is required for directed networks that are not strongly connected. 
    for u in t.nodes:
        for v in t.nodes:
            if u!=v:
                closeness[name_map[u]] += 1./D[name_map[v], name_map[u]] 
    return closeness
Exemplo n.º 8
0
def GetTemporalCloseness(t, delta=1):
    """Calculates the temporal closeness centralities of all nodes 
    in a temporal network t, based on the minimal shortest time-respecting paths with a 
    maximum time difference of delta. This function then returns a numpy 
    array of average (temporal) closeness centrality values of nodes. The ordering of these 
    values corresponds to the ordering of nodes in the vertex sequence of the igraph first order 
    time-aggregated network. A mapping between node names and array indices can be found in 
    Utilities.firstOrderNameMap().
    
    @param t: the temporal network for which temporal closeness centralities will be computed    
    @param delta: the maximum waiting time used in the time-respecting path definition (default 1)      
        Note that this parameter is independent from the delta used internally for the extraction of two-paths
        by the class TemporalNetwork     
    """

    cl = np.array([0.]*len(t.nodes))

    name_map = Utilities.firstOrderNameMap( t )

    minD, minPaths = Paths.GetMinTemporalDistance(t, delta, collect_paths=False)

    for u in t.nodes:
        for v in t.nodes:
            if u!= v:
                cl[name_map[v]] += 1./minD[name_map[u], name_map[v]]
    return cl
Exemplo n.º 9
0
def GetFirstOrderDistanceMatrix(t):        
    """Calculates a matrix D containing the shortest path lengths between all
    pairs of nodes calculated based on the topology of the *first-order* aggregate network. 
    The ordering of rows/columns corresponds to the ordering of nodes in the vertex sequence of 
    the igraph first order time-aggregated network. A mapping between nodes and indices can be 
    found in Utilities.firstOrderNameMap().    
    
    @param t: the temporal network to calculate shortest path lengths for based on a first-order
        aggregate representation    
    """   

    # This way of generating the first-order time-aggregated network makes sure that 
    # links are not omitted even if they do not contribute to any time-respecting path
    g1 = t.igraphFirstOrder(all_links=False, force=True)

    name_map = Utilities.firstOrderNameMap( t )

    D = np.zeros(shape=(len(t.nodes),len(t.nodes)))
    D.fill(np.inf)
    np.fill_diagonal(D, 0)

    for v in g1.vs()["name"]:
        for w in g1.vs()["name"]:
            # Compute all shortest paths using igraph
            X = g1.get_shortest_paths(v,w)
            for p in X:
                if len(p)>0:
                    D[name_map[v], name_map[w]] = len(p)-1
    return D
Exemplo n.º 10
0
def GetTemporalBetweenness(t, delta=1, normalized=False):
    """Calculates the temporal betweenness centralities of all nodes 
    in a temporal network t based on the shortest time-respecting paths with a 
    maximum waiting time of delta. This function returns a numpy array of temporal betweenness centrality values of 
    nodes. The ordering of these values corresponds to the ordering of nodes in the vertex sequence 
    of the igraph first order time-aggregated network. A mapping between node names and array 
    indices can be found in  Utilities.firstOrderNameMap().
    
    @param t: the temporal network for which temporal closeness centralities will be computed    
    @param delta: the maximum time difference used in the time-respecting path definition (default 1).
        Note that this parameter is independent from the delta used internally for the extraction of two-paths
        by the class TemporalNetwork
    @param normalized: whether or not to normalize centralities by dividing each value byt the total number 
        of shortest time-respecting paths.
    """

    bw = np.array([0]*len(t.nodes))
    S = 0

    name_map = Utilities.firstOrderNameMap(t)

    minD, minPaths = Paths.GetMinTemporalDistance(t, delta=1, collect_paths=True)

    for v in t.nodes:
        for w in t.nodes:
            for p in minPaths[v][w]:
                for i in range(1,len(p)-1):
                    bw[name_map[p[i][0]]] += 1
                    S+=1
    return bw
Exemplo n.º 11
0
def GetTemporalCloseness(t, delta=1):
    """Calculates the temporal closeness centralities of all nodes 
    in a temporal network t, based on the minimal shortest time-respecting paths with a 
    maximum time difference of delta. This function then returns a numpy 
    array of average (temporal) closeness centrality values of nodes. The ordering of these 
    values corresponds to the ordering of nodes in the vertex sequence of the igraph first order 
    time-aggregated network. A mapping between node names and array indices can be found in 
    Utilities.firstOrderNameMap().
    
    @param t: the temporal network for which temporal closeness centralities will be computed    
    @param delta: the maximum waiting time used in the time-respecting path definition (default 1)      
        Note that this parameter is independent from the delta used internally for the extraction of two-paths
        by the class TemporalNetwork     
    """

    cl = np.array([0.] * len(t.nodes))

    name_map = Utilities.firstOrderNameMap(t)

    minD, minPaths = Paths.GetMinTemporalDistance(t,
                                                  delta,
                                                  collect_paths=False)

    for u in t.nodes:
        for v in t.nodes:
            if u != v:
                cl[name_map[v]] += 1. / minD[name_map[u], name_map[v]]
    return cl
Exemplo n.º 12
0
def GetStaticCloseness(t, model='SECOND'):
    """Computes closeness centralities of nodes based on the first- or second-order time-aggregated network.
    
    @param t: The temporal network instance for which closeness centralities will be computed
    @param model: either C{"FIRST"}, C{"SECOND"} or C{"SECONDNULL"}, where C{"SECOND"} is the 
      the default value.
    """

    if model == 'FIRST':
        D = Paths.GetFirstOrderDistanceMatrix(t)
    else:
        D = Paths.GetSecondOrderDistanceMatrix(t, model)

    name_map = Utilities.firstOrderNameMap(t)

    closeness = np.zeros(len(name_map))

    # Calculate closeness for each node u, by summing the reciprocal of its
    # distances to all other nodes. Note that this definition of closeness centrality
    # is required for directed networks that are not strongly connected.
    for u in t.nodes:
        for v in t.nodes:
            if u != v:
                closeness[name_map[u]] += 1. / D[name_map[v], name_map[u]]
    return closeness
Exemplo n.º 13
0
def GetTemporalBetweennessInstantaneous(t,
                                        start_t=0,
                                        delta=1,
                                        normalized=False):
    """Calculates the temporal betweennness values of 
    all nodes fir a given start time start_t in an empirical temporal network t.
    This function returns a numpy array of (temporal) betweenness centrality values. 
    The ordering of these values corresponds to the ordering of nodes in the vertex 
    sequence of the igraph first order time-aggregated network. A mapping between node names
    and array indices can be found in Utilities.firstOrderNameMap().
    
    @param t: the temporal network for which temporal betweenness centralities will be computed
    @param start_t: the start time for which to consider time-respecting paths (default 0). This is 
        important, since any unambigious definition of a shortest time-respecting path between
        two nodes must include the time range to be considered (c.f. Holme and Saramäki, Phys. Rep., 2012)
    @param delta: the maximum waiting time used in the time-respecting path definition (default 1)
        Note that this parameter is independent from the delta used internally for the extraction of two-paths
        by the class TemporalNetwork
    @param normalized: whether or not to normalize the temporal betweenness centrality values by
    dividing by the number of all shortest time-respecting paths in the temporal network.
    """

    bw = np.array([0] * len(t.nodes))

    # First calculate all shortest time-respecting paths starting at time start_t
    D, paths = Paths.GetTemporalDistanceMatrix(t,
                                               start_t,
                                               delta,
                                               collect_paths=True)

    # Get a mapping between node names and matrix indices
    name_map = Utilities.firstOrderNameMap(t)

    # Compute betweenness scores of all nodes based on shortest time-respecting paths
    k = 0
    for u in t.nodes:
        for v in t.nodes:
            if u != v:
                for p in paths[u][v]:
                    for i in range(1, len(p) - 1):
                        bw[name_map[p[i][0]]] += 1
                        k += 1

    # Normalize by dividing by the total number of shortest time-respecting paths
    if normalized:
        bw = bw / k
    return bw
Exemplo n.º 14
0
def GetStaticPageRank(t,
                      model='SECOND',
                      projection='TARGET',
                      normalization=False):
    """Computes PageRank of nodes based on the second-order aggregate network, 
    and aggregates PageRank values to obtain the PageRank of nodes in the
    first-order network.
    
    @param t: The temporalnetwork instance to work on
    @param model: either C{"SECOND"} or C{"NULL"}, where C{"SECOND"} is the 
      the default value.
    """

    assert model is "SECOND" or model is "NULL"
    assert projection is 'TARGET' or projection is 'SOURCE'

    name_map = Utilities.firstOrderNameMap(t)

    if model == 'SECOND':
        g2 = t.igraphSecondOrder()
    else:
        g2 = t.igraphSecondOrderNull()

    # Compute pagerank centrality in second-order network
    pagerank_2 = np.array(g2.pagerank(weights=g2.es()['weight'],
                                      directed=True))

    # Aggregate to obtain first-order pagerank centrality
    pagerank_1 = np.zeros(len(name_map))
    counts = np.array([1] * len(name_map))
    sep = t.separator
    for i in range(len(pagerank_2)):
        # Get name of target node
        if projection == 'TARGET':
            target = g2.vs()[i]["name"].split(sep)[1]
            pagerank_1[name_map[target]] += pagerank_2[i]
            counts[name_map[target]] += 1
        else:
            source = g2.vs()[i]["name"].split(sep)[0]
            pagerank_1[name_map[source]] += pagerank_2[i]
            counts[name_map[source]] += 1

    if normalization == True:
        pagerank_1 = pagerank_1 / counts

    return pagerank_1
Exemplo n.º 15
0
def GetMinTemporalDistance(t, delta=1, collect_paths=True):
    """ Computes the minimum temporal distance between all pairs of nodes in 
        terms of time-respecting paths (using a given maximum time difference delta), 
        across all possible starting times in the temporal network

        @param t: the temporal network to calculate the distance for
        @param delta: the maximum waiting time to be used for the definition of time-respecting paths.
            Note that this is independent of the delta parameter set in the temporal networks instancd
           for the two-path extraction
        @param collect_paths: whether or not to return all shortest time-respecting paths. If False, only 
            shortest path distances will be returned.
    """

    Log.add('Computing minimum temporal distances for delta = ' +
            str(int(delta)) + ' ...')

    name_map = Utilities.firstOrderNameMap(t)

    minD = np.zeros(shape=(len(t.nodes), len(t.nodes)))
    minD.fill(np.inf)

    # Each node is connected to itself via a path of length zero
    np.fill_diagonal(minD, 0)

    minPaths = defaultdict(lambda: defaultdict(lambda: []))

    for start_t in t.ordered_times:
        D, paths = GetTemporalDistanceMatrix(t, start_t, delta, collect_paths)
        for v in t.nodes:
            for w in t.nodes:
                if D[name_map[v], name_map[w]] < minD[name_map[v],
                                                      name_map[w]]:
                    minD[name_map[v], name_map[w]] = D[name_map[v],
                                                       name_map[w]]
                    minPaths[v][w] = paths[v][w]
                elif D[name_map[v],
                       name_map[w]] == minD[name_map[v], name_map[w]] and minD[
                           name_map[v], name_map[w]] < np.inf:
                    for p in paths[v][w]:
                        if p not in minPaths[v][w]:
                            minPaths[v][w] = minPaths[v][w] + [p]
    Log.add('finished.')
    return minD, minPaths
Exemplo n.º 16
0
def GetStaticPageRank(t, model='SECOND', projection='TARGET', normalization=False):
    """Computes PageRank of nodes based on the second-order aggregate network, 
    and aggregates PageRank values to obtain the PageRank of nodes in the
    first-order network.
    
    @param t: The temporalnetwork instance to work on
    @param model: either C{"SECOND"} or C{"NULL"}, where C{"SECOND"} is the 
      the default value.
    """

    assert model is "SECOND" or model is "NULL"
    assert projection is 'TARGET' or projection is 'SOURCE'

    name_map = Utilities.firstOrderNameMap( t )

    if model == 'SECOND':
        g2 = t.igraphSecondOrder()
    else:
        g2 = t.igraphSecondOrderNull()    

    # Compute pagerank centrality in second-order network
    pagerank_2 = np.array(g2.pagerank(weights=g2.es()['weight'], directed=True))
    
    # Aggregate to obtain first-order pagerank centrality
    pagerank_1 = np.zeros(len(name_map))
    counts = np.array([1]*len(name_map))
    sep = t.separator
    for i in range(len(pagerank_2)):
        # Get name of target node        
        if projection == 'TARGET':
            target = g2.vs()[i]["name"].split(sep)[1]
            pagerank_1[name_map[target]] += pagerank_2[i]
            counts[name_map[target]] +=1 
        else:
            source = g2.vs()[i]["name"].split(sep)[0]
            pagerank_1[name_map[source]] += pagerank_2[i]
            counts[name_map[source]] +=1 
    
    if normalization == True:
        pagerank_1 = pagerank_1 / counts
    
    return pagerank_1
Exemplo n.º 17
0
def GetTemporalBetweennessInstantaneous(t, start_t=0, delta=1, normalized=False):
    """Calculates the temporal betweennness values of 
    all nodes fir a given start time start_t in an empirical temporal network t.
    This function returns a numpy array of (temporal) betweenness centrality values. 
    The ordering of these values corresponds to the ordering of nodes in the vertex 
    sequence of the igraph first order time-aggregated network. A mapping between node names
    and array indices can be found in Utilities.firstOrderNameMap().
    
    @param t: the temporal network for which temporal betweenness centralities will be computed
    @param start_t: the start time for which to consider time-respecting paths (default 0). This is 
        important, since any unambigious definition of a shortest time-respecting path between
        two nodes must include the time range to be considered (c.f. Holme and Saramäki, Phys. Rep., 2012)
    @param delta: the maximum waiting time used in the time-respecting path definition (default 1)
        Note that this parameter is independent from the delta used internally for the extraction of two-paths
        by the class TemporalNetwork
    @param normalized: whether or not to normalize the temporal betweenness centrality values by
    dividing by the number of all shortest time-respecting paths in the temporal network.
    """

    bw = np.array([0]*len(t.nodes))

    # First calculate all shortest time-respecting paths starting at time start_t
    D, paths = Paths.GetTemporalDistanceMatrix(t, start_t, delta, collect_paths=True)

    # Get a mapping between node names and matrix indices
    name_map = Utilities.firstOrderNameMap( t )

    # Compute betweenness scores of all nodes based on shortest time-respecting paths
    k=0
    for u in t.nodes:
        for v in t.nodes:
            if u != v:
                for p in paths[u][v]:
                    for i in range(1, len(p)-1):
                        bw[name_map[p[i][0]]] += 1
                        k+=1

    # Normalize by dividing by the total number of shortest time-respecting paths
    if normalized:
        bw = bw/k
    return bw
Exemplo n.º 18
0
def GetSecondOrderDistanceMatrix(t, model='SECOND'):
    """Calculates a matrix D containing the shortest path lengths between all
    pairs of nodes calculated based on the topology of the *second-order* aggregate network. 
    The ordering of rows/columns corresponds to the ordering of nodes in the vertex sequence of 
    the igraph first order time-aggregated network. A mapping between nodes and indices can be 
    found in Utilities.firstOrderNameMap().    
    
    @param t: the temporal network to calculate shortest path lengths for based on a second-order
        aggregate representation 
    @param model: either C{"SECOND"} or C{"NULL"}, where C{"SECOND"} is the 
      the default value.   
    """

    if (model is "SECOND" or "NULL") == False:
        raise ValueError("model must be one of \"SECOND\" or \"NULL\"")

    name_map = Utilities.firstOrderNameMap(t)

    if model == 'SECOND':
        g2 = t.igraphSecondOrder()
    else:
        g2 = t.igraphSecondOrderNull()

    D = np.zeros(shape=(len(t.nodes), len(t.nodes)))
    D.fill(np.inf)
    np.fill_diagonal(D, 0)

    sep = t.separator

    for v in g2.vs()["name"]:
        source = v.split(sep)[0]
        for w in g2.vs()["name"]:
            target = w.split(sep)[1]
            X = g2.get_shortest_paths(v, w)
            for p in X:
                if len(p) > 0:
                    D[name_map[source], name_map[target]] = min(
                        len(p), D[name_map[source], name_map[target]])
    return D
Exemplo n.º 19
0
def GetMinTemporalDistance(t, delta=1, collect_paths=True):
    """ Computes the minimum temporal distance between all pairs of nodes in 
        terms of time-respecting paths (using a given maximum time difference delta), 
        across all possible starting times in the temporal network

        @param t: the temporal network to calculate the distance for
        @param delta: the maximum waiting time to be used for the definition of time-respecting paths.
            Note that this is independent of the delta parameter set in the temporal networks instancd
           for the two-path extraction
        @param collect_paths: whether or not to return all shortest time-respecting paths. If False, only 
            shortest path distances will be returned.
    """

    Log.add('Computing minimum temporal distances for delta = ' + str(int(delta)) + ' ...')

    name_map = Utilities.firstOrderNameMap( t )

    minD = np.zeros(shape=(len(t.nodes),len(t.nodes)))
    minD.fill(np.inf)

    # Each node is connected to itself via a path of length zero
    np.fill_diagonal(minD, 0)

    minPaths = defaultdict( lambda: defaultdict( lambda: [] ) )

    for start_t in t.ordered_times:
        D, paths = GetTemporalDistanceMatrix(t, start_t, delta, collect_paths)
        for v in t.nodes:
            for w in t.nodes:
                if D[name_map[v], name_map[w]] < minD[name_map[v], name_map[w]]:
                    minD[name_map[v], name_map[w]] = D[name_map[v], name_map[w]]
                    minPaths[v][w] = paths[v][w]
                elif D[name_map[v], name_map[w]] == minD[name_map[v], name_map[w]] and minD[name_map[v], name_map[w]] < np.inf:
                    for p in paths[v][w]:
                        if p not in minPaths[v][w]:
                            minPaths[v][w] = minPaths[v][w] + [p]
    Log.add('finished.')
    return minD, minPaths
Exemplo n.º 20
0
def GetSecondOrderDistanceMatrix(t, model='SECOND'):
    """Calculates a matrix D containing the shortest path lengths between all
    pairs of nodes calculated based on the topology of the *second-order* aggregate network. 
    The ordering of rows/columns corresponds to the ordering of nodes in the vertex sequence of 
    the igraph first order time-aggregated network. A mapping between nodes and indices can be 
    found in Utilities.firstOrderNameMap().    
    
    @param t: the temporal network to calculate shortest path lengths for based on a second-order
        aggregate representation 
    @param model: either C{"SECOND"} or C{"NULL"}, where C{"SECOND"} is the 
      the default value.   
    """   

    if (model is "SECOND" or "NULL") == False:
        raise ValueError("model must be one of \"SECOND\" or \"NULL\"")

    name_map = Utilities.firstOrderNameMap( t )

    if model == 'SECOND':
        g2 = t.igraphSecondOrder()
    else:
        g2 = t.igraphSecondOrderNull()    

    D = np.zeros(shape=(len(t.nodes),len(t.nodes)))
    D.fill(np.inf)
    np.fill_diagonal(D, 0)

    sep = t.separator

    for v in g2.vs()["name"]:
        source = v.split(sep)[0]
        for w in g2.vs()["name"]:
            target = w.split(sep)[1]
            X = g2.get_shortest_paths(v,w)            
            for p in X:
                if len(p)>0:
                    D[name_map[source], name_map[target]] = min(len(p), D[name_map[source], name_map[target]])
    return D
Exemplo n.º 21
0
def GetTemporalClosenessInstantaneous(t, start_t=0, delta=1):
    """Calculates the temporal closeness values of 
    all nodes for a given start time start_t in a temporal network t.
    This function returns a numpy array of (temporal) closeness centrality values. 
    The ordering of these values corresponds to the ordering of nodes in the vertex 
    sequence of the igraph first order time-aggregated network. A mapping between node names
    and array indices can be found in Utilities.firstOrderNameMap().
    
    @param t: the temporal network for which temporal closeness centralities will be computed
    @param start_t: the start time for which to consider time-respecting paths (default 0). This is 
        important, since any unambigious definition of a shortest time-respecting path between
        two nodes must include the time range to be considered (c.f. Holme and Saramäki, Phys. Rep., 2012)
    @param delta: the maximum time difference time used in the time-respecting path definition (default 1)
        Note that this parameter is independent from the delta used internally for the extraction of two-paths
        by the class TemporalNetwork.
    """

    closeness = np.array([0.] * len(t.nodes))

    # Calculate all shortest time-respecting paths
    D, paths = Paths.GetTemporalDistanceMatrix(t,
                                               start_t,
                                               delta,
                                               collect_paths=False)

    # Get a mapping between node names and matrix indices
    name_map = Utilities.firstOrderNameMap(t)

    # Calculate closeness for each node u, by summing the reciprocal of its
    # distances to all other nodes. Note that this definition of closeness centrality
    # is required for directed networks that are not strongly connected.
    for u in t.nodes:
        for v in t.nodes:
            if u != v:
                closeness[name_map[u]] += 1. / D[name_map[v], name_map[u]]

    return closeness
Exemplo n.º 22
0
def GetStaticBetweenness(t, model='SECOND'):
    """Computes betweenness centralities of nodes based on the second-order aggregate network, 
    and aggregates betweenness centralities to obtain the betweenness centrality of nodes in the 
    first-order network.
    
    @param t: The temporalnetwork instance to work on
    @param model: either C{"SECOND"} or C{"NULL"}, where C{"SECOND"} is the 
      the default value.
    """

    if (model is "SECOND" or "NULL") == False:
        raise ValueError("model must be one of \"SECOND\" or \"NULL\"")

    D = Paths.GetSecondOrderDistanceMatrix(t)
    name_map = Utilities.firstOrderNameMap( t )

    if model == 'SECOND':
        g2 = t.igraphSecondOrder()
    else:
        g2 = t.igraphSecondOrderNull()

    # Compute betweenness centrality based on second-order network
    bwcent_1 = np.zeros(len(name_map))
    sep = t.separator

    for v in g2.vs()["name"]:
        for w in g2.vs()["name"]:
            s = v.split(sep)[0]
            t = w.split(sep)[1]
            X = g2.get_all_shortest_paths(v,w)
            for p in X:
                if D[name_map[s], name_map[t]] == len(p) and len(p) > 1:
                    for i in range(len(p)):
                        source = g2.vs()["name"][p[i]].split(sep)[0]
                        if i>0:
                            bwcent_1[name_map[source]] += 1 
    return bwcent_1
Exemplo n.º 23
0
def GetStaticBetweenness(t, model='SECOND'):
    """Computes betweenness centralities of nodes based on the second-order aggregate network, 
    and aggregates betweenness centralities to obtain the betweenness centrality of nodes in the 
    first-order network.
    
    @param t: The temporalnetwork instance to work on
    @param model: either C{"SECOND"} or C{"NULL"}, where C{"SECOND"} is the 
      the default value.
    """

    if (model is "SECOND" or "NULL") == False:
        raise ValueError("model must be one of \"SECOND\" or \"NULL\"")

    D = Paths.GetSecondOrderDistanceMatrix(t)
    name_map = Utilities.firstOrderNameMap(t)

    if model == 'SECOND':
        g2 = t.igraphSecondOrder()
    else:
        g2 = t.igraphSecondOrderNull()

    # Compute betweenness centrality based on second-order network
    bwcent_1 = np.zeros(len(name_map))
    sep = t.separator

    for v in g2.vs()["name"]:
        for w in g2.vs()["name"]:
            s = v.split(sep)[0]
            t = w.split(sep)[1]
            X = g2.get_all_shortest_paths(v, w)
            for p in X:
                if D[name_map[s], name_map[t]] == len(p) and len(p) > 1:
                    for i in range(len(p)):
                        source = g2.vs()["name"][p[i]].split(sep)[0]
                        if i > 0:
                            bwcent_1[name_map[source]] += 1
    return bwcent_1
Exemplo n.º 24
0
def GetTemporalDistanceMatrix(t, start_t=-1, delta=1, collect_paths=True):
    """A new and faster method to compute the (topologically) shortest time-respecting paths between 
    all pairs of nodes starting at time start_t in an empirical temporal network t.
    This function returns a tuple consisting of 
        1) a matrix D containing the shortest time-respecting path lengths between all
            pairs of nodes. The ordering of rows/columns corresponds to the ordering of nodes 
            in the vertex sequence of the igraph first order time-aggregated network. A
            mapping between nodes and indices can be found in Utilities.firstOrderNameMap().
        2) a list of shortest time-respecting paths, each entry being an ordered sequence 
            of nodes on the corresponding path.
    
    @param t: the temporal network to calculate shortest time-respecting paths for
    @param start_t: the start time for which to consider time-respecting paths (default is t.ordered_times[0])
    @param delta: the maximum time difference to be used in the time-respecting path definition (default 1).
        Note that this parameter is independent from the internal parameter delta used for two-path extraction
        in the class TemporalNetwork
    @param collect_paths: whether or not to collect all shortest time-respecting paths (default = True). If this is 
        set to False, the method will only compute the lengths of shortest time-respecting paths, but not return the actual 
        paths.
        """

    if start_t == -1:
        start_t = t.ordered_times[0]

    # Initialize dictionary taking shortest paths
    Paths = defaultdict(lambda: defaultdict(lambda: []))

    # Get a mapping between node names and matrix indices
    name_map = Utilities.firstOrderNameMap(t)

    # Initialize topological distance matrix
    # TODO: This may yield a memory problem for large graphs
    D = np.zeros(shape=(len(t.nodes), len(t.nodes)))
    D.fill(np.inf)

    # For each node v, calculate shortest/fastest paths to all other nodes ...
    for v in t.nodes:

        # Mark node v as visited at the start time start_t...
        D[name_map[v], name_map[v]] = 0
        Paths[v][v] = [[(v, start_t)]]

        stack = set([(v, start_t)])

        # While there are nodes, which could possibly continue a time-respecting path
        while len(stack) > 0:

            (x, ts) = stack.pop()

            # Get indices of time range within which a time-respecting path via x
            # can possibly be continued
            min_ix = bisect_left(t.activities[x], ts)
            max_ix = bisect_left(t.activities[x], ts + delta) - 1

            # For all time-stamps at which x is a source node ...
            for j in range(min_ix, max_ix + 1):
                time = t.activities[x][j]

                # For all edges starting at node x at this time
                for e in t.sources[time][x]:

                    # We found a new node on a time-respecting path
                    new_node = (e[1], time + 1)

                    # This node can again continue time-respecting paths
                    # The set will take care that no duplicates are recorded
                    stack.add(new_node)

                    # Check whether we found a time-respecting path shorter than the current shortest one ...
                    if D[name_map[v],
                         name_map[e[1]]] > D[name_map[v], name_map[e[0]]] + 1:

                        # In this case we update the distance matrix
                        D[name_map[v],
                          name_map[e[1]]] = D[name_map[v], name_map[e[0]]] + 1

                        if collect_paths == True:
                            # Delete any previous shortest paths
                            Paths[v][e[1]] = []

                            # Collect all paths to e[0] and concatenate with the current node e[1]
                            for p in Paths[v][e[0]]:
                                Paths[v][e[1]] = Paths[v][e[1]] + [
                                    p + [(e[1], time + 1)]
                                ]

                    # We may also have found a path that has the same length as other shortest paths ...
                    elif collect_paths == True and D[name_map[v], name_map[
                            e[1]]] == D[name_map[v], name_map[e[0]]] + 1:

                        # Collect all paths to e[0] and concatenate with the current node e[1]
                        for p in Paths[v][e[0]]:
                            Paths[v][e[1]] = Paths[v][e[1]] + [
                                p + [(e[1], time + 1)]
                            ]

    # The algorithm terminates as soon as it is impossible to continue any of the time-respecting paths
    return D, Paths
Exemplo n.º 25
0
def GetTemporalDistanceMatrix(t, start_t=-1, delta=1, collect_paths=True):
    """A new and faster method to compute the (topologically) shortest time-respecting paths between 
    all pairs of nodes starting at time start_t in an empirical temporal network t.
    This function returns a tuple consisting of 
        1) a matrix D containing the shortest time-respecting path lengths between all
            pairs of nodes. The ordering of rows/columns corresponds to the ordering of nodes 
            in the vertex sequence of the igraph first order time-aggregated network. A
            mapping between nodes and indices can be found in Utilities.firstOrderNameMap().
        2) a list of shortest time-respecting paths, each entry being an ordered sequence 
            of nodes on the corresponding path.
    
    @param t: the temporal network to calculate shortest time-respecting paths for
    @param start_t: the start time for which to consider time-respecting paths (default is t.ordered_times[0])
    @param delta: the maximum time difference to be used in the time-respecting path definition (default 1).
        Note that this parameter is independent from the internal parameter delta used for two-path extraction
        in the class TemporalNetwork
    @param collect_paths: whether or not to collect all shortest time-respecting paths (default = True). If this is 
        set to False, the method will only compute the lengths of shortest time-respecting paths, but not return the actual 
        paths.
        """

    if start_t == -1:
        start_t = t.ordered_times[0]

    # Initialize dictionary taking shortest paths 
    Paths = defaultdict( lambda: defaultdict( lambda: [] ) )

    # Get a mapping between node names and matrix indices
    name_map = Utilities.firstOrderNameMap( t )

    # Initialize topological distance matrix
    # TODO: This may yield a memory problem for large graphs 
    D = np.zeros(shape=(len(t.nodes),len(t.nodes)))
    D.fill(np.inf)

    # For each node v, calculate shortest/fastest paths to all other nodes ... 
    for v in t.nodes:
        
        # Mark node v as visited at the start time start_t... 
        D[name_map[v], name_map[v]] = 0        
        Paths[v][v] = [ [(v,start_t)] ]

        stack = set([ (v, start_t) ])
        
        # While there are nodes, which could possibly continue a time-respecting path
        while len(stack)>0:

            (x,ts) = stack.pop()

            # Get indices of time range within which a time-respecting path via x 
            # can possibly be continued
            min_ix = bisect_left(t.activities[x], ts)
            max_ix = bisect_left(t.activities[x], ts+delta)-1

            # For all time-stamps at which x is a source node ... 
            for j in range(min_ix, max_ix+1):
                time = t.activities[x][j]

                # For all edges starting at node x at this time
                for e in t.sources[time][x]:

                    # We found a new node on a time-respecting path
                    new_node = (e[1], time+1)
                    
                    # This node can again continue time-respecting paths
                    # The set will take care that no duplicates are recorded
                    stack.add( new_node )

                    # Check whether we found a time-respecting path shorter than the current shortest one ... 
                    if D[name_map[v], name_map[e[1]]] > D[name_map[v], name_map[e[0]]] + 1:
                        
                        # In this case we update the distance matrix
                        D[name_map[v], name_map[e[1]]] = D[name_map[v], name_map[e[0]]] + 1

                        if collect_paths == True:
                            # Delete any previous shortest paths 
                            Paths[v][e[1]] = []

                            # Collect all paths to e[0] and concatenate with the current node e[1]
                            for p in Paths[v][e[0]]:
                                Paths[v][e[1]] = Paths[v][e[1]] + [p + [(e[1],time+1)]]

                    # We may also have found a path that has the same length as other shortest paths ...
                    elif collect_paths == True and D[name_map[v], name_map[e[1]]] == D[name_map[v], name_map[e[0]]] + 1:

                        # Collect all paths to e[0] and concatenate with the current node e[1]
                        for p in Paths[v][e[0]]:
                            Paths[v][e[1]] = Paths[v][e[1]] + [p + [(e[1],time+1)]]
        
    # The algorithm terminates as soon as it is impossible to continue any of the time-respecting paths
    return D, Paths