Skip to content

Commit 7b1cc8d

Browse files
impl node py filter iter (#2270)
* impl node py filter iter * chore: apply tidy-public auto-fixes * impl path_from_graph, path_from_node, edges, nested_edges py filter, fix tests, * rid iter_graph * add more tests * add more tests * add exploded edges test --------- Co-authored-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com>
1 parent 30e5bad commit 7b1cc8d

File tree

34 files changed

+2220
-3720
lines changed

34 files changed

+2220
-3720
lines changed

python/python/raphtory/__init__.pyi

Lines changed: 462 additions & 259 deletions
Large diffs are not rendered by default.

python/python/raphtory/algorithms/__init__.pyi

Lines changed: 146 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
"""
22
Algorithmic functions that can be run on Raphtory graphs
33
"""
4+
45
from __future__ import annotations
56

67
###############################################################################
@@ -25,8 +26,59 @@ from os import PathLike
2526
import networkx as nx # type: ignore
2627
import pyvis # type: ignore
2728

28-
__all__ = ['dijkstra_single_source_shortest_paths', 'global_reciprocity', 'betweenness_centrality', 'all_local_reciprocity', 'triplet_count', 'local_triangle_count', 'average_degree', 'directed_graph_density', 'degree_centrality', 'max_degree', 'min_degree', 'max_out_degree', 'max_in_degree', 'min_out_degree', 'min_in_degree', 'pagerank', 'single_source_shortest_path', 'global_clustering_coefficient', 'temporally_reachable_nodes', 'temporal_bipartite_graph_projection', 'local_clustering_coefficient', 'local_clustering_coefficient_batch', 'weakly_connected_components', 'strongly_connected_components', 'in_components', 'in_component', 'out_components', 'out_component', 'fast_rp', 'global_temporal_three_node_motif', 'global_temporal_three_node_motif_multi', 'local_temporal_three_node_motifs', 'hits', 'balance', 'label_propagation', 'k_core', 'temporal_SEIR', 'louvain', 'fruchterman_reingold', 'cohesive_fruchterman_reingold', 'max_weight_matching', 'Matching', 'Infected']
29-
def dijkstra_single_source_shortest_paths(graph: GraphView, source: NodeInput, targets: list[NodeInput], direction: Direction = "both", weight: str = 'weight') -> NodeStateWeightedSP:
29+
__all__ = [
30+
"dijkstra_single_source_shortest_paths",
31+
"global_reciprocity",
32+
"betweenness_centrality",
33+
"all_local_reciprocity",
34+
"triplet_count",
35+
"local_triangle_count",
36+
"average_degree",
37+
"directed_graph_density",
38+
"degree_centrality",
39+
"max_degree",
40+
"min_degree",
41+
"max_out_degree",
42+
"max_in_degree",
43+
"min_out_degree",
44+
"min_in_degree",
45+
"pagerank",
46+
"single_source_shortest_path",
47+
"global_clustering_coefficient",
48+
"temporally_reachable_nodes",
49+
"temporal_bipartite_graph_projection",
50+
"local_clustering_coefficient",
51+
"local_clustering_coefficient_batch",
52+
"weakly_connected_components",
53+
"strongly_connected_components",
54+
"in_components",
55+
"in_component",
56+
"out_components",
57+
"out_component",
58+
"fast_rp",
59+
"global_temporal_three_node_motif",
60+
"global_temporal_three_node_motif_multi",
61+
"local_temporal_three_node_motifs",
62+
"hits",
63+
"balance",
64+
"label_propagation",
65+
"k_core",
66+
"temporal_SEIR",
67+
"louvain",
68+
"fruchterman_reingold",
69+
"cohesive_fruchterman_reingold",
70+
"max_weight_matching",
71+
"Matching",
72+
"Infected",
73+
]
74+
75+
def dijkstra_single_source_shortest_paths(
76+
graph: GraphView,
77+
source: NodeInput,
78+
targets: list[NodeInput],
79+
direction: Direction = "both",
80+
weight: str = "weight",
81+
) -> NodeStateWeightedSP:
3082
"""
3183
Finds the shortest paths from a single source to multiple targets in a graph.
3284
@@ -56,7 +108,9 @@ def global_reciprocity(graph: GraphView) -> float:
56108
float: reciprocity of the graph between 0 and 1.
57109
"""
58110

59-
def betweenness_centrality(graph: GraphView, k: Optional[int] = None, normalized: bool = True) -> NodeStateF64:
111+
def betweenness_centrality(
112+
graph: GraphView, k: Optional[int] = None, normalized: bool = True
113+
) -> NodeStateF64:
60114
"""
61115
Computes the betweenness centrality for nodes in a given graph.
62116
@@ -224,7 +278,13 @@ def min_in_degree(graph: GraphView) -> int:
224278
int: value of the smallest indegree
225279
"""
226280

227-
def pagerank(graph: GraphView, iter_count: int = 20, max_diff: Optional[float] = None, use_l2_norm: bool = True, damping_factor: float = 0.85) -> NodeStateF64:
281+
def pagerank(
282+
graph: GraphView,
283+
iter_count: int = 20,
284+
max_diff: Optional[float] = None,
285+
use_l2_norm: bool = True,
286+
damping_factor: float = 0.85,
287+
) -> NodeStateF64:
228288
"""
229289
Pagerank -- pagerank centrality value of the nodes in a graph
230290
@@ -245,7 +305,9 @@ def pagerank(graph: GraphView, iter_count: int = 20, max_diff: Optional[float] =
245305
NodeStateF64: Mapping of nodes to their pagerank value.
246306
"""
247307

248-
def single_source_shortest_path(graph: GraphView, source: NodeInput, cutoff: Optional[int] = None) -> NodeStateNodes:
308+
def single_source_shortest_path(
309+
graph: GraphView, source: NodeInput, cutoff: Optional[int] = None
310+
) -> NodeStateNodes:
249311
"""
250312
Calculates the single source shortest paths from a given source node.
251313
@@ -276,7 +338,13 @@ def global_clustering_coefficient(graph: GraphView) -> float:
276338
[`Triplet Count`](triplet_count)
277339
"""
278340

279-
def temporally_reachable_nodes(graph: GraphView, max_hops: int, start_time: int, seed_nodes: list[NodeInput], stop_nodes: Optional[list[NodeInput]] = None) -> NodeStateReachability:
341+
def temporally_reachable_nodes(
342+
graph: GraphView,
343+
max_hops: int,
344+
start_time: int,
345+
seed_nodes: list[NodeInput],
346+
stop_nodes: Optional[list[NodeInput]] = None,
347+
) -> NodeStateReachability:
280348
"""
281349
Temporally reachable nodes -- the nodes that are reachable by a time respecting path followed out from a set of seed nodes at a starting time.
282350
@@ -295,7 +363,9 @@ def temporally_reachable_nodes(graph: GraphView, max_hops: int, start_time: int,
295363
NodeStateReachability: Mapping of nodes to their reachability history.
296364
"""
297365

298-
def temporal_bipartite_graph_projection(graph: GraphView, delta: int, pivot_type: str) -> Graph:
366+
def temporal_bipartite_graph_projection(
367+
graph: GraphView, delta: int, pivot_type: str
368+
) -> Graph:
299369
"""
300370
Projects a temporal bipartite graph into an undirected temporal graph over the pivot node type. Let `G` be a bipartite graph with node types `A` and `B`. Given `delta > 0`, the projection graph `G'` pivoting over type `B` nodes,
301371
will make a connection between nodes `n1` and `n2` (of type `A`) at time `(t1 + t2)/2` if they respectively have an edge at time `t1`, `t2` with the same node of type `B` in `G`, and `|t2-t1| < delta`.
@@ -323,9 +393,7 @@ def local_clustering_coefficient(graph: GraphView, v: NodeInput) -> float:
323393
float: the local clustering coefficient of node v in graph.
324394
"""
325395

326-
def local_clustering_coefficient_batch(graph, v):
327-
...
328-
396+
def local_clustering_coefficient_batch(graph, v): ...
329397
def weakly_connected_components(graph: GraphView) -> NodeStateUsize:
330398
"""
331399
Weakly connected components -- partitions the graph into node sets which are mutually reachable by an undirected path
@@ -397,7 +465,14 @@ def out_component(node: Node) -> NodeStateUsize:
397465
NodeStateUsize: A NodeState mapping the nodes in the out-component to their distance from the starting node.
398466
"""
399467

400-
def fast_rp(graph: GraphView, embedding_dim: int, normalization_strength: float, iter_weights: list[float], seed: Optional[int] = None, threads: Optional[int] = None) -> NodeStateListF64:
468+
def fast_rp(
469+
graph: GraphView,
470+
embedding_dim: int,
471+
normalization_strength: float,
472+
iter_weights: list[float],
473+
seed: Optional[int] = None,
474+
threads: Optional[int] = None,
475+
) -> NodeStateListF64:
401476
"""
402477
Computes embedding vectors for each vertex of an undirected/bidirectional graph according to the Fast RP algorithm.
403478
Original Paper: https://doi.org/10.48550/arXiv.1908.11512
@@ -413,7 +488,9 @@ def fast_rp(graph: GraphView, embedding_dim: int, normalization_strength: float,
413488
NodeStateListF64: Mapping from nodes to embedding vectors.
414489
"""
415490

416-
def global_temporal_three_node_motif(graph: GraphView, delta: int, threads: Optional[int] = None) -> list[int]:
491+
def global_temporal_three_node_motif(
492+
graph: GraphView, delta: int, threads: Optional[int] = None
493+
) -> list[int]:
417494
"""
418495
Computes the number of three edge, up-to-three node delta-temporal motifs in the graph, using the algorithm of Paranjape et al, Motifs in Temporal Networks (2017).
419496
We point the reader to this reference for more information on the algorithm and background, but provide a short summary below.
@@ -462,7 +539,9 @@ def global_temporal_three_node_motif(graph: GraphView, delta: int, threads: Opti
462539
463540
"""
464541

465-
def global_temporal_three_node_motif_multi(graph: GraphView, deltas: list[int], threads: Optional[int] = None) -> list[list[int]]:
542+
def global_temporal_three_node_motif_multi(
543+
graph: GraphView, deltas: list[int], threads: Optional[int] = None
544+
) -> list[list[int]]:
466545
"""
467546
Computes the global counts of three-edge up-to-three node temporal motifs for a range of timescales. See `global_temporal_three_node_motif` for an interpretation of each row returned.
468547
@@ -475,7 +554,9 @@ def global_temporal_three_node_motif_multi(graph: GraphView, deltas: list[int],
475554
list[list[int]]: A list of 40d arrays, each array is the motif count for a particular value of delta, returned in the order that the deltas were given as input.
476555
"""
477556

478-
def local_temporal_three_node_motifs(graph: GraphView, delta: int, threads=None) -> NodeStateMotifs:
557+
def local_temporal_three_node_motifs(
558+
graph: GraphView, delta: int, threads=None
559+
) -> NodeStateMotifs:
479560
"""
480561
Computes the number of each type of motif that each node participates in. See global_temporal_three_node_motifs for a summary of the motifs involved.
481562
@@ -491,7 +572,9 @@ def local_temporal_three_node_motifs(graph: GraphView, delta: int, threads=None)
491572
the motif. For two node motifs, both constituent nodes count the motif. For triangles, all three constituent nodes count the motif.
492573
"""
493574

494-
def hits(graph: GraphView, iter_count: int = 20, threads: Optional[int] = None) -> NodeStateHits:
575+
def hits(
576+
graph: GraphView, iter_count: int = 20, threads: Optional[int] = None
577+
) -> NodeStateHits:
495578
"""
496579
HITS (Hubs and Authority) Algorithm:
497580
@@ -510,7 +593,9 @@ def hits(graph: GraphView, iter_count: int = 20, threads: Optional[int] = None)
510593
NodeStateHits: A mapping from nodes their hub and authority scores
511594
"""
512595

513-
def balance(graph: GraphView, name: str = "weight", direction: Direction = "both") -> NodeStateF64:
596+
def balance(
597+
graph: GraphView, name: str = "weight", direction: Direction = "both"
598+
) -> NodeStateF64:
514599
"""
515600
Sums the weights of edges in the graph based on the specified direction.
516601
@@ -529,7 +614,9 @@ def balance(graph: GraphView, name: str = "weight", direction: Direction = "both
529614
530615
"""
531616

532-
def label_propagation(graph: GraphView, seed: Optional[bytes] = None) -> list[set[Node]]:
617+
def label_propagation(
618+
graph: GraphView, seed: Optional[bytes] = None
619+
) -> list[set[Node]]:
533620
"""
534621
Computes components using a label propagation algorithm
535622
@@ -542,7 +629,9 @@ def label_propagation(graph: GraphView, seed: Optional[bytes] = None) -> list[se
542629
543630
"""
544631

545-
def k_core(graph: GraphView, k: int, iter_count: int, threads: Optional[int] = None) -> list[Node]:
632+
def k_core(
633+
graph: GraphView, k: int, iter_count: int, threads: Optional[int] = None
634+
) -> list[Node]:
546635
"""
547636
Determines which nodes are in the k-core for a given value of k
548637
@@ -557,7 +646,15 @@ def k_core(graph: GraphView, k: int, iter_count: int, threads: Optional[int] = N
557646
558647
"""
559648

560-
def temporal_SEIR(graph: GraphView, seeds: int | float | list[NodeInput], infection_prob: float, initial_infection: int | str | datetime, recovery_rate: float | None = None, incubation_rate: float | None = None, rng_seed: int | None = None) -> NodeStateSEIR:
649+
def temporal_SEIR(
650+
graph: GraphView,
651+
seeds: int | float | list[NodeInput],
652+
infection_prob: float,
653+
initial_infection: int | str | datetime,
654+
recovery_rate: float | None = None,
655+
incubation_rate: float | None = None,
656+
rng_seed: int | None = None,
657+
) -> NodeStateSEIR:
561658
"""
562659
Simulate an SEIR dynamic on the network
563660
@@ -587,7 +684,12 @@ def temporal_SEIR(graph: GraphView, seeds: int | float | list[NodeInput], infect
587684
588685
"""
589686

590-
def louvain(graph: GraphView, resolution: float = 1.0, weight_prop: str | None = None, tol: None | float = None) -> NodeStateUsize:
687+
def louvain(
688+
graph: GraphView,
689+
resolution: float = 1.0,
690+
weight_prop: str | None = None,
691+
tol: None | float = None,
692+
) -> NodeStateUsize:
591693
"""
592694
Louvain algorithm for community detection
593695
@@ -601,7 +703,14 @@ def louvain(graph: GraphView, resolution: float = 1.0, weight_prop: str | None =
601703
NodeStateUsize: Mapping of nodes to their community assignment
602704
"""
603705

604-
def fruchterman_reingold(graph: GraphView, iterations: int | None = 100, scale: float | None = 1.0, node_start_size: float | None = 1.0, cooloff_factor: float | None = 0.95, dt: float | None = 0.1) -> NodeLayout:
706+
def fruchterman_reingold(
707+
graph: GraphView,
708+
iterations: int | None = 100,
709+
scale: float | None = 1.0,
710+
node_start_size: float | None = 1.0,
711+
cooloff_factor: float | None = 0.95,
712+
dt: float | None = 0.1,
713+
) -> NodeLayout:
605714
"""
606715
Fruchterman Reingold layout algorithm
607716
@@ -617,7 +726,14 @@ def fruchterman_reingold(graph: GraphView, iterations: int | None = 100, scale:
617726
NodeLayout: A mapping from nodes to their [x, y] positions
618727
"""
619728

620-
def cohesive_fruchterman_reingold(graph: GraphView, iter_count: int = 100, scale: float = 1.0, node_start_size: float = 1.0, cooloff_factor: float = 0.95, dt: float = 0.1) -> NodeLayout:
729+
def cohesive_fruchterman_reingold(
730+
graph: GraphView,
731+
iter_count: int = 100,
732+
scale: float = 1.0,
733+
node_start_size: float = 1.0,
734+
cooloff_factor: float = 0.95,
735+
dt: float = 0.1,
736+
) -> NodeLayout:
621737
"""
622738
Cohesive version of `fruchterman_reingold` that adds virtual edges between isolated nodes
623739
Arguments:
@@ -633,7 +749,12 @@ def cohesive_fruchterman_reingold(graph: GraphView, iter_count: int = 100, scale
633749
634750
"""
635751

636-
def max_weight_matching(graph: GraphView, weight_prop: Optional[str] = None, max_cardinality: bool = True, verify_optimum_flag: bool = False) -> Matching:
752+
def max_weight_matching(
753+
graph: GraphView,
754+
weight_prop: Optional[str] = None,
755+
max_cardinality: bool = True,
756+
verify_optimum_flag: bool = False,
757+
) -> Matching:
637758
"""
638759
Compute a maximum-weighted matching in the general undirected weighted
639760
graph given by "edges". If `max_cardinality` is true, only
@@ -670,7 +791,7 @@ def max_weight_matching(graph: GraphView, weight_prop: Optional[str] = None, max
670791
Matching: The matching
671792
"""
672793

673-
class Matching(object):
794+
class Matching(object):
674795
"""A Matching (i.e., a set of edges that do not share any nodes)"""
675796

676797
def __bool__(self):
@@ -742,8 +863,7 @@ class Matching(object):
742863
743864
"""
744865

745-
class Infected(object):
746-
866+
class Infected(object):
747867
def __repr__(self):
748868
"""Return repr(self)."""
749869

0 commit comments

Comments
 (0)