Skip to main content
Ctrl+K
Logo image

graph-tool documentation (2.59)

  • graph-tool
  • Welcome to graph-tool’s documentation!
  • Quick start guide
  • Cookbook guides
    • Inferring modular network structure
    • Animations with graph-tool
    • Integration with matplotlib
    • Writing extensions in C++
  • Submodules
    • graph_tool
      • graph_tool.Graph
      • graph_tool.GraphView
      • graph_tool.Vertex
      • graph_tool.Edge
      • graph_tool.PropertyMap
      • graph_tool.VertexPropertyMap
      • graph_tool.EdgePropertyMap
      • graph_tool.GraphPropertyMap
      • graph_tool.PropertyArray
      • graph_tool.group_vector_property
      • graph_tool.ungroup_vector_property
      • graph_tool.map_property_values
      • graph_tool.infect_vertex_property
      • graph_tool.edge_endpoint_property
      • graph_tool.incident_edges_op
      • graph_tool.perfect_prop_hash
      • graph_tool.value_types
      • graph_tool.load_graph
      • graph_tool.load_graph_from_csv
      • graph_tool.openmp_enabled
      • graph_tool.openmp_get_num_threads
      • graph_tool.openmp_set_num_threads
      • graph_tool.openmp_get_schedule
      • graph_tool.openmp_set_schedule
      • graph_tool.show_config
    • graph_tool.centrality
      • graph_tool.centrality.pagerank
      • graph_tool.centrality.betweenness
      • graph_tool.centrality.central_point_dominance
      • graph_tool.centrality.closeness
      • graph_tool.centrality.eigenvector
      • graph_tool.centrality.katz
      • graph_tool.centrality.hits
      • graph_tool.centrality.eigentrust
      • graph_tool.centrality.trust_transitivity
    • graph_tool.clustering
      • graph_tool.clustering.local_clustering
      • graph_tool.clustering.global_clustering
      • graph_tool.clustering.extended_clustering
      • graph_tool.clustering.motifs
      • graph_tool.clustering.motif_significance
    • graph_tool.collection
      • graph_tool.collection.LCF_graph
      • graph_tool.collection.bull_graph
      • graph_tool.collection.chvatal_graph
      • graph_tool.collection.cubical_graph
      • graph_tool.collection.desargues_graph
      • graph_tool.collection.diamond_graph
      • graph_tool.collection.dodecahedral_graph
      • graph_tool.collection.frucht_graph
      • graph_tool.collection.heawood_graph
      • graph_tool.collection.hoffman_singleton_graph
      • graph_tool.collection.house_graph
      • graph_tool.collection.icosahedral_graph
      • graph_tool.collection.krackhardt_kite_graph
      • graph_tool.collection.moebius_kantor_graph
      • graph_tool.collection.octahedral_graph
      • graph_tool.collection.pappus_graph
      • graph_tool.collection.petersen_graph
      • graph_tool.collection.sedgewick_maze_graph
      • graph_tool.collection.tetrahedral_graph
      • graph_tool.collection.truncated_cube_graph
      • graph_tool.collection.truncated_tetrahedron_graph
      • graph_tool.collection.tutte_graph
    • graph_tool.correlations
      • graph_tool.correlations.assortativity
      • graph_tool.correlations.scalar_assortativity
      • graph_tool.correlations.corr_hist
      • graph_tool.correlations.combined_corr_hist
      • graph_tool.correlations.avg_neighbor_corr
      • graph_tool.correlations.avg_combined_corr
    • graph_tool.dynamics
      • graph_tool.dynamics.DiscreteStateBase
      • graph_tool.dynamics.EpidemicStateBase
      • graph_tool.dynamics.SIState
      • graph_tool.dynamics.SISState
      • graph_tool.dynamics.SIRState
      • graph_tool.dynamics.SIRSState
      • graph_tool.dynamics.VoterState
      • graph_tool.dynamics.MajorityVoterState
      • graph_tool.dynamics.BinaryThresholdState
      • graph_tool.dynamics.IsingGlauberState
      • graph_tool.dynamics.CIsingGlauberState
      • graph_tool.dynamics.IsingMetropolisState
      • graph_tool.dynamics.PottsGlauberState
      • graph_tool.dynamics.PottsMetropolisState
      • graph_tool.dynamics.AxelrodState
      • graph_tool.dynamics.BooleanState
      • graph_tool.dynamics.KirmanState
      • graph_tool.dynamics.ContinuousStateBase
      • graph_tool.dynamics.KuramotoState
    • graph_tool.draw
      • graph_tool.draw.sfdp_layout
      • graph_tool.draw.fruchterman_reingold_layout
      • graph_tool.draw.arf_layout
      • graph_tool.draw.radial_tree_layout
      • graph_tool.draw.planar_layout
      • graph_tool.draw.random_layout
      • graph_tool.draw.graph_draw
      • graph_tool.draw.draw_hierarchy
      • graph_tool.draw.graphviz_draw
      • graph_tool.draw.prop_to_size
      • graph_tool.draw.get_hierarchy_control_points
      • graph_tool.draw.cairo_draw
      • graph_tool.draw.interactive_window
      • graph_tool.draw.GraphWidget
      • graph_tool.draw.GraphWindow
    • graph_tool.flow
      • graph_tool.flow.edmonds_karp_max_flow
      • graph_tool.flow.push_relabel_max_flow
      • graph_tool.flow.boykov_kolmogorov_max_flow
      • graph_tool.flow.min_st_cut
      • graph_tool.flow.min_cut
    • graph_tool.generation
      • graph_tool.generation.random_graph
      • graph_tool.generation.random_rewire
      • graph_tool.generation.add_random_edges
      • graph_tool.generation.remove_random_edges
      • graph_tool.generation.generate_triadic_closure
      • graph_tool.generation.price_network
      • graph_tool.generation.generate_sbm
      • graph_tool.generation.generate_maxent_sbm
      • graph_tool.generation.solve_sbm_fugacities
      • graph_tool.generation.generate_knn
      • graph_tool.generation.geometric_graph
      • graph_tool.generation.triangulation
      • graph_tool.generation.predecessor_tree
      • graph_tool.generation.line_graph
      • graph_tool.generation.condensation_graph
      • graph_tool.generation.contract_parallel_edges
      • graph_tool.generation.remove_parallel_edges
      • graph_tool.generation.expand_parallel_edges
      • graph_tool.generation.label_parallel_edges
      • graph_tool.generation.remove_self_loops
      • graph_tool.generation.label_self_loops
      • graph_tool.generation.graph_union
      • graph_tool.generation.lattice
      • graph_tool.generation.complete_graph
      • graph_tool.generation.circular_graph
    • graph_tool.inference
      • graph_tool.inference.minimize_blockmodel_dl
      • graph_tool.inference.minimize_nested_blockmodel_dl
      • graph_tool.inference.BlockState
      • graph_tool.inference.OverlapBlockState
      • graph_tool.inference.LayeredBlockState
      • graph_tool.inference.NestedBlockState
      • graph_tool.inference.PPBlockState
      • graph_tool.inference.RankedBlockState
      • graph_tool.inference.ModularityState
      • graph_tool.inference.NormCutState
      • graph_tool.inference.TemperingState
      • graph_tool.inference.CliqueState
      • graph_tool.inference.MCMCState
      • graph_tool.inference.MultiflipMCMCState
      • graph_tool.inference.MultilevelMCMCState
      • graph_tool.inference.GibbsMCMCState
      • graph_tool.inference.MulticanonicalMCMCState
      • graph_tool.inference.ExhaustiveSweepState
      • graph_tool.inference.DrawBlockState
      • graph_tool.inference.mcmc_equilibrate
      • graph_tool.inference.mcmc_anneal
      • graph_tool.inference.multicanonical_equilibrate
      • graph_tool.inference.MulticanonicalState
      • graph_tool.inference.PartitionModeState
      • graph_tool.inference.ModeClusterState
      • graph_tool.inference.PartitionCentroidState
      • graph_tool.inference.partition_overlap
      • graph_tool.inference.nested_partition_overlap
      • graph_tool.inference.variation_information
      • graph_tool.inference.mutual_information
      • graph_tool.inference.reduced_mutual_information
      • graph_tool.inference.contingency_graph
      • graph_tool.inference.shuffle_partition_labels
      • graph_tool.inference.order_partition_labels
      • graph_tool.inference.order_nested_partition_labels
      • graph_tool.inference.align_partition_labels
      • graph_tool.inference.align_nested_partition_labels
      • graph_tool.inference.partition_overlap_center
      • graph_tool.inference.nested_partition_overlap_center
      • graph_tool.inference.nested_partition_clear_null
      • graph_tool.inference.contiguous_map
      • graph_tool.inference.nested_contiguous_map
      • graph_tool.inference.mf_entropy
      • graph_tool.inference.bethe_entropy
      • graph_tool.inference.microstate_entropy
      • graph_tool.inference.marginal_multigraph_entropy
      • graph_tool.inference.half_edge_graph
      • graph_tool.inference.get_block_edge_gradient
      • graph_tool.inference.PartitionHist
      • graph_tool.inference.BlockPairHist
      • graph_tool.inference.LatentLayerBaseState
      • graph_tool.inference.LatentMultigraphBlockState
      • graph_tool.inference.LatentClosureBlockState
      • graph_tool.inference.MeasuredBlockState
      • graph_tool.inference.MeasuredClosureBlockState
      • graph_tool.inference.MixedMeasuredBlockState
      • graph_tool.inference.UncertainBlockState
      • graph_tool.inference.UncertainBaseState
      • graph_tool.inference.DynamicsBlockStateBase
      • graph_tool.inference.EpidemicsBlockState
      • graph_tool.inference.IsingBaseBlockState
      • graph_tool.inference.IsingGlauberBlockState
      • graph_tool.inference.CIsingGlauberBlockState
      • graph_tool.inference.PseudoIsingBlockState
      • graph_tool.inference.PseudoCIsingBlockState
      • graph_tool.inference.latent_multigraph
      • graph_tool.inference.EMBlockState
      • graph_tool.inference.em_infer
      • graph_tool.inference.modularity
    • graph_tool.search
      • graph_tool.search.bfs_search
      • graph_tool.search.bfs_iterator
      • graph_tool.search.dfs_search
      • graph_tool.search.dfs_iterator
      • graph_tool.search.dijkstra_search
      • graph_tool.search.dijkstra_iterator
      • graph_tool.search.astar_search
      • graph_tool.search.astar_iterator
      • graph_tool.search.bellman_ford_search
      • graph_tool.search.BFSVisitor
      • graph_tool.search.DFSVisitor
      • graph_tool.search.DijkstraVisitor
      • graph_tool.search.BellmanFordVisitor
      • graph_tool.search.AStarVisitor
      • graph_tool.search.StopSearch
    • graph_tool.spectral
      • graph_tool.spectral.adjacency
      • graph_tool.spectral.laplacian
      • graph_tool.spectral.incidence
      • graph_tool.spectral.transition
      • graph_tool.spectral.modularity_matrix
      • graph_tool.spectral.hashimoto
      • graph_tool.spectral.AdjacencyOperator
      • graph_tool.spectral.LaplacianOperator
      • graph_tool.spectral.IncidenceOperator
      • graph_tool.spectral.TransitionOperator
      • graph_tool.spectral.HashimotoOperator
      • graph_tool.spectral.CompactHashimotoOperator
    • graph_tool.stats
      • graph_tool.stats.vertex_hist
      • graph_tool.stats.edge_hist
      • graph_tool.stats.vertex_average
      • graph_tool.stats.edge_average
      • graph_tool.stats.distance_histogram
    • graph_tool.topology
      • graph_tool.topology.shortest_distance
      • graph_tool.topology.shortest_path
      • graph_tool.topology.random_shortest_path
      • graph_tool.topology.count_shortest_paths
      • graph_tool.topology.all_shortest_paths
      • graph_tool.topology.all_predecessors
      • graph_tool.topology.all_paths
      • graph_tool.topology.all_circuits
      • graph_tool.topology.pseudo_diameter
      • graph_tool.topology.similarity
      • graph_tool.topology.vertex_similarity
      • graph_tool.topology.isomorphism
      • graph_tool.topology.subgraph_isomorphism
      • graph_tool.topology.mark_subgraph
      • graph_tool.topology.max_cliques
      • graph_tool.topology.max_cardinality_matching
      • graph_tool.topology.max_independent_vertex_set
      • graph_tool.topology.min_spanning_tree
      • graph_tool.topology.random_spanning_tree
      • graph_tool.topology.dominator_tree
      • graph_tool.topology.topological_sort
      • graph_tool.topology.transitive_closure
      • graph_tool.topology.label_components
      • graph_tool.topology.label_biconnected_components
      • graph_tool.topology.label_largest_component
      • graph_tool.topology.extract_largest_component
      • graph_tool.topology.label_out_component
      • graph_tool.topology.vertex_percolation
      • graph_tool.topology.edge_percolation
      • graph_tool.topology.kcore_decomposition
      • graph_tool.topology.is_bipartite
      • graph_tool.topology.is_DAG
      • graph_tool.topology.is_planar
      • graph_tool.topology.make_maximal_planar
      • graph_tool.topology.edge_reciprocity
      • graph_tool.topology.tsp_tour
      • graph_tool.topology.sequential_vertex_coloring
    • graph_tool.util
      • graph_tool.util.find_vertex
      • graph_tool.util.find_vertex_range
      • graph_tool.util.find_edge
      • graph_tool.util.find_edge_range
  • The gt file format
  • FAQ

Indices

  • General Index
  • Python Module Index
  • .rst

graph_tool.search.astar_search

Contents

  • astar_search()

graph_tool.search.astar_search#

graph_tool.search.astar_search(g, source, weight, visitor=<graph_tool.search.AStarVisitor object>, heuristic=<function <lambda>>, dist_map=None, pred_map=None, cost_map=None, combine=<function <lambda>>, compare=<function <lambda>>, zero=0, infinity=inf, implicit=False)[source]#

Heuristic \(A^*\) search on a weighted, directed or undirected graph for the case where all edge weights are non-negative.

Parameters:
gGraph

Graph to be used.

sourceVertex

Source vertex.

weightEdgePropertyMap

Edge property map with weight values.

visitorAStarVisitor (optional, default: AStarVisitor())

A visitor object that is invoked at the event points inside the algorithm. This should be a subclass of AStarVisitor.

heuristicunary function (optional, default: lambda v: 1)

The heuristic function that guides the search. It should take a single argument which is a Vertex, and output an estimated distance from the supplied vertex to the target vertex.

dist_mapVertexPropertyMap (optional, default: None)

A vertex property map where the distances from the source will be stored.

pred_mapVertexPropertyMap (optional, default: None)

A vertex property map where the predecessor map will be stored (must have value type “int64_t”).

cost_mapVertexPropertyMap (optional, default: None)

A vertex property map where the vertex costs will be stored. It must have the same value type as dist_map. This parameter is only used if implicit is True.

combinebinary function (optional, default: lambda a, b: a + b)

This function is used to combine distances to compute the distance of a path.

comparebinary function (optional, default: lambda a, b: a < b)

This function is use to compare distances to determine which vertex is closer to the source vertex.

implicitbool (optional, default: False)

If true, the underlying graph will be assumed to be implicit (i.e. constructed during the search).

zeroint or float (optional, default: 0)

Value assumed to correspond to a distance of zero by the combine and compare functions.

infinityint or float (optional, default: float('inf'))

Value assumed to correspond to a distance of infinity by the combine and compare functions.

Returns:
dist_mapVertexPropertyMap

A vertex property map with the computed distances from the source.

pred_mapVertexPropertyMap

A vertex property map with the predecessor tree.

See also

bfs_search

Breadth-first search

dfs_search

Depth-first search

dijkstra_search

Dijkstra’s search algorithm

Notes

The \(A^*\) algorithm is a heuristic graph search algorithm: an \(A^*\) search is “guided” by a heuristic function. A heuristic function \(h(v)\) is one which estimates the cost from a non-goal state (v) in the graph to some goal state, t. Intuitively, \(A^*\) follows paths (through the graph) to the goal that are estimated by the heuristic function to be the best paths. Unlike best-first search, \(A^*\) takes into account the known cost from the start of the search to v; the paths \(A^*\) takes are guided by a function \(f(v) = g(v) + h(v)\), where \(h(v)\) is the heuristic function, and \(g(v)\) (sometimes denoted \(c(s, v)\)) is the known cost from the start to v. Clearly, the efficiency of \(A^*\) is highly dependent on the heuristic function with which it is used.

The time complexity is \(O((E + V)\log V)\).

The pseudo-code for the \(A^*\) algorithm is listed below, with the annotated event points, for which the given visitor object will be called with the appropriate method.

A*(G, source, h)
  for each vertex u in V                 initialize vertex u
    d[u] := f[u] := infinity
    color[u] := WHITE
  end for
  color[s] := GRAY
  d[s] := 0
  f[s] := h(source)
  INSERT(Q, source)                      discover vertex source
  while (Q != Ø)
    u := EXTRACT-MIN(Q)                  examine vertex u
    for each vertex v in Adj[u]          examine edge (u,v)
      if (w(u,v) + d[u] < d[v])
        d[v] := w(u,v) + d[u]            edge (u,v) relaxed
        f[v] := d[v] + h(v)
        if (color[v] = WHITE)
          color[v] := GRAY
          INSERT(Q, v)                   discover vertex v
        else if (color[v] = BLACK)
          color[v] := GRAY
          INSERT(Q, v)                   reopen vertex v
        end if
      else
        ...                              edge (u,v) not relaxed
    end for
    color[u] := BLACK                    finish vertex u
  end while

References

[astar]

Hart, P. E.; Nilsson, N. J.; Raphael, B. “A Formal Basis for the Heuristic Determination of Minimum Cost Paths”. IEEE Transactions on Systems Science and Cybernetics SSC4 4 (2): 100-107, 1968. DOI: 10.1109/TSSC.1968.300136 [sci-hub, @tor]

[astar-bgl]

http://www.boost.org/doc/libs/release/libs/graph/doc/astar_search.html

[astar-wikipedia]

http://en.wikipedia.org/wiki/A*_search_algorithm

Examples

We will use an irregular two-dimensional lattice as an example, where the heuristic function will be based on the euclidean distance to the target.

The heuristic function will be defined as:

def h(v, target, pos):
    return sqrt(sum((pos[v].a - pos[target].a) ** 2))

where pos is the vertex position in the plane.

We must define what should be done during the search by subclassing AStarVisitor, and specializing the appropriate methods. In the following we will keep track of the discovered vertices, and which edges were examined, as well as the predecessor tree. We will also abort the search when a given target vertex is found, by raising the StopSearch exception.

class VisitorExample(gt.AStarVisitor):

    def __init__(self, touched_v, touched_e, target):
        self.touched_v = touched_v
        self.touched_e = touched_e
        self.target = target

    def discover_vertex(self, u):
        self.touched_v[u] = True

    def examine_edge(self, e):
        self.touched_e[e] = True

    def edge_relaxed(self, e):
        if e.target() == self.target:
            raise gt.StopSearch()

With the above class defined, we can perform the \(A^*\) search as follows.

>>> points = random((500, 2)) * 4
>>> points[0] = [-0.01, 0.01]
>>> points[1] = [4.01, 4.01]
>>> g, pos = gt.triangulation(points, type="delaunay")
>>> weight = g.new_edge_property("double") # Edge weights corresponding to
...                                        # Euclidean distances
>>> for e in g.edges():
...    weight[e] = sqrt(sum((pos[e.source()].a -
...                          pos[e.target()].a) ** 2))
>>> touch_v = g.new_vertex_property("bool")
>>> touch_e = g.new_edge_property("bool")
>>> target = g.vertex(1)
>>> dist, pred = gt.astar_search(g, g.vertex(0), weight,
...                              VisitorExample(touch_v, touch_e, target),
...                              heuristic=lambda v: h(v, target, pos))

We can now observe the best path found, and how many vertices and edges were visited in the process.

>>> ecolor = g.new_edge_property("string")
>>> ewidth = g.new_edge_property("double")
>>> ewidth.a = 1
>>> for e in g.edges():
...    ecolor[e] = "#3465a4" if touch_e[e] else "#d3d7cf"
>>> v = target
>>> while v != g.vertex(0):
...     p = g.vertex(pred[v])
...     for e in v.out_edges():
...         if e.target() == p:
...             ecolor[e] = "#a40000"
...             ewidth[e] = 3
...     v = p
>>> gt.graph_draw(g, pos=pos, output_size=(300, 300), vertex_fill_color=touch_v,
...               vcmap=matplotlib.cm.binary, edge_color=ecolor,
...               edge_pen_width=ewidth, output="astar-delaunay.svg")
<...>
../_images/astar-delaunay.svg

The shortest path is shown in red. The visited edges are shown in blue, and the visited vertices in black.#

The \(A^*\) algorithm is very useful for searching implicit graphs, i.e. graphs which are not entirely stored in memory and are generated “on-the-fly” during the search. In the following example we will carry out a search in a hamming hypercube of 10 bits witch has random weights on its edges in the range \([0,1]\). The vertices of the hypercube will be created during the search.

The heuristic function will use the Hamming distance between vertices:

def h(v, target, state):
    return sum(abs(state[v].a - target)) / 2

In the following visitor we will keep growing the graph on-the-fly, and abort the search when a given target vertex is found, by raising the StopSearch exception.

from numpy.random import random

class HammingVisitor(gt.AStarVisitor):

    def __init__(self, g, target, state, weight, dist, cost):
        self.g = g
        self.state = state
        self.target = target
        self.weight = weight
        self.dist = dist
        self.cost = cost
        self.visited = {}

    def examine_vertex(self, u):
        for i in range(len(self.state[u])):
            nstate = list(self.state[u])
            nstate[i] ^= 1
            if tuple(nstate) in self.visited:
                v = self.visited[tuple(nstate)]
            else:
                v = self.g.add_vertex()
                self.visited[tuple(nstate)] = v
                self.state[v] = nstate
                self.dist[v] = self.cost[v] = float('inf')
            for e in u.out_edges():
                if e.target() == v:
                    break
            else:
                e = self.g.add_edge(u, v)
                self.weight[e] = random()
        self.visited[tuple(self.state[u])] = u

    def edge_relaxed(self, e):
        if self.state[e.target()] == self.target:
            self.visited[tuple(self.target)] = e.target()
            raise gt.StopSearch()

With the above class defined, we can perform the \(A^*\) search as follows.

>>> g = gt.Graph(directed=False)
>>> state = g.new_vertex_property("vector<bool>")
>>> v = g.add_vertex()
>>> state[v] = [0] * 10
>>> target = [1] * 10
>>> weight = g.new_edge_property("double")
>>> dist = g.new_vertex_property("double")
>>> cost = g.new_vertex_property("double")
>>> visitor = HammingVisitor(g, target, state, weight, dist, cost)
>>> dist, pred = gt.astar_search(g, g.vertex(0), weight, visitor, dist_map=dist,
...                              cost_map=cost, heuristic=lambda v: h(v, array(target), state),
...                              implicit=True)

We can now observe the best path found, and how many vertices and edges were visited in the process.

>>> ecolor = g.new_edge_property("string")
>>> vcolor = g.new_vertex_property("string")
>>> ewidth = g.new_edge_property("double")
>>> ewidth.a = 1
>>> for e in g.edges():
...    ecolor[e] = "black"
>>> for v in g.vertices():
...    vcolor[v] = "white"
>>> v = visitor.visited[tuple(target)]
>>> while v != g.vertex(0):
...     vcolor[v] = "black"
...     p = g.vertex(pred[v])
...     for e in v.out_edges():
...         if e.target() == p:
...             ecolor[e] = "#a40000"
...             ewidth[e] = 3
...     v = p
>>> vcolor[v] = "black"
>>> pos = gt.graph_draw(g, output_size=(300, 300), vertex_fill_color=vcolor, edge_color=ecolor,
...                     edge_pen_width=ewidth, output="astar-implicit.svg")
../_images/astar-implicit.svg

The shortest path is shown in red, and the vertices which belong to it are in black. Note that the number of vertices visited is much smaller than the total number \(2^{10} = 1024\).#

previous

graph_tool.search.dijkstra_iterator

next

graph_tool.search.astar_iterator

Contents
  • astar_search()

© Copyright 2006-2023, Tiago de Paula Peixoto <tiago@skewed.de>.

Last updated on Jan 07, 2024.