networkx API Reference

Full documentation for networkx (3.4.2)

networkx.AmbiguousSolution
Python Library Documentation: class AmbiguousSolution in module networkx.exception

class AmbiguousSolution(NetworkXException)
 |  Raised if more than one valid solution exists for an intermediary step
 |  of an algorithm.
 |
 |  In the face of ambiguity, refuse the temptation to guess.
 |  This may occur, for example, when trying to determine the
 |  bipartite node sets in a disconnected bipartite graph when
 |  computing bipartite matchings.
 |
 |  Method resolution order:
 |      AmbiguousSolution
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.ArborescenceIterator
Python Library Documentation: class ArborescenceIterator in module networkx.algorithms.tree.branchings

class ArborescenceIterator(builtins.object)
 |  ArborescenceIterator(G, weight='weight', minimum=True, init_partition=None)
 |
 |  Iterate over all spanning arborescences of a graph in either increasing or
 |  decreasing cost.
 |
 |  Notes
 |  -----
 |  This iterator uses the partition scheme from [1]_ (included edges,
 |  excluded edges and open edges). It generates minimum spanning
 |  arborescences using a modified Edmonds' Algorithm which respects the
 |  partition of edges. For arborescences with the same weight, ties are
 |  broken arbitrarily.
 |
 |  References
 |  ----------
 |  .. [1] G.K. Janssens, K. Sörensen, An algorithm to generate all spanning
 |         trees in order of increasing cost, Pesquisa Operacional, 2005-08,
 |         Vol. 25 (2), p. 219-229,
 |         https://www.scielo.br/j/pope/a/XHswBwRwJyrfL88dmMwYNWp/?lang=en
 |
 |  Methods defined here:
 |
 |  __init__(self, G, weight='weight', minimum=True, init_partition=None)
 |      Initialize the iterator
 |
 |      Parameters
 |      ----------
 |      G : nx.DiGraph
 |          The directed graph which we need to iterate trees over
 |
 |      weight : String, default = "weight"
 |          The edge attribute used to store the weight of the edge
 |
 |      minimum : bool, default = True
 |          Return the trees in increasing order while true and decreasing order
 |          while false.
 |
 |      init_partition : tuple, default = None
 |          In the case that certain edges have to be included or excluded from
 |          the arborescences, `init_partition` should be in the form
 |          `(included_edges, excluded_edges)` where each edges is a
 |          `(u, v)`-tuple inside an iterable such as a list or set.
 |
 |  __iter__(self)
 |      Returns
 |      -------
 |      ArborescenceIterator
 |          The iterator object for this graph
 |
 |  __next__(self)
 |      Returns
 |      -------
 |      (multi)Graph
 |          The spanning tree of next greatest weight, which ties broken
 |          arbitrarily.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors defined here:
 |
 |  __dict__
 |      dictionary for instance variables
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes defined here:
 |
 |  Partition = <class 'networkx.algorithms.tree.branchings.ArborescenceIt...
 |      This dataclass represents a partition and stores a dict with the edge
 |      data and the weight of the minimum spanning arborescence of the
 |      partition dict.
networkx.DiGraph
Python Library Documentation: class DiGraph in module networkx.classes.digraph

class DiGraph(networkx.classes.graph.Graph)
 |  DiGraph(incoming_graph_data=None, **attr)
 |
 |  Base class for directed graphs.
 |
 |  A DiGraph stores nodes and edges with optional data, or attributes.
 |
 |  DiGraphs hold directed edges.  Self loops are allowed but multiple
 |  (parallel) edges are not.
 |
 |  Nodes can be arbitrary (hashable) Python objects with optional
 |  key/value attributes. By convention `None` is not used as a node.
 |
 |  Edges are represented as links between nodes with optional
 |  key/value attributes.
 |
 |  Parameters
 |  ----------
 |  incoming_graph_data : input graph (optional, default: None)
 |      Data to initialize graph. If None (default) an empty
 |      graph is created.  The data can be any format that is supported
 |      by the to_networkx_graph() function, currently including edge list,
 |      dict of dicts, dict of lists, NetworkX graph, 2D NumPy array, SciPy
 |      sparse matrix, or PyGraphviz graph.
 |
 |  attr : keyword arguments, optional (default= no attributes)
 |      Attributes to add to graph as key=value pairs.
 |
 |  See Also
 |  --------
 |  Graph
 |  MultiGraph
 |  MultiDiGraph
 |
 |  Examples
 |  --------
 |  Create an empty graph structure (a "null graph") with no nodes and
 |  no edges.
 |
 |  >>> G = nx.DiGraph()
 |
 |  G can be grown in several ways.
 |
 |  **Nodes:**
 |
 |  Add one node at a time:
 |
 |  >>> G.add_node(1)
 |
 |  Add the nodes from any container (a list, dict, set or
 |  even the lines from a file or the nodes from another graph).
 |
 |  >>> G.add_nodes_from([2, 3])
 |  >>> G.add_nodes_from(range(100, 110))
 |  >>> H = nx.path_graph(10)
 |  >>> G.add_nodes_from(H)
 |
 |  In addition to strings and integers any hashable Python object
 |  (except None) can represent a node, e.g. a customized node object,
 |  or even another Graph.
 |
 |  >>> G.add_node(H)
 |
 |  **Edges:**
 |
 |  G can also be grown by adding edges.
 |
 |  Add one edge,
 |
 |  >>> G.add_edge(1, 2)
 |
 |  a list of edges,
 |
 |  >>> G.add_edges_from([(1, 2), (1, 3)])
 |
 |  or a collection of edges,
 |
 |  >>> G.add_edges_from(H.edges)
 |
 |  If some edges connect nodes not yet in the graph, the nodes
 |  are added automatically.  There are no errors when adding
 |  nodes or edges that already exist.
 |
 |  **Attributes:**
 |
 |  Each graph, node, and edge can hold key/value attribute pairs
 |  in an associated attribute dictionary (the keys must be hashable).
 |  By default these are empty, but can be added or changed using
 |  add_edge, add_node or direct manipulation of the attribute
 |  dictionaries named graph, node and edge respectively.
 |
 |  >>> G = nx.DiGraph(day="Friday")
 |  >>> G.graph
 |  {'day': 'Friday'}
 |
 |  Add node attributes using add_node(), add_nodes_from() or G.nodes
 |
 |  >>> G.add_node(1, time="5pm")
 |  >>> G.add_nodes_from([3], time="2pm")
 |  >>> G.nodes[1]
 |  {'time': '5pm'}
 |  >>> G.nodes[1]["room"] = 714
 |  >>> del G.nodes[1]["room"]  # remove attribute
 |  >>> list(G.nodes(data=True))
 |  [(1, {'time': '5pm'}), (3, {'time': '2pm'})]
 |
 |  Add edge attributes using add_edge(), add_edges_from(), subscript
 |  notation, or G.edges.
 |
 |  >>> G.add_edge(1, 2, weight=4.7)
 |  >>> G.add_edges_from([(3, 4), (4, 5)], color="red")
 |  >>> G.add_edges_from([(1, 2, {"color": "blue"}), (2, 3, {"weight": 8})])
 |  >>> G[1][2]["weight"] = 4.7
 |  >>> G.edges[1, 2]["weight"] = 4
 |
 |  Warning: we protect the graph data structure by making `G.edges[1, 2]` a
 |  read-only dict-like structure. However, you can assign to attributes
 |  in e.g. `G.edges[1, 2]`. Thus, use 2 sets of brackets to add/change
 |  data attributes: `G.edges[1, 2]['weight'] = 4`
 |  (For multigraphs: `MG.edges[u, v, key][name] = value`).
 |
 |  **Shortcuts:**
 |
 |  Many common graph features allow python syntax to speed reporting.
 |
 |  >>> 1 in G  # check if node in graph
 |  True
 |  >>> [n for n in G if n < 3]  # iterate through nodes
 |  [1, 2]
 |  >>> len(G)  # number of nodes in graph
 |  5
 |
 |  Often the best way to traverse all edges of a graph is via the neighbors.
 |  The neighbors are reported as an adjacency-dict `G.adj` or `G.adjacency()`
 |
 |  >>> for n, nbrsdict in G.adjacency():
 |  ...     for nbr, eattr in nbrsdict.items():
 |  ...         if "weight" in eattr:
 |  ...             # Do something useful with the edges
 |  ...             pass
 |
 |  But the edges reporting object is often more convenient:
 |
 |  >>> for u, v, weight in G.edges(data="weight"):
 |  ...     if weight is not None:
 |  ...         # Do something useful with the edges
 |  ...         pass
 |
 |  **Reporting:**
 |
 |  Simple graph information is obtained using object-attributes and methods.
 |  Reporting usually provides views instead of containers to reduce memory
 |  usage. The views update as the graph is updated similarly to dict-views.
 |  The objects `nodes`, `edges` and `adj` provide access to data attributes
 |  via lookup (e.g. `nodes[n]`, `edges[u, v]`, `adj[u][v]`) and iteration
 |  (e.g. `nodes.items()`, `nodes.data('color')`,
 |  `nodes.data('color', default='blue')` and similarly for `edges`)
 |  Views exist for `nodes`, `edges`, `neighbors()`/`adj` and `degree`.
 |
 |  For details on these and other miscellaneous methods, see below.
 |
 |  **Subclasses (Advanced):**
 |
 |  The Graph class uses a dict-of-dict-of-dict data structure.
 |  The outer dict (node_dict) holds adjacency information keyed by node.
 |  The next dict (adjlist_dict) represents the adjacency information and holds
 |  edge data keyed by neighbor.  The inner dict (edge_attr_dict) represents
 |  the edge data and holds edge attribute values keyed by attribute names.
 |
 |  Each of these three dicts can be replaced in a subclass by a user defined
 |  dict-like object. In general, the dict-like features should be
 |  maintained but extra features can be added. To replace one of the
 |  dicts create a new graph class by changing the class(!) variable
 |  holding the factory for that dict-like structure. The variable names are
 |  node_dict_factory, node_attr_dict_factory, adjlist_inner_dict_factory,
 |  adjlist_outer_dict_factory, edge_attr_dict_factory and graph_attr_dict_factory.
 |
 |  node_dict_factory : function, (default: dict)
 |      Factory function to be used to create the dict containing node
 |      attributes, keyed by node id.
 |      It should require no arguments and return a dict-like object
 |
 |  node_attr_dict_factory: function, (default: dict)
 |      Factory function to be used to create the node attribute
 |      dict which holds attribute values keyed by attribute name.
 |      It should require no arguments and return a dict-like object
 |
 |  adjlist_outer_dict_factory : function, (default: dict)
 |      Factory function to be used to create the outer-most dict
 |      in the data structure that holds adjacency info keyed by node.
 |      It should require no arguments and return a dict-like object.
 |
 |  adjlist_inner_dict_factory : function, optional (default: dict)
 |      Factory function to be used to create the adjacency list
 |      dict which holds edge data keyed by neighbor.
 |      It should require no arguments and return a dict-like object
 |
 |  edge_attr_dict_factory : function, optional (default: dict)
 |      Factory function to be used to create the edge attribute
 |      dict which holds attribute values keyed by attribute name.
 |      It should require no arguments and return a dict-like object.
 |
 |  graph_attr_dict_factory : function, (default: dict)
 |      Factory function to be used to create the graph attribute
 |      dict which holds attribute values keyed by attribute name.
 |      It should require no arguments and return a dict-like object.
 |
 |  Typically, if your extension doesn't impact the data structure all
 |  methods will inherited without issue except: `to_directed/to_undirected`.
 |  By default these methods create a DiGraph/Graph class and you probably
 |  want them to create your extension of a DiGraph/Graph. To facilitate
 |  this we define two class variables that you can set in your subclass.
 |
 |  to_directed_class : callable, (default: DiGraph or MultiDiGraph)
 |      Class to create a new graph structure in the `to_directed` method.
 |      If `None`, a NetworkX class (DiGraph or MultiDiGraph) is used.
 |
 |  to_undirected_class : callable, (default: Graph or MultiGraph)
 |      Class to create a new graph structure in the `to_undirected` method.
 |      If `None`, a NetworkX class (Graph or MultiGraph) is used.
 |
 |  **Subclassing Example**
 |
 |  Create a low memory graph class that effectively disallows edge
 |  attributes by using a single attribute dict for all edges.
 |  This reduces the memory used, but you lose edge attributes.
 |
 |  >>> class ThinGraph(nx.Graph):
 |  ...     all_edge_dict = {"weight": 1}
 |  ...
 |  ...     def single_edge_dict(self):
 |  ...         return self.all_edge_dict
 |  ...
 |  ...     edge_attr_dict_factory = single_edge_dict
 |  >>> G = ThinGraph()
 |  >>> G.add_edge(2, 1)
 |  >>> G[2][1]
 |  {'weight': 1}
 |  >>> G.add_edge(2, 2)
 |  >>> G[2][1] is G[2][2]
 |  True
 |
 |  Method resolution order:
 |      DiGraph
 |      networkx.classes.graph.Graph
 |      builtins.object
 |
 |  Methods defined here:
 |
 |  __init__(self, incoming_graph_data=None, **attr)
 |      Initialize a graph with edges, name, or graph attributes.
 |
 |      Parameters
 |      ----------
 |      incoming_graph_data : input graph (optional, default: None)
 |          Data to initialize graph.  If None (default) an empty
 |          graph is created.  The data can be an edge list, or any
 |          NetworkX graph object.  If the corresponding optional Python
 |          packages are installed the data can also be a 2D NumPy array, a
 |          SciPy sparse array, or a PyGraphviz graph.
 |
 |      attr : keyword arguments, optional (default= no attributes)
 |          Attributes to add to graph as key=value pairs.
 |
 |      See Also
 |      --------
 |      convert
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G = nx.Graph(name="my graph")
 |      >>> e = [(1, 2), (2, 3), (3, 4)]  # list of edges
 |      >>> G = nx.Graph(e)
 |
 |      Arbitrary graph attribute pairs (key=value) may be assigned
 |
 |      >>> G = nx.Graph(e, day="Friday")
 |      >>> G.graph
 |      {'day': 'Friday'}
 |
 |  add_edge(self, u_of_edge, v_of_edge, **attr)
 |      Add an edge between u and v.
 |
 |      The nodes u and v will be automatically added if they are
 |      not already in the graph.
 |
 |      Edge attributes can be specified with keywords or by directly
 |      accessing the edge's attribute dictionary. See examples below.
 |
 |      Parameters
 |      ----------
 |      u_of_edge, v_of_edge : nodes
 |          Nodes can be, for example, strings or numbers.
 |          Nodes must be hashable (and not None) Python objects.
 |      attr : keyword arguments, optional
 |          Edge data (or labels or objects) can be assigned using
 |          keyword arguments.
 |
 |      See Also
 |      --------
 |      add_edges_from : add a collection of edges
 |
 |      Notes
 |      -----
 |      Adding an edge that already exists updates the edge data.
 |
 |      Many NetworkX algorithms designed for weighted graphs use
 |      an edge attribute (by default `weight`) to hold a numerical value.
 |
 |      Examples
 |      --------
 |      The following all add the edge e=(1, 2) to graph G:
 |
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> e = (1, 2)
 |      >>> G.add_edge(1, 2)  # explicit two-node form
 |      >>> G.add_edge(*e)  # single edge as tuple of two nodes
 |      >>> G.add_edges_from([(1, 2)])  # add edges from iterable container
 |
 |      Associate data to edges using keywords:
 |
 |      >>> G.add_edge(1, 2, weight=3)
 |      >>> G.add_edge(1, 3, weight=7, capacity=15, length=342.7)
 |
 |      For non-string attribute keys, use subscript notation.
 |
 |      >>> G.add_edge(1, 2)
 |      >>> G[1][2].update({0: 5})
 |      >>> G.edges[1, 2].update({0: 5})
 |
 |  add_edges_from(self, ebunch_to_add, **attr)
 |      Add all the edges in ebunch_to_add.
 |
 |      Parameters
 |      ----------
 |      ebunch_to_add : container of edges
 |          Each edge given in the container will be added to the
 |          graph. The edges must be given as 2-tuples (u, v) or
 |          3-tuples (u, v, d) where d is a dictionary containing edge data.
 |      attr : keyword arguments, optional
 |          Edge data (or labels or objects) can be assigned using
 |          keyword arguments.
 |
 |      See Also
 |      --------
 |      add_edge : add a single edge
 |      add_weighted_edges_from : convenient way to add weighted edges
 |
 |      Notes
 |      -----
 |      Adding the same edge twice has no effect but any edge data
 |      will be updated when each duplicate edge is added.
 |
 |      Edge attributes specified in an ebunch take precedence over
 |      attributes specified via keyword arguments.
 |
 |      When adding edges from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_edges)`, and pass this
 |      object to `G.add_edges_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_edges_from([(0, 1), (1, 2)])  # using a list of edge tuples
 |      >>> e = zip(range(0, 3), range(1, 4))
 |      >>> G.add_edges_from(e)  # Add the path graph 0-1-2-3
 |
 |      Associate data to edges
 |
 |      >>> G.add_edges_from([(1, 2), (2, 3)], weight=3)
 |      >>> G.add_edges_from([(3, 4), (1, 4)], label="WN2898")
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 4)])
 |      >>> # Grow graph by one new node, adding edges to all existing nodes.
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_edges_from(((5, n) for n in G.nodes))
 |      >>> # right way - note that there will be no self-edge for node 5
 |      >>> G.add_edges_from(list((5, n) for n in G.nodes))
 |
 |  add_node(self, node_for_adding, **attr)
 |      Add a single node `node_for_adding` and update node attributes.
 |
 |      Parameters
 |      ----------
 |      node_for_adding : node
 |          A node can be any hashable Python object except None.
 |      attr : keyword arguments, optional
 |          Set or change node attributes using key=value.
 |
 |      See Also
 |      --------
 |      add_nodes_from
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_node(1)
 |      >>> G.add_node("Hello")
 |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
 |      >>> G.add_node(K3)
 |      >>> G.number_of_nodes()
 |      3
 |
 |      Use keywords set/change node attributes:
 |
 |      >>> G.add_node(1, size=10)
 |      >>> G.add_node(3, weight=0.4, UTM=("13S", 382871, 3972649))
 |
 |      Notes
 |      -----
 |      A hashable object is one that can be used as a key in a Python
 |      dictionary. This includes strings, numbers, tuples of strings
 |      and numbers, etc.
 |
 |      On many platforms hashable items also include mutables such as
 |      NetworkX Graphs, though one should be careful that the hash
 |      doesn't change on mutables.
 |
 |  add_nodes_from(self, nodes_for_adding, **attr)
 |      Add multiple nodes.
 |
 |      Parameters
 |      ----------
 |      nodes_for_adding : iterable container
 |          A container of nodes (list, dict, set, etc.).
 |          OR
 |          A container of (node, attribute dict) tuples.
 |          Node attributes are updated using the attribute dict.
 |      attr : keyword arguments, optional (default= no attributes)
 |          Update attributes for all nodes in nodes.
 |          Node attributes specified in nodes as a tuple take
 |          precedence over attributes specified via keyword arguments.
 |
 |      See Also
 |      --------
 |      add_node
 |
 |      Notes
 |      -----
 |      When adding nodes from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
 |      object to `G.add_nodes_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_nodes_from("Hello")
 |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
 |      >>> G.add_nodes_from(K3)
 |      >>> sorted(G.nodes(), key=str)
 |      [0, 1, 2, 'H', 'e', 'l', 'o']
 |
 |      Use keywords to update specific node attributes for every node.
 |
 |      >>> G.add_nodes_from([1, 2], size=10)
 |      >>> G.add_nodes_from([3, 4], weight=0.4)
 |
 |      Use (node, attrdict) tuples to update attributes for specific nodes.
 |
 |      >>> G.add_nodes_from([(1, dict(size=11)), (2, {"color": "blue"})])
 |      >>> G.nodes[1]["size"]
 |      11
 |      >>> H = nx.Graph()
 |      >>> H.add_nodes_from(G.nodes(data=True))
 |      >>> H.nodes[1]["size"]
 |      11
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.DiGraph([(0, 1), (1, 2), (3, 4)])
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_nodes_from(n + 1 for n in G.nodes)
 |      >>> # correct way
 |      >>> G.add_nodes_from(list(n + 1 for n in G.nodes))
 |
 |  adj = <functools.cached_property object>
 |      Graph adjacency object holding the neighbors of each node.
 |
 |      This object is a read-only dict-like structure with node keys
 |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
 |      to the edge-data-dict.  So `G.adj[3][2]['color'] = 'blue'` sets
 |      the color of the edge `(3, 2)` to `"blue"`.
 |
 |      Iterating over G.adj behaves like a dict. Useful idioms include
 |      `for nbr, datadict in G.adj[n].items():`.
 |
 |      The neighbor information is also provided by subscripting the graph.
 |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
 |
 |      For directed graphs, `G.adj` holds outgoing (successor) info.
 |
 |  clear(self)
 |      Remove all nodes and edges from the graph.
 |
 |      This also removes the name, and all graph, node, and edge attributes.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.clear()
 |      >>> list(G.nodes)
 |      []
 |      >>> list(G.edges)
 |      []
 |
 |  clear_edges(self)
 |      Remove all edges from the graph without altering nodes.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.clear_edges()
 |      >>> list(G.nodes)
 |      [0, 1, 2, 3]
 |      >>> list(G.edges)
 |      []
 |
 |  degree = <functools.cached_property object>
 |      A DegreeView for the Graph as G.degree or G.degree().
 |
 |      The node degree is the number of edges adjacent to the node.
 |      The weighted node degree is the sum of the edge weights for
 |      edges incident to that node.
 |
 |      This object provides an iterator for (node, degree) as well as
 |      lookup for the degree for a single node.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      weight : string or None, optional (default=None)
 |         The name of an edge attribute that holds the numerical value used
 |         as a weight.  If None, then each edge has weight 1.
 |         The degree is the sum of the edge weights adjacent to the node.
 |
 |      Returns
 |      -------
 |      DiDegreeView or int
 |          If multiple nodes are requested (the default), returns a `DiDegreeView`
 |          mapping nodes to their degree.
 |          If a single node is requested, returns the degree of the node as an integer.
 |
 |      See Also
 |      --------
 |      in_degree, out_degree
 |
 |      Examples
 |      --------
 |      >>> G = nx.DiGraph()  # or MultiDiGraph
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.degree(0)  # node 0 with degree 1
 |      1
 |      >>> list(G.degree([0, 1, 2]))
 |      [(0, 1), (1, 2), (2, 2)]
 |
 |  edges = <functools.cached_property object>
 |      An OutEdgeView of the DiGraph as G.edges or G.edges().
 |
 |      edges(self, nbunch=None, data=False, default=None)
 |
 |      The OutEdgeView provides set-like operations on the edge-tuples
 |      as well as edge attribute lookup. When called, it also provides
 |      an EdgeDataView object which allows control of access to edge
 |      attributes (but does not provide set-like operations).
 |      Hence, `G.edges[u, v]['color']` provides the value of the color
 |      attribute for edge `(u, v)` while
 |      `for (u, v, c) in G.edges.data('color', default='red'):`
 |      iterates through all the edges yielding the color attribute
 |      with default `'red'` if no color attribute exists.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges from these nodes.
 |      data : string or bool, optional (default=False)
 |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
 |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
 |          If False, return 2-tuple (u, v).
 |      default : value, optional (default=None)
 |          Value used for edges that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      edges : OutEdgeView
 |          A view of edge attributes, usually it iterates over (u, v)
 |          or (u, v, d) tuples of edges, but can also be used for
 |          attribute lookup as `edges[u, v]['foo']`.
 |
 |      See Also
 |      --------
 |      in_edges, out_edges
 |
 |      Notes
 |      -----
 |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
 |      For directed graphs this returns the out-edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
 |      >>> nx.add_path(G, [0, 1, 2])
 |      >>> G.add_edge(2, 3, weight=5)
 |      >>> [e for e in G.edges]
 |      [(0, 1), (1, 2), (2, 3)]
 |      >>> G.edges.data()  # default data is {} (empty dict)
 |      OutEdgeDataView([(0, 1, {}), (1, 2, {}), (2, 3, {'weight': 5})])
 |      >>> G.edges.data("weight", default=1)
 |      OutEdgeDataView([(0, 1, 1), (1, 2, 1), (2, 3, 5)])
 |      >>> G.edges([0, 2])  # only edges originating from these nodes
 |      OutEdgeDataView([(0, 1), (2, 3)])
 |      >>> G.edges(0)  # only edges from node 0
 |      OutEdgeDataView([(0, 1)])
 |
 |  has_predecessor(self, u, v)
 |      Returns True if node u has predecessor v.
 |
 |      This is true if graph has the edge u<-v.
 |
 |  has_successor(self, u, v)
 |      Returns True if node u has successor v.
 |
 |      This is true if graph has the edge u->v.
 |
 |  in_degree = <functools.cached_property object>
 |      An InDegreeView for (node, in_degree) or in_degree for single node.
 |
 |      The node in_degree is the number of edges pointing to the node.
 |      The weighted node degree is the sum of the edge weights for
 |      edges incident to that node.
 |
 |      This object provides an iteration over (node, in_degree) as well as
 |      lookup for the degree for a single node.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      weight : string or None, optional (default=None)
 |         The name of an edge attribute that holds the numerical value used
 |         as a weight.  If None, then each edge has weight 1.
 |         The degree is the sum of the edge weights adjacent to the node.
 |
 |      Returns
 |      -------
 |      If a single node is requested
 |      deg : int
 |          In-degree of the node
 |
 |      OR if multiple nodes are requested
 |      nd_iter : iterator
 |          The iterator returns two-tuples of (node, in-degree).
 |
 |      See Also
 |      --------
 |      degree, out_degree
 |
 |      Examples
 |      --------
 |      >>> G = nx.DiGraph()
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.in_degree(0)  # node 0 with degree 0
 |      0
 |      >>> list(G.in_degree([0, 1, 2]))
 |      [(0, 0), (1, 1), (2, 1)]
 |
 |  in_edges = <functools.cached_property object>
 |      A view of the in edges of the graph as G.in_edges or G.in_edges().
 |
 |      in_edges(self, nbunch=None, data=False, default=None):
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |      data : string or bool, optional (default=False)
 |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
 |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
 |          If False, return 2-tuple (u, v).
 |      default : value, optional (default=None)
 |          Value used for edges that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      in_edges : InEdgeView or InEdgeDataView
 |          A view of edge attributes, usually it iterates over (u, v)
 |          or (u, v, d) tuples of edges, but can also be used for
 |          attribute lookup as `edges[u, v]['foo']`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.DiGraph()
 |      >>> G.add_edge(1, 2, color="blue")
 |      >>> G.in_edges()
 |      InEdgeView([(1, 2)])
 |      >>> G.in_edges(nbunch=2)
 |      InEdgeDataView([(1, 2)])
 |
 |      See Also
 |      --------
 |      edges
 |
 |  is_directed(self)
 |      Returns True if graph is directed, False otherwise.
 |
 |  is_multigraph(self)
 |      Returns True if graph is a multigraph, False otherwise.
 |
 |  neighbors = successors(self, n)
 |
 |  out_degree = <functools.cached_property object>
 |      An OutDegreeView for (node, out_degree)
 |
 |      The node out_degree is the number of edges pointing out of the node.
 |      The weighted node degree is the sum of the edge weights for
 |      edges incident to that node.
 |
 |      This object provides an iterator over (node, out_degree) as well as
 |      lookup for the degree for a single node.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      weight : string or None, optional (default=None)
 |         The name of an edge attribute that holds the numerical value used
 |         as a weight.  If None, then each edge has weight 1.
 |         The degree is the sum of the edge weights adjacent to the node.
 |
 |      Returns
 |      -------
 |      If a single node is requested
 |      deg : int
 |          Out-degree of the node
 |
 |      OR if multiple nodes are requested
 |      nd_iter : iterator
 |          The iterator returns two-tuples of (node, out-degree).
 |
 |      See Also
 |      --------
 |      degree, in_degree
 |
 |      Examples
 |      --------
 |      >>> G = nx.DiGraph()
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.out_degree(0)  # node 0 with degree 1
 |      1
 |      >>> list(G.out_degree([0, 1, 2]))
 |      [(0, 1), (1, 1), (2, 1)]
 |
 |  out_edges = <functools.cached_property object>
 |      An OutEdgeView of the DiGraph as G.edges or G.edges().
 |
 |      edges(self, nbunch=None, data=False, default=None)
 |
 |      The OutEdgeView provides set-like operations on the edge-tuples
 |      as well as edge attribute lookup. When called, it also provides
 |      an EdgeDataView object which allows control of access to edge
 |      attributes (but does not provide set-like operations).
 |      Hence, `G.edges[u, v]['color']` provides the value of the color
 |      attribute for edge `(u, v)` while
 |      `for (u, v, c) in G.edges.data('color', default='red'):`
 |      iterates through all the edges yielding the color attribute
 |      with default `'red'` if no color attribute exists.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges from these nodes.
 |      data : string or bool, optional (default=False)
 |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
 |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
 |          If False, return 2-tuple (u, v).
 |      default : value, optional (default=None)
 |          Value used for edges that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      edges : OutEdgeView
 |          A view of edge attributes, usually it iterates over (u, v)
 |          or (u, v, d) tuples of edges, but can also be used for
 |          attribute lookup as `edges[u, v]['foo']`.
 |
 |      See Also
 |      --------
 |      in_edges, out_edges
 |
 |      Notes
 |      -----
 |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
 |      For directed graphs this returns the out-edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
 |      >>> nx.add_path(G, [0, 1, 2])
 |      >>> G.add_edge(2, 3, weight=5)
 |      >>> [e for e in G.edges]
 |      [(0, 1), (1, 2), (2, 3)]
 |      >>> G.edges.data()  # default data is {} (empty dict)
 |      OutEdgeDataView([(0, 1, {}), (1, 2, {}), (2, 3, {'weight': 5})])
 |      >>> G.edges.data("weight", default=1)
 |      OutEdgeDataView([(0, 1, 1), (1, 2, 1), (2, 3, 5)])
 |      >>> G.edges([0, 2])  # only edges originating from these nodes
 |      OutEdgeDataView([(0, 1), (2, 3)])
 |      >>> G.edges(0)  # only edges from node 0
 |      OutEdgeDataView([(0, 1)])
 |
 |  pred = <functools.cached_property object>
 |      Graph adjacency object holding the predecessors of each node.
 |
 |      This object is a read-only dict-like structure with node keys
 |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
 |      to the edge-data-dict.  So `G.pred[2][3]['color'] = 'blue'` sets
 |      the color of the edge `(3, 2)` to `"blue"`.
 |
 |      Iterating over G.pred behaves like a dict. Useful idioms include
 |      `for nbr, datadict in G.pred[n].items():`.  A data-view not provided
 |      by dicts also exists: `for nbr, foovalue in G.pred[node].data('foo'):`
 |      A default can be set via a `default` argument to the `data` method.
 |
 |  predecessors(self, n)
 |      Returns an iterator over predecessor nodes of n.
 |
 |      A predecessor of n is a node m such that there exists a directed
 |      edge from m to n.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Raises
 |      ------
 |      NetworkXError
 |         If n is not in the graph.
 |
 |      See Also
 |      --------
 |      successors
 |
 |  remove_edge(self, u, v)
 |      Remove the edge between u and v.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |          Remove the edge between nodes u and v.
 |
 |      Raises
 |      ------
 |      NetworkXError
 |          If there is not an edge between u and v.
 |
 |      See Also
 |      --------
 |      remove_edges_from : remove a collection of edges
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, etc
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.remove_edge(0, 1)
 |      >>> e = (1, 2)
 |      >>> G.remove_edge(*e)  # unpacks e from an edge tuple
 |      >>> e = (2, 3, {"weight": 7})  # an edge with attribute data
 |      >>> G.remove_edge(*e[:2])  # select first part of edge tuple
 |
 |  remove_edges_from(self, ebunch)
 |      Remove all edges specified in ebunch.
 |
 |      Parameters
 |      ----------
 |      ebunch: list or container of edge tuples
 |          Each edge given in the list or container will be removed
 |          from the graph. The edges can be:
 |
 |              - 2-tuples (u, v) edge between u and v.
 |              - 3-tuples (u, v, k) where k is ignored.
 |
 |      See Also
 |      --------
 |      remove_edge : remove a single edge
 |
 |      Notes
 |      -----
 |      Will fail silently if an edge in ebunch is not in the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> ebunch = [(1, 2), (2, 3)]
 |      >>> G.remove_edges_from(ebunch)
 |
 |  remove_node(self, n)
 |      Remove node n.
 |
 |      Removes the node n and all adjacent edges.
 |      Attempting to remove a nonexistent node will raise an exception.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Raises
 |      ------
 |      NetworkXError
 |         If n is not in the graph.
 |
 |      See Also
 |      --------
 |      remove_nodes_from
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> list(G.edges)
 |      [(0, 1), (1, 2)]
 |      >>> G.remove_node(1)
 |      >>> list(G.edges)
 |      []
 |
 |  remove_nodes_from(self, nodes)
 |      Remove multiple nodes.
 |
 |      Parameters
 |      ----------
 |      nodes : iterable container
 |          A container of nodes (list, dict, set, etc.).  If a node
 |          in the container is not in the graph it is silently ignored.
 |
 |      See Also
 |      --------
 |      remove_node
 |
 |      Notes
 |      -----
 |      When removing nodes from an iterator over the graph you are changing,
 |      a `RuntimeError` will be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
 |      object to `G.remove_nodes_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> e = list(G.nodes)
 |      >>> e
 |      [0, 1, 2]
 |      >>> G.remove_nodes_from(e)
 |      >>> list(G.nodes)
 |      []
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.DiGraph([(0, 1), (1, 2), (3, 4)])
 |      >>> # this command will fail, as the graph's dict is modified during iteration
 |      >>> # G.remove_nodes_from(n for n in G.nodes if n < 2)
 |      >>> # this command will work, since the dictionary underlying graph is not modified
 |      >>> G.remove_nodes_from(list(n for n in G.nodes if n < 2))
 |
 |  reverse(self, copy=True)
 |      Returns the reverse of the graph.
 |
 |      The reverse is a graph with the same nodes and edges
 |      but with the directions of the edges reversed.
 |
 |      Parameters
 |      ----------
 |      copy : bool optional (default=True)
 |          If True, return a new DiGraph holding the reversed edges.
 |          If False, the reverse graph is created using a view of
 |          the original graph.
 |
 |  succ = <functools.cached_property object>
 |      Graph adjacency object holding the successors of each node.
 |
 |      This object is a read-only dict-like structure with node keys
 |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
 |      to the edge-data-dict.  So `G.succ[3][2]['color'] = 'blue'` sets
 |      the color of the edge `(3, 2)` to `"blue"`.
 |
 |      Iterating over G.succ behaves like a dict. Useful idioms include
 |      `for nbr, datadict in G.succ[n].items():`.  A data-view not provided
 |      by dicts also exists: `for nbr, foovalue in G.succ[node].data('foo'):`
 |      and a default can be set via a `default` argument to the `data` method.
 |
 |      The neighbor information is also provided by subscripting the graph.
 |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
 |
 |      For directed graphs, `G.adj` is identical to `G.succ`.
 |
 |  successors(self, n)
 |      Returns an iterator over successor nodes of n.
 |
 |      A successor of n is a node m such that there exists a directed
 |      edge from n to m.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Raises
 |      ------
 |      NetworkXError
 |         If n is not in the graph.
 |
 |      See Also
 |      --------
 |      predecessors
 |
 |      Notes
 |      -----
 |      neighbors() and successors() are the same.
 |
 |  to_undirected(self, reciprocal=False, as_view=False)
 |      Returns an undirected representation of the digraph.
 |
 |      Parameters
 |      ----------
 |      reciprocal : bool (optional)
 |        If True only keep edges that appear in both directions
 |        in the original digraph.
 |      as_view : bool (optional, default=False)
 |        If True return an undirected view of the original directed graph.
 |
 |      Returns
 |      -------
 |      G : Graph
 |          An undirected graph with the same name and nodes and
 |          with edge (u, v, data) if either (u, v, data) or (v, u, data)
 |          is in the digraph.  If both edges exist in digraph and
 |          their edge data is different, only one edge is created
 |          with an arbitrary choice of which edge data to use.
 |          You must check and correct for this manually if desired.
 |
 |      See Also
 |      --------
 |      Graph, copy, add_edge, add_edges_from
 |
 |      Notes
 |      -----
 |      If edges in both directions (u, v) and (v, u) exist in the
 |      graph, attributes for the new undirected edge will be a combination of
 |      the attributes of the directed edges.  The edge data is updated
 |      in the (arbitrary) order that the edges are encountered.  For
 |      more customized control of the edge attributes use add_edge().
 |
 |      This returns a "deepcopy" of the edge, node, and
 |      graph attributes which attempts to completely copy
 |      all of the data and references.
 |
 |      This is in contrast to the similar G=DiGraph(D) which returns a
 |      shallow copy of the data.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Warning: If you have subclassed DiGraph to use dict-like objects
 |      in the data structure, those changes do not transfer to the
 |      Graph created by this method.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(2)  # or MultiGraph, etc
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1), (1, 0)]
 |      >>> G2 = H.to_undirected()
 |      >>> list(G2.edges)
 |      [(0, 1)]
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from networkx.classes.graph.Graph:
 |
 |  __contains__(self, n)
 |      Returns True if n is a node, False otherwise. Use: 'n in G'.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> 1 in G
 |      True
 |
 |  __getitem__(self, n)
 |      Returns a dict of neighbors of node n.  Use: 'G[n]'.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph.
 |
 |      Returns
 |      -------
 |      adj_dict : dictionary
 |         The adjacency dictionary for nodes connected to n.
 |
 |      Notes
 |      -----
 |      G[n] is the same as G.adj[n] and similar to G.neighbors(n)
 |      (which is an iterator over G.adj[n])
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G[0]
 |      AtlasView({1: {}})
 |
 |  __iter__(self)
 |      Iterate over the nodes. Use: 'for n in G'.
 |
 |      Returns
 |      -------
 |      niter : iterator
 |          An iterator over all nodes in the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> [n for n in G]
 |      [0, 1, 2, 3]
 |      >>> list(G)
 |      [0, 1, 2, 3]
 |
 |  __len__(self)
 |      Returns the number of nodes in the graph. Use: 'len(G)'.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      number_of_nodes: identical method
 |      order: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> len(G)
 |      4
 |
 |  __str__(self)
 |      Returns a short summary of the graph.
 |
 |      Returns
 |      -------
 |      info : string
 |          Graph information including the graph name (if any), graph type, and the
 |          number of nodes and edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph(name="foo")
 |      >>> str(G)
 |      "Graph named 'foo' with 0 nodes and 0 edges"
 |
 |      >>> G = nx.path_graph(3)
 |      >>> str(G)
 |      'Graph with 3 nodes and 2 edges'
 |
 |  add_weighted_edges_from(self, ebunch_to_add, weight='weight', **attr)
 |      Add weighted edges in `ebunch_to_add` with specified weight attr
 |
 |      Parameters
 |      ----------
 |      ebunch_to_add : container of edges
 |          Each edge given in the list or container will be added
 |          to the graph. The edges must be given as 3-tuples (u, v, w)
 |          where w is a number.
 |      weight : string, optional (default= 'weight')
 |          The attribute name for the edge weights to be added.
 |      attr : keyword arguments, optional (default= no attributes)
 |          Edge attributes to add/update for all edges.
 |
 |      See Also
 |      --------
 |      add_edge : add a single edge
 |      add_edges_from : add multiple edges
 |
 |      Notes
 |      -----
 |      Adding the same edge twice for Graph/DiGraph simply updates
 |      the edge data. For MultiGraph/MultiDiGraph, duplicate edges
 |      are stored.
 |
 |      When adding edges from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_edges)`, and pass this
 |      object to `G.add_weighted_edges_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_weighted_edges_from([(0, 1, 3.0), (1, 2, 7.5)])
 |
 |      Evaluate an iterator over edges before passing it
 |
 |      >>> G = nx.Graph([(1, 2), (2, 3), (3, 4)])
 |      >>> weight = 0.1
 |      >>> # Grow graph by one new node, adding edges to all existing nodes.
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_weighted_edges_from(((5, n, weight) for n in G.nodes))
 |      >>> # correct way - note that there will be no self-edge for node 5
 |      >>> G.add_weighted_edges_from(list((5, n, weight) for n in G.nodes))
 |
 |  adjacency(self)
 |      Returns an iterator over (node, adjacency dict) tuples for all nodes.
 |
 |      For directed graphs, only outgoing neighbors/adjacencies are included.
 |
 |      Returns
 |      -------
 |      adj_iter : iterator
 |         An iterator over (node, adjacency dictionary) for all nodes in
 |         the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> [(n, nbrdict) for n, nbrdict in G.adjacency()]
 |      [(0, {1: {}}), (1, {0: {}, 2: {}}), (2, {1: {}, 3: {}}), (3, {2: {}})]
 |
 |  copy(self, as_view=False)
 |      Returns a copy of the graph.
 |
 |      The copy method by default returns an independent shallow copy
 |      of the graph and attributes. That is, if an attribute is a
 |      container, that container is shared by the original an the copy.
 |      Use Python's `copy.deepcopy` for new containers.
 |
 |      If `as_view` is True then a view is returned instead of a copy.
 |
 |      Notes
 |      -----
 |      All copies reproduce the graph structure, but data attributes
 |      may be handled in different ways. There are four types of copies
 |      of a graph that people might want.
 |
 |      Deepcopy -- A "deepcopy" copies the graph structure as well as
 |      all data attributes and any objects they might contain.
 |      The entire graph object is new so that changes in the copy
 |      do not affect the original object. (see Python's copy.deepcopy)
 |
 |      Data Reference (Shallow) -- For a shallow copy the graph structure
 |      is copied but the edge, node and graph attribute dicts are
 |      references to those in the original graph. This saves
 |      time and memory but could cause confusion if you change an attribute
 |      in one graph and it changes the attribute in the other.
 |      NetworkX does not provide this level of shallow copy.
 |
 |      Independent Shallow -- This copy creates new independent attribute
 |      dicts and then does a shallow copy of the attributes. That is, any
 |      attributes that are containers are shared between the new graph
 |      and the original. This is exactly what `dict.copy()` provides.
 |      You can obtain this style copy using:
 |
 |          >>> G = nx.path_graph(5)
 |          >>> H = G.copy()
 |          >>> H = G.copy(as_view=False)
 |          >>> H = nx.Graph(G)
 |          >>> H = G.__class__(G)
 |
 |      Fresh Data -- For fresh data, the graph structure is copied while
 |      new empty data attribute dicts are created. The resulting graph
 |      is independent of the original and it has no edge, node or graph
 |      attributes. Fresh copies are not enabled. Instead use:
 |
 |          >>> H = G.__class__()
 |          >>> H.add_nodes_from(G)
 |          >>> H.add_edges_from(G.edges)
 |
 |      View -- Inspired by dict-views, graph-views act like read-only
 |      versions of the original graph, providing a copy of the original
 |      structure without requiring any memory for copying the information.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Parameters
 |      ----------
 |      as_view : bool, optional (default=False)
 |          If True, the returned graph-view provides a read-only view
 |          of the original graph without actually copying any data.
 |
 |      Returns
 |      -------
 |      G : Graph
 |          A copy of the graph.
 |
 |      See Also
 |      --------
 |      to_directed: return a directed copy of the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> H = G.copy()
 |
 |  edge_subgraph(self, edges)
 |      Returns the subgraph induced by the specified edges.
 |
 |      The induced subgraph contains each edge in `edges` and each
 |      node incident to any one of those edges.
 |
 |      Parameters
 |      ----------
 |      edges : iterable
 |          An iterable of edges in this graph.
 |
 |      Returns
 |      -------
 |      G : Graph
 |          An edge-induced subgraph of this graph with the same edge
 |          attributes.
 |
 |      Notes
 |      -----
 |      The graph, edge, and node attributes in the returned subgraph
 |      view are references to the corresponding attributes in the original
 |      graph. The view is read-only.
 |
 |      To create a full graph version of the subgraph with its own copy
 |      of the edge or node attributes, use::
 |
 |          G.edge_subgraph(edges).copy()
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(5)
 |      >>> H = G.edge_subgraph([(0, 1), (3, 4)])
 |      >>> list(H.nodes)
 |      [0, 1, 3, 4]
 |      >>> list(H.edges)
 |      [(0, 1), (3, 4)]
 |
 |  get_edge_data(self, u, v, default=None)
 |      Returns the attribute dictionary associated with edge (u, v).
 |
 |      This is identical to `G[u][v]` except the default is returned
 |      instead of an exception if the edge doesn't exist.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |      default:  any Python object (default=None)
 |          Value to return if the edge (u, v) is not found.
 |
 |      Returns
 |      -------
 |      edge_dict : dictionary
 |          The edge attribute dictionary.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G[0][1]
 |      {}
 |
 |      Warning: Assigning to `G[u][v]` is not permitted.
 |      But it is safe to assign attributes `G[u][v]['foo']`
 |
 |      >>> G[0][1]["weight"] = 7
 |      >>> G[0][1]["weight"]
 |      7
 |      >>> G[1][0]["weight"]
 |      7
 |
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.get_edge_data(0, 1)  # default edge data is {}
 |      {}
 |      >>> e = (0, 1)
 |      >>> G.get_edge_data(*e)  # tuple form
 |      {}
 |      >>> G.get_edge_data("a", "b", default=0)  # edge not in graph, return 0
 |      0
 |
 |  has_edge(self, u, v)
 |      Returns True if the edge (u, v) is in the graph.
 |
 |      This is the same as `v in G[u]` without KeyError exceptions.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |          Nodes can be, for example, strings or numbers.
 |          Nodes must be hashable (and not None) Python objects.
 |
 |      Returns
 |      -------
 |      edge_ind : bool
 |          True if edge is in the graph, False otherwise.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.has_edge(0, 1)  # using two nodes
 |      True
 |      >>> e = (0, 1)
 |      >>> G.has_edge(*e)  #  e is a 2-tuple (u, v)
 |      True
 |      >>> e = (0, 1, {"weight": 7})
 |      >>> G.has_edge(*e[:2])  # e is a 3-tuple (u, v, data_dictionary)
 |      True
 |
 |      The following syntax are equivalent:
 |
 |      >>> G.has_edge(0, 1)
 |      True
 |      >>> 1 in G[0]  # though this gives KeyError if 0 not in G
 |      True
 |
 |  has_node(self, n)
 |      Returns True if the graph contains the node n.
 |
 |      Identical to `n in G`
 |
 |      Parameters
 |      ----------
 |      n : node
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.has_node(0)
 |      True
 |
 |      It is more readable and simpler to use
 |
 |      >>> 0 in G
 |      True
 |
 |  nbunch_iter(self, nbunch=None)
 |      Returns an iterator over nodes contained in nbunch that are
 |      also in the graph.
 |
 |      The nodes in nbunch are checked for membership in the graph
 |      and if not are silently ignored.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      Returns
 |      -------
 |      niter : iterator
 |          An iterator over nodes in nbunch that are also in the graph.
 |          If nbunch is None, iterate over all nodes in the graph.
 |
 |      Raises
 |      ------
 |      NetworkXError
 |          If nbunch is not a node or sequence of nodes.
 |          If a node in nbunch is not hashable.
 |
 |      See Also
 |      --------
 |      Graph.__iter__
 |
 |      Notes
 |      -----
 |      When nbunch is an iterator, the returned iterator yields values
 |      directly from nbunch, becoming exhausted when nbunch is exhausted.
 |
 |      To test whether nbunch is a single node, one can use
 |      "if nbunch in self:", even after processing with this routine.
 |
 |      If nbunch is not a node or a (possibly empty) sequence/iterator
 |      or None, a :exc:`NetworkXError` is raised.  Also, if any object in
 |      nbunch is not hashable, a :exc:`NetworkXError` is raised.
 |
 |  nodes = <functools.cached_property object>
 |      A NodeView of the Graph as G.nodes or G.nodes().
 |
 |      Can be used as `G.nodes` for data lookup and for set-like operations.
 |      Can also be used as `G.nodes(data='color', default=None)` to return a
 |      NodeDataView which reports specific node data but no set operations.
 |      It presents a dict-like interface as well with `G.nodes.items()`
 |      iterating over `(node, nodedata)` 2-tuples and `G.nodes[3]['foo']`
 |      providing the value of the `foo` attribute for node `3`. In addition,
 |      a view `G.nodes.data('foo')` provides a dict-like interface to the
 |      `foo` attribute of each node. `G.nodes.data('foo', default=1)`
 |      provides a default for nodes that do not have attribute `foo`.
 |
 |      Parameters
 |      ----------
 |      data : string or bool, optional (default=False)
 |          The node attribute returned in 2-tuple (n, ddict[data]).
 |          If True, return entire node attribute dict as (n, ddict).
 |          If False, return just the nodes n.
 |
 |      default : value, optional (default=None)
 |          Value used for nodes that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      NodeView
 |          Allows set-like operations over the nodes as well as node
 |          attribute dict lookup and calling to get a NodeDataView.
 |          A NodeDataView iterates over `(n, data)` and has no set operations.
 |          A NodeView iterates over `n` and includes set operations.
 |
 |          When called, if data is False, an iterator over nodes.
 |          Otherwise an iterator of 2-tuples (node, attribute value)
 |          where the attribute is specified in `data`.
 |          If data is True then the attribute becomes the
 |          entire data dictionary.
 |
 |      Notes
 |      -----
 |      If your node data is not needed, it is simpler and equivalent
 |      to use the expression ``for n in G``, or ``list(G)``.
 |
 |      Examples
 |      --------
 |      There are two simple ways of getting a list of all nodes in the graph:
 |
 |      >>> G = nx.path_graph(3)
 |      >>> list(G.nodes)
 |      [0, 1, 2]
 |      >>> list(G)
 |      [0, 1, 2]
 |
 |      To get the node data along with the nodes:
 |
 |      >>> G.add_node(1, time="5pm")
 |      >>> G.nodes[0]["foo"] = "bar"
 |      >>> list(G.nodes(data=True))
 |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
 |      >>> list(G.nodes.data())
 |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
 |
 |      >>> list(G.nodes(data="foo"))
 |      [(0, 'bar'), (1, None), (2, None)]
 |      >>> list(G.nodes.data("foo"))
 |      [(0, 'bar'), (1, None), (2, None)]
 |
 |      >>> list(G.nodes(data="time"))
 |      [(0, None), (1, '5pm'), (2, None)]
 |      >>> list(G.nodes.data("time"))
 |      [(0, None), (1, '5pm'), (2, None)]
 |
 |      >>> list(G.nodes(data="time", default="Not Available"))
 |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
 |      >>> list(G.nodes.data("time", default="Not Available"))
 |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
 |
 |      If some of your nodes have an attribute and the rest are assumed
 |      to have a default attribute value you can create a dictionary
 |      from node/attribute pairs using the `default` keyword argument
 |      to guarantee the value is never None::
 |
 |          >>> G = nx.Graph()
 |          >>> G.add_node(0)
 |          >>> G.add_node(1, weight=2)
 |          >>> G.add_node(2, weight=3)
 |          >>> dict(G.nodes(data="weight", default=1))
 |          {0: 1, 1: 2, 2: 3}
 |
 |  number_of_edges(self, u=None, v=None)
 |      Returns the number of edges between two nodes.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes, optional (default=all edges)
 |          If u and v are specified, return the number of edges between
 |          u and v. Otherwise return the total number of all edges.
 |
 |      Returns
 |      -------
 |      nedges : int
 |          The number of edges in the graph.  If nodes `u` and `v` are
 |          specified return the number of edges between those nodes. If
 |          the graph is directed, this only returns the number of edges
 |          from `u` to `v`.
 |
 |      See Also
 |      --------
 |      size
 |
 |      Examples
 |      --------
 |      For undirected graphs, this method counts the total number of
 |      edges in the graph:
 |
 |      >>> G = nx.path_graph(4)
 |      >>> G.number_of_edges()
 |      3
 |
 |      If you specify two nodes, this counts the total number of edges
 |      joining the two nodes:
 |
 |      >>> G.number_of_edges(0, 1)
 |      1
 |
 |      For directed graphs, this method can count the total number of
 |      directed edges from `u` to `v`:
 |
 |      >>> G = nx.DiGraph()
 |      >>> G.add_edge(0, 1)
 |      >>> G.add_edge(1, 0)
 |      >>> G.number_of_edges(0, 1)
 |      1
 |
 |  number_of_nodes(self)
 |      Returns the number of nodes in the graph.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      order: identical method
 |      __len__: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.number_of_nodes()
 |      3
 |
 |  order(self)
 |      Returns the number of nodes in the graph.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      number_of_nodes: identical method
 |      __len__: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.order()
 |      3
 |
 |  size(self, weight=None)
 |      Returns the number of edges or total of all edge weights.
 |
 |      Parameters
 |      ----------
 |      weight : string or None, optional (default=None)
 |          The edge attribute that holds the numerical value used
 |          as a weight. If None, then each edge has weight 1.
 |
 |      Returns
 |      -------
 |      size : numeric
 |          The number of edges or
 |          (if weight keyword is provided) the total weight sum.
 |
 |          If weight is None, returns an int. Otherwise a float
 |          (or more general numeric if the weights are more general).
 |
 |      See Also
 |      --------
 |      number_of_edges
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.size()
 |      3
 |
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_edge("a", "b", weight=2)
 |      >>> G.add_edge("b", "c", weight=4)
 |      >>> G.size()
 |      2
 |      >>> G.size(weight="weight")
 |      6.0
 |
 |  subgraph(self, nodes)
 |      Returns a SubGraph view of the subgraph induced on `nodes`.
 |
 |      The induced subgraph of the graph contains the nodes in `nodes`
 |      and the edges between those nodes.
 |
 |      Parameters
 |      ----------
 |      nodes : list, iterable
 |          A container of nodes which will be iterated through once.
 |
 |      Returns
 |      -------
 |      G : SubGraph View
 |          A subgraph view of the graph. The graph structure cannot be
 |          changed but node/edge attributes can and are shared with the
 |          original graph.
 |
 |      Notes
 |      -----
 |      The graph, edge and node attributes are shared with the original graph.
 |      Changes to the graph structure is ruled out by the view, but changes
 |      to attributes are reflected in the original graph.
 |
 |      To create a subgraph with its own copy of the edge/node attributes use:
 |      G.subgraph(nodes).copy()
 |
 |      For an inplace reduction of a graph to a subgraph you can remove nodes:
 |      G.remove_nodes_from([n for n in G if n not in set(nodes)])
 |
 |      Subgraph views are sometimes NOT what you want. In most cases where
 |      you want to do more than simply look at the induced edges, it makes
 |      more sense to just create the subgraph as its own graph with code like:
 |
 |      ::
 |
 |          # Create a subgraph SG based on a (possibly multigraph) G
 |          SG = G.__class__()
 |          SG.add_nodes_from((n, G.nodes[n]) for n in largest_wcc)
 |          if SG.is_multigraph():
 |              SG.add_edges_from(
 |                  (n, nbr, key, d)
 |                  for n, nbrs in G.adj.items()
 |                  if n in largest_wcc
 |                  for nbr, keydict in nbrs.items()
 |                  if nbr in largest_wcc
 |                  for key, d in keydict.items()
 |              )
 |          else:
 |              SG.add_edges_from(
 |                  (n, nbr, d)
 |                  for n, nbrs in G.adj.items()
 |                  if n in largest_wcc
 |                  for nbr, d in nbrs.items()
 |                  if nbr in largest_wcc
 |              )
 |          SG.graph.update(G.graph)
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> H = G.subgraph([0, 1, 2])
 |      >>> list(H.edges)
 |      [(0, 1), (1, 2)]
 |
 |  to_directed(self, as_view=False)
 |      Returns a directed representation of the graph.
 |
 |      Returns
 |      -------
 |      G : DiGraph
 |          A directed graph with the same name, same nodes, and with
 |          each edge (u, v, data) replaced by two directed edges
 |          (u, v, data) and (v, u, data).
 |
 |      Notes
 |      -----
 |      This returns a "deepcopy" of the edge, node, and
 |      graph attributes which attempts to completely copy
 |      all of the data and references.
 |
 |      This is in contrast to the similar D=DiGraph(G) which returns a
 |      shallow copy of the data.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Warning: If you have subclassed Graph to use dict-like objects
 |      in the data structure, those changes do not transfer to the
 |      DiGraph created by this method.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or MultiGraph, etc
 |      >>> G.add_edge(0, 1)
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1), (1, 0)]
 |
 |      If already directed, return a (deep) copy
 |
 |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
 |      >>> G.add_edge(0, 1)
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1)]
 |
 |  to_directed_class(self)
 |      Returns the class to use for empty directed copies.
 |
 |      If you subclass the base classes, use this to designate
 |      what directed class to use for `to_directed()` copies.
 |
 |  to_undirected_class(self)
 |      Returns the class to use for empty undirected copies.
 |
 |      If you subclass the base classes, use this to designate
 |      what directed class to use for `to_directed()` copies.
 |
 |  update(self, edges=None, nodes=None)
 |      Update the graph using nodes/edges/graphs as input.
 |
 |      Like dict.update, this method takes a graph as input, adding the
 |      graph's nodes and edges to this graph. It can also take two inputs:
 |      edges and nodes. Finally it can take either edges or nodes.
 |      To specify only nodes the keyword `nodes` must be used.
 |
 |      The collections of edges and nodes are treated similarly to
 |      the add_edges_from/add_nodes_from methods. When iterated, they
 |      should yield 2-tuples (u, v) or 3-tuples (u, v, datadict).
 |
 |      Parameters
 |      ----------
 |      edges : Graph object, collection of edges, or None
 |          The first parameter can be a graph or some edges. If it has
 |          attributes `nodes` and `edges`, then it is taken to be a
 |          Graph-like object and those attributes are used as collections
 |          of nodes and edges to be added to the graph.
 |          If the first parameter does not have those attributes, it is
 |          treated as a collection of edges and added to the graph.
 |          If the first argument is None, no edges are added.
 |      nodes : collection of nodes, or None
 |          The second parameter is treated as a collection of nodes
 |          to be added to the graph unless it is None.
 |          If `edges is None` and `nodes is None` an exception is raised.
 |          If the first parameter is a Graph, then `nodes` is ignored.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(5)
 |      >>> G.update(nx.complete_graph(range(4, 10)))
 |      >>> from itertools import combinations
 |      >>> edges = (
 |      ...     (u, v, {"power": u * v})
 |      ...     for u, v in combinations(range(10, 20), 2)
 |      ...     if u * v < 225
 |      ... )
 |      >>> nodes = [1000]  # for singleton, use a container
 |      >>> G.update(edges, nodes)
 |
 |      Notes
 |      -----
 |      It you want to update the graph using an adjacency structure
 |      it is straightforward to obtain the edges/nodes from adjacency.
 |      The following examples provide common cases, your adjacency may
 |      be slightly different and require tweaks of these examples::
 |
 |      >>> # dict-of-set/list/tuple
 |      >>> adj = {1: {2, 3}, 2: {1, 3}, 3: {1, 2}}
 |      >>> e = [(u, v) for u, nbrs in adj.items() for v in nbrs]
 |      >>> G.update(edges=e, nodes=adj)
 |
 |      >>> DG = nx.DiGraph()
 |      >>> # dict-of-dict-of-attribute
 |      >>> adj = {1: {2: 1.3, 3: 0.7}, 2: {1: 1.4}, 3: {1: 0.7}}
 |      >>> e = [
 |      ...     (u, v, {"weight": d})
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, d in nbrs.items()
 |      ... ]
 |      >>> DG.update(edges=e, nodes=adj)
 |
 |      >>> # dict-of-dict-of-dict
 |      >>> adj = {1: {2: {"weight": 1.3}, 3: {"color": 0.7, "weight": 1.2}}}
 |      >>> e = [
 |      ...     (u, v, {"weight": d})
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, d in nbrs.items()
 |      ... ]
 |      >>> DG.update(edges=e, nodes=adj)
 |
 |      >>> # predecessor adjacency (dict-of-set)
 |      >>> pred = {1: {2, 3}, 2: {3}, 3: {3}}
 |      >>> e = [(v, u) for u, nbrs in pred.items() for v in nbrs]
 |
 |      >>> # MultiGraph dict-of-dict-of-dict-of-attribute
 |      >>> MDG = nx.MultiDiGraph()
 |      >>> adj = {
 |      ...     1: {2: {0: {"weight": 1.3}, 1: {"weight": 1.2}}},
 |      ...     3: {2: {0: {"weight": 0.7}}},
 |      ... }
 |      >>> e = [
 |      ...     (u, v, ekey, d)
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, keydict in nbrs.items()
 |      ...     for ekey, d in keydict.items()
 |      ... ]
 |      >>> MDG.update(edges=e)
 |
 |      See Also
 |      --------
 |      add_edges_from: add multiple edges to a graph
 |      add_nodes_from: add multiple nodes to a graph
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from networkx.classes.graph.Graph:
 |
 |  __dict__
 |      dictionary for instance variables
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  name
 |      String identifier of the graph.
 |
 |      This graph attribute appears in the attribute dict G.graph
 |      keyed by the string `"name"`. as well as an attribute (technically
 |      a property) `G.name`. This is entirely user controlled.
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes inherited from networkx.classes.graph.Graph:
 |
 |  __networkx_backend__ = 'networkx'
 |
 |  adjlist_inner_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  adjlist_outer_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  edge_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  graph_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  node_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  node_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
networkx.EdgePartition
Python Library Documentation: class EdgePartition in module networkx.algorithms.tree.mst

class EdgePartition(enum.Enum)
 |  EdgePartition(*values)
 |
 |  An enum to store the state of an edge partition. The enum is written to the
 |  edges of a graph before being pasted to `kruskal_mst_edges`. Options are:
 |
 |  - EdgePartition.OPEN
 |  - EdgePartition.INCLUDED
 |  - EdgePartition.EXCLUDED
 |
 |  Method resolution order:
 |      EdgePartition
 |      enum.Enum
 |      builtins.object
 |
 |  Data and other attributes defined here:
 |
 |  EXCLUDED = <EdgePartition.EXCLUDED: 2>
 |
 |  INCLUDED = <EdgePartition.INCLUDED: 1>
 |
 |  OPEN = <EdgePartition.OPEN: 0>
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from enum.Enum:
 |
 |  name
 |      The name of the Enum member.
 |
 |  value
 |      The value of the Enum member.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from enum.EnumType:
 |
 |  __contains__(value)
 |      Return True if `value` is in `cls`.
 |
 |      `value` is in `cls` if:
 |      1) `value` is a member of `cls`, or
 |      2) `value` is the value of one of the `cls`'s members.
 |
 |  __getitem__(name)
 |      Return the member matching `name`.
 |
 |  __iter__()
 |      Return members in definition order.
 |
 |  __len__()
 |      Return the number of members (no aliases)
 |
 |  ----------------------------------------------------------------------
 |  Readonly properties inherited from enum.EnumType:
 |
 |  __members__
 |      Returns a mapping of member name->value.
 |
 |      This mapping lists all enum members, including aliases. Note that this
 |      is a read-only view of the internal mapping.
networkx.ExceededMaxIterations
Python Library Documentation: class ExceededMaxIterations in module networkx.exception

class ExceededMaxIterations(NetworkXException)
 |  Raised if a loop iterates too many times without breaking.
 |
 |  This may occur, for example, in an algorithm that computes
 |  progressively better approximations to a value but exceeds an
 |  iteration bound specified by the user.
 |
 |  Method resolution order:
 |      ExceededMaxIterations
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.Graph
Python Library Documentation: class Graph in module networkx.classes.graph

class Graph(builtins.object)
 |  Graph(incoming_graph_data=None, **attr)
 |
 |  Base class for undirected graphs.
 |
 |  A Graph stores nodes and edges with optional data, or attributes.
 |
 |  Graphs hold undirected edges.  Self loops are allowed but multiple
 |  (parallel) edges are not.
 |
 |  Nodes can be arbitrary (hashable) Python objects with optional
 |  key/value attributes, except that `None` is not allowed as a node.
 |
 |  Edges are represented as links between nodes with optional
 |  key/value attributes.
 |
 |  Parameters
 |  ----------
 |  incoming_graph_data : input graph (optional, default: None)
 |      Data to initialize graph. If None (default) an empty
 |      graph is created.  The data can be any format that is supported
 |      by the to_networkx_graph() function, currently including edge list,
 |      dict of dicts, dict of lists, NetworkX graph, 2D NumPy array, SciPy
 |      sparse matrix, or PyGraphviz graph.
 |
 |  attr : keyword arguments, optional (default= no attributes)
 |      Attributes to add to graph as key=value pairs.
 |
 |  See Also
 |  --------
 |  DiGraph
 |  MultiGraph
 |  MultiDiGraph
 |
 |  Examples
 |  --------
 |  Create an empty graph structure (a "null graph") with no nodes and
 |  no edges.
 |
 |  >>> G = nx.Graph()
 |
 |  G can be grown in several ways.
 |
 |  **Nodes:**
 |
 |  Add one node at a time:
 |
 |  >>> G.add_node(1)
 |
 |  Add the nodes from any container (a list, dict, set or
 |  even the lines from a file or the nodes from another graph).
 |
 |  >>> G.add_nodes_from([2, 3])
 |  >>> G.add_nodes_from(range(100, 110))
 |  >>> H = nx.path_graph(10)
 |  >>> G.add_nodes_from(H)
 |
 |  In addition to strings and integers any hashable Python object
 |  (except None) can represent a node, e.g. a customized node object,
 |  or even another Graph.
 |
 |  >>> G.add_node(H)
 |
 |  **Edges:**
 |
 |  G can also be grown by adding edges.
 |
 |  Add one edge,
 |
 |  >>> G.add_edge(1, 2)
 |
 |  a list of edges,
 |
 |  >>> G.add_edges_from([(1, 2), (1, 3)])
 |
 |  or a collection of edges,
 |
 |  >>> G.add_edges_from(H.edges)
 |
 |  If some edges connect nodes not yet in the graph, the nodes
 |  are added automatically.  There are no errors when adding
 |  nodes or edges that already exist.
 |
 |  **Attributes:**
 |
 |  Each graph, node, and edge can hold key/value attribute pairs
 |  in an associated attribute dictionary (the keys must be hashable).
 |  By default these are empty, but can be added or changed using
 |  add_edge, add_node or direct manipulation of the attribute
 |  dictionaries named graph, node and edge respectively.
 |
 |  >>> G = nx.Graph(day="Friday")
 |  >>> G.graph
 |  {'day': 'Friday'}
 |
 |  Add node attributes using add_node(), add_nodes_from() or G.nodes
 |
 |  >>> G.add_node(1, time="5pm")
 |  >>> G.add_nodes_from([3], time="2pm")
 |  >>> G.nodes[1]
 |  {'time': '5pm'}
 |  >>> G.nodes[1]["room"] = 714  # node must exist already to use G.nodes
 |  >>> del G.nodes[1]["room"]  # remove attribute
 |  >>> list(G.nodes(data=True))
 |  [(1, {'time': '5pm'}), (3, {'time': '2pm'})]
 |
 |  Add edge attributes using add_edge(), add_edges_from(), subscript
 |  notation, or G.edges.
 |
 |  >>> G.add_edge(1, 2, weight=4.7)
 |  >>> G.add_edges_from([(3, 4), (4, 5)], color="red")
 |  >>> G.add_edges_from([(1, 2, {"color": "blue"}), (2, 3, {"weight": 8})])
 |  >>> G[1][2]["weight"] = 4.7
 |  >>> G.edges[1, 2]["weight"] = 4
 |
 |  Warning: we protect the graph data structure by making `G.edges` a
 |  read-only dict-like structure. However, you can assign to attributes
 |  in e.g. `G.edges[1, 2]`. Thus, use 2 sets of brackets to add/change
 |  data attributes: `G.edges[1, 2]['weight'] = 4`
 |  (For multigraphs: `MG.edges[u, v, key][name] = value`).
 |
 |  **Shortcuts:**
 |
 |  Many common graph features allow python syntax to speed reporting.
 |
 |  >>> 1 in G  # check if node in graph
 |  True
 |  >>> [n for n in G if n < 3]  # iterate through nodes
 |  [1, 2]
 |  >>> len(G)  # number of nodes in graph
 |  5
 |
 |  Often the best way to traverse all edges of a graph is via the neighbors.
 |  The neighbors are reported as an adjacency-dict `G.adj` or `G.adjacency()`
 |
 |  >>> for n, nbrsdict in G.adjacency():
 |  ...     for nbr, eattr in nbrsdict.items():
 |  ...         if "weight" in eattr:
 |  ...             # Do something useful with the edges
 |  ...             pass
 |
 |  But the edges() method is often more convenient:
 |
 |  >>> for u, v, weight in G.edges.data("weight"):
 |  ...     if weight is not None:
 |  ...         # Do something useful with the edges
 |  ...         pass
 |
 |  **Reporting:**
 |
 |  Simple graph information is obtained using object-attributes and methods.
 |  Reporting typically provides views instead of containers to reduce memory
 |  usage. The views update as the graph is updated similarly to dict-views.
 |  The objects `nodes`, `edges` and `adj` provide access to data attributes
 |  via lookup (e.g. `nodes[n]`, `edges[u, v]`, `adj[u][v]`) and iteration
 |  (e.g. `nodes.items()`, `nodes.data('color')`,
 |  `nodes.data('color', default='blue')` and similarly for `edges`)
 |  Views exist for `nodes`, `edges`, `neighbors()`/`adj` and `degree`.
 |
 |  For details on these and other miscellaneous methods, see below.
 |
 |  **Subclasses (Advanced):**
 |
 |  The Graph class uses a dict-of-dict-of-dict data structure.
 |  The outer dict (node_dict) holds adjacency information keyed by node.
 |  The next dict (adjlist_dict) represents the adjacency information and holds
 |  edge data keyed by neighbor.  The inner dict (edge_attr_dict) represents
 |  the edge data and holds edge attribute values keyed by attribute names.
 |
 |  Each of these three dicts can be replaced in a subclass by a user defined
 |  dict-like object. In general, the dict-like features should be
 |  maintained but extra features can be added. To replace one of the
 |  dicts create a new graph class by changing the class(!) variable
 |  holding the factory for that dict-like structure.
 |
 |  node_dict_factory : function, (default: dict)
 |      Factory function to be used to create the dict containing node
 |      attributes, keyed by node id.
 |      It should require no arguments and return a dict-like object
 |
 |  node_attr_dict_factory: function, (default: dict)
 |      Factory function to be used to create the node attribute
 |      dict which holds attribute values keyed by attribute name.
 |      It should require no arguments and return a dict-like object
 |
 |  adjlist_outer_dict_factory : function, (default: dict)
 |      Factory function to be used to create the outer-most dict
 |      in the data structure that holds adjacency info keyed by node.
 |      It should require no arguments and return a dict-like object.
 |
 |  adjlist_inner_dict_factory : function, (default: dict)
 |      Factory function to be used to create the adjacency list
 |      dict which holds edge data keyed by neighbor.
 |      It should require no arguments and return a dict-like object
 |
 |  edge_attr_dict_factory : function, (default: dict)
 |      Factory function to be used to create the edge attribute
 |      dict which holds attribute values keyed by attribute name.
 |      It should require no arguments and return a dict-like object.
 |
 |  graph_attr_dict_factory : function, (default: dict)
 |      Factory function to be used to create the graph attribute
 |      dict which holds attribute values keyed by attribute name.
 |      It should require no arguments and return a dict-like object.
 |
 |  Typically, if your extension doesn't impact the data structure all
 |  methods will inherit without issue except: `to_directed/to_undirected`.
 |  By default these methods create a DiGraph/Graph class and you probably
 |  want them to create your extension of a DiGraph/Graph. To facilitate
 |  this we define two class variables that you can set in your subclass.
 |
 |  to_directed_class : callable, (default: DiGraph or MultiDiGraph)
 |      Class to create a new graph structure in the `to_directed` method.
 |      If `None`, a NetworkX class (DiGraph or MultiDiGraph) is used.
 |
 |  to_undirected_class : callable, (default: Graph or MultiGraph)
 |      Class to create a new graph structure in the `to_undirected` method.
 |      If `None`, a NetworkX class (Graph or MultiGraph) is used.
 |
 |  **Subclassing Example**
 |
 |  Create a low memory graph class that effectively disallows edge
 |  attributes by using a single attribute dict for all edges.
 |  This reduces the memory used, but you lose edge attributes.
 |
 |  >>> class ThinGraph(nx.Graph):
 |  ...     all_edge_dict = {"weight": 1}
 |  ...
 |  ...     def single_edge_dict(self):
 |  ...         return self.all_edge_dict
 |  ...
 |  ...     edge_attr_dict_factory = single_edge_dict
 |  >>> G = ThinGraph()
 |  >>> G.add_edge(2, 1)
 |  >>> G[2][1]
 |  {'weight': 1}
 |  >>> G.add_edge(2, 2)
 |  >>> G[2][1] is G[2][2]
 |  True
 |
 |  Methods defined here:
 |
 |  __contains__(self, n)
 |      Returns True if n is a node, False otherwise. Use: 'n in G'.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> 1 in G
 |      True
 |
 |  __getitem__(self, n)
 |      Returns a dict of neighbors of node n.  Use: 'G[n]'.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph.
 |
 |      Returns
 |      -------
 |      adj_dict : dictionary
 |         The adjacency dictionary for nodes connected to n.
 |
 |      Notes
 |      -----
 |      G[n] is the same as G.adj[n] and similar to G.neighbors(n)
 |      (which is an iterator over G.adj[n])
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G[0]
 |      AtlasView({1: {}})
 |
 |  __init__(self, incoming_graph_data=None, **attr)
 |      Initialize a graph with edges, name, or graph attributes.
 |
 |      Parameters
 |      ----------
 |      incoming_graph_data : input graph (optional, default: None)
 |          Data to initialize graph. If None (default) an empty
 |          graph is created.  The data can be an edge list, or any
 |          NetworkX graph object.  If the corresponding optional Python
 |          packages are installed the data can also be a 2D NumPy array, a
 |          SciPy sparse array, or a PyGraphviz graph.
 |
 |      attr : keyword arguments, optional (default= no attributes)
 |          Attributes to add to graph as key=value pairs.
 |
 |      See Also
 |      --------
 |      convert
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G = nx.Graph(name="my graph")
 |      >>> e = [(1, 2), (2, 3), (3, 4)]  # list of edges
 |      >>> G = nx.Graph(e)
 |
 |      Arbitrary graph attribute pairs (key=value) may be assigned
 |
 |      >>> G = nx.Graph(e, day="Friday")
 |      >>> G.graph
 |      {'day': 'Friday'}
 |
 |  __iter__(self)
 |      Iterate over the nodes. Use: 'for n in G'.
 |
 |      Returns
 |      -------
 |      niter : iterator
 |          An iterator over all nodes in the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> [n for n in G]
 |      [0, 1, 2, 3]
 |      >>> list(G)
 |      [0, 1, 2, 3]
 |
 |  __len__(self)
 |      Returns the number of nodes in the graph. Use: 'len(G)'.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      number_of_nodes: identical method
 |      order: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> len(G)
 |      4
 |
 |  __str__(self)
 |      Returns a short summary of the graph.
 |
 |      Returns
 |      -------
 |      info : string
 |          Graph information including the graph name (if any), graph type, and the
 |          number of nodes and edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph(name="foo")
 |      >>> str(G)
 |      "Graph named 'foo' with 0 nodes and 0 edges"
 |
 |      >>> G = nx.path_graph(3)
 |      >>> str(G)
 |      'Graph with 3 nodes and 2 edges'
 |
 |  add_edge(self, u_of_edge, v_of_edge, **attr)
 |      Add an edge between u and v.
 |
 |      The nodes u and v will be automatically added if they are
 |      not already in the graph.
 |
 |      Edge attributes can be specified with keywords or by directly
 |      accessing the edge's attribute dictionary. See examples below.
 |
 |      Parameters
 |      ----------
 |      u_of_edge, v_of_edge : nodes
 |          Nodes can be, for example, strings or numbers.
 |          Nodes must be hashable (and not None) Python objects.
 |      attr : keyword arguments, optional
 |          Edge data (or labels or objects) can be assigned using
 |          keyword arguments.
 |
 |      See Also
 |      --------
 |      add_edges_from : add a collection of edges
 |
 |      Notes
 |      -----
 |      Adding an edge that already exists updates the edge data.
 |
 |      Many NetworkX algorithms designed for weighted graphs use
 |      an edge attribute (by default `weight`) to hold a numerical value.
 |
 |      Examples
 |      --------
 |      The following all add the edge e=(1, 2) to graph G:
 |
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> e = (1, 2)
 |      >>> G.add_edge(1, 2)  # explicit two-node form
 |      >>> G.add_edge(*e)  # single edge as tuple of two nodes
 |      >>> G.add_edges_from([(1, 2)])  # add edges from iterable container
 |
 |      Associate data to edges using keywords:
 |
 |      >>> G.add_edge(1, 2, weight=3)
 |      >>> G.add_edge(1, 3, weight=7, capacity=15, length=342.7)
 |
 |      For non-string attribute keys, use subscript notation.
 |
 |      >>> G.add_edge(1, 2)
 |      >>> G[1][2].update({0: 5})
 |      >>> G.edges[1, 2].update({0: 5})
 |
 |  add_edges_from(self, ebunch_to_add, **attr)
 |      Add all the edges in ebunch_to_add.
 |
 |      Parameters
 |      ----------
 |      ebunch_to_add : container of edges
 |          Each edge given in the container will be added to the
 |          graph. The edges must be given as 2-tuples (u, v) or
 |          3-tuples (u, v, d) where d is a dictionary containing edge data.
 |      attr : keyword arguments, optional
 |          Edge data (or labels or objects) can be assigned using
 |          keyword arguments.
 |
 |      See Also
 |      --------
 |      add_edge : add a single edge
 |      add_weighted_edges_from : convenient way to add weighted edges
 |
 |      Notes
 |      -----
 |      Adding the same edge twice has no effect but any edge data
 |      will be updated when each duplicate edge is added.
 |
 |      Edge attributes specified in an ebunch take precedence over
 |      attributes specified via keyword arguments.
 |
 |      When adding edges from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_edges)`, and pass this
 |      object to `G.add_edges_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_edges_from([(0, 1), (1, 2)])  # using a list of edge tuples
 |      >>> e = zip(range(0, 3), range(1, 4))
 |      >>> G.add_edges_from(e)  # Add the path graph 0-1-2-3
 |
 |      Associate data to edges
 |
 |      >>> G.add_edges_from([(1, 2), (2, 3)], weight=3)
 |      >>> G.add_edges_from([(3, 4), (1, 4)], label="WN2898")
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.Graph([(1, 2), (2, 3), (3, 4)])
 |      >>> # Grow graph by one new node, adding edges to all existing nodes.
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_edges_from(((5, n) for n in G.nodes))
 |      >>> # correct way - note that there will be no self-edge for node 5
 |      >>> G.add_edges_from(list((5, n) for n in G.nodes))
 |
 |  add_node(self, node_for_adding, **attr)
 |      Add a single node `node_for_adding` and update node attributes.
 |
 |      Parameters
 |      ----------
 |      node_for_adding : node
 |          A node can be any hashable Python object except None.
 |      attr : keyword arguments, optional
 |          Set or change node attributes using key=value.
 |
 |      See Also
 |      --------
 |      add_nodes_from
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_node(1)
 |      >>> G.add_node("Hello")
 |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
 |      >>> G.add_node(K3)
 |      >>> G.number_of_nodes()
 |      3
 |
 |      Use keywords set/change node attributes:
 |
 |      >>> G.add_node(1, size=10)
 |      >>> G.add_node(3, weight=0.4, UTM=("13S", 382871, 3972649))
 |
 |      Notes
 |      -----
 |      A hashable object is one that can be used as a key in a Python
 |      dictionary. This includes strings, numbers, tuples of strings
 |      and numbers, etc.
 |
 |      On many platforms hashable items also include mutables such as
 |      NetworkX Graphs, though one should be careful that the hash
 |      doesn't change on mutables.
 |
 |  add_nodes_from(self, nodes_for_adding, **attr)
 |      Add multiple nodes.
 |
 |      Parameters
 |      ----------
 |      nodes_for_adding : iterable container
 |          A container of nodes (list, dict, set, etc.).
 |          OR
 |          A container of (node, attribute dict) tuples.
 |          Node attributes are updated using the attribute dict.
 |      attr : keyword arguments, optional (default= no attributes)
 |          Update attributes for all nodes in nodes.
 |          Node attributes specified in nodes as a tuple take
 |          precedence over attributes specified via keyword arguments.
 |
 |      See Also
 |      --------
 |      add_node
 |
 |      Notes
 |      -----
 |      When adding nodes from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
 |      object to `G.add_nodes_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_nodes_from("Hello")
 |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
 |      >>> G.add_nodes_from(K3)
 |      >>> sorted(G.nodes(), key=str)
 |      [0, 1, 2, 'H', 'e', 'l', 'o']
 |
 |      Use keywords to update specific node attributes for every node.
 |
 |      >>> G.add_nodes_from([1, 2], size=10)
 |      >>> G.add_nodes_from([3, 4], weight=0.4)
 |
 |      Use (node, attrdict) tuples to update attributes for specific nodes.
 |
 |      >>> G.add_nodes_from([(1, dict(size=11)), (2, {"color": "blue"})])
 |      >>> G.nodes[1]["size"]
 |      11
 |      >>> H = nx.Graph()
 |      >>> H.add_nodes_from(G.nodes(data=True))
 |      >>> H.nodes[1]["size"]
 |      11
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.Graph([(0, 1), (1, 2), (3, 4)])
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_nodes_from(n + 1 for n in G.nodes)
 |      >>> # correct way
 |      >>> G.add_nodes_from(list(n + 1 for n in G.nodes))
 |
 |  add_weighted_edges_from(self, ebunch_to_add, weight='weight', **attr)
 |      Add weighted edges in `ebunch_to_add` with specified weight attr
 |
 |      Parameters
 |      ----------
 |      ebunch_to_add : container of edges
 |          Each edge given in the list or container will be added
 |          to the graph. The edges must be given as 3-tuples (u, v, w)
 |          where w is a number.
 |      weight : string, optional (default= 'weight')
 |          The attribute name for the edge weights to be added.
 |      attr : keyword arguments, optional (default= no attributes)
 |          Edge attributes to add/update for all edges.
 |
 |      See Also
 |      --------
 |      add_edge : add a single edge
 |      add_edges_from : add multiple edges
 |
 |      Notes
 |      -----
 |      Adding the same edge twice for Graph/DiGraph simply updates
 |      the edge data. For MultiGraph/MultiDiGraph, duplicate edges
 |      are stored.
 |
 |      When adding edges from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_edges)`, and pass this
 |      object to `G.add_weighted_edges_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_weighted_edges_from([(0, 1, 3.0), (1, 2, 7.5)])
 |
 |      Evaluate an iterator over edges before passing it
 |
 |      >>> G = nx.Graph([(1, 2), (2, 3), (3, 4)])
 |      >>> weight = 0.1
 |      >>> # Grow graph by one new node, adding edges to all existing nodes.
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_weighted_edges_from(((5, n, weight) for n in G.nodes))
 |      >>> # correct way - note that there will be no self-edge for node 5
 |      >>> G.add_weighted_edges_from(list((5, n, weight) for n in G.nodes))
 |
 |  adj = <functools.cached_property object>
 |      Graph adjacency object holding the neighbors of each node.
 |
 |      This object is a read-only dict-like structure with node keys
 |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
 |      to the edge-data-dict.  So `G.adj[3][2]['color'] = 'blue'` sets
 |      the color of the edge `(3, 2)` to `"blue"`.
 |
 |      Iterating over G.adj behaves like a dict. Useful idioms include
 |      `for nbr, datadict in G.adj[n].items():`.
 |
 |      The neighbor information is also provided by subscripting the graph.
 |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
 |
 |      For directed graphs, `G.adj` holds outgoing (successor) info.
 |
 |  adjacency(self)
 |      Returns an iterator over (node, adjacency dict) tuples for all nodes.
 |
 |      For directed graphs, only outgoing neighbors/adjacencies are included.
 |
 |      Returns
 |      -------
 |      adj_iter : iterator
 |         An iterator over (node, adjacency dictionary) for all nodes in
 |         the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> [(n, nbrdict) for n, nbrdict in G.adjacency()]
 |      [(0, {1: {}}), (1, {0: {}, 2: {}}), (2, {1: {}, 3: {}}), (3, {2: {}})]
 |
 |  clear(self)
 |      Remove all nodes and edges from the graph.
 |
 |      This also removes the name, and all graph, node, and edge attributes.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.clear()
 |      >>> list(G.nodes)
 |      []
 |      >>> list(G.edges)
 |      []
 |
 |  clear_edges(self)
 |      Remove all edges from the graph without altering nodes.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.clear_edges()
 |      >>> list(G.nodes)
 |      [0, 1, 2, 3]
 |      >>> list(G.edges)
 |      []
 |
 |  copy(self, as_view=False)
 |      Returns a copy of the graph.
 |
 |      The copy method by default returns an independent shallow copy
 |      of the graph and attributes. That is, if an attribute is a
 |      container, that container is shared by the original an the copy.
 |      Use Python's `copy.deepcopy` for new containers.
 |
 |      If `as_view` is True then a view is returned instead of a copy.
 |
 |      Notes
 |      -----
 |      All copies reproduce the graph structure, but data attributes
 |      may be handled in different ways. There are four types of copies
 |      of a graph that people might want.
 |
 |      Deepcopy -- A "deepcopy" copies the graph structure as well as
 |      all data attributes and any objects they might contain.
 |      The entire graph object is new so that changes in the copy
 |      do not affect the original object. (see Python's copy.deepcopy)
 |
 |      Data Reference (Shallow) -- For a shallow copy the graph structure
 |      is copied but the edge, node and graph attribute dicts are
 |      references to those in the original graph. This saves
 |      time and memory but could cause confusion if you change an attribute
 |      in one graph and it changes the attribute in the other.
 |      NetworkX does not provide this level of shallow copy.
 |
 |      Independent Shallow -- This copy creates new independent attribute
 |      dicts and then does a shallow copy of the attributes. That is, any
 |      attributes that are containers are shared between the new graph
 |      and the original. This is exactly what `dict.copy()` provides.
 |      You can obtain this style copy using:
 |
 |          >>> G = nx.path_graph(5)
 |          >>> H = G.copy()
 |          >>> H = G.copy(as_view=False)
 |          >>> H = nx.Graph(G)
 |          >>> H = G.__class__(G)
 |
 |      Fresh Data -- For fresh data, the graph structure is copied while
 |      new empty data attribute dicts are created. The resulting graph
 |      is independent of the original and it has no edge, node or graph
 |      attributes. Fresh copies are not enabled. Instead use:
 |
 |          >>> H = G.__class__()
 |          >>> H.add_nodes_from(G)
 |          >>> H.add_edges_from(G.edges)
 |
 |      View -- Inspired by dict-views, graph-views act like read-only
 |      versions of the original graph, providing a copy of the original
 |      structure without requiring any memory for copying the information.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Parameters
 |      ----------
 |      as_view : bool, optional (default=False)
 |          If True, the returned graph-view provides a read-only view
 |          of the original graph without actually copying any data.
 |
 |      Returns
 |      -------
 |      G : Graph
 |          A copy of the graph.
 |
 |      See Also
 |      --------
 |      to_directed: return a directed copy of the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> H = G.copy()
 |
 |  degree = <functools.cached_property object>
 |      A DegreeView for the Graph as G.degree or G.degree().
 |
 |      The node degree is the number of edges adjacent to the node.
 |      The weighted node degree is the sum of the edge weights for
 |      edges incident to that node.
 |
 |      This object provides an iterator for (node, degree) as well as
 |      lookup for the degree for a single node.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      weight : string or None, optional (default=None)
 |         The name of an edge attribute that holds the numerical value used
 |         as a weight.  If None, then each edge has weight 1.
 |         The degree is the sum of the edge weights adjacent to the node.
 |
 |      Returns
 |      -------
 |      DegreeView or int
 |          If multiple nodes are requested (the default), returns a `DegreeView`
 |          mapping nodes to their degree.
 |          If a single node is requested, returns the degree of the node as an integer.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.degree[0]  # node 0 has degree 1
 |      1
 |      >>> list(G.degree([0, 1, 2]))
 |      [(0, 1), (1, 2), (2, 2)]
 |
 |  edge_subgraph(self, edges)
 |      Returns the subgraph induced by the specified edges.
 |
 |      The induced subgraph contains each edge in `edges` and each
 |      node incident to any one of those edges.
 |
 |      Parameters
 |      ----------
 |      edges : iterable
 |          An iterable of edges in this graph.
 |
 |      Returns
 |      -------
 |      G : Graph
 |          An edge-induced subgraph of this graph with the same edge
 |          attributes.
 |
 |      Notes
 |      -----
 |      The graph, edge, and node attributes in the returned subgraph
 |      view are references to the corresponding attributes in the original
 |      graph. The view is read-only.
 |
 |      To create a full graph version of the subgraph with its own copy
 |      of the edge or node attributes, use::
 |
 |          G.edge_subgraph(edges).copy()
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(5)
 |      >>> H = G.edge_subgraph([(0, 1), (3, 4)])
 |      >>> list(H.nodes)
 |      [0, 1, 3, 4]
 |      >>> list(H.edges)
 |      [(0, 1), (3, 4)]
 |
 |  edges = <functools.cached_property object>
 |      An EdgeView of the Graph as G.edges or G.edges().
 |
 |      edges(self, nbunch=None, data=False, default=None)
 |
 |      The EdgeView provides set-like operations on the edge-tuples
 |      as well as edge attribute lookup. When called, it also provides
 |      an EdgeDataView object which allows control of access to edge
 |      attributes (but does not provide set-like operations).
 |      Hence, `G.edges[u, v]['color']` provides the value of the color
 |      attribute for edge `(u, v)` while
 |      `for (u, v, c) in G.edges.data('color', default='red'):`
 |      iterates through all the edges yielding the color attribute
 |      with default `'red'` if no color attribute exists.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges from these nodes.
 |      data : string or bool, optional (default=False)
 |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
 |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
 |          If False, return 2-tuple (u, v).
 |      default : value, optional (default=None)
 |          Value used for edges that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      edges : EdgeView
 |          A view of edge attributes, usually it iterates over (u, v)
 |          or (u, v, d) tuples of edges, but can also be used for
 |          attribute lookup as `edges[u, v]['foo']`.
 |
 |      Notes
 |      -----
 |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
 |      For directed graphs this returns the out-edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or MultiGraph, etc
 |      >>> G.add_edge(2, 3, weight=5)
 |      >>> [e for e in G.edges]
 |      [(0, 1), (1, 2), (2, 3)]
 |      >>> G.edges.data()  # default data is {} (empty dict)
 |      EdgeDataView([(0, 1, {}), (1, 2, {}), (2, 3, {'weight': 5})])
 |      >>> G.edges.data("weight", default=1)
 |      EdgeDataView([(0, 1, 1), (1, 2, 1), (2, 3, 5)])
 |      >>> G.edges([0, 3])  # only edges from these nodes
 |      EdgeDataView([(0, 1), (3, 2)])
 |      >>> G.edges(0)  # only edges from node 0
 |      EdgeDataView([(0, 1)])
 |
 |  get_edge_data(self, u, v, default=None)
 |      Returns the attribute dictionary associated with edge (u, v).
 |
 |      This is identical to `G[u][v]` except the default is returned
 |      instead of an exception if the edge doesn't exist.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |      default:  any Python object (default=None)
 |          Value to return if the edge (u, v) is not found.
 |
 |      Returns
 |      -------
 |      edge_dict : dictionary
 |          The edge attribute dictionary.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G[0][1]
 |      {}
 |
 |      Warning: Assigning to `G[u][v]` is not permitted.
 |      But it is safe to assign attributes `G[u][v]['foo']`
 |
 |      >>> G[0][1]["weight"] = 7
 |      >>> G[0][1]["weight"]
 |      7
 |      >>> G[1][0]["weight"]
 |      7
 |
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.get_edge_data(0, 1)  # default edge data is {}
 |      {}
 |      >>> e = (0, 1)
 |      >>> G.get_edge_data(*e)  # tuple form
 |      {}
 |      >>> G.get_edge_data("a", "b", default=0)  # edge not in graph, return 0
 |      0
 |
 |  has_edge(self, u, v)
 |      Returns True if the edge (u, v) is in the graph.
 |
 |      This is the same as `v in G[u]` without KeyError exceptions.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |          Nodes can be, for example, strings or numbers.
 |          Nodes must be hashable (and not None) Python objects.
 |
 |      Returns
 |      -------
 |      edge_ind : bool
 |          True if edge is in the graph, False otherwise.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.has_edge(0, 1)  # using two nodes
 |      True
 |      >>> e = (0, 1)
 |      >>> G.has_edge(*e)  #  e is a 2-tuple (u, v)
 |      True
 |      >>> e = (0, 1, {"weight": 7})
 |      >>> G.has_edge(*e[:2])  # e is a 3-tuple (u, v, data_dictionary)
 |      True
 |
 |      The following syntax are equivalent:
 |
 |      >>> G.has_edge(0, 1)
 |      True
 |      >>> 1 in G[0]  # though this gives KeyError if 0 not in G
 |      True
 |
 |  has_node(self, n)
 |      Returns True if the graph contains the node n.
 |
 |      Identical to `n in G`
 |
 |      Parameters
 |      ----------
 |      n : node
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.has_node(0)
 |      True
 |
 |      It is more readable and simpler to use
 |
 |      >>> 0 in G
 |      True
 |
 |  is_directed(self)
 |      Returns True if graph is directed, False otherwise.
 |
 |  is_multigraph(self)
 |      Returns True if graph is a multigraph, False otherwise.
 |
 |  nbunch_iter(self, nbunch=None)
 |      Returns an iterator over nodes contained in nbunch that are
 |      also in the graph.
 |
 |      The nodes in nbunch are checked for membership in the graph
 |      and if not are silently ignored.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      Returns
 |      -------
 |      niter : iterator
 |          An iterator over nodes in nbunch that are also in the graph.
 |          If nbunch is None, iterate over all nodes in the graph.
 |
 |      Raises
 |      ------
 |      NetworkXError
 |          If nbunch is not a node or sequence of nodes.
 |          If a node in nbunch is not hashable.
 |
 |      See Also
 |      --------
 |      Graph.__iter__
 |
 |      Notes
 |      -----
 |      When nbunch is an iterator, the returned iterator yields values
 |      directly from nbunch, becoming exhausted when nbunch is exhausted.
 |
 |      To test whether nbunch is a single node, one can use
 |      "if nbunch in self:", even after processing with this routine.
 |
 |      If nbunch is not a node or a (possibly empty) sequence/iterator
 |      or None, a :exc:`NetworkXError` is raised.  Also, if any object in
 |      nbunch is not hashable, a :exc:`NetworkXError` is raised.
 |
 |  neighbors(self, n)
 |      Returns an iterator over all neighbors of node n.
 |
 |      This is identical to `iter(G[n])`
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Returns
 |      -------
 |      neighbors : iterator
 |          An iterator over all neighbors of node n
 |
 |      Raises
 |      ------
 |      NetworkXError
 |          If the node n is not in the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> [n for n in G.neighbors(0)]
 |      [1]
 |
 |      Notes
 |      -----
 |      Alternate ways to access the neighbors are ``G.adj[n]`` or ``G[n]``:
 |
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_edge("a", "b", weight=7)
 |      >>> G["a"]
 |      AtlasView({'b': {'weight': 7}})
 |      >>> G = nx.path_graph(4)
 |      >>> [n for n in G[0]]
 |      [1]
 |
 |  nodes = <functools.cached_property object>
 |      A NodeView of the Graph as G.nodes or G.nodes().
 |
 |      Can be used as `G.nodes` for data lookup and for set-like operations.
 |      Can also be used as `G.nodes(data='color', default=None)` to return a
 |      NodeDataView which reports specific node data but no set operations.
 |      It presents a dict-like interface as well with `G.nodes.items()`
 |      iterating over `(node, nodedata)` 2-tuples and `G.nodes[3]['foo']`
 |      providing the value of the `foo` attribute for node `3`. In addition,
 |      a view `G.nodes.data('foo')` provides a dict-like interface to the
 |      `foo` attribute of each node. `G.nodes.data('foo', default=1)`
 |      provides a default for nodes that do not have attribute `foo`.
 |
 |      Parameters
 |      ----------
 |      data : string or bool, optional (default=False)
 |          The node attribute returned in 2-tuple (n, ddict[data]).
 |          If True, return entire node attribute dict as (n, ddict).
 |          If False, return just the nodes n.
 |
 |      default : value, optional (default=None)
 |          Value used for nodes that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      NodeView
 |          Allows set-like operations over the nodes as well as node
 |          attribute dict lookup and calling to get a NodeDataView.
 |          A NodeDataView iterates over `(n, data)` and has no set operations.
 |          A NodeView iterates over `n` and includes set operations.
 |
 |          When called, if data is False, an iterator over nodes.
 |          Otherwise an iterator of 2-tuples (node, attribute value)
 |          where the attribute is specified in `data`.
 |          If data is True then the attribute becomes the
 |          entire data dictionary.
 |
 |      Notes
 |      -----
 |      If your node data is not needed, it is simpler and equivalent
 |      to use the expression ``for n in G``, or ``list(G)``.
 |
 |      Examples
 |      --------
 |      There are two simple ways of getting a list of all nodes in the graph:
 |
 |      >>> G = nx.path_graph(3)
 |      >>> list(G.nodes)
 |      [0, 1, 2]
 |      >>> list(G)
 |      [0, 1, 2]
 |
 |      To get the node data along with the nodes:
 |
 |      >>> G.add_node(1, time="5pm")
 |      >>> G.nodes[0]["foo"] = "bar"
 |      >>> list(G.nodes(data=True))
 |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
 |      >>> list(G.nodes.data())
 |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
 |
 |      >>> list(G.nodes(data="foo"))
 |      [(0, 'bar'), (1, None), (2, None)]
 |      >>> list(G.nodes.data("foo"))
 |      [(0, 'bar'), (1, None), (2, None)]
 |
 |      >>> list(G.nodes(data="time"))
 |      [(0, None), (1, '5pm'), (2, None)]
 |      >>> list(G.nodes.data("time"))
 |      [(0, None), (1, '5pm'), (2, None)]
 |
 |      >>> list(G.nodes(data="time", default="Not Available"))
 |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
 |      >>> list(G.nodes.data("time", default="Not Available"))
 |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
 |
 |      If some of your nodes have an attribute and the rest are assumed
 |      to have a default attribute value you can create a dictionary
 |      from node/attribute pairs using the `default` keyword argument
 |      to guarantee the value is never None::
 |
 |          >>> G = nx.Graph()
 |          >>> G.add_node(0)
 |          >>> G.add_node(1, weight=2)
 |          >>> G.add_node(2, weight=3)
 |          >>> dict(G.nodes(data="weight", default=1))
 |          {0: 1, 1: 2, 2: 3}
 |
 |  number_of_edges(self, u=None, v=None)
 |      Returns the number of edges between two nodes.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes, optional (default=all edges)
 |          If u and v are specified, return the number of edges between
 |          u and v. Otherwise return the total number of all edges.
 |
 |      Returns
 |      -------
 |      nedges : int
 |          The number of edges in the graph.  If nodes `u` and `v` are
 |          specified return the number of edges between those nodes. If
 |          the graph is directed, this only returns the number of edges
 |          from `u` to `v`.
 |
 |      See Also
 |      --------
 |      size
 |
 |      Examples
 |      --------
 |      For undirected graphs, this method counts the total number of
 |      edges in the graph:
 |
 |      >>> G = nx.path_graph(4)
 |      >>> G.number_of_edges()
 |      3
 |
 |      If you specify two nodes, this counts the total number of edges
 |      joining the two nodes:
 |
 |      >>> G.number_of_edges(0, 1)
 |      1
 |
 |      For directed graphs, this method can count the total number of
 |      directed edges from `u` to `v`:
 |
 |      >>> G = nx.DiGraph()
 |      >>> G.add_edge(0, 1)
 |      >>> G.add_edge(1, 0)
 |      >>> G.number_of_edges(0, 1)
 |      1
 |
 |  number_of_nodes(self)
 |      Returns the number of nodes in the graph.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      order: identical method
 |      __len__: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.number_of_nodes()
 |      3
 |
 |  order(self)
 |      Returns the number of nodes in the graph.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      number_of_nodes: identical method
 |      __len__: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.order()
 |      3
 |
 |  remove_edge(self, u, v)
 |      Remove the edge between u and v.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |          Remove the edge between nodes u and v.
 |
 |      Raises
 |      ------
 |      NetworkXError
 |          If there is not an edge between u and v.
 |
 |      See Also
 |      --------
 |      remove_edges_from : remove a collection of edges
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, etc
 |      >>> G.remove_edge(0, 1)
 |      >>> e = (1, 2)
 |      >>> G.remove_edge(*e)  # unpacks e from an edge tuple
 |      >>> e = (2, 3, {"weight": 7})  # an edge with attribute data
 |      >>> G.remove_edge(*e[:2])  # select first part of edge tuple
 |
 |  remove_edges_from(self, ebunch)
 |      Remove all edges specified in ebunch.
 |
 |      Parameters
 |      ----------
 |      ebunch: list or container of edge tuples
 |          Each edge given in the list or container will be removed
 |          from the graph. The edges can be:
 |
 |              - 2-tuples (u, v) edge between u and v.
 |              - 3-tuples (u, v, k) where k is ignored.
 |
 |      See Also
 |      --------
 |      remove_edge : remove a single edge
 |
 |      Notes
 |      -----
 |      Will fail silently if an edge in ebunch is not in the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> ebunch = [(1, 2), (2, 3)]
 |      >>> G.remove_edges_from(ebunch)
 |
 |  remove_node(self, n)
 |      Remove node n.
 |
 |      Removes the node n and all adjacent edges.
 |      Attempting to remove a nonexistent node will raise an exception.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Raises
 |      ------
 |      NetworkXError
 |         If n is not in the graph.
 |
 |      See Also
 |      --------
 |      remove_nodes_from
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> list(G.edges)
 |      [(0, 1), (1, 2)]
 |      >>> G.remove_node(1)
 |      >>> list(G.edges)
 |      []
 |
 |  remove_nodes_from(self, nodes)
 |      Remove multiple nodes.
 |
 |      Parameters
 |      ----------
 |      nodes : iterable container
 |          A container of nodes (list, dict, set, etc.).  If a node
 |          in the container is not in the graph it is silently
 |          ignored.
 |
 |      See Also
 |      --------
 |      remove_node
 |
 |      Notes
 |      -----
 |      When removing nodes from an iterator over the graph you are changing,
 |      a `RuntimeError` will be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
 |      object to `G.remove_nodes_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> e = list(G.nodes)
 |      >>> e
 |      [0, 1, 2]
 |      >>> G.remove_nodes_from(e)
 |      >>> list(G.nodes)
 |      []
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.Graph([(0, 1), (1, 2), (3, 4)])
 |      >>> # this command will fail, as the graph's dict is modified during iteration
 |      >>> # G.remove_nodes_from(n for n in G.nodes if n < 2)
 |      >>> # this command will work, since the dictionary underlying graph is not modified
 |      >>> G.remove_nodes_from(list(n for n in G.nodes if n < 2))
 |
 |  size(self, weight=None)
 |      Returns the number of edges or total of all edge weights.
 |
 |      Parameters
 |      ----------
 |      weight : string or None, optional (default=None)
 |          The edge attribute that holds the numerical value used
 |          as a weight. If None, then each edge has weight 1.
 |
 |      Returns
 |      -------
 |      size : numeric
 |          The number of edges or
 |          (if weight keyword is provided) the total weight sum.
 |
 |          If weight is None, returns an int. Otherwise a float
 |          (or more general numeric if the weights are more general).
 |
 |      See Also
 |      --------
 |      number_of_edges
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.size()
 |      3
 |
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_edge("a", "b", weight=2)
 |      >>> G.add_edge("b", "c", weight=4)
 |      >>> G.size()
 |      2
 |      >>> G.size(weight="weight")
 |      6.0
 |
 |  subgraph(self, nodes)
 |      Returns a SubGraph view of the subgraph induced on `nodes`.
 |
 |      The induced subgraph of the graph contains the nodes in `nodes`
 |      and the edges between those nodes.
 |
 |      Parameters
 |      ----------
 |      nodes : list, iterable
 |          A container of nodes which will be iterated through once.
 |
 |      Returns
 |      -------
 |      G : SubGraph View
 |          A subgraph view of the graph. The graph structure cannot be
 |          changed but node/edge attributes can and are shared with the
 |          original graph.
 |
 |      Notes
 |      -----
 |      The graph, edge and node attributes are shared with the original graph.
 |      Changes to the graph structure is ruled out by the view, but changes
 |      to attributes are reflected in the original graph.
 |
 |      To create a subgraph with its own copy of the edge/node attributes use:
 |      G.subgraph(nodes).copy()
 |
 |      For an inplace reduction of a graph to a subgraph you can remove nodes:
 |      G.remove_nodes_from([n for n in G if n not in set(nodes)])
 |
 |      Subgraph views are sometimes NOT what you want. In most cases where
 |      you want to do more than simply look at the induced edges, it makes
 |      more sense to just create the subgraph as its own graph with code like:
 |
 |      ::
 |
 |          # Create a subgraph SG based on a (possibly multigraph) G
 |          SG = G.__class__()
 |          SG.add_nodes_from((n, G.nodes[n]) for n in largest_wcc)
 |          if SG.is_multigraph():
 |              SG.add_edges_from(
 |                  (n, nbr, key, d)
 |                  for n, nbrs in G.adj.items()
 |                  if n in largest_wcc
 |                  for nbr, keydict in nbrs.items()
 |                  if nbr in largest_wcc
 |                  for key, d in keydict.items()
 |              )
 |          else:
 |              SG.add_edges_from(
 |                  (n, nbr, d)
 |                  for n, nbrs in G.adj.items()
 |                  if n in largest_wcc
 |                  for nbr, d in nbrs.items()
 |                  if nbr in largest_wcc
 |              )
 |          SG.graph.update(G.graph)
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> H = G.subgraph([0, 1, 2])
 |      >>> list(H.edges)
 |      [(0, 1), (1, 2)]
 |
 |  to_directed(self, as_view=False)
 |      Returns a directed representation of the graph.
 |
 |      Returns
 |      -------
 |      G : DiGraph
 |          A directed graph with the same name, same nodes, and with
 |          each edge (u, v, data) replaced by two directed edges
 |          (u, v, data) and (v, u, data).
 |
 |      Notes
 |      -----
 |      This returns a "deepcopy" of the edge, node, and
 |      graph attributes which attempts to completely copy
 |      all of the data and references.
 |
 |      This is in contrast to the similar D=DiGraph(G) which returns a
 |      shallow copy of the data.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Warning: If you have subclassed Graph to use dict-like objects
 |      in the data structure, those changes do not transfer to the
 |      DiGraph created by this method.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or MultiGraph, etc
 |      >>> G.add_edge(0, 1)
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1), (1, 0)]
 |
 |      If already directed, return a (deep) copy
 |
 |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
 |      >>> G.add_edge(0, 1)
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1)]
 |
 |  to_directed_class(self)
 |      Returns the class to use for empty directed copies.
 |
 |      If you subclass the base classes, use this to designate
 |      what directed class to use for `to_directed()` copies.
 |
 |  to_undirected(self, as_view=False)
 |      Returns an undirected copy of the graph.
 |
 |      Parameters
 |      ----------
 |      as_view : bool (optional, default=False)
 |        If True return a view of the original undirected graph.
 |
 |      Returns
 |      -------
 |      G : Graph/MultiGraph
 |          A deepcopy of the graph.
 |
 |      See Also
 |      --------
 |      Graph, copy, add_edge, add_edges_from
 |
 |      Notes
 |      -----
 |      This returns a "deepcopy" of the edge, node, and
 |      graph attributes which attempts to completely copy
 |      all of the data and references.
 |
 |      This is in contrast to the similar `G = nx.DiGraph(D)` which returns a
 |      shallow copy of the data.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Warning: If you have subclassed DiGraph to use dict-like objects
 |      in the data structure, those changes do not transfer to the
 |      Graph created by this method.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(2)  # or MultiGraph, etc
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1), (1, 0)]
 |      >>> G2 = H.to_undirected()
 |      >>> list(G2.edges)
 |      [(0, 1)]
 |
 |  to_undirected_class(self)
 |      Returns the class to use for empty undirected copies.
 |
 |      If you subclass the base classes, use this to designate
 |      what directed class to use for `to_directed()` copies.
 |
 |  update(self, edges=None, nodes=None)
 |      Update the graph using nodes/edges/graphs as input.
 |
 |      Like dict.update, this method takes a graph as input, adding the
 |      graph's nodes and edges to this graph. It can also take two inputs:
 |      edges and nodes. Finally it can take either edges or nodes.
 |      To specify only nodes the keyword `nodes` must be used.
 |
 |      The collections of edges and nodes are treated similarly to
 |      the add_edges_from/add_nodes_from methods. When iterated, they
 |      should yield 2-tuples (u, v) or 3-tuples (u, v, datadict).
 |
 |      Parameters
 |      ----------
 |      edges : Graph object, collection of edges, or None
 |          The first parameter can be a graph or some edges. If it has
 |          attributes `nodes` and `edges`, then it is taken to be a
 |          Graph-like object and those attributes are used as collections
 |          of nodes and edges to be added to the graph.
 |          If the first parameter does not have those attributes, it is
 |          treated as a collection of edges and added to the graph.
 |          If the first argument is None, no edges are added.
 |      nodes : collection of nodes, or None
 |          The second parameter is treated as a collection of nodes
 |          to be added to the graph unless it is None.
 |          If `edges is None` and `nodes is None` an exception is raised.
 |          If the first parameter is a Graph, then `nodes` is ignored.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(5)
 |      >>> G.update(nx.complete_graph(range(4, 10)))
 |      >>> from itertools import combinations
 |      >>> edges = (
 |      ...     (u, v, {"power": u * v})
 |      ...     for u, v in combinations(range(10, 20), 2)
 |      ...     if u * v < 225
 |      ... )
 |      >>> nodes = [1000]  # for singleton, use a container
 |      >>> G.update(edges, nodes)
 |
 |      Notes
 |      -----
 |      It you want to update the graph using an adjacency structure
 |      it is straightforward to obtain the edges/nodes from adjacency.
 |      The following examples provide common cases, your adjacency may
 |      be slightly different and require tweaks of these examples::
 |
 |      >>> # dict-of-set/list/tuple
 |      >>> adj = {1: {2, 3}, 2: {1, 3}, 3: {1, 2}}
 |      >>> e = [(u, v) for u, nbrs in adj.items() for v in nbrs]
 |      >>> G.update(edges=e, nodes=adj)
 |
 |      >>> DG = nx.DiGraph()
 |      >>> # dict-of-dict-of-attribute
 |      >>> adj = {1: {2: 1.3, 3: 0.7}, 2: {1: 1.4}, 3: {1: 0.7}}
 |      >>> e = [
 |      ...     (u, v, {"weight": d})
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, d in nbrs.items()
 |      ... ]
 |      >>> DG.update(edges=e, nodes=adj)
 |
 |      >>> # dict-of-dict-of-dict
 |      >>> adj = {1: {2: {"weight": 1.3}, 3: {"color": 0.7, "weight": 1.2}}}
 |      >>> e = [
 |      ...     (u, v, {"weight": d})
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, d in nbrs.items()
 |      ... ]
 |      >>> DG.update(edges=e, nodes=adj)
 |
 |      >>> # predecessor adjacency (dict-of-set)
 |      >>> pred = {1: {2, 3}, 2: {3}, 3: {3}}
 |      >>> e = [(v, u) for u, nbrs in pred.items() for v in nbrs]
 |
 |      >>> # MultiGraph dict-of-dict-of-dict-of-attribute
 |      >>> MDG = nx.MultiDiGraph()
 |      >>> adj = {
 |      ...     1: {2: {0: {"weight": 1.3}, 1: {"weight": 1.2}}},
 |      ...     3: {2: {0: {"weight": 0.7}}},
 |      ... }
 |      >>> e = [
 |      ...     (u, v, ekey, d)
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, keydict in nbrs.items()
 |      ...     for ekey, d in keydict.items()
 |      ... ]
 |      >>> MDG.update(edges=e)
 |
 |      See Also
 |      --------
 |      add_edges_from: add multiple edges to a graph
 |      add_nodes_from: add multiple nodes to a graph
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors defined here:
 |
 |  __dict__
 |      dictionary for instance variables
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  name
 |      String identifier of the graph.
 |
 |      This graph attribute appears in the attribute dict G.graph
 |      keyed by the string `"name"`. as well as an attribute (technically
 |      a property) `G.name`. This is entirely user controlled.
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes defined here:
 |
 |  __networkx_backend__ = 'networkx'
 |
 |  adjlist_inner_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  adjlist_outer_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  edge_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  graph_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  node_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  node_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
networkx.GraphMLReader
Python Library Documentation: class GraphMLReader in module networkx.readwrite.graphml

class GraphMLReader(GraphML)
 |  GraphMLReader(node_type=<class 'str'>, edge_key_type=<class 'int'>, force_multigraph=False)
 |
 |  Read a GraphML document.  Produces NetworkX graph objects.
 |
 |  Method resolution order:
 |      GraphMLReader
 |      GraphML
 |      builtins.object
 |
 |  Methods defined here:
 |
 |  __call__(self, path=None, string=None)
 |      Call self as a function.
 |
 |  __init__(self, node_type=<class 'str'>, edge_key_type=<class 'int'>, force_multigraph=False)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  add_edge(self, G, edge_element, graphml_keys)
 |      Add an edge to the graph.
 |
 |  add_node(self, G, node_xml, graphml_keys, defaults)
 |      Add a node to the graph.
 |
 |  decode_data_elements(self, graphml_keys, obj_xml)
 |      Use the key information to decode the data XML if present.
 |
 |  find_graphml_keys(self, graph_element)
 |      Extracts all the keys and key defaults from the xml.
 |
 |  make_graph(self, graph_xml, graphml_keys, defaults, G=None)
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from GraphML:
 |
 |  construct_types(self)
 |
 |  get_xml_type(self, key)
 |      Wrapper around the xml_type dict that raises a more informative
 |      exception message when a user attempts to use data of a type not
 |      supported by GraphML.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from GraphML:
 |
 |  __dict__
 |      dictionary for instance variables
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes inherited from GraphML:
 |
 |  NS_GRAPHML = 'http://graphml.graphdrawing.org/xmlns'
 |
 |  NS_XSI = 'http://www.w3.org/2001/XMLSchema-instance'
 |
 |  NS_Y = 'http://www.yworks.com/xml/graphml'
 |
 |  SCHEMALOCATION = 'http://graphml.graphdrawing.org/xmlns http://graphml...
 |
 |  convert_bool = {'true': True, 'false': False, '0': False, 0: False, '1...
networkx.GraphMLWriter
Python Library Documentation: class GraphMLWriter in module networkx.readwrite.graphml

class GraphMLWriter(GraphML)
 |  GraphMLWriter(graph=None, encoding='utf-8', prettyprint=True, infer_numeric_types=False, named_key_ids=False, edge_id_from_attribute=None)
 |
 |  Method resolution order:
 |      GraphMLWriter
 |      GraphML
 |      builtins.object
 |
 |  Methods defined here:
 |
 |  __init__(self, graph=None, encoding='utf-8', prettyprint=True, infer_numeric_types=False, named_key_ids=False, edge_id_from_attribute=None)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  __str__(self)
 |      Return str(self).
 |
 |  add_attributes(self, scope, xml_obj, data, default)
 |      Appends attribute data to edges or nodes, and stores type information
 |      to be added later. See add_graph_element.
 |
 |  add_data(self, name, element_type, value, scope='all', default=None)
 |      Make a data element for an edge or a node. Keep a log of the
 |      type in the keys table.
 |
 |  add_edges(self, G, graph_element)
 |
 |  add_graph_element(self, G)
 |      Serialize graph G in GraphML to the stream.
 |
 |  add_graphs(self, graph_list)
 |      Add many graphs to this GraphML document.
 |
 |  add_nodes(self, G, graph_element)
 |
 |  attr_type(self, name, scope, value)
 |      Infer the attribute type of data named name. Currently this only
 |      supports inference of numeric types.
 |
 |      If self.infer_numeric_types is false, type is used. Otherwise, pick the
 |      most general of types found across all values with name and scope. This
 |      means edges with data named 'weight' are treated separately from nodes
 |      with data named 'weight'.
 |
 |  dump(self, stream)
 |
 |  get_key(self, name, attr_type, scope, default)
 |
 |  indent(self, elem, level=0)
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from GraphML:
 |
 |  construct_types(self)
 |
 |  get_xml_type(self, key)
 |      Wrapper around the xml_type dict that raises a more informative
 |      exception message when a user attempts to use data of a type not
 |      supported by GraphML.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from GraphML:
 |
 |  __dict__
 |      dictionary for instance variables
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes inherited from GraphML:
 |
 |  NS_GRAPHML = 'http://graphml.graphdrawing.org/xmlns'
 |
 |  NS_XSI = 'http://www.w3.org/2001/XMLSchema-instance'
 |
 |  NS_Y = 'http://www.yworks.com/xml/graphml'
 |
 |  SCHEMALOCATION = 'http://graphml.graphdrawing.org/xmlns http://graphml...
 |
 |  convert_bool = {'true': True, 'false': False, '0': False, 0: False, '1...
networkx.HasACycle
Python Library Documentation: class HasACycle in module networkx.exception

class HasACycle(NetworkXException)
 |  Raised if a graph has a cycle when an algorithm expects that it
 |  will have no cycles.
 |
 |  Method resolution order:
 |      HasACycle
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.LCF_graph
Python Library Documentation: function LCF_graph in module networkx.generators.small

LCF_graph(n, shift_list, repeats, create_using=None, *, backend=None, **backend_kwargs)
    Return the cubic graph specified in LCF notation.

    LCF (Lederberg-Coxeter-Fruchte) notation[1]_ is a compressed
    notation used in the generation of various cubic Hamiltonian
    graphs of high symmetry. See, for example, `dodecahedral_graph`,
    `desargues_graph`, `heawood_graph` and `pappus_graph`.

    Nodes are drawn from ``range(n)``. Each node ``n_i`` is connected with
    node ``n_i + shift % n`` where ``shift`` is given by cycling through
    the input `shift_list` `repeat` s times.

    Parameters
    ----------
    n : int
       The starting graph is the `n`-cycle with nodes ``0, ..., n-1``.
       The null graph is returned if `n` < 1.

    shift_list : list
       A list of integer shifts mod `n`, ``[s1, s2, .., sk]``

    repeats : int
       Integer specifying the number of times that shifts in `shift_list`
       are successively applied to each current node in the n-cycle
       to generate an edge between ``n_current`` and ``n_current + shift mod n``.

    Returns
    -------
    G : Graph
       A graph instance created from the specified LCF notation.

    Examples
    --------
    The utility graph $K_{3,3}$

    >>> G = nx.LCF_graph(6, [3, -3], 3)
    >>> G.edges()
    EdgeView([(0, 1), (0, 5), (0, 3), (1, 2), (1, 4), (2, 3), (2, 5), (3, 4), (4, 5)])

    The Heawood graph:

    >>> G = nx.LCF_graph(14, [5, -5], 7)
    >>> nx.is_isomorphic(G, nx.heawood_graph())
    True

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/LCF_notation
networkx.LFR_benchmark_graph
Python Library Documentation: function LFR_benchmark_graph in module networkx.generators.community

LFR_benchmark_graph(n, tau1, tau2, mu, average_degree=None, min_degree=None, max_degree=None, min_community=None, max_community=None, tol=1e-07, max_iters=500, seed=None, *, backend=None, **backend_kwargs)
    Returns the LFR benchmark graph.

    This algorithm proceeds as follows:

    1) Find a degree sequence with a power law distribution, and minimum
       value ``min_degree``, which has approximate average degree
       ``average_degree``. This is accomplished by either

       a) specifying ``min_degree`` and not ``average_degree``,
       b) specifying ``average_degree`` and not ``min_degree``, in which
          case a suitable minimum degree will be found.

       ``max_degree`` can also be specified, otherwise it will be set to
       ``n``. Each node *u* will have $\mu \mathrm{deg}(u)$ edges
       joining it to nodes in communities other than its own and $(1 -
       \mu) \mathrm{deg}(u)$ edges joining it to nodes in its own
       community.
    2) Generate community sizes according to a power law distribution
       with exponent ``tau2``. If ``min_community`` and
       ``max_community`` are not specified they will be selected to be
       ``min_degree`` and ``max_degree``, respectively.  Community sizes
       are generated until the sum of their sizes equals ``n``.
    3) Each node will be randomly assigned a community with the
       condition that the community is large enough for the node's
       intra-community degree, $(1 - \mu) \mathrm{deg}(u)$ as
       described in step 2. If a community grows too large, a random node
       will be selected for reassignment to a new community, until all
       nodes have been assigned a community.
    4) Each node *u* then adds $(1 - \mu) \mathrm{deg}(u)$
       intra-community edges and $\mu \mathrm{deg}(u)$ inter-community
       edges.

    Parameters
    ----------
    n : int
        Number of nodes in the created graph.

    tau1 : float
        Power law exponent for the degree distribution of the created
        graph. This value must be strictly greater than one.

    tau2 : float
        Power law exponent for the community size distribution in the
        created graph. This value must be strictly greater than one.

    mu : float
        Fraction of inter-community edges incident to each node. This
        value must be in the interval [0, 1].

    average_degree : float
        Desired average degree of nodes in the created graph. This value
        must be in the interval [0, *n*]. Exactly one of this and
        ``min_degree`` must be specified, otherwise a
        :exc:`NetworkXError` is raised.

    min_degree : int
        Minimum degree of nodes in the created graph. This value must be
        in the interval [0, *n*]. Exactly one of this and
        ``average_degree`` must be specified, otherwise a
        :exc:`NetworkXError` is raised.

    max_degree : int
        Maximum degree of nodes in the created graph. If not specified,
        this is set to ``n``, the total number of nodes in the graph.

    min_community : int
        Minimum size of communities in the graph. If not specified, this
        is set to ``min_degree``.

    max_community : int
        Maximum size of communities in the graph. If not specified, this
        is set to ``n``, the total number of nodes in the graph.

    tol : float
        Tolerance when comparing floats, specifically when comparing
        average degree values.

    max_iters : int
        Maximum number of iterations to try to create the community sizes,
        degree distribution, and community affiliations.

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : NetworkX graph
        The LFR benchmark graph generated according to the specified
        parameters.

        Each node in the graph has a node attribute ``'community'`` that
        stores the community (that is, the set of nodes) that includes
        it.

    Raises
    ------
    NetworkXError
        If any of the parameters do not meet their upper and lower bounds:

        - ``tau1`` and ``tau2`` must be strictly greater than 1.
        - ``mu`` must be in [0, 1].
        - ``max_degree`` must be in {1, ..., *n*}.
        - ``min_community`` and ``max_community`` must be in {0, ...,
          *n*}.

        If not exactly one of ``average_degree`` and ``min_degree`` is
        specified.

        If ``min_degree`` is not specified and a suitable ``min_degree``
        cannot be found.

    ExceededMaxIterations
        If a valid degree sequence cannot be created within
        ``max_iters`` number of iterations.

        If a valid set of community sizes cannot be created within
        ``max_iters`` number of iterations.

        If a valid community assignment cannot be created within ``10 *
        n * max_iters`` number of iterations.

    Examples
    --------
    Basic usage::

        >>> from networkx.generators.community import LFR_benchmark_graph
        >>> n = 250
        >>> tau1 = 3
        >>> tau2 = 1.5
        >>> mu = 0.1
        >>> G = LFR_benchmark_graph(
        ...     n, tau1, tau2, mu, average_degree=5, min_community=20, seed=10
        ... )

    Continuing the example above, you can get the communities from the
    node attributes of the graph::

        >>> communities = {frozenset(G.nodes[v]["community"]) for v in G}

    Notes
    -----
    This algorithm differs slightly from the original way it was
    presented in [1].

    1) Rather than connecting the graph via a configuration model then
       rewiring to match the intra-community and inter-community
       degrees, we do this wiring explicitly at the end, which should be
       equivalent.
    2) The code posted on the author's website [2] calculates the random
       power law distributed variables and their average using
       continuous approximations, whereas we use the discrete
       distributions here as both degree and community size are
       discrete.

    Though the authors describe the algorithm as quite robust, testing
    during development indicates that a somewhat narrower parameter set
    is likely to successfully produce a graph. Some suggestions have
    been provided in the event of exceptions.

    References
    ----------
    .. [1] "Benchmark graphs for testing community detection algorithms",
           Andrea Lancichinetti, Santo Fortunato, and Filippo Radicchi,
           Phys. Rev. E 78, 046110 2008
    .. [2] https://www.santofortunato.net/resources
networkx.MultiDiGraph
Python Library Documentation: class MultiDiGraph in module networkx.classes.multidigraph

class MultiDiGraph(networkx.classes.multigraph.MultiGraph, networkx.classes.digraph.DiGraph)
 |  MultiDiGraph(incoming_graph_data=None, multigraph_input=None, **attr)
 |
 |  A directed graph class that can store multiedges.
 |
 |  Multiedges are multiple edges between two nodes.  Each edge
 |  can hold optional data or attributes.
 |
 |  A MultiDiGraph holds directed edges.  Self loops are allowed.
 |
 |  Nodes can be arbitrary (hashable) Python objects with optional
 |  key/value attributes. By convention `None` is not used as a node.
 |
 |  Edges are represented as links between nodes with optional
 |  key/value attributes.
 |
 |  Parameters
 |  ----------
 |  incoming_graph_data : input graph (optional, default: None)
 |      Data to initialize graph. If None (default) an empty
 |      graph is created.  The data can be any format that is supported
 |      by the to_networkx_graph() function, currently including edge list,
 |      dict of dicts, dict of lists, NetworkX graph, 2D NumPy array, SciPy
 |      sparse matrix, or PyGraphviz graph.
 |
 |  multigraph_input : bool or None (default None)
 |      Note: Only used when `incoming_graph_data` is a dict.
 |      If True, `incoming_graph_data` is assumed to be a
 |      dict-of-dict-of-dict-of-dict structure keyed by
 |      node to neighbor to edge keys to edge data for multi-edges.
 |      A NetworkXError is raised if this is not the case.
 |      If False, :func:`to_networkx_graph` is used to try to determine
 |      the dict's graph data structure as either a dict-of-dict-of-dict
 |      keyed by node to neighbor to edge data, or a dict-of-iterable
 |      keyed by node to neighbors.
 |      If None, the treatment for True is tried, but if it fails,
 |      the treatment for False is tried.
 |
 |  attr : keyword arguments, optional (default= no attributes)
 |      Attributes to add to graph as key=value pairs.
 |
 |  See Also
 |  --------
 |  Graph
 |  DiGraph
 |  MultiGraph
 |
 |  Examples
 |  --------
 |  Create an empty graph structure (a "null graph") with no nodes and
 |  no edges.
 |
 |  >>> G = nx.MultiDiGraph()
 |
 |  G can be grown in several ways.
 |
 |  **Nodes:**
 |
 |  Add one node at a time:
 |
 |  >>> G.add_node(1)
 |
 |  Add the nodes from any container (a list, dict, set or
 |  even the lines from a file or the nodes from another graph).
 |
 |  >>> G.add_nodes_from([2, 3])
 |  >>> G.add_nodes_from(range(100, 110))
 |  >>> H = nx.path_graph(10)
 |  >>> G.add_nodes_from(H)
 |
 |  In addition to strings and integers any hashable Python object
 |  (except None) can represent a node, e.g. a customized node object,
 |  or even another Graph.
 |
 |  >>> G.add_node(H)
 |
 |  **Edges:**
 |
 |  G can also be grown by adding edges.
 |
 |  Add one edge,
 |
 |  >>> key = G.add_edge(1, 2)
 |
 |  a list of edges,
 |
 |  >>> keys = G.add_edges_from([(1, 2), (1, 3)])
 |
 |  or a collection of edges,
 |
 |  >>> keys = G.add_edges_from(H.edges)
 |
 |  If some edges connect nodes not yet in the graph, the nodes
 |  are added automatically.  If an edge already exists, an additional
 |  edge is created and stored using a key to identify the edge.
 |  By default the key is the lowest unused integer.
 |
 |  >>> keys = G.add_edges_from([(4, 5, dict(route=282)), (4, 5, dict(route=37))])
 |  >>> G[4]
 |  AdjacencyView({5: {0: {}, 1: {'route': 282}, 2: {'route': 37}}})
 |
 |  **Attributes:**
 |
 |  Each graph, node, and edge can hold key/value attribute pairs
 |  in an associated attribute dictionary (the keys must be hashable).
 |  By default these are empty, but can be added or changed using
 |  add_edge, add_node or direct manipulation of the attribute
 |  dictionaries named graph, node and edge respectively.
 |
 |  >>> G = nx.MultiDiGraph(day="Friday")
 |  >>> G.graph
 |  {'day': 'Friday'}
 |
 |  Add node attributes using add_node(), add_nodes_from() or G.nodes
 |
 |  >>> G.add_node(1, time="5pm")
 |  >>> G.add_nodes_from([3], time="2pm")
 |  >>> G.nodes[1]
 |  {'time': '5pm'}
 |  >>> G.nodes[1]["room"] = 714
 |  >>> del G.nodes[1]["room"]  # remove attribute
 |  >>> list(G.nodes(data=True))
 |  [(1, {'time': '5pm'}), (3, {'time': '2pm'})]
 |
 |  Add edge attributes using add_edge(), add_edges_from(), subscript
 |  notation, or G.edges.
 |
 |  >>> key = G.add_edge(1, 2, weight=4.7)
 |  >>> keys = G.add_edges_from([(3, 4), (4, 5)], color="red")
 |  >>> keys = G.add_edges_from([(1, 2, {"color": "blue"}), (2, 3, {"weight": 8})])
 |  >>> G[1][2][0]["weight"] = 4.7
 |  >>> G.edges[1, 2, 0]["weight"] = 4
 |
 |  Warning: we protect the graph data structure by making `G.edges[1,
 |  2, 0]` a read-only dict-like structure. However, you can assign to
 |  attributes in e.g. `G.edges[1, 2, 0]`. Thus, use 2 sets of brackets
 |  to add/change data attributes: `G.edges[1, 2, 0]['weight'] = 4`
 |  (for multigraphs the edge key is required: `MG.edges[u, v,
 |  key][name] = value`).
 |
 |  **Shortcuts:**
 |
 |  Many common graph features allow python syntax to speed reporting.
 |
 |  >>> 1 in G  # check if node in graph
 |  True
 |  >>> [n for n in G if n < 3]  # iterate through nodes
 |  [1, 2]
 |  >>> len(G)  # number of nodes in graph
 |  5
 |  >>> G[1]  # adjacency dict-like view mapping neighbor -> edge key -> edge attributes
 |  AdjacencyView({2: {0: {'weight': 4}, 1: {'color': 'blue'}}})
 |
 |  Often the best way to traverse all edges of a graph is via the neighbors.
 |  The neighbors are available as an adjacency-view `G.adj` object or via
 |  the method `G.adjacency()`.
 |
 |  >>> for n, nbrsdict in G.adjacency():
 |  ...     for nbr, keydict in nbrsdict.items():
 |  ...         for key, eattr in keydict.items():
 |  ...             if "weight" in eattr:
 |  ...                 # Do something useful with the edges
 |  ...                 pass
 |
 |  But the edges() method is often more convenient:
 |
 |  >>> for u, v, keys, weight in G.edges(data="weight", keys=True):
 |  ...     if weight is not None:
 |  ...         # Do something useful with the edges
 |  ...         pass
 |
 |  **Reporting:**
 |
 |  Simple graph information is obtained using methods and object-attributes.
 |  Reporting usually provides views instead of containers to reduce memory
 |  usage. The views update as the graph is updated similarly to dict-views.
 |  The objects `nodes`, `edges` and `adj` provide access to data attributes
 |  via lookup (e.g. `nodes[n]`, `edges[u, v, k]`, `adj[u][v]`) and iteration
 |  (e.g. `nodes.items()`, `nodes.data('color')`,
 |  `nodes.data('color', default='blue')` and similarly for `edges`)
 |  Views exist for `nodes`, `edges`, `neighbors()`/`adj` and `degree`.
 |
 |  For details on these and other miscellaneous methods, see below.
 |
 |  **Subclasses (Advanced):**
 |
 |  The MultiDiGraph class uses a dict-of-dict-of-dict-of-dict structure.
 |  The outer dict (node_dict) holds adjacency information keyed by node.
 |  The next dict (adjlist_dict) represents the adjacency information
 |  and holds edge_key dicts keyed by neighbor. The edge_key dict holds
 |  each edge_attr dict keyed by edge key. The inner dict
 |  (edge_attr_dict) represents the edge data and holds edge attribute
 |  values keyed by attribute names.
 |
 |  Each of these four dicts in the dict-of-dict-of-dict-of-dict
 |  structure can be replaced by a user defined dict-like object.
 |  In general, the dict-like features should be maintained but
 |  extra features can be added. To replace one of the dicts create
 |  a new graph class by changing the class(!) variable holding the
 |  factory for that dict-like structure. The variable names are
 |  node_dict_factory, node_attr_dict_factory, adjlist_inner_dict_factory,
 |  adjlist_outer_dict_factory, edge_key_dict_factory, edge_attr_dict_factory
 |  and graph_attr_dict_factory.
 |
 |  node_dict_factory : function, (default: dict)
 |      Factory function to be used to create the dict containing node
 |      attributes, keyed by node id.
 |      It should require no arguments and return a dict-like object
 |
 |  node_attr_dict_factory: function, (default: dict)
 |      Factory function to be used to create the node attribute
 |      dict which holds attribute values keyed by attribute name.
 |      It should require no arguments and return a dict-like object
 |
 |  adjlist_outer_dict_factory : function, (default: dict)
 |      Factory function to be used to create the outer-most dict
 |      in the data structure that holds adjacency info keyed by node.
 |      It should require no arguments and return a dict-like object.
 |
 |  adjlist_inner_dict_factory : function, (default: dict)
 |      Factory function to be used to create the adjacency list
 |      dict which holds multiedge key dicts keyed by neighbor.
 |      It should require no arguments and return a dict-like object.
 |
 |  edge_key_dict_factory : function, (default: dict)
 |      Factory function to be used to create the edge key dict
 |      which holds edge data keyed by edge key.
 |      It should require no arguments and return a dict-like object.
 |
 |  edge_attr_dict_factory : function, (default: dict)
 |      Factory function to be used to create the edge attribute
 |      dict which holds attribute values keyed by attribute name.
 |      It should require no arguments and return a dict-like object.
 |
 |  graph_attr_dict_factory : function, (default: dict)
 |      Factory function to be used to create the graph attribute
 |      dict which holds attribute values keyed by attribute name.
 |      It should require no arguments and return a dict-like object.
 |
 |  Typically, if your extension doesn't impact the data structure all
 |  methods will inherited without issue except: `to_directed/to_undirected`.
 |  By default these methods create a DiGraph/Graph class and you probably
 |  want them to create your extension of a DiGraph/Graph. To facilitate
 |  this we define two class variables that you can set in your subclass.
 |
 |  to_directed_class : callable, (default: DiGraph or MultiDiGraph)
 |      Class to create a new graph structure in the `to_directed` method.
 |      If `None`, a NetworkX class (DiGraph or MultiDiGraph) is used.
 |
 |  to_undirected_class : callable, (default: Graph or MultiGraph)
 |      Class to create a new graph structure in the `to_undirected` method.
 |      If `None`, a NetworkX class (Graph or MultiGraph) is used.
 |
 |  **Subclassing Example**
 |
 |  Create a low memory graph class that effectively disallows edge
 |  attributes by using a single attribute dict for all edges.
 |  This reduces the memory used, but you lose edge attributes.
 |
 |  >>> class ThinGraph(nx.Graph):
 |  ...     all_edge_dict = {"weight": 1}
 |  ...
 |  ...     def single_edge_dict(self):
 |  ...         return self.all_edge_dict
 |  ...
 |  ...     edge_attr_dict_factory = single_edge_dict
 |  >>> G = ThinGraph()
 |  >>> G.add_edge(2, 1)
 |  >>> G[2][1]
 |  {'weight': 1}
 |  >>> G.add_edge(2, 2)
 |  >>> G[2][1] is G[2][2]
 |  True
 |
 |  Method resolution order:
 |      MultiDiGraph
 |      networkx.classes.multigraph.MultiGraph
 |      networkx.classes.digraph.DiGraph
 |      networkx.classes.graph.Graph
 |      builtins.object
 |
 |  Methods defined here:
 |
 |  __init__(self, incoming_graph_data=None, multigraph_input=None, **attr)
 |      Initialize a graph with edges, name, or graph attributes.
 |
 |      Parameters
 |      ----------
 |      incoming_graph_data : input graph
 |          Data to initialize graph.  If incoming_graph_data=None (default)
 |          an empty graph is created.  The data can be an edge list, or any
 |          NetworkX graph object.  If the corresponding optional Python
 |          packages are installed the data can also be a 2D NumPy array, a
 |          SciPy sparse array, or a PyGraphviz graph.
 |
 |      multigraph_input : bool or None (default None)
 |          Note: Only used when `incoming_graph_data` is a dict.
 |          If True, `incoming_graph_data` is assumed to be a
 |          dict-of-dict-of-dict-of-dict structure keyed by
 |          node to neighbor to edge keys to edge data for multi-edges.
 |          A NetworkXError is raised if this is not the case.
 |          If False, :func:`to_networkx_graph` is used to try to determine
 |          the dict's graph data structure as either a dict-of-dict-of-dict
 |          keyed by node to neighbor to edge data, or a dict-of-iterable
 |          keyed by node to neighbors.
 |          If None, the treatment for True is tried, but if it fails,
 |          the treatment for False is tried.
 |
 |      attr : keyword arguments, optional (default= no attributes)
 |          Attributes to add to graph as key=value pairs.
 |
 |      See Also
 |      --------
 |      convert
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G = nx.Graph(name="my graph")
 |      >>> e = [(1, 2), (2, 3), (3, 4)]  # list of edges
 |      >>> G = nx.Graph(e)
 |
 |      Arbitrary graph attribute pairs (key=value) may be assigned
 |
 |      >>> G = nx.Graph(e, day="Friday")
 |      >>> G.graph
 |      {'day': 'Friday'}
 |
 |  add_edge(self, u_for_edge, v_for_edge, key=None, **attr)
 |      Add an edge between u and v.
 |
 |      The nodes u and v will be automatically added if they are
 |      not already in the graph.
 |
 |      Edge attributes can be specified with keywords or by directly
 |      accessing the edge's attribute dictionary. See examples below.
 |
 |      Parameters
 |      ----------
 |      u_for_edge, v_for_edge : nodes
 |          Nodes can be, for example, strings or numbers.
 |          Nodes must be hashable (and not None) Python objects.
 |      key : hashable identifier, optional (default=lowest unused integer)
 |          Used to distinguish multiedges between a pair of nodes.
 |      attr : keyword arguments, optional
 |          Edge data (or labels or objects) can be assigned using
 |          keyword arguments.
 |
 |      Returns
 |      -------
 |      The edge key assigned to the edge.
 |
 |      See Also
 |      --------
 |      add_edges_from : add a collection of edges
 |
 |      Notes
 |      -----
 |      To replace/update edge data, use the optional key argument
 |      to identify a unique edge.  Otherwise a new edge will be created.
 |
 |      NetworkX algorithms designed for weighted graphs cannot use
 |      multigraphs directly because it is not clear how to handle
 |      multiedge weights.  Convert to Graph using edge attribute
 |      'weight' to enable weighted graph algorithms.
 |
 |      Default keys are generated using the method `new_edge_key()`.
 |      This method can be overridden by subclassing the base class and
 |      providing a custom `new_edge_key()` method.
 |
 |      Examples
 |      --------
 |      The following all add the edge e=(1, 2) to graph G:
 |
 |      >>> G = nx.MultiDiGraph()
 |      >>> e = (1, 2)
 |      >>> key = G.add_edge(1, 2)  # explicit two-node form
 |      >>> G.add_edge(*e)  # single edge as tuple of two nodes
 |      1
 |      >>> G.add_edges_from([(1, 2)])  # add edges from iterable container
 |      [2]
 |
 |      Associate data to edges using keywords:
 |
 |      >>> key = G.add_edge(1, 2, weight=3)
 |      >>> key = G.add_edge(1, 2, key=0, weight=4)  # update data for key=0
 |      >>> key = G.add_edge(1, 3, weight=7, capacity=15, length=342.7)
 |
 |      For non-string attribute keys, use subscript notation.
 |
 |      >>> ekey = G.add_edge(1, 2)
 |      >>> G[1][2][0].update({0: 5})
 |      >>> G.edges[1, 2, 0].update({0: 5})
 |
 |  adj = <functools.cached_property object>
 |      Graph adjacency object holding the neighbors of each node.
 |
 |      This object is a read-only dict-like structure with node keys
 |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
 |      to the edgekey-dict.  So `G.adj[3][2][0]['color'] = 'blue'` sets
 |      the color of the edge `(3, 2, 0)` to `"blue"`.
 |
 |      Iterating over G.adj behaves like a dict. Useful idioms include
 |      `for nbr, datadict in G.adj[n].items():`.
 |
 |      The neighbor information is also provided by subscripting the graph.
 |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
 |
 |      For directed graphs, `G.adj` holds outgoing (successor) info.
 |
 |  degree = <functools.cached_property object>
 |      A DegreeView for the Graph as G.degree or G.degree().
 |
 |      The node degree is the number of edges adjacent to the node.
 |      The weighted node degree is the sum of the edge weights for
 |      edges incident to that node.
 |
 |      This object provides an iterator for (node, degree) as well as
 |      lookup for the degree for a single node.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      weight : string or None, optional (default=None)
 |         The name of an edge attribute that holds the numerical value used
 |         as a weight.  If None, then each edge has weight 1.
 |         The degree is the sum of the edge weights adjacent to the node.
 |
 |      Returns
 |      -------
 |      DiMultiDegreeView or int
 |          If multiple nodes are requested (the default), returns a `DiMultiDegreeView`
 |          mapping nodes to their degree.
 |          If a single node is requested, returns the degree of the node as an integer.
 |
 |      See Also
 |      --------
 |      out_degree, in_degree
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiDiGraph()
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.degree(0)  # node 0 with degree 1
 |      1
 |      >>> list(G.degree([0, 1, 2]))
 |      [(0, 1), (1, 2), (2, 2)]
 |      >>> G.add_edge(0, 1)  # parallel edge
 |      1
 |      >>> list(G.degree([0, 1, 2]))  # parallel edges are counted
 |      [(0, 2), (1, 3), (2, 2)]
 |
 |  edges = <functools.cached_property object>
 |      An OutMultiEdgeView of the Graph as G.edges or G.edges().
 |
 |      edges(self, nbunch=None, data=False, keys=False, default=None)
 |
 |      The OutMultiEdgeView provides set-like operations on the edge-tuples
 |      as well as edge attribute lookup. When called, it also provides
 |      an EdgeDataView object which allows control of access to edge
 |      attributes (but does not provide set-like operations).
 |      Hence, ``G.edges[u, v, k]['color']`` provides the value of the color
 |      attribute for the edge from ``u`` to ``v`` with key ``k`` while
 |      ``for (u, v, k, c) in G.edges(data='color', default='red', keys=True):``
 |      iterates through all the edges yielding the color attribute with
 |      default `'red'` if no color attribute exists.
 |
 |      Edges are returned as tuples with optional data and keys
 |      in the order (node, neighbor, key, data). If ``keys=True`` is not
 |      provided, the tuples will just be (node, neighbor, data), but
 |      multiple tuples with the same node and neighbor will be
 |      generated when multiple edges between two nodes exist.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges from these nodes.
 |      data : string or bool, optional (default=False)
 |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
 |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
 |          If False, return 2-tuple (u, v).
 |      keys : bool, optional (default=False)
 |          If True, return edge keys with each edge, creating (u, v, k,
 |          d) tuples when data is also requested (the default) and (u,
 |          v, k) tuples when data is not requested.
 |      default : value, optional (default=None)
 |          Value used for edges that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      edges : OutMultiEdgeView
 |          A view of edge attributes, usually it iterates over (u, v)
 |          (u, v, k) or (u, v, k, d) tuples of edges, but can also be
 |          used for attribute lookup as ``edges[u, v, k]['foo']``.
 |
 |      Notes
 |      -----
 |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
 |      For directed graphs this returns the out-edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiDiGraph()
 |      >>> nx.add_path(G, [0, 1, 2])
 |      >>> key = G.add_edge(2, 3, weight=5)
 |      >>> key2 = G.add_edge(1, 2)  # second edge between these nodes
 |      >>> [e for e in G.edges()]
 |      [(0, 1), (1, 2), (1, 2), (2, 3)]
 |      >>> list(G.edges(data=True))  # default data is {} (empty dict)
 |      [(0, 1, {}), (1, 2, {}), (1, 2, {}), (2, 3, {'weight': 5})]
 |      >>> list(G.edges(data="weight", default=1))
 |      [(0, 1, 1), (1, 2, 1), (1, 2, 1), (2, 3, 5)]
 |      >>> list(G.edges(keys=True))  # default keys are integers
 |      [(0, 1, 0), (1, 2, 0), (1, 2, 1), (2, 3, 0)]
 |      >>> list(G.edges(data=True, keys=True))
 |      [(0, 1, 0, {}), (1, 2, 0, {}), (1, 2, 1, {}), (2, 3, 0, {'weight': 5})]
 |      >>> list(G.edges(data="weight", default=1, keys=True))
 |      [(0, 1, 0, 1), (1, 2, 0, 1), (1, 2, 1, 1), (2, 3, 0, 5)]
 |      >>> list(G.edges([0, 2]))
 |      [(0, 1), (2, 3)]
 |      >>> list(G.edges(0))
 |      [(0, 1)]
 |      >>> list(G.edges(1))
 |      [(1, 2), (1, 2)]
 |
 |      See Also
 |      --------
 |      in_edges, out_edges
 |
 |  in_degree = <functools.cached_property object>
 |      A DegreeView for (node, in_degree) or in_degree for single node.
 |
 |      The node in-degree is the number of edges pointing into the node.
 |      The weighted node degree is the sum of the edge weights for
 |      edges incident to that node.
 |
 |      This object provides an iterator for (node, degree) as well as
 |      lookup for the degree for a single node.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      weight : string or None, optional (default=None)
 |         The edge attribute that holds the numerical value used
 |         as a weight.  If None, then each edge has weight 1.
 |         The degree is the sum of the edge weights adjacent to the node.
 |
 |      Returns
 |      -------
 |      If a single node is requested
 |      deg : int
 |          Degree of the node
 |
 |      OR if multiple nodes are requested
 |      nd_iter : iterator
 |          The iterator returns two-tuples of (node, in-degree).
 |
 |      See Also
 |      --------
 |      degree, out_degree
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiDiGraph()
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.in_degree(0)  # node 0 with degree 0
 |      0
 |      >>> list(G.in_degree([0, 1, 2]))
 |      [(0, 0), (1, 1), (2, 1)]
 |      >>> G.add_edge(0, 1)  # parallel edge
 |      1
 |      >>> list(G.in_degree([0, 1, 2]))  # parallel edges counted
 |      [(0, 0), (1, 2), (2, 1)]
 |
 |  in_edges = <functools.cached_property object>
 |      A view of the in edges of the graph as G.in_edges or G.in_edges().
 |
 |      in_edges(self, nbunch=None, data=False, keys=False, default=None)
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |      data : string or bool, optional (default=False)
 |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
 |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
 |          If False, return 2-tuple (u, v).
 |      keys : bool, optional (default=False)
 |          If True, return edge keys with each edge, creating 3-tuples
 |          (u, v, k) or with data, 4-tuples (u, v, k, d).
 |      default : value, optional (default=None)
 |          Value used for edges that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      in_edges : InMultiEdgeView or InMultiEdgeDataView
 |          A view of edge attributes, usually it iterates over (u, v)
 |          or (u, v, k) or (u, v, k, d) tuples of edges, but can also be
 |          used for attribute lookup as `edges[u, v, k]['foo']`.
 |
 |      See Also
 |      --------
 |      edges
 |
 |  is_directed(self)
 |      Returns True if graph is directed, False otherwise.
 |
 |  is_multigraph(self)
 |      Returns True if graph is a multigraph, False otherwise.
 |
 |  out_degree = <functools.cached_property object>
 |      Returns an iterator for (node, out-degree) or out-degree for single node.
 |
 |      out_degree(self, nbunch=None, weight=None)
 |
 |      The node out-degree is the number of edges pointing out of the node.
 |      This function returns the out-degree for a single node or an iterator
 |      for a bunch of nodes or if nothing is passed as argument.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      weight : string or None, optional (default=None)
 |         The edge attribute that holds the numerical value used
 |         as a weight.  If None, then each edge has weight 1.
 |         The degree is the sum of the edge weights.
 |
 |      Returns
 |      -------
 |      If a single node is requested
 |      deg : int
 |          Degree of the node
 |
 |      OR if multiple nodes are requested
 |      nd_iter : iterator
 |          The iterator returns two-tuples of (node, out-degree).
 |
 |      See Also
 |      --------
 |      degree, in_degree
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiDiGraph()
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.out_degree(0)  # node 0 with degree 1
 |      1
 |      >>> list(G.out_degree([0, 1, 2]))
 |      [(0, 1), (1, 1), (2, 1)]
 |      >>> G.add_edge(0, 1)  # parallel edge
 |      1
 |      >>> list(G.out_degree([0, 1, 2]))  # counts parallel edges
 |      [(0, 2), (1, 1), (2, 1)]
 |
 |  out_edges = <functools.cached_property object>
 |      An OutMultiEdgeView of the Graph as G.edges or G.edges().
 |
 |      edges(self, nbunch=None, data=False, keys=False, default=None)
 |
 |      The OutMultiEdgeView provides set-like operations on the edge-tuples
 |      as well as edge attribute lookup. When called, it also provides
 |      an EdgeDataView object which allows control of access to edge
 |      attributes (but does not provide set-like operations).
 |      Hence, ``G.edges[u, v, k]['color']`` provides the value of the color
 |      attribute for the edge from ``u`` to ``v`` with key ``k`` while
 |      ``for (u, v, k, c) in G.edges(data='color', default='red', keys=True):``
 |      iterates through all the edges yielding the color attribute with
 |      default `'red'` if no color attribute exists.
 |
 |      Edges are returned as tuples with optional data and keys
 |      in the order (node, neighbor, key, data). If ``keys=True`` is not
 |      provided, the tuples will just be (node, neighbor, data), but
 |      multiple tuples with the same node and neighbor will be
 |      generated when multiple edges between two nodes exist.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges from these nodes.
 |      data : string or bool, optional (default=False)
 |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
 |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
 |          If False, return 2-tuple (u, v).
 |      keys : bool, optional (default=False)
 |          If True, return edge keys with each edge, creating (u, v, k,
 |          d) tuples when data is also requested (the default) and (u,
 |          v, k) tuples when data is not requested.
 |      default : value, optional (default=None)
 |          Value used for edges that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      edges : OutMultiEdgeView
 |          A view of edge attributes, usually it iterates over (u, v)
 |          (u, v, k) or (u, v, k, d) tuples of edges, but can also be
 |          used for attribute lookup as ``edges[u, v, k]['foo']``.
 |
 |      Notes
 |      -----
 |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
 |      For directed graphs this returns the out-edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiDiGraph()
 |      >>> nx.add_path(G, [0, 1, 2])
 |      >>> key = G.add_edge(2, 3, weight=5)
 |      >>> key2 = G.add_edge(1, 2)  # second edge between these nodes
 |      >>> [e for e in G.edges()]
 |      [(0, 1), (1, 2), (1, 2), (2, 3)]
 |      >>> list(G.edges(data=True))  # default data is {} (empty dict)
 |      [(0, 1, {}), (1, 2, {}), (1, 2, {}), (2, 3, {'weight': 5})]
 |      >>> list(G.edges(data="weight", default=1))
 |      [(0, 1, 1), (1, 2, 1), (1, 2, 1), (2, 3, 5)]
 |      >>> list(G.edges(keys=True))  # default keys are integers
 |      [(0, 1, 0), (1, 2, 0), (1, 2, 1), (2, 3, 0)]
 |      >>> list(G.edges(data=True, keys=True))
 |      [(0, 1, 0, {}), (1, 2, 0, {}), (1, 2, 1, {}), (2, 3, 0, {'weight': 5})]
 |      >>> list(G.edges(data="weight", default=1, keys=True))
 |      [(0, 1, 0, 1), (1, 2, 0, 1), (1, 2, 1, 1), (2, 3, 0, 5)]
 |      >>> list(G.edges([0, 2]))
 |      [(0, 1), (2, 3)]
 |      >>> list(G.edges(0))
 |      [(0, 1)]
 |      >>> list(G.edges(1))
 |      [(1, 2), (1, 2)]
 |
 |      See Also
 |      --------
 |      in_edges, out_edges
 |
 |  pred = <functools.cached_property object>
 |      Graph adjacency object holding the predecessors of each node.
 |
 |      This object is a read-only dict-like structure with node keys
 |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
 |      to the edgekey-dict.  So `G.adj[3][2][0]['color'] = 'blue'` sets
 |      the color of the edge `(3, 2, 0)` to `"blue"`.
 |
 |      Iterating over G.adj behaves like a dict. Useful idioms include
 |      `for nbr, datadict in G.adj[n].items():`.
 |
 |  remove_edge(self, u, v, key=None)
 |      Remove an edge between u and v.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |          Remove an edge between nodes u and v.
 |      key : hashable identifier, optional (default=None)
 |          Used to distinguish multiple edges between a pair of nodes.
 |          If None, remove a single edge between u and v. If there are
 |          multiple edges, removes the last edge added in terms of
 |          insertion order.
 |
 |      Raises
 |      ------
 |      NetworkXError
 |          If there is not an edge between u and v, or
 |          if there is no edge with the specified key.
 |
 |      See Also
 |      --------
 |      remove_edges_from : remove a collection of edges
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiDiGraph()
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.remove_edge(0, 1)
 |      >>> e = (1, 2)
 |      >>> G.remove_edge(*e)  # unpacks e from an edge tuple
 |
 |      For multiple edges
 |
 |      >>> G = nx.MultiDiGraph()
 |      >>> G.add_edges_from([(1, 2), (1, 2), (1, 2)])  # key_list returned
 |      [0, 1, 2]
 |
 |      When ``key=None`` (the default), edges are removed in the opposite
 |      order that they were added:
 |
 |      >>> G.remove_edge(1, 2)
 |      >>> G.edges(keys=True)
 |      OutMultiEdgeView([(1, 2, 0), (1, 2, 1)])
 |
 |      For edges with keys
 |
 |      >>> G = nx.MultiDiGraph()
 |      >>> G.add_edge(1, 2, key="first")
 |      'first'
 |      >>> G.add_edge(1, 2, key="second")
 |      'second'
 |      >>> G.remove_edge(1, 2, key="first")
 |      >>> G.edges(keys=True)
 |      OutMultiEdgeView([(1, 2, 'second')])
 |
 |  reverse(self, copy=True)
 |      Returns the reverse of the graph.
 |
 |      The reverse is a graph with the same nodes and edges
 |      but with the directions of the edges reversed.
 |
 |      Parameters
 |      ----------
 |      copy : bool optional (default=True)
 |          If True, return a new DiGraph holding the reversed edges.
 |          If False, the reverse graph is created using a view of
 |          the original graph.
 |
 |  succ = <functools.cached_property object>
 |      Graph adjacency object holding the successors of each node.
 |
 |      This object is a read-only dict-like structure with node keys
 |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
 |      to the edgekey-dict.  So `G.adj[3][2][0]['color'] = 'blue'` sets
 |      the color of the edge `(3, 2, 0)` to `"blue"`.
 |
 |      Iterating over G.adj behaves like a dict. Useful idioms include
 |      `for nbr, datadict in G.adj[n].items():`.
 |
 |      The neighbor information is also provided by subscripting the graph.
 |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
 |
 |      For directed graphs, `G.succ` is identical to `G.adj`.
 |
 |  to_undirected(self, reciprocal=False, as_view=False)
 |      Returns an undirected representation of the digraph.
 |
 |      Parameters
 |      ----------
 |      reciprocal : bool (optional)
 |        If True only keep edges that appear in both directions
 |        in the original digraph.
 |      as_view : bool (optional, default=False)
 |        If True return an undirected view of the original directed graph.
 |
 |      Returns
 |      -------
 |      G : MultiGraph
 |          An undirected graph with the same name and nodes and
 |          with edge (u, v, data) if either (u, v, data) or (v, u, data)
 |          is in the digraph.  If both edges exist in digraph and
 |          their edge data is different, only one edge is created
 |          with an arbitrary choice of which edge data to use.
 |          You must check and correct for this manually if desired.
 |
 |      See Also
 |      --------
 |      MultiGraph, copy, add_edge, add_edges_from
 |
 |      Notes
 |      -----
 |      This returns a "deepcopy" of the edge, node, and
 |      graph attributes which attempts to completely copy
 |      all of the data and references.
 |
 |      This is in contrast to the similar D=MultiDiGraph(G) which
 |      returns a shallow copy of the data.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Warning: If you have subclassed MultiDiGraph to use dict-like
 |      objects in the data structure, those changes do not transfer
 |      to the MultiGraph created by this method.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(2)  # or MultiGraph, etc
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1), (1, 0)]
 |      >>> G2 = H.to_undirected()
 |      >>> list(G2.edges)
 |      [(0, 1)]
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes defined here:
 |
 |  edge_key_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from networkx.classes.multigraph.MultiGraph:
 |
 |  add_edges_from(self, ebunch_to_add, **attr)
 |      Add all the edges in ebunch_to_add.
 |
 |      Parameters
 |      ----------
 |      ebunch_to_add : container of edges
 |          Each edge given in the container will be added to the
 |          graph. The edges can be:
 |
 |              - 2-tuples (u, v) or
 |              - 3-tuples (u, v, d) for an edge data dict d, or
 |              - 3-tuples (u, v, k) for not iterable key k, or
 |              - 4-tuples (u, v, k, d) for an edge with data and key k
 |
 |      attr : keyword arguments, optional
 |          Edge data (or labels or objects) can be assigned using
 |          keyword arguments.
 |
 |      Returns
 |      -------
 |      A list of edge keys assigned to the edges in `ebunch`.
 |
 |      See Also
 |      --------
 |      add_edge : add a single edge
 |      add_weighted_edges_from : convenient way to add weighted edges
 |
 |      Notes
 |      -----
 |      Adding the same edge twice has no effect but any edge data
 |      will be updated when each duplicate edge is added.
 |
 |      Edge attributes specified in an ebunch take precedence over
 |      attributes specified via keyword arguments.
 |
 |      Default keys are generated using the method ``new_edge_key()``.
 |      This method can be overridden by subclassing the base class and
 |      providing a custom ``new_edge_key()`` method.
 |
 |      When adding edges from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_edges)`, and pass this
 |      object to `G.add_edges_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_edges_from([(0, 1), (1, 2)])  # using a list of edge tuples
 |      >>> e = zip(range(0, 3), range(1, 4))
 |      >>> G.add_edges_from(e)  # Add the path graph 0-1-2-3
 |
 |      Associate data to edges
 |
 |      >>> G.add_edges_from([(1, 2), (2, 3)], weight=3)
 |      >>> G.add_edges_from([(3, 4), (1, 4)], label="WN2898")
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.MultiGraph([(1, 2), (2, 3), (3, 4)])
 |      >>> # Grow graph by one new node, adding edges to all existing nodes.
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_edges_from(((5, n) for n in G.nodes))
 |      >>> # right way - note that there will be no self-edge for node 5
 |      >>> assigned_keys = G.add_edges_from(list((5, n) for n in G.nodes))
 |
 |  copy(self, as_view=False)
 |      Returns a copy of the graph.
 |
 |      The copy method by default returns an independent shallow copy
 |      of the graph and attributes. That is, if an attribute is a
 |      container, that container is shared by the original an the copy.
 |      Use Python's `copy.deepcopy` for new containers.
 |
 |      If `as_view` is True then a view is returned instead of a copy.
 |
 |      Notes
 |      -----
 |      All copies reproduce the graph structure, but data attributes
 |      may be handled in different ways. There are four types of copies
 |      of a graph that people might want.
 |
 |      Deepcopy -- A "deepcopy" copies the graph structure as well as
 |      all data attributes and any objects they might contain.
 |      The entire graph object is new so that changes in the copy
 |      do not affect the original object. (see Python's copy.deepcopy)
 |
 |      Data Reference (Shallow) -- For a shallow copy the graph structure
 |      is copied but the edge, node and graph attribute dicts are
 |      references to those in the original graph. This saves
 |      time and memory but could cause confusion if you change an attribute
 |      in one graph and it changes the attribute in the other.
 |      NetworkX does not provide this level of shallow copy.
 |
 |      Independent Shallow -- This copy creates new independent attribute
 |      dicts and then does a shallow copy of the attributes. That is, any
 |      attributes that are containers are shared between the new graph
 |      and the original. This is exactly what `dict.copy()` provides.
 |      You can obtain this style copy using:
 |
 |          >>> G = nx.path_graph(5)
 |          >>> H = G.copy()
 |          >>> H = G.copy(as_view=False)
 |          >>> H = nx.Graph(G)
 |          >>> H = G.__class__(G)
 |
 |      Fresh Data -- For fresh data, the graph structure is copied while
 |      new empty data attribute dicts are created. The resulting graph
 |      is independent of the original and it has no edge, node or graph
 |      attributes. Fresh copies are not enabled. Instead use:
 |
 |          >>> H = G.__class__()
 |          >>> H.add_nodes_from(G)
 |          >>> H.add_edges_from(G.edges)
 |
 |      View -- Inspired by dict-views, graph-views act like read-only
 |      versions of the original graph, providing a copy of the original
 |      structure without requiring any memory for copying the information.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Parameters
 |      ----------
 |      as_view : bool, optional (default=False)
 |          If True, the returned graph-view provides a read-only view
 |          of the original graph without actually copying any data.
 |
 |      Returns
 |      -------
 |      G : Graph
 |          A copy of the graph.
 |
 |      See Also
 |      --------
 |      to_directed: return a directed copy of the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> H = G.copy()
 |
 |  get_edge_data(self, u, v, key=None, default=None)
 |      Returns the attribute dictionary associated with edge (u, v,
 |      key).
 |
 |      If a key is not provided, returns a dictionary mapping edge keys
 |      to attribute dictionaries for each edge between u and v.
 |
 |      This is identical to `G[u][v][key]` except the default is returned
 |      instead of an exception is the edge doesn't exist.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |
 |      default :  any Python object (default=None)
 |          Value to return if the specific edge (u, v, key) is not
 |          found, OR if there are no edges between u and v and no key
 |          is specified.
 |
 |      key : hashable identifier, optional (default=None)
 |          Return data only for the edge with specified key, as an
 |          attribute dictionary (rather than a dictionary mapping keys
 |          to attribute dictionaries).
 |
 |      Returns
 |      -------
 |      edge_dict : dictionary
 |          The edge attribute dictionary, OR a dictionary mapping edge
 |          keys to attribute dictionaries for each of those edges if no
 |          specific key is provided (even if there's only one edge
 |          between u and v).
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiGraph()  # or MultiDiGraph
 |      >>> key = G.add_edge(0, 1, key="a", weight=7)
 |      >>> G[0][1]["a"]  # key='a'
 |      {'weight': 7}
 |      >>> G.edges[0, 1, "a"]  # key='a'
 |      {'weight': 7}
 |
 |      Warning: we protect the graph data structure by making
 |      `G.edges` and `G[1][2]` read-only dict-like structures.
 |      However, you can assign values to attributes in e.g.
 |      `G.edges[1, 2, 'a']` or `G[1][2]['a']` using an additional
 |      bracket as shown next. You need to specify all edge info
 |      to assign to the edge data associated with an edge.
 |
 |      >>> G[0][1]["a"]["weight"] = 10
 |      >>> G.edges[0, 1, "a"]["weight"] = 10
 |      >>> G[0][1]["a"]["weight"]
 |      10
 |      >>> G.edges[1, 0, "a"]["weight"]
 |      10
 |
 |      >>> G = nx.MultiGraph()  # or MultiDiGraph
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.edges[0, 1, 0]["weight"] = 5
 |      >>> G.get_edge_data(0, 1)
 |      {0: {'weight': 5}}
 |      >>> e = (0, 1)
 |      >>> G.get_edge_data(*e)  # tuple form
 |      {0: {'weight': 5}}
 |      >>> G.get_edge_data(3, 0)  # edge not in graph, returns None
 |      >>> G.get_edge_data(3, 0, default=0)  # edge not in graph, return default
 |      0
 |      >>> G.get_edge_data(1, 0, 0)  # specific key gives back
 |      {'weight': 5}
 |
 |  has_edge(self, u, v, key=None)
 |      Returns True if the graph has an edge between nodes u and v.
 |
 |      This is the same as `v in G[u] or key in G[u][v]`
 |      without KeyError exceptions.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |          Nodes can be, for example, strings or numbers.
 |
 |      key : hashable identifier, optional (default=None)
 |          If specified return True only if the edge with
 |          key is found.
 |
 |      Returns
 |      -------
 |      edge_ind : bool
 |          True if edge is in the graph, False otherwise.
 |
 |      Examples
 |      --------
 |      Can be called either using two nodes u, v, an edge tuple (u, v),
 |      or an edge tuple (u, v, key).
 |
 |      >>> G = nx.MultiGraph()  # or MultiDiGraph
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.has_edge(0, 1)  # using two nodes
 |      True
 |      >>> e = (0, 1)
 |      >>> G.has_edge(*e)  #  e is a 2-tuple (u, v)
 |      True
 |      >>> G.add_edge(0, 1, key="a")
 |      'a'
 |      >>> G.has_edge(0, 1, key="a")  # specify key
 |      True
 |      >>> G.has_edge(1, 0, key="a")  # edges aren't directed
 |      True
 |      >>> e = (0, 1, "a")
 |      >>> G.has_edge(*e)  # e is a 3-tuple (u, v, 'a')
 |      True
 |
 |      The following syntax are equivalent:
 |
 |      >>> G.has_edge(0, 1)
 |      True
 |      >>> 1 in G[0]  # though this gives :exc:`KeyError` if 0 not in G
 |      True
 |      >>> 0 in G[1]  # other order; also gives :exc:`KeyError` if 0 not in G
 |      True
 |
 |  new_edge_key(self, u, v)
 |      Returns an unused key for edges between nodes `u` and `v`.
 |
 |      The nodes `u` and `v` do not need to be already in the graph.
 |
 |      Notes
 |      -----
 |      In the standard MultiGraph class the new key is the number of existing
 |      edges between `u` and `v` (increased if necessary to ensure unused).
 |      The first edge will have key 0, then 1, etc. If an edge is removed
 |      further new_edge_keys may not be in this order.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |
 |      Returns
 |      -------
 |      key : int
 |
 |  number_of_edges(self, u=None, v=None)
 |      Returns the number of edges between two nodes.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes, optional (Default=all edges)
 |          If u and v are specified, return the number of edges between
 |          u and v. Otherwise return the total number of all edges.
 |
 |      Returns
 |      -------
 |      nedges : int
 |          The number of edges in the graph.  If nodes `u` and `v` are
 |          specified return the number of edges between those nodes. If
 |          the graph is directed, this only returns the number of edges
 |          from `u` to `v`.
 |
 |      See Also
 |      --------
 |      size
 |
 |      Examples
 |      --------
 |      For undirected multigraphs, this method counts the total number
 |      of edges in the graph::
 |
 |          >>> G = nx.MultiGraph()
 |          >>> G.add_edges_from([(0, 1), (0, 1), (1, 2)])
 |          [0, 1, 0]
 |          >>> G.number_of_edges()
 |          3
 |
 |      If you specify two nodes, this counts the total number of edges
 |      joining the two nodes::
 |
 |          >>> G.number_of_edges(0, 1)
 |          2
 |
 |      For directed multigraphs, this method can count the total number
 |      of directed edges from `u` to `v`::
 |
 |          >>> G = nx.MultiDiGraph()
 |          >>> G.add_edges_from([(0, 1), (0, 1), (1, 0)])
 |          [0, 1, 0]
 |          >>> G.number_of_edges(0, 1)
 |          2
 |          >>> G.number_of_edges(1, 0)
 |          1
 |
 |  remove_edges_from(self, ebunch)
 |      Remove all edges specified in ebunch.
 |
 |      Parameters
 |      ----------
 |      ebunch: list or container of edge tuples
 |          Each edge given in the list or container will be removed
 |          from the graph. The edges can be:
 |
 |              - 2-tuples (u, v) A single edge between u and v is removed.
 |              - 3-tuples (u, v, key) The edge identified by key is removed.
 |              - 4-tuples (u, v, key, data) where data is ignored.
 |
 |      See Also
 |      --------
 |      remove_edge : remove a single edge
 |
 |      Notes
 |      -----
 |      Will fail silently if an edge in ebunch is not in the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> ebunch = [(1, 2), (2, 3)]
 |      >>> G.remove_edges_from(ebunch)
 |
 |      Removing multiple copies of edges
 |
 |      >>> G = nx.MultiGraph()
 |      >>> keys = G.add_edges_from([(1, 2), (1, 2), (1, 2)])
 |      >>> G.remove_edges_from([(1, 2), (2, 1)])  # edges aren't directed
 |      >>> list(G.edges())
 |      [(1, 2)]
 |      >>> G.remove_edges_from([(1, 2), (1, 2)])  # silently ignore extra copy
 |      >>> list(G.edges)  # now empty graph
 |      []
 |
 |      When the edge is a 2-tuple ``(u, v)`` but there are multiple edges between
 |      u and v in the graph, the most recent edge (in terms of insertion
 |      order) is removed.
 |
 |      >>> G = nx.MultiGraph()
 |      >>> for key in ("x", "y", "a"):
 |      ...     k = G.add_edge(0, 1, key=key)
 |      >>> G.edges(keys=True)
 |      MultiEdgeView([(0, 1, 'x'), (0, 1, 'y'), (0, 1, 'a')])
 |      >>> G.remove_edges_from([(0, 1)])
 |      >>> G.edges(keys=True)
 |      MultiEdgeView([(0, 1, 'x'), (0, 1, 'y')])
 |
 |  to_directed(self, as_view=False)
 |      Returns a directed representation of the graph.
 |
 |      Returns
 |      -------
 |      G : MultiDiGraph
 |          A directed graph with the same name, same nodes, and with
 |          each edge (u, v, k, data) replaced by two directed edges
 |          (u, v, k, data) and (v, u, k, data).
 |
 |      Notes
 |      -----
 |      This returns a "deepcopy" of the edge, node, and
 |      graph attributes which attempts to completely copy
 |      all of the data and references.
 |
 |      This is in contrast to the similar D=MultiDiGraph(G) which
 |      returns a shallow copy of the data.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Warning: If you have subclassed MultiGraph to use dict-like objects
 |      in the data structure, those changes do not transfer to the
 |      MultiDiGraph created by this method.
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiGraph()
 |      >>> G.add_edge(0, 1)
 |      0
 |      >>> G.add_edge(0, 1)
 |      1
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1, 0), (0, 1, 1), (1, 0, 0), (1, 0, 1)]
 |
 |      If already directed, return a (deep) copy
 |
 |      >>> G = nx.MultiDiGraph()
 |      >>> G.add_edge(0, 1)
 |      0
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1, 0)]
 |
 |  to_directed_class(self)
 |      Returns the class to use for empty directed copies.
 |
 |      If you subclass the base classes, use this to designate
 |      what directed class to use for `to_directed()` copies.
 |
 |  to_undirected_class(self)
 |      Returns the class to use for empty undirected copies.
 |
 |      If you subclass the base classes, use this to designate
 |      what directed class to use for `to_directed()` copies.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from networkx.classes.digraph.DiGraph:
 |
 |  add_node(self, node_for_adding, **attr)
 |      Add a single node `node_for_adding` and update node attributes.
 |
 |      Parameters
 |      ----------
 |      node_for_adding : node
 |          A node can be any hashable Python object except None.
 |      attr : keyword arguments, optional
 |          Set or change node attributes using key=value.
 |
 |      See Also
 |      --------
 |      add_nodes_from
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_node(1)
 |      >>> G.add_node("Hello")
 |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
 |      >>> G.add_node(K3)
 |      >>> G.number_of_nodes()
 |      3
 |
 |      Use keywords set/change node attributes:
 |
 |      >>> G.add_node(1, size=10)
 |      >>> G.add_node(3, weight=0.4, UTM=("13S", 382871, 3972649))
 |
 |      Notes
 |      -----
 |      A hashable object is one that can be used as a key in a Python
 |      dictionary. This includes strings, numbers, tuples of strings
 |      and numbers, etc.
 |
 |      On many platforms hashable items also include mutables such as
 |      NetworkX Graphs, though one should be careful that the hash
 |      doesn't change on mutables.
 |
 |  add_nodes_from(self, nodes_for_adding, **attr)
 |      Add multiple nodes.
 |
 |      Parameters
 |      ----------
 |      nodes_for_adding : iterable container
 |          A container of nodes (list, dict, set, etc.).
 |          OR
 |          A container of (node, attribute dict) tuples.
 |          Node attributes are updated using the attribute dict.
 |      attr : keyword arguments, optional (default= no attributes)
 |          Update attributes for all nodes in nodes.
 |          Node attributes specified in nodes as a tuple take
 |          precedence over attributes specified via keyword arguments.
 |
 |      See Also
 |      --------
 |      add_node
 |
 |      Notes
 |      -----
 |      When adding nodes from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
 |      object to `G.add_nodes_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_nodes_from("Hello")
 |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
 |      >>> G.add_nodes_from(K3)
 |      >>> sorted(G.nodes(), key=str)
 |      [0, 1, 2, 'H', 'e', 'l', 'o']
 |
 |      Use keywords to update specific node attributes for every node.
 |
 |      >>> G.add_nodes_from([1, 2], size=10)
 |      >>> G.add_nodes_from([3, 4], weight=0.4)
 |
 |      Use (node, attrdict) tuples to update attributes for specific nodes.
 |
 |      >>> G.add_nodes_from([(1, dict(size=11)), (2, {"color": "blue"})])
 |      >>> G.nodes[1]["size"]
 |      11
 |      >>> H = nx.Graph()
 |      >>> H.add_nodes_from(G.nodes(data=True))
 |      >>> H.nodes[1]["size"]
 |      11
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.DiGraph([(0, 1), (1, 2), (3, 4)])
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_nodes_from(n + 1 for n in G.nodes)
 |      >>> # correct way
 |      >>> G.add_nodes_from(list(n + 1 for n in G.nodes))
 |
 |  clear(self)
 |      Remove all nodes and edges from the graph.
 |
 |      This also removes the name, and all graph, node, and edge attributes.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.clear()
 |      >>> list(G.nodes)
 |      []
 |      >>> list(G.edges)
 |      []
 |
 |  clear_edges(self)
 |      Remove all edges from the graph without altering nodes.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.clear_edges()
 |      >>> list(G.nodes)
 |      [0, 1, 2, 3]
 |      >>> list(G.edges)
 |      []
 |
 |  has_predecessor(self, u, v)
 |      Returns True if node u has predecessor v.
 |
 |      This is true if graph has the edge u<-v.
 |
 |  has_successor(self, u, v)
 |      Returns True if node u has successor v.
 |
 |      This is true if graph has the edge u->v.
 |
 |  neighbors = successors(self, n)
 |
 |  predecessors(self, n)
 |      Returns an iterator over predecessor nodes of n.
 |
 |      A predecessor of n is a node m such that there exists a directed
 |      edge from m to n.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Raises
 |      ------
 |      NetworkXError
 |         If n is not in the graph.
 |
 |      See Also
 |      --------
 |      successors
 |
 |  remove_node(self, n)
 |      Remove node n.
 |
 |      Removes the node n and all adjacent edges.
 |      Attempting to remove a nonexistent node will raise an exception.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Raises
 |      ------
 |      NetworkXError
 |         If n is not in the graph.
 |
 |      See Also
 |      --------
 |      remove_nodes_from
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> list(G.edges)
 |      [(0, 1), (1, 2)]
 |      >>> G.remove_node(1)
 |      >>> list(G.edges)
 |      []
 |
 |  remove_nodes_from(self, nodes)
 |      Remove multiple nodes.
 |
 |      Parameters
 |      ----------
 |      nodes : iterable container
 |          A container of nodes (list, dict, set, etc.).  If a node
 |          in the container is not in the graph it is silently ignored.
 |
 |      See Also
 |      --------
 |      remove_node
 |
 |      Notes
 |      -----
 |      When removing nodes from an iterator over the graph you are changing,
 |      a `RuntimeError` will be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
 |      object to `G.remove_nodes_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> e = list(G.nodes)
 |      >>> e
 |      [0, 1, 2]
 |      >>> G.remove_nodes_from(e)
 |      >>> list(G.nodes)
 |      []
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.DiGraph([(0, 1), (1, 2), (3, 4)])
 |      >>> # this command will fail, as the graph's dict is modified during iteration
 |      >>> # G.remove_nodes_from(n for n in G.nodes if n < 2)
 |      >>> # this command will work, since the dictionary underlying graph is not modified
 |      >>> G.remove_nodes_from(list(n for n in G.nodes if n < 2))
 |
 |  successors(self, n)
 |      Returns an iterator over successor nodes of n.
 |
 |      A successor of n is a node m such that there exists a directed
 |      edge from n to m.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Raises
 |      ------
 |      NetworkXError
 |         If n is not in the graph.
 |
 |      See Also
 |      --------
 |      predecessors
 |
 |      Notes
 |      -----
 |      neighbors() and successors() are the same.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from networkx.classes.graph.Graph:
 |
 |  __contains__(self, n)
 |      Returns True if n is a node, False otherwise. Use: 'n in G'.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> 1 in G
 |      True
 |
 |  __getitem__(self, n)
 |      Returns a dict of neighbors of node n.  Use: 'G[n]'.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph.
 |
 |      Returns
 |      -------
 |      adj_dict : dictionary
 |         The adjacency dictionary for nodes connected to n.
 |
 |      Notes
 |      -----
 |      G[n] is the same as G.adj[n] and similar to G.neighbors(n)
 |      (which is an iterator over G.adj[n])
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G[0]
 |      AtlasView({1: {}})
 |
 |  __iter__(self)
 |      Iterate over the nodes. Use: 'for n in G'.
 |
 |      Returns
 |      -------
 |      niter : iterator
 |          An iterator over all nodes in the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> [n for n in G]
 |      [0, 1, 2, 3]
 |      >>> list(G)
 |      [0, 1, 2, 3]
 |
 |  __len__(self)
 |      Returns the number of nodes in the graph. Use: 'len(G)'.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      number_of_nodes: identical method
 |      order: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> len(G)
 |      4
 |
 |  __str__(self)
 |      Returns a short summary of the graph.
 |
 |      Returns
 |      -------
 |      info : string
 |          Graph information including the graph name (if any), graph type, and the
 |          number of nodes and edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph(name="foo")
 |      >>> str(G)
 |      "Graph named 'foo' with 0 nodes and 0 edges"
 |
 |      >>> G = nx.path_graph(3)
 |      >>> str(G)
 |      'Graph with 3 nodes and 2 edges'
 |
 |  add_weighted_edges_from(self, ebunch_to_add, weight='weight', **attr)
 |      Add weighted edges in `ebunch_to_add` with specified weight attr
 |
 |      Parameters
 |      ----------
 |      ebunch_to_add : container of edges
 |          Each edge given in the list or container will be added
 |          to the graph. The edges must be given as 3-tuples (u, v, w)
 |          where w is a number.
 |      weight : string, optional (default= 'weight')
 |          The attribute name for the edge weights to be added.
 |      attr : keyword arguments, optional (default= no attributes)
 |          Edge attributes to add/update for all edges.
 |
 |      See Also
 |      --------
 |      add_edge : add a single edge
 |      add_edges_from : add multiple edges
 |
 |      Notes
 |      -----
 |      Adding the same edge twice for Graph/DiGraph simply updates
 |      the edge data. For MultiGraph/MultiDiGraph, duplicate edges
 |      are stored.
 |
 |      When adding edges from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_edges)`, and pass this
 |      object to `G.add_weighted_edges_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_weighted_edges_from([(0, 1, 3.0), (1, 2, 7.5)])
 |
 |      Evaluate an iterator over edges before passing it
 |
 |      >>> G = nx.Graph([(1, 2), (2, 3), (3, 4)])
 |      >>> weight = 0.1
 |      >>> # Grow graph by one new node, adding edges to all existing nodes.
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_weighted_edges_from(((5, n, weight) for n in G.nodes))
 |      >>> # correct way - note that there will be no self-edge for node 5
 |      >>> G.add_weighted_edges_from(list((5, n, weight) for n in G.nodes))
 |
 |  adjacency(self)
 |      Returns an iterator over (node, adjacency dict) tuples for all nodes.
 |
 |      For directed graphs, only outgoing neighbors/adjacencies are included.
 |
 |      Returns
 |      -------
 |      adj_iter : iterator
 |         An iterator over (node, adjacency dictionary) for all nodes in
 |         the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> [(n, nbrdict) for n, nbrdict in G.adjacency()]
 |      [(0, {1: {}}), (1, {0: {}, 2: {}}), (2, {1: {}, 3: {}}), (3, {2: {}})]
 |
 |  edge_subgraph(self, edges)
 |      Returns the subgraph induced by the specified edges.
 |
 |      The induced subgraph contains each edge in `edges` and each
 |      node incident to any one of those edges.
 |
 |      Parameters
 |      ----------
 |      edges : iterable
 |          An iterable of edges in this graph.
 |
 |      Returns
 |      -------
 |      G : Graph
 |          An edge-induced subgraph of this graph with the same edge
 |          attributes.
 |
 |      Notes
 |      -----
 |      The graph, edge, and node attributes in the returned subgraph
 |      view are references to the corresponding attributes in the original
 |      graph. The view is read-only.
 |
 |      To create a full graph version of the subgraph with its own copy
 |      of the edge or node attributes, use::
 |
 |          G.edge_subgraph(edges).copy()
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(5)
 |      >>> H = G.edge_subgraph([(0, 1), (3, 4)])
 |      >>> list(H.nodes)
 |      [0, 1, 3, 4]
 |      >>> list(H.edges)
 |      [(0, 1), (3, 4)]
 |
 |  has_node(self, n)
 |      Returns True if the graph contains the node n.
 |
 |      Identical to `n in G`
 |
 |      Parameters
 |      ----------
 |      n : node
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.has_node(0)
 |      True
 |
 |      It is more readable and simpler to use
 |
 |      >>> 0 in G
 |      True
 |
 |  nbunch_iter(self, nbunch=None)
 |      Returns an iterator over nodes contained in nbunch that are
 |      also in the graph.
 |
 |      The nodes in nbunch are checked for membership in the graph
 |      and if not are silently ignored.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      Returns
 |      -------
 |      niter : iterator
 |          An iterator over nodes in nbunch that are also in the graph.
 |          If nbunch is None, iterate over all nodes in the graph.
 |
 |      Raises
 |      ------
 |      NetworkXError
 |          If nbunch is not a node or sequence of nodes.
 |          If a node in nbunch is not hashable.
 |
 |      See Also
 |      --------
 |      Graph.__iter__
 |
 |      Notes
 |      -----
 |      When nbunch is an iterator, the returned iterator yields values
 |      directly from nbunch, becoming exhausted when nbunch is exhausted.
 |
 |      To test whether nbunch is a single node, one can use
 |      "if nbunch in self:", even after processing with this routine.
 |
 |      If nbunch is not a node or a (possibly empty) sequence/iterator
 |      or None, a :exc:`NetworkXError` is raised.  Also, if any object in
 |      nbunch is not hashable, a :exc:`NetworkXError` is raised.
 |
 |  nodes = <functools.cached_property object>
 |      A NodeView of the Graph as G.nodes or G.nodes().
 |
 |      Can be used as `G.nodes` for data lookup and for set-like operations.
 |      Can also be used as `G.nodes(data='color', default=None)` to return a
 |      NodeDataView which reports specific node data but no set operations.
 |      It presents a dict-like interface as well with `G.nodes.items()`
 |      iterating over `(node, nodedata)` 2-tuples and `G.nodes[3]['foo']`
 |      providing the value of the `foo` attribute for node `3`. In addition,
 |      a view `G.nodes.data('foo')` provides a dict-like interface to the
 |      `foo` attribute of each node. `G.nodes.data('foo', default=1)`
 |      provides a default for nodes that do not have attribute `foo`.
 |
 |      Parameters
 |      ----------
 |      data : string or bool, optional (default=False)
 |          The node attribute returned in 2-tuple (n, ddict[data]).
 |          If True, return entire node attribute dict as (n, ddict).
 |          If False, return just the nodes n.
 |
 |      default : value, optional (default=None)
 |          Value used for nodes that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      NodeView
 |          Allows set-like operations over the nodes as well as node
 |          attribute dict lookup and calling to get a NodeDataView.
 |          A NodeDataView iterates over `(n, data)` and has no set operations.
 |          A NodeView iterates over `n` and includes set operations.
 |
 |          When called, if data is False, an iterator over nodes.
 |          Otherwise an iterator of 2-tuples (node, attribute value)
 |          where the attribute is specified in `data`.
 |          If data is True then the attribute becomes the
 |          entire data dictionary.
 |
 |      Notes
 |      -----
 |      If your node data is not needed, it is simpler and equivalent
 |      to use the expression ``for n in G``, or ``list(G)``.
 |
 |      Examples
 |      --------
 |      There are two simple ways of getting a list of all nodes in the graph:
 |
 |      >>> G = nx.path_graph(3)
 |      >>> list(G.nodes)
 |      [0, 1, 2]
 |      >>> list(G)
 |      [0, 1, 2]
 |
 |      To get the node data along with the nodes:
 |
 |      >>> G.add_node(1, time="5pm")
 |      >>> G.nodes[0]["foo"] = "bar"
 |      >>> list(G.nodes(data=True))
 |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
 |      >>> list(G.nodes.data())
 |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
 |
 |      >>> list(G.nodes(data="foo"))
 |      [(0, 'bar'), (1, None), (2, None)]
 |      >>> list(G.nodes.data("foo"))
 |      [(0, 'bar'), (1, None), (2, None)]
 |
 |      >>> list(G.nodes(data="time"))
 |      [(0, None), (1, '5pm'), (2, None)]
 |      >>> list(G.nodes.data("time"))
 |      [(0, None), (1, '5pm'), (2, None)]
 |
 |      >>> list(G.nodes(data="time", default="Not Available"))
 |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
 |      >>> list(G.nodes.data("time", default="Not Available"))
 |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
 |
 |      If some of your nodes have an attribute and the rest are assumed
 |      to have a default attribute value you can create a dictionary
 |      from node/attribute pairs using the `default` keyword argument
 |      to guarantee the value is never None::
 |
 |          >>> G = nx.Graph()
 |          >>> G.add_node(0)
 |          >>> G.add_node(1, weight=2)
 |          >>> G.add_node(2, weight=3)
 |          >>> dict(G.nodes(data="weight", default=1))
 |          {0: 1, 1: 2, 2: 3}
 |
 |  number_of_nodes(self)
 |      Returns the number of nodes in the graph.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      order: identical method
 |      __len__: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.number_of_nodes()
 |      3
 |
 |  order(self)
 |      Returns the number of nodes in the graph.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      number_of_nodes: identical method
 |      __len__: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.order()
 |      3
 |
 |  size(self, weight=None)
 |      Returns the number of edges or total of all edge weights.
 |
 |      Parameters
 |      ----------
 |      weight : string or None, optional (default=None)
 |          The edge attribute that holds the numerical value used
 |          as a weight. If None, then each edge has weight 1.
 |
 |      Returns
 |      -------
 |      size : numeric
 |          The number of edges or
 |          (if weight keyword is provided) the total weight sum.
 |
 |          If weight is None, returns an int. Otherwise a float
 |          (or more general numeric if the weights are more general).
 |
 |      See Also
 |      --------
 |      number_of_edges
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.size()
 |      3
 |
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_edge("a", "b", weight=2)
 |      >>> G.add_edge("b", "c", weight=4)
 |      >>> G.size()
 |      2
 |      >>> G.size(weight="weight")
 |      6.0
 |
 |  subgraph(self, nodes)
 |      Returns a SubGraph view of the subgraph induced on `nodes`.
 |
 |      The induced subgraph of the graph contains the nodes in `nodes`
 |      and the edges between those nodes.
 |
 |      Parameters
 |      ----------
 |      nodes : list, iterable
 |          A container of nodes which will be iterated through once.
 |
 |      Returns
 |      -------
 |      G : SubGraph View
 |          A subgraph view of the graph. The graph structure cannot be
 |          changed but node/edge attributes can and are shared with the
 |          original graph.
 |
 |      Notes
 |      -----
 |      The graph, edge and node attributes are shared with the original graph.
 |      Changes to the graph structure is ruled out by the view, but changes
 |      to attributes are reflected in the original graph.
 |
 |      To create a subgraph with its own copy of the edge/node attributes use:
 |      G.subgraph(nodes).copy()
 |
 |      For an inplace reduction of a graph to a subgraph you can remove nodes:
 |      G.remove_nodes_from([n for n in G if n not in set(nodes)])
 |
 |      Subgraph views are sometimes NOT what you want. In most cases where
 |      you want to do more than simply look at the induced edges, it makes
 |      more sense to just create the subgraph as its own graph with code like:
 |
 |      ::
 |
 |          # Create a subgraph SG based on a (possibly multigraph) G
 |          SG = G.__class__()
 |          SG.add_nodes_from((n, G.nodes[n]) for n in largest_wcc)
 |          if SG.is_multigraph():
 |              SG.add_edges_from(
 |                  (n, nbr, key, d)
 |                  for n, nbrs in G.adj.items()
 |                  if n in largest_wcc
 |                  for nbr, keydict in nbrs.items()
 |                  if nbr in largest_wcc
 |                  for key, d in keydict.items()
 |              )
 |          else:
 |              SG.add_edges_from(
 |                  (n, nbr, d)
 |                  for n, nbrs in G.adj.items()
 |                  if n in largest_wcc
 |                  for nbr, d in nbrs.items()
 |                  if nbr in largest_wcc
 |              )
 |          SG.graph.update(G.graph)
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> H = G.subgraph([0, 1, 2])
 |      >>> list(H.edges)
 |      [(0, 1), (1, 2)]
 |
 |  update(self, edges=None, nodes=None)
 |      Update the graph using nodes/edges/graphs as input.
 |
 |      Like dict.update, this method takes a graph as input, adding the
 |      graph's nodes and edges to this graph. It can also take two inputs:
 |      edges and nodes. Finally it can take either edges or nodes.
 |      To specify only nodes the keyword `nodes` must be used.
 |
 |      The collections of edges and nodes are treated similarly to
 |      the add_edges_from/add_nodes_from methods. When iterated, they
 |      should yield 2-tuples (u, v) or 3-tuples (u, v, datadict).
 |
 |      Parameters
 |      ----------
 |      edges : Graph object, collection of edges, or None
 |          The first parameter can be a graph or some edges. If it has
 |          attributes `nodes` and `edges`, then it is taken to be a
 |          Graph-like object and those attributes are used as collections
 |          of nodes and edges to be added to the graph.
 |          If the first parameter does not have those attributes, it is
 |          treated as a collection of edges and added to the graph.
 |          If the first argument is None, no edges are added.
 |      nodes : collection of nodes, or None
 |          The second parameter is treated as a collection of nodes
 |          to be added to the graph unless it is None.
 |          If `edges is None` and `nodes is None` an exception is raised.
 |          If the first parameter is a Graph, then `nodes` is ignored.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(5)
 |      >>> G.update(nx.complete_graph(range(4, 10)))
 |      >>> from itertools import combinations
 |      >>> edges = (
 |      ...     (u, v, {"power": u * v})
 |      ...     for u, v in combinations(range(10, 20), 2)
 |      ...     if u * v < 225
 |      ... )
 |      >>> nodes = [1000]  # for singleton, use a container
 |      >>> G.update(edges, nodes)
 |
 |      Notes
 |      -----
 |      It you want to update the graph using an adjacency structure
 |      it is straightforward to obtain the edges/nodes from adjacency.
 |      The following examples provide common cases, your adjacency may
 |      be slightly different and require tweaks of these examples::
 |
 |      >>> # dict-of-set/list/tuple
 |      >>> adj = {1: {2, 3}, 2: {1, 3}, 3: {1, 2}}
 |      >>> e = [(u, v) for u, nbrs in adj.items() for v in nbrs]
 |      >>> G.update(edges=e, nodes=adj)
 |
 |      >>> DG = nx.DiGraph()
 |      >>> # dict-of-dict-of-attribute
 |      >>> adj = {1: {2: 1.3, 3: 0.7}, 2: {1: 1.4}, 3: {1: 0.7}}
 |      >>> e = [
 |      ...     (u, v, {"weight": d})
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, d in nbrs.items()
 |      ... ]
 |      >>> DG.update(edges=e, nodes=adj)
 |
 |      >>> # dict-of-dict-of-dict
 |      >>> adj = {1: {2: {"weight": 1.3}, 3: {"color": 0.7, "weight": 1.2}}}
 |      >>> e = [
 |      ...     (u, v, {"weight": d})
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, d in nbrs.items()
 |      ... ]
 |      >>> DG.update(edges=e, nodes=adj)
 |
 |      >>> # predecessor adjacency (dict-of-set)
 |      >>> pred = {1: {2, 3}, 2: {3}, 3: {3}}
 |      >>> e = [(v, u) for u, nbrs in pred.items() for v in nbrs]
 |
 |      >>> # MultiGraph dict-of-dict-of-dict-of-attribute
 |      >>> MDG = nx.MultiDiGraph()
 |      >>> adj = {
 |      ...     1: {2: {0: {"weight": 1.3}, 1: {"weight": 1.2}}},
 |      ...     3: {2: {0: {"weight": 0.7}}},
 |      ... }
 |      >>> e = [
 |      ...     (u, v, ekey, d)
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, keydict in nbrs.items()
 |      ...     for ekey, d in keydict.items()
 |      ... ]
 |      >>> MDG.update(edges=e)
 |
 |      See Also
 |      --------
 |      add_edges_from: add multiple edges to a graph
 |      add_nodes_from: add multiple nodes to a graph
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from networkx.classes.graph.Graph:
 |
 |  __dict__
 |      dictionary for instance variables
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  name
 |      String identifier of the graph.
 |
 |      This graph attribute appears in the attribute dict G.graph
 |      keyed by the string `"name"`. as well as an attribute (technically
 |      a property) `G.name`. This is entirely user controlled.
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes inherited from networkx.classes.graph.Graph:
 |
 |  __networkx_backend__ = 'networkx'
 |
 |  adjlist_inner_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  adjlist_outer_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  edge_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  graph_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  node_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  node_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
networkx.MultiGraph
Python Library Documentation: class MultiGraph in module networkx.classes.multigraph

class MultiGraph(networkx.classes.graph.Graph)
 |  MultiGraph(incoming_graph_data=None, multigraph_input=None, **attr)
 |
 |  An undirected graph class that can store multiedges.
 |
 |  Multiedges are multiple edges between two nodes.  Each edge
 |  can hold optional data or attributes.
 |
 |  A MultiGraph holds undirected edges.  Self loops are allowed.
 |
 |  Nodes can be arbitrary (hashable) Python objects with optional
 |  key/value attributes. By convention `None` is not used as a node.
 |
 |  Edges are represented as links between nodes with optional
 |  key/value attributes, in a MultiGraph each edge has a key to
 |  distinguish between multiple edges that have the same source and
 |  destination nodes.
 |
 |  Parameters
 |  ----------
 |  incoming_graph_data : input graph (optional, default: None)
 |      Data to initialize graph. If None (default) an empty
 |      graph is created.  The data can be any format that is supported
 |      by the to_networkx_graph() function, currently including edge list,
 |      dict of dicts, dict of lists, NetworkX graph, 2D NumPy array,
 |      SciPy sparse array, or PyGraphviz graph.
 |
 |  multigraph_input : bool or None (default None)
 |      Note: Only used when `incoming_graph_data` is a dict.
 |      If True, `incoming_graph_data` is assumed to be a
 |      dict-of-dict-of-dict-of-dict structure keyed by
 |      node to neighbor to edge keys to edge data for multi-edges.
 |      A NetworkXError is raised if this is not the case.
 |      If False, :func:`to_networkx_graph` is used to try to determine
 |      the dict's graph data structure as either a dict-of-dict-of-dict
 |      keyed by node to neighbor to edge data, or a dict-of-iterable
 |      keyed by node to neighbors.
 |      If None, the treatment for True is tried, but if it fails,
 |      the treatment for False is tried.
 |
 |  attr : keyword arguments, optional (default= no attributes)
 |      Attributes to add to graph as key=value pairs.
 |
 |  See Also
 |  --------
 |  Graph
 |  DiGraph
 |  MultiDiGraph
 |
 |  Examples
 |  --------
 |  Create an empty graph structure (a "null graph") with no nodes and
 |  no edges.
 |
 |  >>> G = nx.MultiGraph()
 |
 |  G can be grown in several ways.
 |
 |  **Nodes:**
 |
 |  Add one node at a time:
 |
 |  >>> G.add_node(1)
 |
 |  Add the nodes from any container (a list, dict, set or
 |  even the lines from a file or the nodes from another graph).
 |
 |  >>> G.add_nodes_from([2, 3])
 |  >>> G.add_nodes_from(range(100, 110))
 |  >>> H = nx.path_graph(10)
 |  >>> G.add_nodes_from(H)
 |
 |  In addition to strings and integers any hashable Python object
 |  (except None) can represent a node, e.g. a customized node object,
 |  or even another Graph.
 |
 |  >>> G.add_node(H)
 |
 |  **Edges:**
 |
 |  G can also be grown by adding edges.
 |
 |  Add one edge,
 |
 |  >>> key = G.add_edge(1, 2)
 |
 |  a list of edges,
 |
 |  >>> keys = G.add_edges_from([(1, 2), (1, 3)])
 |
 |  or a collection of edges,
 |
 |  >>> keys = G.add_edges_from(H.edges)
 |
 |  If some edges connect nodes not yet in the graph, the nodes
 |  are added automatically.  If an edge already exists, an additional
 |  edge is created and stored using a key to identify the edge.
 |  By default the key is the lowest unused integer.
 |
 |  >>> keys = G.add_edges_from([(4, 5, {"route": 28}), (4, 5, {"route": 37})])
 |  >>> G[4]
 |  AdjacencyView({3: {0: {}}, 5: {0: {}, 1: {'route': 28}, 2: {'route': 37}}})
 |
 |  **Attributes:**
 |
 |  Each graph, node, and edge can hold key/value attribute pairs
 |  in an associated attribute dictionary (the keys must be hashable).
 |  By default these are empty, but can be added or changed using
 |  add_edge, add_node or direct manipulation of the attribute
 |  dictionaries named graph, node and edge respectively.
 |
 |  >>> G = nx.MultiGraph(day="Friday")
 |  >>> G.graph
 |  {'day': 'Friday'}
 |
 |  Add node attributes using add_node(), add_nodes_from() or G.nodes
 |
 |  >>> G.add_node(1, time="5pm")
 |  >>> G.add_nodes_from([3], time="2pm")
 |  >>> G.nodes[1]
 |  {'time': '5pm'}
 |  >>> G.nodes[1]["room"] = 714
 |  >>> del G.nodes[1]["room"]  # remove attribute
 |  >>> list(G.nodes(data=True))
 |  [(1, {'time': '5pm'}), (3, {'time': '2pm'})]
 |
 |  Add edge attributes using add_edge(), add_edges_from(), subscript
 |  notation, or G.edges.
 |
 |  >>> key = G.add_edge(1, 2, weight=4.7)
 |  >>> keys = G.add_edges_from([(3, 4), (4, 5)], color="red")
 |  >>> keys = G.add_edges_from([(1, 2, {"color": "blue"}), (2, 3, {"weight": 8})])
 |  >>> G[1][2][0]["weight"] = 4.7
 |  >>> G.edges[1, 2, 0]["weight"] = 4
 |
 |  Warning: we protect the graph data structure by making `G.edges[1,
 |  2, 0]` a read-only dict-like structure. However, you can assign to
 |  attributes in e.g. `G.edges[1, 2, 0]`. Thus, use 2 sets of brackets
 |  to add/change data attributes: `G.edges[1, 2, 0]['weight'] = 4`.
 |
 |  **Shortcuts:**
 |
 |  Many common graph features allow python syntax to speed reporting.
 |
 |  >>> 1 in G  # check if node in graph
 |  True
 |  >>> [n for n in G if n < 3]  # iterate through nodes
 |  [1, 2]
 |  >>> len(G)  # number of nodes in graph
 |  5
 |  >>> G[1]  # adjacency dict-like view mapping neighbor -> edge key -> edge attributes
 |  AdjacencyView({2: {0: {'weight': 4}, 1: {'color': 'blue'}}})
 |
 |  Often the best way to traverse all edges of a graph is via the neighbors.
 |  The neighbors are reported as an adjacency-dict `G.adj` or `G.adjacency()`.
 |
 |  >>> for n, nbrsdict in G.adjacency():
 |  ...     for nbr, keydict in nbrsdict.items():
 |  ...         for key, eattr in keydict.items():
 |  ...             if "weight" in eattr:
 |  ...                 # Do something useful with the edges
 |  ...                 pass
 |
 |  But the edges() method is often more convenient:
 |
 |  >>> for u, v, keys, weight in G.edges(data="weight", keys=True):
 |  ...     if weight is not None:
 |  ...         # Do something useful with the edges
 |  ...         pass
 |
 |  **Reporting:**
 |
 |  Simple graph information is obtained using methods and object-attributes.
 |  Reporting usually provides views instead of containers to reduce memory
 |  usage. The views update as the graph is updated similarly to dict-views.
 |  The objects `nodes`, `edges` and `adj` provide access to data attributes
 |  via lookup (e.g. `nodes[n]`, `edges[u, v, k]`, `adj[u][v]`) and iteration
 |  (e.g. `nodes.items()`, `nodes.data('color')`,
 |  `nodes.data('color', default='blue')` and similarly for `edges`)
 |  Views exist for `nodes`, `edges`, `neighbors()`/`adj` and `degree`.
 |
 |  For details on these and other miscellaneous methods, see below.
 |
 |  **Subclasses (Advanced):**
 |
 |  The MultiGraph class uses a dict-of-dict-of-dict-of-dict data structure.
 |  The outer dict (node_dict) holds adjacency information keyed by node.
 |  The next dict (adjlist_dict) represents the adjacency information
 |  and holds edge_key dicts keyed by neighbor. The edge_key dict holds
 |  each edge_attr dict keyed by edge key. The inner dict
 |  (edge_attr_dict) represents the edge data and holds edge attribute
 |  values keyed by attribute names.
 |
 |  Each of these four dicts in the dict-of-dict-of-dict-of-dict
 |  structure can be replaced by a user defined dict-like object.
 |  In general, the dict-like features should be maintained but
 |  extra features can be added. To replace one of the dicts create
 |  a new graph class by changing the class(!) variable holding the
 |  factory for that dict-like structure. The variable names are
 |  node_dict_factory, node_attr_dict_factory, adjlist_inner_dict_factory,
 |  adjlist_outer_dict_factory, edge_key_dict_factory, edge_attr_dict_factory
 |  and graph_attr_dict_factory.
 |
 |  node_dict_factory : function, (default: dict)
 |      Factory function to be used to create the dict containing node
 |      attributes, keyed by node id.
 |      It should require no arguments and return a dict-like object
 |
 |  node_attr_dict_factory: function, (default: dict)
 |      Factory function to be used to create the node attribute
 |      dict which holds attribute values keyed by attribute name.
 |      It should require no arguments and return a dict-like object
 |
 |  adjlist_outer_dict_factory : function, (default: dict)
 |      Factory function to be used to create the outer-most dict
 |      in the data structure that holds adjacency info keyed by node.
 |      It should require no arguments and return a dict-like object.
 |
 |  adjlist_inner_dict_factory : function, (default: dict)
 |      Factory function to be used to create the adjacency list
 |      dict which holds multiedge key dicts keyed by neighbor.
 |      It should require no arguments and return a dict-like object.
 |
 |  edge_key_dict_factory : function, (default: dict)
 |      Factory function to be used to create the edge key dict
 |      which holds edge data keyed by edge key.
 |      It should require no arguments and return a dict-like object.
 |
 |  edge_attr_dict_factory : function, (default: dict)
 |      Factory function to be used to create the edge attribute
 |      dict which holds attribute values keyed by attribute name.
 |      It should require no arguments and return a dict-like object.
 |
 |  graph_attr_dict_factory : function, (default: dict)
 |      Factory function to be used to create the graph attribute
 |      dict which holds attribute values keyed by attribute name.
 |      It should require no arguments and return a dict-like object.
 |
 |  Typically, if your extension doesn't impact the data structure all
 |  methods will inherited without issue except: `to_directed/to_undirected`.
 |  By default these methods create a DiGraph/Graph class and you probably
 |  want them to create your extension of a DiGraph/Graph. To facilitate
 |  this we define two class variables that you can set in your subclass.
 |
 |  to_directed_class : callable, (default: DiGraph or MultiDiGraph)
 |      Class to create a new graph structure in the `to_directed` method.
 |      If `None`, a NetworkX class (DiGraph or MultiDiGraph) is used.
 |
 |  to_undirected_class : callable, (default: Graph or MultiGraph)
 |      Class to create a new graph structure in the `to_undirected` method.
 |      If `None`, a NetworkX class (Graph or MultiGraph) is used.
 |
 |  **Subclassing Example**
 |
 |  Create a low memory graph class that effectively disallows edge
 |  attributes by using a single attribute dict for all edges.
 |  This reduces the memory used, but you lose edge attributes.
 |
 |  >>> class ThinGraph(nx.Graph):
 |  ...     all_edge_dict = {"weight": 1}
 |  ...
 |  ...     def single_edge_dict(self):
 |  ...         return self.all_edge_dict
 |  ...
 |  ...     edge_attr_dict_factory = single_edge_dict
 |  >>> G = ThinGraph()
 |  >>> G.add_edge(2, 1)
 |  >>> G[2][1]
 |  {'weight': 1}
 |  >>> G.add_edge(2, 2)
 |  >>> G[2][1] is G[2][2]
 |  True
 |
 |  Method resolution order:
 |      MultiGraph
 |      networkx.classes.graph.Graph
 |      builtins.object
 |
 |  Methods defined here:
 |
 |  __init__(self, incoming_graph_data=None, multigraph_input=None, **attr)
 |      Initialize a graph with edges, name, or graph attributes.
 |
 |      Parameters
 |      ----------
 |      incoming_graph_data : input graph
 |          Data to initialize graph.  If incoming_graph_data=None (default)
 |          an empty graph is created.  The data can be an edge list, or any
 |          NetworkX graph object.  If the corresponding optional Python
 |          packages are installed the data can also be a 2D NumPy array, a
 |          SciPy sparse array, or a PyGraphviz graph.
 |
 |      multigraph_input : bool or None (default None)
 |          Note: Only used when `incoming_graph_data` is a dict.
 |          If True, `incoming_graph_data` is assumed to be a
 |          dict-of-dict-of-dict-of-dict structure keyed by
 |          node to neighbor to edge keys to edge data for multi-edges.
 |          A NetworkXError is raised if this is not the case.
 |          If False, :func:`to_networkx_graph` is used to try to determine
 |          the dict's graph data structure as either a dict-of-dict-of-dict
 |          keyed by node to neighbor to edge data, or a dict-of-iterable
 |          keyed by node to neighbors.
 |          If None, the treatment for True is tried, but if it fails,
 |          the treatment for False is tried.
 |
 |      attr : keyword arguments, optional (default= no attributes)
 |          Attributes to add to graph as key=value pairs.
 |
 |      See Also
 |      --------
 |      convert
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiGraph()
 |      >>> G = nx.MultiGraph(name="my graph")
 |      >>> e = [(1, 2), (1, 2), (2, 3), (3, 4)]  # list of edges
 |      >>> G = nx.MultiGraph(e)
 |
 |      Arbitrary graph attribute pairs (key=value) may be assigned
 |
 |      >>> G = nx.MultiGraph(e, day="Friday")
 |      >>> G.graph
 |      {'day': 'Friday'}
 |
 |  add_edge(self, u_for_edge, v_for_edge, key=None, **attr)
 |      Add an edge between u and v.
 |
 |      The nodes u and v will be automatically added if they are
 |      not already in the graph.
 |
 |      Edge attributes can be specified with keywords or by directly
 |      accessing the edge's attribute dictionary. See examples below.
 |
 |      Parameters
 |      ----------
 |      u_for_edge, v_for_edge : nodes
 |          Nodes can be, for example, strings or numbers.
 |          Nodes must be hashable (and not None) Python objects.
 |      key : hashable identifier, optional (default=lowest unused integer)
 |          Used to distinguish multiedges between a pair of nodes.
 |      attr : keyword arguments, optional
 |          Edge data (or labels or objects) can be assigned using
 |          keyword arguments.
 |
 |      Returns
 |      -------
 |      The edge key assigned to the edge.
 |
 |      See Also
 |      --------
 |      add_edges_from : add a collection of edges
 |
 |      Notes
 |      -----
 |      To replace/update edge data, use the optional key argument
 |      to identify a unique edge.  Otherwise a new edge will be created.
 |
 |      NetworkX algorithms designed for weighted graphs cannot use
 |      multigraphs directly because it is not clear how to handle
 |      multiedge weights.  Convert to Graph using edge attribute
 |      'weight' to enable weighted graph algorithms.
 |
 |      Default keys are generated using the method `new_edge_key()`.
 |      This method can be overridden by subclassing the base class and
 |      providing a custom `new_edge_key()` method.
 |
 |      Examples
 |      --------
 |      The following each add an additional edge e=(1, 2) to graph G:
 |
 |      >>> G = nx.MultiGraph()
 |      >>> e = (1, 2)
 |      >>> ekey = G.add_edge(1, 2)  # explicit two-node form
 |      >>> G.add_edge(*e)  # single edge as tuple of two nodes
 |      1
 |      >>> G.add_edges_from([(1, 2)])  # add edges from iterable container
 |      [2]
 |
 |      Associate data to edges using keywords:
 |
 |      >>> ekey = G.add_edge(1, 2, weight=3)
 |      >>> ekey = G.add_edge(1, 2, key=0, weight=4)  # update data for key=0
 |      >>> ekey = G.add_edge(1, 3, weight=7, capacity=15, length=342.7)
 |
 |      For non-string attribute keys, use subscript notation.
 |
 |      >>> ekey = G.add_edge(1, 2)
 |      >>> G[1][2][0].update({0: 5})
 |      >>> G.edges[1, 2, 0].update({0: 5})
 |
 |  add_edges_from(self, ebunch_to_add, **attr)
 |      Add all the edges in ebunch_to_add.
 |
 |      Parameters
 |      ----------
 |      ebunch_to_add : container of edges
 |          Each edge given in the container will be added to the
 |          graph. The edges can be:
 |
 |              - 2-tuples (u, v) or
 |              - 3-tuples (u, v, d) for an edge data dict d, or
 |              - 3-tuples (u, v, k) for not iterable key k, or
 |              - 4-tuples (u, v, k, d) for an edge with data and key k
 |
 |      attr : keyword arguments, optional
 |          Edge data (or labels or objects) can be assigned using
 |          keyword arguments.
 |
 |      Returns
 |      -------
 |      A list of edge keys assigned to the edges in `ebunch`.
 |
 |      See Also
 |      --------
 |      add_edge : add a single edge
 |      add_weighted_edges_from : convenient way to add weighted edges
 |
 |      Notes
 |      -----
 |      Adding the same edge twice has no effect but any edge data
 |      will be updated when each duplicate edge is added.
 |
 |      Edge attributes specified in an ebunch take precedence over
 |      attributes specified via keyword arguments.
 |
 |      Default keys are generated using the method ``new_edge_key()``.
 |      This method can be overridden by subclassing the base class and
 |      providing a custom ``new_edge_key()`` method.
 |
 |      When adding edges from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_edges)`, and pass this
 |      object to `G.add_edges_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_edges_from([(0, 1), (1, 2)])  # using a list of edge tuples
 |      >>> e = zip(range(0, 3), range(1, 4))
 |      >>> G.add_edges_from(e)  # Add the path graph 0-1-2-3
 |
 |      Associate data to edges
 |
 |      >>> G.add_edges_from([(1, 2), (2, 3)], weight=3)
 |      >>> G.add_edges_from([(3, 4), (1, 4)], label="WN2898")
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.MultiGraph([(1, 2), (2, 3), (3, 4)])
 |      >>> # Grow graph by one new node, adding edges to all existing nodes.
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_edges_from(((5, n) for n in G.nodes))
 |      >>> # right way - note that there will be no self-edge for node 5
 |      >>> assigned_keys = G.add_edges_from(list((5, n) for n in G.nodes))
 |
 |  adj = <functools.cached_property object>
 |      Graph adjacency object holding the neighbors of each node.
 |
 |      This object is a read-only dict-like structure with node keys
 |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
 |      to the edgekey-data-dict.  So `G.adj[3][2][0]['color'] = 'blue'` sets
 |      the color of the edge `(3, 2, 0)` to `"blue"`.
 |
 |      Iterating over G.adj behaves like a dict. Useful idioms include
 |      `for nbr, edgesdict in G.adj[n].items():`.
 |
 |      The neighbor information is also provided by subscripting the graph.
 |
 |      Examples
 |      --------
 |      >>> e = [(1, 2), (1, 2), (1, 3), (3, 4)]  # list of edges
 |      >>> G = nx.MultiGraph(e)
 |      >>> G.edges[1, 2, 0]["weight"] = 3
 |      >>> result = set()
 |      >>> for edgekey, data in G[1][2].items():
 |      ...     result.add(data.get("weight", 1))
 |      >>> result
 |      {1, 3}
 |
 |      For directed graphs, `G.adj` holds outgoing (successor) info.
 |
 |  copy(self, as_view=False)
 |      Returns a copy of the graph.
 |
 |      The copy method by default returns an independent shallow copy
 |      of the graph and attributes. That is, if an attribute is a
 |      container, that container is shared by the original an the copy.
 |      Use Python's `copy.deepcopy` for new containers.
 |
 |      If `as_view` is True then a view is returned instead of a copy.
 |
 |      Notes
 |      -----
 |      All copies reproduce the graph structure, but data attributes
 |      may be handled in different ways. There are four types of copies
 |      of a graph that people might want.
 |
 |      Deepcopy -- A "deepcopy" copies the graph structure as well as
 |      all data attributes and any objects they might contain.
 |      The entire graph object is new so that changes in the copy
 |      do not affect the original object. (see Python's copy.deepcopy)
 |
 |      Data Reference (Shallow) -- For a shallow copy the graph structure
 |      is copied but the edge, node and graph attribute dicts are
 |      references to those in the original graph. This saves
 |      time and memory but could cause confusion if you change an attribute
 |      in one graph and it changes the attribute in the other.
 |      NetworkX does not provide this level of shallow copy.
 |
 |      Independent Shallow -- This copy creates new independent attribute
 |      dicts and then does a shallow copy of the attributes. That is, any
 |      attributes that are containers are shared between the new graph
 |      and the original. This is exactly what `dict.copy()` provides.
 |      You can obtain this style copy using:
 |
 |          >>> G = nx.path_graph(5)
 |          >>> H = G.copy()
 |          >>> H = G.copy(as_view=False)
 |          >>> H = nx.Graph(G)
 |          >>> H = G.__class__(G)
 |
 |      Fresh Data -- For fresh data, the graph structure is copied while
 |      new empty data attribute dicts are created. The resulting graph
 |      is independent of the original and it has no edge, node or graph
 |      attributes. Fresh copies are not enabled. Instead use:
 |
 |          >>> H = G.__class__()
 |          >>> H.add_nodes_from(G)
 |          >>> H.add_edges_from(G.edges)
 |
 |      View -- Inspired by dict-views, graph-views act like read-only
 |      versions of the original graph, providing a copy of the original
 |      structure without requiring any memory for copying the information.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Parameters
 |      ----------
 |      as_view : bool, optional (default=False)
 |          If True, the returned graph-view provides a read-only view
 |          of the original graph without actually copying any data.
 |
 |      Returns
 |      -------
 |      G : Graph
 |          A copy of the graph.
 |
 |      See Also
 |      --------
 |      to_directed: return a directed copy of the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> H = G.copy()
 |
 |  degree = <functools.cached_property object>
 |      A DegreeView for the Graph as G.degree or G.degree().
 |
 |      The node degree is the number of edges adjacent to the node.
 |      The weighted node degree is the sum of the edge weights for
 |      edges incident to that node.
 |
 |      This object provides an iterator for (node, degree) as well as
 |      lookup for the degree for a single node.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      weight : string or None, optional (default=None)
 |         The name of an edge attribute that holds the numerical value used
 |         as a weight.  If None, then each edge has weight 1.
 |         The degree is the sum of the edge weights adjacent to the node.
 |
 |      Returns
 |      -------
 |      MultiDegreeView or int
 |          If multiple nodes are requested (the default), returns a `MultiDegreeView`
 |          mapping nodes to their degree.
 |          If a single node is requested, returns the degree of the node as an integer.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.degree(0)  # node 0 with degree 1
 |      1
 |      >>> list(G.degree([0, 1]))
 |      [(0, 1), (1, 2)]
 |
 |  edges = <functools.cached_property object>
 |      Returns an iterator over the edges.
 |
 |      edges(self, nbunch=None, data=False, keys=False, default=None)
 |
 |      The MultiEdgeView provides set-like operations on the edge-tuples
 |      as well as edge attribute lookup. When called, it also provides
 |      an EdgeDataView object which allows control of access to edge
 |      attributes (but does not provide set-like operations).
 |      Hence, ``G.edges[u, v, k]['color']`` provides the value of the color
 |      attribute for the edge from ``u`` to ``v`` with key ``k`` while
 |      ``for (u, v, k, c) in G.edges(data='color', keys=True, default="red"):``
 |      iterates through all the edges yielding the color attribute with
 |      default `'red'` if no color attribute exists.
 |
 |      Edges are returned as tuples with optional data and keys
 |      in the order (node, neighbor, key, data). If ``keys=True`` is not
 |      provided, the tuples will just be (node, neighbor, data), but
 |      multiple tuples with the same node and neighbor will be generated
 |      when multiple edges exist between two nodes.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges from these nodes.
 |      data : string or bool, optional (default=False)
 |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
 |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
 |          If False, return 2-tuple (u, v).
 |      keys : bool, optional (default=False)
 |          If True, return edge keys with each edge, creating (u, v, k)
 |          tuples or (u, v, k, d) tuples if data is also requested.
 |      default : value, optional (default=None)
 |          Value used for edges that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      edges : MultiEdgeView
 |          A view of edge attributes, usually it iterates over (u, v)
 |          (u, v, k) or (u, v, k, d) tuples of edges, but can also be
 |          used for attribute lookup as ``edges[u, v, k]['foo']``.
 |
 |      Notes
 |      -----
 |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
 |      For directed graphs this returns the out-edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiGraph()
 |      >>> nx.add_path(G, [0, 1, 2])
 |      >>> key = G.add_edge(2, 3, weight=5)
 |      >>> key2 = G.add_edge(2, 1, weight=2)  # multi-edge
 |      >>> [e for e in G.edges()]
 |      [(0, 1), (1, 2), (1, 2), (2, 3)]
 |      >>> G.edges.data()  # default data is {} (empty dict)
 |      MultiEdgeDataView([(0, 1, {}), (1, 2, {}), (1, 2, {'weight': 2}), (2, 3, {'weight': 5})])
 |      >>> G.edges.data("weight", default=1)
 |      MultiEdgeDataView([(0, 1, 1), (1, 2, 1), (1, 2, 2), (2, 3, 5)])
 |      >>> G.edges(keys=True)  # default keys are integers
 |      MultiEdgeView([(0, 1, 0), (1, 2, 0), (1, 2, 1), (2, 3, 0)])
 |      >>> G.edges.data(keys=True)
 |      MultiEdgeDataView([(0, 1, 0, {}), (1, 2, 0, {}), (1, 2, 1, {'weight': 2}), (2, 3, 0, {'weight': 5})])
 |      >>> G.edges.data("weight", default=1, keys=True)
 |      MultiEdgeDataView([(0, 1, 0, 1), (1, 2, 0, 1), (1, 2, 1, 2), (2, 3, 0, 5)])
 |      >>> G.edges([0, 3])  # Note ordering of tuples from listed sources
 |      MultiEdgeDataView([(0, 1), (3, 2)])
 |      >>> G.edges([0, 3, 2, 1])  # Note ordering of tuples
 |      MultiEdgeDataView([(0, 1), (3, 2), (2, 1), (2, 1)])
 |      >>> G.edges(0)
 |      MultiEdgeDataView([(0, 1)])
 |
 |  get_edge_data(self, u, v, key=None, default=None)
 |      Returns the attribute dictionary associated with edge (u, v,
 |      key).
 |
 |      If a key is not provided, returns a dictionary mapping edge keys
 |      to attribute dictionaries for each edge between u and v.
 |
 |      This is identical to `G[u][v][key]` except the default is returned
 |      instead of an exception is the edge doesn't exist.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |
 |      default :  any Python object (default=None)
 |          Value to return if the specific edge (u, v, key) is not
 |          found, OR if there are no edges between u and v and no key
 |          is specified.
 |
 |      key : hashable identifier, optional (default=None)
 |          Return data only for the edge with specified key, as an
 |          attribute dictionary (rather than a dictionary mapping keys
 |          to attribute dictionaries).
 |
 |      Returns
 |      -------
 |      edge_dict : dictionary
 |          The edge attribute dictionary, OR a dictionary mapping edge
 |          keys to attribute dictionaries for each of those edges if no
 |          specific key is provided (even if there's only one edge
 |          between u and v).
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiGraph()  # or MultiDiGraph
 |      >>> key = G.add_edge(0, 1, key="a", weight=7)
 |      >>> G[0][1]["a"]  # key='a'
 |      {'weight': 7}
 |      >>> G.edges[0, 1, "a"]  # key='a'
 |      {'weight': 7}
 |
 |      Warning: we protect the graph data structure by making
 |      `G.edges` and `G[1][2]` read-only dict-like structures.
 |      However, you can assign values to attributes in e.g.
 |      `G.edges[1, 2, 'a']` or `G[1][2]['a']` using an additional
 |      bracket as shown next. You need to specify all edge info
 |      to assign to the edge data associated with an edge.
 |
 |      >>> G[0][1]["a"]["weight"] = 10
 |      >>> G.edges[0, 1, "a"]["weight"] = 10
 |      >>> G[0][1]["a"]["weight"]
 |      10
 |      >>> G.edges[1, 0, "a"]["weight"]
 |      10
 |
 |      >>> G = nx.MultiGraph()  # or MultiDiGraph
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.edges[0, 1, 0]["weight"] = 5
 |      >>> G.get_edge_data(0, 1)
 |      {0: {'weight': 5}}
 |      >>> e = (0, 1)
 |      >>> G.get_edge_data(*e)  # tuple form
 |      {0: {'weight': 5}}
 |      >>> G.get_edge_data(3, 0)  # edge not in graph, returns None
 |      >>> G.get_edge_data(3, 0, default=0)  # edge not in graph, return default
 |      0
 |      >>> G.get_edge_data(1, 0, 0)  # specific key gives back
 |      {'weight': 5}
 |
 |  has_edge(self, u, v, key=None)
 |      Returns True if the graph has an edge between nodes u and v.
 |
 |      This is the same as `v in G[u] or key in G[u][v]`
 |      without KeyError exceptions.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |          Nodes can be, for example, strings or numbers.
 |
 |      key : hashable identifier, optional (default=None)
 |          If specified return True only if the edge with
 |          key is found.
 |
 |      Returns
 |      -------
 |      edge_ind : bool
 |          True if edge is in the graph, False otherwise.
 |
 |      Examples
 |      --------
 |      Can be called either using two nodes u, v, an edge tuple (u, v),
 |      or an edge tuple (u, v, key).
 |
 |      >>> G = nx.MultiGraph()  # or MultiDiGraph
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.has_edge(0, 1)  # using two nodes
 |      True
 |      >>> e = (0, 1)
 |      >>> G.has_edge(*e)  #  e is a 2-tuple (u, v)
 |      True
 |      >>> G.add_edge(0, 1, key="a")
 |      'a'
 |      >>> G.has_edge(0, 1, key="a")  # specify key
 |      True
 |      >>> G.has_edge(1, 0, key="a")  # edges aren't directed
 |      True
 |      >>> e = (0, 1, "a")
 |      >>> G.has_edge(*e)  # e is a 3-tuple (u, v, 'a')
 |      True
 |
 |      The following syntax are equivalent:
 |
 |      >>> G.has_edge(0, 1)
 |      True
 |      >>> 1 in G[0]  # though this gives :exc:`KeyError` if 0 not in G
 |      True
 |      >>> 0 in G[1]  # other order; also gives :exc:`KeyError` if 0 not in G
 |      True
 |
 |  is_directed(self)
 |      Returns True if graph is directed, False otherwise.
 |
 |  is_multigraph(self)
 |      Returns True if graph is a multigraph, False otherwise.
 |
 |  new_edge_key(self, u, v)
 |      Returns an unused key for edges between nodes `u` and `v`.
 |
 |      The nodes `u` and `v` do not need to be already in the graph.
 |
 |      Notes
 |      -----
 |      In the standard MultiGraph class the new key is the number of existing
 |      edges between `u` and `v` (increased if necessary to ensure unused).
 |      The first edge will have key 0, then 1, etc. If an edge is removed
 |      further new_edge_keys may not be in this order.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |
 |      Returns
 |      -------
 |      key : int
 |
 |  number_of_edges(self, u=None, v=None)
 |      Returns the number of edges between two nodes.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes, optional (Default=all edges)
 |          If u and v are specified, return the number of edges between
 |          u and v. Otherwise return the total number of all edges.
 |
 |      Returns
 |      -------
 |      nedges : int
 |          The number of edges in the graph.  If nodes `u` and `v` are
 |          specified return the number of edges between those nodes. If
 |          the graph is directed, this only returns the number of edges
 |          from `u` to `v`.
 |
 |      See Also
 |      --------
 |      size
 |
 |      Examples
 |      --------
 |      For undirected multigraphs, this method counts the total number
 |      of edges in the graph::
 |
 |          >>> G = nx.MultiGraph()
 |          >>> G.add_edges_from([(0, 1), (0, 1), (1, 2)])
 |          [0, 1, 0]
 |          >>> G.number_of_edges()
 |          3
 |
 |      If you specify two nodes, this counts the total number of edges
 |      joining the two nodes::
 |
 |          >>> G.number_of_edges(0, 1)
 |          2
 |
 |      For directed multigraphs, this method can count the total number
 |      of directed edges from `u` to `v`::
 |
 |          >>> G = nx.MultiDiGraph()
 |          >>> G.add_edges_from([(0, 1), (0, 1), (1, 0)])
 |          [0, 1, 0]
 |          >>> G.number_of_edges(0, 1)
 |          2
 |          >>> G.number_of_edges(1, 0)
 |          1
 |
 |  remove_edge(self, u, v, key=None)
 |      Remove an edge between u and v.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |          Remove an edge between nodes u and v.
 |      key : hashable identifier, optional (default=None)
 |          Used to distinguish multiple edges between a pair of nodes.
 |          If None, remove a single edge between u and v. If there are
 |          multiple edges, removes the last edge added in terms of
 |          insertion order.
 |
 |      Raises
 |      ------
 |      NetworkXError
 |          If there is not an edge between u and v, or
 |          if there is no edge with the specified key.
 |
 |      See Also
 |      --------
 |      remove_edges_from : remove a collection of edges
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiGraph()
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.remove_edge(0, 1)
 |      >>> e = (1, 2)
 |      >>> G.remove_edge(*e)  # unpacks e from an edge tuple
 |
 |      For multiple edges
 |
 |      >>> G = nx.MultiGraph()  # or MultiDiGraph, etc
 |      >>> G.add_edges_from([(1, 2), (1, 2), (1, 2)])  # key_list returned
 |      [0, 1, 2]
 |
 |      When ``key=None`` (the default), edges are removed in the opposite
 |      order that they were added:
 |
 |      >>> G.remove_edge(1, 2)
 |      >>> G.edges(keys=True)
 |      MultiEdgeView([(1, 2, 0), (1, 2, 1)])
 |      >>> G.remove_edge(2, 1)  # edges are not directed
 |      >>> G.edges(keys=True)
 |      MultiEdgeView([(1, 2, 0)])
 |
 |      For edges with keys
 |
 |      >>> G = nx.MultiGraph()
 |      >>> G.add_edge(1, 2, key="first")
 |      'first'
 |      >>> G.add_edge(1, 2, key="second")
 |      'second'
 |      >>> G.remove_edge(1, 2, key="first")
 |      >>> G.edges(keys=True)
 |      MultiEdgeView([(1, 2, 'second')])
 |
 |  remove_edges_from(self, ebunch)
 |      Remove all edges specified in ebunch.
 |
 |      Parameters
 |      ----------
 |      ebunch: list or container of edge tuples
 |          Each edge given in the list or container will be removed
 |          from the graph. The edges can be:
 |
 |              - 2-tuples (u, v) A single edge between u and v is removed.
 |              - 3-tuples (u, v, key) The edge identified by key is removed.
 |              - 4-tuples (u, v, key, data) where data is ignored.
 |
 |      See Also
 |      --------
 |      remove_edge : remove a single edge
 |
 |      Notes
 |      -----
 |      Will fail silently if an edge in ebunch is not in the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> ebunch = [(1, 2), (2, 3)]
 |      >>> G.remove_edges_from(ebunch)
 |
 |      Removing multiple copies of edges
 |
 |      >>> G = nx.MultiGraph()
 |      >>> keys = G.add_edges_from([(1, 2), (1, 2), (1, 2)])
 |      >>> G.remove_edges_from([(1, 2), (2, 1)])  # edges aren't directed
 |      >>> list(G.edges())
 |      [(1, 2)]
 |      >>> G.remove_edges_from([(1, 2), (1, 2)])  # silently ignore extra copy
 |      >>> list(G.edges)  # now empty graph
 |      []
 |
 |      When the edge is a 2-tuple ``(u, v)`` but there are multiple edges between
 |      u and v in the graph, the most recent edge (in terms of insertion
 |      order) is removed.
 |
 |      >>> G = nx.MultiGraph()
 |      >>> for key in ("x", "y", "a"):
 |      ...     k = G.add_edge(0, 1, key=key)
 |      >>> G.edges(keys=True)
 |      MultiEdgeView([(0, 1, 'x'), (0, 1, 'y'), (0, 1, 'a')])
 |      >>> G.remove_edges_from([(0, 1)])
 |      >>> G.edges(keys=True)
 |      MultiEdgeView([(0, 1, 'x'), (0, 1, 'y')])
 |
 |  to_directed(self, as_view=False)
 |      Returns a directed representation of the graph.
 |
 |      Returns
 |      -------
 |      G : MultiDiGraph
 |          A directed graph with the same name, same nodes, and with
 |          each edge (u, v, k, data) replaced by two directed edges
 |          (u, v, k, data) and (v, u, k, data).
 |
 |      Notes
 |      -----
 |      This returns a "deepcopy" of the edge, node, and
 |      graph attributes which attempts to completely copy
 |      all of the data and references.
 |
 |      This is in contrast to the similar D=MultiDiGraph(G) which
 |      returns a shallow copy of the data.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Warning: If you have subclassed MultiGraph to use dict-like objects
 |      in the data structure, those changes do not transfer to the
 |      MultiDiGraph created by this method.
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiGraph()
 |      >>> G.add_edge(0, 1)
 |      0
 |      >>> G.add_edge(0, 1)
 |      1
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1, 0), (0, 1, 1), (1, 0, 0), (1, 0, 1)]
 |
 |      If already directed, return a (deep) copy
 |
 |      >>> G = nx.MultiDiGraph()
 |      >>> G.add_edge(0, 1)
 |      0
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1, 0)]
 |
 |  to_directed_class(self)
 |      Returns the class to use for empty directed copies.
 |
 |      If you subclass the base classes, use this to designate
 |      what directed class to use for `to_directed()` copies.
 |
 |  to_undirected(self, as_view=False)
 |      Returns an undirected copy of the graph.
 |
 |      Returns
 |      -------
 |      G : Graph/MultiGraph
 |          A deepcopy of the graph.
 |
 |      See Also
 |      --------
 |      copy, add_edge, add_edges_from
 |
 |      Notes
 |      -----
 |      This returns a "deepcopy" of the edge, node, and
 |      graph attributes which attempts to completely copy
 |      all of the data and references.
 |
 |      This is in contrast to the similar `G = nx.MultiGraph(D)`
 |      which returns a shallow copy of the data.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Warning: If you have subclassed MultiGraph to use dict-like
 |      objects in the data structure, those changes do not transfer
 |      to the MultiGraph created by this method.
 |
 |      Examples
 |      --------
 |      >>> G = nx.MultiGraph([(0, 1), (0, 1), (1, 2)])
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1, 0), (0, 1, 1), (1, 0, 0), (1, 0, 1), (1, 2, 0), (2, 1, 0)]
 |      >>> G2 = H.to_undirected()
 |      >>> list(G2.edges)
 |      [(0, 1, 0), (0, 1, 1), (1, 2, 0)]
 |
 |  to_undirected_class(self)
 |      Returns the class to use for empty undirected copies.
 |
 |      If you subclass the base classes, use this to designate
 |      what directed class to use for `to_directed()` copies.
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes defined here:
 |
 |  edge_key_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from networkx.classes.graph.Graph:
 |
 |  __contains__(self, n)
 |      Returns True if n is a node, False otherwise. Use: 'n in G'.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> 1 in G
 |      True
 |
 |  __getitem__(self, n)
 |      Returns a dict of neighbors of node n.  Use: 'G[n]'.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph.
 |
 |      Returns
 |      -------
 |      adj_dict : dictionary
 |         The adjacency dictionary for nodes connected to n.
 |
 |      Notes
 |      -----
 |      G[n] is the same as G.adj[n] and similar to G.neighbors(n)
 |      (which is an iterator over G.adj[n])
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G[0]
 |      AtlasView({1: {}})
 |
 |  __iter__(self)
 |      Iterate over the nodes. Use: 'for n in G'.
 |
 |      Returns
 |      -------
 |      niter : iterator
 |          An iterator over all nodes in the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> [n for n in G]
 |      [0, 1, 2, 3]
 |      >>> list(G)
 |      [0, 1, 2, 3]
 |
 |  __len__(self)
 |      Returns the number of nodes in the graph. Use: 'len(G)'.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      number_of_nodes: identical method
 |      order: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> len(G)
 |      4
 |
 |  __str__(self)
 |      Returns a short summary of the graph.
 |
 |      Returns
 |      -------
 |      info : string
 |          Graph information including the graph name (if any), graph type, and the
 |          number of nodes and edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph(name="foo")
 |      >>> str(G)
 |      "Graph named 'foo' with 0 nodes and 0 edges"
 |
 |      >>> G = nx.path_graph(3)
 |      >>> str(G)
 |      'Graph with 3 nodes and 2 edges'
 |
 |  add_node(self, node_for_adding, **attr)
 |      Add a single node `node_for_adding` and update node attributes.
 |
 |      Parameters
 |      ----------
 |      node_for_adding : node
 |          A node can be any hashable Python object except None.
 |      attr : keyword arguments, optional
 |          Set or change node attributes using key=value.
 |
 |      See Also
 |      --------
 |      add_nodes_from
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_node(1)
 |      >>> G.add_node("Hello")
 |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
 |      >>> G.add_node(K3)
 |      >>> G.number_of_nodes()
 |      3
 |
 |      Use keywords set/change node attributes:
 |
 |      >>> G.add_node(1, size=10)
 |      >>> G.add_node(3, weight=0.4, UTM=("13S", 382871, 3972649))
 |
 |      Notes
 |      -----
 |      A hashable object is one that can be used as a key in a Python
 |      dictionary. This includes strings, numbers, tuples of strings
 |      and numbers, etc.
 |
 |      On many platforms hashable items also include mutables such as
 |      NetworkX Graphs, though one should be careful that the hash
 |      doesn't change on mutables.
 |
 |  add_nodes_from(self, nodes_for_adding, **attr)
 |      Add multiple nodes.
 |
 |      Parameters
 |      ----------
 |      nodes_for_adding : iterable container
 |          A container of nodes (list, dict, set, etc.).
 |          OR
 |          A container of (node, attribute dict) tuples.
 |          Node attributes are updated using the attribute dict.
 |      attr : keyword arguments, optional (default= no attributes)
 |          Update attributes for all nodes in nodes.
 |          Node attributes specified in nodes as a tuple take
 |          precedence over attributes specified via keyword arguments.
 |
 |      See Also
 |      --------
 |      add_node
 |
 |      Notes
 |      -----
 |      When adding nodes from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
 |      object to `G.add_nodes_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_nodes_from("Hello")
 |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
 |      >>> G.add_nodes_from(K3)
 |      >>> sorted(G.nodes(), key=str)
 |      [0, 1, 2, 'H', 'e', 'l', 'o']
 |
 |      Use keywords to update specific node attributes for every node.
 |
 |      >>> G.add_nodes_from([1, 2], size=10)
 |      >>> G.add_nodes_from([3, 4], weight=0.4)
 |
 |      Use (node, attrdict) tuples to update attributes for specific nodes.
 |
 |      >>> G.add_nodes_from([(1, dict(size=11)), (2, {"color": "blue"})])
 |      >>> G.nodes[1]["size"]
 |      11
 |      >>> H = nx.Graph()
 |      >>> H.add_nodes_from(G.nodes(data=True))
 |      >>> H.nodes[1]["size"]
 |      11
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.Graph([(0, 1), (1, 2), (3, 4)])
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_nodes_from(n + 1 for n in G.nodes)
 |      >>> # correct way
 |      >>> G.add_nodes_from(list(n + 1 for n in G.nodes))
 |
 |  add_weighted_edges_from(self, ebunch_to_add, weight='weight', **attr)
 |      Add weighted edges in `ebunch_to_add` with specified weight attr
 |
 |      Parameters
 |      ----------
 |      ebunch_to_add : container of edges
 |          Each edge given in the list or container will be added
 |          to the graph. The edges must be given as 3-tuples (u, v, w)
 |          where w is a number.
 |      weight : string, optional (default= 'weight')
 |          The attribute name for the edge weights to be added.
 |      attr : keyword arguments, optional (default= no attributes)
 |          Edge attributes to add/update for all edges.
 |
 |      See Also
 |      --------
 |      add_edge : add a single edge
 |      add_edges_from : add multiple edges
 |
 |      Notes
 |      -----
 |      Adding the same edge twice for Graph/DiGraph simply updates
 |      the edge data. For MultiGraph/MultiDiGraph, duplicate edges
 |      are stored.
 |
 |      When adding edges from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_edges)`, and pass this
 |      object to `G.add_weighted_edges_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_weighted_edges_from([(0, 1, 3.0), (1, 2, 7.5)])
 |
 |      Evaluate an iterator over edges before passing it
 |
 |      >>> G = nx.Graph([(1, 2), (2, 3), (3, 4)])
 |      >>> weight = 0.1
 |      >>> # Grow graph by one new node, adding edges to all existing nodes.
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_weighted_edges_from(((5, n, weight) for n in G.nodes))
 |      >>> # correct way - note that there will be no self-edge for node 5
 |      >>> G.add_weighted_edges_from(list((5, n, weight) for n in G.nodes))
 |
 |  adjacency(self)
 |      Returns an iterator over (node, adjacency dict) tuples for all nodes.
 |
 |      For directed graphs, only outgoing neighbors/adjacencies are included.
 |
 |      Returns
 |      -------
 |      adj_iter : iterator
 |         An iterator over (node, adjacency dictionary) for all nodes in
 |         the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> [(n, nbrdict) for n, nbrdict in G.adjacency()]
 |      [(0, {1: {}}), (1, {0: {}, 2: {}}), (2, {1: {}, 3: {}}), (3, {2: {}})]
 |
 |  clear(self)
 |      Remove all nodes and edges from the graph.
 |
 |      This also removes the name, and all graph, node, and edge attributes.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.clear()
 |      >>> list(G.nodes)
 |      []
 |      >>> list(G.edges)
 |      []
 |
 |  clear_edges(self)
 |      Remove all edges from the graph without altering nodes.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.clear_edges()
 |      >>> list(G.nodes)
 |      [0, 1, 2, 3]
 |      >>> list(G.edges)
 |      []
 |
 |  edge_subgraph(self, edges)
 |      Returns the subgraph induced by the specified edges.
 |
 |      The induced subgraph contains each edge in `edges` and each
 |      node incident to any one of those edges.
 |
 |      Parameters
 |      ----------
 |      edges : iterable
 |          An iterable of edges in this graph.
 |
 |      Returns
 |      -------
 |      G : Graph
 |          An edge-induced subgraph of this graph with the same edge
 |          attributes.
 |
 |      Notes
 |      -----
 |      The graph, edge, and node attributes in the returned subgraph
 |      view are references to the corresponding attributes in the original
 |      graph. The view is read-only.
 |
 |      To create a full graph version of the subgraph with its own copy
 |      of the edge or node attributes, use::
 |
 |          G.edge_subgraph(edges).copy()
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(5)
 |      >>> H = G.edge_subgraph([(0, 1), (3, 4)])
 |      >>> list(H.nodes)
 |      [0, 1, 3, 4]
 |      >>> list(H.edges)
 |      [(0, 1), (3, 4)]
 |
 |  has_node(self, n)
 |      Returns True if the graph contains the node n.
 |
 |      Identical to `n in G`
 |
 |      Parameters
 |      ----------
 |      n : node
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.has_node(0)
 |      True
 |
 |      It is more readable and simpler to use
 |
 |      >>> 0 in G
 |      True
 |
 |  nbunch_iter(self, nbunch=None)
 |      Returns an iterator over nodes contained in nbunch that are
 |      also in the graph.
 |
 |      The nodes in nbunch are checked for membership in the graph
 |      and if not are silently ignored.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      Returns
 |      -------
 |      niter : iterator
 |          An iterator over nodes in nbunch that are also in the graph.
 |          If nbunch is None, iterate over all nodes in the graph.
 |
 |      Raises
 |      ------
 |      NetworkXError
 |          If nbunch is not a node or sequence of nodes.
 |          If a node in nbunch is not hashable.
 |
 |      See Also
 |      --------
 |      Graph.__iter__
 |
 |      Notes
 |      -----
 |      When nbunch is an iterator, the returned iterator yields values
 |      directly from nbunch, becoming exhausted when nbunch is exhausted.
 |
 |      To test whether nbunch is a single node, one can use
 |      "if nbunch in self:", even after processing with this routine.
 |
 |      If nbunch is not a node or a (possibly empty) sequence/iterator
 |      or None, a :exc:`NetworkXError` is raised.  Also, if any object in
 |      nbunch is not hashable, a :exc:`NetworkXError` is raised.
 |
 |  neighbors(self, n)
 |      Returns an iterator over all neighbors of node n.
 |
 |      This is identical to `iter(G[n])`
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Returns
 |      -------
 |      neighbors : iterator
 |          An iterator over all neighbors of node n
 |
 |      Raises
 |      ------
 |      NetworkXError
 |          If the node n is not in the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> [n for n in G.neighbors(0)]
 |      [1]
 |
 |      Notes
 |      -----
 |      Alternate ways to access the neighbors are ``G.adj[n]`` or ``G[n]``:
 |
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_edge("a", "b", weight=7)
 |      >>> G["a"]
 |      AtlasView({'b': {'weight': 7}})
 |      >>> G = nx.path_graph(4)
 |      >>> [n for n in G[0]]
 |      [1]
 |
 |  nodes = <functools.cached_property object>
 |      A NodeView of the Graph as G.nodes or G.nodes().
 |
 |      Can be used as `G.nodes` for data lookup and for set-like operations.
 |      Can also be used as `G.nodes(data='color', default=None)` to return a
 |      NodeDataView which reports specific node data but no set operations.
 |      It presents a dict-like interface as well with `G.nodes.items()`
 |      iterating over `(node, nodedata)` 2-tuples and `G.nodes[3]['foo']`
 |      providing the value of the `foo` attribute for node `3`. In addition,
 |      a view `G.nodes.data('foo')` provides a dict-like interface to the
 |      `foo` attribute of each node. `G.nodes.data('foo', default=1)`
 |      provides a default for nodes that do not have attribute `foo`.
 |
 |      Parameters
 |      ----------
 |      data : string or bool, optional (default=False)
 |          The node attribute returned in 2-tuple (n, ddict[data]).
 |          If True, return entire node attribute dict as (n, ddict).
 |          If False, return just the nodes n.
 |
 |      default : value, optional (default=None)
 |          Value used for nodes that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      NodeView
 |          Allows set-like operations over the nodes as well as node
 |          attribute dict lookup and calling to get a NodeDataView.
 |          A NodeDataView iterates over `(n, data)` and has no set operations.
 |          A NodeView iterates over `n` and includes set operations.
 |
 |          When called, if data is False, an iterator over nodes.
 |          Otherwise an iterator of 2-tuples (node, attribute value)
 |          where the attribute is specified in `data`.
 |          If data is True then the attribute becomes the
 |          entire data dictionary.
 |
 |      Notes
 |      -----
 |      If your node data is not needed, it is simpler and equivalent
 |      to use the expression ``for n in G``, or ``list(G)``.
 |
 |      Examples
 |      --------
 |      There are two simple ways of getting a list of all nodes in the graph:
 |
 |      >>> G = nx.path_graph(3)
 |      >>> list(G.nodes)
 |      [0, 1, 2]
 |      >>> list(G)
 |      [0, 1, 2]
 |
 |      To get the node data along with the nodes:
 |
 |      >>> G.add_node(1, time="5pm")
 |      >>> G.nodes[0]["foo"] = "bar"
 |      >>> list(G.nodes(data=True))
 |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
 |      >>> list(G.nodes.data())
 |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
 |
 |      >>> list(G.nodes(data="foo"))
 |      [(0, 'bar'), (1, None), (2, None)]
 |      >>> list(G.nodes.data("foo"))
 |      [(0, 'bar'), (1, None), (2, None)]
 |
 |      >>> list(G.nodes(data="time"))
 |      [(0, None), (1, '5pm'), (2, None)]
 |      >>> list(G.nodes.data("time"))
 |      [(0, None), (1, '5pm'), (2, None)]
 |
 |      >>> list(G.nodes(data="time", default="Not Available"))
 |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
 |      >>> list(G.nodes.data("time", default="Not Available"))
 |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
 |
 |      If some of your nodes have an attribute and the rest are assumed
 |      to have a default attribute value you can create a dictionary
 |      from node/attribute pairs using the `default` keyword argument
 |      to guarantee the value is never None::
 |
 |          >>> G = nx.Graph()
 |          >>> G.add_node(0)
 |          >>> G.add_node(1, weight=2)
 |          >>> G.add_node(2, weight=3)
 |          >>> dict(G.nodes(data="weight", default=1))
 |          {0: 1, 1: 2, 2: 3}
 |
 |  number_of_nodes(self)
 |      Returns the number of nodes in the graph.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      order: identical method
 |      __len__: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.number_of_nodes()
 |      3
 |
 |  order(self)
 |      Returns the number of nodes in the graph.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      number_of_nodes: identical method
 |      __len__: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.order()
 |      3
 |
 |  remove_node(self, n)
 |      Remove node n.
 |
 |      Removes the node n and all adjacent edges.
 |      Attempting to remove a nonexistent node will raise an exception.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Raises
 |      ------
 |      NetworkXError
 |         If n is not in the graph.
 |
 |      See Also
 |      --------
 |      remove_nodes_from
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> list(G.edges)
 |      [(0, 1), (1, 2)]
 |      >>> G.remove_node(1)
 |      >>> list(G.edges)
 |      []
 |
 |  remove_nodes_from(self, nodes)
 |      Remove multiple nodes.
 |
 |      Parameters
 |      ----------
 |      nodes : iterable container
 |          A container of nodes (list, dict, set, etc.).  If a node
 |          in the container is not in the graph it is silently
 |          ignored.
 |
 |      See Also
 |      --------
 |      remove_node
 |
 |      Notes
 |      -----
 |      When removing nodes from an iterator over the graph you are changing,
 |      a `RuntimeError` will be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
 |      object to `G.remove_nodes_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> e = list(G.nodes)
 |      >>> e
 |      [0, 1, 2]
 |      >>> G.remove_nodes_from(e)
 |      >>> list(G.nodes)
 |      []
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.Graph([(0, 1), (1, 2), (3, 4)])
 |      >>> # this command will fail, as the graph's dict is modified during iteration
 |      >>> # G.remove_nodes_from(n for n in G.nodes if n < 2)
 |      >>> # this command will work, since the dictionary underlying graph is not modified
 |      >>> G.remove_nodes_from(list(n for n in G.nodes if n < 2))
 |
 |  size(self, weight=None)
 |      Returns the number of edges or total of all edge weights.
 |
 |      Parameters
 |      ----------
 |      weight : string or None, optional (default=None)
 |          The edge attribute that holds the numerical value used
 |          as a weight. If None, then each edge has weight 1.
 |
 |      Returns
 |      -------
 |      size : numeric
 |          The number of edges or
 |          (if weight keyword is provided) the total weight sum.
 |
 |          If weight is None, returns an int. Otherwise a float
 |          (or more general numeric if the weights are more general).
 |
 |      See Also
 |      --------
 |      number_of_edges
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.size()
 |      3
 |
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_edge("a", "b", weight=2)
 |      >>> G.add_edge("b", "c", weight=4)
 |      >>> G.size()
 |      2
 |      >>> G.size(weight="weight")
 |      6.0
 |
 |  subgraph(self, nodes)
 |      Returns a SubGraph view of the subgraph induced on `nodes`.
 |
 |      The induced subgraph of the graph contains the nodes in `nodes`
 |      and the edges between those nodes.
 |
 |      Parameters
 |      ----------
 |      nodes : list, iterable
 |          A container of nodes which will be iterated through once.
 |
 |      Returns
 |      -------
 |      G : SubGraph View
 |          A subgraph view of the graph. The graph structure cannot be
 |          changed but node/edge attributes can and are shared with the
 |          original graph.
 |
 |      Notes
 |      -----
 |      The graph, edge and node attributes are shared with the original graph.
 |      Changes to the graph structure is ruled out by the view, but changes
 |      to attributes are reflected in the original graph.
 |
 |      To create a subgraph with its own copy of the edge/node attributes use:
 |      G.subgraph(nodes).copy()
 |
 |      For an inplace reduction of a graph to a subgraph you can remove nodes:
 |      G.remove_nodes_from([n for n in G if n not in set(nodes)])
 |
 |      Subgraph views are sometimes NOT what you want. In most cases where
 |      you want to do more than simply look at the induced edges, it makes
 |      more sense to just create the subgraph as its own graph with code like:
 |
 |      ::
 |
 |          # Create a subgraph SG based on a (possibly multigraph) G
 |          SG = G.__class__()
 |          SG.add_nodes_from((n, G.nodes[n]) for n in largest_wcc)
 |          if SG.is_multigraph():
 |              SG.add_edges_from(
 |                  (n, nbr, key, d)
 |                  for n, nbrs in G.adj.items()
 |                  if n in largest_wcc
 |                  for nbr, keydict in nbrs.items()
 |                  if nbr in largest_wcc
 |                  for key, d in keydict.items()
 |              )
 |          else:
 |              SG.add_edges_from(
 |                  (n, nbr, d)
 |                  for n, nbrs in G.adj.items()
 |                  if n in largest_wcc
 |                  for nbr, d in nbrs.items()
 |                  if nbr in largest_wcc
 |              )
 |          SG.graph.update(G.graph)
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> H = G.subgraph([0, 1, 2])
 |      >>> list(H.edges)
 |      [(0, 1), (1, 2)]
 |
 |  update(self, edges=None, nodes=None)
 |      Update the graph using nodes/edges/graphs as input.
 |
 |      Like dict.update, this method takes a graph as input, adding the
 |      graph's nodes and edges to this graph. It can also take two inputs:
 |      edges and nodes. Finally it can take either edges or nodes.
 |      To specify only nodes the keyword `nodes` must be used.
 |
 |      The collections of edges and nodes are treated similarly to
 |      the add_edges_from/add_nodes_from methods. When iterated, they
 |      should yield 2-tuples (u, v) or 3-tuples (u, v, datadict).
 |
 |      Parameters
 |      ----------
 |      edges : Graph object, collection of edges, or None
 |          The first parameter can be a graph or some edges. If it has
 |          attributes `nodes` and `edges`, then it is taken to be a
 |          Graph-like object and those attributes are used as collections
 |          of nodes and edges to be added to the graph.
 |          If the first parameter does not have those attributes, it is
 |          treated as a collection of edges and added to the graph.
 |          If the first argument is None, no edges are added.
 |      nodes : collection of nodes, or None
 |          The second parameter is treated as a collection of nodes
 |          to be added to the graph unless it is None.
 |          If `edges is None` and `nodes is None` an exception is raised.
 |          If the first parameter is a Graph, then `nodes` is ignored.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(5)
 |      >>> G.update(nx.complete_graph(range(4, 10)))
 |      >>> from itertools import combinations
 |      >>> edges = (
 |      ...     (u, v, {"power": u * v})
 |      ...     for u, v in combinations(range(10, 20), 2)
 |      ...     if u * v < 225
 |      ... )
 |      >>> nodes = [1000]  # for singleton, use a container
 |      >>> G.update(edges, nodes)
 |
 |      Notes
 |      -----
 |      It you want to update the graph using an adjacency structure
 |      it is straightforward to obtain the edges/nodes from adjacency.
 |      The following examples provide common cases, your adjacency may
 |      be slightly different and require tweaks of these examples::
 |
 |      >>> # dict-of-set/list/tuple
 |      >>> adj = {1: {2, 3}, 2: {1, 3}, 3: {1, 2}}
 |      >>> e = [(u, v) for u, nbrs in adj.items() for v in nbrs]
 |      >>> G.update(edges=e, nodes=adj)
 |
 |      >>> DG = nx.DiGraph()
 |      >>> # dict-of-dict-of-attribute
 |      >>> adj = {1: {2: 1.3, 3: 0.7}, 2: {1: 1.4}, 3: {1: 0.7}}
 |      >>> e = [
 |      ...     (u, v, {"weight": d})
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, d in nbrs.items()
 |      ... ]
 |      >>> DG.update(edges=e, nodes=adj)
 |
 |      >>> # dict-of-dict-of-dict
 |      >>> adj = {1: {2: {"weight": 1.3}, 3: {"color": 0.7, "weight": 1.2}}}
 |      >>> e = [
 |      ...     (u, v, {"weight": d})
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, d in nbrs.items()
 |      ... ]
 |      >>> DG.update(edges=e, nodes=adj)
 |
 |      >>> # predecessor adjacency (dict-of-set)
 |      >>> pred = {1: {2, 3}, 2: {3}, 3: {3}}
 |      >>> e = [(v, u) for u, nbrs in pred.items() for v in nbrs]
 |
 |      >>> # MultiGraph dict-of-dict-of-dict-of-attribute
 |      >>> MDG = nx.MultiDiGraph()
 |      >>> adj = {
 |      ...     1: {2: {0: {"weight": 1.3}, 1: {"weight": 1.2}}},
 |      ...     3: {2: {0: {"weight": 0.7}}},
 |      ... }
 |      >>> e = [
 |      ...     (u, v, ekey, d)
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, keydict in nbrs.items()
 |      ...     for ekey, d in keydict.items()
 |      ... ]
 |      >>> MDG.update(edges=e)
 |
 |      See Also
 |      --------
 |      add_edges_from: add multiple edges to a graph
 |      add_nodes_from: add multiple nodes to a graph
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from networkx.classes.graph.Graph:
 |
 |  __dict__
 |      dictionary for instance variables
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  name
 |      String identifier of the graph.
 |
 |      This graph attribute appears in the attribute dict G.graph
 |      keyed by the string `"name"`. as well as an attribute (technically
 |      a property) `G.name`. This is entirely user controlled.
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes inherited from networkx.classes.graph.Graph:
 |
 |  __networkx_backend__ = 'networkx'
 |
 |  adjlist_inner_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  adjlist_outer_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  edge_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  graph_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  node_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  node_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
networkx.NetworkXAlgorithmError
Python Library Documentation: class NetworkXAlgorithmError in module networkx.exception

class NetworkXAlgorithmError(NetworkXException)
 |  Exception for unexpected termination of algorithms.
 |
 |  Method resolution order:
 |      NetworkXAlgorithmError
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.NetworkXError
Python Library Documentation: class NetworkXError in module networkx.exception

class NetworkXError(NetworkXException)
 |  Exception for a serious error in NetworkX
 |
 |  Method resolution order:
 |      NetworkXError
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.NetworkXException
Python Library Documentation: class NetworkXException in module networkx.exception

class NetworkXException(builtins.Exception)
 |  Base class for exceptions in NetworkX.
 |
 |  Method resolution order:
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors defined here:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.NetworkXNoCycle
Python Library Documentation: class NetworkXNoCycle in module networkx.exception

class NetworkXNoCycle(NetworkXUnfeasible)
 |  Exception for algorithms that should return a cycle when running
 |  on graphs where such a cycle does not exist.
 |
 |  Method resolution order:
 |      NetworkXNoCycle
 |      NetworkXUnfeasible
 |      NetworkXAlgorithmError
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.NetworkXNoPath
Python Library Documentation: class NetworkXNoPath in module networkx.exception

class NetworkXNoPath(NetworkXUnfeasible)
 |  Exception for algorithms that should return a path when running
 |  on graphs where such a path does not exist.
 |
 |  Method resolution order:
 |      NetworkXNoPath
 |      NetworkXUnfeasible
 |      NetworkXAlgorithmError
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.NetworkXNotImplemented
Python Library Documentation: class NetworkXNotImplemented in module networkx.exception

class NetworkXNotImplemented(NetworkXException)
 |  Exception raised by algorithms not implemented for a type of graph.
 |
 |  Method resolution order:
 |      NetworkXNotImplemented
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.NetworkXPointlessConcept
Python Library Documentation: class NetworkXPointlessConcept in module networkx.exception

class NetworkXPointlessConcept(NetworkXException)
 |  Raised when a null graph is provided as input to an algorithm
 |  that cannot use it.
 |
 |  The null graph is sometimes considered a pointless concept [1]_,
 |  thus the name of the exception.
 |
 |  Notes
 |  -----
 |  Null graphs and empty graphs are often used interchangeably but they
 |  are well defined in NetworkX. An ``empty_graph`` is a graph with ``n`` nodes
 |  and 0 edges, and a ``null_graph`` is a graph with 0 nodes and 0 edges.
 |
 |  References
 |  ----------
 |  .. [1] Harary, F. and Read, R. "Is the Null Graph a Pointless
 |     Concept?"  In Graphs and Combinatorics Conference, George
 |     Washington University.  New York: Springer-Verlag, 1973.
 |
 |  Method resolution order:
 |      NetworkXPointlessConcept
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.NetworkXTreewidthBoundExceeded
Python Library Documentation: class NetworkXTreewidthBoundExceeded in module networkx.algorithms.chordal

class NetworkXTreewidthBoundExceeded(networkx.exception.NetworkXException)
 |  Exception raised when a treewidth bound has been provided and it has
 |  been exceeded
 |
 |  Method resolution order:
 |      NetworkXTreewidthBoundExceeded
 |      networkx.exception.NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from networkx.exception.NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.NetworkXUnbounded
Python Library Documentation: class NetworkXUnbounded in module networkx.exception

class NetworkXUnbounded(NetworkXAlgorithmError)
 |  Exception raised by algorithms trying to solve a maximization
 |  or a minimization problem instance that is unbounded.
 |
 |  Method resolution order:
 |      NetworkXUnbounded
 |      NetworkXAlgorithmError
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.NetworkXUnfeasible
Python Library Documentation: class NetworkXUnfeasible in module networkx.exception

class NetworkXUnfeasible(NetworkXAlgorithmError)
 |  Exception raised by algorithms trying to solve a problem
 |  instance that has no feasible solution.
 |
 |  Method resolution order:
 |      NetworkXUnfeasible
 |      NetworkXAlgorithmError
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.NodeNotFound
Python Library Documentation: class NodeNotFound in module networkx.exception

class NodeNotFound(NetworkXException)
 |  Exception raised if requested node is not present in the graph
 |
 |  Method resolution order:
 |      NodeNotFound
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.NotATree
Python Library Documentation: class NotATree in module networkx.algorithms.tree.coding

class NotATree(networkx.exception.NetworkXException)
 |  Raised when a function expects a tree (that is, a connected
 |  undirected graph with no cycles) but gets a non-tree graph as input
 |  instead.
 |
 |  Method resolution order:
 |      NotATree
 |      networkx.exception.NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Data descriptors inherited from networkx.exception.NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.Exception:
 |
 |  __init__(self, /, *args, **kwargs)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.PlanarEmbedding
Python Library Documentation: class PlanarEmbedding in module networkx.algorithms.planarity

class PlanarEmbedding(networkx.classes.digraph.DiGraph)
 |  PlanarEmbedding(incoming_graph_data=None, **attr)
 |
 |  Represents a planar graph with its planar embedding.
 |
 |  The planar embedding is given by a `combinatorial embedding
 |  <https://en.wikipedia.org/wiki/Graph_embedding#Combinatorial_embedding>`_.
 |
 |  .. note:: `check_planarity` is the preferred way to check if a graph is planar.
 |
 |  **Neighbor ordering:**
 |
 |  In comparison to a usual graph structure, the embedding also stores the
 |  order of all neighbors for every vertex.
 |  The order of the neighbors can be given in clockwise (cw) direction or
 |  counterclockwise (ccw) direction. This order is stored as edge attributes
 |  in the underlying directed graph. For the edge (u, v) the edge attribute
 |  'cw' is set to the neighbor of u that follows immediately after v in
 |  clockwise direction.
 |
 |  In order for a PlanarEmbedding to be valid it must fulfill multiple
 |  conditions. It is possible to check if these conditions are fulfilled with
 |  the method :meth:`check_structure`.
 |  The conditions are:
 |
 |  * Edges must go in both directions (because the edge attributes differ)
 |  * Every edge must have a 'cw' and 'ccw' attribute which corresponds to a
 |    correct planar embedding.
 |
 |  As long as a PlanarEmbedding is invalid only the following methods should
 |  be called:
 |
 |  * :meth:`add_half_edge`
 |  * :meth:`connect_components`
 |
 |  Even though the graph is a subclass of nx.DiGraph, it can still be used
 |  for algorithms that require undirected graphs, because the method
 |  :meth:`is_directed` is overridden. This is possible, because a valid
 |  PlanarGraph must have edges in both directions.
 |
 |  **Half edges:**
 |
 |  In methods like `add_half_edge` the term "half-edge" is used, which is
 |  a term that is used in `doubly connected edge lists
 |  <https://en.wikipedia.org/wiki/Doubly_connected_edge_list>`_. It is used
 |  to emphasize that the edge is only in one direction and there exists
 |  another half-edge in the opposite direction.
 |  While conventional edges always have two faces (including outer face) next
 |  to them, it is possible to assign each half-edge *exactly one* face.
 |  For a half-edge (u, v) that is oriented such that u is below v then the
 |  face that belongs to (u, v) is to the right of this half-edge.
 |
 |  See Also
 |  --------
 |  is_planar :
 |      Preferred way to check if an existing graph is planar.
 |
 |  check_planarity :
 |      A convenient way to create a `PlanarEmbedding`. If not planar,
 |      it returns a subgraph that shows this.
 |
 |  Examples
 |  --------
 |
 |  Create an embedding of a star graph (compare `nx.star_graph(3)`):
 |
 |  >>> G = nx.PlanarEmbedding()
 |  >>> G.add_half_edge(0, 1)
 |  >>> G.add_half_edge(0, 2, ccw=1)
 |  >>> G.add_half_edge(0, 3, ccw=2)
 |  >>> G.add_half_edge(1, 0)
 |  >>> G.add_half_edge(2, 0)
 |  >>> G.add_half_edge(3, 0)
 |
 |  Alternatively the same embedding can also be defined in counterclockwise
 |  orientation. The following results in exactly the same PlanarEmbedding:
 |
 |  >>> G = nx.PlanarEmbedding()
 |  >>> G.add_half_edge(0, 1)
 |  >>> G.add_half_edge(0, 3, cw=1)
 |  >>> G.add_half_edge(0, 2, cw=3)
 |  >>> G.add_half_edge(1, 0)
 |  >>> G.add_half_edge(2, 0)
 |  >>> G.add_half_edge(3, 0)
 |
 |  After creating a graph, it is possible to validate that the PlanarEmbedding
 |  object is correct:
 |
 |  >>> G.check_structure()
 |
 |  Method resolution order:
 |      PlanarEmbedding
 |      networkx.classes.digraph.DiGraph
 |      networkx.classes.graph.Graph
 |      builtins.object
 |
 |  Methods defined here:
 |
 |  __init__(self, incoming_graph_data=None, **attr)
 |      Initialize a graph with edges, name, or graph attributes.
 |
 |      Parameters
 |      ----------
 |      incoming_graph_data : input graph (optional, default: None)
 |          Data to initialize graph.  If None (default) an empty
 |          graph is created.  The data can be an edge list, or any
 |          NetworkX graph object.  If the corresponding optional Python
 |          packages are installed the data can also be a 2D NumPy array, a
 |          SciPy sparse array, or a PyGraphviz graph.
 |
 |      attr : keyword arguments, optional (default= no attributes)
 |          Attributes to add to graph as key=value pairs.
 |
 |      See Also
 |      --------
 |      convert
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G = nx.Graph(name="my graph")
 |      >>> e = [(1, 2), (2, 3), (3, 4)]  # list of edges
 |      >>> G = nx.Graph(e)
 |
 |      Arbitrary graph attribute pairs (key=value) may be assigned
 |
 |      >>> G = nx.Graph(e, day="Friday")
 |      >>> G.graph
 |      {'day': 'Friday'}
 |
 |  add_half_edge(self, start_node, end_node, *, cw=None, ccw=None)
 |      Adds a half-edge from `start_node` to `end_node`.
 |
 |      If the half-edge is not the first one out of `start_node`, a reference
 |      node must be provided either in the clockwise (parameter `cw`) or in
 |      the counterclockwise (parameter `ccw`) direction. Only one of `cw`/`ccw`
 |      can be specified (or neither in the case of the first edge).
 |      Note that specifying a reference in the clockwise (`cw`) direction means
 |      inserting the new edge in the first counterclockwise position with
 |      respect to the reference (and vice-versa).
 |
 |      Parameters
 |      ----------
 |      start_node : node
 |          Start node of inserted edge.
 |      end_node : node
 |          End node of inserted edge.
 |      cw, ccw: node
 |          End node of reference edge.
 |          Omit or pass `None` if adding the first out-half-edge of `start_node`.
 |
 |
 |      Raises
 |      ------
 |      NetworkXException
 |          If the `cw` or `ccw` node is not a successor of `start_node`.
 |          If `start_node` has successors, but neither `cw` or `ccw` is provided.
 |          If both `cw` and `ccw` are specified.
 |
 |      See Also
 |      --------
 |      connect_components
 |
 |  add_half_edge_ccw(self, start_node, end_node, reference_neighbor)
 |      Adds a half-edge from start_node to end_node.
 |
 |      The half-edge is added counter clockwise next to the existing half-edge
 |      (start_node, reference_neighbor).
 |
 |      Parameters
 |      ----------
 |      start_node : node
 |          Start node of inserted edge.
 |      end_node : node
 |          End node of inserted edge.
 |      reference_neighbor: node
 |          End node of reference edge.
 |
 |      Raises
 |      ------
 |      NetworkXException
 |          If the reference_neighbor does not exist.
 |
 |      See Also
 |      --------
 |      add_half_edge
 |      add_half_edge_cw
 |      connect_components
 |
 |  add_half_edge_cw(self, start_node, end_node, reference_neighbor)
 |      Adds a half-edge from start_node to end_node.
 |
 |      The half-edge is added clockwise next to the existing half-edge
 |      (start_node, reference_neighbor).
 |
 |      Parameters
 |      ----------
 |      start_node : node
 |          Start node of inserted edge.
 |      end_node : node
 |          End node of inserted edge.
 |      reference_neighbor: node
 |          End node of reference edge.
 |
 |      Raises
 |      ------
 |      NetworkXException
 |          If the reference_neighbor does not exist.
 |
 |      See Also
 |      --------
 |      add_half_edge
 |      add_half_edge_ccw
 |      connect_components
 |
 |  add_half_edge_first(self, start_node, end_node)
 |      Add a half-edge and set end_node as start_node's leftmost neighbor.
 |
 |      The new edge is inserted counterclockwise with respect to the current
 |      leftmost neighbor, if there is one.
 |
 |      Parameters
 |      ----------
 |      start_node : node
 |      end_node : node
 |
 |      See Also
 |      --------
 |      add_half_edge
 |      connect_components
 |
 |  check_structure(self)
 |      Runs without exceptions if this object is valid.
 |
 |      Checks that the following properties are fulfilled:
 |
 |      * Edges go in both directions (because the edge attributes differ).
 |      * Every edge has a 'cw' and 'ccw' attribute which corresponds to a
 |        correct planar embedding.
 |
 |      Running this method verifies that the underlying Graph must be planar.
 |
 |      Raises
 |      ------
 |      NetworkXException
 |          This exception is raised with a short explanation if the
 |          PlanarEmbedding is invalid.
 |
 |  connect_components(self, v, w)
 |      Adds half-edges for (v, w) and (w, v) at some position.
 |
 |      This method should only be called if v and w are in different
 |      components, or it might break the embedding.
 |      This especially means that if `connect_components(v, w)`
 |      is called it is not allowed to call `connect_components(w, v)`
 |      afterwards. The neighbor orientations in both directions are
 |      all set correctly after the first call.
 |
 |      Parameters
 |      ----------
 |      v : node
 |      w : node
 |
 |      See Also
 |      --------
 |      add_half_edge
 |
 |  copy(self, as_view=False)
 |      Returns a copy of the graph.
 |
 |      The copy method by default returns an independent shallow copy
 |      of the graph and attributes. That is, if an attribute is a
 |      container, that container is shared by the original an the copy.
 |      Use Python's `copy.deepcopy` for new containers.
 |
 |      If `as_view` is True then a view is returned instead of a copy.
 |
 |      Notes
 |      -----
 |      All copies reproduce the graph structure, but data attributes
 |      may be handled in different ways. There are four types of copies
 |      of a graph that people might want.
 |
 |      Deepcopy -- A "deepcopy" copies the graph structure as well as
 |      all data attributes and any objects they might contain.
 |      The entire graph object is new so that changes in the copy
 |      do not affect the original object. (see Python's copy.deepcopy)
 |
 |      Data Reference (Shallow) -- For a shallow copy the graph structure
 |      is copied but the edge, node and graph attribute dicts are
 |      references to those in the original graph. This saves
 |      time and memory but could cause confusion if you change an attribute
 |      in one graph and it changes the attribute in the other.
 |      NetworkX does not provide this level of shallow copy.
 |
 |      Independent Shallow -- This copy creates new independent attribute
 |      dicts and then does a shallow copy of the attributes. That is, any
 |      attributes that are containers are shared between the new graph
 |      and the original. This is exactly what `dict.copy()` provides.
 |      You can obtain this style copy using:
 |
 |          >>> G = nx.path_graph(5)
 |          >>> H = G.copy()
 |          >>> H = G.copy(as_view=False)
 |          >>> H = nx.Graph(G)
 |          >>> H = G.__class__(G)
 |
 |      Fresh Data -- For fresh data, the graph structure is copied while
 |      new empty data attribute dicts are created. The resulting graph
 |      is independent of the original and it has no edge, node or graph
 |      attributes. Fresh copies are not enabled. Instead use:
 |
 |          >>> H = G.__class__()
 |          >>> H.add_nodes_from(G)
 |          >>> H.add_edges_from(G.edges)
 |
 |      View -- Inspired by dict-views, graph-views act like read-only
 |      versions of the original graph, providing a copy of the original
 |      structure without requiring any memory for copying the information.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Parameters
 |      ----------
 |      as_view : bool, optional (default=False)
 |          If True, the returned graph-view provides a read-only view
 |          of the original graph without actually copying any data.
 |
 |      Returns
 |      -------
 |      G : Graph
 |          A copy of the graph.
 |
 |      See Also
 |      --------
 |      to_directed: return a directed copy of the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> H = G.copy()
 |
 |  get_data(self)
 |      Converts the adjacency structure into a better readable structure.
 |
 |      Returns
 |      -------
 |      embedding : dict
 |          A dict mapping all nodes to a list of neighbors sorted in
 |          clockwise order.
 |
 |      See Also
 |      --------
 |      set_data
 |
 |  is_directed(self)
 |      A valid PlanarEmbedding is undirected.
 |
 |      All reverse edges are contained, i.e. for every existing
 |      half-edge (v, w) the half-edge in the opposite direction (w, v) is also
 |      contained.
 |
 |  neighbors_cw_order(self, v)
 |      Generator for the neighbors of v in clockwise order.
 |
 |      Parameters
 |      ----------
 |      v : node
 |
 |      Yields
 |      ------
 |      node
 |
 |  next_face_half_edge(self, v, w)
 |      Returns the following half-edge left of a face.
 |
 |      Parameters
 |      ----------
 |      v : node
 |      w : node
 |
 |      Returns
 |      -------
 |      half-edge : tuple
 |
 |  remove_edge(self, u, v)
 |      Remove the edge between u and v.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |      Remove the half-edges (u, v) and (v, u) and update the
 |      edge ordering around the removed edge.
 |
 |      Raises
 |      ------
 |      NetworkXError
 |      If there is not an edge between u and v.
 |
 |      See Also
 |      --------
 |      remove_edges_from : remove a collection of edges
 |
 |  remove_edges_from(self, ebunch)
 |      Remove all edges specified in ebunch.
 |
 |      Parameters
 |      ----------
 |      ebunch: list or container of edge tuples
 |          Each pair of half-edges between the nodes given in the tuples
 |          will be removed from the graph. The nodes can be passed as:
 |
 |              - 2-tuples (u, v) half-edges (u, v) and (v, u).
 |              - 3-tuples (u, v, k) where k is ignored.
 |
 |      See Also
 |      --------
 |      remove_edge : remove a single edge
 |
 |      Notes
 |      -----
 |      Will fail silently if an edge in ebunch is not in the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> ebunch = [(1, 2), (2, 3)]
 |      >>> G.remove_edges_from(ebunch)
 |
 |  remove_node(self, n)
 |      Remove node n.
 |
 |      Removes the node n and all adjacent edges, updating the
 |      PlanarEmbedding to account for any resulting edge removal.
 |      Attempting to remove a non-existent node will raise an exception.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Raises
 |      ------
 |      NetworkXError
 |         If n is not in the graph.
 |
 |      See Also
 |      --------
 |      remove_nodes_from
 |
 |  remove_nodes_from(self, nodes)
 |      Remove multiple nodes.
 |
 |      Parameters
 |      ----------
 |      nodes : iterable container
 |          A container of nodes (list, dict, set, etc.).  If a node
 |          in the container is not in the graph it is silently ignored.
 |
 |      See Also
 |      --------
 |      remove_node
 |
 |      Notes
 |      -----
 |      When removing nodes from an iterator over the graph you are changing,
 |      a `RuntimeError` will be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
 |      object to `G.remove_nodes_from`.
 |
 |  set_data(self, data)
 |      Inserts edges according to given sorted neighbor list.
 |
 |      The input format is the same as the output format of get_data().
 |
 |      Parameters
 |      ----------
 |      data : dict
 |          A dict mapping all nodes to a list of neighbors sorted in
 |          clockwise order.
 |
 |      See Also
 |      --------
 |      get_data
 |
 |  traverse_face(self, v, w, mark_half_edges=None)
 |      Returns nodes on the face that belong to the half-edge (v, w).
 |
 |      The face that is traversed lies to the right of the half-edge (in an
 |      orientation where v is below w).
 |
 |      Optionally it is possible to pass a set to which all encountered half
 |      edges are added. Before calling this method, this set must not include
 |      any half-edges that belong to the face.
 |
 |      Parameters
 |      ----------
 |      v : node
 |          Start node of half-edge.
 |      w : node
 |          End node of half-edge.
 |      mark_half_edges: set, optional
 |          Set to which all encountered half-edges are added.
 |
 |      Returns
 |      -------
 |      face : list
 |          A list of nodes that lie on this face.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from networkx.classes.digraph.DiGraph:
 |
 |  add_edge(self, u_of_edge, v_of_edge, **attr)
 |      Add an edge between u and v.
 |
 |      The nodes u and v will be automatically added if they are
 |      not already in the graph.
 |
 |      Edge attributes can be specified with keywords or by directly
 |      accessing the edge's attribute dictionary. See examples below.
 |
 |      Parameters
 |      ----------
 |      u_of_edge, v_of_edge : nodes
 |          Nodes can be, for example, strings or numbers.
 |          Nodes must be hashable (and not None) Python objects.
 |      attr : keyword arguments, optional
 |          Edge data (or labels or objects) can be assigned using
 |          keyword arguments.
 |
 |      See Also
 |      --------
 |      add_edges_from : add a collection of edges
 |
 |      Notes
 |      -----
 |      Adding an edge that already exists updates the edge data.
 |
 |      Many NetworkX algorithms designed for weighted graphs use
 |      an edge attribute (by default `weight`) to hold a numerical value.
 |
 |      Examples
 |      --------
 |      The following all add the edge e=(1, 2) to graph G:
 |
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> e = (1, 2)
 |      >>> G.add_edge(1, 2)  # explicit two-node form
 |      >>> G.add_edge(*e)  # single edge as tuple of two nodes
 |      >>> G.add_edges_from([(1, 2)])  # add edges from iterable container
 |
 |      Associate data to edges using keywords:
 |
 |      >>> G.add_edge(1, 2, weight=3)
 |      >>> G.add_edge(1, 3, weight=7, capacity=15, length=342.7)
 |
 |      For non-string attribute keys, use subscript notation.
 |
 |      >>> G.add_edge(1, 2)
 |      >>> G[1][2].update({0: 5})
 |      >>> G.edges[1, 2].update({0: 5})
 |
 |  add_edges_from(self, ebunch_to_add, **attr)
 |      Add all the edges in ebunch_to_add.
 |
 |      Parameters
 |      ----------
 |      ebunch_to_add : container of edges
 |          Each edge given in the container will be added to the
 |          graph. The edges must be given as 2-tuples (u, v) or
 |          3-tuples (u, v, d) where d is a dictionary containing edge data.
 |      attr : keyword arguments, optional
 |          Edge data (or labels or objects) can be assigned using
 |          keyword arguments.
 |
 |      See Also
 |      --------
 |      add_edge : add a single edge
 |      add_weighted_edges_from : convenient way to add weighted edges
 |
 |      Notes
 |      -----
 |      Adding the same edge twice has no effect but any edge data
 |      will be updated when each duplicate edge is added.
 |
 |      Edge attributes specified in an ebunch take precedence over
 |      attributes specified via keyword arguments.
 |
 |      When adding edges from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_edges)`, and pass this
 |      object to `G.add_edges_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_edges_from([(0, 1), (1, 2)])  # using a list of edge tuples
 |      >>> e = zip(range(0, 3), range(1, 4))
 |      >>> G.add_edges_from(e)  # Add the path graph 0-1-2-3
 |
 |      Associate data to edges
 |
 |      >>> G.add_edges_from([(1, 2), (2, 3)], weight=3)
 |      >>> G.add_edges_from([(3, 4), (1, 4)], label="WN2898")
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 4)])
 |      >>> # Grow graph by one new node, adding edges to all existing nodes.
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_edges_from(((5, n) for n in G.nodes))
 |      >>> # right way - note that there will be no self-edge for node 5
 |      >>> G.add_edges_from(list((5, n) for n in G.nodes))
 |
 |  add_node(self, node_for_adding, **attr)
 |      Add a single node `node_for_adding` and update node attributes.
 |
 |      Parameters
 |      ----------
 |      node_for_adding : node
 |          A node can be any hashable Python object except None.
 |      attr : keyword arguments, optional
 |          Set or change node attributes using key=value.
 |
 |      See Also
 |      --------
 |      add_nodes_from
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_node(1)
 |      >>> G.add_node("Hello")
 |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
 |      >>> G.add_node(K3)
 |      >>> G.number_of_nodes()
 |      3
 |
 |      Use keywords set/change node attributes:
 |
 |      >>> G.add_node(1, size=10)
 |      >>> G.add_node(3, weight=0.4, UTM=("13S", 382871, 3972649))
 |
 |      Notes
 |      -----
 |      A hashable object is one that can be used as a key in a Python
 |      dictionary. This includes strings, numbers, tuples of strings
 |      and numbers, etc.
 |
 |      On many platforms hashable items also include mutables such as
 |      NetworkX Graphs, though one should be careful that the hash
 |      doesn't change on mutables.
 |
 |  add_nodes_from(self, nodes_for_adding, **attr)
 |      Add multiple nodes.
 |
 |      Parameters
 |      ----------
 |      nodes_for_adding : iterable container
 |          A container of nodes (list, dict, set, etc.).
 |          OR
 |          A container of (node, attribute dict) tuples.
 |          Node attributes are updated using the attribute dict.
 |      attr : keyword arguments, optional (default= no attributes)
 |          Update attributes for all nodes in nodes.
 |          Node attributes specified in nodes as a tuple take
 |          precedence over attributes specified via keyword arguments.
 |
 |      See Also
 |      --------
 |      add_node
 |
 |      Notes
 |      -----
 |      When adding nodes from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
 |      object to `G.add_nodes_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_nodes_from("Hello")
 |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
 |      >>> G.add_nodes_from(K3)
 |      >>> sorted(G.nodes(), key=str)
 |      [0, 1, 2, 'H', 'e', 'l', 'o']
 |
 |      Use keywords to update specific node attributes for every node.
 |
 |      >>> G.add_nodes_from([1, 2], size=10)
 |      >>> G.add_nodes_from([3, 4], weight=0.4)
 |
 |      Use (node, attrdict) tuples to update attributes for specific nodes.
 |
 |      >>> G.add_nodes_from([(1, dict(size=11)), (2, {"color": "blue"})])
 |      >>> G.nodes[1]["size"]
 |      11
 |      >>> H = nx.Graph()
 |      >>> H.add_nodes_from(G.nodes(data=True))
 |      >>> H.nodes[1]["size"]
 |      11
 |
 |      Evaluate an iterator over a graph if using it to modify the same graph
 |
 |      >>> G = nx.DiGraph([(0, 1), (1, 2), (3, 4)])
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_nodes_from(n + 1 for n in G.nodes)
 |      >>> # correct way
 |      >>> G.add_nodes_from(list(n + 1 for n in G.nodes))
 |
 |  adj = <functools.cached_property object>
 |      Graph adjacency object holding the neighbors of each node.
 |
 |      This object is a read-only dict-like structure with node keys
 |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
 |      to the edge-data-dict.  So `G.adj[3][2]['color'] = 'blue'` sets
 |      the color of the edge `(3, 2)` to `"blue"`.
 |
 |      Iterating over G.adj behaves like a dict. Useful idioms include
 |      `for nbr, datadict in G.adj[n].items():`.
 |
 |      The neighbor information is also provided by subscripting the graph.
 |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
 |
 |      For directed graphs, `G.adj` holds outgoing (successor) info.
 |
 |  clear(self)
 |      Remove all nodes and edges from the graph.
 |
 |      This also removes the name, and all graph, node, and edge attributes.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.clear()
 |      >>> list(G.nodes)
 |      []
 |      >>> list(G.edges)
 |      []
 |
 |  clear_edges(self)
 |      Remove all edges from the graph without altering nodes.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.clear_edges()
 |      >>> list(G.nodes)
 |      [0, 1, 2, 3]
 |      >>> list(G.edges)
 |      []
 |
 |  degree = <functools.cached_property object>
 |      A DegreeView for the Graph as G.degree or G.degree().
 |
 |      The node degree is the number of edges adjacent to the node.
 |      The weighted node degree is the sum of the edge weights for
 |      edges incident to that node.
 |
 |      This object provides an iterator for (node, degree) as well as
 |      lookup for the degree for a single node.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      weight : string or None, optional (default=None)
 |         The name of an edge attribute that holds the numerical value used
 |         as a weight.  If None, then each edge has weight 1.
 |         The degree is the sum of the edge weights adjacent to the node.
 |
 |      Returns
 |      -------
 |      DiDegreeView or int
 |          If multiple nodes are requested (the default), returns a `DiDegreeView`
 |          mapping nodes to their degree.
 |          If a single node is requested, returns the degree of the node as an integer.
 |
 |      See Also
 |      --------
 |      in_degree, out_degree
 |
 |      Examples
 |      --------
 |      >>> G = nx.DiGraph()  # or MultiDiGraph
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.degree(0)  # node 0 with degree 1
 |      1
 |      >>> list(G.degree([0, 1, 2]))
 |      [(0, 1), (1, 2), (2, 2)]
 |
 |  edges = <functools.cached_property object>
 |      An OutEdgeView of the DiGraph as G.edges or G.edges().
 |
 |      edges(self, nbunch=None, data=False, default=None)
 |
 |      The OutEdgeView provides set-like operations on the edge-tuples
 |      as well as edge attribute lookup. When called, it also provides
 |      an EdgeDataView object which allows control of access to edge
 |      attributes (but does not provide set-like operations).
 |      Hence, `G.edges[u, v]['color']` provides the value of the color
 |      attribute for edge `(u, v)` while
 |      `for (u, v, c) in G.edges.data('color', default='red'):`
 |      iterates through all the edges yielding the color attribute
 |      with default `'red'` if no color attribute exists.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges from these nodes.
 |      data : string or bool, optional (default=False)
 |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
 |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
 |          If False, return 2-tuple (u, v).
 |      default : value, optional (default=None)
 |          Value used for edges that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      edges : OutEdgeView
 |          A view of edge attributes, usually it iterates over (u, v)
 |          or (u, v, d) tuples of edges, but can also be used for
 |          attribute lookup as `edges[u, v]['foo']`.
 |
 |      See Also
 |      --------
 |      in_edges, out_edges
 |
 |      Notes
 |      -----
 |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
 |      For directed graphs this returns the out-edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
 |      >>> nx.add_path(G, [0, 1, 2])
 |      >>> G.add_edge(2, 3, weight=5)
 |      >>> [e for e in G.edges]
 |      [(0, 1), (1, 2), (2, 3)]
 |      >>> G.edges.data()  # default data is {} (empty dict)
 |      OutEdgeDataView([(0, 1, {}), (1, 2, {}), (2, 3, {'weight': 5})])
 |      >>> G.edges.data("weight", default=1)
 |      OutEdgeDataView([(0, 1, 1), (1, 2, 1), (2, 3, 5)])
 |      >>> G.edges([0, 2])  # only edges originating from these nodes
 |      OutEdgeDataView([(0, 1), (2, 3)])
 |      >>> G.edges(0)  # only edges from node 0
 |      OutEdgeDataView([(0, 1)])
 |
 |  has_predecessor(self, u, v)
 |      Returns True if node u has predecessor v.
 |
 |      This is true if graph has the edge u<-v.
 |
 |  has_successor(self, u, v)
 |      Returns True if node u has successor v.
 |
 |      This is true if graph has the edge u->v.
 |
 |  in_degree = <functools.cached_property object>
 |      An InDegreeView for (node, in_degree) or in_degree for single node.
 |
 |      The node in_degree is the number of edges pointing to the node.
 |      The weighted node degree is the sum of the edge weights for
 |      edges incident to that node.
 |
 |      This object provides an iteration over (node, in_degree) as well as
 |      lookup for the degree for a single node.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      weight : string or None, optional (default=None)
 |         The name of an edge attribute that holds the numerical value used
 |         as a weight.  If None, then each edge has weight 1.
 |         The degree is the sum of the edge weights adjacent to the node.
 |
 |      Returns
 |      -------
 |      If a single node is requested
 |      deg : int
 |          In-degree of the node
 |
 |      OR if multiple nodes are requested
 |      nd_iter : iterator
 |          The iterator returns two-tuples of (node, in-degree).
 |
 |      See Also
 |      --------
 |      degree, out_degree
 |
 |      Examples
 |      --------
 |      >>> G = nx.DiGraph()
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.in_degree(0)  # node 0 with degree 0
 |      0
 |      >>> list(G.in_degree([0, 1, 2]))
 |      [(0, 0), (1, 1), (2, 1)]
 |
 |  in_edges = <functools.cached_property object>
 |      A view of the in edges of the graph as G.in_edges or G.in_edges().
 |
 |      in_edges(self, nbunch=None, data=False, default=None):
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |      data : string or bool, optional (default=False)
 |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
 |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
 |          If False, return 2-tuple (u, v).
 |      default : value, optional (default=None)
 |          Value used for edges that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      in_edges : InEdgeView or InEdgeDataView
 |          A view of edge attributes, usually it iterates over (u, v)
 |          or (u, v, d) tuples of edges, but can also be used for
 |          attribute lookup as `edges[u, v]['foo']`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.DiGraph()
 |      >>> G.add_edge(1, 2, color="blue")
 |      >>> G.in_edges()
 |      InEdgeView([(1, 2)])
 |      >>> G.in_edges(nbunch=2)
 |      InEdgeDataView([(1, 2)])
 |
 |      See Also
 |      --------
 |      edges
 |
 |  is_multigraph(self)
 |      Returns True if graph is a multigraph, False otherwise.
 |
 |  neighbors = successors(self, n)
 |
 |  out_degree = <functools.cached_property object>
 |      An OutDegreeView for (node, out_degree)
 |
 |      The node out_degree is the number of edges pointing out of the node.
 |      The weighted node degree is the sum of the edge weights for
 |      edges incident to that node.
 |
 |      This object provides an iterator over (node, out_degree) as well as
 |      lookup for the degree for a single node.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      weight : string or None, optional (default=None)
 |         The name of an edge attribute that holds the numerical value used
 |         as a weight.  If None, then each edge has weight 1.
 |         The degree is the sum of the edge weights adjacent to the node.
 |
 |      Returns
 |      -------
 |      If a single node is requested
 |      deg : int
 |          Out-degree of the node
 |
 |      OR if multiple nodes are requested
 |      nd_iter : iterator
 |          The iterator returns two-tuples of (node, out-degree).
 |
 |      See Also
 |      --------
 |      degree, in_degree
 |
 |      Examples
 |      --------
 |      >>> G = nx.DiGraph()
 |      >>> nx.add_path(G, [0, 1, 2, 3])
 |      >>> G.out_degree(0)  # node 0 with degree 1
 |      1
 |      >>> list(G.out_degree([0, 1, 2]))
 |      [(0, 1), (1, 1), (2, 1)]
 |
 |  out_edges = <functools.cached_property object>
 |      An OutEdgeView of the DiGraph as G.edges or G.edges().
 |
 |      edges(self, nbunch=None, data=False, default=None)
 |
 |      The OutEdgeView provides set-like operations on the edge-tuples
 |      as well as edge attribute lookup. When called, it also provides
 |      an EdgeDataView object which allows control of access to edge
 |      attributes (but does not provide set-like operations).
 |      Hence, `G.edges[u, v]['color']` provides the value of the color
 |      attribute for edge `(u, v)` while
 |      `for (u, v, c) in G.edges.data('color', default='red'):`
 |      iterates through all the edges yielding the color attribute
 |      with default `'red'` if no color attribute exists.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges from these nodes.
 |      data : string or bool, optional (default=False)
 |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
 |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
 |          If False, return 2-tuple (u, v).
 |      default : value, optional (default=None)
 |          Value used for edges that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      edges : OutEdgeView
 |          A view of edge attributes, usually it iterates over (u, v)
 |          or (u, v, d) tuples of edges, but can also be used for
 |          attribute lookup as `edges[u, v]['foo']`.
 |
 |      See Also
 |      --------
 |      in_edges, out_edges
 |
 |      Notes
 |      -----
 |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
 |      For directed graphs this returns the out-edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
 |      >>> nx.add_path(G, [0, 1, 2])
 |      >>> G.add_edge(2, 3, weight=5)
 |      >>> [e for e in G.edges]
 |      [(0, 1), (1, 2), (2, 3)]
 |      >>> G.edges.data()  # default data is {} (empty dict)
 |      OutEdgeDataView([(0, 1, {}), (1, 2, {}), (2, 3, {'weight': 5})])
 |      >>> G.edges.data("weight", default=1)
 |      OutEdgeDataView([(0, 1, 1), (1, 2, 1), (2, 3, 5)])
 |      >>> G.edges([0, 2])  # only edges originating from these nodes
 |      OutEdgeDataView([(0, 1), (2, 3)])
 |      >>> G.edges(0)  # only edges from node 0
 |      OutEdgeDataView([(0, 1)])
 |
 |  pred = <functools.cached_property object>
 |      Graph adjacency object holding the predecessors of each node.
 |
 |      This object is a read-only dict-like structure with node keys
 |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
 |      to the edge-data-dict.  So `G.pred[2][3]['color'] = 'blue'` sets
 |      the color of the edge `(3, 2)` to `"blue"`.
 |
 |      Iterating over G.pred behaves like a dict. Useful idioms include
 |      `for nbr, datadict in G.pred[n].items():`.  A data-view not provided
 |      by dicts also exists: `for nbr, foovalue in G.pred[node].data('foo'):`
 |      A default can be set via a `default` argument to the `data` method.
 |
 |  predecessors(self, n)
 |      Returns an iterator over predecessor nodes of n.
 |
 |      A predecessor of n is a node m such that there exists a directed
 |      edge from m to n.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Raises
 |      ------
 |      NetworkXError
 |         If n is not in the graph.
 |
 |      See Also
 |      --------
 |      successors
 |
 |  reverse(self, copy=True)
 |      Returns the reverse of the graph.
 |
 |      The reverse is a graph with the same nodes and edges
 |      but with the directions of the edges reversed.
 |
 |      Parameters
 |      ----------
 |      copy : bool optional (default=True)
 |          If True, return a new DiGraph holding the reversed edges.
 |          If False, the reverse graph is created using a view of
 |          the original graph.
 |
 |  succ = <functools.cached_property object>
 |      Graph adjacency object holding the successors of each node.
 |
 |      This object is a read-only dict-like structure with node keys
 |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
 |      to the edge-data-dict.  So `G.succ[3][2]['color'] = 'blue'` sets
 |      the color of the edge `(3, 2)` to `"blue"`.
 |
 |      Iterating over G.succ behaves like a dict. Useful idioms include
 |      `for nbr, datadict in G.succ[n].items():`.  A data-view not provided
 |      by dicts also exists: `for nbr, foovalue in G.succ[node].data('foo'):`
 |      and a default can be set via a `default` argument to the `data` method.
 |
 |      The neighbor information is also provided by subscripting the graph.
 |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
 |
 |      For directed graphs, `G.adj` is identical to `G.succ`.
 |
 |  successors(self, n)
 |      Returns an iterator over successor nodes of n.
 |
 |      A successor of n is a node m such that there exists a directed
 |      edge from n to m.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph
 |
 |      Raises
 |      ------
 |      NetworkXError
 |         If n is not in the graph.
 |
 |      See Also
 |      --------
 |      predecessors
 |
 |      Notes
 |      -----
 |      neighbors() and successors() are the same.
 |
 |  to_undirected(self, reciprocal=False, as_view=False)
 |      Returns an undirected representation of the digraph.
 |
 |      Parameters
 |      ----------
 |      reciprocal : bool (optional)
 |        If True only keep edges that appear in both directions
 |        in the original digraph.
 |      as_view : bool (optional, default=False)
 |        If True return an undirected view of the original directed graph.
 |
 |      Returns
 |      -------
 |      G : Graph
 |          An undirected graph with the same name and nodes and
 |          with edge (u, v, data) if either (u, v, data) or (v, u, data)
 |          is in the digraph.  If both edges exist in digraph and
 |          their edge data is different, only one edge is created
 |          with an arbitrary choice of which edge data to use.
 |          You must check and correct for this manually if desired.
 |
 |      See Also
 |      --------
 |      Graph, copy, add_edge, add_edges_from
 |
 |      Notes
 |      -----
 |      If edges in both directions (u, v) and (v, u) exist in the
 |      graph, attributes for the new undirected edge will be a combination of
 |      the attributes of the directed edges.  The edge data is updated
 |      in the (arbitrary) order that the edges are encountered.  For
 |      more customized control of the edge attributes use add_edge().
 |
 |      This returns a "deepcopy" of the edge, node, and
 |      graph attributes which attempts to completely copy
 |      all of the data and references.
 |
 |      This is in contrast to the similar G=DiGraph(D) which returns a
 |      shallow copy of the data.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Warning: If you have subclassed DiGraph to use dict-like objects
 |      in the data structure, those changes do not transfer to the
 |      Graph created by this method.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(2)  # or MultiGraph, etc
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1), (1, 0)]
 |      >>> G2 = H.to_undirected()
 |      >>> list(G2.edges)
 |      [(0, 1)]
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from networkx.classes.graph.Graph:
 |
 |  __contains__(self, n)
 |      Returns True if n is a node, False otherwise. Use: 'n in G'.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> 1 in G
 |      True
 |
 |  __getitem__(self, n)
 |      Returns a dict of neighbors of node n.  Use: 'G[n]'.
 |
 |      Parameters
 |      ----------
 |      n : node
 |         A node in the graph.
 |
 |      Returns
 |      -------
 |      adj_dict : dictionary
 |         The adjacency dictionary for nodes connected to n.
 |
 |      Notes
 |      -----
 |      G[n] is the same as G.adj[n] and similar to G.neighbors(n)
 |      (which is an iterator over G.adj[n])
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G[0]
 |      AtlasView({1: {}})
 |
 |  __iter__(self)
 |      Iterate over the nodes. Use: 'for n in G'.
 |
 |      Returns
 |      -------
 |      niter : iterator
 |          An iterator over all nodes in the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> [n for n in G]
 |      [0, 1, 2, 3]
 |      >>> list(G)
 |      [0, 1, 2, 3]
 |
 |  __len__(self)
 |      Returns the number of nodes in the graph. Use: 'len(G)'.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      number_of_nodes: identical method
 |      order: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> len(G)
 |      4
 |
 |  __str__(self)
 |      Returns a short summary of the graph.
 |
 |      Returns
 |      -------
 |      info : string
 |          Graph information including the graph name (if any), graph type, and the
 |          number of nodes and edges.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph(name="foo")
 |      >>> str(G)
 |      "Graph named 'foo' with 0 nodes and 0 edges"
 |
 |      >>> G = nx.path_graph(3)
 |      >>> str(G)
 |      'Graph with 3 nodes and 2 edges'
 |
 |  add_weighted_edges_from(self, ebunch_to_add, weight='weight', **attr)
 |      Add weighted edges in `ebunch_to_add` with specified weight attr
 |
 |      Parameters
 |      ----------
 |      ebunch_to_add : container of edges
 |          Each edge given in the list or container will be added
 |          to the graph. The edges must be given as 3-tuples (u, v, w)
 |          where w is a number.
 |      weight : string, optional (default= 'weight')
 |          The attribute name for the edge weights to be added.
 |      attr : keyword arguments, optional (default= no attributes)
 |          Edge attributes to add/update for all edges.
 |
 |      See Also
 |      --------
 |      add_edge : add a single edge
 |      add_edges_from : add multiple edges
 |
 |      Notes
 |      -----
 |      Adding the same edge twice for Graph/DiGraph simply updates
 |      the edge data. For MultiGraph/MultiDiGraph, duplicate edges
 |      are stored.
 |
 |      When adding edges from an iterator over the graph you are changing,
 |      a `RuntimeError` can be raised with message:
 |      `RuntimeError: dictionary changed size during iteration`. This
 |      happens when the graph's underlying dictionary is modified during
 |      iteration. To avoid this error, evaluate the iterator into a separate
 |      object, e.g. by using `list(iterator_of_edges)`, and pass this
 |      object to `G.add_weighted_edges_from`.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_weighted_edges_from([(0, 1, 3.0), (1, 2, 7.5)])
 |
 |      Evaluate an iterator over edges before passing it
 |
 |      >>> G = nx.Graph([(1, 2), (2, 3), (3, 4)])
 |      >>> weight = 0.1
 |      >>> # Grow graph by one new node, adding edges to all existing nodes.
 |      >>> # wrong way - will raise RuntimeError
 |      >>> # G.add_weighted_edges_from(((5, n, weight) for n in G.nodes))
 |      >>> # correct way - note that there will be no self-edge for node 5
 |      >>> G.add_weighted_edges_from(list((5, n, weight) for n in G.nodes))
 |
 |  adjacency(self)
 |      Returns an iterator over (node, adjacency dict) tuples for all nodes.
 |
 |      For directed graphs, only outgoing neighbors/adjacencies are included.
 |
 |      Returns
 |      -------
 |      adj_iter : iterator
 |         An iterator over (node, adjacency dictionary) for all nodes in
 |         the graph.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> [(n, nbrdict) for n, nbrdict in G.adjacency()]
 |      [(0, {1: {}}), (1, {0: {}, 2: {}}), (2, {1: {}, 3: {}}), (3, {2: {}})]
 |
 |  edge_subgraph(self, edges)
 |      Returns the subgraph induced by the specified edges.
 |
 |      The induced subgraph contains each edge in `edges` and each
 |      node incident to any one of those edges.
 |
 |      Parameters
 |      ----------
 |      edges : iterable
 |          An iterable of edges in this graph.
 |
 |      Returns
 |      -------
 |      G : Graph
 |          An edge-induced subgraph of this graph with the same edge
 |          attributes.
 |
 |      Notes
 |      -----
 |      The graph, edge, and node attributes in the returned subgraph
 |      view are references to the corresponding attributes in the original
 |      graph. The view is read-only.
 |
 |      To create a full graph version of the subgraph with its own copy
 |      of the edge or node attributes, use::
 |
 |          G.edge_subgraph(edges).copy()
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(5)
 |      >>> H = G.edge_subgraph([(0, 1), (3, 4)])
 |      >>> list(H.nodes)
 |      [0, 1, 3, 4]
 |      >>> list(H.edges)
 |      [(0, 1), (3, 4)]
 |
 |  get_edge_data(self, u, v, default=None)
 |      Returns the attribute dictionary associated with edge (u, v).
 |
 |      This is identical to `G[u][v]` except the default is returned
 |      instead of an exception if the edge doesn't exist.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |      default:  any Python object (default=None)
 |          Value to return if the edge (u, v) is not found.
 |
 |      Returns
 |      -------
 |      edge_dict : dictionary
 |          The edge attribute dictionary.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G[0][1]
 |      {}
 |
 |      Warning: Assigning to `G[u][v]` is not permitted.
 |      But it is safe to assign attributes `G[u][v]['foo']`
 |
 |      >>> G[0][1]["weight"] = 7
 |      >>> G[0][1]["weight"]
 |      7
 |      >>> G[1][0]["weight"]
 |      7
 |
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.get_edge_data(0, 1)  # default edge data is {}
 |      {}
 |      >>> e = (0, 1)
 |      >>> G.get_edge_data(*e)  # tuple form
 |      {}
 |      >>> G.get_edge_data("a", "b", default=0)  # edge not in graph, return 0
 |      0
 |
 |  has_edge(self, u, v)
 |      Returns True if the edge (u, v) is in the graph.
 |
 |      This is the same as `v in G[u]` without KeyError exceptions.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes
 |          Nodes can be, for example, strings or numbers.
 |          Nodes must be hashable (and not None) Python objects.
 |
 |      Returns
 |      -------
 |      edge_ind : bool
 |          True if edge is in the graph, False otherwise.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.has_edge(0, 1)  # using two nodes
 |      True
 |      >>> e = (0, 1)
 |      >>> G.has_edge(*e)  #  e is a 2-tuple (u, v)
 |      True
 |      >>> e = (0, 1, {"weight": 7})
 |      >>> G.has_edge(*e[:2])  # e is a 3-tuple (u, v, data_dictionary)
 |      True
 |
 |      The following syntax are equivalent:
 |
 |      >>> G.has_edge(0, 1)
 |      True
 |      >>> 1 in G[0]  # though this gives KeyError if 0 not in G
 |      True
 |
 |  has_node(self, n)
 |      Returns True if the graph contains the node n.
 |
 |      Identical to `n in G`
 |
 |      Parameters
 |      ----------
 |      n : node
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.has_node(0)
 |      True
 |
 |      It is more readable and simpler to use
 |
 |      >>> 0 in G
 |      True
 |
 |  nbunch_iter(self, nbunch=None)
 |      Returns an iterator over nodes contained in nbunch that are
 |      also in the graph.
 |
 |      The nodes in nbunch are checked for membership in the graph
 |      and if not are silently ignored.
 |
 |      Parameters
 |      ----------
 |      nbunch : single node, container, or all nodes (default= all nodes)
 |          The view will only report edges incident to these nodes.
 |
 |      Returns
 |      -------
 |      niter : iterator
 |          An iterator over nodes in nbunch that are also in the graph.
 |          If nbunch is None, iterate over all nodes in the graph.
 |
 |      Raises
 |      ------
 |      NetworkXError
 |          If nbunch is not a node or sequence of nodes.
 |          If a node in nbunch is not hashable.
 |
 |      See Also
 |      --------
 |      Graph.__iter__
 |
 |      Notes
 |      -----
 |      When nbunch is an iterator, the returned iterator yields values
 |      directly from nbunch, becoming exhausted when nbunch is exhausted.
 |
 |      To test whether nbunch is a single node, one can use
 |      "if nbunch in self:", even after processing with this routine.
 |
 |      If nbunch is not a node or a (possibly empty) sequence/iterator
 |      or None, a :exc:`NetworkXError` is raised.  Also, if any object in
 |      nbunch is not hashable, a :exc:`NetworkXError` is raised.
 |
 |  nodes = <functools.cached_property object>
 |      A NodeView of the Graph as G.nodes or G.nodes().
 |
 |      Can be used as `G.nodes` for data lookup and for set-like operations.
 |      Can also be used as `G.nodes(data='color', default=None)` to return a
 |      NodeDataView which reports specific node data but no set operations.
 |      It presents a dict-like interface as well with `G.nodes.items()`
 |      iterating over `(node, nodedata)` 2-tuples and `G.nodes[3]['foo']`
 |      providing the value of the `foo` attribute for node `3`. In addition,
 |      a view `G.nodes.data('foo')` provides a dict-like interface to the
 |      `foo` attribute of each node. `G.nodes.data('foo', default=1)`
 |      provides a default for nodes that do not have attribute `foo`.
 |
 |      Parameters
 |      ----------
 |      data : string or bool, optional (default=False)
 |          The node attribute returned in 2-tuple (n, ddict[data]).
 |          If True, return entire node attribute dict as (n, ddict).
 |          If False, return just the nodes n.
 |
 |      default : value, optional (default=None)
 |          Value used for nodes that don't have the requested attribute.
 |          Only relevant if data is not True or False.
 |
 |      Returns
 |      -------
 |      NodeView
 |          Allows set-like operations over the nodes as well as node
 |          attribute dict lookup and calling to get a NodeDataView.
 |          A NodeDataView iterates over `(n, data)` and has no set operations.
 |          A NodeView iterates over `n` and includes set operations.
 |
 |          When called, if data is False, an iterator over nodes.
 |          Otherwise an iterator of 2-tuples (node, attribute value)
 |          where the attribute is specified in `data`.
 |          If data is True then the attribute becomes the
 |          entire data dictionary.
 |
 |      Notes
 |      -----
 |      If your node data is not needed, it is simpler and equivalent
 |      to use the expression ``for n in G``, or ``list(G)``.
 |
 |      Examples
 |      --------
 |      There are two simple ways of getting a list of all nodes in the graph:
 |
 |      >>> G = nx.path_graph(3)
 |      >>> list(G.nodes)
 |      [0, 1, 2]
 |      >>> list(G)
 |      [0, 1, 2]
 |
 |      To get the node data along with the nodes:
 |
 |      >>> G.add_node(1, time="5pm")
 |      >>> G.nodes[0]["foo"] = "bar"
 |      >>> list(G.nodes(data=True))
 |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
 |      >>> list(G.nodes.data())
 |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
 |
 |      >>> list(G.nodes(data="foo"))
 |      [(0, 'bar'), (1, None), (2, None)]
 |      >>> list(G.nodes.data("foo"))
 |      [(0, 'bar'), (1, None), (2, None)]
 |
 |      >>> list(G.nodes(data="time"))
 |      [(0, None), (1, '5pm'), (2, None)]
 |      >>> list(G.nodes.data("time"))
 |      [(0, None), (1, '5pm'), (2, None)]
 |
 |      >>> list(G.nodes(data="time", default="Not Available"))
 |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
 |      >>> list(G.nodes.data("time", default="Not Available"))
 |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
 |
 |      If some of your nodes have an attribute and the rest are assumed
 |      to have a default attribute value you can create a dictionary
 |      from node/attribute pairs using the `default` keyword argument
 |      to guarantee the value is never None::
 |
 |          >>> G = nx.Graph()
 |          >>> G.add_node(0)
 |          >>> G.add_node(1, weight=2)
 |          >>> G.add_node(2, weight=3)
 |          >>> dict(G.nodes(data="weight", default=1))
 |          {0: 1, 1: 2, 2: 3}
 |
 |  number_of_edges(self, u=None, v=None)
 |      Returns the number of edges between two nodes.
 |
 |      Parameters
 |      ----------
 |      u, v : nodes, optional (default=all edges)
 |          If u and v are specified, return the number of edges between
 |          u and v. Otherwise return the total number of all edges.
 |
 |      Returns
 |      -------
 |      nedges : int
 |          The number of edges in the graph.  If nodes `u` and `v` are
 |          specified return the number of edges between those nodes. If
 |          the graph is directed, this only returns the number of edges
 |          from `u` to `v`.
 |
 |      See Also
 |      --------
 |      size
 |
 |      Examples
 |      --------
 |      For undirected graphs, this method counts the total number of
 |      edges in the graph:
 |
 |      >>> G = nx.path_graph(4)
 |      >>> G.number_of_edges()
 |      3
 |
 |      If you specify two nodes, this counts the total number of edges
 |      joining the two nodes:
 |
 |      >>> G.number_of_edges(0, 1)
 |      1
 |
 |      For directed graphs, this method can count the total number of
 |      directed edges from `u` to `v`:
 |
 |      >>> G = nx.DiGraph()
 |      >>> G.add_edge(0, 1)
 |      >>> G.add_edge(1, 0)
 |      >>> G.number_of_edges(0, 1)
 |      1
 |
 |  number_of_nodes(self)
 |      Returns the number of nodes in the graph.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      order: identical method
 |      __len__: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.number_of_nodes()
 |      3
 |
 |  order(self)
 |      Returns the number of nodes in the graph.
 |
 |      Returns
 |      -------
 |      nnodes : int
 |          The number of nodes in the graph.
 |
 |      See Also
 |      --------
 |      number_of_nodes: identical method
 |      __len__: identical method
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.order()
 |      3
 |
 |  size(self, weight=None)
 |      Returns the number of edges or total of all edge weights.
 |
 |      Parameters
 |      ----------
 |      weight : string or None, optional (default=None)
 |          The edge attribute that holds the numerical value used
 |          as a weight. If None, then each edge has weight 1.
 |
 |      Returns
 |      -------
 |      size : numeric
 |          The number of edges or
 |          (if weight keyword is provided) the total weight sum.
 |
 |          If weight is None, returns an int. Otherwise a float
 |          (or more general numeric if the weights are more general).
 |
 |      See Also
 |      --------
 |      number_of_edges
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.size()
 |      3
 |
 |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> G.add_edge("a", "b", weight=2)
 |      >>> G.add_edge("b", "c", weight=4)
 |      >>> G.size()
 |      2
 |      >>> G.size(weight="weight")
 |      6.0
 |
 |  subgraph(self, nodes)
 |      Returns a SubGraph view of the subgraph induced on `nodes`.
 |
 |      The induced subgraph of the graph contains the nodes in `nodes`
 |      and the edges between those nodes.
 |
 |      Parameters
 |      ----------
 |      nodes : list, iterable
 |          A container of nodes which will be iterated through once.
 |
 |      Returns
 |      -------
 |      G : SubGraph View
 |          A subgraph view of the graph. The graph structure cannot be
 |          changed but node/edge attributes can and are shared with the
 |          original graph.
 |
 |      Notes
 |      -----
 |      The graph, edge and node attributes are shared with the original graph.
 |      Changes to the graph structure is ruled out by the view, but changes
 |      to attributes are reflected in the original graph.
 |
 |      To create a subgraph with its own copy of the edge/node attributes use:
 |      G.subgraph(nodes).copy()
 |
 |      For an inplace reduction of a graph to a subgraph you can remove nodes:
 |      G.remove_nodes_from([n for n in G if n not in set(nodes)])
 |
 |      Subgraph views are sometimes NOT what you want. In most cases where
 |      you want to do more than simply look at the induced edges, it makes
 |      more sense to just create the subgraph as its own graph with code like:
 |
 |      ::
 |
 |          # Create a subgraph SG based on a (possibly multigraph) G
 |          SG = G.__class__()
 |          SG.add_nodes_from((n, G.nodes[n]) for n in largest_wcc)
 |          if SG.is_multigraph():
 |              SG.add_edges_from(
 |                  (n, nbr, key, d)
 |                  for n, nbrs in G.adj.items()
 |                  if n in largest_wcc
 |                  for nbr, keydict in nbrs.items()
 |                  if nbr in largest_wcc
 |                  for key, d in keydict.items()
 |              )
 |          else:
 |              SG.add_edges_from(
 |                  (n, nbr, d)
 |                  for n, nbrs in G.adj.items()
 |                  if n in largest_wcc
 |                  for nbr, d in nbrs.items()
 |                  if nbr in largest_wcc
 |              )
 |          SG.graph.update(G.graph)
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
 |      >>> H = G.subgraph([0, 1, 2])
 |      >>> list(H.edges)
 |      [(0, 1), (1, 2)]
 |
 |  to_directed(self, as_view=False)
 |      Returns a directed representation of the graph.
 |
 |      Returns
 |      -------
 |      G : DiGraph
 |          A directed graph with the same name, same nodes, and with
 |          each edge (u, v, data) replaced by two directed edges
 |          (u, v, data) and (v, u, data).
 |
 |      Notes
 |      -----
 |      This returns a "deepcopy" of the edge, node, and
 |      graph attributes which attempts to completely copy
 |      all of the data and references.
 |
 |      This is in contrast to the similar D=DiGraph(G) which returns a
 |      shallow copy of the data.
 |
 |      See the Python copy module for more information on shallow
 |      and deep copies, https://docs.python.org/3/library/copy.html.
 |
 |      Warning: If you have subclassed Graph to use dict-like objects
 |      in the data structure, those changes do not transfer to the
 |      DiGraph created by this method.
 |
 |      Examples
 |      --------
 |      >>> G = nx.Graph()  # or MultiGraph, etc
 |      >>> G.add_edge(0, 1)
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1), (1, 0)]
 |
 |      If already directed, return a (deep) copy
 |
 |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
 |      >>> G.add_edge(0, 1)
 |      >>> H = G.to_directed()
 |      >>> list(H.edges)
 |      [(0, 1)]
 |
 |  to_directed_class(self)
 |      Returns the class to use for empty directed copies.
 |
 |      If you subclass the base classes, use this to designate
 |      what directed class to use for `to_directed()` copies.
 |
 |  to_undirected_class(self)
 |      Returns the class to use for empty undirected copies.
 |
 |      If you subclass the base classes, use this to designate
 |      what directed class to use for `to_directed()` copies.
 |
 |  update(self, edges=None, nodes=None)
 |      Update the graph using nodes/edges/graphs as input.
 |
 |      Like dict.update, this method takes a graph as input, adding the
 |      graph's nodes and edges to this graph. It can also take two inputs:
 |      edges and nodes. Finally it can take either edges or nodes.
 |      To specify only nodes the keyword `nodes` must be used.
 |
 |      The collections of edges and nodes are treated similarly to
 |      the add_edges_from/add_nodes_from methods. When iterated, they
 |      should yield 2-tuples (u, v) or 3-tuples (u, v, datadict).
 |
 |      Parameters
 |      ----------
 |      edges : Graph object, collection of edges, or None
 |          The first parameter can be a graph or some edges. If it has
 |          attributes `nodes` and `edges`, then it is taken to be a
 |          Graph-like object and those attributes are used as collections
 |          of nodes and edges to be added to the graph.
 |          If the first parameter does not have those attributes, it is
 |          treated as a collection of edges and added to the graph.
 |          If the first argument is None, no edges are added.
 |      nodes : collection of nodes, or None
 |          The second parameter is treated as a collection of nodes
 |          to be added to the graph unless it is None.
 |          If `edges is None` and `nodes is None` an exception is raised.
 |          If the first parameter is a Graph, then `nodes` is ignored.
 |
 |      Examples
 |      --------
 |      >>> G = nx.path_graph(5)
 |      >>> G.update(nx.complete_graph(range(4, 10)))
 |      >>> from itertools import combinations
 |      >>> edges = (
 |      ...     (u, v, {"power": u * v})
 |      ...     for u, v in combinations(range(10, 20), 2)
 |      ...     if u * v < 225
 |      ... )
 |      >>> nodes = [1000]  # for singleton, use a container
 |      >>> G.update(edges, nodes)
 |
 |      Notes
 |      -----
 |      It you want to update the graph using an adjacency structure
 |      it is straightforward to obtain the edges/nodes from adjacency.
 |      The following examples provide common cases, your adjacency may
 |      be slightly different and require tweaks of these examples::
 |
 |      >>> # dict-of-set/list/tuple
 |      >>> adj = {1: {2, 3}, 2: {1, 3}, 3: {1, 2}}
 |      >>> e = [(u, v) for u, nbrs in adj.items() for v in nbrs]
 |      >>> G.update(edges=e, nodes=adj)
 |
 |      >>> DG = nx.DiGraph()
 |      >>> # dict-of-dict-of-attribute
 |      >>> adj = {1: {2: 1.3, 3: 0.7}, 2: {1: 1.4}, 3: {1: 0.7}}
 |      >>> e = [
 |      ...     (u, v, {"weight": d})
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, d in nbrs.items()
 |      ... ]
 |      >>> DG.update(edges=e, nodes=adj)
 |
 |      >>> # dict-of-dict-of-dict
 |      >>> adj = {1: {2: {"weight": 1.3}, 3: {"color": 0.7, "weight": 1.2}}}
 |      >>> e = [
 |      ...     (u, v, {"weight": d})
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, d in nbrs.items()
 |      ... ]
 |      >>> DG.update(edges=e, nodes=adj)
 |
 |      >>> # predecessor adjacency (dict-of-set)
 |      >>> pred = {1: {2, 3}, 2: {3}, 3: {3}}
 |      >>> e = [(v, u) for u, nbrs in pred.items() for v in nbrs]
 |
 |      >>> # MultiGraph dict-of-dict-of-dict-of-attribute
 |      >>> MDG = nx.MultiDiGraph()
 |      >>> adj = {
 |      ...     1: {2: {0: {"weight": 1.3}, 1: {"weight": 1.2}}},
 |      ...     3: {2: {0: {"weight": 0.7}}},
 |      ... }
 |      >>> e = [
 |      ...     (u, v, ekey, d)
 |      ...     for u, nbrs in adj.items()
 |      ...     for v, keydict in nbrs.items()
 |      ...     for ekey, d in keydict.items()
 |      ... ]
 |      >>> MDG.update(edges=e)
 |
 |      See Also
 |      --------
 |      add_edges_from: add multiple edges to a graph
 |      add_nodes_from: add multiple nodes to a graph
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from networkx.classes.graph.Graph:
 |
 |  __dict__
 |      dictionary for instance variables
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  name
 |      String identifier of the graph.
 |
 |      This graph attribute appears in the attribute dict G.graph
 |      keyed by the string `"name"`. as well as an attribute (technically
 |      a property) `G.name`. This is entirely user controlled.
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes inherited from networkx.classes.graph.Graph:
 |
 |  __networkx_backend__ = 'networkx'
 |
 |  adjlist_inner_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  adjlist_outer_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  edge_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  graph_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  node_attr_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
 |
 |
 |  node_dict_factory = <class 'dict'>
 |      dict() -> new empty dictionary
 |      dict(mapping) -> new dictionary initialized from a mapping object's
 |          (key, value) pairs
 |      dict(iterable) -> new dictionary initialized as if via:
 |          d = {}
 |          for k, v in iterable:
 |              d[k] = v
 |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
 |          in the keyword argument list.  For example:  dict(one=1, two=2)
networkx.PowerIterationFailedConvergence
Python Library Documentation: class PowerIterationFailedConvergence in module networkx.exception

class PowerIterationFailedConvergence(ExceededMaxIterations)
 |  PowerIterationFailedConvergence(num_iterations, *args, **kw)
 |
 |  Raised when the power iteration method fails to converge within a
 |  specified iteration limit.
 |
 |  `num_iterations` is the number of iterations that have been
 |  completed when this exception was raised.
 |
 |  Method resolution order:
 |      PowerIterationFailedConvergence
 |      ExceededMaxIterations
 |      NetworkXException
 |      builtins.Exception
 |      builtins.BaseException
 |      builtins.object
 |
 |  Methods defined here:
 |
 |  __init__(self, num_iterations, *args, **kw)
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from NetworkXException:
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from builtins.Exception:
 |
 |  __new__(*args, **kwargs) class method of builtins.Exception
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from builtins.BaseException:
 |
 |  __getattribute__(self, name, /)
 |      Return getattr(self, name).
 |
 |  __reduce__(...)
 |      Helper for pickle.
 |
 |  __repr__(self, /)
 |      Return repr(self).
 |
 |  __setstate__(...)
 |
 |  __str__(self, /)
 |      Return str(self).
 |
 |  add_note(...)
 |      Exception.add_note(note) --
 |      add a note to the exception
 |
 |  with_traceback(...)
 |      Exception.with_traceback(tb) --
 |      set self.__traceback__ to tb and return self.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors inherited from builtins.BaseException:
 |
 |  __cause__
 |      exception cause
 |
 |  __context__
 |      exception context
 |
 |  __dict__
 |
 |  __suppress_context__
 |
 |  __traceback__
 |
 |  args
networkx.SpanningTreeIterator
Python Library Documentation: class SpanningTreeIterator in module networkx.algorithms.tree.mst

class SpanningTreeIterator(builtins.object)
 |  SpanningTreeIterator(G, weight='weight', minimum=True, ignore_nan=False)
 |
 |  Iterate over all spanning trees of a graph in either increasing or
 |  decreasing cost.
 |
 |  Notes
 |  -----
 |  This iterator uses the partition scheme from [1]_ (included edges,
 |  excluded edges and open edges) as well as a modified Kruskal's Algorithm
 |  to generate minimum spanning trees which respect the partition of edges.
 |  For spanning trees with the same weight, ties are broken arbitrarily.
 |
 |  References
 |  ----------
 |  .. [1] G.K. Janssens, K. Sörensen, An algorithm to generate all spanning
 |         trees in order of increasing cost, Pesquisa Operacional, 2005-08,
 |         Vol. 25 (2), p. 219-229,
 |         https://www.scielo.br/j/pope/a/XHswBwRwJyrfL88dmMwYNWp/?lang=en
 |
 |  Methods defined here:
 |
 |  __init__(self, G, weight='weight', minimum=True, ignore_nan=False)
 |      Initialize the iterator
 |
 |      Parameters
 |      ----------
 |      G : nx.Graph
 |          The directed graph which we need to iterate trees over
 |
 |      weight : String, default = "weight"
 |          The edge attribute used to store the weight of the edge
 |
 |      minimum : bool, default = True
 |          Return the trees in increasing order while true and decreasing order
 |          while false.
 |
 |      ignore_nan : bool, default = False
 |          If a NaN is found as an edge weight normally an exception is raised.
 |          If `ignore_nan is True` then that edge is ignored instead.
 |
 |  __iter__(self)
 |      Returns
 |      -------
 |      SpanningTreeIterator
 |          The iterator object for this graph
 |
 |  __next__(self)
 |      Returns
 |      -------
 |      (multi)Graph
 |          The spanning tree of next greatest weight, which ties broken
 |          arbitrarily.
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors defined here:
 |
 |  __dict__
 |      dictionary for instance variables
 |
 |  __weakref__
 |      list of weak references to the object
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes defined here:
 |
 |  Partition = <class 'networkx.algorithms.tree.mst.SpanningTreeIterator....
 |      This dataclass represents a partition and stores a dict with the edge
 |      data and the weight of the minimum spanning tree of the partition dict.
networkx.adamic_adar_index
Python Library Documentation: function adamic_adar_index in module networkx.algorithms.link_prediction

adamic_adar_index(G, ebunch=None, *, backend=None, **backend_kwargs)
    Compute the Adamic-Adar index of all node pairs in ebunch.

    Adamic-Adar index of `u` and `v` is defined as

    .. math::

        \sum_{w \in \Gamma(u) \cap \Gamma(v)} \frac{1}{\log |\Gamma(w)|}

    where $\Gamma(u)$ denotes the set of neighbors of $u$.
    This index leads to zero-division for nodes only connected via self-loops.
    It is intended to be used when no self-loops are present.

    Parameters
    ----------
    G : graph
        NetworkX undirected graph.

    ebunch : iterable of node pairs, optional (default = None)
        Adamic-Adar index will be computed for each pair of nodes given
        in the iterable. The pairs must be given as 2-tuples (u, v)
        where u and v are nodes in the graph. If ebunch is None then all
        nonexistent edges in the graph will be used.
        Default value: None.

    Returns
    -------
    piter : iterator
        An iterator of 3-tuples in the form (u, v, p) where (u, v) is a
        pair of nodes and p is their Adamic-Adar index.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a `DiGraph`, a `Multigraph` or a `MultiDiGraph`.

    NodeNotFound
        If `ebunch` has a node that is not in `G`.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> preds = nx.adamic_adar_index(G, [(0, 1), (2, 3)])
    >>> for u, v, p in preds:
    ...     print(f"({u}, {v}) -> {p:.8f}")
    (0, 1) -> 2.16404256
    (2, 3) -> 2.16404256

    References
    ----------
    .. [1] D. Liben-Nowell, J. Kleinberg.
           The Link Prediction Problem for Social Networks (2004).
           http://www.cs.cornell.edu/home/kleinber/link-pred.pdf
networkx.add_cycle
Python Library Documentation: function add_cycle in module networkx.classes.function

add_cycle(G_to_add_to, nodes_for_cycle, **attr)
    Add a cycle to the Graph G_to_add_to.

    Parameters
    ----------
    G_to_add_to : graph
        A NetworkX graph
    nodes_for_cycle: iterable container
        A container of nodes.  A cycle will be constructed from
        the nodes (in order) and added to the graph.
    attr : keyword arguments, optional (default= no attributes)
        Attributes to add to every edge in cycle.

    See Also
    --------
    add_path, add_star

    Examples
    --------
    >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
    >>> nx.add_cycle(G, [0, 1, 2, 3])
    >>> nx.add_cycle(G, [10, 11, 12], weight=7)
networkx.add_path
Python Library Documentation: function add_path in module networkx.classes.function

add_path(G_to_add_to, nodes_for_path, **attr)
    Add a path to the Graph G_to_add_to.

    Parameters
    ----------
    G_to_add_to : graph
        A NetworkX graph
    nodes_for_path : iterable container
        A container of nodes.  A path will be constructed from
        the nodes (in order) and added to the graph.
    attr : keyword arguments, optional (default= no attributes)
        Attributes to add to every edge in path.

    See Also
    --------
    add_star, add_cycle

    Examples
    --------
    >>> G = nx.Graph()
    >>> nx.add_path(G, [0, 1, 2, 3])
    >>> nx.add_path(G, [10, 11, 12], weight=7)
networkx.add_star
Python Library Documentation: function add_star in module networkx.classes.function

add_star(G_to_add_to, nodes_for_star, **attr)
    Add a star to Graph G_to_add_to.

    The first node in `nodes_for_star` is the middle of the star.
    It is connected to all other nodes.

    Parameters
    ----------
    G_to_add_to : graph
        A NetworkX graph
    nodes_for_star : iterable container
        A container of nodes.
    attr : keyword arguments, optional (default= no attributes)
        Attributes to add to every edge in star.

    See Also
    --------
    add_path, add_cycle

    Examples
    --------
    >>> G = nx.Graph()
    >>> nx.add_star(G, [0, 1, 2, 3])
    >>> nx.add_star(G, [10, 11, 12], weight=2)
networkx.adjacency
Python Library Documentation: module networkx.readwrite.json_graph.adjacency in networkx.readwrite.json_graph

NAME
    networkx.readwrite.json_graph.adjacency

FUNCTIONS
    adjacency_data(G, attrs={'id': 'id', 'key': 'key'})
        Returns data in adjacency format that is suitable for JSON serialization
        and use in JavaScript documents.

        Parameters
        ----------
        G : NetworkX graph

        attrs : dict
            A dictionary that contains two keys 'id' and 'key'. The corresponding
            values provide the attribute names for storing NetworkX-internal graph
            data. The values should be unique. Default value:
            :samp:`dict(id='id', key='key')`.

            If some user-defined graph data use these attribute names as data keys,
            they may be silently dropped.

        Returns
        -------
        data : dict
           A dictionary with adjacency formatted data.

        Raises
        ------
        NetworkXError
            If values in attrs are not unique.

        Examples
        --------
        >>> from networkx.readwrite import json_graph
        >>> G = nx.Graph([(1, 2)])
        >>> data = json_graph.adjacency_data(G)

        To serialize with json

        >>> import json
        >>> s = json.dumps(data)

        Notes
        -----
        Graph, node, and link attributes will be written when using this format
        but attribute keys must be strings if you want to serialize the resulting
        data with JSON.

        The default value of attrs will be changed in a future release of NetworkX.

        See Also
        --------
        adjacency_graph, node_link_data, tree_data

    adjacency_graph(data, directed=False, multigraph=True, attrs={'id': 'id', 'key': 'key'}, *, backend=None, **backend_kwargs)
        Returns graph from adjacency data format.

        Parameters
        ----------
        data : dict
            Adjacency list formatted graph data

        directed : bool
            If True, and direction not specified in data, return a directed graph.

        multigraph : bool
            If True, and multigraph not specified in data, return a multigraph.

        attrs : dict
            A dictionary that contains two keys 'id' and 'key'. The corresponding
            values provide the attribute names for storing NetworkX-internal graph
            data. The values should be unique. Default value:
            :samp:`dict(id='id', key='key')`.

        Returns
        -------
        G : NetworkX graph
           A NetworkX graph object

        Examples
        --------
        >>> from networkx.readwrite import json_graph
        >>> G = nx.Graph([(1, 2)])
        >>> data = json_graph.adjacency_data(G)
        >>> H = json_graph.adjacency_graph(data)

        Notes
        -----
        The default value of attrs will be changed in a future release of NetworkX.

        See Also
        --------
        adjacency_graph, node_link_data, tree_data

DATA
    __all__ = ['adjacency_data', 'adjacency_graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\json_graph\adjacency.py

networkx.adjacency_data
Python Library Documentation: function adjacency_data in module networkx.readwrite.json_graph.adjacency

adjacency_data(G, attrs={'id': 'id', 'key': 'key'})
    Returns data in adjacency format that is suitable for JSON serialization
    and use in JavaScript documents.

    Parameters
    ----------
    G : NetworkX graph

    attrs : dict
        A dictionary that contains two keys 'id' and 'key'. The corresponding
        values provide the attribute names for storing NetworkX-internal graph
        data. The values should be unique. Default value:
        :samp:`dict(id='id', key='key')`.

        If some user-defined graph data use these attribute names as data keys,
        they may be silently dropped.

    Returns
    -------
    data : dict
       A dictionary with adjacency formatted data.

    Raises
    ------
    NetworkXError
        If values in attrs are not unique.

    Examples
    --------
    >>> from networkx.readwrite import json_graph
    >>> G = nx.Graph([(1, 2)])
    >>> data = json_graph.adjacency_data(G)

    To serialize with json

    >>> import json
    >>> s = json.dumps(data)

    Notes
    -----
    Graph, node, and link attributes will be written when using this format
    but attribute keys must be strings if you want to serialize the resulting
    data with JSON.

    The default value of attrs will be changed in a future release of NetworkX.

    See Also
    --------
    adjacency_graph, node_link_data, tree_data
networkx.adjacency_graph
Python Library Documentation: function adjacency_graph in module networkx.readwrite.json_graph.adjacency

adjacency_graph(data, directed=False, multigraph=True, attrs={'id': 'id', 'key': 'key'}, *, backend=None, **backend_kwargs)
    Returns graph from adjacency data format.

    Parameters
    ----------
    data : dict
        Adjacency list formatted graph data

    directed : bool
        If True, and direction not specified in data, return a directed graph.

    multigraph : bool
        If True, and multigraph not specified in data, return a multigraph.

    attrs : dict
        A dictionary that contains two keys 'id' and 'key'. The corresponding
        values provide the attribute names for storing NetworkX-internal graph
        data. The values should be unique. Default value:
        :samp:`dict(id='id', key='key')`.

    Returns
    -------
    G : NetworkX graph
       A NetworkX graph object

    Examples
    --------
    >>> from networkx.readwrite import json_graph
    >>> G = nx.Graph([(1, 2)])
    >>> data = json_graph.adjacency_data(G)
    >>> H = json_graph.adjacency_graph(data)

    Notes
    -----
    The default value of attrs will be changed in a future release of NetworkX.

    See Also
    --------
    adjacency_graph, node_link_data, tree_data
networkx.adjacency_matrix
Python Library Documentation: function adjacency_matrix in module networkx.linalg.graphmatrix

adjacency_matrix(G, nodelist=None, dtype=None, weight='weight', *, backend=None, **backend_kwargs)
    Returns adjacency matrix of `G`.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    nodelist : list, optional
       The rows and columns are ordered according to the nodes in `nodelist`.
       If ``nodelist=None`` (the default), then the ordering is produced by
       ``G.nodes()``.

    dtype : NumPy data-type, optional
        The desired data-type for the array.
        If `None`, then the NumPy default is used.

    weight : string or None, optional (default='weight')
       The edge data key used to provide each value in the matrix.
       If None, then each edge has weight 1.

    Returns
    -------
    A : SciPy sparse array
      Adjacency matrix representation of G.

    Notes
    -----
    For directed graphs, entry ``i, j`` corresponds to an edge from ``i`` to ``j``.

    If you want a pure Python adjacency matrix representation try
    :func:`~networkx.convert.to_dict_of_dicts` which will return a
    dictionary-of-dictionaries format that can be addressed as a
    sparse matrix.

    For multigraphs with parallel edges the weights are summed.
    See :func:`networkx.convert_matrix.to_numpy_array` for other options.

    The convention used for self-loop edges in graphs is to assign the
    diagonal matrix entry value to the edge weight attribute
    (or the number 1 if the edge has no weight attribute).  If the
    alternate convention of doubling the edge weight is desired the
    resulting SciPy sparse array can be modified as follows::

        >>> G = nx.Graph([(1, 1)])
        >>> A = nx.adjacency_matrix(G)
        >>> A.toarray()
        array([[1]])
        >>> A.setdiag(A.diagonal() * 2)
        >>> A.toarray()
        array([[2]])

    See Also
    --------
    to_numpy_array
    to_scipy_sparse_array
    to_dict_of_dicts
    adjacency_spectrum
networkx.adjacency_spectrum
Python Library Documentation: function adjacency_spectrum in module networkx.linalg.spectrum

adjacency_spectrum(G, weight='weight', *, backend=None, **backend_kwargs)
    Returns eigenvalues of the adjacency matrix of G.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    weight : string or None, optional (default='weight')
       The edge data key used to compute each value in the matrix.
       If None, then each edge has weight 1.

    Returns
    -------
    evals : NumPy array
      Eigenvalues

    Notes
    -----
    For MultiGraph/MultiDiGraph, the edges weights are summed.
    See to_numpy_array for other options.

    See Also
    --------
    adjacency_matrix
networkx.adjlist
Python Library Documentation: module networkx.readwrite.adjlist in networkx.readwrite

NAME
    networkx.readwrite.adjlist

DESCRIPTION
    **************
    Adjacency List
    **************
    Read and write NetworkX graphs as adjacency lists.

    Adjacency list format is useful for graphs without data associated
    with nodes or edges and for nodes that can be meaningfully represented
    as strings.

    Format
    ------
    The adjacency list format consists of lines with node labels.  The
    first label in a line is the source node.  Further labels in the line
    are considered target nodes and are added to the graph along with an edge
    between the source node and target node.

    The graph with edges a-b, a-c, d-e can be represented as the following
    adjacency list (anything following the # in a line is a comment)::

         a b c # source target target
         d e

FUNCTIONS
    generate_adjlist(G, delimiter=' ')
        Generate a single line of the graph G in adjacency list format.

        Parameters
        ----------
        G : NetworkX graph

        delimiter : string, optional
           Separator for node labels

        Returns
        -------
        lines : string
            Lines of data in adjlist format.

        Examples
        --------
        >>> G = nx.lollipop_graph(4, 3)
        >>> for line in nx.generate_adjlist(G):
        ...     print(line)
        0 1 2 3
        1 2 3
        2 3
        3 4
        4 5
        5 6
        6

        See Also
        --------
        write_adjlist, read_adjlist

        Notes
        -----
        The default `delimiter=" "` will result in unexpected results if node names contain
        whitespace characters. To avoid this problem, specify an alternate delimiter when spaces are
        valid in node names.

        NB: This option is not available for data that isn't user-generated.

    parse_adjlist(lines, comments='#', delimiter=None, create_using=None, nodetype=None, *, backend=None, **backend_kwargs)
        Parse lines of a graph adjacency list representation.

        Parameters
        ----------
        lines : list or iterator of strings
            Input data in adjlist format

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        nodetype : Python type, optional
           Convert nodes to this type.

        comments : string, optional
           Marker for comment lines

        delimiter : string, optional
           Separator for node labels.  The default is whitespace.

        Returns
        -------
        G: NetworkX graph
            The graph corresponding to the lines in adjacency list format.

        Examples
        --------
        >>> lines = ["1 2 5", "2 3 4", "3 5", "4", "5"]
        >>> G = nx.parse_adjlist(lines, nodetype=int)
        >>> nodes = [1, 2, 3, 4, 5]
        >>> all(node in G for node in nodes)
        True
        >>> edges = [(1, 2), (1, 5), (2, 3), (2, 4), (3, 5)]
        >>> all((u, v) in G.edges() or (v, u) in G.edges() for (u, v) in edges)
        True

        See Also
        --------
        read_adjlist

    read_adjlist(path, comments='#', delimiter=None, create_using=None, nodetype=None, encoding='utf-8', *, backend=None, **backend_kwargs)
        Read graph in adjacency list format from path.

        Parameters
        ----------
        path : string or file
           Filename or file handle to read.
           Filenames ending in .gz or .bz2 will be uncompressed.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        nodetype : Python type, optional
           Convert nodes to this type.

        comments : string, optional
           Marker for comment lines

        delimiter : string, optional
           Separator for node labels.  The default is whitespace.

        Returns
        -------
        G: NetworkX graph
            The graph corresponding to the lines in adjacency list format.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_adjlist(G, "test.adjlist")
        >>> G = nx.read_adjlist("test.adjlist")

        The path can be a filehandle or a string with the name of the file. If a
        filehandle is provided, it has to be opened in 'rb' mode.

        >>> fh = open("test.adjlist", "rb")
        >>> G = nx.read_adjlist(fh)

        Filenames ending in .gz or .bz2 will be compressed.

        >>> nx.write_adjlist(G, "test.adjlist.gz")
        >>> G = nx.read_adjlist("test.adjlist.gz")

        The optional nodetype is a function to convert node strings to nodetype.

        For example

        >>> G = nx.read_adjlist("test.adjlist", nodetype=int)

        will attempt to convert all nodes to integer type.

        Since nodes must be hashable, the function nodetype must return hashable
        types (e.g. int, float, str, frozenset - or tuples of those, etc.)

        The optional create_using parameter indicates the type of NetworkX graph
        created.  The default is `nx.Graph`, an undirected graph.
        To read the data as a directed graph use

        >>> G = nx.read_adjlist("test.adjlist", create_using=nx.DiGraph)

        Notes
        -----
        This format does not store graph or node data.

        See Also
        --------
        write_adjlist

    write_adjlist(G, path, comments='#', delimiter=' ', encoding='utf-8')
        Write graph G in single-line adjacency-list format to path.


        Parameters
        ----------
        G : NetworkX graph

        path : string or file
           Filename or file handle for data output.
           Filenames ending in .gz or .bz2 will be compressed.

        comments : string, optional
           Marker for comment lines

        delimiter : string, optional
           Separator for node labels

        encoding : string, optional
           Text encoding.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_adjlist(G, "test.adjlist")

        The path can be a filehandle or a string with the name of the file. If a
        filehandle is provided, it has to be opened in 'wb' mode.

        >>> fh = open("test.adjlist", "wb")
        >>> nx.write_adjlist(G, fh)

        Notes
        -----
        The default `delimiter=" "` will result in unexpected results if node names contain
        whitespace characters. To avoid this problem, specify an alternate delimiter when spaces are
        valid in node names.
        NB: This option is not available for data that isn't user-generated.

        This format does not store graph, node, or edge data.

        See Also
        --------
        read_adjlist, generate_adjlist

DATA
    __all__ = ['generate_adjlist', 'write_adjlist', 'parse_adjlist', 'read...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\adjlist.py

networkx.algebraic_connectivity
Python Library Documentation: function algebraic_connectivity in module networkx.linalg.algebraicconnectivity

algebraic_connectivity(G, weight='weight', normalized=False, tol=1e-08, method='tracemin_pcg', seed=None, *, backend=None, **backend_kwargs)
    Returns the algebraic connectivity of an undirected graph.

    The algebraic connectivity of a connected undirected graph is the second
    smallest eigenvalue of its Laplacian matrix.

    Parameters
    ----------
    G : NetworkX graph
        An undirected graph.

    weight : object, optional (default: None)
        The data key used to determine the weight of each edge. If None, then
        each edge has unit weight.

    normalized : bool, optional (default: False)
        Whether the normalized Laplacian matrix is used.

    tol : float, optional (default: 1e-8)
        Tolerance of relative residual in eigenvalue computation.

    method : string, optional (default: 'tracemin_pcg')
        Method of eigenvalue computation. It must be one of the tracemin
        options shown below (TraceMIN), 'lanczos' (Lanczos iteration)
        or 'lobpcg' (LOBPCG).

        The TraceMIN algorithm uses a linear system solver. The following
        values allow specifying the solver to be used.

        =============== ========================================
        Value           Solver
        =============== ========================================
        'tracemin_pcg'  Preconditioned conjugate gradient method
        'tracemin_lu'   LU factorization
        =============== ========================================

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    algebraic_connectivity : float
        Algebraic connectivity.

    Raises
    ------
    NetworkXNotImplemented
        If G is directed.

    NetworkXError
        If G has less than two nodes.

    Notes
    -----
    Edge weights are interpreted by their absolute values. For MultiGraph's,
    weights of parallel edges are summed. Zero-weighted edges are ignored.

    See Also
    --------
    laplacian_matrix

    Examples
    --------
    For undirected graphs algebraic connectivity can tell us if a graph is connected or not
    `G` is connected iff  ``algebraic_connectivity(G) > 0``:

    >>> G = nx.complete_graph(5)
    >>> nx.algebraic_connectivity(G) > 0
    True
    >>> G.add_node(10)  # G is no longer connected
    >>> nx.algebraic_connectivity(G) > 0
    False
networkx.algebraicconnectivity
Python Library Documentation: module networkx.linalg.algebraicconnectivity in networkx.linalg

NAME
    networkx.linalg.algebraicconnectivity - Algebraic connectivity and Fiedler vectors of undirected graphs.

FUNCTIONS
    algebraic_connectivity(G, weight='weight', normalized=False, tol=1e-08, method='tracemin_pcg', seed=None, *, backend=None, **backend_kwargs)
        Returns the algebraic connectivity of an undirected graph.

        The algebraic connectivity of a connected undirected graph is the second
        smallest eigenvalue of its Laplacian matrix.

        Parameters
        ----------
        G : NetworkX graph
            An undirected graph.

        weight : object, optional (default: None)
            The data key used to determine the weight of each edge. If None, then
            each edge has unit weight.

        normalized : bool, optional (default: False)
            Whether the normalized Laplacian matrix is used.

        tol : float, optional (default: 1e-8)
            Tolerance of relative residual in eigenvalue computation.

        method : string, optional (default: 'tracemin_pcg')
            Method of eigenvalue computation. It must be one of the tracemin
            options shown below (TraceMIN), 'lanczos' (Lanczos iteration)
            or 'lobpcg' (LOBPCG).

            The TraceMIN algorithm uses a linear system solver. The following
            values allow specifying the solver to be used.

            =============== ========================================
            Value           Solver
            =============== ========================================
            'tracemin_pcg'  Preconditioned conjugate gradient method
            'tracemin_lu'   LU factorization
            =============== ========================================

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        algebraic_connectivity : float
            Algebraic connectivity.

        Raises
        ------
        NetworkXNotImplemented
            If G is directed.

        NetworkXError
            If G has less than two nodes.

        Notes
        -----
        Edge weights are interpreted by their absolute values. For MultiGraph's,
        weights of parallel edges are summed. Zero-weighted edges are ignored.

        See Also
        --------
        laplacian_matrix

        Examples
        --------
        For undirected graphs algebraic connectivity can tell us if a graph is connected or not
        `G` is connected iff  ``algebraic_connectivity(G) > 0``:

        >>> G = nx.complete_graph(5)
        >>> nx.algebraic_connectivity(G) > 0
        True
        >>> G.add_node(10)  # G is no longer connected
        >>> nx.algebraic_connectivity(G) > 0
        False

    fiedler_vector(G, weight='weight', normalized=False, tol=1e-08, method='tracemin_pcg', seed=None, *, backend=None, **backend_kwargs)
        Returns the Fiedler vector of a connected undirected graph.

        The Fiedler vector of a connected undirected graph is the eigenvector
        corresponding to the second smallest eigenvalue of the Laplacian matrix
        of the graph.

        Parameters
        ----------
        G : NetworkX graph
            An undirected graph.

        weight : object, optional (default: None)
            The data key used to determine the weight of each edge. If None, then
            each edge has unit weight.

        normalized : bool, optional (default: False)
            Whether the normalized Laplacian matrix is used.

        tol : float, optional (default: 1e-8)
            Tolerance of relative residual in eigenvalue computation.

        method : string, optional (default: 'tracemin_pcg')
            Method of eigenvalue computation. It must be one of the tracemin
            options shown below (TraceMIN), 'lanczos' (Lanczos iteration)
            or 'lobpcg' (LOBPCG).

            The TraceMIN algorithm uses a linear system solver. The following
            values allow specifying the solver to be used.

            =============== ========================================
            Value           Solver
            =============== ========================================
            'tracemin_pcg'  Preconditioned conjugate gradient method
            'tracemin_lu'   LU factorization
            =============== ========================================

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        fiedler_vector : NumPy array of floats.
            Fiedler vector.

        Raises
        ------
        NetworkXNotImplemented
            If G is directed.

        NetworkXError
            If G has less than two nodes or is not connected.

        Notes
        -----
        Edge weights are interpreted by their absolute values. For MultiGraph's,
        weights of parallel edges are summed. Zero-weighted edges are ignored.

        See Also
        --------
        laplacian_matrix

        Examples
        --------
        Given a connected graph the signs of the values in the Fiedler vector can be
        used to partition the graph into two components.

        >>> G = nx.barbell_graph(5, 0)
        >>> nx.fiedler_vector(G, normalized=True, seed=1)
        array([-0.32864129, -0.32864129, -0.32864129, -0.32864129, -0.26072899,
                0.26072899,  0.32864129,  0.32864129,  0.32864129,  0.32864129])

        The connected components are the two 5-node cliques of the barbell graph.

    spectral_bisection(G, weight='weight', normalized=False, tol=1e-08, method='tracemin_pcg', seed=None, *, backend=None, **backend_kwargs)
        Bisect the graph using the Fiedler vector.

        This method uses the Fiedler vector to bisect a graph.
        The partition is defined by the nodes which are associated with
        either positive or negative values in the vector.

        Parameters
        ----------
        G : NetworkX Graph

        weight : str, optional (default: weight)
            The data key used to determine the weight of each edge. If None, then
            each edge has unit weight.

        normalized : bool, optional (default: False)
            Whether the normalized Laplacian matrix is used.

        tol : float, optional (default: 1e-8)
            Tolerance of relative residual in eigenvalue computation.

        method : string, optional (default: 'tracemin_pcg')
            Method of eigenvalue computation. It must be one of the tracemin
            options shown below (TraceMIN), 'lanczos' (Lanczos iteration)
            or 'lobpcg' (LOBPCG).

            The TraceMIN algorithm uses a linear system solver. The following
            values allow specifying the solver to be used.

            =============== ========================================
            Value           Solver
            =============== ========================================
            'tracemin_pcg'  Preconditioned conjugate gradient method
            'tracemin_lu'   LU factorization
            =============== ========================================

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        bisection : tuple of sets
            Sets with the bisection of nodes

        Examples
        --------
        >>> G = nx.barbell_graph(3, 0)
        >>> nx.spectral_bisection(G)
        ({0, 1, 2}, {3, 4, 5})

        References
        ----------
        .. [1] M. E. J Newman 'Networks: An Introduction', pages 364-370
           Oxford University Press 2011.

    spectral_ordering(G, weight='weight', normalized=False, tol=1e-08, method='tracemin_pcg', seed=None, *, backend=None, **backend_kwargs)
        Compute the spectral_ordering of a graph.

        The spectral ordering of a graph is an ordering of its nodes where nodes
        in the same weakly connected components appear contiguous and ordered by
        their corresponding elements in the Fiedler vector of the component.

        Parameters
        ----------
        G : NetworkX graph
            A graph.

        weight : object, optional (default: None)
            The data key used to determine the weight of each edge. If None, then
            each edge has unit weight.

        normalized : bool, optional (default: False)
            Whether the normalized Laplacian matrix is used.

        tol : float, optional (default: 1e-8)
            Tolerance of relative residual in eigenvalue computation.

        method : string, optional (default: 'tracemin_pcg')
            Method of eigenvalue computation. It must be one of the tracemin
            options shown below (TraceMIN), 'lanczos' (Lanczos iteration)
            or 'lobpcg' (LOBPCG).

            The TraceMIN algorithm uses a linear system solver. The following
            values allow specifying the solver to be used.

            =============== ========================================
            Value           Solver
            =============== ========================================
            'tracemin_pcg'  Preconditioned conjugate gradient method
            'tracemin_lu'   LU factorization
            =============== ========================================

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        spectral_ordering : NumPy array of floats.
            Spectral ordering of nodes.

        Raises
        ------
        NetworkXError
            If G is empty.

        Notes
        -----
        Edge weights are interpreted by their absolute values. For MultiGraph's,
        weights of parallel edges are summed. Zero-weighted edges are ignored.

        See Also
        --------
        laplacian_matrix

DATA
    __all__ = ['algebraic_connectivity', 'fiedler_vector', 'spectral_order...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\linalg\algebraicconnectivity.py

networkx.algorithms
Python Library Documentation: package networkx.algorithms in networkx

NAME
    networkx.algorithms

PACKAGE CONTENTS
    approximation (package)
    assortativity (package)
    asteroidal
    bipartite (package)
    boundary
    bridges
    broadcasting
    centrality (package)
    chains
    chordal
    clique
    cluster
    coloring (package)
    communicability_alg
    community (package)
    components (package)
    connectivity (package)
    core
    covering
    cuts
    cycles
    d_separation
    dag
    distance_measures
    distance_regular
    dominance
    dominating
    efficiency_measures
    euler
    flow (package)
    graph_hashing
    graphical
    hierarchy
    hybrid
    isolate
    isomorphism (package)
    link_analysis (package)
    link_prediction
    lowest_common_ancestors
    matching
    minors (package)
    mis
    moral
    node_classification
    non_randomness
    operators (package)
    planar_drawing
    planarity
    polynomials
    reciprocity
    regular
    richclub
    shortest_paths (package)
    similarity
    simple_paths
    smallworld
    smetric
    sparsifiers
    structuralholes
    summarization
    swap
    tests (package)
    threshold
    time_dependent
    tournament
    traversal (package)
    tree (package)
    triads
    vitality
    voronoi
    walks
    wiener

SUBMODULES
    all
    astar
    attracting
    beamsearch
    betweenness
    betweenness_subset
    biconnected
    binary
    breadth_first_search
    closeness
    connected
    correlation
    current_flow_betweenness
    current_flow_betweenness_subset
    current_flow_closeness
    degree_alg
    dense
    depth_first_search
    edgebfs
    edgedfs
    eigenvector
    flow_matrix
    generic
    group
    harmonic
    hits_alg
    katz
    laplacian
    load
    mixing
    neighbor_degree
    pagerank_alg
    pairs
    percolation
    product
    reaching
    second_order
    semiconnected
    strongly_connected
    subgraph_alg
    trophic
    unary
    unweighted
    voterank_alg
    weakly_connected
    weighted

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\__init__.py

networkx.all
Python Library Documentation: module networkx.algorithms.operators.all in networkx.algorithms.operators

NAME
    networkx.algorithms.operators.all - Operations on many graphs.

FUNCTIONS
    compose_all(graphs, *, backend=None, **backend_kwargs)
        Returns the composition of all graphs.

        Composition is the simple union of the node sets and edge sets.
        The node sets of the supplied graphs need not be disjoint.

        Parameters
        ----------
        graphs : iterable
           Iterable of NetworkX graphs

        Returns
        -------
        C : A graph with the same type as the first graph in list

        Raises
        ------
        ValueError
           If `graphs` is an empty list.

        NetworkXError
            In case of mixed type graphs, like MultiGraph and Graph, or directed and undirected graphs.

        Examples
        --------
        >>> G1 = nx.Graph([(1, 2), (2, 3)])
        >>> G2 = nx.Graph([(3, 4), (5, 6)])
        >>> C = nx.compose_all([G1, G2])
        >>> list(C.nodes())
        [1, 2, 3, 4, 5, 6]
        >>> list(C.edges())
        [(1, 2), (2, 3), (3, 4), (5, 6)]

        Notes
        -----
        For operating on mixed type graphs, they should be converted to the same type.

        Graph, edge, and node attributes are propagated to the union graph.
        If a graph attribute is present in multiple graphs, then the value
        from the last graph in the list with that attribute is used.

    disjoint_union_all(graphs, *, backend=None, **backend_kwargs)
        Returns the disjoint union of all graphs.

        This operation forces distinct integer node labels starting with 0
        for the first graph in the list and numbering consecutively.

        Parameters
        ----------
        graphs : iterable
           Iterable of NetworkX graphs

        Returns
        -------
        U : A graph with the same type as the first graph in list

        Raises
        ------
        ValueError
           If `graphs` is an empty list.

        NetworkXError
            In case of mixed type graphs, like MultiGraph and Graph, or directed and undirected graphs.

        Examples
        --------
        >>> G1 = nx.Graph([(1, 2), (2, 3)])
        >>> G2 = nx.Graph([(4, 5), (5, 6)])
        >>> U = nx.disjoint_union_all([G1, G2])
        >>> list(U.nodes())
        [0, 1, 2, 3, 4, 5]
        >>> list(U.edges())
        [(0, 1), (1, 2), (3, 4), (4, 5)]

        Notes
        -----
        For operating on mixed type graphs, they should be converted to the same type.

        Graph, edge, and node attributes are propagated to the union graph.
        If a graph attribute is present in multiple graphs, then the value
        from the last graph in the list with that attribute is used.

    intersection_all(graphs, *, backend=None, **backend_kwargs)
        Returns a new graph that contains only the nodes and the edges that exist in
        all graphs.

        Parameters
        ----------
        graphs : iterable
           Iterable of NetworkX graphs

        Returns
        -------
        R : A new graph with the same type as the first graph in list

        Raises
        ------
        ValueError
           If `graphs` is an empty list.

        NetworkXError
            In case of mixed type graphs, like MultiGraph and Graph, or directed and undirected graphs.

        Notes
        -----
        For operating on mixed type graphs, they should be converted to the same type.

        Attributes from the graph, nodes, and edges are not copied to the new
        graph.

        The resulting graph can be updated with attributes if desired. For example, code which adds the minimum attribute for each node across all graphs could work.
        >>> g = nx.Graph()
        >>> g.add_node(0, capacity=4)
        >>> g.add_node(1, capacity=3)
        >>> g.add_edge(0, 1)

        >>> h = g.copy()
        >>> h.nodes[0]["capacity"] = 2

        >>> gh = nx.intersection_all([g, h])

        >>> new_node_attr = {
        ...     n: min(*(anyG.nodes[n].get("capacity", float("inf")) for anyG in [g, h]))
        ...     for n in gh
        ... }
        >>> nx.set_node_attributes(gh, new_node_attr, "new_capacity")
        >>> gh.nodes(data=True)
        NodeDataView({0: {'new_capacity': 2}, 1: {'new_capacity': 3}})

        Examples
        --------
        >>> G1 = nx.Graph([(1, 2), (2, 3)])
        >>> G2 = nx.Graph([(2, 3), (3, 4)])
        >>> R = nx.intersection_all([G1, G2])
        >>> list(R.nodes())
        [2, 3]
        >>> list(R.edges())
        [(2, 3)]

    union_all(graphs, rename=(), *, backend=None, **backend_kwargs)
        Returns the union of all graphs.

        The graphs must be disjoint, otherwise an exception is raised.

        Parameters
        ----------
        graphs : iterable
           Iterable of NetworkX graphs

        rename : iterable , optional
           Node names of graphs can be changed by specifying the tuple
           rename=('G-','H-') (for example).  Node "u" in G is then renamed
           "G-u" and "v" in H is renamed "H-v". Infinite generators (like itertools.count)
           are also supported.

        Returns
        -------
        U : a graph with the same type as the first graph in list

        Raises
        ------
        ValueError
           If `graphs` is an empty list.

        NetworkXError
            In case of mixed type graphs, like MultiGraph and Graph, or directed and undirected graphs.

        Notes
        -----
        For operating on mixed type graphs, they should be converted to the same type.
        >>> G = nx.Graph()
        >>> H = nx.DiGraph()
        >>> GH = union_all([nx.DiGraph(G), H])

        To force a disjoint union with node relabeling, use
        disjoint_union_all(G,H) or convert_node_labels_to integers().

        Graph, edge, and node attributes are propagated to the union graph.
        If a graph attribute is present in multiple graphs, then the value
        from the last graph in the list with that attribute is used.

        Examples
        --------
        >>> G1 = nx.Graph([(1, 2), (2, 3)])
        >>> G2 = nx.Graph([(4, 5), (5, 6)])
        >>> result_graph = nx.union_all([G1, G2])
        >>> result_graph.nodes()
        NodeView((1, 2, 3, 4, 5, 6))
        >>> result_graph.edges()
        EdgeView([(1, 2), (2, 3), (4, 5), (5, 6)])

        See Also
        --------
        union
        disjoint_union_all

DATA
    __all__ = ['union_all', 'compose_all', 'disjoint_union_all', 'intersec...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\operators\all.py

networkx.all_neighbors
Python Library Documentation: function all_neighbors in module networkx.classes.function

all_neighbors(graph, node)
    Returns all of the neighbors of a node in the graph.

    If the graph is directed returns predecessors as well as successors.

    Parameters
    ----------
    graph : NetworkX graph
        Graph to find neighbors.

    node : node
        The node whose neighbors will be returned.

    Returns
    -------
    neighbors : iterator
        Iterator of neighbors
networkx.all_node_cuts
Python Library Documentation: function all_node_cuts in module networkx.algorithms.connectivity.kcutsets

all_node_cuts(G, k=None, flow_func=None, *, backend=None, **backend_kwargs)
    Returns all minimum k cutsets of an undirected graph G.

    This implementation is based on Kanevsky's algorithm [1]_ for finding all
    minimum-size node cut-sets of an undirected graph G; ie the set (or sets)
    of nodes of cardinality equal to the node connectivity of G. Thus if
    removed, would break G into two or more connected components.

    Parameters
    ----------
    G : NetworkX graph
        Undirected graph

    k : Integer
        Node connectivity of the input graph. If k is None, then it is
        computed. Default value: None.

    flow_func : function
        Function to perform the underlying flow computations. Default value is
        :func:`~networkx.algorithms.flow.edmonds_karp`. This function performs
        better in sparse graphs with right tailed degree distributions.
        :func:`~networkx.algorithms.flow.shortest_augmenting_path` will
        perform better in denser graphs.


    Returns
    -------
    cuts : a generator of node cutsets
        Each node cutset has cardinality equal to the node connectivity of
        the input graph.

    Examples
    --------
    >>> # A two-dimensional grid graph has 4 cutsets of cardinality 2
    >>> G = nx.grid_2d_graph(5, 5)
    >>> cutsets = list(nx.all_node_cuts(G))
    >>> len(cutsets)
    4
    >>> all(2 == len(cutset) for cutset in cutsets)
    True
    >>> nx.node_connectivity(G)
    2

    Notes
    -----
    This implementation is based on the sequential algorithm for finding all
    minimum-size separating vertex sets in a graph [1]_. The main idea is to
    compute minimum cuts using local maximum flow computations among a set
    of nodes of highest degree and all other non-adjacent nodes in the Graph.
    Once we find a minimum cut, we add an edge between the high degree
    node and the target node of the local maximum flow computation to make
    sure that we will not find that minimum cut again.

    See also
    --------
    node_connectivity
    edmonds_karp
    shortest_augmenting_path

    References
    ----------
    .. [1]  Kanevsky, A. (1993). Finding all minimum-size separating vertex
            sets in a graph. Networks 23(6), 533--541.
            http://onlinelibrary.wiley.com/doi/10.1002/net.3230230604/abstract
networkx.all_pairs_all_shortest_paths
Python Library Documentation: function all_pairs_all_shortest_paths in module networkx.algorithms.shortest_paths.generic

all_pairs_all_shortest_paths(G, weight=None, method='dijkstra', *, backend=None, **backend_kwargs)
    Compute all shortest paths between all nodes.

    Parameters
    ----------
    G : NetworkX graph

    weight : None, string or function, optional (default = None)
        If None, every edge has weight/distance/cost 1.
        If a string, use this edge attribute as the edge weight.
        Any edge attribute not present defaults to 1.
        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly
        three positional arguments: the two endpoints of an edge and
        the dictionary of edge attributes for that edge.
        The function must return a number.

    method : string, optional (default = 'dijkstra')
       The algorithm to use to compute the path lengths.
       Supported options: 'dijkstra', 'bellman-ford'.
       Other inputs produce a ValueError.
       If `weight` is None, unweighted graph methods are used, and this
       suggestion is ignored.

    Returns
    -------
    paths : generator of dictionary
        Dictionary of arrays, keyed by source and target, of all shortest paths.

    Raises
    ------
    ValueError
        If `method` is not among the supported options.

    Examples
    --------
    >>> G = nx.cycle_graph(4)
    >>> dict(nx.all_pairs_all_shortest_paths(G))[0][2]
    [[0, 1, 2], [0, 3, 2]]
    >>> dict(nx.all_pairs_all_shortest_paths(G))[0][3]
    [[0, 3]]

    Notes
    -----
    There may be multiple shortest paths with equal lengths. Unlike
    all_pairs_shortest_path, this method returns all shortest paths.

    See Also
    --------
    all_pairs_shortest_path
    single_source_all_shortest_paths
networkx.all_pairs_bellman_ford_path
Python Library Documentation: function all_pairs_bellman_ford_path in module networkx.algorithms.shortest_paths.weighted

all_pairs_bellman_ford_path(G, weight='weight', *, backend=None, **backend_kwargs)
    Compute shortest paths between all nodes in a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    weight : string or function (default="weight")
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

    Returns
    -------
    paths : iterator
        (source, dictionary) iterator with dictionary keyed by target and
        shortest path as the key value.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> path = dict(nx.all_pairs_bellman_ford_path(G))
    >>> path[0][4]
    [0, 1, 2, 3, 4]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    See Also
    --------
    floyd_warshall, all_pairs_dijkstra_path
networkx.all_pairs_bellman_ford_path_length
Python Library Documentation: function all_pairs_bellman_ford_path_length in module networkx.algorithms.shortest_paths.weighted

all_pairs_bellman_ford_path_length(G, weight='weight', *, backend=None, **backend_kwargs)
    Compute shortest path lengths between all nodes in a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    weight : string or function (default="weight")
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

    Returns
    -------
    distance : iterator
        (source, dictionary) iterator with dictionary keyed by target and
        shortest path length as the key value.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> length = dict(nx.all_pairs_bellman_ford_path_length(G))
    >>> for node in [0, 1, 2, 3, 4]:
    ...     print(f"1 - {node}: {length[1][node]}")
    1 - 0: 1
    1 - 1: 0
    1 - 2: 1
    1 - 3: 2
    1 - 4: 3
    >>> length[3][2]
    1
    >>> length[2][2]
    0

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The dictionary returned only has keys for reachable node pairs.
networkx.all_pairs_dijkstra
Python Library Documentation: function all_pairs_dijkstra in module networkx.algorithms.shortest_paths.weighted

all_pairs_dijkstra(G, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
    Find shortest weighted paths and lengths between all nodes.

    Parameters
    ----------
    G : NetworkX graph

    cutoff : integer or float, optional
        Length (sum of edge weights) at which the search is stopped.
        If cutoff is provided, only return paths with summed weight <= cutoff.

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edge[u][v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Yields
    ------
    (node, (distance, path)) : (node obj, (dict, dict))
        Each source node has two associated dicts. The first holds distance
        keyed by target and the second holds paths keyed by target.
        (See single_source_dijkstra for the source/target node terminology.)
        If desired you can apply `dict()` to this function to create a dict
        keyed by source node to the two dicts.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> len_path = dict(nx.all_pairs_dijkstra(G))
    >>> len_path[3][0][1]
    2
    >>> for node in [0, 1, 2, 3, 4]:
    ...     print(f"3 - {node}: {len_path[3][0][node]}")
    3 - 0: 3
    3 - 1: 2
    3 - 2: 1
    3 - 3: 0
    3 - 4: 1
    >>> len_path[3][1][1]
    [3, 2, 1]
    >>> for n, (dist, path) in nx.all_pairs_dijkstra(G):
    ...     print(path[1])
    [0, 1]
    [1]
    [2, 1]
    [3, 2, 1]
    [4, 3, 2, 1]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The yielded dicts only have keys for reachable nodes.
networkx.all_pairs_dijkstra_path
Python Library Documentation: function all_pairs_dijkstra_path in module networkx.algorithms.shortest_paths.weighted

all_pairs_dijkstra_path(G, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
    Compute shortest paths between all nodes in a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    cutoff : integer or float, optional
        Length (sum of edge weights) at which the search is stopped.
        If cutoff is provided, only return paths with summed weight <= cutoff.

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Returns
    -------
    paths : iterator
        (source, dictionary) iterator with dictionary keyed by target and
        shortest path as the key value.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> path = dict(nx.all_pairs_dijkstra_path(G))
    >>> path[0][4]
    [0, 1, 2, 3, 4]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    See Also
    --------
    floyd_warshall, all_pairs_bellman_ford_path
networkx.all_pairs_dijkstra_path_length
Python Library Documentation: function all_pairs_dijkstra_path_length in module networkx.algorithms.shortest_paths.weighted

all_pairs_dijkstra_path_length(G, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
    Compute shortest path lengths between all nodes in a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    cutoff : integer or float, optional
        Length (sum of edge weights) at which the search is stopped.
        If cutoff is provided, only return paths with summed weight <= cutoff.

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Returns
    -------
    distance : iterator
        (source, dictionary) iterator with dictionary keyed by target and
        shortest path length as the key value.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> length = dict(nx.all_pairs_dijkstra_path_length(G))
    >>> for node in [0, 1, 2, 3, 4]:
    ...     print(f"1 - {node}: {length[1][node]}")
    1 - 0: 1
    1 - 1: 0
    1 - 2: 1
    1 - 3: 2
    1 - 4: 3
    >>> length[3][2]
    1
    >>> length[2][2]
    0

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The dictionary returned only has keys for reachable node pairs.
networkx.all_pairs_lowest_common_ancestor
Python Library Documentation: function all_pairs_lowest_common_ancestor in module networkx.algorithms.lowest_common_ancestors

all_pairs_lowest_common_ancestor(G, pairs=None, *, backend=None, **backend_kwargs)
    Return the lowest common ancestor of all pairs or the provided pairs

    Parameters
    ----------
    G : NetworkX directed graph

    pairs : iterable of pairs of nodes, optional (default: all pairs)
        The pairs of nodes of interest.
        If None, will find the LCA of all pairs of nodes.

    Yields
    ------
    ((node1, node2), lca) : 2-tuple
        Where lca is least common ancestor of node1 and node2.
        Note that for the default case, the order of the node pair is not considered,
        e.g. you will not get both ``(a, b)`` and ``(b, a)``

    Raises
    ------
    NetworkXPointlessConcept
        If `G` is null.
    NetworkXError
        If `G` is not a DAG.

    Examples
    --------
    The default behavior is to yield the lowest common ancestor for all
    possible combinations of nodes in `G`, including self-pairings:

    >>> G = nx.DiGraph([(0, 1), (0, 3), (1, 2)])
    >>> dict(nx.all_pairs_lowest_common_ancestor(G))
    {(0, 0): 0, (0, 1): 0, (0, 3): 0, (0, 2): 0, (1, 1): 1, (1, 3): 0, (1, 2): 1, (3, 3): 3, (3, 2): 0, (2, 2): 2}

    The pairs argument can be used to limit the output to only the
    specified node pairings:

    >>> dict(nx.all_pairs_lowest_common_ancestor(G, pairs=[(1, 2), (2, 3)]))
    {(1, 2): 1, (2, 3): 0}

    Notes
    -----
    Only defined on non-null directed acyclic graphs.

    See Also
    --------
    lowest_common_ancestor
networkx.all_pairs_node_connectivity
Python Library Documentation: function all_pairs_node_connectivity in module networkx.algorithms.connectivity.connectivity

all_pairs_node_connectivity(G, nbunch=None, flow_func=None, *, backend=None, **backend_kwargs)
    Compute node connectivity between all pairs of nodes of G.

    Parameters
    ----------
    G : NetworkX graph
        Undirected graph

    nbunch: container
        Container of nodes. If provided node connectivity will be computed
        only over pairs of nodes in nbunch.

    flow_func : function
        A function for computing the maximum flow among a pair of nodes.
        The function has to accept at least three parameters: a Digraph,
        a source node, and a target node. And return a residual network
        that follows NetworkX conventions (see :meth:`maximum_flow` for
        details). If flow_func is None, the default maximum flow function
        (:meth:`edmonds_karp`) is used. See below for details. The
        choice of the default function may change from version
        to version and should not be relied on. Default value: None.

    Returns
    -------
    all_pairs : dict
        A dictionary with node connectivity between all pairs of nodes
        in G, or in nbunch if provided.

    See also
    --------
    :meth:`local_node_connectivity`
    :meth:`edge_connectivity`
    :meth:`local_edge_connectivity`
    :meth:`maximum_flow`
    :meth:`edmonds_karp`
    :meth:`preflow_push`
    :meth:`shortest_augmenting_path`
networkx.all_pairs_shortest_path
Python Library Documentation: function all_pairs_shortest_path in module networkx.algorithms.shortest_paths.unweighted

all_pairs_shortest_path(G, cutoff=None, *, backend=None, **backend_kwargs)
    Compute shortest paths between all nodes.

    Parameters
    ----------
    G : NetworkX graph

    cutoff : integer, optional
        Depth at which to stop the search. Only paths of length at most
        `cutoff` are returned.

    Returns
    -------
    paths : iterator
        Dictionary, keyed by source and target, of shortest paths.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> path = dict(nx.all_pairs_shortest_path(G))
    >>> print(path[0][4])
    [0, 1, 2, 3, 4]

    Notes
    -----
    There may be multiple shortest paths with the same length between
    two nodes. For each pair, this function returns only one of those paths.

    See Also
    --------
    floyd_warshall
    all_pairs_all_shortest_paths
networkx.all_pairs_shortest_path_length
Python Library Documentation: function all_pairs_shortest_path_length in module networkx.algorithms.shortest_paths.unweighted

all_pairs_shortest_path_length(G, cutoff=None, *, backend=None, **backend_kwargs)
    Computes the shortest path lengths between all nodes in `G`.

    Parameters
    ----------
    G : NetworkX graph

    cutoff : integer, optional
        Depth at which to stop the search. Only paths of length at most
        `cutoff` are returned.

    Returns
    -------
    lengths : iterator
        (source, dictionary) iterator with dictionary keyed by target and
        shortest path length as the key value.

    Notes
    -----
    The iterator returned only has reachable node pairs.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> length = dict(nx.all_pairs_shortest_path_length(G))
    >>> for node in [0, 1, 2, 3, 4]:
    ...     print(f"1 - {node}: {length[1][node]}")
    1 - 0: 1
    1 - 1: 0
    1 - 2: 1
    1 - 3: 2
    1 - 4: 3
    >>> length[3][2]
    1
    >>> length[2][2]
    0
networkx.all_shortest_paths
Python Library Documentation: function all_shortest_paths in module networkx.algorithms.shortest_paths.generic

all_shortest_paths(G, source, target, weight=None, method='dijkstra', *, backend=None, **backend_kwargs)
    Compute all shortest simple paths in the graph.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Starting node for path.

    target : node
       Ending node for path.

    weight : None, string or function, optional (default = None)
        If None, every edge has weight/distance/cost 1.
        If a string, use this edge attribute as the edge weight.
        Any edge attribute not present defaults to 1.
        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly
        three positional arguments: the two endpoints of an edge and
        the dictionary of edge attributes for that edge.
        The function must return a number.

    method : string, optional (default = 'dijkstra')
       The algorithm to use to compute the path lengths.
       Supported options: 'dijkstra', 'bellman-ford'.
       Other inputs produce a ValueError.
       If `weight` is None, unweighted graph methods are used, and this
       suggestion is ignored.

    Returns
    -------
    paths : generator of lists
        A generator of all paths between source and target.

    Raises
    ------
    ValueError
        If `method` is not among the supported options.

    NetworkXNoPath
        If `target` cannot be reached from `source`.

    Examples
    --------
    >>> G = nx.Graph()
    >>> nx.add_path(G, [0, 1, 2])
    >>> nx.add_path(G, [0, 10, 2])
    >>> print([p for p in nx.all_shortest_paths(G, source=0, target=2)])
    [[0, 1, 2], [0, 10, 2]]

    Notes
    -----
    There may be many shortest paths between the source and target.  If G
    contains zero-weight cycles, this function will not produce all shortest
    paths because doing so would produce infinitely many paths of unbounded
    length -- instead, we only produce the shortest simple paths.

    See Also
    --------
    shortest_path
    single_source_shortest_path
    all_pairs_shortest_path
networkx.all_simple_edge_paths
Python Library Documentation: function all_simple_edge_paths in module networkx.algorithms.simple_paths

all_simple_edge_paths(G, source, target, cutoff=None, *, backend=None, **backend_kwargs)
    Generate lists of edges for all simple paths in G from source to target.

    A simple path is a path with no repeated nodes.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Starting node for path

    target : nodes
       Single node or iterable of nodes at which to end path

    cutoff : integer, optional
        Depth to stop the search. Only paths of length <= cutoff are returned.

    Returns
    -------
    path_generator: generator
       A generator that produces lists of simple paths.  If there are no paths
       between the source and target within the given cutoff the generator
       produces no output.
       For multigraphs, the list of edges have elements of the form `(u,v,k)`.
       Where `k` corresponds to the edge key.

    Examples
    --------

    Print the simple path edges of a Graph::

        >>> g = nx.Graph([(1, 2), (2, 4), (1, 3), (3, 4)])
        >>> for path in sorted(nx.all_simple_edge_paths(g, 1, 4)):
        ...     print(path)
        [(1, 2), (2, 4)]
        [(1, 3), (3, 4)]

    Print the simple path edges of a MultiGraph. Returned edges come with
    their associated keys::

        >>> mg = nx.MultiGraph()
        >>> mg.add_edge(1, 2, key="k0")
        'k0'
        >>> mg.add_edge(1, 2, key="k1")
        'k1'
        >>> mg.add_edge(2, 3, key="k0")
        'k0'
        >>> for path in sorted(nx.all_simple_edge_paths(mg, 1, 3)):
        ...     print(path)
        [(1, 2, 'k0'), (2, 3, 'k0')]
        [(1, 2, 'k1'), (2, 3, 'k0')]

    When ``source`` is one of the targets, the empty path starting and ending at
    ``source`` without traversing any edge is considered a valid simple edge path
    and is included in the results:

        >>> G = nx.Graph()
        >>> G.add_node(0)
        >>> paths = list(nx.all_simple_edge_paths(G, 0, 0))
        >>> for path in paths:
        ...     print(path)
        []
        >>> len(paths)
        1


    Notes
    -----
    This algorithm uses a modified depth-first search to generate the
    paths [1]_.  A single path can be found in $O(V+E)$ time but the
    number of simple paths in a graph can be very large, e.g. $O(n!)$ in
    the complete graph of order $n$.

    References
    ----------
    .. [1] R. Sedgewick, "Algorithms in C, Part 5: Graph Algorithms",
       Addison Wesley Professional, 3rd ed., 2001.

    See Also
    --------
    all_shortest_paths, shortest_path, all_simple_paths
networkx.all_simple_paths
Python Library Documentation: function all_simple_paths in module networkx.algorithms.simple_paths

all_simple_paths(G, source, target, cutoff=None, *, backend=None, **backend_kwargs)
    Generate all simple paths in the graph G from source to target.

    A simple path is a path with no repeated nodes.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Starting node for path

    target : nodes
       Single node or iterable of nodes at which to end path

    cutoff : integer, optional
        Depth to stop the search. Only paths of length <= cutoff are returned.

    Returns
    -------
    path_generator: generator
       A generator that produces lists of simple paths.  If there are no paths
       between the source and target within the given cutoff the generator
       produces no output. If it is possible to traverse the same sequence of
       nodes in multiple ways, namely through parallel edges, then it will be
       returned multiple times (once for each viable edge combination).

    Examples
    --------
    This iterator generates lists of nodes::

        >>> G = nx.complete_graph(4)
        >>> for path in nx.all_simple_paths(G, source=0, target=3):
        ...     print(path)
        ...
        [0, 1, 2, 3]
        [0, 1, 3]
        [0, 2, 1, 3]
        [0, 2, 3]
        [0, 3]

    You can generate only those paths that are shorter than a certain
    length by using the `cutoff` keyword argument::

        >>> paths = nx.all_simple_paths(G, source=0, target=3, cutoff=2)
        >>> print(list(paths))
        [[0, 1, 3], [0, 2, 3], [0, 3]]

    To get each path as the corresponding list of edges, you can use the
    :func:`networkx.utils.pairwise` helper function::

        >>> paths = nx.all_simple_paths(G, source=0, target=3)
        >>> for path in map(nx.utils.pairwise, paths):
        ...     print(list(path))
        [(0, 1), (1, 2), (2, 3)]
        [(0, 1), (1, 3)]
        [(0, 2), (2, 1), (1, 3)]
        [(0, 2), (2, 3)]
        [(0, 3)]

    Pass an iterable of nodes as target to generate all paths ending in any of several nodes::

        >>> G = nx.complete_graph(4)
        >>> for path in nx.all_simple_paths(G, source=0, target=[3, 2]):
        ...     print(path)
        ...
        [0, 1, 2]
        [0, 1, 2, 3]
        [0, 1, 3]
        [0, 1, 3, 2]
        [0, 2]
        [0, 2, 1, 3]
        [0, 2, 3]
        [0, 3]
        [0, 3, 1, 2]
        [0, 3, 2]

    The singleton path from ``source`` to itself is considered a simple path and is
    included in the results:

        >>> G = nx.empty_graph(5)
        >>> list(nx.all_simple_paths(G, source=0, target=0))
        [[0]]

        >>> G = nx.path_graph(3)
        >>> list(nx.all_simple_paths(G, source=0, target={0, 1, 2}))
        [[0], [0, 1], [0, 1, 2]]

    Iterate over each path from the root nodes to the leaf nodes in a
    directed acyclic graph using a functional programming approach::

        >>> from itertools import chain
        >>> from itertools import product
        >>> from itertools import starmap
        >>> from functools import partial
        >>>
        >>> chaini = chain.from_iterable
        >>>
        >>> G = nx.DiGraph([(0, 1), (1, 2), (0, 3), (3, 2)])
        >>> roots = (v for v, d in G.in_degree() if d == 0)
        >>> leaves = (v for v, d in G.out_degree() if d == 0)
        >>> all_paths = partial(nx.all_simple_paths, G)
        >>> list(chaini(starmap(all_paths, product(roots, leaves))))
        [[0, 1, 2], [0, 3, 2]]

    The same list computed using an iterative approach::

        >>> G = nx.DiGraph([(0, 1), (1, 2), (0, 3), (3, 2)])
        >>> roots = (v for v, d in G.in_degree() if d == 0)
        >>> leaves = (v for v, d in G.out_degree() if d == 0)
        >>> all_paths = []
        >>> for root in roots:
        ...     for leaf in leaves:
        ...         paths = nx.all_simple_paths(G, root, leaf)
        ...         all_paths.extend(paths)
        >>> all_paths
        [[0, 1, 2], [0, 3, 2]]

    Iterate over each path from the root nodes to the leaf nodes in a
    directed acyclic graph passing all leaves together to avoid unnecessary
    compute::

        >>> G = nx.DiGraph([(0, 1), (2, 1), (1, 3), (1, 4)])
        >>> roots = (v for v, d in G.in_degree() if d == 0)
        >>> leaves = [v for v, d in G.out_degree() if d == 0]
        >>> all_paths = []
        >>> for root in roots:
        ...     paths = nx.all_simple_paths(G, root, leaves)
        ...     all_paths.extend(paths)
        >>> all_paths
        [[0, 1, 3], [0, 1, 4], [2, 1, 3], [2, 1, 4]]

    If parallel edges offer multiple ways to traverse a given sequence of
    nodes, this sequence of nodes will be returned multiple times:

        >>> G = nx.MultiDiGraph([(0, 1), (0, 1), (1, 2)])
        >>> list(nx.all_simple_paths(G, 0, 2))
        [[0, 1, 2], [0, 1, 2]]

    Notes
    -----
    This algorithm uses a modified depth-first search to generate the
    paths [1]_.  A single path can be found in $O(V+E)$ time but the
    number of simple paths in a graph can be very large, e.g. $O(n!)$ in
    the complete graph of order $n$.

    This function does not check that a path exists between `source` and
    `target`. For large graphs, this may result in very long runtimes.
    Consider using `has_path` to check that a path exists between `source` and
    `target` before calling this function on large graphs.

    References
    ----------
    .. [1] R. Sedgewick, "Algorithms in C, Part 5: Graph Algorithms",
       Addison Wesley Professional, 3rd ed., 2001.

    See Also
    --------
    all_shortest_paths, shortest_path, has_path
networkx.all_topological_sorts
Python Library Documentation: function all_topological_sorts in module networkx.algorithms.dag

all_topological_sorts(G, *, backend=None, **backend_kwargs)
    Returns a generator of _all_ topological sorts of the directed graph G.

    A topological sort is a nonunique permutation of the nodes such that an
    edge from u to v implies that u appears before v in the topological sort
    order.

    Parameters
    ----------
    G : NetworkX DiGraph
        A directed graph

    Yields
    ------
    topological_sort_order : list
        a list of nodes in `G`, representing one of the topological sort orders

    Raises
    ------
    NetworkXNotImplemented
        If `G` is not directed
    NetworkXUnfeasible
        If `G` is not acyclic

    Examples
    --------
    To enumerate all topological sorts of directed graph:

    >>> DG = nx.DiGraph([(1, 2), (2, 3), (2, 4)])
    >>> list(nx.all_topological_sorts(DG))
    [[1, 2, 4, 3], [1, 2, 3, 4]]

    Notes
    -----
    Implements an iterative version of the algorithm given in [1].

    References
    ----------
    .. [1] Knuth, Donald E., Szwarcfiter, Jayme L. (1974).
       "A Structured Program to Generate All Topological Sorting Arrangements"
       Information Processing Letters, Volume 2, Issue 6, 1974, Pages 153-157,
       ISSN 0020-0190,
       https://doi.org/10.1016/0020-0190(74)90001-5.
       Elsevier (North-Holland), Amsterdam
networkx.all_triads
Python Library Documentation: function all_triads in module networkx.algorithms.triads

all_triads(G, *, backend=None, **backend_kwargs)
    A generator of all possible triads in G.

    Parameters
    ----------
    G : digraph
       A NetworkX DiGraph

    Returns
    -------
    all_triads : generator of DiGraphs
       Generator of triads (order-3 DiGraphs)

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 1), (3, 4), (4, 1), (4, 2)])
    >>> for triad in nx.all_triads(G):
    ...     print(triad.edges)
    [(1, 2), (2, 3), (3, 1)]
    [(1, 2), (4, 1), (4, 2)]
    [(3, 1), (3, 4), (4, 1)]
    [(2, 3), (3, 4), (4, 2)]
networkx.all_triplets
Python Library Documentation: function all_triplets in module networkx.algorithms.triads

all_triplets(G, *, backend=None, **backend_kwargs)
    Returns a generator of all possible sets of 3 nodes in a DiGraph.

    .. deprecated:: 3.3

       all_triplets is deprecated and will be removed in NetworkX version 3.5.
       Use `itertools.combinations` instead::

          all_triplets = itertools.combinations(G, 3)

    Parameters
    ----------
    G : digraph
       A NetworkX DiGraph

    Returns
    -------
    triplets : generator of 3-tuples
       Generator of tuples of 3 nodes

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 4)])
    >>> list(nx.all_triplets(G))
    [(1, 2, 3), (1, 2, 4), (1, 3, 4), (2, 3, 4)]
networkx.ancestors
Python Library Documentation: function ancestors in module networkx.algorithms.dag

ancestors(G, source, *, backend=None, **backend_kwargs)
    Returns all nodes having a path to `source` in `G`.

    Parameters
    ----------
    G : NetworkX Graph
    source : node in `G`

    Returns
    -------
    set()
        The ancestors of `source` in `G`

    Raises
    ------
    NetworkXError
        If node `source` is not in `G`.

    Examples
    --------
    >>> DG = nx.path_graph(5, create_using=nx.DiGraph)
    >>> sorted(nx.ancestors(DG, 2))
    [0, 1]

    The `source` node is not an ancestor of itself, but can be included manually:

    >>> sorted(nx.ancestors(DG, 2) | {2})
    [0, 1, 2]

    See also
    --------
    descendants
networkx.antichains
Python Library Documentation: function antichains in module networkx.algorithms.dag

antichains(G, topo_order=None, *, backend=None, **backend_kwargs)
    Generates antichains from a directed acyclic graph (DAG).

    An antichain is a subset of a partially ordered set such that any
    two elements in the subset are incomparable.

    Parameters
    ----------
    G : NetworkX DiGraph
        A directed acyclic graph (DAG)

    topo_order: list or tuple, optional
        A topological order for G (if None, the function will compute one)

    Yields
    ------
    antichain : list
        a list of nodes in `G` representing an antichain

    Raises
    ------
    NetworkXNotImplemented
        If `G` is not directed

    NetworkXUnfeasible
        If `G` contains a cycle

    Examples
    --------
    >>> DG = nx.DiGraph([(1, 2), (1, 3)])
    >>> list(nx.antichains(DG))
    [[], [3], [2], [2, 3], [1]]

    Notes
    -----
    This function was originally developed by Peter Jipsen and Franco Saliola
    for the SAGE project. It's included in NetworkX with permission from the
    authors. Original SAGE code at:

    https://github.com/sagemath/sage/blob/master/src/sage/combinat/posets/hasse_diagram.py

    References
    ----------
    .. [1] Free Lattices, by R. Freese, J. Jezek and J. B. Nation,
       AMS, Vol 42, 1995, p. 226.
networkx.approximate_current_flow_betweenness_centrality
Python Library Documentation: function approximate_current_flow_betweenness_centrality in module networkx.algorithms.centrality.current_flow_betweenness

approximate_current_flow_betweenness_centrality(G, normalized=True, weight=None, dtype=<class 'float'>, solver='full', epsilon=0.5, kmax=10000, seed=None, *, backend=None, **backend_kwargs)
    Compute the approximate current-flow betweenness centrality for nodes.

    Approximates the current-flow betweenness centrality within absolute
    error of epsilon with high probability [1]_.


    Parameters
    ----------
    G : graph
      A NetworkX graph

    normalized : bool, optional (default=True)
      If True the betweenness values are normalized by 2/[(n-1)(n-2)] where
      n is the number of nodes in G.

    weight : string or None, optional (default=None)
      Key for edge data used as the edge weight.
      If None, then use 1 as each edge weight.
      The weight reflects the capacity or the strength of the
      edge.

    dtype : data type (float)
      Default data type for internal matrices.
      Set to np.float32 for lower memory consumption.

    solver : string (default='full')
       Type of linear solver to use for computing the flow matrix.
       Options are "full" (uses most memory), "lu" (recommended), and
       "cg" (uses least memory).

    epsilon: float
        Absolute error tolerance.

    kmax: int
       Maximum number of sample node pairs to use for approximation.

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with betweenness centrality as the value.

    See Also
    --------
    current_flow_betweenness_centrality

    Notes
    -----
    The running time is $O((1/\epsilon^2)m{\sqrt k} \log n)$
    and the space required is $O(m)$ for $n$ nodes and $m$ edges.

    If the edges have a 'weight' attribute they will be used as
    weights in this algorithm.  Unspecified weights are set to 1.

    References
    ----------
    .. [1] Ulrik Brandes and Daniel Fleischer:
       Centrality Measures Based on Current Flow.
       Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
       LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
       https://doi.org/10.1007/978-3-540-31856-9_44
networkx.approximation
Python Library Documentation: package networkx.algorithms.approximation in networkx.algorithms

NAME
    networkx.algorithms.approximation - Approximations of graph properties and Heuristic methods for optimization.

DESCRIPTION
    The functions in this class are not imported into the top-level ``networkx``
    namespace so the easiest way to use them is with::

        >>> from networkx.algorithms import approximation

    Another option is to import the specific function with
    ``from networkx.algorithms.approximation import function_name``.

PACKAGE CONTENTS
    clique
    clustering_coefficient
    connectivity
    distance_measures
    dominating_set
    kcomponents
    matching
    maxcut
    ramsey
    steinertree
    tests (package)
    traveling_salesman
    treewidth
    vertex_cover

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\approximation\__init__.py

networkx.arf_layout
Python Library Documentation: function arf_layout in module networkx.drawing.layout

arf_layout(G, pos=None, scaling=1, a=1.1, etol=1e-06, dt=0.001, max_iter=1000, *, seed=None)
    Arf layout for networkx

    The attractive and repulsive forces (arf) layout [1]
    improves the spring layout in three ways. First, it
    prevents congestion of highly connected nodes due to
    strong forcing between nodes. Second, it utilizes the
    layout space more effectively by preventing large gaps
    that spring layout tends to create. Lastly, the arf
    layout represents symmetries in the layout better than
    the default spring layout.

    Parameters
    ----------
    G : nx.Graph or nx.DiGraph
        Networkx graph.
    pos : dict
        Initial  position of  the nodes.  If set  to None  a
        random layout will be used.
    scaling : float
        Scales the radius of the circular layout space.
    a : float
        Strength of springs between connected nodes. Should be larger than 1. The greater a, the clearer the separation ofunconnected sub clusters.
    etol : float
        Gradient sum of spring forces must be larger than `etol` before successful termination.
    dt : float
        Time step for force differential equation simulations.
    max_iter : int
        Max iterations before termination of the algorithm.
    seed : int, RandomState instance or None  optional (default=None)
        Set the random state for deterministic node layouts.
        If int, `seed` is the seed used by the random number generator,
        if numpy.random.RandomState instance, `seed` is the random
        number generator,
        if None, the random number generator is the RandomState instance used
        by numpy.random.

    References
    .. [1] "Self-Organization Applied to Dynamic Network Layout", M. Geipel,
            International Journal of Modern Physics C, 2007, Vol 18, No 10, pp. 1537-1549.
            https://doi.org/10.1142/S0129183107011558 https://arxiv.org/abs/0704.1748

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node.

    Examples
    --------
    >>> G = nx.grid_graph((5, 5))
    >>> pos = nx.arf_layout(G)
networkx.articulation_points
Python Library Documentation: function articulation_points in module networkx.algorithms.components.biconnected

articulation_points(G, *, backend=None, **backend_kwargs)
    Yield the articulation points, or cut vertices, of a graph.

    An articulation point or cut vertex is any node whose removal (along with
    all its incident edges) increases the number of connected components of
    a graph.  An undirected connected graph without articulation points is
    biconnected. Articulation points belong to more than one biconnected
    component of a graph.

    Notice that by convention a dyad is considered a biconnected component.

    Parameters
    ----------
    G : NetworkX Graph
        An undirected graph.

    Yields
    ------
    node
        An articulation point in the graph.

    Raises
    ------
    NetworkXNotImplemented
        If the input graph is not undirected.

    Examples
    --------

    >>> G = nx.barbell_graph(4, 2)
    >>> print(nx.is_biconnected(G))
    False
    >>> len(list(nx.articulation_points(G)))
    4
    >>> G.add_edge(2, 8)
    >>> print(nx.is_biconnected(G))
    True
    >>> len(list(nx.articulation_points(G)))
    0

    See Also
    --------
    is_biconnected
    biconnected_components
    biconnected_component_edges

    Notes
    -----
    The algorithm to find articulation points and biconnected
    components is implemented using a non-recursive depth-first-search
    (DFS) that keeps track of the highest level that back edges reach
    in the DFS tree.  A node `n` is an articulation point if, and only
    if, there exists a subtree rooted at `n` such that there is no
    back edge from any successor of `n` that links to a predecessor of
    `n` in the DFS tree.  By keeping track of all the edges traversed
    by the DFS we can obtain the biconnected components because all
    edges of a bicomponent will be traversed consecutively between
    articulation points.

    References
    ----------
    .. [1] Hopcroft, J.; Tarjan, R. (1973).
           "Efficient algorithms for graph manipulation".
           Communications of the ACM 16: 372–378. doi:10.1145/362248.362272
networkx.assortativity
Python Library Documentation: package networkx.algorithms.assortativity in networkx.algorithms

NAME
    networkx.algorithms.assortativity

PACKAGE CONTENTS
    connectivity
    correlation
    mixing
    neighbor_degree
    pairs
    tests (package)

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\assortativity\__init__.py

networkx.astar
Python Library Documentation: module networkx.algorithms.shortest_paths.astar in networkx.algorithms.shortest_paths

NAME
    networkx.algorithms.shortest_paths.astar - Shortest paths and path lengths using the A* ("A star") algorithm.

FUNCTIONS
    astar_path(G, source, target, heuristic=None, weight='weight', *, cutoff=None, backend=None, **backend_kwargs)
        Returns a list of nodes in a shortest path between source and target
        using the A* ("A-star") algorithm.

        There may be more than one shortest path.  This returns only one.

        Parameters
        ----------
        G : NetworkX graph

        source : node
           Starting node for path

        target : node
           Ending node for path

        heuristic : function
           A function to evaluate the estimate of the distance
           from the a node to the target.  The function takes
           two nodes arguments and must return a number.
           If the heuristic is inadmissible (if it might
           overestimate the cost of reaching the goal from a node),
           the result may not be a shortest path.
           The algorithm does not support updating heuristic
           values for the same node due to caching the first
           heuristic calculation per node.

        weight : string or function
           If this is a string, then edge weights will be accessed via the
           edge attribute with this key (that is, the weight of the edge
           joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
           such edge attribute exists, the weight of the edge is assumed to
           be one.
           If this is a function, the weight of an edge is the value
           returned by the function. The function must accept exactly three
           positional arguments: the two endpoints of an edge and the
           dictionary of edge attributes for that edge. The function must
           return a number or None to indicate a hidden edge.

        cutoff : float, optional
           If this is provided, the search will be bounded to this value. I.e. if
           the evaluation function surpasses this value for a node n, the node will not
           be expanded further and will be ignored. More formally, let h'(n) be the
           heuristic function, and g(n) be the cost of reaching n from the source node. Then,
           if g(n) + h'(n) > cutoff, the node will not be explored further.
           Note that if the heuristic is inadmissible, it is possible that paths
           are ignored even though they satisfy the cutoff.

        Raises
        ------
        NetworkXNoPath
            If no path exists between source and target.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> print(nx.astar_path(G, 0, 4))
        [0, 1, 2, 3, 4]
        >>> G = nx.grid_graph(dim=[3, 3])  # nodes are two-tuples (x,y)
        >>> nx.set_edge_attributes(G, {e: e[1][0] * 2 for e in G.edges()}, "cost")
        >>> def dist(a, b):
        ...     (x1, y1) = a
        ...     (x2, y2) = b
        ...     return ((x1 - x2) ** 2 + (y1 - y2) ** 2) ** 0.5
        >>> print(nx.astar_path(G, (0, 0), (2, 2), heuristic=dist, weight="cost"))
        [(0, 0), (0, 1), (0, 2), (1, 2), (2, 2)]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The weight function can be used to hide edges by returning None.
        So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
        will find the shortest red path.

        See Also
        --------
        shortest_path, dijkstra_path

    astar_path_length(G, source, target, heuristic=None, weight='weight', *, cutoff=None, backend=None, **backend_kwargs)
        Returns the length of the shortest path between source and target using
        the A* ("A-star") algorithm.

        Parameters
        ----------
        G : NetworkX graph

        source : node
           Starting node for path

        target : node
           Ending node for path

        heuristic : function
           A function to evaluate the estimate of the distance
           from the a node to the target.  The function takes
           two nodes arguments and must return a number.
           If the heuristic is inadmissible (if it might
           overestimate the cost of reaching the goal from a node),
           the result may not be a shortest path.
           The algorithm does not support updating heuristic
           values for the same node due to caching the first
           heuristic calculation per node.

        weight : string or function
           If this is a string, then edge weights will be accessed via the
           edge attribute with this key (that is, the weight of the edge
           joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
           such edge attribute exists, the weight of the edge is assumed to
           be one.
           If this is a function, the weight of an edge is the value
           returned by the function. The function must accept exactly three
           positional arguments: the two endpoints of an edge and the
           dictionary of edge attributes for that edge. The function must
           return a number or None to indicate a hidden edge.

        cutoff : float, optional
           If this is provided, the search will be bounded to this value. I.e. if
           the evaluation function surpasses this value for a node n, the node will not
           be expanded further and will be ignored. More formally, let h'(n) be the
           heuristic function, and g(n) be the cost of reaching n from the source node. Then,
           if g(n) + h'(n) > cutoff, the node will not be explored further.
           Note that if the heuristic is inadmissible, it is possible that paths
           are ignored even though they satisfy the cutoff.

        Raises
        ------
        NetworkXNoPath
            If no path exists between source and target.

        See Also
        --------
        astar_path

DATA
    __all__ = ['astar_path', 'astar_path_length']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\shortest_paths\astar.py

networkx.astar_path
Python Library Documentation: function astar_path in module networkx.algorithms.shortest_paths.astar

astar_path(G, source, target, heuristic=None, weight='weight', *, cutoff=None, backend=None, **backend_kwargs)
    Returns a list of nodes in a shortest path between source and target
    using the A* ("A-star") algorithm.

    There may be more than one shortest path.  This returns only one.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Starting node for path

    target : node
       Ending node for path

    heuristic : function
       A function to evaluate the estimate of the distance
       from the a node to the target.  The function takes
       two nodes arguments and must return a number.
       If the heuristic is inadmissible (if it might
       overestimate the cost of reaching the goal from a node),
       the result may not be a shortest path.
       The algorithm does not support updating heuristic
       values for the same node due to caching the first
       heuristic calculation per node.

    weight : string or function
       If this is a string, then edge weights will be accessed via the
       edge attribute with this key (that is, the weight of the edge
       joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
       such edge attribute exists, the weight of the edge is assumed to
       be one.
       If this is a function, the weight of an edge is the value
       returned by the function. The function must accept exactly three
       positional arguments: the two endpoints of an edge and the
       dictionary of edge attributes for that edge. The function must
       return a number or None to indicate a hidden edge.

    cutoff : float, optional
       If this is provided, the search will be bounded to this value. I.e. if
       the evaluation function surpasses this value for a node n, the node will not
       be expanded further and will be ignored. More formally, let h'(n) be the
       heuristic function, and g(n) be the cost of reaching n from the source node. Then,
       if g(n) + h'(n) > cutoff, the node will not be explored further.
       Note that if the heuristic is inadmissible, it is possible that paths
       are ignored even though they satisfy the cutoff.

    Raises
    ------
    NetworkXNoPath
        If no path exists between source and target.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> print(nx.astar_path(G, 0, 4))
    [0, 1, 2, 3, 4]
    >>> G = nx.grid_graph(dim=[3, 3])  # nodes are two-tuples (x,y)
    >>> nx.set_edge_attributes(G, {e: e[1][0] * 2 for e in G.edges()}, "cost")
    >>> def dist(a, b):
    ...     (x1, y1) = a
    ...     (x2, y2) = b
    ...     return ((x1 - x2) ** 2 + (y1 - y2) ** 2) ** 0.5
    >>> print(nx.astar_path(G, (0, 0), (2, 2), heuristic=dist, weight="cost"))
    [(0, 0), (0, 1), (0, 2), (1, 2), (2, 2)]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The weight function can be used to hide edges by returning None.
    So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
    will find the shortest red path.

    See Also
    --------
    shortest_path, dijkstra_path
networkx.astar_path_length
Python Library Documentation: function astar_path_length in module networkx.algorithms.shortest_paths.astar

astar_path_length(G, source, target, heuristic=None, weight='weight', *, cutoff=None, backend=None, **backend_kwargs)
    Returns the length of the shortest path between source and target using
    the A* ("A-star") algorithm.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Starting node for path

    target : node
       Ending node for path

    heuristic : function
       A function to evaluate the estimate of the distance
       from the a node to the target.  The function takes
       two nodes arguments and must return a number.
       If the heuristic is inadmissible (if it might
       overestimate the cost of reaching the goal from a node),
       the result may not be a shortest path.
       The algorithm does not support updating heuristic
       values for the same node due to caching the first
       heuristic calculation per node.

    weight : string or function
       If this is a string, then edge weights will be accessed via the
       edge attribute with this key (that is, the weight of the edge
       joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
       such edge attribute exists, the weight of the edge is assumed to
       be one.
       If this is a function, the weight of an edge is the value
       returned by the function. The function must accept exactly three
       positional arguments: the two endpoints of an edge and the
       dictionary of edge attributes for that edge. The function must
       return a number or None to indicate a hidden edge.

    cutoff : float, optional
       If this is provided, the search will be bounded to this value. I.e. if
       the evaluation function surpasses this value for a node n, the node will not
       be expanded further and will be ignored. More formally, let h'(n) be the
       heuristic function, and g(n) be the cost of reaching n from the source node. Then,
       if g(n) + h'(n) > cutoff, the node will not be explored further.
       Note that if the heuristic is inadmissible, it is possible that paths
       are ignored even though they satisfy the cutoff.

    Raises
    ------
    NetworkXNoPath
        If no path exists between source and target.

    See Also
    --------
    astar_path
networkx.asteroidal
Python Library Documentation: module networkx.algorithms.asteroidal in networkx.algorithms

NAME
    networkx.algorithms.asteroidal - Algorithms for asteroidal triples and asteroidal numbers in graphs.

DESCRIPTION
    An asteroidal triple in a graph G is a set of three non-adjacent vertices
    u, v and w such that there exist a path between any two of them that avoids
    closed neighborhood of the third. More formally, v_j, v_k belongs to the same
    connected component of G - N[v_i], where N[v_i] denotes the closed neighborhood
    of v_i. A graph which does not contain any asteroidal triples is called
    an AT-free graph. The class of AT-free graphs is a graph class for which
    many NP-complete problems are solvable in polynomial time. Amongst them,
    independent set and coloring.

FUNCTIONS
    find_asteroidal_triple(G, *, backend=None, **backend_kwargs)
        Find an asteroidal triple in the given graph.

        An asteroidal triple is a triple of non-adjacent vertices such that
        there exists a path between any two of them which avoids the closed
        neighborhood of the third. It checks all independent triples of vertices
        and whether they are an asteroidal triple or not. This is done with the
        help of a data structure called a component structure.
        A component structure encodes information about which vertices belongs to
        the same connected component when the closed neighborhood of a given vertex
        is removed from the graph. The algorithm used to check is the trivial
        one, outlined in [1]_, which has a runtime of
        :math:`O(|V||\overline{E} + |V||E|)`, where the second term is the
        creation of the component structure.

        Parameters
        ----------
        G : NetworkX Graph
            The graph to check whether is AT-free or not

        Returns
        -------
        list or None
            An asteroidal triple is returned as a list of nodes. If no asteroidal
            triple exists, i.e. the graph is AT-free, then None is returned.
            The returned value depends on the certificate parameter. The default
            option is a bool which is True if the graph is AT-free, i.e. the
            given graph contains no asteroidal triples, and False otherwise, i.e.
            if the graph contains at least one asteroidal triple.

        Notes
        -----
        The component structure and the algorithm is described in [1]_. The current
        implementation implements the trivial algorithm for simple graphs.

        References
        ----------
        .. [1] Ekkehard Köhler,
           "Recognizing Graphs without asteroidal triples",
           Journal of Discrete Algorithms 2, pages 439-452, 2004.
           https://www.sciencedirect.com/science/article/pii/S157086670400019X

    is_at_free(G, *, backend=None, **backend_kwargs)
        Check if a graph is AT-free.

        The method uses the `find_asteroidal_triple` method to recognize
        an AT-free graph. If no asteroidal triple is found the graph is
        AT-free and True is returned. If at least one asteroidal triple is
        found the graph is not AT-free and False is returned.

        Parameters
        ----------
        G : NetworkX Graph
            The graph to check whether is AT-free or not.

        Returns
        -------
        bool
            True if G is AT-free and False otherwise.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (1, 2), (1, 3), (1, 4), (4, 5)])
        >>> nx.is_at_free(G)
        True

        >>> G = nx.cycle_graph(6)
        >>> nx.is_at_free(G)
        False

DATA
    __all__ = ['is_at_free', 'find_asteroidal_triple']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\asteroidal.py

networkx.atlas
Python Library Documentation: module networkx.generators.atlas in networkx.generators

NAME
    networkx.generators.atlas - Generators for the small graph atlas.

FUNCTIONS
    graph_atlas(i, *, backend=None, **backend_kwargs)
        Returns graph number `i` from the Graph Atlas.

        For more information, see :func:`.graph_atlas_g`.

        Parameters
        ----------
        i : int
            The index of the graph from the atlas to get. The graph at index
            0 is assumed to be the null graph.

        Returns
        -------
        list
            A list of :class:`~networkx.Graph` objects, the one at index *i*
            corresponding to the graph *i* in the Graph Atlas.

        See also
        --------
        graph_atlas_g

        Notes
        -----
        The time required by this function increases linearly with the
        argument `i`, since it reads a large file sequentially in order to
        generate the graph [1]_.

        References
        ----------
        .. [1] Ronald C. Read and Robin J. Wilson, *An Atlas of Graphs*.
               Oxford University Press, 1998.

    graph_atlas_g(*, backend=None, **backend_kwargs)
        Returns the list of all graphs with up to seven nodes named in the
        Graph Atlas.

        The graphs are listed in increasing order by

        1. number of nodes,
        2. number of edges,
        3. degree sequence (for example 111223 < 112222),
        4. number of automorphisms,

        in that order, with three exceptions as described in the *Notes*
        section below. This causes the list to correspond with the index of
        the graphs in the Graph Atlas [atlas]_, with the first graph,
        ``G[0]``, being the null graph.

        Returns
        -------
        list
            A list of :class:`~networkx.Graph` objects, the one at index *i*
            corresponding to the graph *i* in the Graph Atlas.

        See also
        --------
        graph_atlas

        Notes
        -----
        This function may be expensive in both time and space, since it
        reads a large file sequentially in order to populate the list.

        Although the NetworkX atlas functions match the order of graphs
        given in the "Atlas of Graphs" book, there are (at least) three
        errors in the ordering described in the book. The following three
        pairs of nodes violate the lexicographically nondecreasing sorted
        degree sequence rule:

        - graphs 55 and 56 with degree sequences 001111 and 000112,
        - graphs 1007 and 1008 with degree sequences 3333444 and 3333336,
        - graphs 1012 and 1213 with degree sequences 1244555 and 1244456.

        References
        ----------
        .. [atlas] Ronald C. Read and Robin J. Wilson,
                   *An Atlas of Graphs*.
                   Oxford University Press, 1998.

DATA
    __all__ = ['graph_atlas', 'graph_atlas_g']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\atlas.py

networkx.attr_matrix
Python Library Documentation: function attr_matrix in module networkx.linalg.attrmatrix

attr_matrix(G, edge_attr=None, node_attr=None, normalized=False, rc_order=None, dtype=None, order=None, *, backend=None, **backend_kwargs)
    Returns the attribute matrix using attributes from `G` as a numpy array.

    If only `G` is passed in, then the adjacency matrix is constructed.

    Let A be a discrete set of values for the node attribute `node_attr`. Then
    the elements of A represent the rows and columns of the constructed matrix.
    Now, iterate through every edge e=(u,v) in `G` and consider the value
    of the edge attribute `edge_attr`.  If ua and va are the values of the
    node attribute `node_attr` for u and v, respectively, then the value of
    the edge attribute is added to the matrix element at (ua, va).

    Parameters
    ----------
    G : graph
        The NetworkX graph used to construct the attribute matrix.

    edge_attr : str, optional
        Each element of the matrix represents a running total of the
        specified edge attribute for edges whose node attributes correspond
        to the rows/cols of the matrix. The attribute must be present for
        all edges in the graph. If no attribute is specified, then we
        just count the number of edges whose node attributes correspond
        to the matrix element.

    node_attr : str, optional
        Each row and column in the matrix represents a particular value
        of the node attribute.  The attribute must be present for all nodes
        in the graph. Note, the values of this attribute should be reliably
        hashable. So, float values are not recommended. If no attribute is
        specified, then the rows and columns will be the nodes of the graph.

    normalized : bool, optional
        If True, then each row is normalized by the summation of its values.

    rc_order : list, optional
        A list of the node attribute values. This list specifies the ordering
        of rows and columns of the array. If no ordering is provided, then
        the ordering will be random (and also, a return value).

    Other Parameters
    ----------------
    dtype : NumPy data-type, optional
        A valid NumPy dtype used to initialize the array. Keep in mind certain
        dtypes can yield unexpected results if the array is to be normalized.
        The parameter is passed to numpy.zeros(). If unspecified, the NumPy
        default is used.

    order : {'C', 'F'}, optional
        Whether to store multidimensional data in C- or Fortran-contiguous
        (row- or column-wise) order in memory. This parameter is passed to
        numpy.zeros(). If unspecified, the NumPy default is used.

    Returns
    -------
    M : 2D NumPy ndarray
        The attribute matrix.

    ordering : list
        If `rc_order` was specified, then only the attribute matrix is returned.
        However, if `rc_order` was None, then the ordering used to construct
        the matrix is returned as well.

    Examples
    --------
    Construct an adjacency matrix:

    >>> G = nx.Graph()
    >>> G.add_edge(0, 1, thickness=1, weight=3)
    >>> G.add_edge(0, 2, thickness=2)
    >>> G.add_edge(1, 2, thickness=3)
    >>> nx.attr_matrix(G, rc_order=[0, 1, 2])
    array([[0., 1., 1.],
           [1., 0., 1.],
           [1., 1., 0.]])

    Alternatively, we can obtain the matrix describing edge thickness.

    >>> nx.attr_matrix(G, edge_attr="thickness", rc_order=[0, 1, 2])
    array([[0., 1., 2.],
           [1., 0., 3.],
           [2., 3., 0.]])

    We can also color the nodes and ask for the probability distribution over
    all edges (u,v) describing:

        Pr(v has color Y | u has color X)

    >>> G.nodes[0]["color"] = "red"
    >>> G.nodes[1]["color"] = "red"
    >>> G.nodes[2]["color"] = "blue"
    >>> rc = ["red", "blue"]
    >>> nx.attr_matrix(G, node_attr="color", normalized=True, rc_order=rc)
    array([[0.33333333, 0.66666667],
           [1.        , 0.        ]])

    For example, the above tells us that for all edges (u,v):

        Pr( v is red  | u is red)  = 1/3
        Pr( v is blue | u is red)  = 2/3

        Pr( v is red  | u is blue) = 1
        Pr( v is blue | u is blue) = 0

    Finally, we can obtain the total weights listed by the node colors.

    >>> nx.attr_matrix(G, edge_attr="weight", node_attr="color", rc_order=rc)
    array([[3., 2.],
           [2., 0.]])

    Thus, the total weight over all edges (u,v) with u and v having colors:

        (red, red)   is 3   # the sole contribution is from edge (0,1)
        (red, blue)  is 2   # contributions from edges (0,2) and (1,2)
        (blue, red)  is 2   # same as (red, blue) since graph is undirected
        (blue, blue) is 0   # there are no edges with blue endpoints
networkx.attr_sparse_matrix
Python Library Documentation: function attr_sparse_matrix in module networkx.linalg.attrmatrix

attr_sparse_matrix(G, edge_attr=None, node_attr=None, normalized=False, rc_order=None, dtype=None, *, backend=None, **backend_kwargs)
    Returns a SciPy sparse array using attributes from G.

    If only `G` is passed in, then the adjacency matrix is constructed.

    Let A be a discrete set of values for the node attribute `node_attr`. Then
    the elements of A represent the rows and columns of the constructed matrix.
    Now, iterate through every edge e=(u,v) in `G` and consider the value
    of the edge attribute `edge_attr`.  If ua and va are the values of the
    node attribute `node_attr` for u and v, respectively, then the value of
    the edge attribute is added to the matrix element at (ua, va).

    Parameters
    ----------
    G : graph
        The NetworkX graph used to construct the NumPy matrix.

    edge_attr : str, optional
        Each element of the matrix represents a running total of the
        specified edge attribute for edges whose node attributes correspond
        to the rows/cols of the matrix. The attribute must be present for
        all edges in the graph. If no attribute is specified, then we
        just count the number of edges whose node attributes correspond
        to the matrix element.

    node_attr : str, optional
        Each row and column in the matrix represents a particular value
        of the node attribute.  The attribute must be present for all nodes
        in the graph. Note, the values of this attribute should be reliably
        hashable. So, float values are not recommended. If no attribute is
        specified, then the rows and columns will be the nodes of the graph.

    normalized : bool, optional
        If True, then each row is normalized by the summation of its values.

    rc_order : list, optional
        A list of the node attribute values. This list specifies the ordering
        of rows and columns of the array. If no ordering is provided, then
        the ordering will be random (and also, a return value).

    Other Parameters
    ----------------
    dtype : NumPy data-type, optional
        A valid NumPy dtype used to initialize the array. Keep in mind certain
        dtypes can yield unexpected results if the array is to be normalized.
        The parameter is passed to numpy.zeros(). If unspecified, the NumPy
        default is used.

    Returns
    -------
    M : SciPy sparse array
        The attribute matrix.

    ordering : list
        If `rc_order` was specified, then only the matrix is returned.
        However, if `rc_order` was None, then the ordering used to construct
        the matrix is returned as well.

    Examples
    --------
    Construct an adjacency matrix:

    >>> G = nx.Graph()
    >>> G.add_edge(0, 1, thickness=1, weight=3)
    >>> G.add_edge(0, 2, thickness=2)
    >>> G.add_edge(1, 2, thickness=3)
    >>> M = nx.attr_sparse_matrix(G, rc_order=[0, 1, 2])
    >>> M.toarray()
    array([[0., 1., 1.],
           [1., 0., 1.],
           [1., 1., 0.]])

    Alternatively, we can obtain the matrix describing edge thickness.

    >>> M = nx.attr_sparse_matrix(G, edge_attr="thickness", rc_order=[0, 1, 2])
    >>> M.toarray()
    array([[0., 1., 2.],
           [1., 0., 3.],
           [2., 3., 0.]])

    We can also color the nodes and ask for the probability distribution over
    all edges (u,v) describing:

        Pr(v has color Y | u has color X)

    >>> G.nodes[0]["color"] = "red"
    >>> G.nodes[1]["color"] = "red"
    >>> G.nodes[2]["color"] = "blue"
    >>> rc = ["red", "blue"]
    >>> M = nx.attr_sparse_matrix(G, node_attr="color", normalized=True, rc_order=rc)
    >>> M.toarray()
    array([[0.33333333, 0.66666667],
           [1.        , 0.        ]])

    For example, the above tells us that for all edges (u,v):

        Pr( v is red  | u is red)  = 1/3
        Pr( v is blue | u is red)  = 2/3

        Pr( v is red  | u is blue) = 1
        Pr( v is blue | u is blue) = 0

    Finally, we can obtain the total weights listed by the node colors.

    >>> M = nx.attr_sparse_matrix(G, edge_attr="weight", node_attr="color", rc_order=rc)
    >>> M.toarray()
    array([[3., 2.],
           [2., 0.]])

    Thus, the total weight over all edges (u,v) with u and v having colors:

        (red, red)   is 3   # the sole contribution is from edge (0,1)
        (red, blue)  is 2   # contributions from edges (0,2) and (1,2)
        (blue, red)  is 2   # same as (red, blue) since graph is undirected
        (blue, blue) is 0   # there are no edges with blue endpoints
networkx.attracting
Python Library Documentation: module networkx.algorithms.components.attracting in networkx.algorithms.components

NAME
    networkx.algorithms.components.attracting - Attracting components.

FUNCTIONS
    attracting_components(G, *, backend=None, **backend_kwargs)
        Generates the attracting components in `G`.

        An attracting component in a directed graph `G` is a strongly connected
        component with the property that a random walker on the graph will never
        leave the component, once it enters the component.

        The nodes in attracting components can also be thought of as recurrent
        nodes.  If a random walker enters the attractor containing the node, then
        the node will be visited infinitely often.

        To obtain induced subgraphs on each component use:
        ``(G.subgraph(c).copy() for c in attracting_components(G))``

        Parameters
        ----------
        G : DiGraph, MultiDiGraph
            The graph to be analyzed.

        Returns
        -------
        attractors : generator of sets
            A generator of sets of nodes, one for each attracting component of G.

        Raises
        ------
        NetworkXNotImplemented
            If the input graph is undirected.

        See Also
        --------
        number_attracting_components
        is_attracting_component

    is_attracting_component(G, *, backend=None, **backend_kwargs)
        Returns True if `G` consists of a single attracting component.

        Parameters
        ----------
        G : DiGraph, MultiDiGraph
            The graph to be analyzed.

        Returns
        -------
        attracting : bool
            True if `G` has a single attracting component. Otherwise, False.

        Raises
        ------
        NetworkXNotImplemented
            If the input graph is undirected.

        See Also
        --------
        attracting_components
        number_attracting_components

    number_attracting_components(G, *, backend=None, **backend_kwargs)
        Returns the number of attracting components in `G`.

        Parameters
        ----------
        G : DiGraph, MultiDiGraph
            The graph to be analyzed.

        Returns
        -------
        n : int
            The number of attracting components in G.

        Raises
        ------
        NetworkXNotImplemented
            If the input graph is undirected.

        See Also
        --------
        attracting_components
        is_attracting_component

DATA
    __all__ = ['number_attracting_components', 'attracting_components', 'i...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\components\attracting.py

networkx.attracting_components
Python Library Documentation: function attracting_components in module networkx.algorithms.components.attracting

attracting_components(G, *, backend=None, **backend_kwargs)
    Generates the attracting components in `G`.

    An attracting component in a directed graph `G` is a strongly connected
    component with the property that a random walker on the graph will never
    leave the component, once it enters the component.

    The nodes in attracting components can also be thought of as recurrent
    nodes.  If a random walker enters the attractor containing the node, then
    the node will be visited infinitely often.

    To obtain induced subgraphs on each component use:
    ``(G.subgraph(c).copy() for c in attracting_components(G))``

    Parameters
    ----------
    G : DiGraph, MultiDiGraph
        The graph to be analyzed.

    Returns
    -------
    attractors : generator of sets
        A generator of sets of nodes, one for each attracting component of G.

    Raises
    ------
    NetworkXNotImplemented
        If the input graph is undirected.

    See Also
    --------
    number_attracting_components
    is_attracting_component
networkx.attribute_assortativity_coefficient
Python Library Documentation: function attribute_assortativity_coefficient in module networkx.algorithms.assortativity.correlation

attribute_assortativity_coefficient(G, attribute, nodes=None, *, backend=None, **backend_kwargs)
    Compute assortativity for node attributes.

    Assortativity measures the similarity of connections
    in the graph with respect to the given attribute.

    Parameters
    ----------
    G : NetworkX graph

    attribute : string
        Node attribute key

    nodes: list or iterable (optional)
        Compute attribute assortativity for nodes in container.
        The default is all nodes.

    Returns
    -------
    r: float
       Assortativity of graph for given attribute

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_nodes_from([0, 1], color="red")
    >>> G.add_nodes_from([2, 3], color="blue")
    >>> G.add_edges_from([(0, 1), (2, 3)])
    >>> print(nx.attribute_assortativity_coefficient(G, "color"))
    1.0

    Notes
    -----
    This computes Eq. (2) in Ref. [1]_ , (trace(M)-sum(M^2))/(1-sum(M^2)),
    where M is the joint probability distribution (mixing matrix)
    of the specified attribute.

    References
    ----------
    .. [1] M. E. J. Newman, Mixing patterns in networks,
       Physical Review E, 67 026126, 2003
networkx.attribute_mixing_dict
Python Library Documentation: function attribute_mixing_dict in module networkx.algorithms.assortativity.mixing

attribute_mixing_dict(G, attribute, nodes=None, normalized=False, *, backend=None, **backend_kwargs)
    Returns dictionary representation of mixing matrix for attribute.

    Parameters
    ----------
    G : graph
       NetworkX graph object.

    attribute : string
       Node attribute key.

    nodes: list or iterable (optional)
        Unse nodes in container to build the dict. The default is all nodes.

    normalized : bool (default=False)
       Return counts if False or probabilities if True.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_nodes_from([0, 1], color="red")
    >>> G.add_nodes_from([2, 3], color="blue")
    >>> G.add_edge(1, 3)
    >>> d = nx.attribute_mixing_dict(G, "color")
    >>> print(d["red"]["blue"])
    1
    >>> print(d["blue"]["red"])  # d symmetric for undirected graphs
    1

    Returns
    -------
    d : dictionary
       Counts or joint probability of occurrence of attribute pairs.
networkx.attribute_mixing_matrix
Python Library Documentation: function attribute_mixing_matrix in module networkx.algorithms.assortativity.mixing

attribute_mixing_matrix(G, attribute, nodes=None, mapping=None, normalized=True, *, backend=None, **backend_kwargs)
    Returns mixing matrix for attribute.

    Parameters
    ----------
    G : graph
       NetworkX graph object.

    attribute : string
       Node attribute key.

    nodes: list or iterable (optional)
        Use only nodes in container to build the matrix. The default is
        all nodes.

    mapping : dictionary, optional
       Mapping from node attribute to integer index in matrix.
       If not specified, an arbitrary ordering will be used.

    normalized : bool (default=True)
       Return counts if False or probabilities if True.

    Returns
    -------
    m: numpy array
       Counts or joint probability of occurrence of attribute pairs.

    Notes
    -----
    If each node has a unique attribute value, the unnormalized mixing matrix
    will be equal to the adjacency matrix. To get a denser mixing matrix,
    the rounding can be performed to form groups of nodes with equal values.
    For example, the exact height of persons in cm (180.79155222, 163.9080892,
    163.30095355, 167.99016217, 168.21590163, ...) can be rounded to (180, 163,
    163, 168, 168, ...).

    Definitions of attribute mixing matrix vary on whether the matrix
    should include rows for attribute values that don't arise. Here we
    do not include such empty-rows. But you can force them to appear
    by inputting a `mapping` that includes those values.

    Examples
    --------
    >>> G = nx.path_graph(3)
    >>> gender = {0: "male", 1: "female", 2: "female"}
    >>> nx.set_node_attributes(G, gender, "gender")
    >>> mapping = {"male": 0, "female": 1}
    >>> mix_mat = nx.attribute_mixing_matrix(G, "gender", mapping=mapping)
    >>> mix_mat
    array([[0.  , 0.25],
           [0.25, 0.5 ]])
networkx.attrmatrix
Python Library Documentation: module networkx.linalg.attrmatrix in networkx.linalg

NAME
    networkx.linalg.attrmatrix - Functions for constructing matrix-like objects from graph attributes.

FUNCTIONS
    attr_matrix(G, edge_attr=None, node_attr=None, normalized=False, rc_order=None, dtype=None, order=None, *, backend=None, **backend_kwargs)
        Returns the attribute matrix using attributes from `G` as a numpy array.

        If only `G` is passed in, then the adjacency matrix is constructed.

        Let A be a discrete set of values for the node attribute `node_attr`. Then
        the elements of A represent the rows and columns of the constructed matrix.
        Now, iterate through every edge e=(u,v) in `G` and consider the value
        of the edge attribute `edge_attr`.  If ua and va are the values of the
        node attribute `node_attr` for u and v, respectively, then the value of
        the edge attribute is added to the matrix element at (ua, va).

        Parameters
        ----------
        G : graph
            The NetworkX graph used to construct the attribute matrix.

        edge_attr : str, optional
            Each element of the matrix represents a running total of the
            specified edge attribute for edges whose node attributes correspond
            to the rows/cols of the matrix. The attribute must be present for
            all edges in the graph. If no attribute is specified, then we
            just count the number of edges whose node attributes correspond
            to the matrix element.

        node_attr : str, optional
            Each row and column in the matrix represents a particular value
            of the node attribute.  The attribute must be present for all nodes
            in the graph. Note, the values of this attribute should be reliably
            hashable. So, float values are not recommended. If no attribute is
            specified, then the rows and columns will be the nodes of the graph.

        normalized : bool, optional
            If True, then each row is normalized by the summation of its values.

        rc_order : list, optional
            A list of the node attribute values. This list specifies the ordering
            of rows and columns of the array. If no ordering is provided, then
            the ordering will be random (and also, a return value).

        Other Parameters
        ----------------
        dtype : NumPy data-type, optional
            A valid NumPy dtype used to initialize the array. Keep in mind certain
            dtypes can yield unexpected results if the array is to be normalized.
            The parameter is passed to numpy.zeros(). If unspecified, the NumPy
            default is used.

        order : {'C', 'F'}, optional
            Whether to store multidimensional data in C- or Fortran-contiguous
            (row- or column-wise) order in memory. This parameter is passed to
            numpy.zeros(). If unspecified, the NumPy default is used.

        Returns
        -------
        M : 2D NumPy ndarray
            The attribute matrix.

        ordering : list
            If `rc_order` was specified, then only the attribute matrix is returned.
            However, if `rc_order` was None, then the ordering used to construct
            the matrix is returned as well.

        Examples
        --------
        Construct an adjacency matrix:

        >>> G = nx.Graph()
        >>> G.add_edge(0, 1, thickness=1, weight=3)
        >>> G.add_edge(0, 2, thickness=2)
        >>> G.add_edge(1, 2, thickness=3)
        >>> nx.attr_matrix(G, rc_order=[0, 1, 2])
        array([[0., 1., 1.],
               [1., 0., 1.],
               [1., 1., 0.]])

        Alternatively, we can obtain the matrix describing edge thickness.

        >>> nx.attr_matrix(G, edge_attr="thickness", rc_order=[0, 1, 2])
        array([[0., 1., 2.],
               [1., 0., 3.],
               [2., 3., 0.]])

        We can also color the nodes and ask for the probability distribution over
        all edges (u,v) describing:

            Pr(v has color Y | u has color X)

        >>> G.nodes[0]["color"] = "red"
        >>> G.nodes[1]["color"] = "red"
        >>> G.nodes[2]["color"] = "blue"
        >>> rc = ["red", "blue"]
        >>> nx.attr_matrix(G, node_attr="color", normalized=True, rc_order=rc)
        array([[0.33333333, 0.66666667],
               [1.        , 0.        ]])

        For example, the above tells us that for all edges (u,v):

            Pr( v is red  | u is red)  = 1/3
            Pr( v is blue | u is red)  = 2/3

            Pr( v is red  | u is blue) = 1
            Pr( v is blue | u is blue) = 0

        Finally, we can obtain the total weights listed by the node colors.

        >>> nx.attr_matrix(G, edge_attr="weight", node_attr="color", rc_order=rc)
        array([[3., 2.],
               [2., 0.]])

        Thus, the total weight over all edges (u,v) with u and v having colors:

            (red, red)   is 3   # the sole contribution is from edge (0,1)
            (red, blue)  is 2   # contributions from edges (0,2) and (1,2)
            (blue, red)  is 2   # same as (red, blue) since graph is undirected
            (blue, blue) is 0   # there are no edges with blue endpoints

    attr_sparse_matrix(G, edge_attr=None, node_attr=None, normalized=False, rc_order=None, dtype=None, *, backend=None, **backend_kwargs)
        Returns a SciPy sparse array using attributes from G.

        If only `G` is passed in, then the adjacency matrix is constructed.

        Let A be a discrete set of values for the node attribute `node_attr`. Then
        the elements of A represent the rows and columns of the constructed matrix.
        Now, iterate through every edge e=(u,v) in `G` and consider the value
        of the edge attribute `edge_attr`.  If ua and va are the values of the
        node attribute `node_attr` for u and v, respectively, then the value of
        the edge attribute is added to the matrix element at (ua, va).

        Parameters
        ----------
        G : graph
            The NetworkX graph used to construct the NumPy matrix.

        edge_attr : str, optional
            Each element of the matrix represents a running total of the
            specified edge attribute for edges whose node attributes correspond
            to the rows/cols of the matrix. The attribute must be present for
            all edges in the graph. If no attribute is specified, then we
            just count the number of edges whose node attributes correspond
            to the matrix element.

        node_attr : str, optional
            Each row and column in the matrix represents a particular value
            of the node attribute.  The attribute must be present for all nodes
            in the graph. Note, the values of this attribute should be reliably
            hashable. So, float values are not recommended. If no attribute is
            specified, then the rows and columns will be the nodes of the graph.

        normalized : bool, optional
            If True, then each row is normalized by the summation of its values.

        rc_order : list, optional
            A list of the node attribute values. This list specifies the ordering
            of rows and columns of the array. If no ordering is provided, then
            the ordering will be random (and also, a return value).

        Other Parameters
        ----------------
        dtype : NumPy data-type, optional
            A valid NumPy dtype used to initialize the array. Keep in mind certain
            dtypes can yield unexpected results if the array is to be normalized.
            The parameter is passed to numpy.zeros(). If unspecified, the NumPy
            default is used.

        Returns
        -------
        M : SciPy sparse array
            The attribute matrix.

        ordering : list
            If `rc_order` was specified, then only the matrix is returned.
            However, if `rc_order` was None, then the ordering used to construct
            the matrix is returned as well.

        Examples
        --------
        Construct an adjacency matrix:

        >>> G = nx.Graph()
        >>> G.add_edge(0, 1, thickness=1, weight=3)
        >>> G.add_edge(0, 2, thickness=2)
        >>> G.add_edge(1, 2, thickness=3)
        >>> M = nx.attr_sparse_matrix(G, rc_order=[0, 1, 2])
        >>> M.toarray()
        array([[0., 1., 1.],
               [1., 0., 1.],
               [1., 1., 0.]])

        Alternatively, we can obtain the matrix describing edge thickness.

        >>> M = nx.attr_sparse_matrix(G, edge_attr="thickness", rc_order=[0, 1, 2])
        >>> M.toarray()
        array([[0., 1., 2.],
               [1., 0., 3.],
               [2., 3., 0.]])

        We can also color the nodes and ask for the probability distribution over
        all edges (u,v) describing:

            Pr(v has color Y | u has color X)

        >>> G.nodes[0]["color"] = "red"
        >>> G.nodes[1]["color"] = "red"
        >>> G.nodes[2]["color"] = "blue"
        >>> rc = ["red", "blue"]
        >>> M = nx.attr_sparse_matrix(G, node_attr="color", normalized=True, rc_order=rc)
        >>> M.toarray()
        array([[0.33333333, 0.66666667],
               [1.        , 0.        ]])

        For example, the above tells us that for all edges (u,v):

            Pr( v is red  | u is red)  = 1/3
            Pr( v is blue | u is red)  = 2/3

            Pr( v is red  | u is blue) = 1
            Pr( v is blue | u is blue) = 0

        Finally, we can obtain the total weights listed by the node colors.

        >>> M = nx.attr_sparse_matrix(G, edge_attr="weight", node_attr="color", rc_order=rc)
        >>> M.toarray()
        array([[3., 2.],
               [2., 0.]])

        Thus, the total weight over all edges (u,v) with u and v having colors:

            (red, red)   is 3   # the sole contribution is from edge (0,1)
            (red, blue)  is 2   # contributions from edges (0,2) and (1,2)
            (blue, red)  is 2   # same as (red, blue) since graph is undirected
            (blue, blue) is 0   # there are no edges with blue endpoints

DATA
    __all__ = ['attr_matrix', 'attr_sparse_matrix']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\linalg\attrmatrix.py

networkx.average_clustering
Python Library Documentation: function average_clustering in module networkx.algorithms.cluster

average_clustering(G, nodes=None, weight=None, count_zeros=True, *, backend=None, **backend_kwargs)
    Compute the average clustering coefficient for the graph G.

    The clustering coefficient for the graph is the average,

    .. math::

       C = \frac{1}{n}\sum_{v \in G} c_v,

    where :math:`n` is the number of nodes in `G`.

    Parameters
    ----------
    G : graph

    nodes : container of nodes, optional (default=all nodes in G)
       Compute average clustering for nodes in this container.

    weight : string or None, optional (default=None)
       The edge attribute that holds the numerical value used as a weight.
       If None, then each edge has weight 1.

    count_zeros : bool
       If False include only the nodes with nonzero clustering in the average.

    Returns
    -------
    avg : float
       Average clustering

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> print(nx.average_clustering(G))
    1.0

    Notes
    -----
    This is a space saving routine; it might be faster
    to use the clustering function to get a list and then take the average.

    Self loops are ignored.

    References
    ----------
    .. [1] Generalizations of the clustering coefficient to weighted
       complex networks by J. Saramäki, M. Kivelä, J.-P. Onnela,
       K. Kaski, and J. Kertész, Physical Review E, 75 027105 (2007).
       http://jponnela.com/web_documents/a9.pdf
    .. [2] Marcus Kaiser,  Mean clustering coefficients: the role of isolated
       nodes and leafs on clustering measures for small-world networks.
       https://arxiv.org/abs/0802.2512
networkx.average_degree_connectivity
Python Library Documentation: function average_degree_connectivity in module networkx.algorithms.assortativity.connectivity

average_degree_connectivity(G, source='in+out', target='in+out', nodes=None, weight=None, *, backend=None, **backend_kwargs)
    Compute the average degree connectivity of graph.

    The average degree connectivity is the average nearest neighbor degree of
    nodes with degree k. For weighted graphs, an analogous measure can
    be computed using the weighted average neighbors degree defined in
    [1]_, for a node `i`, as

    .. math::

        k_{nn,i}^{w} = \frac{1}{s_i} \sum_{j \in N(i)} w_{ij} k_j

    where `s_i` is the weighted degree of node `i`,
    `w_{ij}` is the weight of the edge that links `i` and `j`,
    and `N(i)` are the neighbors of node `i`.

    Parameters
    ----------
    G : NetworkX graph

    source :  "in"|"out"|"in+out" (default:"in+out")
       Directed graphs only. Use "in"- or "out"-degree for source node.

    target : "in"|"out"|"in+out" (default:"in+out"
       Directed graphs only. Use "in"- or "out"-degree for target node.

    nodes : list or iterable (optional)
        Compute neighbor connectivity for these nodes. The default is all
        nodes.

    weight : string or None, optional (default=None)
       The edge attribute that holds the numerical value used as a weight.
       If None, then each edge has weight 1.

    Returns
    -------
    d : dict
       A dictionary keyed by degree k with the value of average connectivity.

    Raises
    ------
    NetworkXError
        If either `source` or `target` are not one of 'in',
        'out', or 'in+out'.
        If either `source` or `target` is passed for an undirected graph.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> G.edges[1, 2]["weight"] = 3
    >>> nx.average_degree_connectivity(G)
    {1: 2.0, 2: 1.5}
    >>> nx.average_degree_connectivity(G, weight="weight")
    {1: 2.0, 2: 1.75}

    See Also
    --------
    average_neighbor_degree

    References
    ----------
    .. [1] A. Barrat, M. Barthélemy, R. Pastor-Satorras, and A. Vespignani,
       "The architecture of complex weighted networks".
       PNAS 101 (11): 3747–3752 (2004).
networkx.average_neighbor_degree
Python Library Documentation: function average_neighbor_degree in module networkx.algorithms.assortativity.neighbor_degree

average_neighbor_degree(G, source='out', target='out', nodes=None, weight=None, *, backend=None, **backend_kwargs)
    Returns the average degree of the neighborhood of each node.

    In an undirected graph, the neighborhood `N(i)` of node `i` contains the
    nodes that are connected to `i` by an edge.

    For directed graphs, `N(i)` is defined according to the parameter `source`:

        - if source is 'in', then `N(i)` consists of predecessors of node `i`.
        - if source is 'out', then `N(i)` consists of successors of node `i`.
        - if source is 'in+out', then `N(i)` is both predecessors and successors.

    The average neighborhood degree of a node `i` is

    .. math::

        k_{nn,i} = \frac{1}{|N(i)|} \sum_{j \in N(i)} k_j

    where `N(i)` are the neighbors of node `i` and `k_j` is
    the degree of node `j` which belongs to `N(i)`. For weighted
    graphs, an analogous measure can be defined [1]_,

    .. math::

        k_{nn,i}^{w} = \frac{1}{s_i} \sum_{j \in N(i)} w_{ij} k_j

    where `s_i` is the weighted degree of node `i`, `w_{ij}`
    is the weight of the edge that links `i` and `j` and
    `N(i)` are the neighbors of node `i`.


    Parameters
    ----------
    G : NetworkX graph

    source : string ("in"|"out"|"in+out"), optional (default="out")
       Directed graphs only.
       Use "in"- or "out"-neighbors of source node.

    target : string ("in"|"out"|"in+out"), optional (default="out")
       Directed graphs only.
       Use "in"- or "out"-degree for target node.

    nodes : list or iterable, optional (default=G.nodes)
        Compute neighbor degree only for specified nodes.

    weight : string or None, optional (default=None)
       The edge attribute that holds the numerical value used as a weight.
       If None, then each edge has weight 1.

    Returns
    -------
    d: dict
       A dictionary keyed by node to the average degree of its neighbors.

    Raises
    ------
    NetworkXError
        If either `source` or `target` are not one of 'in', 'out', or 'in+out'.
        If either `source` or `target` is passed for an undirected graph.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> G.edges[0, 1]["weight"] = 5
    >>> G.edges[2, 3]["weight"] = 3

    >>> nx.average_neighbor_degree(G)
    {0: 2.0, 1: 1.5, 2: 1.5, 3: 2.0}
    >>> nx.average_neighbor_degree(G, weight="weight")
    {0: 2.0, 1: 1.1666666666666667, 2: 1.25, 3: 2.0}

    >>> G = nx.DiGraph()
    >>> nx.add_path(G, [0, 1, 2, 3])
    >>> nx.average_neighbor_degree(G, source="in", target="in")
    {0: 0.0, 1: 0.0, 2: 1.0, 3: 1.0}

    >>> nx.average_neighbor_degree(G, source="out", target="out")
    {0: 1.0, 1: 1.0, 2: 0.0, 3: 0.0}

    See Also
    --------
    average_degree_connectivity

    References
    ----------
    .. [1] A. Barrat, M. Barthélemy, R. Pastor-Satorras, and A. Vespignani,
       "The architecture of complex weighted networks".
       PNAS 101 (11): 3747–3752 (2004).
networkx.average_node_connectivity
Python Library Documentation: function average_node_connectivity in module networkx.algorithms.connectivity.connectivity

average_node_connectivity(G, flow_func=None, *, backend=None, **backend_kwargs)
    Returns the average connectivity of a graph G.

    The average connectivity `\bar{\kappa}` of a graph G is the average
    of local node connectivity over all pairs of nodes of G [1]_ .

    .. math::

        \bar{\kappa}(G) = \frac{\sum_{u,v} \kappa_{G}(u,v)}{{n \choose 2}}

    Parameters
    ----------

    G : NetworkX graph
        Undirected graph

    flow_func : function
        A function for computing the maximum flow among a pair of nodes.
        The function has to accept at least three parameters: a Digraph,
        a source node, and a target node. And return a residual network
        that follows NetworkX conventions (see :meth:`maximum_flow` for
        details). If flow_func is None, the default maximum flow function
        (:meth:`edmonds_karp`) is used. See :meth:`local_node_connectivity`
        for details. The choice of the default function may change from
        version to version and should not be relied on. Default value: None.

    Returns
    -------
    K : float
        Average node connectivity

    See also
    --------
    :meth:`local_node_connectivity`
    :meth:`node_connectivity`
    :meth:`edge_connectivity`
    :meth:`maximum_flow`
    :meth:`edmonds_karp`
    :meth:`preflow_push`
    :meth:`shortest_augmenting_path`

    References
    ----------
    .. [1]  Beineke, L., O. Oellermann, and R. Pippert (2002). The average
            connectivity of a graph. Discrete mathematics 252(1-3), 31-45.
            http://www.sciencedirect.com/science/article/pii/S0012365X01001807
networkx.average_shortest_path_length
Python Library Documentation: function average_shortest_path_length in module networkx.algorithms.shortest_paths.generic

average_shortest_path_length(G, weight=None, method=None, *, backend=None, **backend_kwargs)
    Returns the average shortest path length.

    The average shortest path length is

    .. math::

       a =\sum_{\substack{s,t \in V \\ s\neq t}} \frac{d(s, t)}{n(n-1)}

    where `V` is the set of nodes in `G`,
    `d(s, t)` is the shortest path from `s` to `t`,
    and `n` is the number of nodes in `G`.

    .. versionchanged:: 3.0
       An exception is raised for directed graphs that are not strongly
       connected.

    Parameters
    ----------
    G : NetworkX graph

    weight : None, string or function, optional (default = None)
        If None, every edge has weight/distance/cost 1.
        If a string, use this edge attribute as the edge weight.
        Any edge attribute not present defaults to 1.
        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly
        three positional arguments: the two endpoints of an edge and
        the dictionary of edge attributes for that edge.
        The function must return a number.

    method : string, optional (default = 'unweighted' or 'dijkstra')
        The algorithm to use to compute the path lengths.
        Supported options are 'unweighted', 'dijkstra', 'bellman-ford',
        'floyd-warshall' and 'floyd-warshall-numpy'.
        Other method values produce a ValueError.
        The default method is 'unweighted' if `weight` is None,
        otherwise the default method is 'dijkstra'.

    Raises
    ------
    NetworkXPointlessConcept
        If `G` is the null graph (that is, the graph on zero nodes).

    NetworkXError
        If `G` is not connected (or not strongly connected, in the case
        of a directed graph).

    ValueError
        If `method` is not among the supported options.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> nx.average_shortest_path_length(G)
    2.0

    For disconnected graphs, you can compute the average shortest path
    length for each component

    >>> G = nx.Graph([(1, 2), (3, 4)])
    >>> for C in (G.subgraph(c).copy() for c in nx.connected_components(G)):
    ...     print(nx.average_shortest_path_length(C))
    1.0
    1.0
networkx.balanced_tree
Python Library Documentation: function balanced_tree in module networkx.generators.classic

balanced_tree(r, h, create_using=None, *, backend=None, **backend_kwargs)
    Returns the perfectly balanced `r`-ary tree of height `h`.

    .. plot::

        >>> nx.draw(nx.balanced_tree(2, 3))

    Parameters
    ----------
    r : int
        Branching factor of the tree; each node will have `r`
        children.

    h : int
        Height of the tree.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : NetworkX graph
        A balanced `r`-ary tree of height `h`.

    Notes
    -----
    This is the rooted tree where all leaves are at distance `h` from
    the root. The root has degree `r` and all other internal nodes
    have degree `r + 1`.

    Node labels are integers, starting from zero.

    A balanced tree is also known as a *complete r-ary tree*.
networkx.barabasi_albert_graph
Python Library Documentation: function barabasi_albert_graph in module networkx.generators.random_graphs

barabasi_albert_graph(n, m, seed=None, initial_graph=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns a random graph using Barabási–Albert preferential attachment

    A graph of $n$ nodes is grown by attaching new nodes each with $m$
    edges that are preferentially attached to existing nodes with high degree.

    Parameters
    ----------
    n : int
        Number of nodes
    m : int
        Number of edges to attach from a new node to existing nodes
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    initial_graph : Graph or None (default)
        Initial network for Barabási–Albert algorithm.
        It should be a connected graph for most use cases.
        A copy of `initial_graph` is used.
        If None, starts from a star graph on (m+1) nodes.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Returns
    -------
    G : Graph

    Raises
    ------
    NetworkXError
        If `m` does not satisfy ``1 <= m < n``, or
        the initial graph number of nodes m0 does not satisfy ``m <= m0 <= n``.

    References
    ----------
    .. [1] A. L. Barabási and R. Albert "Emergence of scaling in
       random networks", Science 286, pp 509-512, 1999.
networkx.barbell_graph
Python Library Documentation: function barbell_graph in module networkx.generators.classic

barbell_graph(m1, m2, create_using=None, *, backend=None, **backend_kwargs)
    Returns the Barbell Graph: two complete graphs connected by a path.

    .. plot::

        >>> nx.draw(nx.barbell_graph(4, 2))

    Parameters
    ----------
    m1 : int
        Size of the left and right barbells, must be greater than 2.

    m2 : int
        Length of the path connecting the barbells.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.
       Only undirected Graphs are supported.

    Returns
    -------
    G : NetworkX graph
        A barbell graph.

    Notes
    -----


    Two identical complete graphs $K_{m1}$ form the left and right bells,
    and are connected by a path $P_{m2}$.

    The `2*m1+m2`  nodes are numbered
        `0, ..., m1-1` for the left barbell,
        `m1, ..., m1+m2-1` for the path,
        and `m1+m2, ..., 2*m1+m2-1` for the right barbell.

    The 3 subgraphs are joined via the edges `(m1-1, m1)` and
    `(m1+m2-1, m1+m2)`. If `m2=0`, this is merely two complete
    graphs joined together.

    This graph is an extremal example in David Aldous
    and Jim Fill's e-text on Random Walks on Graphs.
networkx.barycenter
Python Library Documentation: function barycenter in module networkx.algorithms.distance_measures

barycenter(G, weight=None, attr=None, sp=None, *, backend=None, **backend_kwargs)
    Calculate barycenter of a connected graph, optionally with edge weights.

    The :dfn:`barycenter` a
    :func:`connected <networkx.algorithms.components.is_connected>` graph
    :math:`G` is the subgraph induced by the set of its nodes :math:`v`
    minimizing the objective function

    .. math::

        \sum_{u \in V(G)} d_G(u, v),

    where :math:`d_G` is the (possibly weighted) :func:`path length
    <networkx.algorithms.shortest_paths.generic.shortest_path_length>`.
    The barycenter is also called the :dfn:`median`. See [West01]_, p. 78.

    Parameters
    ----------
    G : :class:`networkx.Graph`
        The connected graph :math:`G`.
    weight : :class:`str`, optional
        Passed through to
        :func:`~networkx.algorithms.shortest_paths.generic.shortest_path_length`.
    attr : :class:`str`, optional
        If given, write the value of the objective function to each node's
        `attr` attribute. Otherwise do not store the value.
    sp : dict of dicts, optional
       All pairs shortest path lengths as a dictionary of dictionaries

    Returns
    -------
    list
        Nodes of `G` that induce the barycenter of `G`.

    Raises
    ------
    NetworkXNoPath
        If `G` is disconnected. `G` may appear disconnected to
        :func:`barycenter` if `sp` is given but is missing shortest path
        lengths for any pairs.
    ValueError
        If `sp` and `weight` are both given.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
    >>> nx.barycenter(G)
    [1, 3, 4]

    See Also
    --------
    center
    periphery
networkx.beamsearch
Python Library Documentation: module networkx.algorithms.traversal.beamsearch in networkx.algorithms.traversal

NAME
    networkx.algorithms.traversal.beamsearch - Basic algorithms for breadth-first searching the nodes of a graph.

FUNCTIONS
    bfs_beam_edges(G, source, value, width=None, *, backend=None, **backend_kwargs)
        Iterates over edges in a beam search.

        The beam search is a generalized breadth-first search in which only
        the "best" *w* neighbors of the current node are enqueued, where *w*
        is the beam width and "best" is an application-specific
        heuristic. In general, a beam search with a small beam width might
        not visit each node in the graph.

        .. note::

           With the default value of ``width=None`` or `width` greater than the
           maximum degree of the graph, this function equates to a slower
           version of `~networkx.algorithms.traversal.breadth_first_search.bfs_edges`.
           All nodes will be visited, though the order of the reported edges may
           vary. In such cases, `value` has no effect - consider using `bfs_edges`
           directly instead.

        Parameters
        ----------
        G : NetworkX graph

        source : node
            Starting node for the breadth-first search; this function
            iterates over only those edges in the component reachable from
            this node.

        value : function
            A function that takes a node of the graph as input and returns a
            real number indicating how "good" it is. A higher value means it
            is more likely to be visited sooner during the search. When
            visiting a new node, only the `width` neighbors with the highest
            `value` are enqueued (in decreasing order of `value`).

        width : int (default = None)
            The beam width for the search. This is the number of neighbors
            (ordered by `value`) to enqueue when visiting each new node.

        Yields
        ------
        edge
            Edges in the beam search starting from `source`, given as a pair
            of nodes.

        Examples
        --------
        To give nodes with, for example, a higher centrality precedence
        during the search, set the `value` function to return the centrality
        value of the node:

        >>> G = nx.karate_club_graph()
        >>> centrality = nx.eigenvector_centrality(G)
        >>> list(nx.bfs_beam_edges(G, source=0, value=centrality.get, width=3))
        [(0, 2), (0, 1), (0, 8), (2, 32), (1, 13), (8, 33)]

DATA
    __all__ = ['bfs_beam_edges']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\traversal\beamsearch.py

networkx.bellman_ford_path
Python Library Documentation: function bellman_ford_path in module networkx.algorithms.shortest_paths.weighted

bellman_ford_path(G, source, target, weight='weight', *, backend=None, **backend_kwargs)
    Returns the shortest path from source to target in a weighted graph G.

    Parameters
    ----------
    G : NetworkX graph

    source : node
        Starting node

    target : node
        Ending node

    weight : string or function (default="weight")
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

    Returns
    -------
    path : list
        List of nodes in a shortest path.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    NetworkXNoPath
        If no path exists between source and target.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> nx.bellman_ford_path(G, 0, 4)
    [0, 1, 2, 3, 4]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    See Also
    --------
    dijkstra_path, bellman_ford_path_length
networkx.bellman_ford_path_length
Python Library Documentation: function bellman_ford_path_length in module networkx.algorithms.shortest_paths.weighted

bellman_ford_path_length(G, source, target, weight='weight', *, backend=None, **backend_kwargs)
    Returns the shortest path length from source to target
    in a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    source : node label
        starting node for path

    target : node label
        ending node for path

    weight : string or function (default="weight")
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

    Returns
    -------
    length : number
        Shortest path length.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    NetworkXNoPath
        If no path exists between source and target.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> nx.bellman_ford_path_length(G, 0, 4)
    4

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    See Also
    --------
    dijkstra_path_length, bellman_ford_path
networkx.bellman_ford_predecessor_and_distance
Python Library Documentation: function bellman_ford_predecessor_and_distance in module networkx.algorithms.shortest_paths.weighted

bellman_ford_predecessor_and_distance(G, source, target=None, weight='weight', heuristic=False, *, backend=None, **backend_kwargs)
    Compute shortest path lengths and predecessors on shortest paths
    in weighted graphs.

    The algorithm has a running time of $O(mn)$ where $n$ is the number of
    nodes and $m$ is the number of edges.  It is slower than Dijkstra but
    can handle negative edge weights.

    If a negative cycle is detected, you can use :func:`find_negative_cycle`
    to return the cycle and examine it. Shortest paths are not defined when
    a negative cycle exists because once reached, the path can cycle forever
    to build up arbitrarily low weights.

    Parameters
    ----------
    G : NetworkX graph
        The algorithm works for all types of graphs, including directed
        graphs and multigraphs.

    source: node label
        Starting node for path

    target : node label, optional
        Ending node for path

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

    heuristic : bool
        Determines whether to use a heuristic to early detect negative
        cycles at a hopefully negligible cost.

    Returns
    -------
    pred, dist : dictionaries
        Returns two dictionaries keyed by node to predecessor in the
        path and to the distance from the source respectively.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    NetworkXUnbounded
        If the (di)graph contains a negative (di)cycle, the
        algorithm raises an exception to indicate the presence of the
        negative (di)cycle.  Note: any negative weight edge in an
        undirected graph is a negative cycle.

    Examples
    --------
    >>> G = nx.path_graph(5, create_using=nx.DiGraph())
    >>> pred, dist = nx.bellman_ford_predecessor_and_distance(G, 0)
    >>> sorted(pred.items())
    [(0, []), (1, [0]), (2, [1]), (3, [2]), (4, [3])]
    >>> sorted(dist.items())
    [(0, 0), (1, 1), (2, 2), (3, 3), (4, 4)]

    >>> pred, dist = nx.bellman_ford_predecessor_and_distance(G, 0, 1)
    >>> sorted(pred.items())
    [(0, []), (1, [0]), (2, [1]), (3, [2]), (4, [3])]
    >>> sorted(dist.items())
    [(0, 0), (1, 1), (2, 2), (3, 3), (4, 4)]

    >>> G = nx.cycle_graph(5, create_using=nx.DiGraph())
    >>> G[1][2]["weight"] = -7
    >>> nx.bellman_ford_predecessor_and_distance(G, 0)
    Traceback (most recent call last):
        ...
    networkx.exception.NetworkXUnbounded: Negative cycle detected.

    See Also
    --------
    find_negative_cycle

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The dictionaries returned only have keys for nodes reachable from
    the source.

    In the case where the (di)graph is not connected, if a component
    not containing the source contains a negative (di)cycle, it
    will not be detected.

    In NetworkX v2.1 and prior, the source node had predecessor `[None]`.
    In NetworkX v2.2 this changed to the source node having predecessor `[]`
networkx.bethe_hessian_matrix
Python Library Documentation: function bethe_hessian_matrix in module networkx.linalg.bethehessianmatrix

bethe_hessian_matrix(G, r=None, nodelist=None, *, backend=None, **backend_kwargs)
    Returns the Bethe Hessian matrix of G.

    The Bethe Hessian is a family of matrices parametrized by r, defined as
    H(r) = (r^2 - 1) I - r A + D where A is the adjacency matrix, D is the
    diagonal matrix of node degrees, and I is the identify matrix. It is equal
    to the graph laplacian when the regularizer r = 1.

    The default choice of regularizer should be the ratio [2]_

    .. math::
      r_m = \left(\sum k_i \right)^{-1}\left(\sum k_i^2 \right) - 1

    Parameters
    ----------
    G : Graph
       A NetworkX graph
    r : float
       Regularizer parameter
    nodelist : list, optional
       The rows and columns are ordered according to the nodes in nodelist.
       If nodelist is None, then the ordering is produced by ``G.nodes()``.

    Returns
    -------
    H : scipy.sparse.csr_array
      The Bethe Hessian matrix of `G`, with parameter `r`.

    Examples
    --------
    >>> k = [3, 2, 2, 1, 0]
    >>> G = nx.havel_hakimi_graph(k)
    >>> H = nx.bethe_hessian_matrix(G)
    >>> H.toarray()
    array([[ 3.5625, -1.25  , -1.25  , -1.25  ,  0.    ],
           [-1.25  ,  2.5625, -1.25  ,  0.    ,  0.    ],
           [-1.25  , -1.25  ,  2.5625,  0.    ,  0.    ],
           [-1.25  ,  0.    ,  0.    ,  1.5625,  0.    ],
           [ 0.    ,  0.    ,  0.    ,  0.    ,  0.5625]])

    See Also
    --------
    bethe_hessian_spectrum
    adjacency_matrix
    laplacian_matrix

    References
    ----------
    .. [1] A. Saade, F. Krzakala and L. Zdeborová
       "Spectral Clustering of Graphs with the Bethe Hessian",
       Advances in Neural Information Processing Systems, 2014.
    .. [2] C. M. Le, E. Levina
       "Estimating the number of communities in networks by spectral methods"
       arXiv:1507.00827, 2015.
networkx.bethe_hessian_spectrum
Python Library Documentation: function bethe_hessian_spectrum in module networkx.linalg.spectrum

bethe_hessian_spectrum(G, r=None, *, backend=None, **backend_kwargs)
    Returns eigenvalues of the Bethe Hessian matrix of G.

    Parameters
    ----------
    G : Graph
       A NetworkX Graph or DiGraph

    r : float
       Regularizer parameter

    Returns
    -------
    evals : NumPy array
      Eigenvalues

    See Also
    --------
    bethe_hessian_matrix

    References
    ----------
    .. [1] A. Saade, F. Krzakala and L. Zdeborová
       "Spectral clustering of graphs with the bethe hessian",
       Advances in Neural Information Processing Systems. 2014.
networkx.bethehessianmatrix
Python Library Documentation: module networkx.linalg.bethehessianmatrix in networkx.linalg

NAME
    networkx.linalg.bethehessianmatrix - Bethe Hessian or deformed Laplacian matrix of graphs.

FUNCTIONS
    bethe_hessian_matrix(G, r=None, nodelist=None, *, backend=None, **backend_kwargs)
        Returns the Bethe Hessian matrix of G.

        The Bethe Hessian is a family of matrices parametrized by r, defined as
        H(r) = (r^2 - 1) I - r A + D where A is the adjacency matrix, D is the
        diagonal matrix of node degrees, and I is the identify matrix. It is equal
        to the graph laplacian when the regularizer r = 1.

        The default choice of regularizer should be the ratio [2]_

        .. math::
          r_m = \left(\sum k_i \right)^{-1}\left(\sum k_i^2 \right) - 1

        Parameters
        ----------
        G : Graph
           A NetworkX graph
        r : float
           Regularizer parameter
        nodelist : list, optional
           The rows and columns are ordered according to the nodes in nodelist.
           If nodelist is None, then the ordering is produced by ``G.nodes()``.

        Returns
        -------
        H : scipy.sparse.csr_array
          The Bethe Hessian matrix of `G`, with parameter `r`.

        Examples
        --------
        >>> k = [3, 2, 2, 1, 0]
        >>> G = nx.havel_hakimi_graph(k)
        >>> H = nx.bethe_hessian_matrix(G)
        >>> H.toarray()
        array([[ 3.5625, -1.25  , -1.25  , -1.25  ,  0.    ],
               [-1.25  ,  2.5625, -1.25  ,  0.    ,  0.    ],
               [-1.25  , -1.25  ,  2.5625,  0.    ,  0.    ],
               [-1.25  ,  0.    ,  0.    ,  1.5625,  0.    ],
               [ 0.    ,  0.    ,  0.    ,  0.    ,  0.5625]])

        See Also
        --------
        bethe_hessian_spectrum
        adjacency_matrix
        laplacian_matrix

        References
        ----------
        .. [1] A. Saade, F. Krzakala and L. Zdeborová
           "Spectral Clustering of Graphs with the Bethe Hessian",
           Advances in Neural Information Processing Systems, 2014.
        .. [2] C. M. Le, E. Levina
           "Estimating the number of communities in networks by spectral methods"
           arXiv:1507.00827, 2015.

DATA
    __all__ = ['bethe_hessian_matrix']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\linalg\bethehessianmatrix.py

networkx.betweenness
Python Library Documentation: module networkx.algorithms.centrality.betweenness in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.betweenness - Betweenness centrality measures.

FUNCTIONS
    betweenness_centrality(G, k=None, normalized=True, weight=None, endpoints=False, seed=None, *, backend=None, **backend_kwargs)
        Compute the shortest-path betweenness centrality for nodes.

        Betweenness centrality of a node $v$ is the sum of the
        fraction of all-pairs shortest paths that pass through $v$

        .. math::

           c_B(v) =\sum_{s,t \in V} \frac{\sigma(s, t|v)}{\sigma(s, t)}

        where $V$ is the set of nodes, $\sigma(s, t)$ is the number of
        shortest $(s, t)$-paths,  and $\sigma(s, t|v)$ is the number of
        those paths  passing through some  node $v$ other than $s, t$.
        If $s = t$, $\sigma(s, t) = 1$, and if $v \in {s, t}$,
        $\sigma(s, t|v) = 0$ [2]_.

        Parameters
        ----------
        G : graph
          A NetworkX graph.

        k : int, optional (default=None)
          If k is not None use k node samples to estimate betweenness.
          The value of k <= n where n is the number of nodes in the graph.
          Higher values give better approximation.

        normalized : bool, optional
          If True the betweenness values are normalized by `2/((n-1)(n-2))`
          for graphs, and `1/((n-1)(n-2))` for directed graphs where `n`
          is the number of nodes in G.

        weight : None or string, optional (default=None)
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.
          Weights are used to calculate weighted shortest paths, so they are
          interpreted as distances.

        endpoints : bool, optional
          If True include the endpoints in the shortest path counts.

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
            Note that this is only used if k is not None.

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with betweenness centrality as the value.

        See Also
        --------
        edge_betweenness_centrality
        load_centrality

        Notes
        -----
        The algorithm is from Ulrik Brandes [1]_.
        See [4]_ for the original first published version and [2]_ for details on
        algorithms for variations and related metrics.

        For approximate betweenness calculations set k=#samples to use
        k nodes ("pivots") to estimate the betweenness values. For an estimate
        of the number of pivots needed see [3]_.

        For weighted graphs the edge weights must be greater than zero.
        Zero edge weights can produce an infinite number of equal length
        paths between pairs of nodes.

        The total number of paths between source and target is counted
        differently for directed and undirected graphs. Directed paths
        are easy to count. Undirected paths are tricky: should a path
        from "u" to "v" count as 1 undirected path or as 2 directed paths?

        For betweenness_centrality we report the number of undirected
        paths when G is undirected.

        For betweenness_centrality_subset the reporting is different.
        If the source and target subsets are the same, then we want
        to count undirected paths. But if the source and target subsets
        differ -- for example, if sources is {0} and targets is {1},
        then we are only counting the paths in one direction. They are
        undirected paths but we are counting them in a directed way.
        To count them as undirected paths, each should count as half a path.

        This algorithm is not guaranteed to be correct if edge weights
        are floating point numbers. As a workaround you can use integer
        numbers by multiplying the relevant edge attributes by a convenient
        constant factor (eg 100) and converting to integers.

        References
        ----------
        .. [1] Ulrik Brandes:
           A Faster Algorithm for Betweenness Centrality.
           Journal of Mathematical Sociology 25(2):163-177, 2001.
           https://doi.org/10.1080/0022250X.2001.9990249
        .. [2] Ulrik Brandes:
           On Variants of Shortest-Path Betweenness
           Centrality and their Generic Computation.
           Social Networks 30(2):136-145, 2008.
           https://doi.org/10.1016/j.socnet.2007.11.001
        .. [3] Ulrik Brandes and Christian Pich:
           Centrality Estimation in Large Networks.
           International Journal of Bifurcation and Chaos 17(7):2303-2318, 2007.
           https://dx.doi.org/10.1142/S0218127407018403
        .. [4] Linton C. Freeman:
           A set of measures of centrality based on betweenness.
           Sociometry 40: 35–41, 1977
           https://doi.org/10.2307/3033543

    edge_betweenness_centrality(G, k=None, normalized=True, weight=None, seed=None, *, backend=None, **backend_kwargs)
        Compute betweenness centrality for edges.

        Betweenness centrality of an edge $e$ is the sum of the
        fraction of all-pairs shortest paths that pass through $e$

        .. math::

           c_B(e) =\sum_{s,t \in V} \frac{\sigma(s, t|e)}{\sigma(s, t)}

        where $V$ is the set of nodes, $\sigma(s, t)$ is the number of
        shortest $(s, t)$-paths, and $\sigma(s, t|e)$ is the number of
        those paths passing through edge $e$ [2]_.

        Parameters
        ----------
        G : graph
          A NetworkX graph.

        k : int, optional (default=None)
          If k is not None use k node samples to estimate betweenness.
          The value of k <= n where n is the number of nodes in the graph.
          Higher values give better approximation.

        normalized : bool, optional
          If True the betweenness values are normalized by $2/(n(n-1))$
          for graphs, and $1/(n(n-1))$ for directed graphs where $n$
          is the number of nodes in G.

        weight : None or string, optional (default=None)
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.
          Weights are used to calculate weighted shortest paths, so they are
          interpreted as distances.

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
            Note that this is only used if k is not None.

        Returns
        -------
        edges : dictionary
           Dictionary of edges with betweenness centrality as the value.

        See Also
        --------
        betweenness_centrality
        edge_load

        Notes
        -----
        The algorithm is from Ulrik Brandes [1]_.

        For weighted graphs the edge weights must be greater than zero.
        Zero edge weights can produce an infinite number of equal length
        paths between pairs of nodes.

        References
        ----------
        .. [1]  A Faster Algorithm for Betweenness Centrality. Ulrik Brandes,
           Journal of Mathematical Sociology 25(2):163-177, 2001.
           https://doi.org/10.1080/0022250X.2001.9990249
        .. [2] Ulrik Brandes: On Variants of Shortest-Path Betweenness
           Centrality and their Generic Computation.
           Social Networks 30(2):136-145, 2008.
           https://doi.org/10.1016/j.socnet.2007.11.001

DATA
    __all__ = ['betweenness_centrality', 'edge_betweenness_centrality']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\betweenness.py

networkx.betweenness_centrality
Python Library Documentation: function betweenness_centrality in module networkx.algorithms.centrality.betweenness

betweenness_centrality(G, k=None, normalized=True, weight=None, endpoints=False, seed=None, *, backend=None, **backend_kwargs)
    Compute the shortest-path betweenness centrality for nodes.

    Betweenness centrality of a node $v$ is the sum of the
    fraction of all-pairs shortest paths that pass through $v$

    .. math::

       c_B(v) =\sum_{s,t \in V} \frac{\sigma(s, t|v)}{\sigma(s, t)}

    where $V$ is the set of nodes, $\sigma(s, t)$ is the number of
    shortest $(s, t)$-paths,  and $\sigma(s, t|v)$ is the number of
    those paths  passing through some  node $v$ other than $s, t$.
    If $s = t$, $\sigma(s, t) = 1$, and if $v \in {s, t}$,
    $\sigma(s, t|v) = 0$ [2]_.

    Parameters
    ----------
    G : graph
      A NetworkX graph.

    k : int, optional (default=None)
      If k is not None use k node samples to estimate betweenness.
      The value of k <= n where n is the number of nodes in the graph.
      Higher values give better approximation.

    normalized : bool, optional
      If True the betweenness values are normalized by `2/((n-1)(n-2))`
      for graphs, and `1/((n-1)(n-2))` for directed graphs where `n`
      is the number of nodes in G.

    weight : None or string, optional (default=None)
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.
      Weights are used to calculate weighted shortest paths, so they are
      interpreted as distances.

    endpoints : bool, optional
      If True include the endpoints in the shortest path counts.

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
        Note that this is only used if k is not None.

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with betweenness centrality as the value.

    See Also
    --------
    edge_betweenness_centrality
    load_centrality

    Notes
    -----
    The algorithm is from Ulrik Brandes [1]_.
    See [4]_ for the original first published version and [2]_ for details on
    algorithms for variations and related metrics.

    For approximate betweenness calculations set k=#samples to use
    k nodes ("pivots") to estimate the betweenness values. For an estimate
    of the number of pivots needed see [3]_.

    For weighted graphs the edge weights must be greater than zero.
    Zero edge weights can produce an infinite number of equal length
    paths between pairs of nodes.

    The total number of paths between source and target is counted
    differently for directed and undirected graphs. Directed paths
    are easy to count. Undirected paths are tricky: should a path
    from "u" to "v" count as 1 undirected path or as 2 directed paths?

    For betweenness_centrality we report the number of undirected
    paths when G is undirected.

    For betweenness_centrality_subset the reporting is different.
    If the source and target subsets are the same, then we want
    to count undirected paths. But if the source and target subsets
    differ -- for example, if sources is {0} and targets is {1},
    then we are only counting the paths in one direction. They are
    undirected paths but we are counting them in a directed way.
    To count them as undirected paths, each should count as half a path.

    This algorithm is not guaranteed to be correct if edge weights
    are floating point numbers. As a workaround you can use integer
    numbers by multiplying the relevant edge attributes by a convenient
    constant factor (eg 100) and converting to integers.

    References
    ----------
    .. [1] Ulrik Brandes:
       A Faster Algorithm for Betweenness Centrality.
       Journal of Mathematical Sociology 25(2):163-177, 2001.
       https://doi.org/10.1080/0022250X.2001.9990249
    .. [2] Ulrik Brandes:
       On Variants of Shortest-Path Betweenness
       Centrality and their Generic Computation.
       Social Networks 30(2):136-145, 2008.
       https://doi.org/10.1016/j.socnet.2007.11.001
    .. [3] Ulrik Brandes and Christian Pich:
       Centrality Estimation in Large Networks.
       International Journal of Bifurcation and Chaos 17(7):2303-2318, 2007.
       https://dx.doi.org/10.1142/S0218127407018403
    .. [4] Linton C. Freeman:
       A set of measures of centrality based on betweenness.
       Sociometry 40: 35–41, 1977
       https://doi.org/10.2307/3033543
networkx.betweenness_centrality_subset
Python Library Documentation: function betweenness_centrality_subset in module networkx.algorithms.centrality.betweenness_subset

betweenness_centrality_subset(G, sources, targets, normalized=False, weight=None, *, backend=None, **backend_kwargs)
    Compute betweenness centrality for a subset of nodes.

    .. math::

       c_B(v) =\sum_{s\in S, t \in T} \frac{\sigma(s, t|v)}{\sigma(s, t)}

    where $S$ is the set of sources, $T$ is the set of targets,
    $\sigma(s, t)$ is the number of shortest $(s, t)$-paths,
    and $\sigma(s, t|v)$ is the number of those paths
    passing through some  node $v$ other than $s, t$.
    If $s = t$, $\sigma(s, t) = 1$,
    and if $v \in {s, t}$, $\sigma(s, t|v) = 0$ [2]_.


    Parameters
    ----------
    G : graph
      A NetworkX graph.

    sources: list of nodes
      Nodes to use as sources for shortest paths in betweenness

    targets: list of nodes
      Nodes to use as targets for shortest paths in betweenness

    normalized : bool, optional
      If True the betweenness values are normalized by $2/((n-1)(n-2))$
      for graphs, and $1/((n-1)(n-2))$ for directed graphs where $n$
      is the number of nodes in G.

    weight : None or string, optional (default=None)
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.
      Weights are used to calculate weighted shortest paths, so they are
      interpreted as distances.

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with betweenness centrality as the value.

    See Also
    --------
    edge_betweenness_centrality
    load_centrality

    Notes
    -----
    The basic algorithm is from [1]_.

    For weighted graphs the edge weights must be greater than zero.
    Zero edge weights can produce an infinite number of equal length
    paths between pairs of nodes.

    The normalization might seem a little strange but it is
    designed to make betweenness_centrality(G) be the same as
    betweenness_centrality_subset(G,sources=G.nodes(),targets=G.nodes()).

    The total number of paths between source and target is counted
    differently for directed and undirected graphs. Directed paths
    are easy to count. Undirected paths are tricky: should a path
    from "u" to "v" count as 1 undirected path or as 2 directed paths?

    For betweenness_centrality we report the number of undirected
    paths when G is undirected.

    For betweenness_centrality_subset the reporting is different.
    If the source and target subsets are the same, then we want
    to count undirected paths. But if the source and target subsets
    differ -- for example, if sources is {0} and targets is {1},
    then we are only counting the paths in one direction. They are
    undirected paths but we are counting them in a directed way.
    To count them as undirected paths, each should count as half a path.

    References
    ----------
    .. [1] Ulrik Brandes, A Faster Algorithm for Betweenness Centrality.
       Journal of Mathematical Sociology 25(2):163-177, 2001.
       https://doi.org/10.1080/0022250X.2001.9990249
    .. [2] Ulrik Brandes: On Variants of Shortest-Path Betweenness
       Centrality and their Generic Computation.
       Social Networks 30(2):136-145, 2008.
       https://doi.org/10.1016/j.socnet.2007.11.001
networkx.betweenness_subset
Python Library Documentation: module networkx.algorithms.centrality.betweenness_subset in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.betweenness_subset - Betweenness centrality measures for subsets of nodes.

FUNCTIONS
    betweenness_centrality_subset(G, sources, targets, normalized=False, weight=None, *, backend=None, **backend_kwargs)
        Compute betweenness centrality for a subset of nodes.

        .. math::

           c_B(v) =\sum_{s\in S, t \in T} \frac{\sigma(s, t|v)}{\sigma(s, t)}

        where $S$ is the set of sources, $T$ is the set of targets,
        $\sigma(s, t)$ is the number of shortest $(s, t)$-paths,
        and $\sigma(s, t|v)$ is the number of those paths
        passing through some  node $v$ other than $s, t$.
        If $s = t$, $\sigma(s, t) = 1$,
        and if $v \in {s, t}$, $\sigma(s, t|v) = 0$ [2]_.


        Parameters
        ----------
        G : graph
          A NetworkX graph.

        sources: list of nodes
          Nodes to use as sources for shortest paths in betweenness

        targets: list of nodes
          Nodes to use as targets for shortest paths in betweenness

        normalized : bool, optional
          If True the betweenness values are normalized by $2/((n-1)(n-2))$
          for graphs, and $1/((n-1)(n-2))$ for directed graphs where $n$
          is the number of nodes in G.

        weight : None or string, optional (default=None)
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.
          Weights are used to calculate weighted shortest paths, so they are
          interpreted as distances.

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with betweenness centrality as the value.

        See Also
        --------
        edge_betweenness_centrality
        load_centrality

        Notes
        -----
        The basic algorithm is from [1]_.

        For weighted graphs the edge weights must be greater than zero.
        Zero edge weights can produce an infinite number of equal length
        paths between pairs of nodes.

        The normalization might seem a little strange but it is
        designed to make betweenness_centrality(G) be the same as
        betweenness_centrality_subset(G,sources=G.nodes(),targets=G.nodes()).

        The total number of paths between source and target is counted
        differently for directed and undirected graphs. Directed paths
        are easy to count. Undirected paths are tricky: should a path
        from "u" to "v" count as 1 undirected path or as 2 directed paths?

        For betweenness_centrality we report the number of undirected
        paths when G is undirected.

        For betweenness_centrality_subset the reporting is different.
        If the source and target subsets are the same, then we want
        to count undirected paths. But if the source and target subsets
        differ -- for example, if sources is {0} and targets is {1},
        then we are only counting the paths in one direction. They are
        undirected paths but we are counting them in a directed way.
        To count them as undirected paths, each should count as half a path.

        References
        ----------
        .. [1] Ulrik Brandes, A Faster Algorithm for Betweenness Centrality.
           Journal of Mathematical Sociology 25(2):163-177, 2001.
           https://doi.org/10.1080/0022250X.2001.9990249
        .. [2] Ulrik Brandes: On Variants of Shortest-Path Betweenness
           Centrality and their Generic Computation.
           Social Networks 30(2):136-145, 2008.
           https://doi.org/10.1016/j.socnet.2007.11.001

    edge_betweenness_centrality_subset(G, sources, targets, normalized=False, weight=None, *, backend=None, **backend_kwargs)
        Compute betweenness centrality for edges for a subset of nodes.

        .. math::

           c_B(v) =\sum_{s\in S,t \in T} \frac{\sigma(s, t|e)}{\sigma(s, t)}

        where $S$ is the set of sources, $T$ is the set of targets,
        $\sigma(s, t)$ is the number of shortest $(s, t)$-paths,
        and $\sigma(s, t|e)$ is the number of those paths
        passing through edge $e$ [2]_.

        Parameters
        ----------
        G : graph
          A networkx graph.

        sources: list of nodes
          Nodes to use as sources for shortest paths in betweenness

        targets: list of nodes
          Nodes to use as targets for shortest paths in betweenness

        normalized : bool, optional
          If True the betweenness values are normalized by `2/(n(n-1))`
          for graphs, and `1/(n(n-1))` for directed graphs where `n`
          is the number of nodes in G.

        weight : None or string, optional (default=None)
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.
          Weights are used to calculate weighted shortest paths, so they are
          interpreted as distances.

        Returns
        -------
        edges : dictionary
           Dictionary of edges with Betweenness centrality as the value.

        See Also
        --------
        betweenness_centrality
        edge_load

        Notes
        -----
        The basic algorithm is from [1]_.

        For weighted graphs the edge weights must be greater than zero.
        Zero edge weights can produce an infinite number of equal length
        paths between pairs of nodes.

        The normalization might seem a little strange but it is the same
        as in edge_betweenness_centrality() and is designed to make
        edge_betweenness_centrality(G) be the same as
        edge_betweenness_centrality_subset(G,sources=G.nodes(),targets=G.nodes()).

        References
        ----------
        .. [1] Ulrik Brandes, A Faster Algorithm for Betweenness Centrality.
           Journal of Mathematical Sociology 25(2):163-177, 2001.
           https://doi.org/10.1080/0022250X.2001.9990249
        .. [2] Ulrik Brandes: On Variants of Shortest-Path Betweenness
           Centrality and their Generic Computation.
           Social Networks 30(2):136-145, 2008.
           https://doi.org/10.1016/j.socnet.2007.11.001

DATA
    __all__ = ['betweenness_centrality_subset', 'edge_betweenness_centrali...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\betweenness_subset.py

networkx.bfs_beam_edges
Python Library Documentation: function bfs_beam_edges in module networkx.algorithms.traversal.beamsearch

bfs_beam_edges(G, source, value, width=None, *, backend=None, **backend_kwargs)
    Iterates over edges in a beam search.

    The beam search is a generalized breadth-first search in which only
    the "best" *w* neighbors of the current node are enqueued, where *w*
    is the beam width and "best" is an application-specific
    heuristic. In general, a beam search with a small beam width might
    not visit each node in the graph.

    .. note::

       With the default value of ``width=None`` or `width` greater than the
       maximum degree of the graph, this function equates to a slower
       version of `~networkx.algorithms.traversal.breadth_first_search.bfs_edges`.
       All nodes will be visited, though the order of the reported edges may
       vary. In such cases, `value` has no effect - consider using `bfs_edges`
       directly instead.

    Parameters
    ----------
    G : NetworkX graph

    source : node
        Starting node for the breadth-first search; this function
        iterates over only those edges in the component reachable from
        this node.

    value : function
        A function that takes a node of the graph as input and returns a
        real number indicating how "good" it is. A higher value means it
        is more likely to be visited sooner during the search. When
        visiting a new node, only the `width` neighbors with the highest
        `value` are enqueued (in decreasing order of `value`).

    width : int (default = None)
        The beam width for the search. This is the number of neighbors
        (ordered by `value`) to enqueue when visiting each new node.

    Yields
    ------
    edge
        Edges in the beam search starting from `source`, given as a pair
        of nodes.

    Examples
    --------
    To give nodes with, for example, a higher centrality precedence
    during the search, set the `value` function to return the centrality
    value of the node:

    >>> G = nx.karate_club_graph()
    >>> centrality = nx.eigenvector_centrality(G)
    >>> list(nx.bfs_beam_edges(G, source=0, value=centrality.get, width=3))
    [(0, 2), (0, 1), (0, 8), (2, 32), (1, 13), (8, 33)]
networkx.bfs_edges
Python Library Documentation: function bfs_edges in module networkx.algorithms.traversal.breadth_first_search

bfs_edges(G, source, reverse=False, depth_limit=None, sort_neighbors=None, *, backend=None, **backend_kwargs)
    Iterate over edges in a breadth-first-search starting at source.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Specify starting node for breadth-first search; this function
       iterates over only those edges in the component reachable from
       this node.

    reverse : bool, optional
       If True traverse a directed graph in the reverse direction

    depth_limit : int, optional(default=len(G))
        Specify the maximum search depth

    sort_neighbors : function (default=None)
        A function that takes an iterator over nodes as the input, and
        returns an iterable of the same nodes with a custom ordering.
        For example, `sorted` will sort the nodes in increasing order.

    Yields
    ------
    edge: 2-tuple of nodes
       Yields edges resulting from the breadth-first search.

    Examples
    --------
    To get the edges in a breadth-first search::

        >>> G = nx.path_graph(3)
        >>> list(nx.bfs_edges(G, 0))
        [(0, 1), (1, 2)]
        >>> list(nx.bfs_edges(G, source=0, depth_limit=1))
        [(0, 1)]

    To get the nodes in a breadth-first search order::

        >>> G = nx.path_graph(3)
        >>> root = 2
        >>> edges = nx.bfs_edges(G, root)
        >>> nodes = [root] + [v for u, v in edges]
        >>> nodes
        [2, 1, 0]

    Notes
    -----
    The naming of this function is very similar to
    :func:`~networkx.algorithms.traversal.edgebfs.edge_bfs`. The difference
    is that ``edge_bfs`` yields edges even if they extend back to an already
    explored node while this generator yields the edges of the tree that results
    from a breadth-first-search (BFS) so no edges are reported if they extend
    to already explored nodes. That means ``edge_bfs`` reports all edges while
    ``bfs_edges`` only reports those traversed by a node-based BFS. Yet another
    description is that ``bfs_edges`` reports the edges traversed during BFS
    while ``edge_bfs`` reports all edges in the order they are explored.

    Based on the breadth-first search implementation in PADS [1]_
    by D. Eppstein, July 2004; with modifications to allow depth limits
    as described in [2]_.

    References
    ----------
    .. [1] http://www.ics.uci.edu/~eppstein/PADS/BFS.py.
    .. [2] https://en.wikipedia.org/wiki/Depth-limited_search

    See Also
    --------
    bfs_tree
    :func:`~networkx.algorithms.traversal.depth_first_search.dfs_edges`
    :func:`~networkx.algorithms.traversal.edgebfs.edge_bfs`
networkx.bfs_labeled_edges
Python Library Documentation: function bfs_labeled_edges in module networkx.algorithms.traversal.breadth_first_search

bfs_labeled_edges(G, sources, *, backend=None, **backend_kwargs)
    Iterate over edges in a breadth-first search (BFS) labeled by type.

    We generate triple of the form (*u*, *v*, *d*), where (*u*, *v*) is the
    edge being explored in the breadth-first search and *d* is one of the
    strings 'tree', 'forward', 'level', or 'reverse'.  A 'tree' edge is one in
    which *v* is first discovered and placed into the layer below *u*.  A
    'forward' edge is one in which *u* is on the layer above *v* and *v* has
    already been discovered.  A 'level' edge is one in which both *u* and *v*
    occur on the same layer.  A 'reverse' edge is one in which *u* is on a layer
    below *v*.

    We emit each edge exactly once.  In an undirected graph, 'reverse' edges do
    not occur, because each is discovered either as a 'tree' or 'forward' edge.

    Parameters
    ----------
    G : NetworkX graph
        A graph over which to find the layers using breadth-first search.

    sources : node in `G` or list of nodes in `G`
        Starting nodes for single source or multiple sources breadth-first search

    Yields
    ------
    edges: generator
       A generator of triples (*u*, *v*, *d*) where (*u*, *v*) is the edge being
       explored and *d* is described above.

    Examples
    --------
    >>> G = nx.cycle_graph(4, create_using=nx.DiGraph)
    >>> list(nx.bfs_labeled_edges(G, 0))
    [(0, 1, 'tree'), (1, 2, 'tree'), (2, 3, 'tree'), (3, 0, 'reverse')]
    >>> G = nx.complete_graph(3)
    >>> list(nx.bfs_labeled_edges(G, 0))
    [(0, 1, 'tree'), (0, 2, 'tree'), (1, 2, 'level')]
    >>> list(nx.bfs_labeled_edges(G, [0, 1]))
    [(0, 1, 'level'), (0, 2, 'tree'), (1, 2, 'forward')]
networkx.bfs_layers
Python Library Documentation: function bfs_layers in module networkx.algorithms.traversal.breadth_first_search

bfs_layers(G, sources, *, backend=None, **backend_kwargs)
    Returns an iterator of all the layers in breadth-first search traversal.

    Parameters
    ----------
    G : NetworkX graph
        A graph over which to find the layers using breadth-first search.

    sources : node in `G` or list of nodes in `G`
        Specify starting nodes for single source or multiple sources breadth-first search

    Yields
    ------
    layer: list of nodes
        Yields list of nodes at the same distance from sources

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> dict(enumerate(nx.bfs_layers(G, [0, 4])))
    {0: [0, 4], 1: [1, 3], 2: [2]}
    >>> H = nx.Graph()
    >>> H.add_edges_from([(0, 1), (0, 2), (1, 3), (1, 4), (2, 5), (2, 6)])
    >>> dict(enumerate(nx.bfs_layers(H, [1])))
    {0: [1], 1: [0, 3, 4], 2: [2], 3: [5, 6]}
    >>> dict(enumerate(nx.bfs_layers(H, [1, 6])))
    {0: [1, 6], 1: [0, 3, 4, 2], 2: [5]}
networkx.bfs_layout
Python Library Documentation: function bfs_layout in module networkx.drawing.layout

bfs_layout(G, start, *, align='vertical', scale=1, center=None)
    Position nodes according to breadth-first search algorithm.

    Parameters
    ----------
    G : NetworkX graph
        A position will be assigned to every node in G.

    start : node in `G`
        Starting node for bfs

    center : array-like or None
        Coordinate pair around which to center the layout.

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> pos = nx.bfs_layout(G, 0)

    Notes
    -----
    This algorithm currently only works in two dimensions and does not
    try to minimize edge crossings.
networkx.bfs_predecessors
Python Library Documentation: function bfs_predecessors in module networkx.algorithms.traversal.breadth_first_search

bfs_predecessors(G, source, depth_limit=None, sort_neighbors=None, *, backend=None, **backend_kwargs)
    Returns an iterator of predecessors in breadth-first-search from source.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Specify starting node for breadth-first search

    depth_limit : int, optional(default=len(G))
        Specify the maximum search depth

    sort_neighbors : function (default=None)
        A function that takes an iterator over nodes as the input, and
        returns an iterable of the same nodes with a custom ordering.
        For example, `sorted` will sort the nodes in increasing order.

    Returns
    -------
    pred: iterator
        (node, predecessor) iterator where `predecessor` is the predecessor of
        `node` in a breadth first search starting from `source`.

    Examples
    --------
    >>> G = nx.path_graph(3)
    >>> dict(nx.bfs_predecessors(G, 0))
    {1: 0, 2: 1}
    >>> H = nx.Graph()
    >>> H.add_edges_from([(0, 1), (0, 2), (1, 3), (1, 4), (2, 5), (2, 6)])
    >>> dict(nx.bfs_predecessors(H, 0))
    {1: 0, 2: 0, 3: 1, 4: 1, 5: 2, 6: 2}
    >>> M = nx.Graph()
    >>> nx.add_path(M, [0, 1, 2, 3, 4, 5, 6])
    >>> nx.add_path(M, [2, 7, 8, 9, 10])
    >>> sorted(nx.bfs_predecessors(M, source=1, depth_limit=3))
    [(0, 1), (2, 1), (3, 2), (4, 3), (7, 2), (8, 7)]
    >>> N = nx.DiGraph()
    >>> nx.add_path(N, [0, 1, 2, 3, 4, 7])
    >>> nx.add_path(N, [3, 5, 6, 7])
    >>> sorted(nx.bfs_predecessors(N, source=2))
    [(3, 2), (4, 3), (5, 3), (6, 5), (7, 4)]

    Notes
    -----
    Based on http://www.ics.uci.edu/~eppstein/PADS/BFS.py
    by D. Eppstein, July 2004. The modifications
    to allow depth limits based on the Wikipedia article
    "`Depth-limited-search`_".

    .. _Depth-limited-search: https://en.wikipedia.org/wiki/Depth-limited_search

    See Also
    --------
    bfs_tree
    bfs_edges
    edge_bfs
networkx.bfs_successors
Python Library Documentation: function bfs_successors in module networkx.algorithms.traversal.breadth_first_search

bfs_successors(G, source, depth_limit=None, sort_neighbors=None, *, backend=None, **backend_kwargs)
    Returns an iterator of successors in breadth-first-search from source.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Specify starting node for breadth-first search

    depth_limit : int, optional(default=len(G))
        Specify the maximum search depth

    sort_neighbors : function (default=None)
        A function that takes an iterator over nodes as the input, and
        returns an iterable of the same nodes with a custom ordering.
        For example, `sorted` will sort the nodes in increasing order.

    Returns
    -------
    succ: iterator
       (node, successors) iterator where `successors` is the non-empty list of
       successors of `node` in a breadth first search from `source`.
       To appear in the iterator, `node` must have successors.

    Examples
    --------
    >>> G = nx.path_graph(3)
    >>> dict(nx.bfs_successors(G, 0))
    {0: [1], 1: [2]}
    >>> H = nx.Graph()
    >>> H.add_edges_from([(0, 1), (0, 2), (1, 3), (1, 4), (2, 5), (2, 6)])
    >>> dict(nx.bfs_successors(H, 0))
    {0: [1, 2], 1: [3, 4], 2: [5, 6]}
    >>> G = nx.Graph()
    >>> nx.add_path(G, [0, 1, 2, 3, 4, 5, 6])
    >>> nx.add_path(G, [2, 7, 8, 9, 10])
    >>> dict(nx.bfs_successors(G, source=1, depth_limit=3))
    {1: [0, 2], 2: [3, 7], 3: [4], 7: [8]}
    >>> G = nx.DiGraph()
    >>> nx.add_path(G, [0, 1, 2, 3, 4, 5])
    >>> dict(nx.bfs_successors(G, source=3))
    {3: [4], 4: [5]}

    Notes
    -----
    Based on http://www.ics.uci.edu/~eppstein/PADS/BFS.py
    by D. Eppstein, July 2004.The modifications
    to allow depth limits based on the Wikipedia article
    "`Depth-limited-search`_".

    .. _Depth-limited-search: https://en.wikipedia.org/wiki/Depth-limited_search

    See Also
    --------
    bfs_tree
    bfs_edges
    edge_bfs
networkx.bfs_tree
Python Library Documentation: function bfs_tree in module networkx.algorithms.traversal.breadth_first_search

bfs_tree(G, source, reverse=False, depth_limit=None, sort_neighbors=None, *, backend=None, **backend_kwargs)
    Returns an oriented tree constructed from of a breadth-first-search
    starting at source.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Specify starting node for breadth-first search

    reverse : bool, optional
       If True traverse a directed graph in the reverse direction

    depth_limit : int, optional(default=len(G))
        Specify the maximum search depth

    sort_neighbors : function (default=None)
        A function that takes an iterator over nodes as the input, and
        returns an iterable of the same nodes with a custom ordering.
        For example, `sorted` will sort the nodes in increasing order.

    Returns
    -------
    T: NetworkX DiGraph
       An oriented tree

    Examples
    --------
    >>> G = nx.path_graph(3)
    >>> list(nx.bfs_tree(G, 1).edges())
    [(1, 0), (1, 2)]
    >>> H = nx.Graph()
    >>> nx.add_path(H, [0, 1, 2, 3, 4, 5, 6])
    >>> nx.add_path(H, [2, 7, 8, 9, 10])
    >>> sorted(list(nx.bfs_tree(H, source=3, depth_limit=3).edges()))
    [(1, 0), (2, 1), (2, 7), (3, 2), (3, 4), (4, 5), (5, 6), (7, 8)]


    Notes
    -----
    Based on http://www.ics.uci.edu/~eppstein/PADS/BFS.py
    by D. Eppstein, July 2004. The modifications
    to allow depth limits based on the Wikipedia article
    "`Depth-limited-search`_".

    .. _Depth-limited-search: https://en.wikipedia.org/wiki/Depth-limited_search

    See Also
    --------
    dfs_tree
    bfs_edges
    edge_bfs
networkx.biconnected
Python Library Documentation: module networkx.algorithms.components.biconnected in networkx.algorithms.components

NAME
    networkx.algorithms.components.biconnected - Biconnected components and articulation points.

FUNCTIONS
    articulation_points(G, *, backend=None, **backend_kwargs)
        Yield the articulation points, or cut vertices, of a graph.

        An articulation point or cut vertex is any node whose removal (along with
        all its incident edges) increases the number of connected components of
        a graph.  An undirected connected graph without articulation points is
        biconnected. Articulation points belong to more than one biconnected
        component of a graph.

        Notice that by convention a dyad is considered a biconnected component.

        Parameters
        ----------
        G : NetworkX Graph
            An undirected graph.

        Yields
        ------
        node
            An articulation point in the graph.

        Raises
        ------
        NetworkXNotImplemented
            If the input graph is not undirected.

        Examples
        --------

        >>> G = nx.barbell_graph(4, 2)
        >>> print(nx.is_biconnected(G))
        False
        >>> len(list(nx.articulation_points(G)))
        4
        >>> G.add_edge(2, 8)
        >>> print(nx.is_biconnected(G))
        True
        >>> len(list(nx.articulation_points(G)))
        0

        See Also
        --------
        is_biconnected
        biconnected_components
        biconnected_component_edges

        Notes
        -----
        The algorithm to find articulation points and biconnected
        components is implemented using a non-recursive depth-first-search
        (DFS) that keeps track of the highest level that back edges reach
        in the DFS tree.  A node `n` is an articulation point if, and only
        if, there exists a subtree rooted at `n` such that there is no
        back edge from any successor of `n` that links to a predecessor of
        `n` in the DFS tree.  By keeping track of all the edges traversed
        by the DFS we can obtain the biconnected components because all
        edges of a bicomponent will be traversed consecutively between
        articulation points.

        References
        ----------
        .. [1] Hopcroft, J.; Tarjan, R. (1973).
               "Efficient algorithms for graph manipulation".
               Communications of the ACM 16: 372–378. doi:10.1145/362248.362272

    biconnected_component_edges(G, *, backend=None, **backend_kwargs)
        Returns a generator of lists of edges, one list for each biconnected
        component of the input graph.

        Biconnected components are maximal subgraphs such that the removal of a
        node (and all edges incident on that node) will not disconnect the
        subgraph.  Note that nodes may be part of more than one biconnected
        component.  Those nodes are articulation points, or cut vertices.
        However, each edge belongs to one, and only one, biconnected component.

        Notice that by convention a dyad is considered a biconnected component.

        Parameters
        ----------
        G : NetworkX Graph
            An undirected graph.

        Returns
        -------
        edges : generator of lists
            Generator of lists of edges, one list for each bicomponent.

        Raises
        ------
        NetworkXNotImplemented
            If the input graph is not undirected.

        Examples
        --------
        >>> G = nx.barbell_graph(4, 2)
        >>> print(nx.is_biconnected(G))
        False
        >>> bicomponents_edges = list(nx.biconnected_component_edges(G))
        >>> len(bicomponents_edges)
        5
        >>> G.add_edge(2, 8)
        >>> print(nx.is_biconnected(G))
        True
        >>> bicomponents_edges = list(nx.biconnected_component_edges(G))
        >>> len(bicomponents_edges)
        1

        See Also
        --------
        is_biconnected,
        biconnected_components,
        articulation_points,

        Notes
        -----
        The algorithm to find articulation points and biconnected
        components is implemented using a non-recursive depth-first-search
        (DFS) that keeps track of the highest level that back edges reach
        in the DFS tree.  A node `n` is an articulation point if, and only
        if, there exists a subtree rooted at `n` such that there is no
        back edge from any successor of `n` that links to a predecessor of
        `n` in the DFS tree.  By keeping track of all the edges traversed
        by the DFS we can obtain the biconnected components because all
        edges of a bicomponent will be traversed consecutively between
        articulation points.

        References
        ----------
        .. [1] Hopcroft, J.; Tarjan, R. (1973).
               "Efficient algorithms for graph manipulation".
               Communications of the ACM 16: 372–378. doi:10.1145/362248.362272

    biconnected_components(G, *, backend=None, **backend_kwargs)
        Returns a generator of sets of nodes, one set for each biconnected
        component of the graph

        Biconnected components are maximal subgraphs such that the removal of a
        node (and all edges incident on that node) will not disconnect the
        subgraph. Note that nodes may be part of more than one biconnected
        component.  Those nodes are articulation points, or cut vertices.  The
        removal of articulation points will increase the number of connected
        components of the graph.

        Notice that by convention a dyad is considered a biconnected component.

        Parameters
        ----------
        G : NetworkX Graph
            An undirected graph.

        Returns
        -------
        nodes : generator
            Generator of sets of nodes, one set for each biconnected component.

        Raises
        ------
        NetworkXNotImplemented
            If the input graph is not undirected.

        Examples
        --------
        >>> G = nx.lollipop_graph(5, 1)
        >>> print(nx.is_biconnected(G))
        False
        >>> bicomponents = list(nx.biconnected_components(G))
        >>> len(bicomponents)
        2
        >>> G.add_edge(0, 5)
        >>> print(nx.is_biconnected(G))
        True
        >>> bicomponents = list(nx.biconnected_components(G))
        >>> len(bicomponents)
        1

        You can generate a sorted list of biconnected components, largest
        first, using sort.

        >>> G.remove_edge(0, 5)
        >>> [len(c) for c in sorted(nx.biconnected_components(G), key=len, reverse=True)]
        [5, 2]

        If you only want the largest connected component, it's more
        efficient to use max instead of sort.

        >>> Gc = max(nx.biconnected_components(G), key=len)

        To create the components as subgraphs use:
        ``(G.subgraph(c).copy() for c in biconnected_components(G))``

        See Also
        --------
        is_biconnected
        articulation_points
        biconnected_component_edges
        k_components : this function is a special case where k=2
        bridge_components : similar to this function, but is defined using
            2-edge-connectivity instead of 2-node-connectivity.

        Notes
        -----
        The algorithm to find articulation points and biconnected
        components is implemented using a non-recursive depth-first-search
        (DFS) that keeps track of the highest level that back edges reach
        in the DFS tree.  A node `n` is an articulation point if, and only
        if, there exists a subtree rooted at `n` such that there is no
        back edge from any successor of `n` that links to a predecessor of
        `n` in the DFS tree.  By keeping track of all the edges traversed
        by the DFS we can obtain the biconnected components because all
        edges of a bicomponent will be traversed consecutively between
        articulation points.

        References
        ----------
        .. [1] Hopcroft, J.; Tarjan, R. (1973).
               "Efficient algorithms for graph manipulation".
               Communications of the ACM 16: 372–378. doi:10.1145/362248.362272

    is_biconnected(G, *, backend=None, **backend_kwargs)
        Returns True if the graph is biconnected, False otherwise.

        A graph is biconnected if, and only if, it cannot be disconnected by
        removing only one node (and all edges incident on that node).  If
        removing a node increases the number of disconnected components
        in the graph, that node is called an articulation point, or cut
        vertex.  A biconnected graph has no articulation points.

        Parameters
        ----------
        G : NetworkX Graph
            An undirected graph.

        Returns
        -------
        biconnected : bool
            True if the graph is biconnected, False otherwise.

        Raises
        ------
        NetworkXNotImplemented
            If the input graph is not undirected.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> print(nx.is_biconnected(G))
        False
        >>> G.add_edge(0, 3)
        >>> print(nx.is_biconnected(G))
        True

        See Also
        --------
        biconnected_components
        articulation_points
        biconnected_component_edges
        is_strongly_connected
        is_weakly_connected
        is_connected
        is_semiconnected

        Notes
        -----
        The algorithm to find articulation points and biconnected
        components is implemented using a non-recursive depth-first-search
        (DFS) that keeps track of the highest level that back edges reach
        in the DFS tree.  A node `n` is an articulation point if, and only
        if, there exists a subtree rooted at `n` such that there is no
        back edge from any successor of `n` that links to a predecessor of
        `n` in the DFS tree.  By keeping track of all the edges traversed
        by the DFS we can obtain the biconnected components because all
        edges of a bicomponent will be traversed consecutively between
        articulation points.

        References
        ----------
        .. [1] Hopcroft, J.; Tarjan, R. (1973).
           "Efficient algorithms for graph manipulation".
           Communications of the ACM 16: 372–378. doi:10.1145/362248.362272

DATA
    __all__ = ['biconnected_components', 'biconnected_component_edges', 'i...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\components\biconnected.py

networkx.biconnected_component_edges
Python Library Documentation: function biconnected_component_edges in module networkx.algorithms.components.biconnected

biconnected_component_edges(G, *, backend=None, **backend_kwargs)
    Returns a generator of lists of edges, one list for each biconnected
    component of the input graph.

    Biconnected components are maximal subgraphs such that the removal of a
    node (and all edges incident on that node) will not disconnect the
    subgraph.  Note that nodes may be part of more than one biconnected
    component.  Those nodes are articulation points, or cut vertices.
    However, each edge belongs to one, and only one, biconnected component.

    Notice that by convention a dyad is considered a biconnected component.

    Parameters
    ----------
    G : NetworkX Graph
        An undirected graph.

    Returns
    -------
    edges : generator of lists
        Generator of lists of edges, one list for each bicomponent.

    Raises
    ------
    NetworkXNotImplemented
        If the input graph is not undirected.

    Examples
    --------
    >>> G = nx.barbell_graph(4, 2)
    >>> print(nx.is_biconnected(G))
    False
    >>> bicomponents_edges = list(nx.biconnected_component_edges(G))
    >>> len(bicomponents_edges)
    5
    >>> G.add_edge(2, 8)
    >>> print(nx.is_biconnected(G))
    True
    >>> bicomponents_edges = list(nx.biconnected_component_edges(G))
    >>> len(bicomponents_edges)
    1

    See Also
    --------
    is_biconnected,
    biconnected_components,
    articulation_points,

    Notes
    -----
    The algorithm to find articulation points and biconnected
    components is implemented using a non-recursive depth-first-search
    (DFS) that keeps track of the highest level that back edges reach
    in the DFS tree.  A node `n` is an articulation point if, and only
    if, there exists a subtree rooted at `n` such that there is no
    back edge from any successor of `n` that links to a predecessor of
    `n` in the DFS tree.  By keeping track of all the edges traversed
    by the DFS we can obtain the biconnected components because all
    edges of a bicomponent will be traversed consecutively between
    articulation points.

    References
    ----------
    .. [1] Hopcroft, J.; Tarjan, R. (1973).
           "Efficient algorithms for graph manipulation".
           Communications of the ACM 16: 372–378. doi:10.1145/362248.362272
networkx.biconnected_components
Python Library Documentation: function biconnected_components in module networkx.algorithms.components.biconnected

biconnected_components(G, *, backend=None, **backend_kwargs)
    Returns a generator of sets of nodes, one set for each biconnected
    component of the graph

    Biconnected components are maximal subgraphs such that the removal of a
    node (and all edges incident on that node) will not disconnect the
    subgraph. Note that nodes may be part of more than one biconnected
    component.  Those nodes are articulation points, or cut vertices.  The
    removal of articulation points will increase the number of connected
    components of the graph.

    Notice that by convention a dyad is considered a biconnected component.

    Parameters
    ----------
    G : NetworkX Graph
        An undirected graph.

    Returns
    -------
    nodes : generator
        Generator of sets of nodes, one set for each biconnected component.

    Raises
    ------
    NetworkXNotImplemented
        If the input graph is not undirected.

    Examples
    --------
    >>> G = nx.lollipop_graph(5, 1)
    >>> print(nx.is_biconnected(G))
    False
    >>> bicomponents = list(nx.biconnected_components(G))
    >>> len(bicomponents)
    2
    >>> G.add_edge(0, 5)
    >>> print(nx.is_biconnected(G))
    True
    >>> bicomponents = list(nx.biconnected_components(G))
    >>> len(bicomponents)
    1

    You can generate a sorted list of biconnected components, largest
    first, using sort.

    >>> G.remove_edge(0, 5)
    >>> [len(c) for c in sorted(nx.biconnected_components(G), key=len, reverse=True)]
    [5, 2]

    If you only want the largest connected component, it's more
    efficient to use max instead of sort.

    >>> Gc = max(nx.biconnected_components(G), key=len)

    To create the components as subgraphs use:
    ``(G.subgraph(c).copy() for c in biconnected_components(G))``

    See Also
    --------
    is_biconnected
    articulation_points
    biconnected_component_edges
    k_components : this function is a special case where k=2
    bridge_components : similar to this function, but is defined using
        2-edge-connectivity instead of 2-node-connectivity.

    Notes
    -----
    The algorithm to find articulation points and biconnected
    components is implemented using a non-recursive depth-first-search
    (DFS) that keeps track of the highest level that back edges reach
    in the DFS tree.  A node `n` is an articulation point if, and only
    if, there exists a subtree rooted at `n` such that there is no
    back edge from any successor of `n` that links to a predecessor of
    `n` in the DFS tree.  By keeping track of all the edges traversed
    by the DFS we can obtain the biconnected components because all
    edges of a bicomponent will be traversed consecutively between
    articulation points.

    References
    ----------
    .. [1] Hopcroft, J.; Tarjan, R. (1973).
           "Efficient algorithms for graph manipulation".
           Communications of the ACM 16: 372–378. doi:10.1145/362248.362272
networkx.bidirectional_dijkstra
Python Library Documentation: function bidirectional_dijkstra in module networkx.algorithms.shortest_paths.weighted

bidirectional_dijkstra(G, source, target, weight='weight', *, backend=None, **backend_kwargs)
    Dijkstra's algorithm for shortest paths using bidirectional search.

    Parameters
    ----------
    G : NetworkX graph

    source : node
        Starting node.

    target : node
        Ending node.

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Returns
    -------
    length, path : number and list
        length is the distance from source to target.
        path is a list of nodes on a path from source to target.

    Raises
    ------
    NodeNotFound
        If `source` or `target` is not in `G`.

    NetworkXNoPath
        If no path exists between source and target.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> length, path = nx.bidirectional_dijkstra(G, 0, 4)
    >>> print(length)
    4
    >>> print(path)
    [0, 1, 2, 3, 4]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The weight function can be used to hide edges by returning None.
    So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
    will find the shortest red path.

    In practice  bidirectional Dijkstra is much more than twice as fast as
    ordinary Dijkstra.

    Ordinary Dijkstra expands nodes in a sphere-like manner from the
    source. The radius of this sphere will eventually be the length
    of the shortest path. Bidirectional Dijkstra will expand nodes
    from both the source and the target, making two spheres of half
    this radius. Volume of the first sphere is `\pi*r*r` while the
    others are `2*\pi*r/2*r/2`, making up half the volume.

    This algorithm is not guaranteed to work if edge weights
    are negative or are floating point numbers
    (overflows and roundoff errors can cause problems).

    See Also
    --------
    shortest_path
    shortest_path_length
networkx.bidirectional_shortest_path
Python Library Documentation: function bidirectional_shortest_path in module networkx.algorithms.shortest_paths.unweighted

bidirectional_shortest_path(G, source, target, *, backend=None, **backend_kwargs)
    Returns a list of nodes in a shortest path between source and target.

    Parameters
    ----------
    G : NetworkX graph

    source : node label
       starting node for path

    target : node label
       ending node for path

    Returns
    -------
    path: list
       List of nodes in a path from source to target.

    Raises
    ------
    NetworkXNoPath
       If no path exists between source and target.

    Examples
    --------
    >>> G = nx.Graph()
    >>> nx.add_path(G, [0, 1, 2, 3, 0, 4, 5, 6, 7, 4])
    >>> nx.bidirectional_shortest_path(G, 2, 6)
    [2, 1, 0, 4, 5, 6]

    See Also
    --------
    shortest_path

    Notes
    -----
    This algorithm is used by shortest_path(G, source, target).
networkx.binary
Python Library Documentation: module networkx.algorithms.operators.binary in networkx.algorithms.operators

NAME
    networkx.algorithms.operators.binary - Operations on graphs including union, intersection, difference.

FUNCTIONS
    compose(G, H, *, backend=None, **backend_kwargs)
        Compose graph G with H by combining nodes and edges into a single graph.

        The node sets and edges sets do not need to be disjoint.

        Composing preserves the attributes of nodes and edges.
        Attribute values from H take precedent over attribute values from G.

        Parameters
        ----------
        G, H : graph
           A NetworkX graph

        Returns
        -------
        C: A new graph with the same type as G

        See Also
        --------
        :func:`~networkx.Graph.update`
        union
        disjoint_union

        Notes
        -----
        It is recommended that G and H be either both directed or both undirected.

        For MultiGraphs, the edges are identified by incident nodes AND edge-key.
        This can cause surprises (i.e., edge `(1, 2)` may or may not be the same
        in two graphs) if you use MultiGraph without keeping track of edge keys.

        If combining the attributes of common nodes is not desired, consider union(),
        which raises an exception for name collisions.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2)])
        >>> H = nx.Graph([(0, 1), (1, 2)])
        >>> R = nx.compose(G, H)
        >>> R.nodes
        NodeView((0, 1, 2))
        >>> R.edges
        EdgeView([(0, 1), (0, 2), (1, 2)])

        By default, the attributes from `H` take precedent over attributes from `G`.
        If you prefer another way of combining attributes, you can update them after the compose operation:

        >>> G = nx.Graph([(0, 1, {"weight": 2.0}), (3, 0, {"weight": 100.0})])
        >>> H = nx.Graph([(0, 1, {"weight": 10.0}), (1, 2, {"weight": -1.0})])
        >>> nx.set_node_attributes(G, {0: "dark", 1: "light", 3: "black"}, name="color")
        >>> nx.set_node_attributes(H, {0: "green", 1: "orange", 2: "yellow"}, name="color")
        >>> GcomposeH = nx.compose(G, H)

        Normally, color attribute values of nodes of GcomposeH come from H. We can workaround this as follows:

        >>> node_data = {
        ...     n: G.nodes[n]["color"] + " " + H.nodes[n]["color"]
        ...     for n in G.nodes & H.nodes
        ... }
        >>> nx.set_node_attributes(GcomposeH, node_data, "color")
        >>> print(GcomposeH.nodes[0]["color"])
        dark green

        >>> print(GcomposeH.nodes[3]["color"])
        black

        Similarly, we can update edge attributes after the compose operation in a way we prefer:

        >>> edge_data = {
        ...     e: G.edges[e]["weight"] * H.edges[e]["weight"] for e in G.edges & H.edges
        ... }
        >>> nx.set_edge_attributes(GcomposeH, edge_data, "weight")
        >>> print(GcomposeH.edges[(0, 1)]["weight"])
        20.0

        >>> print(GcomposeH.edges[(3, 0)]["weight"])
        100.0

    difference(G, H, *, backend=None, **backend_kwargs)
        Returns a new graph that contains the edges that exist in G but not in H.

        The node sets of H and G must be the same.

        Parameters
        ----------
        G,H : graph
           A NetworkX graph. G and H must have the same node sets.

        Returns
        -------
        D : A new graph with the same type as G.

        Notes
        -----
        Attributes from the graph, nodes, and edges are not copied to the new
        graph.  If you want a new graph of the difference of G and H with
        the attributes (including edge data) from G use remove_nodes_from()
        as follows:

        >>> G = nx.path_graph(3)
        >>> H = nx.path_graph(5)
        >>> R = G.copy()
        >>> R.remove_nodes_from(n for n in G if n in H)

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (1, 2), (1, 3)])
        >>> H = nx.Graph([(0, 1), (1, 2), (0, 3)])
        >>> R = nx.difference(G, H)
        >>> R.nodes
        NodeView((0, 1, 2, 3))
        >>> R.edges
        EdgeView([(0, 2), (1, 3)])

    disjoint_union(G, H, *, backend=None, **backend_kwargs)
        Combine graphs G and H. The nodes are assumed to be unique (disjoint).

        This algorithm automatically relabels nodes to avoid name collisions.

        Parameters
        ----------
        G,H : graph
           A NetworkX graph

        Returns
        -------
        U : A union graph with the same type as G.

        See Also
        --------
        union
        compose
        :func:`~networkx.Graph.update`

        Notes
        -----
        A new graph is created, of the same class as G.  It is recommended
        that G and H be either both directed or both undirected.

        The nodes of G are relabeled 0 to len(G)-1, and the nodes of H are
        relabeled len(G) to len(G)+len(H)-1.

        Renumbering forces G and H to be disjoint, so no exception is ever raised for a name collision.
        To preserve the check for common nodes, use union().

        Edge and node attributes are propagated from G and H to the union graph.
        Graph attributes are also propagated, but if they are present in both G and H,
        then the value from H is used.

        To combine graphs that have common nodes, consider compose(G, H)
        or the method, Graph.update().

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (1, 2)])
        >>> H = nx.Graph([(0, 3), (1, 2), (2, 3)])
        >>> G.nodes[0]["key1"] = 5
        >>> H.nodes[0]["key2"] = 10
        >>> U = nx.disjoint_union(G, H)
        >>> U.nodes(data=True)
        NodeDataView({0: {'key1': 5}, 1: {}, 2: {}, 3: {'key2': 10}, 4: {}, 5: {}, 6: {}})
        >>> U.edges
        EdgeView([(0, 1), (0, 2), (1, 2), (3, 4), (4, 6), (5, 6)])

    full_join(G, H, rename=(None, None), *, backend=None, **backend_kwargs)
        Returns the full join of graphs G and H.

        Full join is the union of G and H in which all edges between
        G and H are added.
        The node sets of G and H must be disjoint,
        otherwise an exception is raised.

        Parameters
        ----------
        G, H : graph
           A NetworkX graph

        rename : tuple , default=(None, None)
           Node names of G and H can be changed by specifying the tuple
           rename=('G-','H-') (for example).  Node "u" in G is then renamed
           "G-u" and "v" in H is renamed "H-v".

        Returns
        -------
        U : The full join graph with the same type as G.

        Notes
        -----
        It is recommended that G and H be either both directed or both undirected.

        If G is directed, then edges from G to H are added as well as from H to G.

        Note that full_join() does not produce parallel edges for MultiGraphs.

        The full join operation of graphs G and H is the same as getting
        their complement, performing a disjoint union, and finally getting
        the complement of the resulting graph.

        Graph, edge, and node attributes are propagated from G and H
        to the union graph.  If a graph attribute is present in both
        G and H the value from H is used.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2)])
        >>> H = nx.Graph([(3, 4)])
        >>> R = nx.full_join(G, H, rename=("G", "H"))
        >>> R.nodes
        NodeView(('G0', 'G1', 'G2', 'H3', 'H4'))
        >>> R.edges
        EdgeView([('G0', 'G1'), ('G0', 'G2'), ('G0', 'H3'), ('G0', 'H4'), ('G1', 'H3'), ('G1', 'H4'), ('G2', 'H3'), ('G2', 'H4'), ('H3', 'H4')])

        See Also
        --------
        union
        disjoint_union

    intersection(G, H, *, backend=None, **backend_kwargs)
        Returns a new graph that contains only the nodes and the edges that exist in
        both G and H.

        Parameters
        ----------
        G,H : graph
           A NetworkX graph. G and H can have different node sets but must be both graphs or both multigraphs.

        Raises
        ------
        NetworkXError
            If one is a MultiGraph and the other one is a graph.

        Returns
        -------
        GH : A new graph with the same type as G.

        Notes
        -----
        Attributes from the graph, nodes, and edges are not copied to the new
        graph.  If you want a new graph of the intersection of G and H
        with the attributes (including edge data) from G use remove_nodes_from()
        as follows

        >>> G = nx.path_graph(3)
        >>> H = nx.path_graph(5)
        >>> R = G.copy()
        >>> R.remove_nodes_from(n for n in G if n not in H)
        >>> R.remove_edges_from(e for e in G.edges if e not in H.edges)

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (1, 2)])
        >>> H = nx.Graph([(0, 3), (1, 2), (2, 3)])
        >>> R = nx.intersection(G, H)
        >>> R.nodes
        NodeView((0, 1, 2))
        >>> R.edges
        EdgeView([(1, 2)])

    symmetric_difference(G, H, *, backend=None, **backend_kwargs)
        Returns new graph with edges that exist in either G or H but not both.

        The node sets of H and G must be the same.

        Parameters
        ----------
        G,H : graph
           A NetworkX graph.  G and H must have the same node sets.

        Returns
        -------
        D : A new graph with the same type as G.

        Notes
        -----
        Attributes from the graph, nodes, and edges are not copied to the new
        graph.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (1, 2), (1, 3)])
        >>> H = nx.Graph([(0, 1), (1, 2), (0, 3)])
        >>> R = nx.symmetric_difference(G, H)
        >>> R.nodes
        NodeView((0, 1, 2, 3))
        >>> R.edges
        EdgeView([(0, 2), (0, 3), (1, 3)])

    union(G, H, rename=(), *, backend=None, **backend_kwargs)
        Combine graphs G and H. The names of nodes must be unique.

        A name collision between the graphs will raise an exception.

        A renaming facility is provided to avoid name collisions.


        Parameters
        ----------
        G, H : graph
           A NetworkX graph

        rename : iterable , optional
           Node names of G and H can be changed by specifying the tuple
           rename=('G-','H-') (for example).  Node "u" in G is then renamed
           "G-u" and "v" in H is renamed "H-v".

        Returns
        -------
        U : A union graph with the same type as G.

        See Also
        --------
        compose
        :func:`~networkx.Graph.update`
        disjoint_union

        Notes
        -----
        To combine graphs that have common nodes, consider compose(G, H)
        or the method, Graph.update().

        disjoint_union() is similar to union() except that it avoids name clashes
        by relabeling the nodes with sequential integers.

        Edge and node attributes are propagated from G and H to the union graph.
        Graph attributes are also propagated, but if they are present in both G and H,
        then the value from H is used.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (1, 2)])
        >>> H = nx.Graph([(0, 1), (0, 3), (1, 3), (1, 2)])
        >>> U = nx.union(G, H, rename=("G", "H"))
        >>> U.nodes
        NodeView(('G0', 'G1', 'G2', 'H0', 'H1', 'H3', 'H2'))
        >>> U.edges
        EdgeView([('G0', 'G1'), ('G0', 'G2'), ('G1', 'G2'), ('H0', 'H1'), ('H0', 'H3'), ('H1', 'H3'), ('H1', 'H2')])

DATA
    __all__ = ['union', 'compose', 'disjoint_union', 'intersection', 'diff...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\operators\binary.py

networkx.binomial_graph
Python Library Documentation: function gnp_random_graph in module networkx.generators.random_graphs

gnp_random_graph(n, p, seed=None, directed=False, *, create_using=None, backend=None, **backend_kwargs)
    Returns a $G_{n,p}$ random graph, also known as an Erdős-Rényi graph
    or a binomial graph.

    The $G_{n,p}$ model chooses each of the possible edges with probability $p$.

    Parameters
    ----------
    n : int
        The number of nodes.
    p : float
        Probability for edge creation.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    directed : bool, optional (default=False)
        If True, this function returns a directed graph.
    create_using : Graph constructor, optional (default=nx.Graph or nx.DiGraph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph types are not supported and raise a ``NetworkXError``.
        By default NetworkX Graph or DiGraph are used depending on `directed`.

    See Also
    --------
    fast_gnp_random_graph

    Notes
    -----
    This algorithm [2]_ runs in $O(n^2)$ time.  For sparse graphs (that is, for
    small values of $p$), :func:`fast_gnp_random_graph` is a faster algorithm.

    :func:`binomial_graph` and :func:`erdos_renyi_graph` are
    aliases for :func:`gnp_random_graph`.

    >>> nx.binomial_graph is nx.gnp_random_graph
    True
    >>> nx.erdos_renyi_graph is nx.gnp_random_graph
    True

    References
    ----------
    .. [1] P. Erdős and A. Rényi, On Random Graphs, Publ. Math. 6, 290 (1959).
    .. [2] E. N. Gilbert, Random Graphs, Ann. Math. Stat., 30, 1141 (1959).
networkx.binomial_tree
Python Library Documentation: function binomial_tree in module networkx.generators.classic

binomial_tree(n, create_using=None, *, backend=None, **backend_kwargs)
    Returns the Binomial Tree of order n.

    The binomial tree of order 0 consists of a single node. A binomial tree of order k
    is defined recursively by linking two binomial trees of order k-1: the root of one is
    the leftmost child of the root of the other.

    .. plot::

        >>> nx.draw(nx.binomial_tree(3))

    Parameters
    ----------
    n : int
        Order of the binomial tree.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : NetworkX graph
        A binomial tree of $2^n$ nodes and $2^n - 1$ edges.
networkx.bipartite
Python Library Documentation: package networkx.algorithms.bipartite in networkx.algorithms

NAME
    networkx.algorithms.bipartite

DESCRIPTION
    This module provides functions and operations for bipartite
    graphs.  Bipartite graphs `B = (U, V, E)` have two node sets `U,V` and edges in
    `E` that only connect nodes from opposite sets. It is common in the literature
    to use an spatial analogy referring to the two node sets as top and bottom nodes.

    The bipartite algorithms are not imported into the networkx namespace
    at the top level so the easiest way to use them is with:

    >>> from networkx.algorithms import bipartite

    NetworkX does not have a custom bipartite graph class but the Graph()
    or DiGraph() classes can be used to represent bipartite graphs. However,
    you have to keep track of which set each node belongs to, and make
    sure that there is no edge between nodes of the same set. The convention used
    in NetworkX is to use a node attribute named `bipartite` with values 0 or 1 to
    identify the sets each node belongs to. This convention is not enforced in
    the source code of bipartite functions, it's only a recommendation.

    For example:

    >>> B = nx.Graph()
    >>> # Add nodes with the node attribute "bipartite"
    >>> B.add_nodes_from([1, 2, 3, 4], bipartite=0)
    >>> B.add_nodes_from(["a", "b", "c"], bipartite=1)
    >>> # Add edges only between nodes of opposite node sets
    >>> B.add_edges_from([(1, "a"), (1, "b"), (2, "b"), (2, "c"), (3, "c"), (4, "a")])

    Many algorithms of the bipartite module of NetworkX require, as an argument, a
    container with all the nodes that belong to one set, in addition to the bipartite
    graph `B`. The functions in the bipartite package do not check that the node set
    is actually correct nor that the input graph is actually bipartite.
    If `B` is connected, you can find the two node sets using a two-coloring
    algorithm:

    >>> nx.is_connected(B)
    True
    >>> bottom_nodes, top_nodes = bipartite.sets(B)

    However, if the input graph is not connected, there are more than one possible
    colorations. This is the reason why we require the user to pass a container
    with all nodes of one bipartite node set as an argument to most bipartite
    functions. In the face of ambiguity, we refuse the temptation to guess and
    raise an :exc:`AmbiguousSolution <networkx.AmbiguousSolution>`
    Exception if the input graph for
    :func:`bipartite.sets <networkx.algorithms.bipartite.basic.sets>`
    is disconnected.

    Using the `bipartite` node attribute, you can easily get the two node sets:

    >>> top_nodes = {n for n, d in B.nodes(data=True) if d["bipartite"] == 0}
    >>> bottom_nodes = set(B) - top_nodes

    So you can easily use the bipartite algorithms that require, as an argument, a
    container with all nodes that belong to one node set:

    >>> print(round(bipartite.density(B, bottom_nodes), 2))
    0.5
    >>> G = bipartite.projected_graph(B, top_nodes)

    All bipartite graph generators in NetworkX build bipartite graphs with the
    `bipartite` node attribute. Thus, you can use the same approach:

    >>> RB = bipartite.random_graph(5, 7, 0.2)
    >>> RB_top = {n for n, d in RB.nodes(data=True) if d["bipartite"] == 0}
    >>> RB_bottom = set(RB) - RB_top
    >>> list(RB_top)
    [0, 1, 2, 3, 4]
    >>> list(RB_bottom)
    [5, 6, 7, 8, 9, 10, 11]

    For other bipartite graph generators see
    :mod:`Generators <networkx.algorithms.bipartite.generators>`.

PACKAGE CONTENTS
    basic
    centrality
    cluster
    covering
    edgelist
    extendability
    generators
    matching
    matrix
    projection
    redundancy
    spectral
    tests (package)

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\bipartite\__init__.py

networkx.bipartite_layout
Python Library Documentation: function bipartite_layout in module networkx.drawing.layout

bipartite_layout(G, nodes, align='vertical', scale=1, center=None, aspect_ratio=1.3333333333333333)
    Position nodes in two straight lines.

    Parameters
    ----------
    G : NetworkX graph or list of nodes
        A position will be assigned to every node in G.

    nodes : list or container
        Nodes in one node set of the bipartite graph.
        This set will be placed on left or top.

    align : string (default='vertical')
        The alignment of nodes. Vertical or horizontal.

    scale : number (default: 1)
        Scale factor for positions.

    center : array-like or None
        Coordinate pair around which to center the layout.

    aspect_ratio : number (default=4/3):
        The ratio of the width to the height of the layout.

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node.

    Examples
    --------
    >>> G = nx.bipartite.gnmk_random_graph(3, 5, 10, seed=123)
    >>> top = nx.bipartite.sets(G)[0]
    >>> pos = nx.bipartite_layout(G, top)

    Notes
    -----
    This algorithm currently only works in two dimensions and does not
    try to minimize edge crossings.
networkx.boundary
Python Library Documentation: module networkx.algorithms.boundary in networkx.algorithms

NAME
    networkx.algorithms.boundary - Routines to find the boundary of a set of nodes.

DESCRIPTION
    An edge boundary is a set of edges, each of which has exactly one
    endpoint in a given set of nodes (or, in the case of directed graphs,
    the set of edges whose source node is in the set).

    A node boundary of a set *S* of nodes is the set of (out-)neighbors of
    nodes in *S* that are outside *S*.

FUNCTIONS
    edge_boundary(G, nbunch1, nbunch2=None, data=False, keys=False, default=None, *, backend=None, **backend_kwargs)
        Returns the edge boundary of `nbunch1`.

        The *edge boundary* of a set *S* with respect to a set *T* is the
        set of edges (*u*, *v*) such that *u* is in *S* and *v* is in *T*.
        If *T* is not specified, it is assumed to be the set of all nodes
        not in *S*.

        Parameters
        ----------
        G : NetworkX graph

        nbunch1 : iterable
            Iterable of nodes in the graph representing the set of nodes
            whose edge boundary will be returned. (This is the set *S* from
            the definition above.)

        nbunch2 : iterable
            Iterable of nodes representing the target (or "exterior") set of
            nodes. (This is the set *T* from the definition above.) If not
            specified, this is assumed to be the set of all nodes in `G`
            not in `nbunch1`.

        keys : bool
            This parameter has the same meaning as in
            :meth:`MultiGraph.edges`.

        data : bool or object
            This parameter has the same meaning as in
            :meth:`MultiGraph.edges`.

        default : object
            This parameter has the same meaning as in
            :meth:`MultiGraph.edges`.

        Returns
        -------
        iterator
            An iterator over the edges in the boundary of `nbunch1` with
            respect to `nbunch2`. If `keys`, `data`, or `default`
            are specified and `G` is a multigraph, then edges are returned
            with keys and/or data, as in :meth:`MultiGraph.edges`.

        Examples
        --------
        >>> G = nx.wheel_graph(6)

        When nbunch2=None:

        >>> list(nx.edge_boundary(G, (1, 3)))
        [(1, 0), (1, 2), (1, 5), (3, 0), (3, 2), (3, 4)]

        When nbunch2 is given:

        >>> list(nx.edge_boundary(G, (1, 3), (2, 0)))
        [(1, 0), (1, 2), (3, 0), (3, 2)]

        Notes
        -----
        Any element of `nbunch` that is not in the graph `G` will be
        ignored.

        `nbunch1` and `nbunch2` are usually meant to be disjoint, but in
        the interest of speed and generality, that is not required here.

    node_boundary(G, nbunch1, nbunch2=None, *, backend=None, **backend_kwargs)
        Returns the node boundary of `nbunch1`.

        The *node boundary* of a set *S* with respect to a set *T* is the
        set of nodes *v* in *T* such that for some *u* in *S*, there is an
        edge joining *u* to *v*. If *T* is not specified, it is assumed to
        be the set of all nodes not in *S*.

        Parameters
        ----------
        G : NetworkX graph

        nbunch1 : iterable
            Iterable of nodes in the graph representing the set of nodes
            whose node boundary will be returned. (This is the set *S* from
            the definition above.)

        nbunch2 : iterable
            Iterable of nodes representing the target (or "exterior") set of
            nodes. (This is the set *T* from the definition above.) If not
            specified, this is assumed to be the set of all nodes in `G`
            not in `nbunch1`.

        Returns
        -------
        set
            The node boundary of `nbunch1` with respect to `nbunch2`.

        Examples
        --------
        >>> G = nx.wheel_graph(6)

        When nbunch2=None:

        >>> list(nx.node_boundary(G, (3, 4)))
        [0, 2, 5]

        When nbunch2 is given:

        >>> list(nx.node_boundary(G, (3, 4), (0, 1, 5)))
        [0, 5]

        Notes
        -----
        Any element of `nbunch` that is not in the graph `G` will be
        ignored.

        `nbunch1` and `nbunch2` are usually meant to be disjoint, but in
        the interest of speed and generality, that is not required here.

DATA
    __all__ = ['edge_boundary', 'node_boundary']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\boundary.py

networkx.boundary_expansion
Python Library Documentation: function boundary_expansion in module networkx.algorithms.cuts

boundary_expansion(G, S, *, backend=None, **backend_kwargs)
    Returns the boundary expansion of the set `S`.

    The *boundary expansion* is the quotient of the size
    of the node boundary and the cardinality of *S*. [1]

    Parameters
    ----------
    G : NetworkX graph

    S : collection
        A collection of nodes in `G`.

    Returns
    -------
    number
        The boundary expansion of the set `S`.

    See also
    --------
    edge_expansion
    mixing_expansion
    node_expansion

    References
    ----------
    .. [1] Vadhan, Salil P.
           "Pseudorandomness."
           *Foundations and Trends in Theoretical Computer Science*
           7.1–3 (2011): 1–336.
           <https://doi.org/10.1561/0400000010>
networkx.bridges
Python Library Documentation: function bridges in module networkx.algorithms.bridges

bridges(G, root=None, *, backend=None, **backend_kwargs)
    Generate all bridges in a graph.

    A *bridge* in a graph is an edge whose removal causes the number of
    connected components of the graph to increase.  Equivalently, a bridge is an
    edge that does not belong to any cycle. Bridges are also known as cut-edges,
    isthmuses, or cut arcs.

    Parameters
    ----------
    G : undirected graph

    root : node (optional)
       A node in the graph `G`. If specified, only the bridges in the
       connected component containing this node will be returned.

    Yields
    ------
    e : edge
       An edge in the graph whose removal disconnects the graph (or
       causes the number of connected components to increase).

    Raises
    ------
    NodeNotFound
       If `root` is not in the graph `G`.

    NetworkXNotImplemented
        If `G` is a directed graph.

    Examples
    --------
    The barbell graph with parameter zero has a single bridge:

    >>> G = nx.barbell_graph(10, 0)
    >>> list(nx.bridges(G))
    [(9, 10)]

    Notes
    -----
    This is an implementation of the algorithm described in [1]_.  An edge is a
    bridge if and only if it is not contained in any chain. Chains are found
    using the :func:`networkx.chain_decomposition` function.

    The algorithm described in [1]_ requires a simple graph. If the provided
    graph is a multigraph, we convert it to a simple graph and verify that any
    bridges discovered by the chain decomposition algorithm are not multi-edges.

    Ignoring polylogarithmic factors, the worst-case time complexity is the
    same as the :func:`networkx.chain_decomposition` function,
    $O(m + n)$, where $n$ is the number of nodes in the graph and $m$ is
    the number of edges.

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Bridge_%28graph_theory%29#Bridge-Finding_with_Chain_Decompositions
networkx.broadcasting
Python Library Documentation: module networkx.algorithms.broadcasting in networkx.algorithms

NAME
    networkx.algorithms.broadcasting - Routines to calculate the broadcast time of certain graphs.

DESCRIPTION
    Broadcasting is an information dissemination problem in which a node in a graph,
    called the originator, must distribute a message to all other nodes by placing
    a series of calls along the edges of the graph. Once informed, other nodes aid
    the originator in distributing the message.

    The broadcasting must be completed as quickly as possible subject to the
    following constraints:
    - Each call requires one unit of time.
    - A node can only participate in one call per unit of time.
    - Each call only involves two adjacent nodes: a sender and a receiver.

FUNCTIONS
    tree_broadcast_center(G, *, backend=None, **backend_kwargs)
        Return the Broadcast Center of the tree `G`.

        The broadcast center of a graph G denotes the set of nodes having
        minimum broadcast time [1]_. This is a linear algorithm for determining
        the broadcast center of a tree with ``N`` nodes, as a by-product it also
        determines the broadcast time from the broadcast center.

        Parameters
        ----------
        G : undirected graph
            The graph should be an undirected tree

        Returns
        -------
        BC : (int, set) tuple
            minimum broadcast number of the tree, set of broadcast centers

        Raises
        ------
        NetworkXNotImplemented
            If the graph is directed or is a multigraph.

        References
        ----------
        .. [1] Slater, P.J., Cockayne, E.J., Hedetniemi, S.T,
           Information dissemination in trees. SIAM J.Comput. 10(4), 692–701 (1981)

    tree_broadcast_time(G, node=None, *, backend=None, **backend_kwargs)
        Return the Broadcast Time of the tree `G`.

        The minimum broadcast time of a node is defined as the minimum amount
        of time required to complete broadcasting starting from the
        originator. The broadcast time of a graph is the maximum over
        all nodes of the minimum broadcast time from that node [1]_.
        This function returns the minimum broadcast time of `node`.
        If `node` is None the broadcast time for the graph is returned.

        Parameters
        ----------
        G : undirected graph
            The graph should be an undirected tree
        node: int, optional
            index of starting node. If `None`, the algorithm returns the broadcast
            time of the tree.

        Returns
        -------
        BT : int
            Broadcast Time of a node in a tree

        Raises
        ------
        NetworkXNotImplemented
            If the graph is directed or is a multigraph.

        References
        ----------
        .. [1] Harutyunyan, H. A. and Li, Z.
            "A Simple Construction of Broadcast Graphs."
            In Computing and Combinatorics. COCOON 2019
            (Ed. D. Z. Du and C. Tian.) Springer, pp. 240-253, 2019.

DATA
    __all__ = ['tree_broadcast_center', 'tree_broadcast_time']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\broadcasting.py

networkx.bull_graph
Python Library Documentation: function bull_graph in module networkx.generators.small

bull_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Bull Graph

    The Bull Graph has 5 nodes and 5 edges. It is a planar undirected
    graph in the form of a triangle with two disjoint pendant edges [1]_
    The name comes from the triangle and pendant edges representing
    respectively the body and legs of a bull.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        A bull graph with 5 nodes

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Bull_graph.
networkx.capacity_scaling
Python Library Documentation: function capacity_scaling in module networkx.algorithms.flow.capacityscaling

capacity_scaling(G, demand='demand', capacity='capacity', weight='weight', heap=<class 'networkx.utils.heaps.BinaryHeap'>, *, backend=None, **backend_kwargs)
    Find a minimum cost flow satisfying all demands in digraph G.

    This is a capacity scaling successive shortest augmenting path algorithm.

    G is a digraph with edge costs and capacities and in which nodes
    have demand, i.e., they want to send or receive some amount of
    flow. A negative demand means that the node wants to send flow, a
    positive demand means that the node want to receive flow. A flow on
    the digraph G satisfies all demand if the net flow into each node
    is equal to the demand of that node.

    Parameters
    ----------
    G : NetworkX graph
        DiGraph or MultiDiGraph on which a minimum cost flow satisfying all
        demands is to be found.

    demand : string
        Nodes of the graph G are expected to have an attribute demand
        that indicates how much flow a node wants to send (negative
        demand) or receive (positive demand). Note that the sum of the
        demands should be 0 otherwise the problem in not feasible. If
        this attribute is not present, a node is considered to have 0
        demand. Default value: 'demand'.

    capacity : string
        Edges of the graph G are expected to have an attribute capacity
        that indicates how much flow the edge can support. If this
        attribute is not present, the edge is considered to have
        infinite capacity. Default value: 'capacity'.

    weight : string
        Edges of the graph G are expected to have an attribute weight
        that indicates the cost incurred by sending one unit of flow on
        that edge. If not present, the weight is considered to be 0.
        Default value: 'weight'.

    heap : class
        Type of heap to be used in the algorithm. It should be a subclass of
        :class:`MinHeap` or implement a compatible interface.

        If a stock heap implementation is to be used, :class:`BinaryHeap` is
        recommended over :class:`PairingHeap` for Python implementations without
        optimized attribute accesses (e.g., CPython) despite a slower
        asymptotic running time. For Python implementations with optimized
        attribute accesses (e.g., PyPy), :class:`PairingHeap` provides better
        performance. Default value: :class:`BinaryHeap`.

    Returns
    -------
    flowCost : integer
        Cost of a minimum cost flow satisfying all demands.

    flowDict : dictionary
        If G is a digraph, a dict-of-dicts keyed by nodes such that
        flowDict[u][v] is the flow on edge (u, v).
        If G is a MultiDiGraph, a dict-of-dicts-of-dicts keyed by nodes
        so that flowDict[u][v][key] is the flow on edge (u, v, key).

    Raises
    ------
    NetworkXError
        This exception is raised if the input graph is not directed,
        not connected.

    NetworkXUnfeasible
        This exception is raised in the following situations:

            * The sum of the demands is not zero. Then, there is no
              flow satisfying all demands.
            * There is no flow satisfying all demand.

    NetworkXUnbounded
        This exception is raised if the digraph G has a cycle of
        negative cost and infinite capacity. Then, the cost of a flow
        satisfying all demands is unbounded below.

    Notes
    -----
    This algorithm does not work if edge weights are floating-point numbers.

    See also
    --------
    :meth:`network_simplex`

    Examples
    --------
    A simple example of a min cost flow problem.

    >>> G = nx.DiGraph()
    >>> G.add_node("a", demand=-5)
    >>> G.add_node("d", demand=5)
    >>> G.add_edge("a", "b", weight=3, capacity=4)
    >>> G.add_edge("a", "c", weight=6, capacity=10)
    >>> G.add_edge("b", "d", weight=1, capacity=9)
    >>> G.add_edge("c", "d", weight=2, capacity=5)
    >>> flowCost, flowDict = nx.capacity_scaling(G)
    >>> flowCost
    24
    >>> flowDict
    {'a': {'b': 4, 'c': 1}, 'd': {}, 'b': {'d': 4}, 'c': {'d': 1}}

    It is possible to change the name of the attributes used for the
    algorithm.

    >>> G = nx.DiGraph()
    >>> G.add_node("p", spam=-4)
    >>> G.add_node("q", spam=2)
    >>> G.add_node("a", spam=-2)
    >>> G.add_node("d", spam=-1)
    >>> G.add_node("t", spam=2)
    >>> G.add_node("w", spam=3)
    >>> G.add_edge("p", "q", cost=7, vacancies=5)
    >>> G.add_edge("p", "a", cost=1, vacancies=4)
    >>> G.add_edge("q", "d", cost=2, vacancies=3)
    >>> G.add_edge("t", "q", cost=1, vacancies=2)
    >>> G.add_edge("a", "t", cost=2, vacancies=4)
    >>> G.add_edge("d", "w", cost=3, vacancies=4)
    >>> G.add_edge("t", "w", cost=4, vacancies=1)
    >>> flowCost, flowDict = nx.capacity_scaling(
    ...     G, demand="spam", capacity="vacancies", weight="cost"
    ... )
    >>> flowCost
    37
    >>> flowDict
    {'p': {'q': 2, 'a': 2}, 'q': {'d': 1}, 'a': {'t': 4}, 'd': {'w': 2}, 't': {'q': 1, 'w': 1}, 'w': {}}
networkx.cartesian_product
Python Library Documentation: function cartesian_product in module networkx.algorithms.operators.product

cartesian_product(G, H, *, backend=None, **backend_kwargs)
    Returns the Cartesian product of G and H.

    The Cartesian product $P$ of the graphs $G$ and $H$ has a node set that
    is the Cartesian product of the node sets, $V(P)=V(G) \times V(H)$.
    $P$ has an edge $((u,v),(x,y))$ if and only if either $u$ is equal to $x$
    and both $v$ and $y$ are adjacent in $H$ or if $v$ is equal to $y$ and
    both $u$ and $x$ are adjacent in $G$.

    Parameters
    ----------
    G, H: graphs
     Networkx graphs.

    Returns
    -------
    P: NetworkX graph
     The Cartesian product of G and H. P will be a multi-graph if either G
     or H is a multi-graph. Will be a directed if G and H are directed,
     and undirected if G and H are undirected.

    Raises
    ------
    NetworkXError
     If G and H are not both directed or both undirected.

    Notes
    -----
    Node attributes in P are two-tuple of the G and H node attributes.
    Missing attributes are assigned None.

    Examples
    --------
    >>> G = nx.Graph()
    >>> H = nx.Graph()
    >>> G.add_node(0, a1=True)
    >>> H.add_node("a", a2="Spam")
    >>> P = nx.cartesian_product(G, H)
    >>> list(P)
    [(0, 'a')]

    Edge attributes and edge keys (for multigraphs) are also copied to the
    new product graph
networkx.caveman_graph
Python Library Documentation: function caveman_graph in module networkx.generators.community

caveman_graph(l, k, *, backend=None, **backend_kwargs)
    Returns a caveman graph of `l` cliques of size `k`.

    Parameters
    ----------
    l : int
      Number of cliques
    k : int
      Size of cliques

    Returns
    -------
    G : NetworkX Graph
      caveman graph

    Notes
    -----
    This returns an undirected graph, it can be converted to a directed
    graph using :func:`nx.to_directed`, or a multigraph using
    ``nx.MultiGraph(nx.caveman_graph(l, k))``. Only the undirected version is
    described in [1]_ and it is unclear which of the directed
    generalizations is most useful.

    Examples
    --------
    >>> G = nx.caveman_graph(3, 3)

    See also
    --------

    connected_caveman_graph

    References
    ----------
    .. [1] Watts, D. J. 'Networks, Dynamics, and the Small-World Phenomenon.'
       Amer. J. Soc. 105, 493-527, 1999.
networkx.cd_index
Python Library Documentation: function cd_index in module networkx.algorithms.time_dependent

cd_index(G, node, time_delta, *, time='time', weight=None, backend=None, **backend_kwargs)
    Compute the CD index for `node` within the graph `G`.

    Calculates the CD index for the given node of the graph,
    considering only its predecessors who have the `time` attribute
    smaller than or equal to the `time` attribute of the `node`
    plus `time_delta`.

    Parameters
    ----------
    G : graph
       A directed networkx graph whose nodes have `time` attributes and optionally
       `weight` attributes (if a weight is not given, it is considered 1).
    node : node
       The node for which the CD index is calculated.
    time_delta : numeric or timedelta
       Amount of time after the `time` attribute of the `node`. The value of
       `time_delta` must support comparison with the `time` node attribute. For
       example, if the `time` attribute of the nodes are `datetime.datetime`
       objects, then `time_delta` should be a `datetime.timedelta` object.
    time : string (Optional, default is "time")
        The name of the node attribute that will be used for the calculations.
    weight : string (Optional, default is None)
        The name of the node attribute used as weight.

    Returns
    -------
    float
       The CD index calculated for the node `node` within the graph `G`.

    Raises
    ------
    NetworkXError
       If not all nodes have a `time` attribute or
       `time_delta` and `time` attribute types are not compatible or
       `n` equals 0.

    NetworkXNotImplemented
        If `G` is a non-directed graph or a multigraph.

    Examples
    --------
    >>> from datetime import datetime, timedelta
    >>> G = nx.DiGraph()
    >>> nodes = {
    ...     1: {"time": datetime(2015, 1, 1)},
    ...     2: {"time": datetime(2012, 1, 1), "weight": 4},
    ...     3: {"time": datetime(2010, 1, 1)},
    ...     4: {"time": datetime(2008, 1, 1)},
    ...     5: {"time": datetime(2014, 1, 1)},
    ... }
    >>> G.add_nodes_from([(n, nodes[n]) for n in nodes])
    >>> edges = [(1, 3), (1, 4), (2, 3), (3, 4), (3, 5)]
    >>> G.add_edges_from(edges)
    >>> delta = timedelta(days=5 * 365)
    >>> nx.cd_index(G, 3, time_delta=delta, time="time")
    0.5
    >>> nx.cd_index(G, 3, time_delta=delta, time="time", weight="weight")
    0.12

    Integers can also be used for the time values:
    >>> node_times = {1: 2015, 2: 2012, 3: 2010, 4: 2008, 5: 2014}
    >>> nx.set_node_attributes(G, node_times, "new_time")
    >>> nx.cd_index(G, 3, time_delta=4, time="new_time")
    0.5
    >>> nx.cd_index(G, 3, time_delta=4, time="new_time", weight="weight")
    0.12

    Notes
    -----
    This method implements the algorithm for calculating the CD index,
    as described in the paper by Funk and Owen-Smith [1]_. The CD index
    is used in order to check how consolidating or destabilizing a patent
    is, hence the nodes of the graph represent patents and the edges show
    the citations between these patents. The mathematical model is given
    below:

    .. math::
        CD_{t}=\frac{1}{n_{t}}\sum_{i=1}^{n}\frac{-2f_{it}b_{it}+f_{it}}{w_{it}},

    where `f_{it}` equals 1 if `i` cites the focal patent else 0, `b_{it}` equals
    1 if `i` cites any of the focal patents successors else 0, `n_{t}` is the number
    of forward citations in `i` and `w_{it}` is a matrix of weight for patent `i`
    at time `t`.

    The `datetime.timedelta` package can lead to off-by-one issues when converting
    from years to days. In the example above `timedelta(days=5 * 365)` looks like
    5 years, but it isn't because of leap year days. So it gives the same result
    as `timedelta(days=4 * 365)`. But using `timedelta(days=5 * 365 + 1)` gives
    a 5 year delta **for this choice of years** but may not if the 5 year gap has
    more than 1 leap year. To avoid these issues, use integers to represent years,
    or be very careful when you convert units of time.

    References
    ----------
    .. [1] Funk, Russell J., and Jason Owen-Smith.
           "A dynamic network measure of technological change."
           Management science 63, no. 3 (2017): 791-817.
           http://russellfunk.org/cdindex/static/papers/funk_ms_2017.pdf
networkx.center
Python Library Documentation: function center in module networkx.algorithms.distance_measures

center(G, e=None, usebounds=False, weight=None, *, backend=None, **backend_kwargs)
    Returns the center of the graph G.

    The center is the set of nodes with eccentricity equal to radius.

    Parameters
    ----------
    G : NetworkX graph
       A graph

    e : eccentricity dictionary, optional
      A precomputed dictionary of eccentricities.

    weight : string, function, or None
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

        If this is None, every edge has weight/distance/cost 1.

        Weights stored as floating point values can lead to small round-off
        errors in distances. Use integer weights to avoid this.

        Weights should be positive, since they are distances.

    Returns
    -------
    c : list
       List of nodes in center

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
    >>> list(nx.center(G))
    [1, 3, 4]

    See Also
    --------
    barycenter
    periphery
networkx.centrality
Python Library Documentation: package networkx.algorithms.centrality in networkx.algorithms

NAME
    networkx.algorithms.centrality

PACKAGE CONTENTS
    betweenness
    betweenness_subset
    closeness
    current_flow_betweenness
    current_flow_betweenness_subset
    current_flow_closeness
    degree_alg
    dispersion
    eigenvector
    flow_matrix
    group
    harmonic
    katz
    laplacian
    load
    percolation
    reaching
    second_order
    subgraph_alg
    tests (package)
    trophic
    voterank_alg

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\__init__.py

networkx.chain_decomposition
Python Library Documentation: function chain_decomposition in module networkx.algorithms.chains

chain_decomposition(G, root=None, *, backend=None, **backend_kwargs)
    Returns the chain decomposition of a graph.

    The *chain decomposition* of a graph with respect a depth-first
    search tree is a set of cycles or paths derived from the set of
    fundamental cycles of the tree in the following manner. Consider
    each fundamental cycle with respect to the given tree, represented
    as a list of edges beginning with the nontree edge oriented away
    from the root of the tree. For each fundamental cycle, if it
    overlaps with any previous fundamental cycle, just take the initial
    non-overlapping segment, which is a path instead of a cycle. Each
    cycle or path is called a *chain*. For more information, see [1]_.

    Parameters
    ----------
    G : undirected graph

    root : node (optional)
       A node in the graph `G`. If specified, only the chain
       decomposition for the connected component containing this node
       will be returned. This node indicates the root of the depth-first
       search tree.

    Yields
    ------
    chain : list
       A list of edges representing a chain. There is no guarantee on
       the orientation of the edges in each chain (for example, if a
       chain includes the edge joining nodes 1 and 2, the chain may
       include either (1, 2) or (2, 1)).

    Raises
    ------
    NodeNotFound
       If `root` is not in the graph `G`.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (1, 4), (3, 4), (3, 5), (4, 5)])
    >>> list(nx.chain_decomposition(G))
    [[(4, 5), (5, 3), (3, 4)]]

    Notes
    -----
    The worst-case running time of this implementation is linear in the
    number of nodes and number of edges [1]_.

    References
    ----------
    .. [1] Jens M. Schmidt (2013). "A simple test on 2-vertex-
       and 2-edge-connectivity." *Information Processing Letters*,
       113, 241–244. Elsevier. <https://doi.org/10.1016/j.ipl.2013.01.016>
networkx.chains
Python Library Documentation: module networkx.algorithms.chains in networkx.algorithms

NAME
    networkx.algorithms.chains - Functions for finding chains in a graph.

FUNCTIONS
    chain_decomposition(G, root=None, *, backend=None, **backend_kwargs)
        Returns the chain decomposition of a graph.

        The *chain decomposition* of a graph with respect a depth-first
        search tree is a set of cycles or paths derived from the set of
        fundamental cycles of the tree in the following manner. Consider
        each fundamental cycle with respect to the given tree, represented
        as a list of edges beginning with the nontree edge oriented away
        from the root of the tree. For each fundamental cycle, if it
        overlaps with any previous fundamental cycle, just take the initial
        non-overlapping segment, which is a path instead of a cycle. Each
        cycle or path is called a *chain*. For more information, see [1]_.

        Parameters
        ----------
        G : undirected graph

        root : node (optional)
           A node in the graph `G`. If specified, only the chain
           decomposition for the connected component containing this node
           will be returned. This node indicates the root of the depth-first
           search tree.

        Yields
        ------
        chain : list
           A list of edges representing a chain. There is no guarantee on
           the orientation of the edges in each chain (for example, if a
           chain includes the edge joining nodes 1 and 2, the chain may
           include either (1, 2) or (2, 1)).

        Raises
        ------
        NodeNotFound
           If `root` is not in the graph `G`.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (1, 4), (3, 4), (3, 5), (4, 5)])
        >>> list(nx.chain_decomposition(G))
        [[(4, 5), (5, 3), (3, 4)]]

        Notes
        -----
        The worst-case running time of this implementation is linear in the
        number of nodes and number of edges [1]_.

        References
        ----------
        .. [1] Jens M. Schmidt (2013). "A simple test on 2-vertex-
           and 2-edge-connectivity." *Information Processing Letters*,
           113, 241–244. Elsevier. <https://doi.org/10.1016/j.ipl.2013.01.016>

DATA
    __all__ = ['chain_decomposition']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\chains.py

networkx.check_planarity
Python Library Documentation: function check_planarity in module networkx.algorithms.planarity

check_planarity(G, counterexample=False, *, backend=None, **backend_kwargs)
    Check if a graph is planar and return a counterexample or an embedding.

    A graph is planar iff it can be drawn in a plane without
    any edge intersections.

    Parameters
    ----------
    G : NetworkX graph
    counterexample : bool
        A Kuratowski subgraph (to proof non planarity) is only returned if set
        to true.

    Returns
    -------
    (is_planar, certificate) : (bool, NetworkX graph) tuple
        is_planar is true if the graph is planar.
        If the graph is planar `certificate` is a PlanarEmbedding
        otherwise it is a Kuratowski subgraph.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2)])
    >>> is_planar, P = nx.check_planarity(G)
    >>> print(is_planar)
    True

    When `G` is planar, a `PlanarEmbedding` instance is returned:

    >>> P.get_data()
    {0: [1, 2], 1: [0], 2: [0]}

    Notes
    -----
    A (combinatorial) embedding consists of cyclic orderings of the incident
    edges at each vertex. Given such an embedding there are multiple approaches
    discussed in literature to drawing the graph (subject to various
    constraints, e.g. integer coordinates), see e.g. [2].

    The planarity check algorithm and extraction of the combinatorial embedding
    is based on the Left-Right Planarity Test [1].

    A counterexample is only generated if the corresponding parameter is set,
    because the complexity of the counterexample generation is higher.

    See also
    --------
    is_planar :
        Check for planarity without creating a `PlanarEmbedding` or counterexample.

    References
    ----------
    .. [1] Ulrik Brandes:
        The Left-Right Planarity Test
        2009
        http://citeseerx.ist.psu.edu/viewdoc/summary?doi=10.1.1.217.9208
    .. [2] Takao Nishizeki, Md Saidur Rahman:
        Planar graph drawing
        Lecture Notes Series on Computing: Volume 12
        2004
networkx.chordal
Python Library Documentation: module networkx.algorithms.chordal in networkx.algorithms

NAME
    networkx.algorithms.chordal - Algorithms for chordal graphs.

DESCRIPTION
    A graph is chordal if every cycle of length at least 4 has a chord
    (an edge joining two nodes not adjacent in the cycle).
    https://en.wikipedia.org/wiki/Chordal_graph

CLASSES
    networkx.exception.NetworkXException(builtins.Exception)
        NetworkXTreewidthBoundExceeded

    class NetworkXTreewidthBoundExceeded(networkx.exception.NetworkXException)
     |  Exception raised when a treewidth bound has been provided and it has
     |  been exceeded
     |
     |  Method resolution order:
     |      NetworkXTreewidthBoundExceeded
     |      networkx.exception.NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from networkx.exception.NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

FUNCTIONS
    chordal_graph_cliques(G, *, backend=None, **backend_kwargs)
        Returns all maximal cliques of a chordal graph.

        The algorithm breaks the graph in connected components and performs a
        maximum cardinality search in each component to get the cliques.

        Parameters
        ----------
        G : graph
          A NetworkX graph

        Yields
        ------
        frozenset of nodes
            Maximal cliques, each of which is a frozenset of
            nodes in `G`. The order of cliques is arbitrary.

        Raises
        ------
        NetworkXError
            The algorithm does not support DiGraph, MultiGraph and MultiDiGraph.
            The algorithm can only be applied to chordal graphs. If the input
            graph is found to be non-chordal, a :exc:`NetworkXError` is raised.

        Examples
        --------
        >>> e = [
        ...     (1, 2),
        ...     (1, 3),
        ...     (2, 3),
        ...     (2, 4),
        ...     (3, 4),
        ...     (3, 5),
        ...     (3, 6),
        ...     (4, 5),
        ...     (4, 6),
        ...     (5, 6),
        ...     (7, 8),
        ... ]
        >>> G = nx.Graph(e)
        >>> G.add_node(9)
        >>> cliques = [c for c in chordal_graph_cliques(G)]
        >>> cliques[0]
        frozenset({1, 2, 3})

    chordal_graph_treewidth(G, *, backend=None, **backend_kwargs)
        Returns the treewidth of the chordal graph G.

        Parameters
        ----------
        G : graph
          A NetworkX graph

        Returns
        -------
        treewidth : int
            The size of the largest clique in the graph minus one.

        Raises
        ------
        NetworkXError
            The algorithm does not support DiGraph, MultiGraph and MultiDiGraph.
            The algorithm can only be applied to chordal graphs. If the input
            graph is found to be non-chordal, a :exc:`NetworkXError` is raised.

        Examples
        --------
        >>> e = [
        ...     (1, 2),
        ...     (1, 3),
        ...     (2, 3),
        ...     (2, 4),
        ...     (3, 4),
        ...     (3, 5),
        ...     (3, 6),
        ...     (4, 5),
        ...     (4, 6),
        ...     (5, 6),
        ...     (7, 8),
        ... ]
        >>> G = nx.Graph(e)
        >>> G.add_node(9)
        >>> nx.chordal_graph_treewidth(G)
        3

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Tree_decomposition#Treewidth

    complete_to_chordal_graph(G, *, backend=None, **backend_kwargs)
        Return a copy of G completed to a chordal graph

        Adds edges to a copy of G to create a chordal graph. A graph G=(V,E) is
        called chordal if for each cycle with length bigger than 3, there exist
        two non-adjacent nodes connected by an edge (called a chord).

        Parameters
        ----------
        G : NetworkX graph
            Undirected graph

        Returns
        -------
        H : NetworkX graph
            The chordal enhancement of G
        alpha : Dictionary
                The elimination ordering of nodes of G

        Notes
        -----
        There are different approaches to calculate the chordal
        enhancement of a graph. The algorithm used here is called
        MCS-M and gives at least minimal (local) triangulation of graph. Note
        that this triangulation is not necessarily a global minimum.

        https://en.wikipedia.org/wiki/Chordal_graph

        References
        ----------
        .. [1] Berry, Anne & Blair, Jean & Heggernes, Pinar & Peyton, Barry. (2004)
               Maximum Cardinality Search for Computing Minimal Triangulations of
               Graphs.  Algorithmica. 39. 287-298. 10.1007/s00453-004-1084-3.

        Examples
        --------
        >>> from networkx.algorithms.chordal import complete_to_chordal_graph
        >>> G = nx.wheel_graph(10)
        >>> H, alpha = complete_to_chordal_graph(G)

    find_induced_nodes(G, s, t, treewidth_bound=9223372036854775807, *, backend=None, **backend_kwargs)
        Returns the set of induced nodes in the path from s to t.

        Parameters
        ----------
        G : graph
          A chordal NetworkX graph
        s : node
            Source node to look for induced nodes
        t : node
            Destination node to look for induced nodes
        treewidth_bound: float
            Maximum treewidth acceptable for the graph H. The search
            for induced nodes will end as soon as the treewidth_bound is exceeded.

        Returns
        -------
        induced_nodes : Set of nodes
            The set of induced nodes in the path from s to t in G

        Raises
        ------
        NetworkXError
            The algorithm does not support DiGraph, MultiGraph and MultiDiGraph.
            If the input graph is an instance of one of these classes, a
            :exc:`NetworkXError` is raised.
            The algorithm can only be applied to chordal graphs. If the input
            graph is found to be non-chordal, a :exc:`NetworkXError` is raised.

        Examples
        --------
        >>> G = nx.Graph()
        >>> G = nx.generators.classic.path_graph(10)
        >>> induced_nodes = nx.find_induced_nodes(G, 1, 9, 2)
        >>> sorted(induced_nodes)
        [1, 2, 3, 4, 5, 6, 7, 8, 9]

        Notes
        -----
        G must be a chordal graph and (s,t) an edge that is not in G.

        If a treewidth_bound is provided, the search for induced nodes will end
        as soon as the treewidth_bound is exceeded.

        The algorithm is inspired by Algorithm 4 in [1]_.
        A formal definition of induced node can also be found on that reference.

        Self Loops are ignored

        References
        ----------
        .. [1] Learning Bounded Treewidth Bayesian Networks.
           Gal Elidan, Stephen Gould; JMLR, 9(Dec):2699--2731, 2008.
           http://jmlr.csail.mit.edu/papers/volume9/elidan08a/elidan08a.pdf

    is_chordal(G, *, backend=None, **backend_kwargs)
        Checks whether G is a chordal graph.

        A graph is chordal if every cycle of length at least 4 has a chord
        (an edge joining two nodes not adjacent in the cycle).

        Parameters
        ----------
        G : graph
          A NetworkX graph.

        Returns
        -------
        chordal : bool
          True if G is a chordal graph and False otherwise.

        Raises
        ------
        NetworkXNotImplemented
            The algorithm does not support DiGraph, MultiGraph and MultiDiGraph.

        Examples
        --------
        >>> e = [
        ...     (1, 2),
        ...     (1, 3),
        ...     (2, 3),
        ...     (2, 4),
        ...     (3, 4),
        ...     (3, 5),
        ...     (3, 6),
        ...     (4, 5),
        ...     (4, 6),
        ...     (5, 6),
        ... ]
        >>> G = nx.Graph(e)
        >>> nx.is_chordal(G)
        True

        Notes
        -----
        The routine tries to go through every node following maximum cardinality
        search. It returns False when it finds that the separator for any node
        is not a clique.  Based on the algorithms in [1]_.

        Self loops are ignored.

        References
        ----------
        .. [1] R. E. Tarjan and M. Yannakakis, Simple linear-time algorithms
           to test chordality of graphs, test acyclicity of hypergraphs, and
           selectively reduce acyclic hypergraphs, SIAM J. Comput., 13 (1984),
           pp. 566–579.

DATA
    __all__ = ['is_chordal', 'find_induced_nodes', 'chordal_graph_cliques'...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\chordal.py

networkx.chordal_cycle_graph
Python Library Documentation: function chordal_cycle_graph in module networkx.generators.expanders

chordal_cycle_graph(p, create_using=None, *, backend=None, **backend_kwargs)
    Returns the chordal cycle graph on `p` nodes.

    The returned graph is a cycle graph on `p` nodes with chords joining each
    vertex `x` to its inverse modulo `p`. This graph is a (mildly explicit)
    3-regular expander [1]_.

    `p` *must* be a prime number.

    Parameters
    ----------
    p : a prime number

        The number of vertices in the graph. This also indicates where the
        chordal edges in the cycle will be created.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : graph
        The constructed undirected multigraph.

    Raises
    ------
    NetworkXError

        If `create_using` indicates directed or not a multigraph.

    References
    ----------

    .. [1] Theorem 4.4.2 in A. Lubotzky. "Discrete groups, expanding graphs and
           invariant measures", volume 125 of Progress in Mathematics.
           Birkhäuser Verlag, Basel, 1994.
networkx.chordal_graph_cliques
Python Library Documentation: function chordal_graph_cliques in module networkx.algorithms.chordal

chordal_graph_cliques(G, *, backend=None, **backend_kwargs)
    Returns all maximal cliques of a chordal graph.

    The algorithm breaks the graph in connected components and performs a
    maximum cardinality search in each component to get the cliques.

    Parameters
    ----------
    G : graph
      A NetworkX graph

    Yields
    ------
    frozenset of nodes
        Maximal cliques, each of which is a frozenset of
        nodes in `G`. The order of cliques is arbitrary.

    Raises
    ------
    NetworkXError
        The algorithm does not support DiGraph, MultiGraph and MultiDiGraph.
        The algorithm can only be applied to chordal graphs. If the input
        graph is found to be non-chordal, a :exc:`NetworkXError` is raised.

    Examples
    --------
    >>> e = [
    ...     (1, 2),
    ...     (1, 3),
    ...     (2, 3),
    ...     (2, 4),
    ...     (3, 4),
    ...     (3, 5),
    ...     (3, 6),
    ...     (4, 5),
    ...     (4, 6),
    ...     (5, 6),
    ...     (7, 8),
    ... ]
    >>> G = nx.Graph(e)
    >>> G.add_node(9)
    >>> cliques = [c for c in chordal_graph_cliques(G)]
    >>> cliques[0]
    frozenset({1, 2, 3})
networkx.chordal_graph_treewidth
Python Library Documentation: function chordal_graph_treewidth in module networkx.algorithms.chordal

chordal_graph_treewidth(G, *, backend=None, **backend_kwargs)
    Returns the treewidth of the chordal graph G.

    Parameters
    ----------
    G : graph
      A NetworkX graph

    Returns
    -------
    treewidth : int
        The size of the largest clique in the graph minus one.

    Raises
    ------
    NetworkXError
        The algorithm does not support DiGraph, MultiGraph and MultiDiGraph.
        The algorithm can only be applied to chordal graphs. If the input
        graph is found to be non-chordal, a :exc:`NetworkXError` is raised.

    Examples
    --------
    >>> e = [
    ...     (1, 2),
    ...     (1, 3),
    ...     (2, 3),
    ...     (2, 4),
    ...     (3, 4),
    ...     (3, 5),
    ...     (3, 6),
    ...     (4, 5),
    ...     (4, 6),
    ...     (5, 6),
    ...     (7, 8),
    ... ]
    >>> G = nx.Graph(e)
    >>> G.add_node(9)
    >>> nx.chordal_graph_treewidth(G)
    3

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Tree_decomposition#Treewidth
networkx.chordless_cycles
Python Library Documentation: function chordless_cycles in module networkx.algorithms.cycles

chordless_cycles(G, length_bound=None, *, backend=None, **backend_kwargs)
    Find simple chordless cycles of a graph.

    A `simple cycle` is a closed path where no node appears twice.  In a simple
    cycle, a `chord` is an additional edge between two nodes in the cycle.  A
    `chordless cycle` is a simple cycle without chords.  Said differently, a
    chordless cycle is a cycle C in a graph G where the number of edges in the
    induced graph G[C] is equal to the length of `C`.

    Note that some care must be taken in the case that G is not a simple graph
    nor a simple digraph.  Some authors limit the definition of chordless cycles
    to have a prescribed minimum length; we do not.

        1. We interpret self-loops to be chordless cycles, except in multigraphs
           with multiple loops in parallel.  Likewise, in a chordless cycle of
           length greater than 1, there can be no nodes with self-loops.

        2. We interpret directed two-cycles to be chordless cycles, except in
           multi-digraphs when any edge in a two-cycle has a parallel copy.

        3. We interpret parallel pairs of undirected edges as two-cycles, except
           when a third (or more) parallel edge exists between the two nodes.

        4. Generalizing the above, edges with parallel clones may not occur in
           chordless cycles.

    In a directed graph, two chordless cycles are distinct if they are not
    cyclic permutations of each other.  In an undirected graph, two chordless
    cycles are distinct if they are not cyclic permutations of each other nor of
    the other's reversal.

    Optionally, the cycles are bounded in length.

    We use an algorithm strongly inspired by that of Dias et al [1]_.  It has
    been modified in the following ways:

        1. Recursion is avoided, per Python's limitations

        2. The labeling function is not necessary, because the starting paths
            are chosen (and deleted from the host graph) to prevent multiple
            occurrences of the same path

        3. The search is optionally bounded at a specified length

        4. Support for directed graphs is provided by extending cycles along
            forward edges, and blocking nodes along forward and reverse edges

        5. Support for multigraphs is provided by omitting digons from the set
            of forward edges

    Parameters
    ----------
    G : NetworkX DiGraph
       A directed graph

    length_bound : int or None, optional (default=None)
       If length_bound is an int, generate all simple cycles of G with length at
       most length_bound.  Otherwise, generate all simple cycles of G.

    Yields
    ------
    list of nodes
       Each cycle is represented by a list of nodes along the cycle.

    Examples
    --------
    >>> sorted(list(nx.chordless_cycles(nx.complete_graph(4))))
    [[1, 0, 2], [1, 0, 3], [2, 0, 3], [2, 1, 3]]

    Notes
    -----
    When length_bound is None, and the graph is simple, the time complexity is
    $O((n+e)(c+1))$ for $n$ nodes, $e$ edges and $c$ chordless cycles.

    Raises
    ------
    ValueError
        when length_bound < 0.

    References
    ----------
    .. [1] Efficient enumeration of chordless cycles
       E. Dias and D. Castonguay and H. Longo and W.A.R. Jradi
       https://arxiv.org/abs/1309.1051

    See Also
    --------
    simple_cycles
networkx.chromatic_polynomial
Python Library Documentation: function chromatic_polynomial in module networkx.algorithms.polynomials

chromatic_polynomial(G, *, backend=None, **backend_kwargs)
    Returns the chromatic polynomial of `G`

    This function computes the chromatic polynomial via an iterative version of
    the deletion-contraction algorithm.

    The chromatic polynomial `X_G(x)` is a fundamental graph polynomial
    invariant in one variable. Evaluating `X_G(k)` for an natural number `k`
    enumerates the proper k-colorings of `G`.

    There are several equivalent definitions; here are three:

    Def 1 (explicit formula):
    For `G` an undirected graph, `c(G)` the number of connected components of
    `G`, `E` the edge set of `G`, and `G(S)` the spanning subgraph of `G` with
    edge set `S` [1]_:

    .. math::

        X_G(x) = \sum_{S \subseteq E} (-1)^{|S|} x^{c(G(S))}


    Def 2 (interpolating polynomial):
    For `G` an undirected graph, `n(G)` the number of vertices of `G`, `k_0 = 0`,
    and `k_i` the number of distinct ways to color the vertices of `G` with `i`
    unique colors (for `i` a natural number at most `n(G)`), `X_G(x)` is the
    unique Lagrange interpolating polynomial of degree `n(G)` through the points
    `(0, k_0), (1, k_1), \dots, (n(G), k_{n(G)})` [2]_.


    Def 3 (chromatic recurrence):
    For `G` an undirected graph, `G-e` the graph obtained from `G` by deleting
    edge `e`, `G/e` the graph obtained from `G` by contracting edge `e`, `n(G)`
    the number of vertices of `G`, and `e(G)` the number of edges of `G` [3]_:

    .. math::
        X_G(x) = \begin{cases}
           x^{n(G)}, & \text{if $e(G)=0$} \\
           X_{G-e}(x) - X_{G/e}(x), & \text{otherwise, for an arbitrary edge $e$}
        \end{cases}

    This formulation is also known as the Fundamental Reduction Theorem [4]_.


    Parameters
    ----------
    G : NetworkX graph

    Returns
    -------
    instance of `sympy.core.add.Add`
        A Sympy expression representing the chromatic polynomial for `G`.

    Examples
    --------
    >>> C = nx.cycle_graph(5)
    >>> nx.chromatic_polynomial(C)
    x**5 - 5*x**4 + 10*x**3 - 10*x**2 + 4*x

    >>> G = nx.complete_graph(4)
    >>> nx.chromatic_polynomial(G)
    x**4 - 6*x**3 + 11*x**2 - 6*x

    Notes
    -----
    Interpretation of the coefficients is discussed in [5]_. Several special
    cases are listed in [2]_.

    The chromatic polynomial is a specialization of the Tutte polynomial; in
    particular, ``X_G(x) = T_G(x, 0)`` [6]_.

    The chromatic polynomial may take negative arguments, though evaluations
    may not have chromatic interpretations. For instance, ``X_G(-1)`` enumerates
    the acyclic orientations of `G` [7]_.

    References
    ----------
    .. [1] D. B. West,
       "Introduction to Graph Theory," p. 222
    .. [2] E. W. Weisstein
       "Chromatic Polynomial"
       MathWorld--A Wolfram Web Resource
       https://mathworld.wolfram.com/ChromaticPolynomial.html
    .. [3] D. B. West,
       "Introduction to Graph Theory," p. 221
    .. [4] J. Zhang, J. Goodall,
       "An Introduction to Chromatic Polynomials"
       https://math.mit.edu/~apost/courses/18.204_2018/Julie_Zhang_paper.pdf
    .. [5] R. C. Read,
       "An Introduction to Chromatic Polynomials"
       Journal of Combinatorial Theory, 1968
       https://math.berkeley.edu/~mrklug/ReadChromatic.pdf
    .. [6] W. T. Tutte,
       "Graph-polynomials"
       Advances in Applied Mathematics, 2004
       https://www.sciencedirect.com/science/article/pii/S0196885803000411
    .. [7] R. P. Stanley,
       "Acyclic orientations of graphs"
       Discrete Mathematics, 2006
       https://math.mit.edu/~rstan/pubs/pubfiles/18.pdf
networkx.chvatal_graph
Python Library Documentation: function chvatal_graph in module networkx.generators.small

chvatal_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Chvátal Graph

    The Chvátal Graph is an undirected graph with 12 nodes and 24 edges [1]_.
    It has 370 distinct (directed) Hamiltonian cycles, giving a unique generalized
    LCF notation of order 4, two of order 6 , and 43 of order 1 [2]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        The Chvátal graph with 12 nodes and 24 edges

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Chv%C3%A1tal_graph
    .. [2] https://mathworld.wolfram.com/ChvatalGraph.html
networkx.circulant_graph
Python Library Documentation: function circulant_graph in module networkx.generators.classic

circulant_graph(n, offsets, create_using=None, *, backend=None, **backend_kwargs)
    Returns the circulant graph $Ci_n(x_1, x_2, ..., x_m)$ with $n$ nodes.

    The circulant graph $Ci_n(x_1, ..., x_m)$ consists of $n$ nodes $0, ..., n-1$
    such that node $i$ is connected to nodes $(i + x) \mod n$ and $(i - x) \mod n$
    for all $x$ in $x_1, ..., x_m$. Thus $Ci_n(1)$ is a cycle graph.

    .. plot::

        >>> nx.draw(nx.circulant_graph(10, [1]))

    Parameters
    ----------
    n : integer
        The number of nodes in the graph.
    offsets : list of integers
        A list of node offsets, $x_1$ up to $x_m$, as described above.
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    NetworkX Graph of type create_using

    Examples
    --------
    Many well-known graph families are subfamilies of the circulant graphs;
    for example, to create the cycle graph on n points, we connect every
    node to nodes on either side (with offset plus or minus one). For n = 10,

    >>> G = nx.circulant_graph(10, [1])
    >>> edges = [
    ...     (0, 9),
    ...     (0, 1),
    ...     (1, 2),
    ...     (2, 3),
    ...     (3, 4),
    ...     (4, 5),
    ...     (5, 6),
    ...     (6, 7),
    ...     (7, 8),
    ...     (8, 9),
    ... ]
    >>> sorted(edges) == sorted(G.edges())
    True

    Similarly, we can create the complete graph
    on 5 points with the set of offsets [1, 2]:

    >>> G = nx.circulant_graph(5, [1, 2])
    >>> edges = [
    ...     (0, 1),
    ...     (0, 2),
    ...     (0, 3),
    ...     (0, 4),
    ...     (1, 2),
    ...     (1, 3),
    ...     (1, 4),
    ...     (2, 3),
    ...     (2, 4),
    ...     (3, 4),
    ... ]
    >>> sorted(edges) == sorted(G.edges())
    True
networkx.circular_ladder_graph
Python Library Documentation: function circular_ladder_graph in module networkx.generators.classic

circular_ladder_graph(n, create_using=None, *, backend=None, **backend_kwargs)
    Returns the circular ladder graph $CL_n$ of length n.

    $CL_n$ consists of two concentric n-cycles in which
    each of the n pairs of concentric nodes are joined by an edge.

    Node labels are the integers 0 to n-1

    .. plot::

        >>> nx.draw(nx.circular_ladder_graph(5))
networkx.circular_layout
Python Library Documentation: function circular_layout in module networkx.drawing.layout

circular_layout(G, scale=1, center=None, dim=2)
    Position nodes on a circle.

    Parameters
    ----------
    G : NetworkX graph or list of nodes
        A position will be assigned to every node in G.

    scale : number (default: 1)
        Scale factor for positions.

    center : array-like or None
        Coordinate pair around which to center the layout.

    dim : int
        Dimension of layout.
        If dim>2, the remaining dimensions are set to zero
        in the returned positions.
        If dim<2, a ValueError is raised.

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node

    Raises
    ------
    ValueError
        If dim < 2

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> pos = nx.circular_layout(G)

    Notes
    -----
    This algorithm currently only works in two dimensions and does not
    try to minimize edge crossings.
networkx.classes
Python Library Documentation: package networkx.classes in networkx

NAME
    networkx.classes

PACKAGE CONTENTS
    coreviews
    digraph
    filters
    function
    graph
    graphviews
    multidigraph
    multigraph
    reportviews
    tests (package)

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\classes\__init__.py

networkx.classic
Python Library Documentation: module networkx.generators.classic in networkx.generators

NAME
    networkx.generators.classic - Generators for some classic graphs.

DESCRIPTION
    The typical graph builder function is called as follows:

    >>> G = nx.complete_graph(100)

    returning the complete graph on n nodes labeled 0, .., 99
    as a simple graph. Except for `empty_graph`, all the functions
    in this module return a Graph class (i.e. a simple, undirected graph).

FUNCTIONS
    balanced_tree(r, h, create_using=None, *, backend=None, **backend_kwargs)
        Returns the perfectly balanced `r`-ary tree of height `h`.

        .. plot::

            >>> nx.draw(nx.balanced_tree(2, 3))

        Parameters
        ----------
        r : int
            Branching factor of the tree; each node will have `r`
            children.

        h : int
            Height of the tree.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : NetworkX graph
            A balanced `r`-ary tree of height `h`.

        Notes
        -----
        This is the rooted tree where all leaves are at distance `h` from
        the root. The root has degree `r` and all other internal nodes
        have degree `r + 1`.

        Node labels are integers, starting from zero.

        A balanced tree is also known as a *complete r-ary tree*.

    barbell_graph(m1, m2, create_using=None, *, backend=None, **backend_kwargs)
        Returns the Barbell Graph: two complete graphs connected by a path.

        .. plot::

            >>> nx.draw(nx.barbell_graph(4, 2))

        Parameters
        ----------
        m1 : int
            Size of the left and right barbells, must be greater than 2.

        m2 : int
            Length of the path connecting the barbells.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.
           Only undirected Graphs are supported.

        Returns
        -------
        G : NetworkX graph
            A barbell graph.

        Notes
        -----


        Two identical complete graphs $K_{m1}$ form the left and right bells,
        and are connected by a path $P_{m2}$.

        The `2*m1+m2`  nodes are numbered
            `0, ..., m1-1` for the left barbell,
            `m1, ..., m1+m2-1` for the path,
            and `m1+m2, ..., 2*m1+m2-1` for the right barbell.

        The 3 subgraphs are joined via the edges `(m1-1, m1)` and
        `(m1+m2-1, m1+m2)`. If `m2=0`, this is merely two complete
        graphs joined together.

        This graph is an extremal example in David Aldous
        and Jim Fill's e-text on Random Walks on Graphs.

    binomial_tree(n, create_using=None, *, backend=None, **backend_kwargs)
        Returns the Binomial Tree of order n.

        The binomial tree of order 0 consists of a single node. A binomial tree of order k
        is defined recursively by linking two binomial trees of order k-1: the root of one is
        the leftmost child of the root of the other.

        .. plot::

            >>> nx.draw(nx.binomial_tree(3))

        Parameters
        ----------
        n : int
            Order of the binomial tree.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : NetworkX graph
            A binomial tree of $2^n$ nodes and $2^n - 1$ edges.

    circulant_graph(n, offsets, create_using=None, *, backend=None, **backend_kwargs)
        Returns the circulant graph $Ci_n(x_1, x_2, ..., x_m)$ with $n$ nodes.

        The circulant graph $Ci_n(x_1, ..., x_m)$ consists of $n$ nodes $0, ..., n-1$
        such that node $i$ is connected to nodes $(i + x) \mod n$ and $(i - x) \mod n$
        for all $x$ in $x_1, ..., x_m$. Thus $Ci_n(1)$ is a cycle graph.

        .. plot::

            >>> nx.draw(nx.circulant_graph(10, [1]))

        Parameters
        ----------
        n : integer
            The number of nodes in the graph.
        offsets : list of integers
            A list of node offsets, $x_1$ up to $x_m$, as described above.
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        NetworkX Graph of type create_using

        Examples
        --------
        Many well-known graph families are subfamilies of the circulant graphs;
        for example, to create the cycle graph on n points, we connect every
        node to nodes on either side (with offset plus or minus one). For n = 10,

        >>> G = nx.circulant_graph(10, [1])
        >>> edges = [
        ...     (0, 9),
        ...     (0, 1),
        ...     (1, 2),
        ...     (2, 3),
        ...     (3, 4),
        ...     (4, 5),
        ...     (5, 6),
        ...     (6, 7),
        ...     (7, 8),
        ...     (8, 9),
        ... ]
        >>> sorted(edges) == sorted(G.edges())
        True

        Similarly, we can create the complete graph
        on 5 points with the set of offsets [1, 2]:

        >>> G = nx.circulant_graph(5, [1, 2])
        >>> edges = [
        ...     (0, 1),
        ...     (0, 2),
        ...     (0, 3),
        ...     (0, 4),
        ...     (1, 2),
        ...     (1, 3),
        ...     (1, 4),
        ...     (2, 3),
        ...     (2, 4),
        ...     (3, 4),
        ... ]
        >>> sorted(edges) == sorted(G.edges())
        True

    circular_ladder_graph(n, create_using=None, *, backend=None, **backend_kwargs)
        Returns the circular ladder graph $CL_n$ of length n.

        $CL_n$ consists of two concentric n-cycles in which
        each of the n pairs of concentric nodes are joined by an edge.

        Node labels are the integers 0 to n-1

        .. plot::

            >>> nx.draw(nx.circular_ladder_graph(5))

    complete_graph(n, create_using=None, *, backend=None, **backend_kwargs)
        Return the complete graph `K_n` with n nodes.

        A complete graph on `n` nodes means that all pairs
        of distinct nodes have an edge connecting them.

        .. plot::

            >>> nx.draw(nx.complete_graph(5))

        Parameters
        ----------
        n : int or iterable container of nodes
            If n is an integer, nodes are from range(n).
            If n is a container of nodes, those nodes appear in the graph.
            Warning: n is not checked for duplicates and if present the
            resulting graph may not be as desired. Make sure you have no duplicates.
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Examples
        --------
        >>> G = nx.complete_graph(9)
        >>> len(G)
        9
        >>> G.size()
        36
        >>> G = nx.complete_graph(range(11, 14))
        >>> list(G.nodes())
        [11, 12, 13]
        >>> G = nx.complete_graph(4, nx.DiGraph())
        >>> G.is_directed()
        True

    complete_multipartite_graph(*subset_sizes, backend=None, **backend_kwargs)
        Returns the complete multipartite graph with the specified subset sizes.

        .. plot::

            >>> nx.draw(nx.complete_multipartite_graph(1, 2, 3))

        Parameters
        ----------
        subset_sizes : tuple of integers or tuple of node iterables
           The arguments can either all be integer number of nodes or they
           can all be iterables of nodes. If integers, they represent the
           number of nodes in each subset of the multipartite graph.
           If iterables, each is used to create the nodes for that subset.
           The length of subset_sizes is the number of subsets.

        Returns
        -------
        G : NetworkX Graph
           Returns the complete multipartite graph with the specified subsets.

           For each node, the node attribute 'subset' is an integer
           indicating which subset contains the node.

        Examples
        --------
        Creating a complete tripartite graph, with subsets of one, two, and three
        nodes, respectively.

            >>> G = nx.complete_multipartite_graph(1, 2, 3)
            >>> [G.nodes[u]["subset"] for u in G]
            [0, 1, 1, 2, 2, 2]
            >>> list(G.edges(0))
            [(0, 1), (0, 2), (0, 3), (0, 4), (0, 5)]
            >>> list(G.edges(2))
            [(2, 0), (2, 3), (2, 4), (2, 5)]
            >>> list(G.edges(4))
            [(4, 0), (4, 1), (4, 2)]

            >>> G = nx.complete_multipartite_graph("a", "bc", "def")
            >>> [G.nodes[u]["subset"] for u in sorted(G)]
            [0, 1, 1, 2, 2, 2]

        Notes
        -----
        This function generalizes several other graph builder functions.

        - If no subset sizes are given, this returns the null graph.
        - If a single subset size `n` is given, this returns the empty graph on
          `n` nodes.
        - If two subset sizes `m` and `n` are given, this returns the complete
          bipartite graph on `m + n` nodes.
        - If subset sizes `1` and `n` are given, this returns the star graph on
          `n + 1` nodes.

        See also
        --------
        complete_bipartite_graph

    cycle_graph(n, create_using=None, *, backend=None, **backend_kwargs)
        Returns the cycle graph $C_n$ of cyclically connected nodes.

        $C_n$ is a path with its two end-nodes connected.

        .. plot::

            >>> nx.draw(nx.cycle_graph(5))

        Parameters
        ----------
        n : int or iterable container of nodes
            If n is an integer, nodes are from `range(n)`.
            If n is a container of nodes, those nodes appear in the graph.
            Warning: n is not checked for duplicates and if present the
            resulting graph may not be as desired. Make sure you have no duplicates.
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Notes
        -----
        If create_using is directed, the direction is in increasing order.

    dorogovtsev_goltsev_mendes_graph(n, create_using=None, *, backend=None, **backend_kwargs)
        Returns the hierarchically constructed Dorogovtsev--Goltsev--Mendes graph.

        The Dorogovtsev--Goltsev--Mendes [1]_ procedure deterministically produces a
        scale-free graph with ``3/2 * (3**(n-1) + 1)`` nodes
        and ``3**n`` edges for a given `n`.

        Note that `n` denotes the number of times the state transition is applied,
        starting from the base graph with ``n = 0`` (no transitions), as in [2]_.
        This is different from the parameter ``t = n - 1`` in [1]_.

        .. plot::

            >>> nx.draw(nx.dorogovtsev_goltsev_mendes_graph(3))

        Parameters
        ----------
        n : integer
            The generation number.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
            Graph type to create. Directed graphs and multigraphs are not supported.

        Returns
        -------
        G : NetworkX `Graph`

        Raises
        ------
        NetworkXError
            If `n` is less than zero.

            If `create_using` is a directed graph or multigraph.

        Examples
        --------
        >>> G = nx.dorogovtsev_goltsev_mendes_graph(3)
        >>> G.number_of_nodes()
        15
        >>> G.number_of_edges()
        27
        >>> nx.is_planar(G)
        True

        References
        ----------
        .. [1] S. N. Dorogovtsev, A. V. Goltsev and J. F. F. Mendes,
            "Pseudofractal scale-free web", Physical Review E 65, 066122, 2002.
            https://arxiv.org/pdf/cond-mat/0112143.pdf
        .. [2] Weisstein, Eric W. "Dorogovtsev--Goltsev--Mendes Graph".
            From MathWorld--A Wolfram Web Resource.
            https://mathworld.wolfram.com/Dorogovtsev-Goltsev-MendesGraph.html

    empty_graph(n=0, create_using=None, default=<class 'networkx.classes.graph.Graph'>, *, backend=None, **backend_kwargs)
        Returns the empty graph with n nodes and zero edges.

        .. plot::

            >>> nx.draw(nx.empty_graph(5))

        Parameters
        ----------
        n : int or iterable container of nodes (default = 0)
            If n is an integer, nodes are from `range(n)`.
            If n is a container of nodes, those nodes appear in the graph.
        create_using : Graph Instance, Constructor or None
            Indicator of type of graph to return.
            If a Graph-type instance, then clear and use it.
            If None, use the `default` constructor.
            If a constructor, call it to create an empty graph.
        default : Graph constructor (optional, default = nx.Graph)
            The constructor to use if create_using is None.
            If None, then nx.Graph is used.
            This is used when passing an unknown `create_using` value
            through your home-grown function to `empty_graph` and
            you want a default constructor other than nx.Graph.

        Examples
        --------
        >>> G = nx.empty_graph(10)
        >>> G.number_of_nodes()
        10
        >>> G.number_of_edges()
        0
        >>> G = nx.empty_graph("ABC")
        >>> G.number_of_nodes()
        3
        >>> sorted(G)
        ['A', 'B', 'C']

        Notes
        -----
        The variable create_using should be a Graph Constructor or a
        "graph"-like object. Constructors, e.g. `nx.Graph` or `nx.MultiGraph`
        will be used to create the returned graph. "graph"-like objects
        will be cleared (nodes and edges will be removed) and refitted as
        an empty "graph" with nodes specified in n. This capability
        is useful for specifying the class-nature of the resulting empty
        "graph" (i.e. Graph, DiGraph, MyWeirdGraphClass, etc.).

        The variable create_using has three main uses:
        Firstly, the variable create_using can be used to create an
        empty digraph, multigraph, etc.  For example,

        >>> n = 10
        >>> G = nx.empty_graph(n, create_using=nx.DiGraph)

        will create an empty digraph on n nodes.

        Secondly, one can pass an existing graph (digraph, multigraph,
        etc.) via create_using. For example, if G is an existing graph
        (resp. digraph, multigraph, etc.), then empty_graph(n, create_using=G)
        will empty G (i.e. delete all nodes and edges using G.clear())
        and then add n nodes and zero edges, and return the modified graph.

        Thirdly, when constructing your home-grown graph creation function
        you can use empty_graph to construct the graph by passing a user
        defined create_using to empty_graph. In this case, if you want the
        default constructor to be other than nx.Graph, specify `default`.

        >>> def mygraph(n, create_using=None):
        ...     G = nx.empty_graph(n, create_using, nx.MultiGraph)
        ...     G.add_edges_from([(0, 1), (0, 1)])
        ...     return G
        >>> G = mygraph(3)
        >>> G.is_multigraph()
        True
        >>> G = mygraph(3, nx.Graph)
        >>> G.is_multigraph()
        False

        See also create_empty_copy(G).

    full_rary_tree(r, n, create_using=None, *, backend=None, **backend_kwargs)
        Creates a full r-ary tree of `n` nodes.

        Sometimes called a k-ary, n-ary, or m-ary tree.
        "... all non-leaf nodes have exactly r children and all levels
        are full except for some rightmost position of the bottom level
        (if a leaf at the bottom level is missing, then so are all of the
        leaves to its right." [1]_

        .. plot::

            >>> nx.draw(nx.full_rary_tree(2, 10))

        Parameters
        ----------
        r : int
            branching factor of the tree
        n : int
            Number of nodes in the tree
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            An r-ary tree with n nodes

        References
        ----------
        .. [1] An introduction to data structures and algorithms,
               James Andrew Storer,  Birkhauser Boston 2001, (page 225).

    kneser_graph(n, k, *, backend=None, **backend_kwargs)
        Returns the Kneser Graph with parameters `n` and `k`.

        The Kneser Graph has nodes that are k-tuples (subsets) of the integers
        between 0 and ``n-1``. Nodes are adjacent if their corresponding sets are disjoint.

        Parameters
        ----------
        n: int
            Number of integers from which to make node subsets.
            Subsets are drawn from ``set(range(n))``.
        k: int
            Size of the subsets.

        Returns
        -------
        G : NetworkX Graph

        Examples
        --------
        >>> G = nx.kneser_graph(5, 2)
        >>> G.number_of_nodes()
        10
        >>> G.number_of_edges()
        15
        >>> nx.is_isomorphic(G, nx.petersen_graph())
        True

    ladder_graph(n, create_using=None, *, backend=None, **backend_kwargs)
        Returns the Ladder graph of length n.

        This is two paths of n nodes, with
        each pair connected by a single edge.

        Node labels are the integers 0 to 2*n - 1.

        .. plot::

            >>> nx.draw(nx.ladder_graph(5))

    lollipop_graph(m, n, create_using=None, *, backend=None, **backend_kwargs)
        Returns the Lollipop Graph; ``K_m`` connected to ``P_n``.

        This is the Barbell Graph without the right barbell.

        .. plot::

            >>> nx.draw(nx.lollipop_graph(3, 4))

        Parameters
        ----------
        m, n : int or iterable container of nodes
            If an integer, nodes are from ``range(m)`` and ``range(m, m+n)``.
            If a container of nodes, those nodes appear in the graph.
            Warning: `m` and `n` are not checked for duplicates and if present the
            resulting graph may not be as desired. Make sure you have no duplicates.

            The nodes for `m` appear in the complete graph $K_m$ and the nodes
            for `n` appear in the path $P_n$
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        Networkx graph
           A complete graph with `m` nodes connected to a path of length `n`.

        Notes
        -----
        The 2 subgraphs are joined via an edge ``(m-1, m)``.
        If ``n=0``, this is merely a complete graph.

        (This graph is an extremal example in David Aldous and Jim
        Fill's etext on Random Walks on Graphs.)

    null_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Null graph with no nodes or edges.

        See empty_graph for the use of create_using.

    path_graph(n, create_using=None, *, backend=None, **backend_kwargs)
        Returns the Path graph `P_n` of linearly connected nodes.

        .. plot::

            >>> nx.draw(nx.path_graph(5))

        Parameters
        ----------
        n : int or iterable
            If an integer, nodes are 0 to n - 1.
            If an iterable of nodes, in the order they appear in the path.
            Warning: n is not checked for duplicates and if present the
            resulting graph may not be as desired. Make sure you have no duplicates.
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

    star_graph(n, create_using=None, *, backend=None, **backend_kwargs)
        Return the star graph

        The star graph consists of one center node connected to n outer nodes.

        .. plot::

            >>> nx.draw(nx.star_graph(6))

        Parameters
        ----------
        n : int or iterable
            If an integer, node labels are 0 to n with center 0.
            If an iterable of nodes, the center is the first.
            Warning: n is not checked for duplicates and if present the
            resulting graph may not be as desired. Make sure you have no duplicates.
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Notes
        -----
        The graph has n+1 nodes for integer n.
        So star_graph(3) is the same as star_graph(range(4)).

    tadpole_graph(m, n, create_using=None, *, backend=None, **backend_kwargs)
        Returns the (m,n)-tadpole graph; ``C_m`` connected to ``P_n``.

        This graph on m+n nodes connects a cycle of size `m` to a path of length `n`.
        It looks like a tadpole. It is also called a kite graph or a dragon graph.

        .. plot::

            >>> nx.draw(nx.tadpole_graph(3, 5))

        Parameters
        ----------
        m, n : int or iterable container of nodes
            If an integer, nodes are from ``range(m)`` and ``range(m,m+n)``.
            If a container of nodes, those nodes appear in the graph.
            Warning: `m` and `n` are not checked for duplicates and if present the
            resulting graph may not be as desired.

            The nodes for `m` appear in the cycle graph $C_m$ and the nodes
            for `n` appear in the path $P_n$.
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        Networkx graph
           A cycle of size `m` connected to a path of length `n`.

        Raises
        ------
        NetworkXError
            If ``m < 2``. The tadpole graph is undefined for ``m<2``.

        Notes
        -----
        The 2 subgraphs are joined via an edge ``(m-1, m)``.
        If ``n=0``, this is a cycle graph.
        `m` and/or `n` can be a container of nodes instead of an integer.

    trivial_graph(create_using=None, *, backend=None, **backend_kwargs)
        Return the Trivial graph with one node (with label 0) and no edges.

        .. plot::

            >>> nx.draw(nx.trivial_graph(), with_labels=True)

    turan_graph(n, r, *, backend=None, **backend_kwargs)
        Return the Turan Graph

        The Turan Graph is a complete multipartite graph on $n$ nodes
        with $r$ disjoint subsets. That is, edges connect each node to
        every node not in its subset.

        Given $n$ and $r$, we create a complete multipartite graph with
        $r-(n \mod r)$ partitions of size $n/r$, rounded down, and
        $n \mod r$ partitions of size $n/r+1$, rounded down.

        .. plot::

            >>> nx.draw(nx.turan_graph(6, 2))

        Parameters
        ----------
        n : int
            The number of nodes.
        r : int
            The number of partitions.
            Must be less than or equal to n.

        Notes
        -----
        Must satisfy $1 <= r <= n$.
        The graph has $(r-1)(n^2)/(2r)$ edges, rounded down.

    wheel_graph(n, create_using=None, *, backend=None, **backend_kwargs)
        Return the wheel graph

        The wheel graph consists of a hub node connected to a cycle of (n-1) nodes.

        .. plot::

            >>> nx.draw(nx.wheel_graph(5))

        Parameters
        ----------
        n : int or iterable
            If an integer, node labels are 0 to n with center 0.
            If an iterable of nodes, the center is the first.
            Warning: n is not checked for duplicates and if present the
            resulting graph may not be as desired. Make sure you have no duplicates.
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Node labels are the integers 0 to n - 1.

DATA
    __all__ = ['balanced_tree', 'barbell_graph', 'binomial_tree', 'complet...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\classic.py

networkx.clique
Python Library Documentation: module networkx.algorithms.clique in networkx.algorithms

NAME
    networkx.algorithms.clique - Functions for finding and manipulating cliques.

DESCRIPTION
    Finding the largest clique in a graph is NP-complete problem, so most of
    these algorithms have an exponential running time; for more information,
    see the Wikipedia article on the clique problem [1]_.

    .. [1] clique problem:: https://en.wikipedia.org/wiki/Clique_problem

FUNCTIONS
    enumerate_all_cliques(G, *, backend=None, **backend_kwargs)
        Returns all cliques in an undirected graph.

        This function returns an iterator over cliques, each of which is a
        list of nodes. The iteration is ordered by cardinality of the
        cliques: first all cliques of size one, then all cliques of size
        two, etc.

        Parameters
        ----------
        G : NetworkX graph
            An undirected graph.

        Returns
        -------
        iterator
            An iterator over cliques, each of which is a list of nodes in
            `G`. The cliques are ordered according to size.

        Notes
        -----
        To obtain a list of all cliques, use
        `list(enumerate_all_cliques(G))`. However, be aware that in the
        worst-case, the length of this list can be exponential in the number
        of nodes in the graph (for example, when the graph is the complete
        graph). This function avoids storing all cliques in memory by only
        keeping current candidate node lists in memory during its search.

        The implementation is adapted from the algorithm by Zhang, et
        al. (2005) [1]_ to output all cliques discovered.

        This algorithm ignores self-loops and parallel edges, since cliques
        are not conventionally defined with such edges.

        References
        ----------
        .. [1] Yun Zhang, Abu-Khzam, F.N., Baldwin, N.E., Chesler, E.J.,
               Langston, M.A., Samatova, N.F.,
               "Genome-Scale Computational Approaches to Memory-Intensive
               Applications in Systems Biology".
               *Supercomputing*, 2005. Proceedings of the ACM/IEEE SC 2005
               Conference, pp. 12, 12--18 Nov. 2005.
               <https://doi.org/10.1109/SC.2005.29>.

    find_cliques(G, nodes=None, *, backend=None, **backend_kwargs)
        Returns all maximal cliques in an undirected graph.

        For each node *n*, a *maximal clique for n* is a largest complete
        subgraph containing *n*. The largest maximal clique is sometimes
        called the *maximum clique*.

        This function returns an iterator over cliques, each of which is a
        list of nodes. It is an iterative implementation, so should not
        suffer from recursion depth issues.

        This function accepts a list of `nodes` and only the maximal cliques
        containing all of these `nodes` are returned. It can considerably speed up
        the running time if some specific cliques are desired.

        Parameters
        ----------
        G : NetworkX graph
            An undirected graph.

        nodes : list, optional (default=None)
            If provided, only yield *maximal cliques* containing all nodes in `nodes`.
            If `nodes` isn't a clique itself, a ValueError is raised.

        Returns
        -------
        iterator
            An iterator over maximal cliques, each of which is a list of
            nodes in `G`. If `nodes` is provided, only the maximal cliques
            containing all the nodes in `nodes` are returned. The order of
            cliques is arbitrary.

        Raises
        ------
        ValueError
            If `nodes` is not a clique.

        Examples
        --------
        >>> from pprint import pprint  # For nice dict formatting
        >>> G = nx.karate_club_graph()
        >>> sum(1 for c in nx.find_cliques(G))  # The number of maximal cliques in G
        36
        >>> max(nx.find_cliques(G), key=len)  # The largest maximal clique in G
        [0, 1, 2, 3, 13]

        The size of the largest maximal clique is known as the *clique number* of
        the graph, which can be found directly with:

        >>> max(len(c) for c in nx.find_cliques(G))
        5

        One can also compute the number of maximal cliques in `G` that contain a given
        node. The following produces a dictionary keyed by node whose
        values are the number of maximal cliques in `G` that contain the node:

        >>> pprint({n: sum(1 for c in nx.find_cliques(G) if n in c) for n in G})
        {0: 13,
         1: 6,
         2: 7,
         3: 3,
         4: 2,
         5: 3,
         6: 3,
         7: 1,
         8: 3,
         9: 2,
         10: 2,
         11: 1,
         12: 1,
         13: 2,
         14: 1,
         15: 1,
         16: 1,
         17: 1,
         18: 1,
         19: 2,
         20: 1,
         21: 1,
         22: 1,
         23: 3,
         24: 2,
         25: 2,
         26: 1,
         27: 3,
         28: 2,
         29: 2,
         30: 2,
         31: 4,
         32: 9,
         33: 14}

        Or, similarly, the maximal cliques in `G` that contain a given node.
        For example, the 4 maximal cliques that contain node 31:

        >>> [c for c in nx.find_cliques(G) if 31 in c]
        [[0, 31], [33, 32, 31], [33, 28, 31], [24, 25, 31]]

        See Also
        --------
        find_cliques_recursive
            A recursive version of the same algorithm.

        Notes
        -----
        To obtain a list of all maximal cliques, use
        `list(find_cliques(G))`. However, be aware that in the worst-case,
        the length of this list can be exponential in the number of nodes in
        the graph. This function avoids storing all cliques in memory by
        only keeping current candidate node lists in memory during its search.

        This implementation is based on the algorithm published by Bron and
        Kerbosch (1973) [1]_, as adapted by Tomita, Tanaka and Takahashi
        (2006) [2]_ and discussed in Cazals and Karande (2008) [3]_. It
        essentially unrolls the recursion used in the references to avoid
        issues of recursion stack depth (for a recursive implementation, see
        :func:`find_cliques_recursive`).

        This algorithm ignores self-loops and parallel edges, since cliques
        are not conventionally defined with such edges.

        References
        ----------
        .. [1] Bron, C. and Kerbosch, J.
           "Algorithm 457: finding all cliques of an undirected graph".
           *Communications of the ACM* 16, 9 (Sep. 1973), 575--577.
           <http://portal.acm.org/citation.cfm?doid=362342.362367>

        .. [2] Etsuji Tomita, Akira Tanaka, Haruhisa Takahashi,
           "The worst-case time complexity for generating all maximal
           cliques and computational experiments",
           *Theoretical Computer Science*, Volume 363, Issue 1,
           Computing and Combinatorics,
           10th Annual International Conference on
           Computing and Combinatorics (COCOON 2004), 25 October 2006, Pages 28--42
           <https://doi.org/10.1016/j.tcs.2006.06.015>

        .. [3] F. Cazals, C. Karande,
           "A note on the problem of reporting maximal cliques",
           *Theoretical Computer Science*,
           Volume 407, Issues 1--3, 6 November 2008, Pages 564--568,
           <https://doi.org/10.1016/j.tcs.2008.05.010>

    find_cliques_recursive(G, nodes=None, *, backend=None, **backend_kwargs)
        Returns all maximal cliques in a graph.

        For each node *v*, a *maximal clique for v* is a largest complete
        subgraph containing *v*. The largest maximal clique is sometimes
        called the *maximum clique*.

        This function returns an iterator over cliques, each of which is a
        list of nodes. It is a recursive implementation, so may suffer from
        recursion depth issues, but is included for pedagogical reasons.
        For a non-recursive implementation, see :func:`find_cliques`.

        This function accepts a list of `nodes` and only the maximal cliques
        containing all of these `nodes` are returned. It can considerably speed up
        the running time if some specific cliques are desired.

        Parameters
        ----------
        G : NetworkX graph

        nodes : list, optional (default=None)
            If provided, only yield *maximal cliques* containing all nodes in `nodes`.
            If `nodes` isn't a clique itself, a ValueError is raised.

        Returns
        -------
        iterator
            An iterator over maximal cliques, each of which is a list of
            nodes in `G`. If `nodes` is provided, only the maximal cliques
            containing all the nodes in `nodes` are yielded. The order of
            cliques is arbitrary.

        Raises
        ------
        ValueError
            If `nodes` is not a clique.

        See Also
        --------
        find_cliques
            An iterative version of the same algorithm. See docstring for examples.

        Notes
        -----
        To obtain a list of all maximal cliques, use
        `list(find_cliques_recursive(G))`. However, be aware that in the
        worst-case, the length of this list can be exponential in the number
        of nodes in the graph. This function avoids storing all cliques in memory
        by only keeping current candidate node lists in memory during its search.

        This implementation is based on the algorithm published by Bron and
        Kerbosch (1973) [1]_, as adapted by Tomita, Tanaka and Takahashi
        (2006) [2]_ and discussed in Cazals and Karande (2008) [3]_. For a
        non-recursive implementation, see :func:`find_cliques`.

        This algorithm ignores self-loops and parallel edges, since cliques
        are not conventionally defined with such edges.

        References
        ----------
        .. [1] Bron, C. and Kerbosch, J.
           "Algorithm 457: finding all cliques of an undirected graph".
           *Communications of the ACM* 16, 9 (Sep. 1973), 575--577.
           <http://portal.acm.org/citation.cfm?doid=362342.362367>

        .. [2] Etsuji Tomita, Akira Tanaka, Haruhisa Takahashi,
           "The worst-case time complexity for generating all maximal
           cliques and computational experiments",
           *Theoretical Computer Science*, Volume 363, Issue 1,
           Computing and Combinatorics,
           10th Annual International Conference on
           Computing and Combinatorics (COCOON 2004), 25 October 2006, Pages 28--42
           <https://doi.org/10.1016/j.tcs.2006.06.015>

        .. [3] F. Cazals, C. Karande,
           "A note on the problem of reporting maximal cliques",
           *Theoretical Computer Science*,
           Volume 407, Issues 1--3, 6 November 2008, Pages 564--568,
           <https://doi.org/10.1016/j.tcs.2008.05.010>

    make_clique_bipartite(G, fpos=None, create_using=None, name=None, *, backend=None, **backend_kwargs)
        Returns the bipartite clique graph corresponding to `G`.

        In the returned bipartite graph, the "bottom" nodes are the nodes of
        `G` and the "top" nodes represent the maximal cliques of `G`.
        There is an edge from node *v* to clique *C* in the returned graph
        if and only if *v* is an element of *C*.

        Parameters
        ----------
        G : NetworkX graph
            An undirected graph.

        fpos : bool
            If True or not None, the returned graph will have an
            additional attribute, `pos`, a dictionary mapping node to
            position in the Euclidean plane.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        NetworkX graph
            A bipartite graph whose "bottom" set is the nodes of the graph
            `G`, whose "top" set is the cliques of `G`, and whose edges
            join nodes of `G` to the cliques that contain them.

            The nodes of the graph `G` have the node attribute
            'bipartite' set to 1 and the nodes representing cliques
            have the node attribute 'bipartite' set to 0, as is the
            convention for bipartite graphs in NetworkX.

    make_max_clique_graph(G, create_using=None, *, backend=None, **backend_kwargs)
        Returns the maximal clique graph of the given graph.

        The nodes of the maximal clique graph of `G` are the cliques of
        `G` and an edge joins two cliques if the cliques are not disjoint.

        Parameters
        ----------
        G : NetworkX graph

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        NetworkX graph
            A graph whose nodes are the cliques of `G` and whose edges
            join two cliques if they are not disjoint.

        Notes
        -----
        This function behaves like the following code::

            import networkx as nx

            G = nx.make_clique_bipartite(G)
            cliques = [v for v in G.nodes() if G.nodes[v]["bipartite"] == 0]
            G = nx.bipartite.projected_graph(G, cliques)
            G = nx.relabel_nodes(G, {-v: v - 1 for v in G})

        It should be faster, though, since it skips all the intermediate
        steps.

    max_weight_clique(G, weight='weight', *, backend=None, **backend_kwargs)
        Find a maximum weight clique in G.

        A *clique* in a graph is a set of nodes such that every two distinct nodes
        are adjacent.  The *weight* of a clique is the sum of the weights of its
        nodes.  A *maximum weight clique* of graph G is a clique C in G such that
        no clique in G has weight greater than the weight of C.

        Parameters
        ----------
        G : NetworkX graph
            Undirected graph
        weight : string or None, optional (default='weight')
            The node attribute that holds the integer value used as a weight.
            If None, then each node has weight 1.

        Returns
        -------
        clique : list
            the nodes of a maximum weight clique
        weight : int
            the weight of a maximum weight clique

        Notes
        -----
        The implementation is recursive, and therefore it may run into recursion
        depth issues if G contains a clique whose number of nodes is close to the
        recursion depth limit.

        At each search node, the algorithm greedily constructs a weighted
        independent set cover of part of the graph in order to find a small set of
        nodes on which to branch.  The algorithm is very similar to the algorithm
        of Tavares et al. [1]_, other than the fact that the NetworkX version does
        not use bitsets.  This style of algorithm for maximum weight clique (and
        maximum weight independent set, which is the same problem but on the
        complement graph) has a decades-long history.  See Algorithm B of Warren
        and Hicks [2]_ and the references in that paper.

        References
        ----------
        .. [1] Tavares, W.A., Neto, M.B.C., Rodrigues, C.D., Michelon, P.: Um
               algoritmo de branch and bound para o problema da clique máxima
               ponderada.  Proceedings of XLVII SBPO 1 (2015).

        .. [2] Warren, Jeffrey S, Hicks, Illya V.: Combinatorial Branch-and-Bound
               for the Maximum Weight Independent Set Problem.  Technical Report,
               Texas A&M University (2016).

    node_clique_number(G, nodes=None, cliques=None, separate_nodes=False, *, backend=None, **backend_kwargs)
        Returns the size of the largest maximal clique containing each given node.

        Returns a single or list depending on input nodes.
        An optional list of cliques can be input if already computed.

        Parameters
        ----------
        G : NetworkX graph
            An undirected graph.

        cliques : list, optional (default=None)
            A list of cliques, each of which is itself a list of nodes.
            If not specified, the list of all cliques will be computed
            using :func:`find_cliques`.

        Returns
        -------
        int or dict
            If `nodes` is a single node, returns the size of the
            largest maximal clique in `G` containing that node.
            Otherwise return a dict keyed by node to the size
            of the largest maximal clique containing that node.

        See Also
        --------
        find_cliques
            find_cliques yields the maximal cliques of G.
            It accepts a `nodes` argument which restricts consideration to
            maximal cliques containing all the given `nodes`.
            The search for the cliques is optimized for `nodes`.

    number_of_cliques(G, nodes=None, cliques=None)
        Returns the number of maximal cliques for each node.

        Returns a single or list depending on input nodes.
        Optional list of cliques can be input if already computed.

DATA
    __all__ = ['find_cliques', 'find_cliques_recursive', 'make_max_clique_...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\clique.py

networkx.closeness
Python Library Documentation: module networkx.algorithms.centrality.closeness in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.closeness - Closeness centrality measures.

FUNCTIONS
    closeness_centrality(G, u=None, distance=None, wf_improved=True, *, backend=None, **backend_kwargs)
        Compute closeness centrality for nodes.

        Closeness centrality [1]_ of a node `u` is the reciprocal of the
        average shortest path distance to `u` over all `n-1` reachable nodes.

        .. math::

            C(u) = \frac{n - 1}{\sum_{v=1}^{n-1} d(v, u)},

        where `d(v, u)` is the shortest-path distance between `v` and `u`,
        and `n-1` is the number of nodes reachable from `u`. Notice that the
        closeness distance function computes the incoming distance to `u`
        for directed graphs. To use outward distance, act on `G.reverse()`.

        Notice that higher values of closeness indicate higher centrality.

        Wasserman and Faust propose an improved formula for graphs with
        more than one connected component. The result is "a ratio of the
        fraction of actors in the group who are reachable, to the average
        distance" from the reachable actors [2]_. You might think this
        scale factor is inverted but it is not. As is, nodes from small
        components receive a smaller closeness value. Letting `N` denote
        the number of nodes in the graph,

        .. math::

            C_{WF}(u) = \frac{n-1}{N-1} \frac{n - 1}{\sum_{v=1}^{n-1} d(v, u)},

        Parameters
        ----------
        G : graph
          A NetworkX graph

        u : node, optional
          Return only the value for node u

        distance : edge attribute key, optional (default=None)
          Use the specified edge attribute as the edge distance in shortest
          path calculations.  If `None` (the default) all edges have a distance of 1.
          Absent edge attributes are assigned a distance of 1. Note that no check
          is performed to ensure that edges have the provided attribute.

        wf_improved : bool, optional (default=True)
          If True, scale by the fraction of nodes reachable. This gives the
          Wasserman and Faust improved formula. For single component graphs
          it is the same as the original formula.

        Returns
        -------
        nodes : dictionary
          Dictionary of nodes with closeness centrality as the value.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
        >>> nx.closeness_centrality(G)
        {0: 1.0, 1: 1.0, 2: 0.75, 3: 0.75}

        See Also
        --------
        betweenness_centrality, load_centrality, eigenvector_centrality,
        degree_centrality, incremental_closeness_centrality

        Notes
        -----
        The closeness centrality is normalized to `(n-1)/(|G|-1)` where
        `n` is the number of nodes in the connected part of graph
        containing the node.  If the graph is not completely connected,
        this algorithm computes the closeness centrality for each
        connected part separately scaled by that parts size.

        If the 'distance' keyword is set to an edge attribute key then the
        shortest-path length will be computed using Dijkstra's algorithm with
        that edge attribute as the edge weight.

        The closeness centrality uses *inward* distance to a node, not outward.
        If you want to use outword distances apply the function to `G.reverse()`

        In NetworkX 2.2 and earlier a bug caused Dijkstra's algorithm to use the
        outward distance rather than the inward distance. If you use a 'distance'
        keyword and a DiGraph, your results will change between v2.2 and v2.3.

        References
        ----------
        .. [1] Linton C. Freeman: Centrality in networks: I.
           Conceptual clarification. Social Networks 1:215-239, 1979.
           https://doi.org/10.1016/0378-8733(78)90021-7
        .. [2] pg. 201 of Wasserman, S. and Faust, K.,
           Social Network Analysis: Methods and Applications, 1994,
           Cambridge University Press.

    incremental_closeness_centrality(G, edge, prev_cc=None, insertion=True, wf_improved=True, *, backend=None, **backend_kwargs)
        Incremental closeness centrality for nodes.

        Compute closeness centrality for nodes using level-based work filtering
        as described in Incremental Algorithms for Closeness Centrality by Sariyuce et al.

        Level-based work filtering detects unnecessary updates to the closeness
        centrality and filters them out.

        ---
        From "Incremental Algorithms for Closeness Centrality":

        Theorem 1: Let :math:`G = (V, E)` be a graph and u and v be two vertices in V
        such that there is no edge (u, v) in E. Let :math:`G' = (V, E \cup uv)`
        Then :math:`cc[s] = cc'[s]` if and only if :math:`\left|dG(s, u) - dG(s, v)\right| \leq 1`.

        Where :math:`dG(u, v)` denotes the length of the shortest path between
        two vertices u, v in a graph G, cc[s] is the closeness centrality for a
        vertex s in V, and cc'[s] is the closeness centrality for a
        vertex s in V, with the (u, v) edge added.
        ---

        We use Theorem 1 to filter out updates when adding or removing an edge.
        When adding an edge (u, v), we compute the shortest path lengths from all
        other nodes to u and to v before the node is added. When removing an edge,
        we compute the shortest path lengths after the edge is removed. Then we
        apply Theorem 1 to use previously computed closeness centrality for nodes
        where :math:`\left|dG(s, u) - dG(s, v)\right| \leq 1`. This works only for
        undirected, unweighted graphs; the distance argument is not supported.

        Closeness centrality [1]_ of a node `u` is the reciprocal of the
        sum of the shortest path distances from `u` to all `n-1` other nodes.
        Since the sum of distances depends on the number of nodes in the
        graph, closeness is normalized by the sum of minimum possible
        distances `n-1`.

        .. math::

            C(u) = \frac{n - 1}{\sum_{v=1}^{n-1} d(v, u)},

        where `d(v, u)` is the shortest-path distance between `v` and `u`,
        and `n` is the number of nodes in the graph.

        Notice that higher values of closeness indicate higher centrality.

        Parameters
        ----------
        G : graph
          A NetworkX graph

        edge : tuple
          The modified edge (u, v) in the graph.

        prev_cc : dictionary
          The previous closeness centrality for all nodes in the graph.

        insertion : bool, optional
          If True (default) the edge was inserted, otherwise it was deleted from the graph.

        wf_improved : bool, optional (default=True)
          If True, scale by the fraction of nodes reachable. This gives the
          Wasserman and Faust improved formula. For single component graphs
          it is the same as the original formula.

        Returns
        -------
        nodes : dictionary
          Dictionary of nodes with closeness centrality as the value.

        See Also
        --------
        betweenness_centrality, load_centrality, eigenvector_centrality,
        degree_centrality, closeness_centrality

        Notes
        -----
        The closeness centrality is normalized to `(n-1)/(|G|-1)` where
        `n` is the number of nodes in the connected part of graph
        containing the node.  If the graph is not completely connected,
        this algorithm computes the closeness centrality for each
        connected part separately.

        References
        ----------
        .. [1] Freeman, L.C., 1979. Centrality in networks: I.
           Conceptual clarification.  Social Networks 1, 215--239.
           https://doi.org/10.1016/0378-8733(78)90021-7
        .. [2] Sariyuce, A.E. ; Kaya, K. ; Saule, E. ; Catalyiirek, U.V. Incremental
           Algorithms for Closeness Centrality. 2013 IEEE International Conference on Big Data
           http://sariyuce.com/papers/bigdata13.pdf

DATA
    __all__ = ['closeness_centrality', 'incremental_closeness_centrality']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\closeness.py

networkx.closeness_centrality
Python Library Documentation: function closeness_centrality in module networkx.algorithms.centrality.closeness

closeness_centrality(G, u=None, distance=None, wf_improved=True, *, backend=None, **backend_kwargs)
    Compute closeness centrality for nodes.

    Closeness centrality [1]_ of a node `u` is the reciprocal of the
    average shortest path distance to `u` over all `n-1` reachable nodes.

    .. math::

        C(u) = \frac{n - 1}{\sum_{v=1}^{n-1} d(v, u)},

    where `d(v, u)` is the shortest-path distance between `v` and `u`,
    and `n-1` is the number of nodes reachable from `u`. Notice that the
    closeness distance function computes the incoming distance to `u`
    for directed graphs. To use outward distance, act on `G.reverse()`.

    Notice that higher values of closeness indicate higher centrality.

    Wasserman and Faust propose an improved formula for graphs with
    more than one connected component. The result is "a ratio of the
    fraction of actors in the group who are reachable, to the average
    distance" from the reachable actors [2]_. You might think this
    scale factor is inverted but it is not. As is, nodes from small
    components receive a smaller closeness value. Letting `N` denote
    the number of nodes in the graph,

    .. math::

        C_{WF}(u) = \frac{n-1}{N-1} \frac{n - 1}{\sum_{v=1}^{n-1} d(v, u)},

    Parameters
    ----------
    G : graph
      A NetworkX graph

    u : node, optional
      Return only the value for node u

    distance : edge attribute key, optional (default=None)
      Use the specified edge attribute as the edge distance in shortest
      path calculations.  If `None` (the default) all edges have a distance of 1.
      Absent edge attributes are assigned a distance of 1. Note that no check
      is performed to ensure that edges have the provided attribute.

    wf_improved : bool, optional (default=True)
      If True, scale by the fraction of nodes reachable. This gives the
      Wasserman and Faust improved formula. For single component graphs
      it is the same as the original formula.

    Returns
    -------
    nodes : dictionary
      Dictionary of nodes with closeness centrality as the value.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
    >>> nx.closeness_centrality(G)
    {0: 1.0, 1: 1.0, 2: 0.75, 3: 0.75}

    See Also
    --------
    betweenness_centrality, load_centrality, eigenvector_centrality,
    degree_centrality, incremental_closeness_centrality

    Notes
    -----
    The closeness centrality is normalized to `(n-1)/(|G|-1)` where
    `n` is the number of nodes in the connected part of graph
    containing the node.  If the graph is not completely connected,
    this algorithm computes the closeness centrality for each
    connected part separately scaled by that parts size.

    If the 'distance' keyword is set to an edge attribute key then the
    shortest-path length will be computed using Dijkstra's algorithm with
    that edge attribute as the edge weight.

    The closeness centrality uses *inward* distance to a node, not outward.
    If you want to use outword distances apply the function to `G.reverse()`

    In NetworkX 2.2 and earlier a bug caused Dijkstra's algorithm to use the
    outward distance rather than the inward distance. If you use a 'distance'
    keyword and a DiGraph, your results will change between v2.2 and v2.3.

    References
    ----------
    .. [1] Linton C. Freeman: Centrality in networks: I.
       Conceptual clarification. Social Networks 1:215-239, 1979.
       https://doi.org/10.1016/0378-8733(78)90021-7
    .. [2] pg. 201 of Wasserman, S. and Faust, K.,
       Social Network Analysis: Methods and Applications, 1994,
       Cambridge University Press.
networkx.closeness_vitality
Python Library Documentation: function closeness_vitality in module networkx.algorithms.vitality

closeness_vitality(G, node=None, weight=None, wiener_index=None, *, backend=None, **backend_kwargs)
    Returns the closeness vitality for nodes in the graph.

    The *closeness vitality* of a node, defined in Section 3.6.2 of [1],
    is the change in the sum of distances between all node pairs when
    excluding that node.

    Parameters
    ----------
    G : NetworkX graph
        A strongly-connected graph.

    weight : string
        The name of the edge attribute used as weight. This is passed
        directly to the :func:`~networkx.wiener_index` function.

    node : object
        If specified, only the closeness vitality for this node will be
        returned. Otherwise, a dictionary mapping each node to its
        closeness vitality will be returned.

    Other parameters
    ----------------
    wiener_index : number
        If you have already computed the Wiener index of the graph
        `G`, you can provide that value here. Otherwise, it will be
        computed for you.

    Returns
    -------
    dictionary or float
        If `node` is None, this function returns a dictionary
        with nodes as keys and closeness vitality as the
        value. Otherwise, it returns only the closeness vitality for the
        specified `node`.

        The closeness vitality of a node may be negative infinity if
        removing that node would disconnect the graph.

    Examples
    --------
    >>> G = nx.cycle_graph(3)
    >>> nx.closeness_vitality(G)
    {0: 2.0, 1: 2.0, 2: 2.0}

    See Also
    --------
    closeness_centrality

    References
    ----------
    .. [1] Ulrik Brandes, Thomas Erlebach (eds.).
           *Network Analysis: Methodological Foundations*.
           Springer, 2005.
           <http://books.google.com/books?id=TTNhSm7HYrIC>
networkx.cluster
Python Library Documentation: module networkx.algorithms.cluster in networkx.algorithms

NAME
    networkx.algorithms.cluster - Algorithms to characterize the number of triangles in a graph.

FUNCTIONS
    average_clustering(G, nodes=None, weight=None, count_zeros=True, *, backend=None, **backend_kwargs)
        Compute the average clustering coefficient for the graph G.

        The clustering coefficient for the graph is the average,

        .. math::

           C = \frac{1}{n}\sum_{v \in G} c_v,

        where :math:`n` is the number of nodes in `G`.

        Parameters
        ----------
        G : graph

        nodes : container of nodes, optional (default=all nodes in G)
           Compute average clustering for nodes in this container.

        weight : string or None, optional (default=None)
           The edge attribute that holds the numerical value used as a weight.
           If None, then each edge has weight 1.

        count_zeros : bool
           If False include only the nodes with nonzero clustering in the average.

        Returns
        -------
        avg : float
           Average clustering

        Examples
        --------
        >>> G = nx.complete_graph(5)
        >>> print(nx.average_clustering(G))
        1.0

        Notes
        -----
        This is a space saving routine; it might be faster
        to use the clustering function to get a list and then take the average.

        Self loops are ignored.

        References
        ----------
        .. [1] Generalizations of the clustering coefficient to weighted
           complex networks by J. Saramäki, M. Kivelä, J.-P. Onnela,
           K. Kaski, and J. Kertész, Physical Review E, 75 027105 (2007).
           http://jponnela.com/web_documents/a9.pdf
        .. [2] Marcus Kaiser,  Mean clustering coefficients: the role of isolated
           nodes and leafs on clustering measures for small-world networks.
           https://arxiv.org/abs/0802.2512

    clustering(G, nodes=None, weight=None, *, backend=None, **backend_kwargs)
        Compute the clustering coefficient for nodes.

        For unweighted graphs, the clustering of a node :math:`u`
        is the fraction of possible triangles through that node that exist,

        .. math::

          c_u = \frac{2 T(u)}{deg(u)(deg(u)-1)},

        where :math:`T(u)` is the number of triangles through node :math:`u` and
        :math:`deg(u)` is the degree of :math:`u`.

        For weighted graphs, there are several ways to define clustering [1]_.
        the one used here is defined
        as the geometric average of the subgraph edge weights [2]_,

        .. math::

           c_u = \frac{1}{deg(u)(deg(u)-1))}
                 \sum_{vw} (\hat{w}_{uv} \hat{w}_{uw} \hat{w}_{vw})^{1/3}.

        The edge weights :math:`\hat{w}_{uv}` are normalized by the maximum weight
        in the network :math:`\hat{w}_{uv} = w_{uv}/\max(w)`.

        The value of :math:`c_u` is assigned to 0 if :math:`deg(u) < 2`.

        Additionally, this weighted definition has been generalized to support negative edge weights [3]_.

        For directed graphs, the clustering is similarly defined as the fraction
        of all possible directed triangles or geometric average of the subgraph
        edge weights for unweighted and weighted directed graph respectively [4]_.

        .. math::

           c_u = \frac{T(u)}{2(deg^{tot}(u)(deg^{tot}(u)-1) - 2deg^{\leftrightarrow}(u))},

        where :math:`T(u)` is the number of directed triangles through node
        :math:`u`, :math:`deg^{tot}(u)` is the sum of in degree and out degree of
        :math:`u` and :math:`deg^{\leftrightarrow}(u)` is the reciprocal degree of
        :math:`u`.


        Parameters
        ----------
        G : graph

        nodes : node, iterable of nodes, or None (default=None)
            If a singleton node, return the number of triangles for that node.
            If an iterable, compute the number of triangles for each of those nodes.
            If `None` (the default) compute the number of triangles for all nodes in `G`.

        weight : string or None, optional (default=None)
           The edge attribute that holds the numerical value used as a weight.
           If None, then each edge has weight 1.

        Returns
        -------
        out : float, or dictionary
           Clustering coefficient at specified nodes

        Examples
        --------
        >>> G = nx.complete_graph(5)
        >>> print(nx.clustering(G, 0))
        1.0
        >>> print(nx.clustering(G))
        {0: 1.0, 1: 1.0, 2: 1.0, 3: 1.0, 4: 1.0}

        Notes
        -----
        Self loops are ignored.

        References
        ----------
        .. [1] Generalizations of the clustering coefficient to weighted
           complex networks by J. Saramäki, M. Kivelä, J.-P. Onnela,
           K. Kaski, and J. Kertész, Physical Review E, 75 027105 (2007).
           http://jponnela.com/web_documents/a9.pdf
        .. [2] Intensity and coherence of motifs in weighted complex
           networks by J. P. Onnela, J. Saramäki, J. Kertész, and K. Kaski,
           Physical Review E, 71(6), 065103 (2005).
        .. [3] Generalization of Clustering Coefficients to Signed Correlation Networks
           by G. Costantini and M. Perugini, PloS one, 9(2), e88669 (2014).
        .. [4] Clustering in complex directed networks by G. Fagiolo,
           Physical Review E, 76(2), 026107 (2007).

    generalized_degree(G, nodes=None, *, backend=None, **backend_kwargs)
        Compute the generalized degree for nodes.

        For each node, the generalized degree shows how many edges of given
        triangle multiplicity the node is connected to. The triangle multiplicity
        of an edge is the number of triangles an edge participates in. The
        generalized degree of node :math:`i` can be written as a vector
        :math:`\mathbf{k}_i=(k_i^{(0)}, \dotsc, k_i^{(N-2)})` where
        :math:`k_i^{(j)}` is the number of edges attached to node :math:`i` that
        participate in :math:`j` triangles.

        Parameters
        ----------
        G : graph

        nodes : container of nodes, optional (default=all nodes in G)
           Compute the generalized degree for nodes in this container.

        Returns
        -------
        out : Counter, or dictionary of Counters
           Generalized degree of specified nodes. The Counter is keyed by edge
           triangle multiplicity.

        Examples
        --------
        >>> G = nx.complete_graph(5)
        >>> print(nx.generalized_degree(G, 0))
        Counter({3: 4})
        >>> print(nx.generalized_degree(G))
        {0: Counter({3: 4}), 1: Counter({3: 4}), 2: Counter({3: 4}), 3: Counter({3: 4}), 4: Counter({3: 4})}

        To recover the number of triangles attached to a node:

        >>> k1 = nx.generalized_degree(G, 0)
        >>> sum([k * v for k, v in k1.items()]) / 2 == nx.triangles(G, 0)
        True

        Notes
        -----
        Self loops are ignored.

        In a network of N nodes, the highest triangle multiplicity an edge can have
        is N-2.

        The return value does not include a `zero` entry if no edges of a
        particular triangle multiplicity are present.

        The number of triangles node :math:`i` is attached to can be recovered from
        the generalized degree :math:`\mathbf{k}_i=(k_i^{(0)}, \dotsc,
        k_i^{(N-2)})` by :math:`(k_i^{(1)}+2k_i^{(2)}+\dotsc +(N-2)k_i^{(N-2)})/2`.

        References
        ----------
        .. [1] Networks with arbitrary edge multiplicities by V. Zlatić,
            D. Garlaschelli and G. Caldarelli, EPL (Europhysics Letters),
            Volume 97, Number 2 (2012).
            https://iopscience.iop.org/article/10.1209/0295-5075/97/28005

    square_clustering(G, nodes=None, *, backend=None, **backend_kwargs)
        Compute the squares clustering coefficient for nodes.

        For each node return the fraction of possible squares that exist at
        the node [1]_

        .. math::
           C_4(v) = \frac{ \sum_{u=1}^{k_v}
           \sum_{w=u+1}^{k_v} q_v(u,w) }{ \sum_{u=1}^{k_v}
           \sum_{w=u+1}^{k_v} [a_v(u,w) + q_v(u,w)]},

        where :math:`q_v(u,w)` are the number of common neighbors of :math:`u` and
        :math:`w` other than :math:`v` (ie squares), and :math:`a_v(u,w) = (k_u -
        (1+q_v(u,w)+\theta_{uv})) + (k_w - (1+q_v(u,w)+\theta_{uw}))`, where
        :math:`\theta_{uw} = 1` if :math:`u` and :math:`w` are connected and 0
        otherwise. [2]_

        Parameters
        ----------
        G : graph

        nodes : container of nodes, optional (default=all nodes in G)
           Compute clustering for nodes in this container.

        Returns
        -------
        c4 : dictionary
           A dictionary keyed by node with the square clustering coefficient value.

        Examples
        --------
        >>> G = nx.complete_graph(5)
        >>> print(nx.square_clustering(G, 0))
        1.0
        >>> print(nx.square_clustering(G))
        {0: 1.0, 1: 1.0, 2: 1.0, 3: 1.0, 4: 1.0}

        Notes
        -----
        While :math:`C_3(v)` (triangle clustering) gives the probability that
        two neighbors of node v are connected with each other, :math:`C_4(v)` is
        the probability that two neighbors of node v share a common
        neighbor different from v. This algorithm can be applied to both
        bipartite and unipartite networks.

        References
        ----------
        .. [1] Pedro G. Lind, Marta C. González, and Hans J. Herrmann. 2005
            Cycles and clustering in bipartite networks.
            Physical Review E (72) 056127.
        .. [2] Zhang, Peng et al. Clustering Coefficient and Community Structure of
            Bipartite Networks. Physica A: Statistical Mechanics and its Applications 387.27 (2008): 6869–6875.
            https://arxiv.org/abs/0710.0117v1

    transitivity(G, *, backend=None, **backend_kwargs)
        Compute graph transitivity, the fraction of all possible triangles
        present in G.

        Possible triangles are identified by the number of "triads"
        (two edges with a shared vertex).

        The transitivity is

        .. math::

            T = 3\frac{\#triangles}{\#triads}.

        Parameters
        ----------
        G : graph

        Returns
        -------
        out : float
           Transitivity

        Notes
        -----
        Self loops are ignored.

        Examples
        --------
        >>> G = nx.complete_graph(5)
        >>> print(nx.transitivity(G))
        1.0

    triangles(G, nodes=None, *, backend=None, **backend_kwargs)
        Compute the number of triangles.

        Finds the number of triangles that include a node as one vertex.

        Parameters
        ----------
        G : graph
           A networkx graph

        nodes : node, iterable of nodes, or None (default=None)
            If a singleton node, return the number of triangles for that node.
            If an iterable, compute the number of triangles for each of those nodes.
            If `None` (the default) compute the number of triangles for all nodes in `G`.

        Returns
        -------
        out : dict or int
           If `nodes` is a container of nodes, returns number of triangles keyed by node (dict).
           If `nodes` is a specific node, returns number of triangles for the node (int).

        Examples
        --------
        >>> G = nx.complete_graph(5)
        >>> print(nx.triangles(G, 0))
        6
        >>> print(nx.triangles(G))
        {0: 6, 1: 6, 2: 6, 3: 6, 4: 6}
        >>> print(list(nx.triangles(G, [0, 1]).values()))
        [6, 6]

        Notes
        -----
        Self loops are ignored.

DATA
    __all__ = ['triangles', 'average_clustering', 'clustering', 'transitiv...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\cluster.py

networkx.clustering
Python Library Documentation: function clustering in module networkx.algorithms.cluster

clustering(G, nodes=None, weight=None, *, backend=None, **backend_kwargs)
    Compute the clustering coefficient for nodes.

    For unweighted graphs, the clustering of a node :math:`u`
    is the fraction of possible triangles through that node that exist,

    .. math::

      c_u = \frac{2 T(u)}{deg(u)(deg(u)-1)},

    where :math:`T(u)` is the number of triangles through node :math:`u` and
    :math:`deg(u)` is the degree of :math:`u`.

    For weighted graphs, there are several ways to define clustering [1]_.
    the one used here is defined
    as the geometric average of the subgraph edge weights [2]_,

    .. math::

       c_u = \frac{1}{deg(u)(deg(u)-1))}
             \sum_{vw} (\hat{w}_{uv} \hat{w}_{uw} \hat{w}_{vw})^{1/3}.

    The edge weights :math:`\hat{w}_{uv}` are normalized by the maximum weight
    in the network :math:`\hat{w}_{uv} = w_{uv}/\max(w)`.

    The value of :math:`c_u` is assigned to 0 if :math:`deg(u) < 2`.

    Additionally, this weighted definition has been generalized to support negative edge weights [3]_.

    For directed graphs, the clustering is similarly defined as the fraction
    of all possible directed triangles or geometric average of the subgraph
    edge weights for unweighted and weighted directed graph respectively [4]_.

    .. math::

       c_u = \frac{T(u)}{2(deg^{tot}(u)(deg^{tot}(u)-1) - 2deg^{\leftrightarrow}(u))},

    where :math:`T(u)` is the number of directed triangles through node
    :math:`u`, :math:`deg^{tot}(u)` is the sum of in degree and out degree of
    :math:`u` and :math:`deg^{\leftrightarrow}(u)` is the reciprocal degree of
    :math:`u`.


    Parameters
    ----------
    G : graph

    nodes : node, iterable of nodes, or None (default=None)
        If a singleton node, return the number of triangles for that node.
        If an iterable, compute the number of triangles for each of those nodes.
        If `None` (the default) compute the number of triangles for all nodes in `G`.

    weight : string or None, optional (default=None)
       The edge attribute that holds the numerical value used as a weight.
       If None, then each edge has weight 1.

    Returns
    -------
    out : float, or dictionary
       Clustering coefficient at specified nodes

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> print(nx.clustering(G, 0))
    1.0
    >>> print(nx.clustering(G))
    {0: 1.0, 1: 1.0, 2: 1.0, 3: 1.0, 4: 1.0}

    Notes
    -----
    Self loops are ignored.

    References
    ----------
    .. [1] Generalizations of the clustering coefficient to weighted
       complex networks by J. Saramäki, M. Kivelä, J.-P. Onnela,
       K. Kaski, and J. Kertész, Physical Review E, 75 027105 (2007).
       http://jponnela.com/web_documents/a9.pdf
    .. [2] Intensity and coherence of motifs in weighted complex
       networks by J. P. Onnela, J. Saramäki, J. Kertész, and K. Kaski,
       Physical Review E, 71(6), 065103 (2005).
    .. [3] Generalization of Clustering Coefficients to Signed Correlation Networks
       by G. Costantini and M. Perugini, PloS one, 9(2), e88669 (2014).
    .. [4] Clustering in complex directed networks by G. Fagiolo,
       Physical Review E, 76(2), 026107 (2007).
networkx.cn_soundarajan_hopcroft
Python Library Documentation: function cn_soundarajan_hopcroft in module networkx.algorithms.link_prediction

cn_soundarajan_hopcroft(G, ebunch=None, community='community', *, backend=None, **backend_kwargs)
    Count the number of common neighbors of all node pairs in ebunch
        using community information.

    For two nodes $u$ and $v$, this function computes the number of
    common neighbors and bonus one for each common neighbor belonging to
    the same community as $u$ and $v$. Mathematically,

    .. math::

        |\Gamma(u) \cap \Gamma(v)| + \sum_{w \in \Gamma(u) \cap \Gamma(v)} f(w)

    where $f(w)$ equals 1 if $w$ belongs to the same community as $u$
    and $v$ or 0 otherwise and $\Gamma(u)$ denotes the set of
    neighbors of $u$.

    Parameters
    ----------
    G : graph
        A NetworkX undirected graph.

    ebunch : iterable of node pairs, optional (default = None)
        The score will be computed for each pair of nodes given in the
        iterable. The pairs must be given as 2-tuples (u, v) where u
        and v are nodes in the graph. If ebunch is None then all
        nonexistent edges in the graph will be used.
        Default value: None.

    community : string, optional (default = 'community')
        Nodes attribute name containing the community information.
        G[u][community] identifies which community u belongs to. Each
        node belongs to at most one community. Default value: 'community'.

    Returns
    -------
    piter : iterator
        An iterator of 3-tuples in the form (u, v, p) where (u, v) is a
        pair of nodes and p is their score.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a `DiGraph`, a `Multigraph` or a `MultiDiGraph`.

    NetworkXAlgorithmError
        If no community information is available for a node in `ebunch` or in `G` (if `ebunch` is `None`).

    NodeNotFound
        If `ebunch` has a node that is not in `G`.

    Examples
    --------
    >>> G = nx.path_graph(3)
    >>> G.nodes[0]["community"] = 0
    >>> G.nodes[1]["community"] = 0
    >>> G.nodes[2]["community"] = 0
    >>> preds = nx.cn_soundarajan_hopcroft(G, [(0, 2)])
    >>> for u, v, p in preds:
    ...     print(f"({u}, {v}) -> {p}")
    (0, 2) -> 2

    References
    ----------
    .. [1] Sucheta Soundarajan and John Hopcroft.
       Using community information to improve the precision of link
       prediction methods.
       In Proceedings of the 21st international conference companion on
       World Wide Web (WWW '12 Companion). ACM, New York, NY, USA, 607-608.
       http://doi.acm.org/10.1145/2187980.2188150
networkx.cographs
Python Library Documentation: module networkx.generators.cographs in networkx.generators

NAME
    networkx.generators.cographs - Generators for cographs

DESCRIPTION
    A cograph is a graph containing no path on four vertices.
    Cographs or $P_4$-free graphs can be obtained from a single vertex
    by disjoint union and complementation operations.

    References
    ----------
    .. [0] D.G. Corneil, H. Lerchs, L.Stewart Burlingham,
        "Complement reducible graphs",
        Discrete Applied Mathematics, Volume 3, Issue 3, 1981, Pages 163-174,
        ISSN 0166-218X.

FUNCTIONS
    random_cograph(n, seed=None, *, backend=None, **backend_kwargs)
        Returns a random cograph with $2 ^ n$ nodes.

        A cograph is a graph containing no path on four vertices.
        Cographs or $P_4$-free graphs can be obtained from a single vertex
        by disjoint union and complementation operations.

        This generator starts off from a single vertex and performs disjoint
        union and full join operations on itself.
        The decision on which operation will take place is random.

        Parameters
        ----------
        n : int
            The order of the cograph.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        G : A random graph containing no path on four vertices.

        See Also
        --------
        full_join
        union

        References
        ----------
        .. [1] D.G. Corneil, H. Lerchs, L.Stewart Burlingham,
           "Complement reducible graphs",
           Discrete Applied Mathematics, Volume 3, Issue 3, 1981, Pages 163-174,
           ISSN 0166-218X.

DATA
    __all__ = ['random_cograph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\cographs.py

networkx.coloring
Python Library Documentation: package networkx.algorithms.coloring in networkx.algorithms

NAME
    networkx.algorithms.coloring

PACKAGE CONTENTS
    equitable_coloring
    greedy_coloring
    tests (package)

FUNCTIONS
    equitable_color(G, num_colors, *, backend=None, **backend_kwargs)
        Provides an equitable coloring for nodes of `G`.

        Attempts to color a graph using `num_colors` colors, where no neighbors of
        a node can have same color as the node itself and the number of nodes with
        each color differ by at most 1. `num_colors` must be greater than the
        maximum degree of `G`. The algorithm is described in [1]_ and has
        complexity O(num_colors * n**2).

        Parameters
        ----------
        G : networkX graph
           The nodes of this graph will be colored.

        num_colors : number of colors to use
           This number must be at least one more than the maximum degree of nodes
           in the graph.

        Returns
        -------
        A dictionary with keys representing nodes and values representing
        corresponding coloring.

        Examples
        --------
        >>> G = nx.cycle_graph(4)
        >>> nx.coloring.equitable_color(G, num_colors=3)  # doctest: +SKIP
        {0: 2, 1: 1, 2: 2, 3: 0}

        Raises
        ------
        NetworkXAlgorithmError
            If `num_colors` is not at least the maximum degree of the graph `G`

        References
        ----------
        .. [1] Kierstead, H. A., Kostochka, A. V., Mydlarz, M., & Szemerédi, E.
            (2010). A fast algorithm for equitable coloring. Combinatorica, 30(2),
            217-224.

    greedy_color(G, strategy='largest_first', interchange=False, *, backend=None, **backend_kwargs)
        Color a graph using various strategies of greedy graph coloring.

        Attempts to color a graph using as few colors as possible, where no
        neighbors of a node can have same color as the node itself. The
        given strategy determines the order in which nodes are colored.

        The strategies are described in [1]_, and smallest-last is based on
        [2]_.

        Parameters
        ----------
        G : NetworkX graph

        strategy : string or function(G, colors)
           A function (or a string representing a function) that provides
           the coloring strategy, by returning nodes in the ordering they
           should be colored. ``G`` is the graph, and ``colors`` is a
           dictionary of the currently assigned colors, keyed by nodes. The
           function must return an iterable over all the nodes in ``G``.

           If the strategy function is an iterator generator (that is, a
           function with ``yield`` statements), keep in mind that the
           ``colors`` dictionary will be updated after each ``yield``, since
           this function chooses colors greedily.

           If ``strategy`` is a string, it must be one of the following,
           each of which represents one of the built-in strategy functions.

           * ``'largest_first'``
           * ``'random_sequential'``
           * ``'smallest_last'``
           * ``'independent_set'``
           * ``'connected_sequential_bfs'``
           * ``'connected_sequential_dfs'``
           * ``'connected_sequential'`` (alias for the previous strategy)
           * ``'saturation_largest_first'``
           * ``'DSATUR'`` (alias for the previous strategy)

        interchange: bool
           Will use the color interchange algorithm described by [3]_ if set
           to ``True``.

           Note that ``saturation_largest_first`` and ``independent_set``
           do not work with interchange. Furthermore, if you use
           interchange with your own strategy function, you cannot rely
           on the values in the ``colors`` argument.

        Returns
        -------
        A dictionary with keys representing nodes and values representing
        corresponding coloring.

        Examples
        --------
        >>> G = nx.cycle_graph(4)
        >>> d = nx.coloring.greedy_color(G, strategy="largest_first")
        >>> d in [{0: 0, 1: 1, 2: 0, 3: 1}, {0: 1, 1: 0, 2: 1, 3: 0}]
        True

        Raises
        ------
        NetworkXPointlessConcept
            If ``strategy`` is ``saturation_largest_first`` or
            ``independent_set`` and ``interchange`` is ``True``.

        References
        ----------
        .. [1] Adrian Kosowski, and Krzysztof Manuszewski,
           Classical Coloring of Graphs, Graph Colorings, 2-19, 2004.
           ISBN 0-8218-3458-4.
        .. [2] David W. Matula, and Leland L. Beck, "Smallest-last
           ordering and clustering and graph coloring algorithms." *J. ACM* 30,
           3 (July 1983), 417–427. <https://doi.org/10.1145/2402.322385>
        .. [3] Maciej M. Sysło, Narsingh Deo, Janusz S. Kowalik,
           Discrete Optimization Algorithms with Pascal Programs, 415-424, 1983.
           ISBN 0-486-45353-7.

DATA
    __all__ = ['greedy_color', 'equitable_color']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\coloring\__init__.py

networkx.combinatorial_embedding_to_pos
Python Library Documentation: function combinatorial_embedding_to_pos in module networkx.algorithms.planar_drawing

combinatorial_embedding_to_pos(embedding, fully_triangulate=False)
    Assigns every node a (x, y) position based on the given embedding

    The algorithm iteratively inserts nodes of the input graph in a certain
    order and rearranges previously inserted nodes so that the planar drawing
    stays valid. This is done efficiently by only maintaining relative
    positions during the node placements and calculating the absolute positions
    at the end. For more information see [1]_.

    Parameters
    ----------
    embedding : nx.PlanarEmbedding
        This defines the order of the edges

    fully_triangulate : bool
        If set to True the algorithm adds edges to a copy of the input
        embedding and makes it chordal.

    Returns
    -------
    pos : dict
        Maps each node to a tuple that defines the (x, y) position

    References
    ----------
    .. [1] M. Chrobak and T.H. Payne:
        A Linear-time Algorithm for Drawing a Planar Graph on a Grid 1989
        http://citeseerx.ist.psu.edu/viewdoc/summary?doi=10.1.1.51.6677
networkx.common_neighbor_centrality
Python Library Documentation: function common_neighbor_centrality in module networkx.algorithms.link_prediction

common_neighbor_centrality(G, ebunch=None, alpha=0.8, *, backend=None, **backend_kwargs)
    Return the CCPA score for each pair of nodes.

    Compute the Common Neighbor and Centrality based Parameterized Algorithm(CCPA)
    score of all node pairs in ebunch.

    CCPA score of `u` and `v` is defined as

    .. math::

        \alpha \cdot (|\Gamma (u){\cap }^{}\Gamma (v)|)+(1-\alpha )\cdot \frac{N}{{d}_{uv}}

    where $\Gamma(u)$ denotes the set of neighbors of $u$, $\Gamma(v)$ denotes the
    set of neighbors of $v$, $\alpha$ is  parameter varies between [0,1], $N$ denotes
    total number of nodes in the Graph and ${d}_{uv}$ denotes shortest distance
    between $u$ and $v$.

    This algorithm is based on two vital properties of nodes, namely the number
    of common neighbors and their centrality. Common neighbor refers to the common
    nodes between two nodes. Centrality refers to the prestige that a node enjoys
    in a network.

    .. seealso::

        :func:`common_neighbors`

    Parameters
    ----------
    G : graph
        NetworkX undirected graph.

    ebunch : iterable of node pairs, optional (default = None)
        Preferential attachment score will be computed for each pair of
        nodes given in the iterable. The pairs must be given as
        2-tuples (u, v) where u and v are nodes in the graph. If ebunch
        is None then all nonexistent edges in the graph will be used.
        Default value: None.

    alpha : Parameter defined for participation of Common Neighbor
            and Centrality Algorithm share. Values for alpha should
            normally be between 0 and 1. Default value set to 0.8
            because author found better performance at 0.8 for all the
            dataset.
            Default value: 0.8


    Returns
    -------
    piter : iterator
        An iterator of 3-tuples in the form (u, v, p) where (u, v) is a
        pair of nodes and p is their Common Neighbor and Centrality based
        Parameterized Algorithm(CCPA) score.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a `DiGraph`, a `Multigraph` or a `MultiDiGraph`.

    NetworkXAlgorithmError
        If self loops exist in `ebunch` or in `G` (if `ebunch` is `None`).

    NodeNotFound
        If `ebunch` has a node that is not in `G`.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> preds = nx.common_neighbor_centrality(G, [(0, 1), (2, 3)])
    >>> for u, v, p in preds:
    ...     print(f"({u}, {v}) -> {p}")
    (0, 1) -> 3.4000000000000004
    (2, 3) -> 3.4000000000000004

    References
    ----------
    .. [1] Ahmad, I., Akhtar, M.U., Noor, S. et al.
           Missing Link Prediction using Common Neighbor and Centrality based Parameterized Algorithm.
           Sci Rep 10, 364 (2020).
           https://doi.org/10.1038/s41598-019-57304-y
networkx.common_neighbors
Python Library Documentation: function common_neighbors in module networkx.classes.function

common_neighbors(G, u, v)
    Returns the common neighbors of two nodes in a graph.

    Parameters
    ----------
    G : graph
        A NetworkX undirected graph.

    u, v : nodes
        Nodes in the graph.

    Returns
    -------
    cnbors : set
        Set of common neighbors of u and v in the graph.

    Raises
    ------
    NetworkXError
        If u or v is not a node in the graph.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> sorted(nx.common_neighbors(G, 0, 1))
    [2, 3, 4]
networkx.communicability
Python Library Documentation: function communicability in module networkx.algorithms.communicability_alg

communicability(G, *, backend=None, **backend_kwargs)
    Returns communicability between all pairs of nodes in G.

    The communicability between pairs of nodes in G is the sum of
    walks of different lengths starting at node u and ending at node v.

    Parameters
    ----------
    G: graph

    Returns
    -------
    comm: dictionary of dictionaries
        Dictionary of dictionaries keyed by nodes with communicability
        as the value.

    Raises
    ------
    NetworkXError
       If the graph is not undirected and simple.

    See Also
    --------
    communicability_exp:
       Communicability between all pairs of nodes in G  using spectral
       decomposition.
    communicability_betweenness_centrality:
       Communicability betweenness centrality for each node in G.

    Notes
    -----
    This algorithm uses a spectral decomposition of the adjacency matrix.
    Let G=(V,E) be a simple undirected graph.  Using the connection between
    the powers  of the adjacency matrix and the number of walks in the graph,
    the communicability  between nodes `u` and `v` based on the graph spectrum
    is [1]_

    .. math::
        C(u,v)=\sum_{j=1}^{n}\phi_{j}(u)\phi_{j}(v)e^{\lambda_{j}},

    where `\phi_{j}(u)` is the `u\rm{th}` element of the `j\rm{th}` orthonormal
    eigenvector of the adjacency matrix associated with the eigenvalue
    `\lambda_{j}`.

    References
    ----------
    .. [1] Ernesto Estrada, Naomichi Hatano,
       "Communicability in complex networks",
       Phys. Rev. E 77, 036111 (2008).
       https://arxiv.org/abs/0707.0756

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (1, 2), (1, 5), (5, 4), (2, 4), (2, 3), (4, 3), (3, 6)])
    >>> c = nx.communicability(G)
networkx.communicability_alg
Python Library Documentation: module networkx.algorithms.communicability_alg in networkx.algorithms

NAME
    networkx.algorithms.communicability_alg - Communicability.

FUNCTIONS
    communicability(G, *, backend=None, **backend_kwargs)
        Returns communicability between all pairs of nodes in G.

        The communicability between pairs of nodes in G is the sum of
        walks of different lengths starting at node u and ending at node v.

        Parameters
        ----------
        G: graph

        Returns
        -------
        comm: dictionary of dictionaries
            Dictionary of dictionaries keyed by nodes with communicability
            as the value.

        Raises
        ------
        NetworkXError
           If the graph is not undirected and simple.

        See Also
        --------
        communicability_exp:
           Communicability between all pairs of nodes in G  using spectral
           decomposition.
        communicability_betweenness_centrality:
           Communicability betweenness centrality for each node in G.

        Notes
        -----
        This algorithm uses a spectral decomposition of the adjacency matrix.
        Let G=(V,E) be a simple undirected graph.  Using the connection between
        the powers  of the adjacency matrix and the number of walks in the graph,
        the communicability  between nodes `u` and `v` based on the graph spectrum
        is [1]_

        .. math::
            C(u,v)=\sum_{j=1}^{n}\phi_{j}(u)\phi_{j}(v)e^{\lambda_{j}},

        where `\phi_{j}(u)` is the `u\rm{th}` element of the `j\rm{th}` orthonormal
        eigenvector of the adjacency matrix associated with the eigenvalue
        `\lambda_{j}`.

        References
        ----------
        .. [1] Ernesto Estrada, Naomichi Hatano,
           "Communicability in complex networks",
           Phys. Rev. E 77, 036111 (2008).
           https://arxiv.org/abs/0707.0756

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (1, 2), (1, 5), (5, 4), (2, 4), (2, 3), (4, 3), (3, 6)])
        >>> c = nx.communicability(G)

    communicability_exp(G, *, backend=None, **backend_kwargs)
        Returns communicability between all pairs of nodes in G.

        Communicability between pair of node (u,v) of node in G is the sum of
        walks of different lengths starting at node u and ending at node v.

        Parameters
        ----------
        G: graph

        Returns
        -------
        comm: dictionary of dictionaries
            Dictionary of dictionaries keyed by nodes with communicability
            as the value.

        Raises
        ------
        NetworkXError
            If the graph is not undirected and simple.

        See Also
        --------
        communicability:
           Communicability between pairs of nodes in G.
        communicability_betweenness_centrality:
           Communicability betweenness centrality for each node in G.

        Notes
        -----
        This algorithm uses matrix exponentiation of the adjacency matrix.

        Let G=(V,E) be a simple undirected graph.  Using the connection between
        the powers  of the adjacency matrix and the number of walks in the graph,
        the communicability between nodes u and v is [1]_,

        .. math::
            C(u,v) = (e^A)_{uv},

        where `A` is the adjacency matrix of G.

        References
        ----------
        .. [1] Ernesto Estrada, Naomichi Hatano,
           "Communicability in complex networks",
           Phys. Rev. E 77, 036111 (2008).
           https://arxiv.org/abs/0707.0756

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (1, 2), (1, 5), (5, 4), (2, 4), (2, 3), (4, 3), (3, 6)])
        >>> c = nx.communicability_exp(G)

DATA
    __all__ = ['communicability', 'communicability_exp']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\communicability_alg.py

networkx.communicability_betweenness_centrality
Python Library Documentation: function communicability_betweenness_centrality in module networkx.algorithms.centrality.subgraph_alg

communicability_betweenness_centrality(G, *, backend=None, **backend_kwargs)
    Returns subgraph communicability for all pairs of nodes in G.

    Communicability betweenness measure makes use of the number of walks
    connecting every pair of nodes as the basis of a betweenness centrality
    measure.

    Parameters
    ----------
    G: graph

    Returns
    -------
    nodes : dictionary
        Dictionary of nodes with communicability betweenness as the value.

    Raises
    ------
    NetworkXError
        If the graph is not undirected and simple.

    Notes
    -----
    Let `G=(V,E)` be a simple undirected graph with `n` nodes and `m` edges,
    and `A` denote the adjacency matrix of `G`.

    Let `G(r)=(V,E(r))` be the graph resulting from
    removing all edges connected to node `r` but not the node itself.

    The adjacency matrix for `G(r)` is `A+E(r)`,  where `E(r)` has nonzeros
    only in row and column `r`.

    The subraph betweenness of a node `r`  is [1]_

    .. math::

         \omega_{r} = \frac{1}{C}\sum_{p}\sum_{q}\frac{G_{prq}}{G_{pq}},
         p\neq q, q\neq r,

    where
    `G_{prq}=(e^{A}_{pq} - (e^{A+E(r)})_{pq}`  is the number of walks
    involving node r,
    `G_{pq}=(e^{A})_{pq}` is the number of closed walks starting
    at node `p` and ending at node `q`,
    and `C=(n-1)^{2}-(n-1)` is a normalization factor equal to the
    number of terms in the sum.

    The resulting `\omega_{r}` takes values between zero and one.
    The lower bound cannot be attained for a connected
    graph, and the upper bound is attained in the star graph.

    References
    ----------
    .. [1] Ernesto Estrada, Desmond J. Higham, Naomichi Hatano,
       "Communicability Betweenness in Complex Networks"
       Physica A 388 (2009) 764-774.
       https://arxiv.org/abs/0905.4102

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (1, 2), (1, 5), (5, 4), (2, 4), (2, 3), (4, 3), (3, 6)])
    >>> cbc = nx.communicability_betweenness_centrality(G)
    >>> print([f"{node} {cbc[node]:0.2f}" for node in sorted(cbc)])
    ['0 0.03', '1 0.45', '2 0.51', '3 0.45', '4 0.40', '5 0.19', '6 0.03']
networkx.communicability_exp
Python Library Documentation: function communicability_exp in module networkx.algorithms.communicability_alg

communicability_exp(G, *, backend=None, **backend_kwargs)
    Returns communicability between all pairs of nodes in G.

    Communicability between pair of node (u,v) of node in G is the sum of
    walks of different lengths starting at node u and ending at node v.

    Parameters
    ----------
    G: graph

    Returns
    -------
    comm: dictionary of dictionaries
        Dictionary of dictionaries keyed by nodes with communicability
        as the value.

    Raises
    ------
    NetworkXError
        If the graph is not undirected and simple.

    See Also
    --------
    communicability:
       Communicability between pairs of nodes in G.
    communicability_betweenness_centrality:
       Communicability betweenness centrality for each node in G.

    Notes
    -----
    This algorithm uses matrix exponentiation of the adjacency matrix.

    Let G=(V,E) be a simple undirected graph.  Using the connection between
    the powers  of the adjacency matrix and the number of walks in the graph,
    the communicability between nodes u and v is [1]_,

    .. math::
        C(u,v) = (e^A)_{uv},

    where `A` is the adjacency matrix of G.

    References
    ----------
    .. [1] Ernesto Estrada, Naomichi Hatano,
       "Communicability in complex networks",
       Phys. Rev. E 77, 036111 (2008).
       https://arxiv.org/abs/0707.0756

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (1, 2), (1, 5), (5, 4), (2, 4), (2, 3), (4, 3), (3, 6)])
    >>> c = nx.communicability_exp(G)
networkx.community
Python Library Documentation: package networkx.algorithms.community in networkx.algorithms

NAME
    networkx.algorithms.community - Functions for computing and measuring community structure.

DESCRIPTION
    The ``community`` subpackage can be accessed by using :mod:`networkx.community`, then accessing the
    functions as attributes of ``community``. For example::

        >>> import networkx as nx
        >>> G = nx.barbell_graph(5, 1)
        >>> communities_generator = nx.community.girvan_newman(G)
        >>> top_level_communities = next(communities_generator)
        >>> next_level_communities = next(communities_generator)
        >>> sorted(map(sorted, next_level_communities))
        [[0, 1, 2, 3, 4], [5], [6, 7, 8, 9, 10]]

PACKAGE CONTENTS
    asyn_fluid
    centrality
    community_utils
    divisive
    kclique
    kernighan_lin
    label_propagation
    louvain
    lukes
    modularity_max
    quality
    tests (package)

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\community\__init__.py

networkx.complement
Python Library Documentation: function complement in module networkx.algorithms.operators.unary

complement(G, *, backend=None, **backend_kwargs)
    Returns the graph complement of G.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    Returns
    -------
    GC : A new graph.

    Notes
    -----
    Note that `complement` does not create self-loops and also
    does not produce parallel edges for MultiGraphs.

    Graph, node, and edge data are not propagated to the new graph.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (3, 4), (3, 5)])
    >>> G_complement = nx.complement(G)
    >>> G_complement.edges()  # This shows the edges of the complemented graph
    EdgeView([(1, 4), (1, 5), (2, 4), (2, 5), (4, 5)])
networkx.complete_bipartite_graph
Python Library Documentation: function complete_bipartite_graph in module networkx.algorithms.bipartite.generators

complete_bipartite_graph(n1, n2, create_using=None, *, backend=None, **backend_kwargs)
    Returns the complete bipartite graph `K_{n_1,n_2}`.

    The graph is composed of two partitions with nodes 0 to (n1 - 1)
    in the first and nodes n1 to (n1 + n2 - 1) in the second.
    Each node in the first is connected to each node in the second.

    Parameters
    ----------
    n1, n2 : integer or iterable container of nodes
        If integers, nodes are from `range(n1)` and `range(n1, n1 + n2)`.
        If a container, the elements are the nodes.
    create_using : NetworkX graph instance, (default: nx.Graph)
       Return graph of this type.

    Notes
    -----
    Nodes are the integers 0 to `n1 + n2 - 1` unless either n1 or n2 are
    containers of nodes. If only one of n1 or n2 are integers, that
    integer is replaced by `range` of that integer.

    The nodes are assigned the attribute 'bipartite' with the value 0 or 1
    to indicate which bipartite set the node belongs to.

    This function is not imported in the main namespace.
    To use it use nx.bipartite.complete_bipartite_graph
networkx.complete_graph
Python Library Documentation: function complete_graph in module networkx.generators.classic

complete_graph(n, create_using=None, *, backend=None, **backend_kwargs)
    Return the complete graph `K_n` with n nodes.

    A complete graph on `n` nodes means that all pairs
    of distinct nodes have an edge connecting them.

    .. plot::

        >>> nx.draw(nx.complete_graph(5))

    Parameters
    ----------
    n : int or iterable container of nodes
        If n is an integer, nodes are from range(n).
        If n is a container of nodes, those nodes appear in the graph.
        Warning: n is not checked for duplicates and if present the
        resulting graph may not be as desired. Make sure you have no duplicates.
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Examples
    --------
    >>> G = nx.complete_graph(9)
    >>> len(G)
    9
    >>> G.size()
    36
    >>> G = nx.complete_graph(range(11, 14))
    >>> list(G.nodes())
    [11, 12, 13]
    >>> G = nx.complete_graph(4, nx.DiGraph())
    >>> G.is_directed()
    True
networkx.complete_multipartite_graph
Python Library Documentation: function complete_multipartite_graph in module networkx.generators.classic

complete_multipartite_graph(*subset_sizes, backend=None, **backend_kwargs)
    Returns the complete multipartite graph with the specified subset sizes.

    .. plot::

        >>> nx.draw(nx.complete_multipartite_graph(1, 2, 3))

    Parameters
    ----------
    subset_sizes : tuple of integers or tuple of node iterables
       The arguments can either all be integer number of nodes or they
       can all be iterables of nodes. If integers, they represent the
       number of nodes in each subset of the multipartite graph.
       If iterables, each is used to create the nodes for that subset.
       The length of subset_sizes is the number of subsets.

    Returns
    -------
    G : NetworkX Graph
       Returns the complete multipartite graph with the specified subsets.

       For each node, the node attribute 'subset' is an integer
       indicating which subset contains the node.

    Examples
    --------
    Creating a complete tripartite graph, with subsets of one, two, and three
    nodes, respectively.

        >>> G = nx.complete_multipartite_graph(1, 2, 3)
        >>> [G.nodes[u]["subset"] for u in G]
        [0, 1, 1, 2, 2, 2]
        >>> list(G.edges(0))
        [(0, 1), (0, 2), (0, 3), (0, 4), (0, 5)]
        >>> list(G.edges(2))
        [(2, 0), (2, 3), (2, 4), (2, 5)]
        >>> list(G.edges(4))
        [(4, 0), (4, 1), (4, 2)]

        >>> G = nx.complete_multipartite_graph("a", "bc", "def")
        >>> [G.nodes[u]["subset"] for u in sorted(G)]
        [0, 1, 1, 2, 2, 2]

    Notes
    -----
    This function generalizes several other graph builder functions.

    - If no subset sizes are given, this returns the null graph.
    - If a single subset size `n` is given, this returns the empty graph on
      `n` nodes.
    - If two subset sizes `m` and `n` are given, this returns the complete
      bipartite graph on `m + n` nodes.
    - If subset sizes `1` and `n` are given, this returns the star graph on
      `n + 1` nodes.

    See also
    --------
    complete_bipartite_graph
networkx.complete_to_chordal_graph
Python Library Documentation: function complete_to_chordal_graph in module networkx.algorithms.chordal

complete_to_chordal_graph(G, *, backend=None, **backend_kwargs)
    Return a copy of G completed to a chordal graph

    Adds edges to a copy of G to create a chordal graph. A graph G=(V,E) is
    called chordal if for each cycle with length bigger than 3, there exist
    two non-adjacent nodes connected by an edge (called a chord).

    Parameters
    ----------
    G : NetworkX graph
        Undirected graph

    Returns
    -------
    H : NetworkX graph
        The chordal enhancement of G
    alpha : Dictionary
            The elimination ordering of nodes of G

    Notes
    -----
    There are different approaches to calculate the chordal
    enhancement of a graph. The algorithm used here is called
    MCS-M and gives at least minimal (local) triangulation of graph. Note
    that this triangulation is not necessarily a global minimum.

    https://en.wikipedia.org/wiki/Chordal_graph

    References
    ----------
    .. [1] Berry, Anne & Blair, Jean & Heggernes, Pinar & Peyton, Barry. (2004)
           Maximum Cardinality Search for Computing Minimal Triangulations of
           Graphs.  Algorithmica. 39. 287-298. 10.1007/s00453-004-1084-3.

    Examples
    --------
    >>> from networkx.algorithms.chordal import complete_to_chordal_graph
    >>> G = nx.wheel_graph(10)
    >>> H, alpha = complete_to_chordal_graph(G)
networkx.components
Python Library Documentation: package networkx.algorithms.components in networkx.algorithms

NAME
    networkx.algorithms.components

PACKAGE CONTENTS
    attracting
    biconnected
    connected
    semiconnected
    strongly_connected
    tests (package)
    weakly_connected

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\components\__init__.py

networkx.compose
Python Library Documentation: function compose in module networkx.algorithms.operators.binary

compose(G, H, *, backend=None, **backend_kwargs)
    Compose graph G with H by combining nodes and edges into a single graph.

    The node sets and edges sets do not need to be disjoint.

    Composing preserves the attributes of nodes and edges.
    Attribute values from H take precedent over attribute values from G.

    Parameters
    ----------
    G, H : graph
       A NetworkX graph

    Returns
    -------
    C: A new graph with the same type as G

    See Also
    --------
    :func:`~networkx.Graph.update`
    union
    disjoint_union

    Notes
    -----
    It is recommended that G and H be either both directed or both undirected.

    For MultiGraphs, the edges are identified by incident nodes AND edge-key.
    This can cause surprises (i.e., edge `(1, 2)` may or may not be the same
    in two graphs) if you use MultiGraph without keeping track of edge keys.

    If combining the attributes of common nodes is not desired, consider union(),
    which raises an exception for name collisions.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2)])
    >>> H = nx.Graph([(0, 1), (1, 2)])
    >>> R = nx.compose(G, H)
    >>> R.nodes
    NodeView((0, 1, 2))
    >>> R.edges
    EdgeView([(0, 1), (0, 2), (1, 2)])

    By default, the attributes from `H` take precedent over attributes from `G`.
    If you prefer another way of combining attributes, you can update them after the compose operation:

    >>> G = nx.Graph([(0, 1, {"weight": 2.0}), (3, 0, {"weight": 100.0})])
    >>> H = nx.Graph([(0, 1, {"weight": 10.0}), (1, 2, {"weight": -1.0})])
    >>> nx.set_node_attributes(G, {0: "dark", 1: "light", 3: "black"}, name="color")
    >>> nx.set_node_attributes(H, {0: "green", 1: "orange", 2: "yellow"}, name="color")
    >>> GcomposeH = nx.compose(G, H)

    Normally, color attribute values of nodes of GcomposeH come from H. We can workaround this as follows:

    >>> node_data = {
    ...     n: G.nodes[n]["color"] + " " + H.nodes[n]["color"]
    ...     for n in G.nodes & H.nodes
    ... }
    >>> nx.set_node_attributes(GcomposeH, node_data, "color")
    >>> print(GcomposeH.nodes[0]["color"])
    dark green

    >>> print(GcomposeH.nodes[3]["color"])
    black

    Similarly, we can update edge attributes after the compose operation in a way we prefer:

    >>> edge_data = {
    ...     e: G.edges[e]["weight"] * H.edges[e]["weight"] for e in G.edges & H.edges
    ... }
    >>> nx.set_edge_attributes(GcomposeH, edge_data, "weight")
    >>> print(GcomposeH.edges[(0, 1)]["weight"])
    20.0

    >>> print(GcomposeH.edges[(3, 0)]["weight"])
    100.0
networkx.compose_all
Python Library Documentation: function compose_all in module networkx.algorithms.operators.all

compose_all(graphs, *, backend=None, **backend_kwargs)
    Returns the composition of all graphs.

    Composition is the simple union of the node sets and edge sets.
    The node sets of the supplied graphs need not be disjoint.

    Parameters
    ----------
    graphs : iterable
       Iterable of NetworkX graphs

    Returns
    -------
    C : A graph with the same type as the first graph in list

    Raises
    ------
    ValueError
       If `graphs` is an empty list.

    NetworkXError
        In case of mixed type graphs, like MultiGraph and Graph, or directed and undirected graphs.

    Examples
    --------
    >>> G1 = nx.Graph([(1, 2), (2, 3)])
    >>> G2 = nx.Graph([(3, 4), (5, 6)])
    >>> C = nx.compose_all([G1, G2])
    >>> list(C.nodes())
    [1, 2, 3, 4, 5, 6]
    >>> list(C.edges())
    [(1, 2), (2, 3), (3, 4), (5, 6)]

    Notes
    -----
    For operating on mixed type graphs, they should be converted to the same type.

    Graph, edge, and node attributes are propagated to the union graph.
    If a graph attribute is present in multiple graphs, then the value
    from the last graph in the list with that attribute is used.
networkx.compute_v_structures
Python Library Documentation: function compute_v_structures in module networkx.algorithms.dag

compute_v_structures(G, *, backend=None, **backend_kwargs)
    Yields 3-node tuples that represent the v-structures in `G`.

    .. deprecated:: 3.4

       `compute_v_structures` actually yields colliders. It will be removed in
       version 3.6. Use `nx.dag.v_structures` or `nx.dag.colliders` instead.

    Colliders are triples in the directed acyclic graph (DAG) where two parent nodes
    point to the same child node. V-structures are colliders where the two parent
    nodes are not adjacent. In a causal graph setting, the parents do not directly
    depend on each other, but conditioning on the child node provides an association.

    Parameters
    ----------
    G : graph
        A networkx `~networkx.DiGraph`.

    Yields
    ------
    A 3-tuple representation of a v-structure
        Each v-structure is a 3-tuple with the parent, collider, and other parent.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is an undirected graph.

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (0, 4), (3, 1), (2, 4), (0, 5), (4, 5), (1, 5)])
    >>> nx.is_directed_acyclic_graph(G)
    True
    >>> list(nx.compute_v_structures(G))
    [(0, 4, 2), (0, 5, 4), (0, 5, 1), (4, 5, 1)]

    See Also
    --------
    v_structures
    colliders

    Notes
    -----
    This function was written to be used on DAGs, however it works on cyclic graphs
    too. Since colliders are referred to in the cyclic causal graph literature
    [2]_ we allow cyclic graphs in this function. It is suggested that you test if
    your input graph is acyclic as in the example if you want that property.

    References
    ----------
    .. [1]  `Pearl's PRIMER <https://bayes.cs.ucla.edu/PRIMER/primer-ch2.pdf>`_
            Ch-2 page 50: v-structures def.
    .. [2] A Hyttinen, P.O. Hoyer, F. Eberhardt, M J ̈arvisalo, (2013)
           "Discovering cyclic causal models with latent variables:
           a general SAT-based procedure", UAI'13: Proceedings of the Twenty-Ninth
           Conference on Uncertainty in Artificial Intelligence, pg 301–310,
           `doi:10.5555/3023638.3023669 <https://dl.acm.org/doi/10.5555/3023638.3023669>`_
networkx.condensation
Python Library Documentation: function condensation in module networkx.algorithms.components.strongly_connected

condensation(G, scc=None, *, backend=None, **backend_kwargs)
    Returns the condensation of G.

    The condensation of G is the graph with each of the strongly connected
    components contracted into a single node.

    Parameters
    ----------
    G : NetworkX DiGraph
       A directed graph.

    scc:  list or generator (optional, default=None)
       Strongly connected components. If provided, the elements in
       `scc` must partition the nodes in `G`. If not provided, it will be
       calculated as scc=nx.strongly_connected_components(G).

    Returns
    -------
    C : NetworkX DiGraph
       The condensation graph C of G.  The node labels are integers
       corresponding to the index of the component in the list of
       strongly connected components of G.  C has a graph attribute named
       'mapping' with a dictionary mapping the original nodes to the
       nodes in C to which they belong.  Each node in C also has a node
       attribute 'members' with the set of original nodes in G that
       form the SCC that the node in C represents.

    Raises
    ------
    NetworkXNotImplemented
        If G is undirected.

    Examples
    --------
    Contracting two sets of strongly connected nodes into two distinct SCC
    using the barbell graph.

    >>> G = nx.barbell_graph(4, 0)
    >>> G.remove_edge(3, 4)
    >>> G = nx.DiGraph(G)
    >>> H = nx.condensation(G)
    >>> H.nodes.data()
    NodeDataView({0: {'members': {0, 1, 2, 3}}, 1: {'members': {4, 5, 6, 7}}})
    >>> H.graph["mapping"]
    {0: 0, 1: 0, 2: 0, 3: 0, 4: 1, 5: 1, 6: 1, 7: 1}

    Contracting a complete graph into one single SCC.

    >>> G = nx.complete_graph(7, create_using=nx.DiGraph)
    >>> H = nx.condensation(G)
    >>> H.nodes
    NodeView((0,))
    >>> H.nodes.data()
    NodeDataView({0: {'members': {0, 1, 2, 3, 4, 5, 6}}})

    Notes
    -----
    After contracting all strongly connected components to a single node,
    the resulting graph is a directed acyclic graph.
networkx.conductance
Python Library Documentation: function conductance in module networkx.algorithms.cuts

conductance(G, S, T=None, weight=None, *, backend=None, **backend_kwargs)
    Returns the conductance of two sets of nodes.

    The *conductance* is the quotient of the cut size and the smaller of
    the volumes of the two sets. [1]

    Parameters
    ----------
    G : NetworkX graph

    S : collection
        A collection of nodes in `G`.

    T : collection
        A collection of nodes in `G`.

    weight : object
        Edge attribute key to use as weight. If not specified, edges
        have weight one.

    Returns
    -------
    number
        The conductance between the two sets `S` and `T`.

    See also
    --------
    cut_size
    edge_expansion
    normalized_cut_size
    volume

    References
    ----------
    .. [1] David Gleich.
           *Hierarchical Directed Spectral Graph Partitioning*.
           <https://www.cs.purdue.edu/homes/dgleich/publications/Gleich%202005%20-%20hierarchical%20directed%20spectral.pdf>
networkx.config
Python Library Documentation: NetworkXConfig in module networkx.utils.configs object

class NetworkXConfig(Config)
 |  NetworkXConfig(*, backend_priority: networkx.utils.configs.BackendPriorities, backends: networkx.utils.configs.Config, cache_converted_graphs: bool, fallback_to_nx: bool, warnings_to_ignore: set[str]) -> None
 |
 |  Configuration for NetworkX that controls behaviors such as how to use backends.
 |
 |  Attribute and bracket notation are supported for getting and setting configurations::
 |
 |      >>> nx.config.backend_priority == nx.config["backend_priority"]
 |      True
 |
 |  Parameters
 |  ----------
 |  backend_priority : list of backend names or dict or BackendPriorities
 |      Enable automatic conversion of graphs to backend graphs for functions
 |      implemented by the backend. Priority is given to backends listed earlier.
 |      This is a nested configuration with keys ``algos``, ``generators``, and,
 |      optionally, function names. Setting this value to a list of backend names
 |      will set ``nx.config.backend_priority.algos``. For more information, see
 |      ``help(nx.config.backend_priority)``. Default is empty list.
 |
 |  backends : Config mapping of backend names to backend Config
 |      The keys of the Config mapping are names of all installed NetworkX backends,
 |      and the values are their configurations as Config mappings.
 |
 |  cache_converted_graphs : bool
 |      If True, then save converted graphs to the cache of the input graph. Graph
 |      conversion may occur when automatically using a backend from `backend_priority`
 |      or when using the `backend=` keyword argument to a function call. Caching can
 |      improve performance by avoiding repeated conversions, but it uses more memory.
 |      Care should be taken to not manually mutate a graph that has cached graphs; for
 |      example, ``G[u][v][k] = val`` changes the graph, but does not clear the cache.
 |      Using methods such as ``G.add_edge(u, v, weight=val)`` will clear the cache to
 |      keep it consistent. ``G.__networkx_cache__.clear()`` manually clears the cache.
 |      Default is True.
 |
 |  fallback_to_nx : bool
 |      If True, then "fall back" and run with the default "networkx" implementation
 |      for dispatchable functions not implemented by backends of input graphs. When a
 |      backend graph is passed to a dispatchable function, the default behavior is to
 |      use the implementation from that backend if possible and raise if not. Enabling
 |      ``fallback_to_nx`` makes the networkx implementation the fallback to use instead
 |      of raising, and will convert the backend graph to a networkx-compatible graph.
 |      Default is False.
 |
 |  warnings_to_ignore : set of strings
 |      Control which warnings from NetworkX are not emitted. Valid elements:
 |
 |      - `"cache"`: when a cached value is used from ``G.__networkx_cache__``.
 |
 |  Notes
 |  -----
 |  Environment variables may be used to control some default configurations:
 |
 |  - ``NETWORKX_BACKEND_PRIORITY``: set ``backend_priority.algos`` from comma-separated names.
 |  - ``NETWORKX_CACHE_CONVERTED_GRAPHS``: set ``cache_converted_graphs`` to True if nonempty.
 |  - ``NETWORKX_FALLBACK_TO_NX``: set ``fallback_to_nx`` to True if nonempty.
 |  - ``NETWORKX_WARNINGS_TO_IGNORE``: set `warnings_to_ignore` from comma-separated names.
 |
 |  and can be used for finer control of ``backend_priority`` such as:
 |
 |  - ``NETWORKX_BACKEND_PRIORITY_ALGOS``: same as ``NETWORKX_BACKEND_PRIORITY`` to set ``backend_priority.algos``.
 |
 |  This is a global configuration. Use with caution when using from multiple threads.
 |
 |  Method resolution order:
 |      NetworkXConfig
 |      Config
 |      builtins.object
 |
 |  Methods defined here:
 |
 |  __init__(self, *, backend_priority: networkx.utils.configs.BackendPriorities, backends: networkx.utils.configs.Config, cache_converted_graphs: bool, fallback_to_nx: bool, warnings_to_ignore: set[str]) -> None
 |      Initialize self.  See help(type(self)) for accurate signature.
 |
 |  __repr__(self)
 |      Return repr(self).
 |
 |  ----------------------------------------------------------------------
 |  Data descriptors defined here:
 |
 |  backend_priority
 |
 |  backends
 |
 |  cache_converted_graphs
 |
 |  fallback_to_nx
 |
 |  warnings_to_ignore
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes defined here:
 |
 |  __annotations__ = {'backend_priority': <class 'networkx.utils.configs....
 |
 |  __dataclass_fields__ = {'backend_priority': Field(name='backend_priori...
 |
 |  __dataclass_params__ = _DataclassParams(init=True,repr=True,eq=False,o...
 |
 |  ----------------------------------------------------------------------
 |  Methods inherited from Config:
 |
 |  __call__(self, **kwargs)
 |      Call self as a function.
 |
 |  __contains__(self, key)
 |      # Be a `collection.abc.Collection`
 |
 |  __delattr__(self, key)
 |      Implement delattr(self, name).
 |
 |  __delitem__(self, key)
 |
 |  __dir__(self)
 |      Default dir() implementation.
 |
 |  __enter__(self)
 |
 |  __eq__(self, other)
 |      Return self==value.
 |
 |  __exit__(self, exc_type, exc_value, traceback)
 |
 |  __getitem__(self, key)
 |      # Add dunder methods for `collections.abc.Mapping`
 |
 |  __iter__(self)
 |
 |  __len__(self)
 |
 |  __reduce__(self)
 |      Helper for pickle.
 |
 |  __reversed__(self)
 |
 |  __setattr__(self, key, value)
 |      Implement setattr(self, name, value).
 |
 |  __setitem__(self, key, value)
 |
 |  get(self, key, default=None)
 |      # Go ahead and make it a `collections.abc.Mapping`
 |
 |  items(self)
 |
 |  keys(self)
 |
 |  values(self)
 |
 |  ----------------------------------------------------------------------
 |  Class methods inherited from Config:
 |
 |  __init_subclass__(strict=True)
 |      This method is called when a class is subclassed.
 |
 |      The default implementation does nothing. It may be
 |      overridden to extend subclasses.
 |
 |  ----------------------------------------------------------------------
 |  Static methods inherited from Config:
 |
 |  __new__(cls, **kwargs)
 |      Create and return a new object.  See help(type) for accurate signature.
 |
 |  ----------------------------------------------------------------------
 |  Data and other attributes inherited from Config:
 |
 |  __hash__ = None
networkx.configuration_model
Python Library Documentation: function configuration_model in module networkx.generators.degree_seq

configuration_model(deg_sequence, create_using=None, seed=None, *, backend=None, **backend_kwargs)
    Returns a random graph with the given degree sequence.

    The configuration model generates a random pseudograph (graph with
    parallel edges and self loops) by randomly assigning edges to
    match the given degree sequence.

    Parameters
    ----------
    deg_sequence :  list of nonnegative integers
        Each list entry corresponds to the degree of a node.
    create_using : NetworkX graph constructor, optional (default MultiGraph)
        Graph type to create. If graph instance, then cleared before populated.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : MultiGraph
        A graph with the specified degree sequence.
        Nodes are labeled starting at 0 with an index
        corresponding to the position in deg_sequence.

    Raises
    ------
    NetworkXError
        If the degree sequence does not have an even sum.

    See Also
    --------
    is_graphical

    Notes
    -----
    As described by Newman [1]_.

    A non-graphical degree sequence (not realizable by some simple
    graph) is allowed since this function returns graphs with self
    loops and parallel edges.  An exception is raised if the degree
    sequence does not have an even sum.

    This configuration model construction process can lead to
    duplicate edges and loops.  You can remove the self-loops and
    parallel edges (see below) which will likely result in a graph
    that doesn't have the exact degree sequence specified.

    The density of self-loops and parallel edges tends to decrease as
    the number of nodes increases. However, typically the number of
    self-loops will approach a Poisson distribution with a nonzero mean,
    and similarly for the number of parallel edges.  Consider a node
    with *k* stubs. The probability of being joined to another stub of
    the same node is basically (*k* - *1*) / *N*, where *k* is the
    degree and *N* is the number of nodes. So the probability of a
    self-loop scales like *c* / *N* for some constant *c*. As *N* grows,
    this means we expect *c* self-loops. Similarly for parallel edges.

    References
    ----------
    .. [1] M.E.J. Newman, "The structure and function of complex networks",
       SIAM REVIEW 45-2, pp 167-256, 2003.

    Examples
    --------
    You can create a degree sequence following a particular distribution
    by using the one of the distribution functions in
    :mod:`~networkx.utils.random_sequence` (or one of your own). For
    example, to create an undirected multigraph on one hundred nodes
    with degree sequence chosen from the power law distribution:

    >>> sequence = nx.random_powerlaw_tree_sequence(100, tries=5000)
    >>> G = nx.configuration_model(sequence)
    >>> len(G)
    100
    >>> actual_degrees = [d for v, d in G.degree()]
    >>> actual_degrees == sequence
    True

    The returned graph is a multigraph, which may have parallel
    edges. To remove any parallel edges from the returned graph:

    >>> G = nx.Graph(G)

    Similarly, to remove self-loops:

    >>> G.remove_edges_from(nx.selfloop_edges(G))
networkx.connected
Python Library Documentation: module networkx.algorithms.components.connected in networkx.algorithms.components

NAME
    networkx.algorithms.components.connected - Connected components.

FUNCTIONS
    connected_components(G, *, backend=None, **backend_kwargs)
        Generate connected components.

        Parameters
        ----------
        G : NetworkX graph
           An undirected graph

        Returns
        -------
        comp : generator of sets
           A generator of sets of nodes, one for each component of G.

        Raises
        ------
        NetworkXNotImplemented
            If G is directed.

        Examples
        --------
        Generate a sorted list of connected components, largest first.

        >>> G = nx.path_graph(4)
        >>> nx.add_path(G, [10, 11, 12])
        >>> [len(c) for c in sorted(nx.connected_components(G), key=len, reverse=True)]
        [4, 3]

        If you only want the largest connected component, it's more
        efficient to use max instead of sort.

        >>> largest_cc = max(nx.connected_components(G), key=len)

        To create the induced subgraph of each component use:

        >>> S = [G.subgraph(c).copy() for c in nx.connected_components(G)]

        See Also
        --------
        strongly_connected_components
        weakly_connected_components

        Notes
        -----
        For undirected graphs only.

    is_connected(G, *, backend=None, **backend_kwargs)
        Returns True if the graph is connected, False otherwise.

        Parameters
        ----------
        G : NetworkX Graph
           An undirected graph.

        Returns
        -------
        connected : bool
          True if the graph is connected, false otherwise.

        Raises
        ------
        NetworkXNotImplemented
            If G is directed.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> print(nx.is_connected(G))
        True

        See Also
        --------
        is_strongly_connected
        is_weakly_connected
        is_semiconnected
        is_biconnected
        connected_components

        Notes
        -----
        For undirected graphs only.

    node_connected_component(G, n, *, backend=None, **backend_kwargs)
        Returns the set of nodes in the component of graph containing node n.

        Parameters
        ----------
        G : NetworkX Graph
           An undirected graph.

        n : node label
           A node in G

        Returns
        -------
        comp : set
           A set of nodes in the component of G containing node n.

        Raises
        ------
        NetworkXNotImplemented
            If G is directed.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (1, 2), (5, 6), (3, 4)])
        >>> nx.node_connected_component(G, 0)  # nodes of component that contains node 0
        {0, 1, 2}

        See Also
        --------
        connected_components

        Notes
        -----
        For undirected graphs only.

    number_connected_components(G, *, backend=None, **backend_kwargs)
        Returns the number of connected components.

        Parameters
        ----------
        G : NetworkX graph
           An undirected graph.

        Returns
        -------
        n : integer
           Number of connected components

        Raises
        ------
        NetworkXNotImplemented
            If G is directed.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (1, 2), (5, 6), (3, 4)])
        >>> nx.number_connected_components(G)
        3

        See Also
        --------
        connected_components
        number_weakly_connected_components
        number_strongly_connected_components

        Notes
        -----
        For undirected graphs only.

DATA
    __all__ = ['number_connected_components', 'connected_components', 'is_...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\components\connected.py

networkx.connected_caveman_graph
Python Library Documentation: function connected_caveman_graph in module networkx.generators.community

connected_caveman_graph(l, k, *, backend=None, **backend_kwargs)
    Returns a connected caveman graph of `l` cliques of size `k`.

    The connected caveman graph is formed by creating `n` cliques of size
    `k`, then a single edge in each clique is rewired to a node in an
    adjacent clique.

    Parameters
    ----------
    l : int
      number of cliques
    k : int
      size of cliques (k at least 2 or NetworkXError is raised)

    Returns
    -------
    G : NetworkX Graph
      connected caveman graph

    Raises
    ------
    NetworkXError
        If the size of cliques `k` is smaller than 2.

    Notes
    -----
    This returns an undirected graph, it can be converted to a directed
    graph using :func:`nx.to_directed`, or a multigraph using
    ``nx.MultiGraph(nx.caveman_graph(l, k))``. Only the undirected version is
    described in [1]_ and it is unclear which of the directed
    generalizations is most useful.

    Examples
    --------
    >>> G = nx.connected_caveman_graph(3, 3)

    References
    ----------
    .. [1] Watts, D. J. 'Networks, Dynamics, and the Small-World Phenomenon.'
       Amer. J. Soc. 105, 493-527, 1999.
networkx.connected_components
Python Library Documentation: function connected_components in module networkx.algorithms.components.connected

connected_components(G, *, backend=None, **backend_kwargs)
    Generate connected components.

    Parameters
    ----------
    G : NetworkX graph
       An undirected graph

    Returns
    -------
    comp : generator of sets
       A generator of sets of nodes, one for each component of G.

    Raises
    ------
    NetworkXNotImplemented
        If G is directed.

    Examples
    --------
    Generate a sorted list of connected components, largest first.

    >>> G = nx.path_graph(4)
    >>> nx.add_path(G, [10, 11, 12])
    >>> [len(c) for c in sorted(nx.connected_components(G), key=len, reverse=True)]
    [4, 3]

    If you only want the largest connected component, it's more
    efficient to use max instead of sort.

    >>> largest_cc = max(nx.connected_components(G), key=len)

    To create the induced subgraph of each component use:

    >>> S = [G.subgraph(c).copy() for c in nx.connected_components(G)]

    See Also
    --------
    strongly_connected_components
    weakly_connected_components

    Notes
    -----
    For undirected graphs only.
networkx.connected_double_edge_swap
Python Library Documentation: function connected_double_edge_swap in module networkx.algorithms.swap

connected_double_edge_swap(G, nswap=1, _window_threshold=3, seed=None, *, backend=None, **backend_kwargs)
    Attempts the specified number of double-edge swaps in the graph `G`.

    A double-edge swap removes two randomly chosen edges `(u, v)` and `(x,
    y)` and creates the new edges `(u, x)` and `(v, y)`::

     u--v            u  v
            becomes  |  |
     x--y            x  y

    If either `(u, x)` or `(v, y)` already exist, then no swap is performed
    so the actual number of swapped edges is always *at most* `nswap`.

    Parameters
    ----------
    G : graph
       An undirected graph

    nswap : integer (optional, default=1)
       Number of double-edge swaps to perform

    _window_threshold : integer

       The window size below which connectedness of the graph will be checked
       after each swap.

       The "window" in this function is a dynamically updated integer that
       represents the number of swap attempts to make before checking if the
       graph remains connected. It is an optimization used to decrease the
       running time of the algorithm in exchange for increased complexity of
       implementation.

       If the window size is below this threshold, then the algorithm checks
       after each swap if the graph remains connected by checking if there is a
       path joining the two nodes whose edge was just removed. If the window
       size is above this threshold, then the algorithm performs do all the
       swaps in the window and only then check if the graph is still connected.

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    int
       The number of successful swaps

    Raises
    ------

    NetworkXError

       If the input graph is not connected, or if the graph has fewer than four
       nodes.

    Notes
    -----

    The initial graph `G` must be connected, and the resulting graph is
    connected. The graph `G` is modified in place.

    References
    ----------
    .. [1] C. Gkantsidis and M. Mihail and E. Zegura,
           The Markov chain simulation method for generating connected
           power law random graphs, 2003.
           http://citeseer.ist.psu.edu/gkantsidis03markov.html
networkx.connected_watts_strogatz_graph
Python Library Documentation: function connected_watts_strogatz_graph in module networkx.generators.random_graphs

connected_watts_strogatz_graph(n, k, p, tries=100, seed=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns a connected Watts–Strogatz small-world graph.

    Attempts to generate a connected graph by repeated generation of
    Watts–Strogatz small-world graphs.  An exception is raised if the maximum
    number of tries is exceeded.

    Parameters
    ----------
    n : int
        The number of nodes
    k : int
        Each node is joined with its `k` nearest neighbors in a ring
        topology.
    p : float
        The probability of rewiring each edge
    tries : int
        Number of attempts to generate a connected graph.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Notes
    -----
    First create a ring over $n$ nodes [1]_.  Then each node in the ring is joined
    to its $k$ nearest neighbors (or $k - 1$ neighbors if $k$ is odd).
    Then shortcuts are created by replacing some edges as follows: for each
    edge $(u, v)$ in the underlying "$n$-ring with $k$ nearest neighbors"
    with probability $p$ replace it with a new edge $(u, w)$ with uniformly
    random choice of existing node $w$.
    The entire process is repeated until a connected graph results.

    See Also
    --------
    newman_watts_strogatz_graph
    watts_strogatz_graph

    References
    ----------
    .. [1] Duncan J. Watts and Steven H. Strogatz,
       Collective dynamics of small-world networks,
       Nature, 393, pp. 440--442, 1998.
networkx.connectivity
Python Library Documentation: package networkx.algorithms.connectivity in networkx.algorithms

NAME
    networkx.algorithms.connectivity - Connectivity and cut algorithms

PACKAGE CONTENTS
    connectivity
    cuts
    disjoint_paths
    edge_augmentation
    edge_kcomponents
    kcomponents
    kcutsets
    stoerwagner
    tests (package)
    utils

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\connectivity\__init__.py

networkx.constraint
Python Library Documentation: function constraint in module networkx.algorithms.structuralholes

constraint(G, nodes=None, weight=None, *, backend=None, **backend_kwargs)
    Returns the constraint on all nodes in the graph ``G``.

    The *constraint* is a measure of the extent to which a node *v* is
    invested in those nodes that are themselves invested in the
    neighbors of *v*. Formally, the *constraint on v*, denoted `c(v)`,
    is defined by

    .. math::

       c(v) = \sum_{w \in N(v) \setminus \{v\}} \ell(v, w)

    where $N(v)$ is the subset of the neighbors of `v` that are either
    predecessors or successors of `v` and $\ell(v, w)$ is the local
    constraint on `v` with respect to `w` [1]_. For the definition of local
    constraint, see :func:`local_constraint`.

    Parameters
    ----------
    G : NetworkX graph
        The graph containing ``v``. This can be either directed or undirected.

    nodes : container, optional
        Container of nodes in the graph ``G`` to compute the constraint. If
        None, the constraint of every node is computed.

    weight : None or string, optional
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.

    Returns
    -------
    dict
        Dictionary with nodes as keys and the constraint on the node as values.

    See also
    --------
    local_constraint

    References
    ----------
    .. [1] Burt, Ronald S.
           "Structural holes and good ideas".
           American Journal of Sociology (110): 349–399.
networkx.contracted_edge
Python Library Documentation: function contracted_edge in module networkx.algorithms.minors.contraction

contracted_edge(G, edge, self_loops=True, copy=True, *, backend=None, **backend_kwargs)
    Returns the graph that results from contracting the specified edge.

    Edge contraction identifies the two endpoints of the edge as a single node
    incident to any edge that was incident to the original two nodes. A graph
    that results from edge contraction is called a *minor* of the original
    graph.

    Parameters
    ----------
    G : NetworkX graph
       The graph whose edge will be contracted.

    edge : tuple
       Must be a pair of nodes in `G`.

    self_loops : Boolean
       If this is True, any edges (including `edge`) joining the
       endpoints of `edge` in `G` become self-loops on the new node in the
       returned graph.

    copy : Boolean (default True)
        If this is True, a the contraction will be performed on a copy of `G`,
        otherwise the contraction will happen in place.

    Returns
    -------
    Networkx graph
       A new graph object of the same type as `G` (leaving `G` unmodified)
       with endpoints of `edge` identified in a single node. The right node
       of `edge` will be merged into the left one, so only the left one will
       appear in the returned graph.

    Raises
    ------
    ValueError
       If `edge` is not an edge in `G`.

    Examples
    --------
    Attempting to contract two nonadjacent nodes yields an error:

    >>> G = nx.cycle_graph(4)
    >>> nx.contracted_edge(G, (1, 3))
    Traceback (most recent call last):
      ...
    ValueError: Edge (1, 3) does not exist in graph G; cannot contract it

    Contracting two adjacent nodes in the cycle graph on *n* nodes yields the
    cycle graph on *n - 1* nodes:

    >>> C5 = nx.cycle_graph(5)
    >>> C4 = nx.cycle_graph(4)
    >>> M = nx.contracted_edge(C5, (0, 1), self_loops=False)
    >>> nx.is_isomorphic(M, C4)
    True

    See also
    --------
    contracted_nodes
    quotient_graph
networkx.contracted_nodes
Python Library Documentation: function contracted_nodes in module networkx.algorithms.minors.contraction

contracted_nodes(G, u, v, self_loops=True, copy=True, *, backend=None, **backend_kwargs)
    Returns the graph that results from contracting `u` and `v`.

    Node contraction identifies the two nodes as a single node incident to any
    edge that was incident to the original two nodes.

    Parameters
    ----------
    G : NetworkX graph
        The graph whose nodes will be contracted.

    u, v : nodes
        Must be nodes in `G`.

    self_loops : Boolean
        If this is True, any edges joining `u` and `v` in `G` become
        self-loops on the new node in the returned graph.

    copy : Boolean
        If this is True (default True), make a copy of
        `G` and return that instead of directly changing `G`.


    Returns
    -------
    Networkx graph
        If Copy is True,
        A new graph object of the same type as `G` (leaving `G` unmodified)
        with `u` and `v` identified in a single node. The right node `v`
        will be merged into the node `u`, so only `u` will appear in the
        returned graph.
        If copy is False,
        Modifies `G` with `u` and `v` identified in a single node.
        The right node `v` will be merged into the node `u`, so
        only `u` will appear in the returned graph.

    Notes
    -----
    For multigraphs, the edge keys for the realigned edges may
    not be the same as the edge keys for the old edges. This is
    natural because edge keys are unique only within each pair of nodes.

    For non-multigraphs where `u` and `v` are adjacent to a third node
    `w`, the edge (`v`, `w`) will be contracted into the edge (`u`,
    `w`) with its attributes stored into a "contraction" attribute.

    This function is also available as `identified_nodes`.

    Examples
    --------
    Contracting two nonadjacent nodes of the cycle graph on four nodes `C_4`
    yields the path graph (ignoring parallel edges):

    >>> G = nx.cycle_graph(4)
    >>> M = nx.contracted_nodes(G, 1, 3)
    >>> P3 = nx.path_graph(3)
    >>> nx.is_isomorphic(M, P3)
    True

    >>> G = nx.MultiGraph(P3)
    >>> M = nx.contracted_nodes(G, 0, 2)
    >>> M.edges
    MultiEdgeView([(0, 1, 0), (0, 1, 1)])

    >>> G = nx.Graph([(1, 2), (2, 2)])
    >>> H = nx.contracted_nodes(G, 1, 2, self_loops=False)
    >>> list(H.nodes())
    [1]
    >>> list(H.edges())
    [(1, 1)]

    In a ``MultiDiGraph`` with a self loop, the in and out edges will
    be treated separately as edges, so while contracting a node which
    has a self loop the contraction will add multiple edges:

    >>> G = nx.MultiDiGraph([(1, 2), (2, 2)])
    >>> H = nx.contracted_nodes(G, 1, 2)
    >>> list(H.edges())  # edge 1->2, 2->2, 2<-2 from the original Graph G
    [(1, 1), (1, 1), (1, 1)]
    >>> H = nx.contracted_nodes(G, 1, 2, self_loops=False)
    >>> list(H.edges())  # edge 2->2, 2<-2 from the original Graph G
    [(1, 1), (1, 1)]

    See Also
    --------
    contracted_edge
    quotient_graph
networkx.convert
Python Library Documentation: module networkx.convert in networkx

NAME
    networkx.convert - Functions to convert NetworkX graphs to and from other formats.

DESCRIPTION
    The preferred way of converting data to a NetworkX graph is through the
    graph constructor.  The constructor calls the to_networkx_graph() function
    which attempts to guess the input type and convert it automatically.

    Examples
    --------
    Create a graph with a single edge from a dictionary of dictionaries

    >>> d = {0: {1: 1}}  # dict-of-dicts single edge (0,1)
    >>> G = nx.Graph(d)

    See Also
    --------
    nx_agraph, nx_pydot

FUNCTIONS
    from_dict_of_dicts(d, create_using=None, multigraph_input=False, *, backend=None, **backend_kwargs)
        Returns a graph from a dictionary of dictionaries.

        Parameters
        ----------
        d : dictionary of dictionaries
          A dictionary of dictionaries adjacency representation.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.

        multigraph_input : bool (default False)
           When True, the dict `d` is assumed
           to be a dict-of-dict-of-dict-of-dict structure keyed by
           node to neighbor to edge keys to edge data for multi-edges.
           Otherwise this routine assumes dict-of-dict-of-dict keyed by
           node to neighbor to edge data.

        Examples
        --------
        >>> dod = {0: {1: {"weight": 1}}}  # single edge (0,1)
        >>> G = nx.from_dict_of_dicts(dod)

        or

        >>> G = nx.Graph(dod)  # use Graph constructor

    from_dict_of_lists(d, create_using=None, *, backend=None, **backend_kwargs)
        Returns a graph from a dictionary of lists.

        Parameters
        ----------
        d : dictionary of lists
          A dictionary of lists adjacency representation.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.

        Examples
        --------
        >>> dol = {0: [1]}  # single edge (0,1)
        >>> G = nx.from_dict_of_lists(dol)

        or

        >>> G = nx.Graph(dol)  # use Graph constructor

    from_edgelist(edgelist, create_using=None, *, backend=None, **backend_kwargs)
        Returns a graph from a list of edges.

        Parameters
        ----------
        edgelist : list or iterator
          Edge tuples

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.

        Examples
        --------
        >>> edgelist = [(0, 1)]  # single edge (0,1)
        >>> G = nx.from_edgelist(edgelist)

        or

        >>> G = nx.Graph(edgelist)  # use Graph constructor

    to_dict_of_dicts(G, nodelist=None, edge_data=None)
        Returns adjacency representation of graph as a dictionary of dictionaries.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        nodelist : list
           Use only nodes specified in nodelist

        edge_data : scalar, optional
           If provided, the value of the dictionary will be set to `edge_data` for
           all edges. Usual values could be `1` or `True`. If `edge_data` is
           `None` (the default), the edgedata in `G` is used, resulting in a
           dict-of-dict-of-dicts. If `G` is a MultiGraph, the result will be a
           dict-of-dict-of-dict-of-dicts. See Notes for an approach to customize
           handling edge data. `edge_data` should *not* be a container.

        Returns
        -------
        dod : dict
           A nested dictionary representation of `G`. Note that the level of
           nesting depends on the type of `G` and the value of `edge_data`
           (see Examples).

        See Also
        --------
        from_dict_of_dicts, to_dict_of_lists

        Notes
        -----
        For a more custom approach to handling edge data, try::

            dod = {
                n: {nbr: custom(n, nbr, dd) for nbr, dd in nbrdict.items()}
                for n, nbrdict in G.adj.items()
            }

        where `custom` returns the desired edge data for each edge between `n` and
        `nbr`, given existing edge data `dd`.

        Examples
        --------
        >>> G = nx.path_graph(3)
        >>> nx.to_dict_of_dicts(G)
        {0: {1: {}}, 1: {0: {}, 2: {}}, 2: {1: {}}}

        Edge data is preserved by default (``edge_data=None``), resulting
        in dict-of-dict-of-dicts where the innermost dictionary contains the
        edge data:

        >>> G = nx.Graph()
        >>> G.add_edges_from(
        ...     [
        ...         (0, 1, {"weight": 1.0}),
        ...         (1, 2, {"weight": 2.0}),
        ...         (2, 0, {"weight": 1.0}),
        ...     ]
        ... )
        >>> d = nx.to_dict_of_dicts(G)
        >>> d  # doctest: +SKIP
        {0: {1: {'weight': 1.0}, 2: {'weight': 1.0}},
         1: {0: {'weight': 1.0}, 2: {'weight': 2.0}},
         2: {1: {'weight': 2.0}, 0: {'weight': 1.0}}}
        >>> d[1][2]["weight"]
        2.0

        If `edge_data` is not `None`, edge data in the original graph (if any) is
        replaced:

        >>> d = nx.to_dict_of_dicts(G, edge_data=1)
        >>> d
        {0: {1: 1, 2: 1}, 1: {0: 1, 2: 1}, 2: {1: 1, 0: 1}}
        >>> d[1][2]
        1

        This also applies to MultiGraphs: edge data is preserved by default:

        >>> G = nx.MultiGraph()
        >>> G.add_edge(0, 1, key="a", weight=1.0)
        'a'
        >>> G.add_edge(0, 1, key="b", weight=5.0)
        'b'
        >>> d = nx.to_dict_of_dicts(G)
        >>> d  # doctest: +SKIP
        {0: {1: {'a': {'weight': 1.0}, 'b': {'weight': 5.0}}},
         1: {0: {'a': {'weight': 1.0}, 'b': {'weight': 5.0}}}}
        >>> d[0][1]["b"]["weight"]
        5.0

        But multi edge data is lost if `edge_data` is not `None`:

        >>> d = nx.to_dict_of_dicts(G, edge_data=10)
        >>> d
        {0: {1: 10}, 1: {0: 10}}

    to_dict_of_lists(G, nodelist=None, *, backend=None, **backend_kwargs)
        Returns adjacency representation of graph as a dictionary of lists.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        nodelist : list
           Use only nodes specified in nodelist

        Notes
        -----
        Completely ignores edge data for MultiGraph and MultiDiGraph.

    to_edgelist(G, nodelist=None, *, backend=None, **backend_kwargs)
        Returns a list of edges in the graph.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        nodelist : list
           Use only nodes specified in nodelist

    to_networkx_graph(data, create_using=None, multigraph_input=False)
        Make a NetworkX graph from a known data structure.

        The preferred way to call this is automatically
        from the class constructor

        >>> d = {0: {1: {"weight": 1}}}  # dict-of-dicts single edge (0,1)
        >>> G = nx.Graph(d)

        instead of the equivalent

        >>> G = nx.from_dict_of_dicts(d)

        Parameters
        ----------
        data : object to be converted

            Current known types are:
             any NetworkX graph
             dict-of-dicts
             dict-of-lists
             container (e.g. set, list, tuple) of edges
             iterator (e.g. itertools.chain) that produces edges
             generator of edges
             Pandas DataFrame (row per edge)
             2D numpy array
             scipy sparse array
             pygraphviz agraph

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.

        multigraph_input : bool (default False)
            If True and  data is a dict_of_dicts,
            try to create a multigraph assuming dict_of_dict_of_lists.
            If data and create_using are both multigraphs then create
            a multigraph from a multigraph.

DATA
    __all__ = ['to_networkx_graph', 'from_dict_of_dicts', 'to_dict_of_dict...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\convert.py

networkx.convert_matrix
Python Library Documentation: module networkx.convert_matrix in networkx

NAME
    networkx.convert_matrix

DESCRIPTION
    Functions to convert NetworkX graphs to and from common data containers
    like numpy arrays, scipy sparse arrays, and pandas DataFrames.

    The preferred way of converting data to a NetworkX graph is through the
    graph constructor.  The constructor calls the `~networkx.convert.to_networkx_graph`
    function which attempts to guess the input type and convert it automatically.

    Examples
    --------
    Create a 10 node random graph from a numpy array

    >>> import numpy as np
    >>> rng = np.random.default_rng()
    >>> a = rng.integers(low=0, high=2, size=(10, 10))
    >>> DG = nx.from_numpy_array(a, create_using=nx.DiGraph)

    or equivalently:

    >>> DG = nx.DiGraph(a)

    which calls `from_numpy_array` internally based on the type of ``a``.

    See Also
    --------
    nx_agraph, nx_pydot

FUNCTIONS
    from_numpy_array(A, parallel_edges=False, create_using=None, edge_attr='weight', *, nodelist=None, backend=None, **backend_kwargs)
        Returns a graph from a 2D NumPy array.

        The 2D NumPy array is interpreted as an adjacency matrix for the graph.

        Parameters
        ----------
        A : a 2D numpy.ndarray
            An adjacency matrix representation of a graph

        parallel_edges : Boolean
            If this is True, `create_using` is a multigraph, and `A` is an
            integer array, then entry *(i, j)* in the array is interpreted as the
            number of parallel edges joining vertices *i* and *j* in the graph.
            If it is False, then the entries in the array are interpreted as
            the weight of a single edge joining the vertices.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        edge_attr : String, optional (default="weight")
            The attribute to which the array values are assigned on each edge. If
            it is None, edge attributes will not be assigned.

        nodelist : sequence of nodes, optional
            A sequence of objects to use as the nodes in the graph. If provided, the
            list of nodes must be the same length as the dimensions of `A`. The
            default is `None`, in which case the nodes are drawn from ``range(n)``.

        Notes
        -----
        For directed graphs, explicitly mention create_using=nx.DiGraph,
        and entry i,j of A corresponds to an edge from i to j.

        If `create_using` is :class:`networkx.MultiGraph` or
        :class:`networkx.MultiDiGraph`, `parallel_edges` is True, and the
        entries of `A` are of type :class:`int`, then this function returns a
        multigraph (of the same type as `create_using`) with parallel edges.

        If `create_using` indicates an undirected multigraph, then only the edges
        indicated by the upper triangle of the array `A` will be added to the
        graph.

        If `edge_attr` is Falsy (False or None), edge attributes will not be
        assigned, and the array data will be treated like a binary mask of
        edge presence or absence. Otherwise, the attributes will be assigned
        as follows:

        If the NumPy array has a single data type for each array entry it
        will be converted to an appropriate Python data type.

        If the NumPy array has a user-specified compound data type the names
        of the data fields will be used as attribute keys in the resulting
        NetworkX graph.

        See Also
        --------
        to_numpy_array

        Examples
        --------
        Simple integer weights on edges:

        >>> import numpy as np
        >>> A = np.array([[1, 1], [2, 1]])
        >>> G = nx.from_numpy_array(A)
        >>> G.edges(data=True)
        EdgeDataView([(0, 0, {'weight': 1}), (0, 1, {'weight': 2}), (1, 1, {'weight': 1})])

        If `create_using` indicates a multigraph and the array has only integer
        entries and `parallel_edges` is False, then the entries will be treated
        as weights for edges joining the nodes (without creating parallel edges):

        >>> A = np.array([[1, 1], [1, 2]])
        >>> G = nx.from_numpy_array(A, create_using=nx.MultiGraph)
        >>> G[1][1]
        AtlasView({0: {'weight': 2}})

        If `create_using` indicates a multigraph and the array has only integer
        entries and `parallel_edges` is True, then the entries will be treated
        as the number of parallel edges joining those two vertices:

        >>> A = np.array([[1, 1], [1, 2]])
        >>> temp = nx.MultiGraph()
        >>> G = nx.from_numpy_array(A, parallel_edges=True, create_using=temp)
        >>> G[1][1]
        AtlasView({0: {'weight': 1}, 1: {'weight': 1}})

        User defined compound data type on edges:

        >>> dt = [("weight", float), ("cost", int)]
        >>> A = np.array([[(1.0, 2)]], dtype=dt)
        >>> G = nx.from_numpy_array(A)
        >>> G.edges()
        EdgeView([(0, 0)])
        >>> G[0][0]["cost"]
        2
        >>> G[0][0]["weight"]
        1.0

    from_pandas_adjacency(df, create_using=None, *, backend=None, **backend_kwargs)
        Returns a graph from Pandas DataFrame.

        The Pandas DataFrame is interpreted as an adjacency matrix for the graph.

        Parameters
        ----------
        df : Pandas DataFrame
          An adjacency matrix representation of a graph

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Notes
        -----
        For directed graphs, explicitly mention create_using=nx.DiGraph,
        and entry i,j of df corresponds to an edge from i to j.

        If `df` has a single data type for each entry it will be converted to an
        appropriate Python data type.

        If you have node attributes stored in a separate dataframe `df_nodes`,
        you can load those attributes to the graph `G` using the following code:

        ```
        df_nodes = pd.DataFrame({"node_id": [1, 2, 3], "attribute1": ["A", "B", "C"]})
        G.add_nodes_from((n, dict(d)) for n, d in df_nodes.iterrows())
        ```

        If `df` has a user-specified compound data type the names
        of the data fields will be used as attribute keys in the resulting
        NetworkX graph.

        See Also
        --------
        to_pandas_adjacency

        Examples
        --------
        Simple integer weights on edges:

        >>> import pandas as pd
        >>> pd.options.display.max_columns = 20
        >>> df = pd.DataFrame([[1, 1], [2, 1]])
        >>> df
           0  1
        0  1  1
        1  2  1
        >>> G = nx.from_pandas_adjacency(df)
        >>> G.name = "Graph from pandas adjacency matrix"
        >>> print(G)
        Graph named 'Graph from pandas adjacency matrix' with 2 nodes and 3 edges

    from_pandas_edgelist(df, source='source', target='target', edge_attr=None, create_using=None, edge_key=None, *, backend=None, **backend_kwargs)
        Returns a graph from Pandas DataFrame containing an edge list.

        The Pandas DataFrame should contain at least two columns of node names and
        zero or more columns of edge attributes. Each row will be processed as one
        edge instance.

        Note: This function iterates over DataFrame.values, which is not
        guaranteed to retain the data type across columns in the row. This is only
        a problem if your row is entirely numeric and a mix of ints and floats. In
        that case, all values will be returned as floats. See the
        DataFrame.iterrows documentation for an example.

        Parameters
        ----------
        df : Pandas DataFrame
            An edge list representation of a graph

        source : str or int
            A valid column name (string or integer) for the source nodes (for the
            directed case).

        target : str or int
            A valid column name (string or integer) for the target nodes (for the
            directed case).

        edge_attr : str or int, iterable, True, or None
            A valid column name (str or int) or iterable of column names that are
            used to retrieve items and add them to the graph as edge attributes.
            If `True`, all columns will be added except `source`, `target` and `edge_key`.
            If `None`, no edge attributes are added to the graph.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.

        edge_key : str or None, optional (default=None)
            A valid column name for the edge keys (for a MultiGraph). The values in
            this column are used for the edge keys when adding edges if create_using
            is a multigraph.

        If you have node attributes stored in a separate dataframe `df_nodes`,
        you can load those attributes to the graph `G` using the following code:

        ```
        df_nodes = pd.DataFrame({"node_id": [1, 2, 3], "attribute1": ["A", "B", "C"]})
        G.add_nodes_from((n, dict(d)) for n, d in df_nodes.iterrows())
        ```

        See Also
        --------
        to_pandas_edgelist

        Examples
        --------
        Simple integer weights on edges:

        >>> import pandas as pd
        >>> pd.options.display.max_columns = 20
        >>> import numpy as np
        >>> rng = np.random.RandomState(seed=5)
        >>> ints = rng.randint(1, 11, size=(3, 2))
        >>> a = ["A", "B", "C"]
        >>> b = ["D", "A", "E"]
        >>> df = pd.DataFrame(ints, columns=["weight", "cost"])
        >>> df[0] = a
        >>> df["b"] = b
        >>> df[["weight", "cost", 0, "b"]]
           weight  cost  0  b
        0       4     7  A  D
        1       7     1  B  A
        2      10     9  C  E
        >>> G = nx.from_pandas_edgelist(df, 0, "b", ["weight", "cost"])
        >>> G["E"]["C"]["weight"]
        10
        >>> G["E"]["C"]["cost"]
        9
        >>> edges = pd.DataFrame(
        ...     {
        ...         "source": [0, 1, 2],
        ...         "target": [2, 2, 3],
        ...         "weight": [3, 4, 5],
        ...         "color": ["red", "blue", "blue"],
        ...     }
        ... )
        >>> G = nx.from_pandas_edgelist(edges, edge_attr=True)
        >>> G[0][2]["color"]
        'red'

        Build multigraph with custom keys:

        >>> edges = pd.DataFrame(
        ...     {
        ...         "source": [0, 1, 2, 0],
        ...         "target": [2, 2, 3, 2],
        ...         "my_edge_key": ["A", "B", "C", "D"],
        ...         "weight": [3, 4, 5, 6],
        ...         "color": ["red", "blue", "blue", "blue"],
        ...     }
        ... )
        >>> G = nx.from_pandas_edgelist(
        ...     edges,
        ...     edge_key="my_edge_key",
        ...     edge_attr=["weight", "color"],
        ...     create_using=nx.MultiGraph(),
        ... )
        >>> G[0][2]
        AtlasView({'A': {'weight': 3, 'color': 'red'}, 'D': {'weight': 6, 'color': 'blue'}})

    from_scipy_sparse_array(A, parallel_edges=False, create_using=None, edge_attribute='weight', *, backend=None, **backend_kwargs)
        Creates a new graph from an adjacency matrix given as a SciPy sparse
        array.

        Parameters
        ----------
        A: scipy.sparse array
          An adjacency matrix representation of a graph

        parallel_edges : Boolean
          If this is True, `create_using` is a multigraph, and `A` is an
          integer matrix, then entry *(i, j)* in the matrix is interpreted as the
          number of parallel edges joining vertices *i* and *j* in the graph.
          If it is False, then the entries in the matrix are interpreted as
          the weight of a single edge joining the vertices.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        edge_attribute: string
           Name of edge attribute to store matrix numeric value. The data will
           have the same type as the matrix entry (int, float, (real,imag)).

        Notes
        -----
        For directed graphs, explicitly mention create_using=nx.DiGraph,
        and entry i,j of A corresponds to an edge from i to j.

        If `create_using` is :class:`networkx.MultiGraph` or
        :class:`networkx.MultiDiGraph`, `parallel_edges` is True, and the
        entries of `A` are of type :class:`int`, then this function returns a
        multigraph (constructed from `create_using`) with parallel edges.
        In this case, `edge_attribute` will be ignored.

        If `create_using` indicates an undirected multigraph, then only the edges
        indicated by the upper triangle of the matrix `A` will be added to the
        graph.

        Examples
        --------
        >>> import scipy as sp
        >>> A = sp.sparse.eye(2, 2, 1)
        >>> G = nx.from_scipy_sparse_array(A)

        If `create_using` indicates a multigraph and the matrix has only integer
        entries and `parallel_edges` is False, then the entries will be treated
        as weights for edges joining the nodes (without creating parallel edges):

        >>> A = sp.sparse.csr_array([[1, 1], [1, 2]])
        >>> G = nx.from_scipy_sparse_array(A, create_using=nx.MultiGraph)
        >>> G[1][1]
        AtlasView({0: {'weight': 2}})

        If `create_using` indicates a multigraph and the matrix has only integer
        entries and `parallel_edges` is True, then the entries will be treated
        as the number of parallel edges joining those two vertices:

        >>> A = sp.sparse.csr_array([[1, 1], [1, 2]])
        >>> G = nx.from_scipy_sparse_array(
        ...     A, parallel_edges=True, create_using=nx.MultiGraph
        ... )
        >>> G[1][1]
        AtlasView({0: {'weight': 1}, 1: {'weight': 1}})

    to_numpy_array(G, nodelist=None, dtype=None, order=None, multigraph_weight=<built-in function sum>, weight='weight', nonedge=0.0, *, backend=None, **backend_kwargs)
        Returns the graph adjacency matrix as a NumPy array.

        Parameters
        ----------
        G : graph
            The NetworkX graph used to construct the NumPy array.

        nodelist : list, optional
            The rows and columns are ordered according to the nodes in `nodelist`.
            If `nodelist` is ``None``, then the ordering is produced by ``G.nodes()``.

        dtype : NumPy data type, optional
            A NumPy data type used to initialize the array. If None, then the NumPy
            default is used. The dtype can be structured if `weight=None`, in which
            case the dtype field names are used to look up edge attributes. The
            result is a structured array where each named field in the dtype
            corresponds to the adjacency for that edge attribute. See examples for
            details.

        order : {'C', 'F'}, optional
            Whether to store multidimensional data in C- or Fortran-contiguous
            (row- or column-wise) order in memory. If None, then the NumPy default
            is used.

        multigraph_weight : callable, optional
            An function that determines how weights in multigraphs are handled.
            The function should accept a sequence of weights and return a single
            value. The default is to sum the weights of the multiple edges.

        weight : string or None optional (default = 'weight')
            The edge attribute that holds the numerical value used for
            the edge weight. If an edge does not have that attribute, then the
            value 1 is used instead. `weight` must be ``None`` if a structured
            dtype is used.

        nonedge : array_like (default = 0.0)
            The value used to represent non-edges in the adjacency matrix.
            The array values corresponding to nonedges are typically set to zero.
            However, this could be undesirable if there are array values
            corresponding to actual edges that also have the value zero. If so,
            one might prefer nonedges to have some other value, such as ``nan``.

        Returns
        -------
        A : NumPy ndarray
            Graph adjacency matrix

        Raises
        ------
        NetworkXError
            If `dtype` is a structured dtype and `G` is a multigraph
        ValueError
            If `dtype` is a structured dtype and `weight` is not `None`

        See Also
        --------
        from_numpy_array

        Notes
        -----
        For directed graphs, entry ``i, j`` corresponds to an edge from ``i`` to ``j``.

        Entries in the adjacency matrix are given by the `weight` edge attribute.
        When an edge does not have a weight attribute, the value of the entry is
        set to the number 1.  For multiple (parallel) edges, the values of the
        entries are determined by the `multigraph_weight` parameter. The default is
        to sum the weight attributes for each of the parallel edges.

        When `nodelist` does not contain every node in `G`, the adjacency matrix is
        built from the subgraph of `G` that is induced by the nodes in `nodelist`.

        The convention used for self-loop edges in graphs is to assign the
        diagonal array entry value to the weight attribute of the edge
        (or the number 1 if the edge has no weight attribute). If the
        alternate convention of doubling the edge weight is desired the
        resulting NumPy array can be modified as follows:

        >>> import numpy as np
        >>> G = nx.Graph([(1, 1)])
        >>> A = nx.to_numpy_array(G)
        >>> A
        array([[1.]])
        >>> A[np.diag_indices_from(A)] *= 2
        >>> A
        array([[2.]])

        Examples
        --------
        >>> G = nx.MultiDiGraph()
        >>> G.add_edge(0, 1, weight=2)
        0
        >>> G.add_edge(1, 0)
        0
        >>> G.add_edge(2, 2, weight=3)
        0
        >>> G.add_edge(2, 2)
        1
        >>> nx.to_numpy_array(G, nodelist=[0, 1, 2])
        array([[0., 2., 0.],
               [1., 0., 0.],
               [0., 0., 4.]])

        When `nodelist` argument is used, nodes of `G` which do not appear in the `nodelist`
        and their edges are not included in the adjacency matrix. Here is an example:

        >>> G = nx.Graph()
        >>> G.add_edge(3, 1)
        >>> G.add_edge(2, 0)
        >>> G.add_edge(2, 1)
        >>> G.add_edge(3, 0)
        >>> nx.to_numpy_array(G, nodelist=[1, 2, 3])
        array([[0., 1., 1.],
               [1., 0., 0.],
               [1., 0., 0.]])

        This function can also be used to create adjacency matrices for multiple
        edge attributes with structured dtypes:

        >>> G = nx.Graph()
        >>> G.add_edge(0, 1, weight=10)
        >>> G.add_edge(1, 2, cost=5)
        >>> G.add_edge(2, 3, weight=3, cost=-4.0)
        >>> dtype = np.dtype([("weight", int), ("cost", float)])
        >>> A = nx.to_numpy_array(G, dtype=dtype, weight=None)
        >>> A["weight"]
        array([[ 0, 10,  0,  0],
               [10,  0,  1,  0],
               [ 0,  1,  0,  3],
               [ 0,  0,  3,  0]])
        >>> A["cost"]
        array([[ 0.,  1.,  0.,  0.],
               [ 1.,  0.,  5.,  0.],
               [ 0.,  5.,  0., -4.],
               [ 0.,  0., -4.,  0.]])

        As stated above, the argument "nonedge" is useful especially when there are
        actually edges with weight 0 in the graph. Setting a nonedge value different than 0,
        makes it much clearer to differentiate such 0-weighted edges and actual nonedge values.

        >>> G = nx.Graph()
        >>> G.add_edge(3, 1, weight=2)
        >>> G.add_edge(2, 0, weight=0)
        >>> G.add_edge(2, 1, weight=0)
        >>> G.add_edge(3, 0, weight=1)
        >>> nx.to_numpy_array(G, nonedge=-1.0)
        array([[-1.,  2., -1.,  1.],
               [ 2., -1.,  0., -1.],
               [-1.,  0., -1.,  0.],
               [ 1., -1.,  0., -1.]])

    to_pandas_adjacency(G, nodelist=None, dtype=None, order=None, multigraph_weight=<built-in function sum>, weight='weight', nonedge=0.0, *, backend=None, **backend_kwargs)
        Returns the graph adjacency matrix as a Pandas DataFrame.

        Parameters
        ----------
        G : graph
            The NetworkX graph used to construct the Pandas DataFrame.

        nodelist : list, optional
           The rows and columns are ordered according to the nodes in `nodelist`.
           If `nodelist` is None, then the ordering is produced by G.nodes().

        multigraph_weight : {sum, min, max}, optional
            An operator that determines how weights in multigraphs are handled.
            The default is to sum the weights of the multiple edges.

        weight : string or None, optional
            The edge attribute that holds the numerical value used for
            the edge weight.  If an edge does not have that attribute, then the
            value 1 is used instead.

        nonedge : float, optional
            The matrix values corresponding to nonedges are typically set to zero.
            However, this could be undesirable if there are matrix values
            corresponding to actual edges that also have the value zero. If so,
            one might prefer nonedges to have some other value, such as nan.

        Returns
        -------
        df : Pandas DataFrame
           Graph adjacency matrix

        Notes
        -----
        For directed graphs, entry i,j corresponds to an edge from i to j.

        The DataFrame entries are assigned to the weight edge attribute. When
        an edge does not have a weight attribute, the value of the entry is set to
        the number 1.  For multiple (parallel) edges, the values of the entries
        are determined by the 'multigraph_weight' parameter.  The default is to
        sum the weight attributes for each of the parallel edges.

        When `nodelist` does not contain every node in `G`, the matrix is built
        from the subgraph of `G` that is induced by the nodes in `nodelist`.

        The convention used for self-loop edges in graphs is to assign the
        diagonal matrix entry value to the weight attribute of the edge
        (or the number 1 if the edge has no weight attribute).  If the
        alternate convention of doubling the edge weight is desired the
        resulting Pandas DataFrame can be modified as follows::

            >>> import pandas as pd
            >>> G = nx.Graph([(1, 1), (2, 2)])
            >>> df = nx.to_pandas_adjacency(G)
            >>> df
                 1    2
            1  1.0  0.0
            2  0.0  1.0
            >>> diag_idx = list(range(len(df)))
            >>> df.iloc[diag_idx, diag_idx] *= 2
            >>> df
                 1    2
            1  2.0  0.0
            2  0.0  2.0

        Examples
        --------
        >>> G = nx.MultiDiGraph()
        >>> G.add_edge(0, 1, weight=2)
        0
        >>> G.add_edge(1, 0)
        0
        >>> G.add_edge(2, 2, weight=3)
        0
        >>> G.add_edge(2, 2)
        1
        >>> nx.to_pandas_adjacency(G, nodelist=[0, 1, 2], dtype=int)
           0  1  2
        0  0  2  0
        1  1  0  0
        2  0  0  4

    to_pandas_edgelist(G, source='source', target='target', nodelist=None, dtype=None, edge_key=None, *, backend=None, **backend_kwargs)
        Returns the graph edge list as a Pandas DataFrame.

        Parameters
        ----------
        G : graph
            The NetworkX graph used to construct the Pandas DataFrame.

        source : str or int, optional
            A valid column name (string or integer) for the source nodes (for the
            directed case).

        target : str or int, optional
            A valid column name (string or integer) for the target nodes (for the
            directed case).

        nodelist : list, optional
           Use only nodes specified in nodelist

        dtype : dtype, default None
            Use to create the DataFrame. Data type to force.
            Only a single dtype is allowed. If None, infer.

        edge_key : str or int or None, optional (default=None)
            A valid column name (string or integer) for the edge keys (for the
            multigraph case). If None, edge keys are not stored in the DataFrame.

        Returns
        -------
        df : Pandas DataFrame
           Graph edge list

        Examples
        --------
        >>> G = nx.Graph(
        ...     [
        ...         ("A", "B", {"cost": 1, "weight": 7}),
        ...         ("C", "E", {"cost": 9, "weight": 10}),
        ...     ]
        ... )
        >>> df = nx.to_pandas_edgelist(G, nodelist=["A", "C"])
        >>> df[["source", "target", "cost", "weight"]]
          source target  cost  weight
        0      A      B     1       7
        1      C      E     9      10

        >>> G = nx.MultiGraph([("A", "B", {"cost": 1}), ("A", "B", {"cost": 9})])
        >>> df = nx.to_pandas_edgelist(G, nodelist=["A", "C"], edge_key="ekey")
        >>> df[["source", "target", "cost", "ekey"]]
          source target  cost  ekey
        0      A      B     1     0
        1      A      B     9     1

    to_scipy_sparse_array(G, nodelist=None, dtype=None, weight='weight', format='csr', *, backend=None, **backend_kwargs)
        Returns the graph adjacency matrix as a SciPy sparse array.

        Parameters
        ----------
        G : graph
            The NetworkX graph used to construct the sparse array.

        nodelist : list, optional
           The rows and columns are ordered according to the nodes in `nodelist`.
           If `nodelist` is None, then the ordering is produced by ``G.nodes()``.

        dtype : NumPy data-type, optional
            A valid NumPy dtype used to initialize the array. If None, then the
            NumPy default is used.

        weight : string or None, optional (default='weight')
            The edge attribute that holds the numerical value used for
            the edge weight.  If None then all edge weights are 1.

        format : str in {'bsr', 'csr', 'csc', 'coo', 'lil', 'dia', 'dok'}
            The format of the sparse array to be returned (default 'csr').  For
            some algorithms different implementations of sparse arrays
            can perform better.  See [1]_ for details.

        Returns
        -------
        A : SciPy sparse array
           Graph adjacency matrix.

        Notes
        -----
        For directed graphs, matrix entry ``i, j`` corresponds to an edge from
        ``i`` to ``j``.

        The values of the adjacency matrix are populated using the edge attribute held in
        parameter `weight`. When an edge does not have that attribute, the
        value of the entry is 1.

        For multiple edges the matrix values are the sums of the edge weights.

        When `nodelist` does not contain every node in `G`, the adjacency matrix
        is built from the subgraph of `G` that is induced by the nodes in
        `nodelist`.

        The convention used for self-loop edges in graphs is to assign the
        diagonal matrix entry value to the weight attribute of the edge
        (or the number 1 if the edge has no weight attribute).  If the
        alternate convention of doubling the edge weight is desired the
        resulting array can be modified as follows::

            >>> G = nx.Graph([(1, 1)])
            >>> A = nx.to_scipy_sparse_array(G)
            >>> A.toarray()
            array([[1]])
            >>> A.setdiag(A.diagonal() * 2)
            >>> A.toarray()
            array([[2]])

        Examples
        --------

        Basic usage:

        >>> G = nx.path_graph(4)
        >>> A = nx.to_scipy_sparse_array(G)
        >>> A  # doctest: +SKIP
        <Compressed Sparse Row sparse array of dtype 'int64'
            with 6 stored elements and shape (4, 4)>

        >>> A.toarray()
        array([[0, 1, 0, 0],
               [1, 0, 1, 0],
               [0, 1, 0, 1],
               [0, 0, 1, 0]])

        .. note:: The `toarray` method is used in these examples to better visualize
           the adjacancy matrix. For a dense representation of the adjaceny matrix,
           use `to_numpy_array` instead.

        Directed graphs:

        >>> G = nx.DiGraph([(0, 1), (1, 2), (2, 3)])
        >>> nx.to_scipy_sparse_array(G).toarray()
        array([[0, 1, 0, 0],
               [0, 0, 1, 0],
               [0, 0, 0, 1],
               [0, 0, 0, 0]])

        >>> H = G.reverse()
        >>> H.edges
        OutEdgeView([(1, 0), (2, 1), (3, 2)])
        >>> nx.to_scipy_sparse_array(H).toarray()
        array([[0, 0, 0, 0],
               [1, 0, 0, 0],
               [0, 1, 0, 0],
               [0, 0, 1, 0]])

        By default, the order of the rows/columns of the adjacency matrix is determined
        by the ordering of the nodes in `G`:

        >>> G = nx.Graph()
        >>> G.add_nodes_from([3, 5, 0, 1])
        >>> G.add_edges_from([(1, 3), (1, 5)])
        >>> nx.to_scipy_sparse_array(G).toarray()
        array([[0, 0, 0, 1],
               [0, 0, 0, 1],
               [0, 0, 0, 0],
               [1, 1, 0, 0]])

        The ordering of the rows can be changed with `nodelist`:

        >>> ordered = [0, 1, 3, 5]
        >>> nx.to_scipy_sparse_array(G, nodelist=ordered).toarray()
        array([[0, 0, 0, 0],
               [0, 0, 1, 1],
               [0, 1, 0, 0],
               [0, 1, 0, 0]])

        If `nodelist` contains a subset of the nodes in `G`, the adjacency matrix
        for the node-induced subgraph is produced:

        >>> nx.to_scipy_sparse_array(G, nodelist=[1, 3, 5]).toarray()
        array([[0, 1, 1],
               [1, 0, 0],
               [1, 0, 0]])

        The values of the adjacency matrix are drawn from the edge attribute
        specified by the `weight` parameter:

        >>> G = nx.path_graph(4)
        >>> nx.set_edge_attributes(
        ...     G, values={(0, 1): 1, (1, 2): 10, (2, 3): 2}, name="weight"
        ... )
        >>> nx.set_edge_attributes(
        ...     G, values={(0, 1): 50, (1, 2): 35, (2, 3): 10}, name="capacity"
        ... )
        >>> nx.to_scipy_sparse_array(G).toarray()  # Default weight="weight"
        array([[ 0,  1,  0,  0],
               [ 1,  0, 10,  0],
               [ 0, 10,  0,  2],
               [ 0,  0,  2,  0]])
        >>> nx.to_scipy_sparse_array(G, weight="capacity").toarray()
        array([[ 0, 50,  0,  0],
               [50,  0, 35,  0],
               [ 0, 35,  0, 10],
               [ 0,  0, 10,  0]])

        Any edges that don't have a `weight` attribute default to 1:

        >>> G[1][2].pop("capacity")
        35
        >>> nx.to_scipy_sparse_array(G, weight="capacity").toarray()
        array([[ 0, 50,  0,  0],
               [50,  0,  1,  0],
               [ 0,  1,  0, 10],
               [ 0,  0, 10,  0]])

        When `G` is a multigraph, the values in the adjacency matrix are given by
        the sum of the `weight` edge attribute over each edge key:

        >>> G = nx.MultiDiGraph([(0, 1), (0, 1), (0, 1), (2, 0)])
        >>> nx.to_scipy_sparse_array(G).toarray()
        array([[0, 3, 0],
               [0, 0, 0],
               [1, 0, 0]])

        References
        ----------
        .. [1] Scipy Dev. References, "Sparse Arrays",
           https://docs.scipy.org/doc/scipy/reference/sparse.html

DATA
    __all__ = ['from_pandas_adjacency', 'to_pandas_adjacency', 'from_panda...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\convert_matrix.py

networkx.convert_node_labels_to_integers
Python Library Documentation: function convert_node_labels_to_integers in module networkx.relabel

convert_node_labels_to_integers(G, first_label=0, ordering='default', label_attribute=None, *, backend=None, **backend_kwargs)
    Returns a copy of the graph G with the nodes relabeled using
    consecutive integers.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    first_label : int, optional (default=0)
       An integer specifying the starting offset in numbering nodes.
       The new integer labels are numbered first_label, ..., n-1+first_label.

    ordering : string
       "default" : inherit node ordering from G.nodes()
       "sorted"  : inherit node ordering from sorted(G.nodes())
       "increasing degree" : nodes are sorted by increasing degree
       "decreasing degree" : nodes are sorted by decreasing degree

    label_attribute : string, optional (default=None)
       Name of node attribute to store old label.  If None no attribute
       is created.

    Notes
    -----
    Node and edge attribute data are copied to the new (relabeled) graph.

    There is no guarantee that the relabeling of nodes to integers will
    give the same two integers for two (even identical graphs).
    Use the `ordering` argument to try to preserve the order.

    See Also
    --------
    relabel_nodes
networkx.core
Python Library Documentation: module networkx.algorithms.core in networkx.algorithms

NAME
    networkx.algorithms.core - Find the k-cores of a graph.

DESCRIPTION
    The k-core is found by recursively pruning nodes with degrees less than k.

    See the following references for details:

    An O(m) Algorithm for Cores Decomposition of Networks
    Vladimir Batagelj and Matjaz Zaversnik, 2003.
    https://arxiv.org/abs/cs.DS/0310049

    Generalized Cores
    Vladimir Batagelj and Matjaz Zaversnik, 2002.
    https://arxiv.org/pdf/cs/0202039

    For directed graphs a more general notion is that of D-cores which
    looks at (k, l) restrictions on (in, out) degree. The (k, k) D-core
    is the k-core.

    D-cores: Measuring Collaboration of Directed Graphs Based on Degeneracy
    Christos Giatsidis, Dimitrios M. Thilikos, Michalis Vazirgiannis, ICDM 2011.
    http://www.graphdegeneracy.org/dcores_ICDM_2011.pdf

    Multi-scale structure and topological anomaly detection via a new network statistic: The onion decomposition
    L. Hébert-Dufresne, J. A. Grochow, and A. Allard
    Scientific Reports 6, 31708 (2016)
    http://doi.org/10.1038/srep31708

FUNCTIONS
    core_number(G, *, backend=None, **backend_kwargs)
        Returns the core number for each node.

        A k-core is a maximal subgraph that contains nodes of degree k or more.

        The core number of a node is the largest value k of a k-core containing
        that node.

        Parameters
        ----------
        G : NetworkX graph
           An undirected or directed graph

        Returns
        -------
        core_number : dictionary
           A dictionary keyed by node to the core number.

        Raises
        ------
        NetworkXNotImplemented
            If `G` is a multigraph or contains self loops.

        Notes
        -----
        For directed graphs the node degree is defined to be the
        in-degree + out-degree.

        Examples
        --------
        >>> degrees = [0, 1, 2, 2, 2, 2, 3]
        >>> H = nx.havel_hakimi_graph(degrees)
        >>> nx.core_number(H)
        {0: 1, 1: 2, 2: 2, 3: 2, 4: 1, 5: 2, 6: 0}
        >>> G = nx.DiGraph()
        >>> G.add_edges_from([(1, 2), (2, 1), (2, 3), (2, 4), (3, 4), (4, 3)])
        >>> nx.core_number(G)
        {1: 2, 2: 2, 3: 2, 4: 2}

        References
        ----------
        .. [1] An O(m) Algorithm for Cores Decomposition of Networks
           Vladimir Batagelj and Matjaz Zaversnik, 2003.
           https://arxiv.org/abs/cs.DS/0310049

    k_core(G, k=None, core_number=None, *, backend=None, **backend_kwargs)
        Returns the k-core of G.

        A k-core is a maximal subgraph that contains nodes of degree `k` or more.

        .. deprecated:: 3.3
           `k_core` will not accept `MultiGraph` objects in version 3.5.

        Parameters
        ----------
        G : NetworkX graph
          A graph or directed graph
        k : int, optional
          The order of the core. If not specified return the main core.
        core_number : dictionary, optional
          Precomputed core numbers for the graph G.

        Returns
        -------
        G : NetworkX graph
          The k-core subgraph

        Raises
        ------
        NetworkXNotImplemented
          The k-core is not defined for multigraphs or graphs with self loops.

        Notes
        -----
        The main core is the core with `k` as the largest core_number.

        For directed graphs the node degree is defined to be the
        in-degree + out-degree.

        Graph, node, and edge attributes are copied to the subgraph.

        Examples
        --------
        >>> degrees = [0, 1, 2, 2, 2, 2, 3]
        >>> H = nx.havel_hakimi_graph(degrees)
        >>> H.degree
        DegreeView({0: 1, 1: 2, 2: 2, 3: 2, 4: 2, 5: 3, 6: 0})
        >>> nx.k_core(H).nodes
        NodeView((1, 2, 3, 5))

        See Also
        --------
        core_number

        References
        ----------
        .. [1] An O(m) Algorithm for Cores Decomposition of Networks
           Vladimir Batagelj and Matjaz Zaversnik,  2003.
           https://arxiv.org/abs/cs.DS/0310049

    k_corona(G, k, core_number=None, *, backend=None, **backend_kwargs)
        Returns the k-corona of G.

        The k-corona is the subgraph of nodes in the k-core which have
        exactly k neighbors in the k-core.

        .. deprecated:: 3.3
           `k_corona` will not accept `MultiGraph` objects in version 3.5.

        Parameters
        ----------
        G : NetworkX graph
           A graph or directed graph
        k : int
           The order of the corona.
        core_number : dictionary, optional
           Precomputed core numbers for the graph G.

        Returns
        -------
        G : NetworkX graph
           The k-corona subgraph

        Raises
        ------
        NetworkXNotImplemented
            The k-corona is not defined for multigraphs or graphs with self loops.

        Notes
        -----
        For directed graphs the node degree is defined to be the
        in-degree + out-degree.

        Graph, node, and edge attributes are copied to the subgraph.

        Examples
        --------
        >>> degrees = [0, 1, 2, 2, 2, 2, 3]
        >>> H = nx.havel_hakimi_graph(degrees)
        >>> H.degree
        DegreeView({0: 1, 1: 2, 2: 2, 3: 2, 4: 2, 5: 3, 6: 0})
        >>> nx.k_corona(H, k=2).nodes
        NodeView((1, 2, 3, 5))

        See Also
        --------
        core_number

        References
        ----------
        .. [1]  k -core (bootstrap) percolation on complex networks:
           Critical phenomena and nonlocal effects,
           A. V. Goltsev, S. N. Dorogovtsev, and J. F. F. Mendes,
           Phys. Rev. E 73, 056101 (2006)
           http://link.aps.org/doi/10.1103/PhysRevE.73.056101

    k_crust(G, k=None, core_number=None, *, backend=None, **backend_kwargs)
        Returns the k-crust of G.

        The k-crust is the graph G with the edges of the k-core removed
        and isolated nodes found after the removal of edges are also removed.

        .. deprecated:: 3.3
           `k_crust` will not accept `MultiGraph` objects in version 3.5.

        Parameters
        ----------
        G : NetworkX graph
           A graph or directed graph.
        k : int, optional
          The order of the shell. If not specified return the main crust.
        core_number : dictionary, optional
          Precomputed core numbers for the graph G.

        Returns
        -------
        G : NetworkX graph
           The k-crust subgraph

        Raises
        ------
        NetworkXNotImplemented
            The k-crust is not implemented for multigraphs or graphs with self loops.

        Notes
        -----
        This definition of k-crust is different than the definition in [1]_.
        The k-crust in [1]_ is equivalent to the k+1 crust of this algorithm.

        For directed graphs the node degree is defined to be the
        in-degree + out-degree.

        Graph, node, and edge attributes are copied to the subgraph.

        Examples
        --------
        >>> degrees = [0, 1, 2, 2, 2, 2, 3]
        >>> H = nx.havel_hakimi_graph(degrees)
        >>> H.degree
        DegreeView({0: 1, 1: 2, 2: 2, 3: 2, 4: 2, 5: 3, 6: 0})
        >>> nx.k_crust(H, k=1).nodes
        NodeView((0, 4, 6))

        See Also
        --------
        core_number

        References
        ----------
        .. [1] A model of Internet topology using k-shell decomposition
           Shai Carmi, Shlomo Havlin, Scott Kirkpatrick, Yuval Shavitt,
           and Eran Shir, PNAS  July 3, 2007   vol. 104  no. 27  11150-11154
           http://www.pnas.org/content/104/27/11150.full

    k_shell(G, k=None, core_number=None, *, backend=None, **backend_kwargs)
        Returns the k-shell of G.

        The k-shell is the subgraph induced by nodes with core number k.
        That is, nodes in the k-core that are not in the (k+1)-core.

        .. deprecated:: 3.3
           `k_shell` will not accept `MultiGraph` objects in version 3.5.

        Parameters
        ----------
        G : NetworkX graph
          A graph or directed graph.
        k : int, optional
          The order of the shell. If not specified return the outer shell.
        core_number : dictionary, optional
          Precomputed core numbers for the graph G.


        Returns
        -------
        G : NetworkX graph
           The k-shell subgraph

        Raises
        ------
        NetworkXNotImplemented
            The k-shell is not implemented for multigraphs or graphs with self loops.

        Notes
        -----
        This is similar to k_corona but in that case only neighbors in the
        k-core are considered.

        For directed graphs the node degree is defined to be the
        in-degree + out-degree.

        Graph, node, and edge attributes are copied to the subgraph.

        Examples
        --------
        >>> degrees = [0, 1, 2, 2, 2, 2, 3]
        >>> H = nx.havel_hakimi_graph(degrees)
        >>> H.degree
        DegreeView({0: 1, 1: 2, 2: 2, 3: 2, 4: 2, 5: 3, 6: 0})
        >>> nx.k_shell(H, k=1).nodes
        NodeView((0, 4))

        See Also
        --------
        core_number
        k_corona


        References
        ----------
        .. [1] A model of Internet topology using k-shell decomposition
           Shai Carmi, Shlomo Havlin, Scott Kirkpatrick, Yuval Shavitt,
           and Eran Shir, PNAS  July 3, 2007   vol. 104  no. 27  11150-11154
           http://www.pnas.org/content/104/27/11150.full

    k_truss(G, k, *, backend=None, **backend_kwargs)
        Returns the k-truss of `G`.

        The k-truss is the maximal induced subgraph of `G` which contains at least
        three vertices where every edge is incident to at least `k-2` triangles.

        Parameters
        ----------
        G : NetworkX graph
          An undirected graph
        k : int
          The order of the truss

        Returns
        -------
        H : NetworkX graph
          The k-truss subgraph

        Raises
        ------
        NetworkXNotImplemented
          If `G` is a multigraph or directed graph or if it contains self loops.

        Notes
        -----
        A k-clique is a (k-2)-truss and a k-truss is a (k+1)-core.

        Graph, node, and edge attributes are copied to the subgraph.

        K-trusses were originally defined in [2] which states that the k-truss
        is the maximal induced subgraph where each edge belongs to at least
        `k-2` triangles. A more recent paper, [1], uses a slightly different
        definition requiring that each edge belong to at least `k` triangles.
        This implementation uses the original definition of `k-2` triangles.

        Examples
        --------
        >>> degrees = [0, 1, 2, 2, 2, 2, 3]
        >>> H = nx.havel_hakimi_graph(degrees)
        >>> H.degree
        DegreeView({0: 1, 1: 2, 2: 2, 3: 2, 4: 2, 5: 3, 6: 0})
        >>> nx.k_truss(H, k=2).nodes
        NodeView((0, 1, 2, 3, 4, 5))

        References
        ----------
        .. [1] Bounds and Algorithms for k-truss. Paul Burkhardt, Vance Faber,
           David G. Harris, 2018. https://arxiv.org/abs/1806.05523v2
        .. [2] Trusses: Cohesive Subgraphs for Social Network Analysis. Jonathan
           Cohen, 2005.

    onion_layers(G, *, backend=None, **backend_kwargs)
        Returns the layer of each vertex in an onion decomposition of the graph.

        The onion decomposition refines the k-core decomposition by providing
        information on the internal organization of each k-shell. It is usually
        used alongside the `core numbers`.

        Parameters
        ----------
        G : NetworkX graph
            An undirected graph without self loops.

        Returns
        -------
        od_layers : dictionary
            A dictionary keyed by node to the onion layer. The layers are
            contiguous integers starting at 1.

        Raises
        ------
        NetworkXNotImplemented
            If `G` is a multigraph or directed graph or if it contains self loops.

        Examples
        --------
        >>> degrees = [0, 1, 2, 2, 2, 2, 3]
        >>> H = nx.havel_hakimi_graph(degrees)
        >>> H.degree
        DegreeView({0: 1, 1: 2, 2: 2, 3: 2, 4: 2, 5: 3, 6: 0})
        >>> nx.onion_layers(H)
        {6: 1, 0: 2, 4: 3, 1: 4, 2: 4, 3: 4, 5: 4}

        See Also
        --------
        core_number

        References
        ----------
        .. [1] Multi-scale structure and topological anomaly detection via a new
           network statistic: The onion decomposition
           L. Hébert-Dufresne, J. A. Grochow, and A. Allard
           Scientific Reports 6, 31708 (2016)
           http://doi.org/10.1038/srep31708
        .. [2] Percolation and the effective structure of complex networks
           A. Allard and L. Hébert-Dufresne
           Physical Review X 9, 011023 (2019)
           http://doi.org/10.1103/PhysRevX.9.011023

DATA
    __all__ = ['core_number', 'k_core', 'k_shell', 'k_crust', 'k_corona', ...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\core.py

networkx.core_number
Python Library Documentation: function core_number in module networkx.algorithms.core

core_number(G, *, backend=None, **backend_kwargs)
    Returns the core number for each node.

    A k-core is a maximal subgraph that contains nodes of degree k or more.

    The core number of a node is the largest value k of a k-core containing
    that node.

    Parameters
    ----------
    G : NetworkX graph
       An undirected or directed graph

    Returns
    -------
    core_number : dictionary
       A dictionary keyed by node to the core number.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a multigraph or contains self loops.

    Notes
    -----
    For directed graphs the node degree is defined to be the
    in-degree + out-degree.

    Examples
    --------
    >>> degrees = [0, 1, 2, 2, 2, 2, 3]
    >>> H = nx.havel_hakimi_graph(degrees)
    >>> nx.core_number(H)
    {0: 1, 1: 2, 2: 2, 3: 2, 4: 1, 5: 2, 6: 0}
    >>> G = nx.DiGraph()
    >>> G.add_edges_from([(1, 2), (2, 1), (2, 3), (2, 4), (3, 4), (4, 3)])
    >>> nx.core_number(G)
    {1: 2, 2: 2, 3: 2, 4: 2}

    References
    ----------
    .. [1] An O(m) Algorithm for Cores Decomposition of Networks
       Vladimir Batagelj and Matjaz Zaversnik, 2003.
       https://arxiv.org/abs/cs.DS/0310049
networkx.coreviews
Python Library Documentation: module networkx.classes.coreviews in networkx.classes

NAME
    networkx.classes.coreviews

DESCRIPTION
    Views of core data structures such as nested Mappings (e.g. dict-of-dicts).
    These ``Views`` often restrict element access, with either the entire view or
    layers of nested mappings being read-only.

CLASSES
    collections.abc.Mapping(collections.abc.Collection)
        AtlasView
            AdjacencyView
                MultiAdjacencyView
        FilterAdjacency
            FilterMultiAdjacency
            FilterMultiInner
        FilterAtlas
        UnionAdjacency
            UnionMultiAdjacency
        UnionAtlas
            UnionMultiInner

    class AdjacencyView(AtlasView)
     |  AdjacencyView(d)
     |
     |  An AdjacencyView is a Read-only Map of Maps of Maps.
     |
     |  It is a View into a dict-of-dict-of-dict data structure.
     |  The inner level of dict is read-write. But the
     |  outer levels are read-only.
     |
     |  See Also
     |  ========
     |  AtlasView: View into dict-of-dict
     |  MultiAdjacencyView: View into dict-of-dict-of-dict-of-dict
     |
     |  Method resolution order:
     |      AdjacencyView
     |      AtlasView
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, name)
     |
     |  copy(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from AtlasView:
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, d)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  __contains__(self, key)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __hash__ = None
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class AtlasView(collections.abc.Mapping)
     |  AtlasView(d)
     |
     |  An AtlasView is a Read-only Mapping of Mappings.
     |
     |  It is a View into a dict-of-dict data structure.
     |  The inner level of dict is read-write. But the
     |  outer level is read-only.
     |
     |  See Also
     |  ========
     |  AdjacencyView: View into dict-of-dict-of-dict
     |  MultiAdjacencyView: View into dict-of-dict-of-dict-of-dict
     |
     |  Method resolution order:
     |      AtlasView
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, key)
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, d)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  copy(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  __contains__(self, key)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __hash__ = None
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class FilterAdjacency(collections.abc.Mapping)
     |  FilterAdjacency(d, NODE_OK, EDGE_OK)
     |
     |  A read-only Mapping of Mappings with filtering criteria for nodes and edges.
     |
     |  It is a view into a dict-of-dict-of-dict data structure, and it selects nodes
     |  and edges that satisfy specific criteria defined by ``NODE_OK`` and ``EDGE_OK``,
     |  respectively.
     |
     |  See Also
     |  ========
     |  FilterAtlas
     |  FilterMultiInner
     |  FilterMultiAdjacency
     |
     |  Method resolution order:
     |      FilterAdjacency
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, node)
     |
     |  __init__(self, d, NODE_OK, EDGE_OK)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors defined here:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  __contains__(self, key)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __hash__ = None
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class FilterAtlas(collections.abc.Mapping)
     |  FilterAtlas(d, NODE_OK)
     |
     |  A read-only Mapping of Mappings with filtering criteria for nodes.
     |
     |  It is a view into a dict-of-dict data structure, and it selects only
     |  nodes that meet the criteria defined by ``NODE_OK``.
     |
     |  See Also
     |  ========
     |  FilterAdjacency
     |  FilterMultiInner
     |  FilterMultiAdjacency
     |
     |  Method resolution order:
     |      FilterAtlas
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, key)
     |
     |  __init__(self, d, NODE_OK)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors defined here:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  __contains__(self, key)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __hash__ = None
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class FilterMultiAdjacency(FilterAdjacency)
     |  FilterMultiAdjacency(d, NODE_OK, EDGE_OK)
     |
     |  A read-only Mapping of Mappings with filtering criteria
     |  for nodes and edges.
     |
     |  It is a view into a dict-of-dict-of-dict-of-dict data structure,
     |  and it selects nodes and edges that satisfy specific criteria
     |  defined by ``NODE_OK`` and ``EDGE_OK``, respectively.
     |
     |  See Also
     |  ========
     |  FilterAtlas
     |  FilterAdjacency
     |  FilterMultiInner
     |
     |  Method resolution order:
     |      FilterMultiAdjacency
     |      FilterAdjacency
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, node)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from FilterAdjacency:
     |
     |  __init__(self, d, NODE_OK, EDGE_OK)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from FilterAdjacency:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  __contains__(self, key)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __hash__ = None
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class FilterMultiInner(FilterAdjacency)
     |  FilterMultiInner(d, NODE_OK, EDGE_OK)
     |
     |  A read-only Mapping of Mappings with filtering criteria for nodes and edges.
     |
     |  It is a view into a dict-of-dict-of-dict-of-dict data structure, and it selects nodes
     |  and edges that meet specific criteria defined by ``NODE_OK`` and ``EDGE_OK``.
     |
     |  See Also
     |  ========
     |  FilterAtlas
     |  FilterAdjacency
     |  FilterMultiAdjacency
     |
     |  Method resolution order:
     |      FilterMultiInner
     |      FilterAdjacency
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, nbr)
     |
     |  __iter__(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from FilterAdjacency:
     |
     |  __init__(self, d, NODE_OK, EDGE_OK)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from FilterAdjacency:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  __contains__(self, key)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __hash__ = None
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class MultiAdjacencyView(AdjacencyView)
     |  MultiAdjacencyView(d)
     |
     |  An MultiAdjacencyView is a Read-only Map of Maps of Maps of Maps.
     |
     |  It is a View into a dict-of-dict-of-dict-of-dict data structure.
     |  The inner level of dict is read-write. But the
     |  outer levels are read-only.
     |
     |  See Also
     |  ========
     |  AtlasView: View into dict-of-dict
     |  AdjacencyView: View into dict-of-dict-of-dict
     |
     |  Method resolution order:
     |      MultiAdjacencyView
     |      AdjacencyView
     |      AtlasView
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, name)
     |
     |  copy(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from AtlasView:
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, d)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  __contains__(self, key)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __hash__ = None
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class UnionAdjacency(collections.abc.Mapping)
     |  UnionAdjacency(succ, pred)
     |
     |  A read-only union of dict Adjacencies as a Map of Maps of Maps.
     |
     |  The two input dict-of-dict-of-dicts represent the union of
     |  `G.succ` and `G.pred`. Return values are UnionAtlas
     |  The inner level of dict is read-write. But the
     |  middle and outer levels are read-only.
     |
     |  succ : a dict-of-dict-of-dict {node: nbrdict}
     |  pred : a dict-of-dict-of-dict {node: nbrdict}
     |  The keys for the two dicts should be the same
     |
     |  See Also
     |  ========
     |  UnionAtlas: View into dict-of-dict
     |  UnionMultiAdjacency: View into dict-of-dict-of-dict-of-dict
     |
     |  Method resolution order:
     |      UnionAdjacency
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, nbr)
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, succ, pred)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  copy(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  __contains__(self, key)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __hash__ = None
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class UnionAtlas(collections.abc.Mapping)
     |  UnionAtlas(succ, pred)
     |
     |  A read-only union of two atlases (dict-of-dict).
     |
     |  The two dict-of-dicts represent the inner dict of
     |  an Adjacency:  `G.succ[node]` and `G.pred[node]`.
     |  The inner level of dict of both hold attribute key:value
     |  pairs and is read-write. But the outer level is read-only.
     |
     |  See Also
     |  ========
     |  UnionAdjacency: View into dict-of-dict-of-dict
     |  UnionMultiAdjacency: View into dict-of-dict-of-dict-of-dict
     |
     |  Method resolution order:
     |      UnionAtlas
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, key)
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, succ, pred)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  copy(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  __contains__(self, key)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __hash__ = None
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class UnionMultiAdjacency(UnionAdjacency)
     |  UnionMultiAdjacency(succ, pred)
     |
     |  A read-only union of two dict MultiAdjacencies.
     |
     |  The two input dict-of-dict-of-dict-of-dicts represent the union of
     |  `G.succ` and `G.pred` for MultiDiGraphs. Return values are UnionAdjacency.
     |  The inner level of dict is read-write. But the outer levels are read-only.
     |
     |  See Also
     |  ========
     |  UnionAtlas:  View into dict-of-dict
     |  UnionMultiInner:  View into dict-of-dict-of-dict
     |
     |  Method resolution order:
     |      UnionMultiAdjacency
     |      UnionAdjacency
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, node)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from UnionAdjacency:
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, succ, pred)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  copy(self)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  __contains__(self, key)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __hash__ = None
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class UnionMultiInner(UnionAtlas)
     |  UnionMultiInner(succ, pred)
     |
     |  A read-only union of two inner dicts of MultiAdjacencies.
     |
     |  The two input dict-of-dict-of-dicts represent the union of
     |  `G.succ[node]` and `G.pred[node]` for MultiDiGraphs.
     |  Return values are UnionAtlas.
     |  The inner level of dict is read-write. But the outer levels are read-only.
     |
     |  See Also
     |  ========
     |  UnionAtlas: View into dict-of-dict
     |  UnionAdjacency:  View into dict-of-dict-of-dict
     |  UnionMultiAdjacency:  View into dict-of-dict-of-dict-of-dict
     |
     |  Method resolution order:
     |      UnionMultiInner
     |      UnionAtlas
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, node)
     |
     |  copy(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from UnionAtlas:
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, succ, pred)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  __contains__(self, key)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __hash__ = None
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

DATA
    __all__ = ['AtlasView', 'AdjacencyView', 'MultiAdjacencyView', 'UnionA...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\classes\coreviews.py

networkx.corona_product
Python Library Documentation: function corona_product in module networkx.algorithms.operators.product

corona_product(G, H, *, backend=None, **backend_kwargs)
    Returns the Corona product of G and H.

    The corona product of $G$ and $H$ is the graph $C = G \circ H$ obtained by
    taking one copy of $G$, called the center graph, $|V(G)|$ copies of $H$,
    called the outer graph, and making the $i$-th vertex of $G$ adjacent to
    every vertex of the $i$-th copy of $H$, where $1 ≤ i ≤ |V(G)|$.

    Parameters
    ----------
    G, H: NetworkX graphs
        The graphs to take the carona product of.
        `G` is the center graph and `H` is the outer graph

    Returns
    -------
    C: NetworkX graph
        The Corona product of G and H.

    Raises
    ------
    NetworkXError
        If G and H are not both directed or both undirected.

    Examples
    --------
    >>> G = nx.cycle_graph(4)
    >>> H = nx.path_graph(2)
    >>> C = nx.corona_product(G, H)
    >>> list(C)
    [0, 1, 2, 3, (0, 0), (0, 1), (1, 0), (1, 1), (2, 0), (2, 1), (3, 0), (3, 1)]
    >>> print(C)
    Graph with 12 nodes and 16 edges

    References
    ----------
    [1] M. Tavakoli, F. Rahbarnia, and A. R. Ashrafi,
        "Studying the corona product of graphs under some graph invariants,"
        Transactions on Combinatorics, vol. 3, no. 3, pp. 43–49, Sep. 2014,
        doi: 10.22108/toc.2014.5542.
    [2] A. Faraji, "Corona Product in Graph Theory," Ali Faraji, May 11, 2021.
        https://blog.alifaraji.ir/math/graph-theory/corona-product.html (accessed Dec. 07, 2021).
networkx.correlation
Python Library Documentation: module networkx.algorithms.assortativity.correlation in networkx.algorithms.assortativity

NAME
    networkx.algorithms.assortativity.correlation - Node assortativity coefficients and correlation measures.

FUNCTIONS
    attribute_assortativity_coefficient(G, attribute, nodes=None, *, backend=None, **backend_kwargs)
        Compute assortativity for node attributes.

        Assortativity measures the similarity of connections
        in the graph with respect to the given attribute.

        Parameters
        ----------
        G : NetworkX graph

        attribute : string
            Node attribute key

        nodes: list or iterable (optional)
            Compute attribute assortativity for nodes in container.
            The default is all nodes.

        Returns
        -------
        r: float
           Assortativity of graph for given attribute

        Examples
        --------
        >>> G = nx.Graph()
        >>> G.add_nodes_from([0, 1], color="red")
        >>> G.add_nodes_from([2, 3], color="blue")
        >>> G.add_edges_from([(0, 1), (2, 3)])
        >>> print(nx.attribute_assortativity_coefficient(G, "color"))
        1.0

        Notes
        -----
        This computes Eq. (2) in Ref. [1]_ , (trace(M)-sum(M^2))/(1-sum(M^2)),
        where M is the joint probability distribution (mixing matrix)
        of the specified attribute.

        References
        ----------
        .. [1] M. E. J. Newman, Mixing patterns in networks,
           Physical Review E, 67 026126, 2003

    degree_assortativity_coefficient(G, x='out', y='in', weight=None, nodes=None, *, backend=None, **backend_kwargs)
        Compute degree assortativity of graph.

        Assortativity measures the similarity of connections
        in the graph with respect to the node degree.

        Parameters
        ----------
        G : NetworkX graph

        x: string ('in','out')
           The degree type for source node (directed graphs only).

        y: string ('in','out')
           The degree type for target node (directed graphs only).

        weight: string or None, optional (default=None)
           The edge attribute that holds the numerical value used
           as a weight.  If None, then each edge has weight 1.
           The degree is the sum of the edge weights adjacent to the node.

        nodes: list or iterable (optional)
            Compute degree assortativity only for nodes in container.
            The default is all nodes.

        Returns
        -------
        r : float
           Assortativity of graph by degree.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> r = nx.degree_assortativity_coefficient(G)
        >>> print(f"{r:3.1f}")
        -0.5

        See Also
        --------
        attribute_assortativity_coefficient
        numeric_assortativity_coefficient
        degree_mixing_dict
        degree_mixing_matrix

        Notes
        -----
        This computes Eq. (21) in Ref. [1]_ , where e is the joint
        probability distribution (mixing matrix) of the degrees.  If G is
        directed than the matrix e is the joint probability of the
        user-specified degree type for the source and target.

        References
        ----------
        .. [1] M. E. J. Newman, Mixing patterns in networks,
           Physical Review E, 67 026126, 2003
        .. [2] Foster, J.G., Foster, D.V., Grassberger, P. & Paczuski, M.
           Edge direction and the structure of networks, PNAS 107, 10815-20 (2010).

    degree_pearson_correlation_coefficient(G, x='out', y='in', weight=None, nodes=None, *, backend=None, **backend_kwargs)
        Compute degree assortativity of graph.

        Assortativity measures the similarity of connections
        in the graph with respect to the node degree.

        This is the same as degree_assortativity_coefficient but uses the
        potentially faster scipy.stats.pearsonr function.

        Parameters
        ----------
        G : NetworkX graph

        x: string ('in','out')
           The degree type for source node (directed graphs only).

        y: string ('in','out')
           The degree type for target node (directed graphs only).

        weight: string or None, optional (default=None)
           The edge attribute that holds the numerical value used
           as a weight.  If None, then each edge has weight 1.
           The degree is the sum of the edge weights adjacent to the node.

        nodes: list or iterable (optional)
            Compute pearson correlation of degrees only for specified nodes.
            The default is all nodes.

        Returns
        -------
        r : float
           Assortativity of graph by degree.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> r = nx.degree_pearson_correlation_coefficient(G)
        >>> print(f"{r:3.1f}")
        -0.5

        Notes
        -----
        This calls scipy.stats.pearsonr.

        References
        ----------
        .. [1] M. E. J. Newman, Mixing patterns in networks
               Physical Review E, 67 026126, 2003
        .. [2] Foster, J.G., Foster, D.V., Grassberger, P. & Paczuski, M.
           Edge direction and the structure of networks, PNAS 107, 10815-20 (2010).

    numeric_assortativity_coefficient(G, attribute, nodes=None, *, backend=None, **backend_kwargs)
        Compute assortativity for numerical node attributes.

        Assortativity measures the similarity of connections
        in the graph with respect to the given numeric attribute.

        Parameters
        ----------
        G : NetworkX graph

        attribute : string
            Node attribute key.

        nodes: list or iterable (optional)
            Compute numeric assortativity only for attributes of nodes in
            container. The default is all nodes.

        Returns
        -------
        r: float
           Assortativity of graph for given attribute

        Examples
        --------
        >>> G = nx.Graph()
        >>> G.add_nodes_from([0, 1], size=2)
        >>> G.add_nodes_from([2, 3], size=3)
        >>> G.add_edges_from([(0, 1), (2, 3)])
        >>> print(nx.numeric_assortativity_coefficient(G, "size"))
        1.0

        Notes
        -----
        This computes Eq. (21) in Ref. [1]_ , which is the Pearson correlation
        coefficient of the specified (scalar valued) attribute across edges.

        References
        ----------
        .. [1] M. E. J. Newman, Mixing patterns in networks
               Physical Review E, 67 026126, 2003

DATA
    __all__ = ['degree_pearson_correlation_coefficient', 'degree_assortati...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\assortativity\correlation.py

networkx.cost_of_flow
Python Library Documentation: function cost_of_flow in module networkx.algorithms.flow.mincost

cost_of_flow(G, flowDict, weight='weight', *, backend=None, **backend_kwargs)
    Compute the cost of the flow given by flowDict on graph G.

    Note that this function does not check for the validity of the
    flow flowDict. This function will fail if the graph G and the
    flow don't have the same edge set.

    Parameters
    ----------
    G : NetworkX graph
        DiGraph on which a minimum cost flow satisfying all demands is
        to be found.

    weight : string
        Edges of the graph G are expected to have an attribute weight
        that indicates the cost incurred by sending one unit of flow on
        that edge. If not present, the weight is considered to be 0.
        Default value: 'weight'.

    flowDict : dictionary
        Dictionary of dictionaries keyed by nodes such that
        flowDict[u][v] is the flow edge (u, v).

    Returns
    -------
    cost : Integer, float
        The total cost of the flow. This is given by the sum over all
        edges of the product of the edge's flow and the edge's weight.

    See also
    --------
    max_flow_min_cost, min_cost_flow, min_cost_flow_cost, network_simplex

    Notes
    -----
    This algorithm is not guaranteed to work if edge weights or demands
    are floating point numbers (overflows and roundoff errors can
    cause problems). As a workaround you can use integer numbers by
    multiplying the relevant edge attributes by a convenient
    constant factor (eg 100).

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_node("a", demand=-5)
    >>> G.add_node("d", demand=5)
    >>> G.add_edge("a", "b", weight=3, capacity=4)
    >>> G.add_edge("a", "c", weight=6, capacity=10)
    >>> G.add_edge("b", "d", weight=1, capacity=9)
    >>> G.add_edge("c", "d", weight=2, capacity=5)
    >>> flowDict = nx.min_cost_flow(G)
    >>> flowDict
    {'a': {'b': 4, 'c': 1}, 'd': {}, 'b': {'d': 4}, 'c': {'d': 1}}
    >>> nx.cost_of_flow(G, flowDict)
    24
networkx.could_be_isomorphic
Python Library Documentation: function could_be_isomorphic in module networkx.algorithms.isomorphism.isomorph

could_be_isomorphic(G1, G2, *, backend=None, **backend_kwargs)
    Returns False if graphs are definitely not isomorphic.
    True does NOT guarantee isomorphism.

    Parameters
    ----------
    G1, G2 : graphs
       The two graphs G1 and G2 must be the same type.

    Notes
    -----
    Checks for matching degree, triangle, and number of cliques sequences.
    The triangle sequence contains the number of triangles each node is part of.
    The clique sequence contains for each node the number of maximal cliques
    involving that node.
networkx.covering
Python Library Documentation: module networkx.algorithms.covering in networkx.algorithms

NAME
    networkx.algorithms.covering - Functions related to graph covers.

FUNCTIONS
    is_edge_cover(G, cover, *, backend=None, **backend_kwargs)
        Decides whether a set of edges is a valid edge cover of the graph.

        Given a set of edges, whether it is an edge covering can
        be decided if we just check whether all nodes of the graph
        has an edge from the set, incident on it.

        Parameters
        ----------
        G : NetworkX graph
            An undirected bipartite graph.

        cover : set
            Set of edges to be checked.

        Returns
        -------
        bool
            Whether the set of edges is a valid edge cover of the graph.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
        >>> cover = {(2, 1), (3, 0)}
        >>> nx.is_edge_cover(G, cover)
        True

        Notes
        -----
        An edge cover of a graph is a set of edges such that every node of
        the graph is incident to at least one edge of the set.

    min_edge_cover(G, matching_algorithm=None, *, backend=None, **backend_kwargs)
        Returns the min cardinality edge cover of the graph as a set of edges.

        A smallest edge cover can be found in polynomial time by finding
        a maximum matching and extending it greedily so that all nodes
        are covered. This function follows that process. A maximum matching
        algorithm can be specified for the first step of the algorithm.
        The resulting set may return a set with one 2-tuple for each edge,
        (the usual case) or with both 2-tuples `(u, v)` and `(v, u)` for
        each edge. The latter is only done when a bipartite matching algorithm
        is specified as `matching_algorithm`.

        Parameters
        ----------
        G : NetworkX graph
            An undirected graph.

        matching_algorithm : function
            A function that returns a maximum cardinality matching for `G`.
            The function must take one input, the graph `G`, and return
            either a set of edges (with only one direction for the pair of nodes)
            or a dictionary mapping each node to its mate. If not specified,
            :func:`~networkx.algorithms.matching.max_weight_matching` is used.
            Common bipartite matching functions include
            :func:`~networkx.algorithms.bipartite.matching.hopcroft_karp_matching`
            or
            :func:`~networkx.algorithms.bipartite.matching.eppstein_matching`.

        Returns
        -------
        min_cover : set

            A set of the edges in a minimum edge cover in the form of tuples.
            It contains only one of the equivalent 2-tuples `(u, v)` and `(v, u)`
            for each edge. If a bipartite method is used to compute the matching,
            the returned set contains both the 2-tuples `(u, v)` and `(v, u)`
            for each edge of a minimum edge cover.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
        >>> sorted(nx.min_edge_cover(G))
        [(2, 1), (3, 0)]

        Notes
        -----
        An edge cover of a graph is a set of edges such that every node of
        the graph is incident to at least one edge of the set.
        The minimum edge cover is an edge covering of smallest cardinality.

        Due to its implementation, the worst-case running time of this algorithm
        is bounded by the worst-case running time of the function
        ``matching_algorithm``.

        Minimum edge cover for `G` can also be found using the `min_edge_covering`
        function in :mod:`networkx.algorithms.bipartite.covering` which is
        simply this function with a default matching algorithm of
        :func:`~networkx.algorithms.bipartite.matching.hopcraft_karp_matching`

DATA
    __all__ = ['min_edge_cover', 'is_edge_cover']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\covering.py

networkx.create_empty_copy
Python Library Documentation: function create_empty_copy in module networkx.classes.function

create_empty_copy(G, with_data=True)
    Returns a copy of the graph G with all of the edges removed.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    with_data :  bool (default=True)
       Propagate Graph and Nodes data to the new graph.

    See Also
    --------
    empty_graph
networkx.cubical_graph
Python Library Documentation: function cubical_graph in module networkx.generators.small

cubical_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the 3-regular Platonic Cubical Graph

    The skeleton of the cube (the nodes and edges) form a graph, with 8
    nodes, and 12 edges. It is a special case of the hypercube graph.
    It is one of 5 Platonic graphs, each a skeleton of its
    Platonic solid [1]_.
    Such graphs arise in parallel processing in computers.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        A cubical graph with 8 nodes and 12 edges

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Cube#Cubical_graph
networkx.current_flow_betweenness
Python Library Documentation: module networkx.algorithms.centrality.current_flow_betweenness in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.current_flow_betweenness - Current-flow betweenness centrality measures.

FUNCTIONS
    approximate_current_flow_betweenness_centrality(G, normalized=True, weight=None, dtype=<class 'float'>, solver='full', epsilon=0.5, kmax=10000, seed=None, *, backend=None, **backend_kwargs)
        Compute the approximate current-flow betweenness centrality for nodes.

        Approximates the current-flow betweenness centrality within absolute
        error of epsilon with high probability [1]_.


        Parameters
        ----------
        G : graph
          A NetworkX graph

        normalized : bool, optional (default=True)
          If True the betweenness values are normalized by 2/[(n-1)(n-2)] where
          n is the number of nodes in G.

        weight : string or None, optional (default=None)
          Key for edge data used as the edge weight.
          If None, then use 1 as each edge weight.
          The weight reflects the capacity or the strength of the
          edge.

        dtype : data type (float)
          Default data type for internal matrices.
          Set to np.float32 for lower memory consumption.

        solver : string (default='full')
           Type of linear solver to use for computing the flow matrix.
           Options are "full" (uses most memory), "lu" (recommended), and
           "cg" (uses least memory).

        epsilon: float
            Absolute error tolerance.

        kmax: int
           Maximum number of sample node pairs to use for approximation.

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with betweenness centrality as the value.

        See Also
        --------
        current_flow_betweenness_centrality

        Notes
        -----
        The running time is $O((1/\epsilon^2)m{\sqrt k} \log n)$
        and the space required is $O(m)$ for $n$ nodes and $m$ edges.

        If the edges have a 'weight' attribute they will be used as
        weights in this algorithm.  Unspecified weights are set to 1.

        References
        ----------
        .. [1] Ulrik Brandes and Daniel Fleischer:
           Centrality Measures Based on Current Flow.
           Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
           LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
           https://doi.org/10.1007/978-3-540-31856-9_44

    current_flow_betweenness_centrality(G, normalized=True, weight=None, dtype=<class 'float'>, solver='full', *, backend=None, **backend_kwargs)
        Compute current-flow betweenness centrality for nodes.

        Current-flow betweenness centrality uses an electrical current
        model for information spreading in contrast to betweenness
        centrality which uses shortest paths.

        Current-flow betweenness centrality is also known as
        random-walk betweenness centrality [2]_.

        Parameters
        ----------
        G : graph
          A NetworkX graph

        normalized : bool, optional (default=True)
          If True the betweenness values are normalized by 2/[(n-1)(n-2)] where
          n is the number of nodes in G.

        weight : string or None, optional (default=None)
          Key for edge data used as the edge weight.
          If None, then use 1 as each edge weight.
          The weight reflects the capacity or the strength of the
          edge.

        dtype : data type (float)
          Default data type for internal matrices.
          Set to np.float32 for lower memory consumption.

        solver : string (default='full')
           Type of linear solver to use for computing the flow matrix.
           Options are "full" (uses most memory), "lu" (recommended), and
           "cg" (uses least memory).

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with betweenness centrality as the value.

        See Also
        --------
        approximate_current_flow_betweenness_centrality
        betweenness_centrality
        edge_betweenness_centrality
        edge_current_flow_betweenness_centrality

        Notes
        -----
        Current-flow betweenness can be computed in  $O(I(n-1)+mn \log n)$
        time [1]_, where $I(n-1)$ is the time needed to compute the
        inverse Laplacian.  For a full matrix this is $O(n^3)$ but using
        sparse methods you can achieve $O(nm{\sqrt k})$ where $k$ is the
        Laplacian matrix condition number.

        The space required is $O(nw)$ where $w$ is the width of the sparse
        Laplacian matrix.  Worse case is $w=n$ for $O(n^2)$.

        If the edges have a 'weight' attribute they will be used as
        weights in this algorithm.  Unspecified weights are set to 1.

        References
        ----------
        .. [1] Centrality Measures Based on Current Flow.
           Ulrik Brandes and Daniel Fleischer,
           Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
           LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
           https://doi.org/10.1007/978-3-540-31856-9_44

        .. [2] A measure of betweenness centrality based on random walks,
           M. E. J. Newman, Social Networks 27, 39-54 (2005).

    edge_current_flow_betweenness_centrality(G, normalized=True, weight=None, dtype=<class 'float'>, solver='full', *, backend=None, **backend_kwargs)
        Compute current-flow betweenness centrality for edges.

        Current-flow betweenness centrality uses an electrical current
        model for information spreading in contrast to betweenness
        centrality which uses shortest paths.

        Current-flow betweenness centrality is also known as
        random-walk betweenness centrality [2]_.

        Parameters
        ----------
        G : graph
          A NetworkX graph

        normalized : bool, optional (default=True)
          If True the betweenness values are normalized by 2/[(n-1)(n-2)] where
          n is the number of nodes in G.

        weight : string or None, optional (default=None)
          Key for edge data used as the edge weight.
          If None, then use 1 as each edge weight.
          The weight reflects the capacity or the strength of the
          edge.

        dtype : data type (default=float)
          Default data type for internal matrices.
          Set to np.float32 for lower memory consumption.

        solver : string (default='full')
           Type of linear solver to use for computing the flow matrix.
           Options are "full" (uses most memory), "lu" (recommended), and
           "cg" (uses least memory).

        Returns
        -------
        nodes : dictionary
           Dictionary of edge tuples with betweenness centrality as the value.

        Raises
        ------
        NetworkXError
            The algorithm does not support DiGraphs.
            If the input graph is an instance of DiGraph class, NetworkXError
            is raised.

        See Also
        --------
        betweenness_centrality
        edge_betweenness_centrality
        current_flow_betweenness_centrality

        Notes
        -----
        Current-flow betweenness can be computed in $O(I(n-1)+mn \log n)$
        time [1]_, where $I(n-1)$ is the time needed to compute the
        inverse Laplacian.  For a full matrix this is $O(n^3)$ but using
        sparse methods you can achieve $O(nm{\sqrt k})$ where $k$ is the
        Laplacian matrix condition number.

        The space required is $O(nw)$ where $w$ is the width of the sparse
        Laplacian matrix.  Worse case is $w=n$ for $O(n^2)$.

        If the edges have a 'weight' attribute they will be used as
        weights in this algorithm.  Unspecified weights are set to 1.

        References
        ----------
        .. [1] Centrality Measures Based on Current Flow.
           Ulrik Brandes and Daniel Fleischer,
           Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
           LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
           https://doi.org/10.1007/978-3-540-31856-9_44

        .. [2] A measure of betweenness centrality based on random walks,
           M. E. J. Newman, Social Networks 27, 39-54 (2005).

DATA
    __all__ = ['current_flow_betweenness_centrality', 'approximate_current...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\current_flow_betweenness.py

networkx.current_flow_betweenness_centrality
Python Library Documentation: function current_flow_betweenness_centrality in module networkx.algorithms.centrality.current_flow_betweenness

current_flow_betweenness_centrality(G, normalized=True, weight=None, dtype=<class 'float'>, solver='full', *, backend=None, **backend_kwargs)
    Compute current-flow betweenness centrality for nodes.

    Current-flow betweenness centrality uses an electrical current
    model for information spreading in contrast to betweenness
    centrality which uses shortest paths.

    Current-flow betweenness centrality is also known as
    random-walk betweenness centrality [2]_.

    Parameters
    ----------
    G : graph
      A NetworkX graph

    normalized : bool, optional (default=True)
      If True the betweenness values are normalized by 2/[(n-1)(n-2)] where
      n is the number of nodes in G.

    weight : string or None, optional (default=None)
      Key for edge data used as the edge weight.
      If None, then use 1 as each edge weight.
      The weight reflects the capacity or the strength of the
      edge.

    dtype : data type (float)
      Default data type for internal matrices.
      Set to np.float32 for lower memory consumption.

    solver : string (default='full')
       Type of linear solver to use for computing the flow matrix.
       Options are "full" (uses most memory), "lu" (recommended), and
       "cg" (uses least memory).

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with betweenness centrality as the value.

    See Also
    --------
    approximate_current_flow_betweenness_centrality
    betweenness_centrality
    edge_betweenness_centrality
    edge_current_flow_betweenness_centrality

    Notes
    -----
    Current-flow betweenness can be computed in  $O(I(n-1)+mn \log n)$
    time [1]_, where $I(n-1)$ is the time needed to compute the
    inverse Laplacian.  For a full matrix this is $O(n^3)$ but using
    sparse methods you can achieve $O(nm{\sqrt k})$ where $k$ is the
    Laplacian matrix condition number.

    The space required is $O(nw)$ where $w$ is the width of the sparse
    Laplacian matrix.  Worse case is $w=n$ for $O(n^2)$.

    If the edges have a 'weight' attribute they will be used as
    weights in this algorithm.  Unspecified weights are set to 1.

    References
    ----------
    .. [1] Centrality Measures Based on Current Flow.
       Ulrik Brandes and Daniel Fleischer,
       Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
       LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
       https://doi.org/10.1007/978-3-540-31856-9_44

    .. [2] A measure of betweenness centrality based on random walks,
       M. E. J. Newman, Social Networks 27, 39-54 (2005).
networkx.current_flow_betweenness_centrality_subset
Python Library Documentation: function current_flow_betweenness_centrality_subset in module networkx.algorithms.centrality.current_flow_betweenness_subset

current_flow_betweenness_centrality_subset(G, sources, targets, normalized=True, weight=None, dtype=<class 'float'>, solver='lu', *, backend=None, **backend_kwargs)
    Compute current-flow betweenness centrality for subsets of nodes.

    Current-flow betweenness centrality uses an electrical current
    model for information spreading in contrast to betweenness
    centrality which uses shortest paths.

    Current-flow betweenness centrality is also known as
    random-walk betweenness centrality [2]_.

    Parameters
    ----------
    G : graph
      A NetworkX graph

    sources: list of nodes
      Nodes to use as sources for current

    targets: list of nodes
      Nodes to use as sinks for current

    normalized : bool, optional (default=True)
      If True the betweenness values are normalized by b=b/(n-1)(n-2) where
      n is the number of nodes in G.

    weight : string or None, optional (default=None)
      Key for edge data used as the edge weight.
      If None, then use 1 as each edge weight.
      The weight reflects the capacity or the strength of the
      edge.

    dtype: data type (float)
      Default data type for internal matrices.
      Set to np.float32 for lower memory consumption.

    solver: string (default='lu')
       Type of linear solver to use for computing the flow matrix.
       Options are "full" (uses most memory), "lu" (recommended), and
       "cg" (uses least memory).

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with betweenness centrality as the value.

    See Also
    --------
    approximate_current_flow_betweenness_centrality
    betweenness_centrality
    edge_betweenness_centrality
    edge_current_flow_betweenness_centrality

    Notes
    -----
    Current-flow betweenness can be computed in $O(I(n-1)+mn \log n)$
    time [1]_, where $I(n-1)$ is the time needed to compute the
    inverse Laplacian.  For a full matrix this is $O(n^3)$ but using
    sparse methods you can achieve $O(nm{\sqrt k})$ where $k$ is the
    Laplacian matrix condition number.

    The space required is $O(nw)$ where $w$ is the width of the sparse
    Laplacian matrix.  Worse case is $w=n$ for $O(n^2)$.

    If the edges have a 'weight' attribute they will be used as
    weights in this algorithm.  Unspecified weights are set to 1.

    References
    ----------
    .. [1] Centrality Measures Based on Current Flow.
       Ulrik Brandes and Daniel Fleischer,
       Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
       LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
       https://doi.org/10.1007/978-3-540-31856-9_44

    .. [2] A measure of betweenness centrality based on random walks,
       M. E. J. Newman, Social Networks 27, 39-54 (2005).
networkx.current_flow_betweenness_subset
Python Library Documentation: module networkx.algorithms.centrality.current_flow_betweenness_subset in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.current_flow_betweenness_subset - Current-flow betweenness centrality measures for subsets of nodes.

FUNCTIONS
    current_flow_betweenness_centrality_subset(G, sources, targets, normalized=True, weight=None, dtype=<class 'float'>, solver='lu', *, backend=None, **backend_kwargs)
        Compute current-flow betweenness centrality for subsets of nodes.

        Current-flow betweenness centrality uses an electrical current
        model for information spreading in contrast to betweenness
        centrality which uses shortest paths.

        Current-flow betweenness centrality is also known as
        random-walk betweenness centrality [2]_.

        Parameters
        ----------
        G : graph
          A NetworkX graph

        sources: list of nodes
          Nodes to use as sources for current

        targets: list of nodes
          Nodes to use as sinks for current

        normalized : bool, optional (default=True)
          If True the betweenness values are normalized by b=b/(n-1)(n-2) where
          n is the number of nodes in G.

        weight : string or None, optional (default=None)
          Key for edge data used as the edge weight.
          If None, then use 1 as each edge weight.
          The weight reflects the capacity or the strength of the
          edge.

        dtype: data type (float)
          Default data type for internal matrices.
          Set to np.float32 for lower memory consumption.

        solver: string (default='lu')
           Type of linear solver to use for computing the flow matrix.
           Options are "full" (uses most memory), "lu" (recommended), and
           "cg" (uses least memory).

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with betweenness centrality as the value.

        See Also
        --------
        approximate_current_flow_betweenness_centrality
        betweenness_centrality
        edge_betweenness_centrality
        edge_current_flow_betweenness_centrality

        Notes
        -----
        Current-flow betweenness can be computed in $O(I(n-1)+mn \log n)$
        time [1]_, where $I(n-1)$ is the time needed to compute the
        inverse Laplacian.  For a full matrix this is $O(n^3)$ but using
        sparse methods you can achieve $O(nm{\sqrt k})$ where $k$ is the
        Laplacian matrix condition number.

        The space required is $O(nw)$ where $w$ is the width of the sparse
        Laplacian matrix.  Worse case is $w=n$ for $O(n^2)$.

        If the edges have a 'weight' attribute they will be used as
        weights in this algorithm.  Unspecified weights are set to 1.

        References
        ----------
        .. [1] Centrality Measures Based on Current Flow.
           Ulrik Brandes and Daniel Fleischer,
           Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
           LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
           https://doi.org/10.1007/978-3-540-31856-9_44

        .. [2] A measure of betweenness centrality based on random walks,
           M. E. J. Newman, Social Networks 27, 39-54 (2005).

    edge_current_flow_betweenness_centrality_subset(G, sources, targets, normalized=True, weight=None, dtype=<class 'float'>, solver='lu', *, backend=None, **backend_kwargs)
        Compute current-flow betweenness centrality for edges using subsets
        of nodes.

        Current-flow betweenness centrality uses an electrical current
        model for information spreading in contrast to betweenness
        centrality which uses shortest paths.

        Current-flow betweenness centrality is also known as
        random-walk betweenness centrality [2]_.

        Parameters
        ----------
        G : graph
          A NetworkX graph

        sources: list of nodes
          Nodes to use as sources for current

        targets: list of nodes
          Nodes to use as sinks for current

        normalized : bool, optional (default=True)
          If True the betweenness values are normalized by b=b/(n-1)(n-2) where
          n is the number of nodes in G.

        weight : string or None, optional (default=None)
          Key for edge data used as the edge weight.
          If None, then use 1 as each edge weight.
          The weight reflects the capacity or the strength of the
          edge.

        dtype: data type (float)
          Default data type for internal matrices.
          Set to np.float32 for lower memory consumption.

        solver: string (default='lu')
           Type of linear solver to use for computing the flow matrix.
           Options are "full" (uses most memory), "lu" (recommended), and
           "cg" (uses least memory).

        Returns
        -------
        nodes : dict
           Dictionary of edge tuples with betweenness centrality as the value.

        See Also
        --------
        betweenness_centrality
        edge_betweenness_centrality
        current_flow_betweenness_centrality

        Notes
        -----
        Current-flow betweenness can be computed in $O(I(n-1)+mn \log n)$
        time [1]_, where $I(n-1)$ is the time needed to compute the
        inverse Laplacian.  For a full matrix this is $O(n^3)$ but using
        sparse methods you can achieve $O(nm{\sqrt k})$ where $k$ is the
        Laplacian matrix condition number.

        The space required is $O(nw)$ where $w$ is the width of the sparse
        Laplacian matrix.  Worse case is $w=n$ for $O(n^2)$.

        If the edges have a 'weight' attribute they will be used as
        weights in this algorithm.  Unspecified weights are set to 1.

        References
        ----------
        .. [1] Centrality Measures Based on Current Flow.
           Ulrik Brandes and Daniel Fleischer,
           Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
           LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
           https://doi.org/10.1007/978-3-540-31856-9_44

        .. [2] A measure of betweenness centrality based on random walks,
           M. E. J. Newman, Social Networks 27, 39-54 (2005).

DATA
    __all__ = ['current_flow_betweenness_centrality_subset', 'edge_current...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\current_flow_betweenness_subset.py

networkx.current_flow_closeness
Python Library Documentation: module networkx.algorithms.centrality.current_flow_closeness in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.current_flow_closeness - Current-flow closeness centrality measures.

FUNCTIONS
    current_flow_closeness_centrality(G, weight=None, dtype=<class 'float'>, solver='lu', *, backend=None, **backend_kwargs)
        Compute current-flow closeness centrality for nodes.

        Current-flow closeness centrality is variant of closeness
        centrality based on effective resistance between nodes in
        a network. This metric is also known as information centrality.

        Parameters
        ----------
        G : graph
          A NetworkX graph.

        weight : None or string, optional (default=None)
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.
          The weight reflects the capacity or the strength of the
          edge.

        dtype: data type (default=float)
          Default data type for internal matrices.
          Set to np.float32 for lower memory consumption.

        solver: string (default='lu')
           Type of linear solver to use for computing the flow matrix.
           Options are "full" (uses most memory), "lu" (recommended), and
           "cg" (uses least memory).

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with current flow closeness centrality as the value.

        See Also
        --------
        closeness_centrality

        Notes
        -----
        The algorithm is from Brandes [1]_.

        See also [2]_ for the original definition of information centrality.

        References
        ----------
        .. [1] Ulrik Brandes and Daniel Fleischer,
           Centrality Measures Based on Current Flow.
           Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
           LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
           https://doi.org/10.1007/978-3-540-31856-9_44

        .. [2] Karen Stephenson and Marvin Zelen:
           Rethinking centrality: Methods and examples.
           Social Networks 11(1):1-37, 1989.
           https://doi.org/10.1016/0378-8733(89)90016-6

    information_centrality = current_flow_closeness_centrality(G, weight=None, dtype=<class 'float'>, solver='lu', *, backend=None, **backend_kwargs)
        Compute current-flow closeness centrality for nodes.

        Current-flow closeness centrality is variant of closeness
        centrality based on effective resistance between nodes in
        a network. This metric is also known as information centrality.

        Parameters
        ----------
        G : graph
          A NetworkX graph.

        weight : None or string, optional (default=None)
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.
          The weight reflects the capacity or the strength of the
          edge.

        dtype: data type (default=float)
          Default data type for internal matrices.
          Set to np.float32 for lower memory consumption.

        solver: string (default='lu')
           Type of linear solver to use for computing the flow matrix.
           Options are "full" (uses most memory), "lu" (recommended), and
           "cg" (uses least memory).

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with current flow closeness centrality as the value.

        See Also
        --------
        closeness_centrality

        Notes
        -----
        The algorithm is from Brandes [1]_.

        See also [2]_ for the original definition of information centrality.

        References
        ----------
        .. [1] Ulrik Brandes and Daniel Fleischer,
           Centrality Measures Based on Current Flow.
           Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
           LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
           https://doi.org/10.1007/978-3-540-31856-9_44

        .. [2] Karen Stephenson and Marvin Zelen:
           Rethinking centrality: Methods and examples.
           Social Networks 11(1):1-37, 1989.
           https://doi.org/10.1016/0378-8733(89)90016-6

DATA
    __all__ = ['current_flow_closeness_centrality', 'information_centralit...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\current_flow_closeness.py

networkx.current_flow_closeness_centrality
Python Library Documentation: function current_flow_closeness_centrality in module networkx.algorithms.centrality.current_flow_closeness

current_flow_closeness_centrality(G, weight=None, dtype=<class 'float'>, solver='lu', *, backend=None, **backend_kwargs)
    Compute current-flow closeness centrality for nodes.

    Current-flow closeness centrality is variant of closeness
    centrality based on effective resistance between nodes in
    a network. This metric is also known as information centrality.

    Parameters
    ----------
    G : graph
      A NetworkX graph.

    weight : None or string, optional (default=None)
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.
      The weight reflects the capacity or the strength of the
      edge.

    dtype: data type (default=float)
      Default data type for internal matrices.
      Set to np.float32 for lower memory consumption.

    solver: string (default='lu')
       Type of linear solver to use for computing the flow matrix.
       Options are "full" (uses most memory), "lu" (recommended), and
       "cg" (uses least memory).

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with current flow closeness centrality as the value.

    See Also
    --------
    closeness_centrality

    Notes
    -----
    The algorithm is from Brandes [1]_.

    See also [2]_ for the original definition of information centrality.

    References
    ----------
    .. [1] Ulrik Brandes and Daniel Fleischer,
       Centrality Measures Based on Current Flow.
       Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
       LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
       https://doi.org/10.1007/978-3-540-31856-9_44

    .. [2] Karen Stephenson and Marvin Zelen:
       Rethinking centrality: Methods and examples.
       Social Networks 11(1):1-37, 1989.
       https://doi.org/10.1016/0378-8733(89)90016-6
networkx.cut_size
Python Library Documentation: function cut_size in module networkx.algorithms.cuts

cut_size(G, S, T=None, weight=None, *, backend=None, **backend_kwargs)
    Returns the size of the cut between two sets of nodes.

    A *cut* is a partition of the nodes of a graph into two sets. The
    *cut size* is the sum of the weights of the edges "between" the two
    sets of nodes.

    Parameters
    ----------
    G : NetworkX graph

    S : collection
        A collection of nodes in `G`.

    T : collection
        A collection of nodes in `G`. If not specified, this is taken to
        be the set complement of `S`.

    weight : object
        Edge attribute key to use as weight. If not specified, edges
        have weight one.

    Returns
    -------
    number
        Total weight of all edges from nodes in set `S` to nodes in
        set `T` (and, in the case of directed graphs, all edges from
        nodes in `T` to nodes in `S`).

    Examples
    --------
    In the graph with two cliques joined by a single edges, the natural
    bipartition of the graph into two blocks, one for each clique,
    yields a cut of weight one::

        >>> G = nx.barbell_graph(3, 0)
        >>> S = {0, 1, 2}
        >>> T = {3, 4, 5}
        >>> nx.cut_size(G, S, T)
        1

    Each parallel edge in a multigraph is counted when determining the
    cut size::

        >>> G = nx.MultiGraph(["ab", "ab"])
        >>> S = {"a"}
        >>> T = {"b"}
        >>> nx.cut_size(G, S, T)
        2

    Notes
    -----
    In a multigraph, the cut size is the total weight of edges including
    multiplicity.
networkx.cuts
Python Library Documentation: module networkx.algorithms.cuts in networkx.algorithms

NAME
    networkx.algorithms.cuts - Functions for finding and evaluating cuts in a graph.

FUNCTIONS
    boundary_expansion(G, S, *, backend=None, **backend_kwargs)
        Returns the boundary expansion of the set `S`.

        The *boundary expansion* is the quotient of the size
        of the node boundary and the cardinality of *S*. [1]

        Parameters
        ----------
        G : NetworkX graph

        S : collection
            A collection of nodes in `G`.

        Returns
        -------
        number
            The boundary expansion of the set `S`.

        See also
        --------
        edge_expansion
        mixing_expansion
        node_expansion

        References
        ----------
        .. [1] Vadhan, Salil P.
               "Pseudorandomness."
               *Foundations and Trends in Theoretical Computer Science*
               7.1–3 (2011): 1–336.
               <https://doi.org/10.1561/0400000010>

    conductance(G, S, T=None, weight=None, *, backend=None, **backend_kwargs)
        Returns the conductance of two sets of nodes.

        The *conductance* is the quotient of the cut size and the smaller of
        the volumes of the two sets. [1]

        Parameters
        ----------
        G : NetworkX graph

        S : collection
            A collection of nodes in `G`.

        T : collection
            A collection of nodes in `G`.

        weight : object
            Edge attribute key to use as weight. If not specified, edges
            have weight one.

        Returns
        -------
        number
            The conductance between the two sets `S` and `T`.

        See also
        --------
        cut_size
        edge_expansion
        normalized_cut_size
        volume

        References
        ----------
        .. [1] David Gleich.
               *Hierarchical Directed Spectral Graph Partitioning*.
               <https://www.cs.purdue.edu/homes/dgleich/publications/Gleich%202005%20-%20hierarchical%20directed%20spectral.pdf>

    cut_size(G, S, T=None, weight=None, *, backend=None, **backend_kwargs)
        Returns the size of the cut between two sets of nodes.

        A *cut* is a partition of the nodes of a graph into two sets. The
        *cut size* is the sum of the weights of the edges "between" the two
        sets of nodes.

        Parameters
        ----------
        G : NetworkX graph

        S : collection
            A collection of nodes in `G`.

        T : collection
            A collection of nodes in `G`. If not specified, this is taken to
            be the set complement of `S`.

        weight : object
            Edge attribute key to use as weight. If not specified, edges
            have weight one.

        Returns
        -------
        number
            Total weight of all edges from nodes in set `S` to nodes in
            set `T` (and, in the case of directed graphs, all edges from
            nodes in `T` to nodes in `S`).

        Examples
        --------
        In the graph with two cliques joined by a single edges, the natural
        bipartition of the graph into two blocks, one for each clique,
        yields a cut of weight one::

            >>> G = nx.barbell_graph(3, 0)
            >>> S = {0, 1, 2}
            >>> T = {3, 4, 5}
            >>> nx.cut_size(G, S, T)
            1

        Each parallel edge in a multigraph is counted when determining the
        cut size::

            >>> G = nx.MultiGraph(["ab", "ab"])
            >>> S = {"a"}
            >>> T = {"b"}
            >>> nx.cut_size(G, S, T)
            2

        Notes
        -----
        In a multigraph, the cut size is the total weight of edges including
        multiplicity.

    edge_expansion(G, S, T=None, weight=None, *, backend=None, **backend_kwargs)
        Returns the edge expansion between two node sets.

        The *edge expansion* is the quotient of the cut size and the smaller
        of the cardinalities of the two sets. [1]

        Parameters
        ----------
        G : NetworkX graph

        S : collection
            A collection of nodes in `G`.

        T : collection
            A collection of nodes in `G`.

        weight : object
            Edge attribute key to use as weight. If not specified, edges
            have weight one.

        Returns
        -------
        number
            The edge expansion between the two sets `S` and `T`.

        See also
        --------
        boundary_expansion
        mixing_expansion
        node_expansion

        References
        ----------
        .. [1] Fan Chung.
               *Spectral Graph Theory*.
               (CBMS Regional Conference Series in Mathematics, No. 92),
               American Mathematical Society, 1997, ISBN 0-8218-0315-8
               <http://www.math.ucsd.edu/~fan/research/revised.html>

    mixing_expansion(G, S, T=None, weight=None, *, backend=None, **backend_kwargs)
        Returns the mixing expansion between two node sets.

        The *mixing expansion* is the quotient of the cut size and twice the
        number of edges in the graph. [1]

        Parameters
        ----------
        G : NetworkX graph

        S : collection
            A collection of nodes in `G`.

        T : collection
            A collection of nodes in `G`.

        weight : object
            Edge attribute key to use as weight. If not specified, edges
            have weight one.

        Returns
        -------
        number
            The mixing expansion between the two sets `S` and `T`.

        See also
        --------
        boundary_expansion
        edge_expansion
        node_expansion

        References
        ----------
        .. [1] Vadhan, Salil P.
               "Pseudorandomness."
               *Foundations and Trends
               in Theoretical Computer Science* 7.1–3 (2011): 1–336.
               <https://doi.org/10.1561/0400000010>

    node_expansion(G, S, *, backend=None, **backend_kwargs)
        Returns the node expansion of the set `S`.

        The *node expansion* is the quotient of the size of the node
        boundary of *S* and the cardinality of *S*. [1]

        Parameters
        ----------
        G : NetworkX graph

        S : collection
            A collection of nodes in `G`.

        Returns
        -------
        number
            The node expansion of the set `S`.

        See also
        --------
        boundary_expansion
        edge_expansion
        mixing_expansion

        References
        ----------
        .. [1] Vadhan, Salil P.
               "Pseudorandomness."
               *Foundations and Trends
               in Theoretical Computer Science* 7.1–3 (2011): 1–336.
               <https://doi.org/10.1561/0400000010>

    normalized_cut_size(G, S, T=None, weight=None, *, backend=None, **backend_kwargs)
        Returns the normalized size of the cut between two sets of nodes.

        The *normalized cut size* is the cut size times the sum of the
        reciprocal sizes of the volumes of the two sets. [1]

        Parameters
        ----------
        G : NetworkX graph

        S : collection
            A collection of nodes in `G`.

        T : collection
            A collection of nodes in `G`.

        weight : object
            Edge attribute key to use as weight. If not specified, edges
            have weight one.

        Returns
        -------
        number
            The normalized cut size between the two sets `S` and `T`.

        Notes
        -----
        In a multigraph, the cut size is the total weight of edges including
        multiplicity.

        See also
        --------
        conductance
        cut_size
        edge_expansion
        volume

        References
        ----------
        .. [1] David Gleich.
               *Hierarchical Directed Spectral Graph Partitioning*.
               <https://www.cs.purdue.edu/homes/dgleich/publications/Gleich%202005%20-%20hierarchical%20directed%20spectral.pdf>

    volume(G, S, weight=None, *, backend=None, **backend_kwargs)
        Returns the volume of a set of nodes.

        The *volume* of a set *S* is the sum of the (out-)degrees of nodes
        in *S* (taking into account parallel edges in multigraphs). [1]

        Parameters
        ----------
        G : NetworkX graph

        S : collection
            A collection of nodes in `G`.

        weight : object
            Edge attribute key to use as weight. If not specified, edges
            have weight one.

        Returns
        -------
        number
            The volume of the set of nodes represented by `S` in the graph
            `G`.

        See also
        --------
        conductance
        cut_size
        edge_expansion
        edge_boundary
        normalized_cut_size

        References
        ----------
        .. [1] David Gleich.
               *Hierarchical Directed Spectral Graph Partitioning*.
               <https://www.cs.purdue.edu/homes/dgleich/publications/Gleich%202005%20-%20hierarchical%20directed%20spectral.pdf>

DATA
    __all__ = ['boundary_expansion', 'conductance', 'cut_size', 'edge_expa...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\cuts.py

networkx.cycle_basis
Python Library Documentation: function cycle_basis in module networkx.algorithms.cycles

cycle_basis(G, root=None, *, backend=None, **backend_kwargs)
    Returns a list of cycles which form a basis for cycles of G.

    A basis for cycles of a network is a minimal collection of
    cycles such that any cycle in the network can be written
    as a sum of cycles in the basis.  Here summation of cycles
    is defined as "exclusive or" of the edges. Cycle bases are
    useful, e.g. when deriving equations for electric circuits
    using Kirchhoff's Laws.

    Parameters
    ----------
    G : NetworkX Graph
    root : node, optional
       Specify starting node for basis.

    Returns
    -------
    A list of cycle lists.  Each cycle list is a list of nodes
    which forms a cycle (loop) in G.

    Examples
    --------
    >>> G = nx.Graph()
    >>> nx.add_cycle(G, [0, 1, 2, 3])
    >>> nx.add_cycle(G, [0, 3, 4, 5])
    >>> nx.cycle_basis(G, 0)
    [[3, 4, 5, 0], [1, 2, 3, 0]]

    Notes
    -----
    This is adapted from algorithm CACM 491 [1]_.

    References
    ----------
    .. [1] Paton, K. An algorithm for finding a fundamental set of
       cycles of a graph. Comm. ACM 12, 9 (Sept 1969), 514-518.

    See Also
    --------
    simple_cycles
    minimum_cycle_basis
networkx.cycle_graph
Python Library Documentation: function cycle_graph in module networkx.generators.classic

cycle_graph(n, create_using=None, *, backend=None, **backend_kwargs)
    Returns the cycle graph $C_n$ of cyclically connected nodes.

    $C_n$ is a path with its two end-nodes connected.

    .. plot::

        >>> nx.draw(nx.cycle_graph(5))

    Parameters
    ----------
    n : int or iterable container of nodes
        If n is an integer, nodes are from `range(n)`.
        If n is a container of nodes, those nodes appear in the graph.
        Warning: n is not checked for duplicates and if present the
        resulting graph may not be as desired. Make sure you have no duplicates.
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Notes
    -----
    If create_using is directed, the direction is in increasing order.
networkx.cycles
Python Library Documentation: module networkx.algorithms.cycles in networkx.algorithms

NAME
    networkx.algorithms.cycles

DESCRIPTION
    ========================
    Cycle finding algorithms
    ========================

FUNCTIONS
    chordless_cycles(G, length_bound=None, *, backend=None, **backend_kwargs)
        Find simple chordless cycles of a graph.

        A `simple cycle` is a closed path where no node appears twice.  In a simple
        cycle, a `chord` is an additional edge between two nodes in the cycle.  A
        `chordless cycle` is a simple cycle without chords.  Said differently, a
        chordless cycle is a cycle C in a graph G where the number of edges in the
        induced graph G[C] is equal to the length of `C`.

        Note that some care must be taken in the case that G is not a simple graph
        nor a simple digraph.  Some authors limit the definition of chordless cycles
        to have a prescribed minimum length; we do not.

            1. We interpret self-loops to be chordless cycles, except in multigraphs
               with multiple loops in parallel.  Likewise, in a chordless cycle of
               length greater than 1, there can be no nodes with self-loops.

            2. We interpret directed two-cycles to be chordless cycles, except in
               multi-digraphs when any edge in a two-cycle has a parallel copy.

            3. We interpret parallel pairs of undirected edges as two-cycles, except
               when a third (or more) parallel edge exists between the two nodes.

            4. Generalizing the above, edges with parallel clones may not occur in
               chordless cycles.

        In a directed graph, two chordless cycles are distinct if they are not
        cyclic permutations of each other.  In an undirected graph, two chordless
        cycles are distinct if they are not cyclic permutations of each other nor of
        the other's reversal.

        Optionally, the cycles are bounded in length.

        We use an algorithm strongly inspired by that of Dias et al [1]_.  It has
        been modified in the following ways:

            1. Recursion is avoided, per Python's limitations

            2. The labeling function is not necessary, because the starting paths
                are chosen (and deleted from the host graph) to prevent multiple
                occurrences of the same path

            3. The search is optionally bounded at a specified length

            4. Support for directed graphs is provided by extending cycles along
                forward edges, and blocking nodes along forward and reverse edges

            5. Support for multigraphs is provided by omitting digons from the set
                of forward edges

        Parameters
        ----------
        G : NetworkX DiGraph
           A directed graph

        length_bound : int or None, optional (default=None)
           If length_bound is an int, generate all simple cycles of G with length at
           most length_bound.  Otherwise, generate all simple cycles of G.

        Yields
        ------
        list of nodes
           Each cycle is represented by a list of nodes along the cycle.

        Examples
        --------
        >>> sorted(list(nx.chordless_cycles(nx.complete_graph(4))))
        [[1, 0, 2], [1, 0, 3], [2, 0, 3], [2, 1, 3]]

        Notes
        -----
        When length_bound is None, and the graph is simple, the time complexity is
        $O((n+e)(c+1))$ for $n$ nodes, $e$ edges and $c$ chordless cycles.

        Raises
        ------
        ValueError
            when length_bound < 0.

        References
        ----------
        .. [1] Efficient enumeration of chordless cycles
           E. Dias and D. Castonguay and H. Longo and W.A.R. Jradi
           https://arxiv.org/abs/1309.1051

        See Also
        --------
        simple_cycles

    cycle_basis(G, root=None, *, backend=None, **backend_kwargs)
        Returns a list of cycles which form a basis for cycles of G.

        A basis for cycles of a network is a minimal collection of
        cycles such that any cycle in the network can be written
        as a sum of cycles in the basis.  Here summation of cycles
        is defined as "exclusive or" of the edges. Cycle bases are
        useful, e.g. when deriving equations for electric circuits
        using Kirchhoff's Laws.

        Parameters
        ----------
        G : NetworkX Graph
        root : node, optional
           Specify starting node for basis.

        Returns
        -------
        A list of cycle lists.  Each cycle list is a list of nodes
        which forms a cycle (loop) in G.

        Examples
        --------
        >>> G = nx.Graph()
        >>> nx.add_cycle(G, [0, 1, 2, 3])
        >>> nx.add_cycle(G, [0, 3, 4, 5])
        >>> nx.cycle_basis(G, 0)
        [[3, 4, 5, 0], [1, 2, 3, 0]]

        Notes
        -----
        This is adapted from algorithm CACM 491 [1]_.

        References
        ----------
        .. [1] Paton, K. An algorithm for finding a fundamental set of
           cycles of a graph. Comm. ACM 12, 9 (Sept 1969), 514-518.

        See Also
        --------
        simple_cycles
        minimum_cycle_basis

    find_cycle(G, source=None, orientation=None, *, backend=None, **backend_kwargs)
        Returns a cycle found via depth-first traversal.

        The cycle is a list of edges indicating the cyclic path.
        Orientation of directed edges is controlled by `orientation`.

        Parameters
        ----------
        G : graph
            A directed/undirected graph/multigraph.

        source : node, list of nodes
            The node from which the traversal begins. If None, then a source
            is chosen arbitrarily and repeatedly until all edges from each node in
            the graph are searched.

        orientation : None | 'original' | 'reverse' | 'ignore' (default: None)
            For directed graphs and directed multigraphs, edge traversals need not
            respect the original orientation of the edges.
            When set to 'reverse' every edge is traversed in the reverse direction.
            When set to 'ignore', every edge is treated as undirected.
            When set to 'original', every edge is treated as directed.
            In all three cases, the yielded edge tuples add a last entry to
            indicate the direction in which that edge was traversed.
            If orientation is None, the yielded edge has no direction indicated.
            The direction is respected, but not reported.

        Returns
        -------
        edges : directed edges
            A list of directed edges indicating the path taken for the loop.
            If no cycle is found, then an exception is raised.
            For graphs, an edge is of the form `(u, v)` where `u` and `v`
            are the tail and head of the edge as determined by the traversal.
            For multigraphs, an edge is of the form `(u, v, key)`, where `key` is
            the key of the edge. When the graph is directed, then `u` and `v`
            are always in the order of the actual directed edge.
            If orientation is not None then the edge tuple is extended to include
            the direction of traversal ('forward' or 'reverse') on that edge.

        Raises
        ------
        NetworkXNoCycle
            If no cycle was found.

        Examples
        --------
        In this example, we construct a DAG and find, in the first call, that there
        are no directed cycles, and so an exception is raised. In the second call,
        we ignore edge orientations and find that there is an undirected cycle.
        Note that the second call finds a directed cycle while effectively
        traversing an undirected graph, and so, we found an "undirected cycle".
        This means that this DAG structure does not form a directed tree (which
        is also known as a polytree).

        >>> G = nx.DiGraph([(0, 1), (0, 2), (1, 2)])
        >>> nx.find_cycle(G, orientation="original")
        Traceback (most recent call last):
            ...
        networkx.exception.NetworkXNoCycle: No cycle found.
        >>> list(nx.find_cycle(G, orientation="ignore"))
        [(0, 1, 'forward'), (1, 2, 'forward'), (0, 2, 'reverse')]

        See Also
        --------
        simple_cycles

    girth(G, *, backend=None, **backend_kwargs)
        Returns the girth of the graph.

        The girth of a graph is the length of its shortest cycle, or infinity if
        the graph is acyclic. The algorithm follows the description given on the
        Wikipedia page [1]_, and runs in time O(mn) on a graph with m edges and n
        nodes.

        Parameters
        ----------
        G : NetworkX Graph

        Returns
        -------
        int or math.inf

        Examples
        --------
        All examples below (except P_5) can easily be checked using Wikipedia,
        which has a page for each of these famous graphs.

        >>> nx.girth(nx.chvatal_graph())
        4
        >>> nx.girth(nx.tutte_graph())
        4
        >>> nx.girth(nx.petersen_graph())
        5
        >>> nx.girth(nx.heawood_graph())
        6
        >>> nx.girth(nx.pappus_graph())
        6
        >>> nx.girth(nx.path_graph(5))
        inf

        References
        ----------
        .. [1] `Wikipedia: Girth <https://en.wikipedia.org/wiki/Girth_(graph_theory)>`_

    minimum_cycle_basis(G, weight=None, *, backend=None, **backend_kwargs)
        Returns a minimum weight cycle basis for G

        Minimum weight means a cycle basis for which the total weight
        (length for unweighted graphs) of all the cycles is minimum.

        Parameters
        ----------
        G : NetworkX Graph
        weight: string
            name of the edge attribute to use for edge weights

        Returns
        -------
        A list of cycle lists.  Each cycle list is a list of nodes
        which forms a cycle (loop) in G. Note that the nodes are not
        necessarily returned in a order by which they appear in the cycle

        Examples
        --------
        >>> G = nx.Graph()
        >>> nx.add_cycle(G, [0, 1, 2, 3])
        >>> nx.add_cycle(G, [0, 3, 4, 5])
        >>> nx.minimum_cycle_basis(G)
        [[5, 4, 3, 0], [3, 2, 1, 0]]

        References:
            [1] Kavitha, Telikepalli, et al. "An O(m^2n) Algorithm for
            Minimum Cycle Basis of Graphs."
            http://link.springer.com/article/10.1007/s00453-007-9064-z
            [2] de Pina, J. 1995. Applications of shortest path methods.
            Ph.D. thesis, University of Amsterdam, Netherlands

        See Also
        --------
        simple_cycles, cycle_basis

    recursive_simple_cycles(G, *, backend=None, **backend_kwargs)
        Find simple cycles (elementary circuits) of a directed graph.

        A `simple cycle`, or `elementary circuit`, is a closed path where
        no node appears twice. Two elementary circuits are distinct if they
        are not cyclic permutations of each other.

        This version uses a recursive algorithm to build a list of cycles.
        You should probably use the iterator version called simple_cycles().
        Warning: This recursive version uses lots of RAM!
        It appears in NetworkX for pedagogical value.

        Parameters
        ----------
        G : NetworkX DiGraph
           A directed graph

        Returns
        -------
        A list of cycles, where each cycle is represented by a list of nodes
        along the cycle.

        Example:

        >>> edges = [(0, 0), (0, 1), (0, 2), (1, 2), (2, 0), (2, 1), (2, 2)]
        >>> G = nx.DiGraph(edges)
        >>> nx.recursive_simple_cycles(G)
        [[0], [2], [0, 1, 2], [0, 2], [1, 2]]

        Notes
        -----
        The implementation follows pp. 79-80 in [1]_.

        The time complexity is $O((n+e)(c+1))$ for $n$ nodes, $e$ edges and $c$
        elementary circuits.

        References
        ----------
        .. [1] Finding all the elementary circuits of a directed graph.
           D. B. Johnson, SIAM Journal on Computing 4, no. 1, 77-84, 1975.
           https://doi.org/10.1137/0204007

        See Also
        --------
        simple_cycles, cycle_basis

    simple_cycles(G, length_bound=None, *, backend=None, **backend_kwargs)
        Find simple cycles (elementary circuits) of a graph.

        A "simple cycle", or "elementary circuit", is a closed path where
        no node appears twice.  In a directed graph, two simple cycles are distinct
        if they are not cyclic permutations of each other.  In an undirected graph,
        two simple cycles are distinct if they are not cyclic permutations of each
        other nor of the other's reversal.

        Optionally, the cycles are bounded in length.  In the unbounded case, we use
        a nonrecursive, iterator/generator version of Johnson's algorithm [1]_.  In
        the bounded case, we use a version of the algorithm of Gupta and
        Suzumura [2]_. There may be better algorithms for some cases [3]_ [4]_ [5]_.

        The algorithms of Johnson, and Gupta and Suzumura, are enhanced by some
        well-known preprocessing techniques.  When `G` is directed, we restrict our
        attention to strongly connected components of `G`, generate all simple cycles
        containing a certain node, remove that node, and further decompose the
        remainder into strongly connected components.  When `G` is undirected, we
        restrict our attention to biconnected components, generate all simple cycles
        containing a particular edge, remove that edge, and further decompose the
        remainder into biconnected components.

        Note that multigraphs are supported by this function -- and in undirected
        multigraphs, a pair of parallel edges is considered a cycle of length 2.
        Likewise, self-loops are considered to be cycles of length 1.  We define
        cycles as sequences of nodes; so the presence of loops and parallel edges
        does not change the number of simple cycles in a graph.

        Parameters
        ----------
        G : NetworkX Graph
           A networkx graph. Undirected, directed, and multigraphs are all supported.

        length_bound : int or None, optional (default=None)
           If `length_bound` is an int, generate all simple cycles of `G` with length at
           most `length_bound`.  Otherwise, generate all simple cycles of `G`.

        Yields
        ------
        list of nodes
           Each cycle is represented by a list of nodes along the cycle.

        Examples
        --------
        >>> G = nx.DiGraph([(0, 0), (0, 1), (0, 2), (1, 2), (2, 0), (2, 1), (2, 2)])
        >>> sorted(nx.simple_cycles(G))
        [[0], [0, 1, 2], [0, 2], [1, 2], [2]]

        To filter the cycles so that they don't include certain nodes or edges,
        copy your graph and eliminate those nodes or edges before calling.
        For example, to exclude self-loops from the above example:

        >>> H = G.copy()
        >>> H.remove_edges_from(nx.selfloop_edges(G))
        >>> sorted(nx.simple_cycles(H))
        [[0, 1, 2], [0, 2], [1, 2]]

        Notes
        -----
        When `length_bound` is None, the time complexity is $O((n+e)(c+1))$ for $n$
        nodes, $e$ edges and $c$ simple circuits.  Otherwise, when ``length_bound > 1``,
        the time complexity is $O((c+n)(k-1)d^k)$ where $d$ is the average degree of
        the nodes of `G` and $k$ = `length_bound`.

        Raises
        ------
        ValueError
            when ``length_bound < 0``.

        References
        ----------
        .. [1] Finding all the elementary circuits of a directed graph.
           D. B. Johnson, SIAM Journal on Computing 4, no. 1, 77-84, 1975.
           https://doi.org/10.1137/0204007
        .. [2] Finding All Bounded-Length Simple Cycles in a Directed Graph
           A. Gupta and T. Suzumura https://arxiv.org/abs/2105.10094
        .. [3] Enumerating the cycles of a digraph: a new preprocessing strategy.
           G. Loizou and P. Thanish, Information Sciences, v. 27, 163-182, 1982.
        .. [4] A search strategy for the elementary cycles of a directed graph.
           J.L. Szwarcfiter and P.E. Lauer, BIT NUMERICAL MATHEMATICS,
           v. 16, no. 2, 192-204, 1976.
        .. [5] Optimal Listing of Cycles and st-Paths in Undirected Graphs
            R. Ferreira and R. Grossi and A. Marino and N. Pisanti and R. Rizzi and
            G. Sacomoto https://arxiv.org/abs/1205.2766

        See Also
        --------
        cycle_basis
        chordless_cycles

DATA
    __all__ = ['cycle_basis', 'simple_cycles', 'recursive_simple_cycles', ...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\cycles.py

networkx.cytoscape
Python Library Documentation: module networkx.readwrite.json_graph.cytoscape in networkx.readwrite.json_graph

NAME
    networkx.readwrite.json_graph.cytoscape

FUNCTIONS
    cytoscape_data(G, name='name', ident='id')
        Returns data in Cytoscape JSON format (cyjs).

        Parameters
        ----------
        G : NetworkX Graph
            The graph to convert to cytoscape format
        name : string
            A string which is mapped to the 'name' node element in cyjs format.
            Must not have the same value as `ident`.
        ident : string
            A string which is mapped to the 'id' node element in cyjs format.
            Must not have the same value as `name`.

        Returns
        -------
        data: dict
            A dictionary with cyjs formatted data.

        Raises
        ------
        NetworkXError
            If the values for `name` and `ident` are identical.

        See Also
        --------
        cytoscape_graph: convert a dictionary in cyjs format to a graph

        References
        ----------
        .. [1] Cytoscape user's manual:
           http://manual.cytoscape.org/en/stable/index.html

        Examples
        --------
        >>> G = nx.path_graph(2)
        >>> nx.cytoscape_data(G)  # doctest: +SKIP
        {'data': [],
         'directed': False,
         'multigraph': False,
         'elements': {'nodes': [{'data': {'id': '0', 'value': 0, 'name': '0'}},
           {'data': {'id': '1', 'value': 1, 'name': '1'}}],
          'edges': [{'data': {'source': 0, 'target': 1}}]}}

    cytoscape_graph(data, name='name', ident='id', *, backend=None, **backend_kwargs)
        Create a NetworkX graph from a dictionary in cytoscape JSON format.

        Parameters
        ----------
        data : dict
            A dictionary of data conforming to cytoscape JSON format.
        name : string
            A string which is mapped to the 'name' node element in cyjs format.
            Must not have the same value as `ident`.
        ident : string
            A string which is mapped to the 'id' node element in cyjs format.
            Must not have the same value as `name`.

        Returns
        -------
        graph : a NetworkX graph instance
            The `graph` can be an instance of `Graph`, `DiGraph`, `MultiGraph`, or
            `MultiDiGraph` depending on the input data.

        Raises
        ------
        NetworkXError
            If the `name` and `ident` attributes are identical.

        See Also
        --------
        cytoscape_data: convert a NetworkX graph to a dict in cyjs format

        References
        ----------
        .. [1] Cytoscape user's manual:
           http://manual.cytoscape.org/en/stable/index.html

        Examples
        --------
        >>> data_dict = {
        ...     "data": [],
        ...     "directed": False,
        ...     "multigraph": False,
        ...     "elements": {
        ...         "nodes": [
        ...             {"data": {"id": "0", "value": 0, "name": "0"}},
        ...             {"data": {"id": "1", "value": 1, "name": "1"}},
        ...         ],
        ...         "edges": [{"data": {"source": 0, "target": 1}}],
        ...     },
        ... }
        >>> G = nx.cytoscape_graph(data_dict)
        >>> G.name
        ''
        >>> G.nodes()
        NodeView((0, 1))
        >>> G.nodes(data=True)[0]
        {'id': '0', 'value': 0, 'name': '0'}
        >>> G.edges(data=True)
        EdgeDataView([(0, 1, {'source': 0, 'target': 1})])

DATA
    __all__ = ['cytoscape_data', 'cytoscape_graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\json_graph\cytoscape.py

networkx.cytoscape_data
Python Library Documentation: function cytoscape_data in module networkx.readwrite.json_graph.cytoscape

cytoscape_data(G, name='name', ident='id')
    Returns data in Cytoscape JSON format (cyjs).

    Parameters
    ----------
    G : NetworkX Graph
        The graph to convert to cytoscape format
    name : string
        A string which is mapped to the 'name' node element in cyjs format.
        Must not have the same value as `ident`.
    ident : string
        A string which is mapped to the 'id' node element in cyjs format.
        Must not have the same value as `name`.

    Returns
    -------
    data: dict
        A dictionary with cyjs formatted data.

    Raises
    ------
    NetworkXError
        If the values for `name` and `ident` are identical.

    See Also
    --------
    cytoscape_graph: convert a dictionary in cyjs format to a graph

    References
    ----------
    .. [1] Cytoscape user's manual:
       http://manual.cytoscape.org/en/stable/index.html

    Examples
    --------
    >>> G = nx.path_graph(2)
    >>> nx.cytoscape_data(G)  # doctest: +SKIP
    {'data': [],
     'directed': False,
     'multigraph': False,
     'elements': {'nodes': [{'data': {'id': '0', 'value': 0, 'name': '0'}},
       {'data': {'id': '1', 'value': 1, 'name': '1'}}],
      'edges': [{'data': {'source': 0, 'target': 1}}]}}
networkx.cytoscape_graph
Python Library Documentation: function cytoscape_graph in module networkx.readwrite.json_graph.cytoscape

cytoscape_graph(data, name='name', ident='id', *, backend=None, **backend_kwargs)
    Create a NetworkX graph from a dictionary in cytoscape JSON format.

    Parameters
    ----------
    data : dict
        A dictionary of data conforming to cytoscape JSON format.
    name : string
        A string which is mapped to the 'name' node element in cyjs format.
        Must not have the same value as `ident`.
    ident : string
        A string which is mapped to the 'id' node element in cyjs format.
        Must not have the same value as `name`.

    Returns
    -------
    graph : a NetworkX graph instance
        The `graph` can be an instance of `Graph`, `DiGraph`, `MultiGraph`, or
        `MultiDiGraph` depending on the input data.

    Raises
    ------
    NetworkXError
        If the `name` and `ident` attributes are identical.

    See Also
    --------
    cytoscape_data: convert a NetworkX graph to a dict in cyjs format

    References
    ----------
    .. [1] Cytoscape user's manual:
       http://manual.cytoscape.org/en/stable/index.html

    Examples
    --------
    >>> data_dict = {
    ...     "data": [],
    ...     "directed": False,
    ...     "multigraph": False,
    ...     "elements": {
    ...         "nodes": [
    ...             {"data": {"id": "0", "value": 0, "name": "0"}},
    ...             {"data": {"id": "1", "value": 1, "name": "1"}},
    ...         ],
    ...         "edges": [{"data": {"source": 0, "target": 1}}],
    ...     },
    ... }
    >>> G = nx.cytoscape_graph(data_dict)
    >>> G.name
    ''
    >>> G.nodes()
    NodeView((0, 1))
    >>> G.nodes(data=True)[0]
    {'id': '0', 'value': 0, 'name': '0'}
    >>> G.edges(data=True)
    EdgeDataView([(0, 1, {'source': 0, 'target': 1})])
networkx.d_separated
Python Library Documentation: function d_separated in module networkx.algorithms.d_separation

d_separated(G, x, y, z)
    Return whether nodes sets ``x`` and ``y`` are d-separated by ``z``.

    .. deprecated:: 3.3

        This function is deprecated and will be removed in NetworkX v3.5.
        Please use `is_d_separator(G, x, y, z)`.
networkx.d_separation
Python Library Documentation: module networkx.algorithms.d_separation in networkx.algorithms

NAME
    networkx.algorithms.d_separation - Algorithm for testing d-separation in DAGs.

DESCRIPTION
    *d-separation* is a test for conditional independence in probability
    distributions that can be factorized using DAGs.  It is a purely
    graphical test that uses the underlying graph and makes no reference
    to the actual distribution parameters.  See [1]_ for a formal
    definition.

    The implementation is based on the conceptually simple linear time
    algorithm presented in [2]_.  Refer to [3]_, [4]_ for a couple of
    alternative algorithms.

    The functional interface in NetworkX consists of three functions:

    - `find_minimal_d_separator` returns a minimal d-separator set ``z``.
      That is, removing any node or nodes from it makes it no longer a d-separator.
    - `is_d_separator` checks if a given set is a d-separator.
    - `is_minimal_d_separator` checks if a given set is a minimal d-separator.

    D-separators
    ------------

    Here, we provide a brief overview of d-separation and related concepts that
    are relevant for understanding it:

    The ideas of d-separation and d-connection relate to paths being open or blocked.

    - A "path" is a sequence of nodes connected in order by edges. Unlike for most
      graph theory analysis, the direction of the edges is ignored. Thus the path
      can be thought of as a traditional path on the undirected version of the graph.
    - A "candidate d-separator" ``z`` is a set of nodes being considered as
      possibly blocking all paths between two prescribed sets ``x`` and ``y`` of nodes.
      We refer to each node in the candidate d-separator as "known".
    - A "collider" node on a path is a node that is a successor of its two neighbor
      nodes on the path. That is, ``c`` is a collider if the edge directions
      along the path look like ``... u -> c <- v ...``.
    - If a collider node or any of its descendants are "known", the collider
      is called an "open collider". Otherwise it is a "blocking collider".
    - Any path can be "blocked" in two ways. If the path contains a "known" node
      that is not a collider, the path is blocked. Also, if the path contains a
      collider that is not a "known" node, the path is blocked.
    - A path is "open" if it is not blocked. That is, it is open if every node is
      either an open collider or not a "known". Said another way, every
      "known" in the path is a collider and every collider is open (has a
      "known" as a inclusive descendant). The concept of "open path" is meant to
      demonstrate a probabilistic conditional dependence between two nodes given
      prescribed knowledge ("known" nodes).
    - Two sets ``x`` and ``y`` of nodes are "d-separated" by a set of nodes ``z``
      if all paths between nodes in ``x`` and nodes in ``y`` are blocked. That is,
      if there are no open paths from any node in ``x`` to any node in ``y``.
      Such a set ``z`` is a "d-separator" of ``x`` and ``y``.
    - A "minimal d-separator" is a d-separator ``z`` for which no node or subset
      of nodes can be removed with it still being a d-separator.

    The d-separator blocks some paths between ``x`` and ``y`` but opens others.
    Nodes in the d-separator block paths if the nodes are not colliders.
    But if a collider or its descendant nodes are in the d-separation set, the
    colliders are open, allowing a path through that collider.

    Illustration of D-separation with examples
    ------------------------------------------

    A pair of two nodes, ``u`` and ``v``, are d-connected if there is a path
    from ``u`` to ``v`` that is not blocked. That means, there is an open
    path from ``u`` to ``v``.

    For example, if the d-separating set is the empty set, then the following paths are
    open between ``u`` and ``v``:

    - u <- n -> v
    - u -> w -> ... -> n -> v

    If  on the other hand, ``n`` is in the d-separating set, then ``n`` blocks
    those paths between ``u`` and ``v``.

    Colliders block a path if they and their descendants are not included
    in the d-separating set. An example of a path that is blocked when the
    d-separating set is empty is:

    - u -> w -> ... -> n <- v

    The node ``n`` is a collider in this path and is not in the d-separating set.
    So ``n`` blocks this path. However, if ``n`` or a descendant of ``n`` is
    included in the d-separating set, then the path through the collider
    at ``n`` (... -> n <- ...) is "open".

    D-separation is concerned with blocking all paths between nodes from ``x`` to ``y``.
    A d-separating set between ``x`` and ``y`` is one where all paths are blocked.

    D-separation and its applications in probability
    ------------------------------------------------

    D-separation is commonly used in probabilistic causal-graph models. D-separation
    connects the idea of probabilistic "dependence" with separation in a graph. If
    one assumes the causal Markov condition [5]_, (every node is conditionally
    independent of its non-descendants, given its parents) then d-separation implies
    conditional independence in probability distributions.
    Symmetrically, d-connection implies dependence.

    The intuition is as follows. The edges on a causal graph indicate which nodes
    influence the outcome of other nodes directly. An edge from u to v
    implies that the outcome of event ``u`` influences the probabilities for
    the outcome of event ``v``. Certainly knowing ``u`` changes predictions for ``v``.
    But also knowing ``v`` changes predictions for ``u``. The outcomes are dependent.
    Furthermore, an edge from ``v`` to ``w`` would mean that ``w`` and ``v`` are dependent
    and thus that ``u`` could indirectly influence ``w``.

    Without any knowledge about the system (candidate d-separating set is empty)
    a causal graph ``u -> v -> w`` allows all three nodes to be dependent. But
    if we know the outcome of ``v``, the conditional probabilities of outcomes for
    ``u`` and ``w`` are independent of each other. That is, once we know the outcome
    for ```v`, the probabilities for ``w`` do not depend on the outcome for ``u``.
    This is the idea behind ``v`` blocking the path if it is "known" (in the candidate
    d-separating set).

    The same argument works whether the direction of the edges are both
    left-going and when both arrows head out from the middle. Having a "known"
    node on a path blocks the collider-free path because those relationships
    make the conditional probabilities independent.

    The direction of the causal edges does impact dependence precisely in the
    case of a collider e.g. ``u -> v <- w``. In that situation, both ``u`` and ``w``
    influence ``v```. But they do not directly influence each other. So without any
    knowledge of any outcomes, ``u`` and ``w`` are independent. That is the idea behind
    colliders blocking the path. But, if ``v`` is known, the conditional probabilities
    of ``u`` and ``w`` can be dependent. This is the heart of Berkson's Paradox [6]_.
    For example, suppose ``u`` and ``w`` are boolean events (they either happen or do not)
    and ``v`` represents the outcome "at least one of ``u`` and ``w`` occur". Then knowing
    ``v`` is true makes the conditional probabilities of ``u`` and ``w`` dependent.
    Essentially, knowing that at least one of them is true raises the probability of
    each. But further knowledge that ``w`` is true (or false) change the conditional
    probability of ``u`` to either the original value or 1. So the conditional
    probability of ``u`` depends on the outcome of ``w`` even though there is no
    causal relationship between them. When a collider is known, dependence can
    occur across paths through that collider. This is the reason open colliders
    do not block paths.

    Furthermore, even if ``v`` is not "known", if one of its descendants is "known"
    we can use that information to know more about ``v`` which again makes
    ``u`` and ``w`` potentially dependent. Suppose the chance of ``n`` occurring
    is much higher when ``v`` occurs ("at least one of ``u`` and ``w`` occur").
    Then if we know ``n`` occurred, it is more likely that ``v`` occurred and that
    makes the chance of ``u`` and ``w`` dependent. This is the idea behind why
    a collider does no block a path if any descendant of the collider is "known".

    When two sets of nodes ``x`` and ``y`` are d-separated by a set ``z``,
    it means that given the outcomes of the nodes in ``z``, the probabilities
    of outcomes of the nodes in ``x`` are independent of the outcomes of the
    nodes in ``y`` and vice versa.

    Examples
    --------
    A Hidden Markov Model with 5 observed states and 5 hidden states
    where the hidden states have causal relationships resulting in
    a path results in the following causal network. We check that
    early states along the path are separated from late state in
    the path by the d-separator of the middle hidden state.
    Thus if we condition on the middle hidden state, the early
    state probabilities are independent of the late state outcomes.

    >>> G = nx.DiGraph()
    >>> G.add_edges_from(
    ...     [
    ...         ("H1", "H2"),
    ...         ("H2", "H3"),
    ...         ("H3", "H4"),
    ...         ("H4", "H5"),
    ...         ("H1", "O1"),
    ...         ("H2", "O2"),
    ...         ("H3", "O3"),
    ...         ("H4", "O4"),
    ...         ("H5", "O5"),
    ...     ]
    ... )
    >>> x, y, z = ({"H1", "O1"}, {"H5", "O5"}, {"H3"})
    >>> nx.is_d_separator(G, x, y, z)
    True
    >>> nx.is_minimal_d_separator(G, x, y, z)
    True
    >>> nx.is_minimal_d_separator(G, x, y, z | {"O3"})
    False
    >>> z = nx.find_minimal_d_separator(G, x | y, {"O2", "O3", "O4"})
    >>> z == {"H2", "H4"}
    True

    If no minimal_d_separator exists, `None` is returned

    >>> other_z = nx.find_minimal_d_separator(G, x | y, {"H2", "H3"})
    >>> other_z is None
    True


    References
    ----------

    .. [1] Pearl, J.  (2009).  Causality.  Cambridge: Cambridge University Press.

    .. [2] Darwiche, A.  (2009).  Modeling and reasoning with Bayesian networks.
       Cambridge: Cambridge University Press.

    .. [3] Shachter, Ross D. "Bayes-ball: The rational pastime (for
       determining irrelevance and requisite information in belief networks
       and influence diagrams)." In Proceedings of the Fourteenth Conference
       on Uncertainty in Artificial Intelligence (UAI), (pp. 480–487). 1998.

    .. [4] Koller, D., & Friedman, N. (2009).
       Probabilistic graphical models: principles and techniques. The MIT Press.

    .. [5] https://en.wikipedia.org/wiki/Causal_Markov_condition

    .. [6] https://en.wikipedia.org/wiki/Berkson%27s_paradox

FUNCTIONS
    d_separated(G, x, y, z)
        Return whether nodes sets ``x`` and ``y`` are d-separated by ``z``.

        .. deprecated:: 3.3

            This function is deprecated and will be removed in NetworkX v3.5.
            Please use `is_d_separator(G, x, y, z)`.

    find_minimal_d_separator(G, x, y, *, included=None, restricted=None, backend=None, **backend_kwargs)
        Returns a minimal d-separating set between `x` and `y` if possible

        A d-separating set in a DAG is a set of nodes that blocks all
        paths between the two sets of nodes, `x` and `y`. This function
        constructs a d-separating set that is "minimal", meaning no nodes can
        be removed without it losing the d-separating property for `x` and `y`.
        If no d-separating sets exist for `x` and `y`, this returns `None`.

        In a DAG there may be more than one minimal d-separator between two
        sets of nodes. Minimal d-separators are not always unique. This function
        returns one minimal d-separator, or `None` if no d-separator exists.

        Uses the algorithm presented in [1]_. The complexity of the algorithm
        is :math:`O(m)`, where :math:`m` stands for the number of edges in
        the subgraph of G consisting of only the ancestors of `x` and `y`.
        For full details, see [1]_.

        Parameters
        ----------
        G : graph
            A networkx DAG.
        x : set | node
            A node or set of nodes in the graph.
        y : set | node
            A node or set of nodes in the graph.
        included : set | node | None
            A node or set of nodes which must be included in the found separating set,
            default is None, which means the empty set.
        restricted : set | node | None
            Restricted node or set of nodes to consider. Only these nodes can be in
            the found separating set, default is None meaning all nodes in ``G``.

        Returns
        -------
        z : set | None
            The minimal d-separating set, if at least one d-separating set exists,
            otherwise None.

        Raises
        ------
        NetworkXError
            Raises a :exc:`NetworkXError` if the input graph is not a DAG
            or if node sets `x`, `y`, and `included` are not disjoint.

        NodeNotFound
            If any of the input nodes are not found in the graph,
            a :exc:`NodeNotFound` exception is raised.

        References
        ----------
        .. [1] van der Zander, Benito, and Maciej Liśkiewicz. "Finding
            minimal d-separators in linear time and applications." In
            Uncertainty in Artificial Intelligence, pp. 637-647. PMLR, 2020.

    is_d_separator(G, x, y, z, *, backend=None, **backend_kwargs)
        Return whether node sets `x` and `y` are d-separated by `z`.

        Parameters
        ----------
        G : nx.DiGraph
            A NetworkX DAG.

        x : node or set of nodes
            First node or set of nodes in `G`.

        y : node or set of nodes
            Second node or set of nodes in `G`.

        z : node or set of nodes
            Potential separator (set of conditioning nodes in `G`). Can be empty set.

        Returns
        -------
        b : bool
            A boolean that is true if `x` is d-separated from `y` given `z` in `G`.

        Raises
        ------
        NetworkXError
            The *d-separation* test is commonly used on disjoint sets of
            nodes in acyclic directed graphs.  Accordingly, the algorithm
            raises a :exc:`NetworkXError` if the node sets are not
            disjoint or if the input graph is not a DAG.

        NodeNotFound
            If any of the input nodes are not found in the graph,
            a :exc:`NodeNotFound` exception is raised

        Notes
        -----
        A d-separating set in a DAG is a set of nodes that
        blocks all paths between the two sets. Nodes in `z`
        block a path if they are part of the path and are not a collider,
        or a descendant of a collider. Also colliders that are not in `z`
        block a path. A collider structure along a path
        is ``... -> c <- ...`` where ``c`` is the collider node.

        https://en.wikipedia.org/wiki/Bayesian_network#d-separation

    is_minimal_d_separator(G, x, y, z, *, included=None, restricted=None, backend=None, **backend_kwargs)
        Determine if `z` is a minimal d-separator for `x` and `y`.

        A d-separator, `z`, in a DAG is a set of nodes that blocks
        all paths from nodes in set `x` to nodes in set `y`.
        A minimal d-separator is a d-separator `z` such that removing
        any subset of nodes makes it no longer a d-separator.

        Note: This function checks whether `z` is a d-separator AND is
        minimal. One can use the function `is_d_separator` to only check if
        `z` is a d-separator. See examples below.

        Parameters
        ----------
        G : nx.DiGraph
            A NetworkX DAG.
        x : node | set
            A node or set of nodes in the graph.
        y : node | set
            A node or set of nodes in the graph.
        z : node | set
            The node or set of nodes to check if it is a minimal d-separating set.
            The function :func:`is_d_separator` is called inside this function
            to verify that `z` is in fact a d-separator.
        included : set | node | None
            A node or set of nodes which must be included in the found separating set,
            default is ``None``, which means the empty set.
        restricted : set | node | None
            Restricted node or set of nodes to consider. Only these nodes can be in
            the found separating set, default is ``None`` meaning all nodes in ``G``.

        Returns
        -------
        bool
            Whether or not the set `z` is a minimal d-separator subject to
            `restricted` nodes and `included` node constraints.

        Examples
        --------
        >>> G = nx.path_graph([0, 1, 2, 3], create_using=nx.DiGraph)
        >>> G.add_node(4)
        >>> nx.is_minimal_d_separator(G, 0, 2, {1})
        True
        >>> # since {1} is the minimal d-separator, {1, 3, 4} is not minimal
        >>> nx.is_minimal_d_separator(G, 0, 2, {1, 3, 4})
        False
        >>> # alternatively, if we only want to check that {1, 3, 4} is a d-separator
        >>> nx.is_d_separator(G, 0, 2, {1, 3, 4})
        True

        Raises
        ------
        NetworkXError
            Raises a :exc:`NetworkXError` if the input graph is not a DAG.

        NodeNotFound
            If any of the input nodes are not found in the graph,
            a :exc:`NodeNotFound` exception is raised.

        References
        ----------
        .. [1] van der Zander, Benito, and Maciej Liśkiewicz. "Finding
            minimal d-separators in linear time and applications." In
            Uncertainty in Artificial Intelligence, pp. 637-647. PMLR, 2020.

        Notes
        -----
        This function works on verifying that a set is minimal and
        d-separating between two nodes. Uses criterion (a), (b), (c) on
        page 4 of [1]_. a) closure(`x`) and `y` are disjoint. b) `z` contains
        all nodes from `included` and is contained in the `restricted`
        nodes and in the union of ancestors of `x`, `y`, and `included`.
        c) the nodes in `z` not in `included` are contained in both
        closure(x) and closure(y). The closure of a set is the set of nodes
        connected to the set by a directed path in G.

        The complexity is :math:`O(m)`, where :math:`m` stands for the
        number of edges in the subgraph of G consisting of only the
        ancestors of `x` and `y`.

        For full details, see [1]_.

    minimal_d_separator(G, u, v)
        Returns a minimal_d-separating set between `x` and `y` if possible

        .. deprecated:: 3.3

            minimal_d_separator is deprecated and will be removed in NetworkX v3.5.
            Please use `find_minimal_d_separator(G, x, y)`.

DATA
    __all__ = ['is_d_separator', 'is_minimal_d_separator', 'find_minimal_d...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\d_separation.py

networkx.dag
Python Library Documentation: module networkx.algorithms.dag in networkx.algorithms

NAME
    networkx.algorithms.dag - Algorithms for directed acyclic graphs (DAGs).

DESCRIPTION
    Note that most of these functions are only guaranteed to work for DAGs.
    In general, these functions do not check for acyclic-ness, so it is up
    to the user to check for that.

FUNCTIONS
    all_topological_sorts(G, *, backend=None, **backend_kwargs)
        Returns a generator of _all_ topological sorts of the directed graph G.

        A topological sort is a nonunique permutation of the nodes such that an
        edge from u to v implies that u appears before v in the topological sort
        order.

        Parameters
        ----------
        G : NetworkX DiGraph
            A directed graph

        Yields
        ------
        topological_sort_order : list
            a list of nodes in `G`, representing one of the topological sort orders

        Raises
        ------
        NetworkXNotImplemented
            If `G` is not directed
        NetworkXUnfeasible
            If `G` is not acyclic

        Examples
        --------
        To enumerate all topological sorts of directed graph:

        >>> DG = nx.DiGraph([(1, 2), (2, 3), (2, 4)])
        >>> list(nx.all_topological_sorts(DG))
        [[1, 2, 4, 3], [1, 2, 3, 4]]

        Notes
        -----
        Implements an iterative version of the algorithm given in [1].

        References
        ----------
        .. [1] Knuth, Donald E., Szwarcfiter, Jayme L. (1974).
           "A Structured Program to Generate All Topological Sorting Arrangements"
           Information Processing Letters, Volume 2, Issue 6, 1974, Pages 153-157,
           ISSN 0020-0190,
           https://doi.org/10.1016/0020-0190(74)90001-5.
           Elsevier (North-Holland), Amsterdam

    ancestors(G, source, *, backend=None, **backend_kwargs)
        Returns all nodes having a path to `source` in `G`.

        Parameters
        ----------
        G : NetworkX Graph
        source : node in `G`

        Returns
        -------
        set()
            The ancestors of `source` in `G`

        Raises
        ------
        NetworkXError
            If node `source` is not in `G`.

        Examples
        --------
        >>> DG = nx.path_graph(5, create_using=nx.DiGraph)
        >>> sorted(nx.ancestors(DG, 2))
        [0, 1]

        The `source` node is not an ancestor of itself, but can be included manually:

        >>> sorted(nx.ancestors(DG, 2) | {2})
        [0, 1, 2]

        See also
        --------
        descendants

    antichains(G, topo_order=None, *, backend=None, **backend_kwargs)
        Generates antichains from a directed acyclic graph (DAG).

        An antichain is a subset of a partially ordered set such that any
        two elements in the subset are incomparable.

        Parameters
        ----------
        G : NetworkX DiGraph
            A directed acyclic graph (DAG)

        topo_order: list or tuple, optional
            A topological order for G (if None, the function will compute one)

        Yields
        ------
        antichain : list
            a list of nodes in `G` representing an antichain

        Raises
        ------
        NetworkXNotImplemented
            If `G` is not directed

        NetworkXUnfeasible
            If `G` contains a cycle

        Examples
        --------
        >>> DG = nx.DiGraph([(1, 2), (1, 3)])
        >>> list(nx.antichains(DG))
        [[], [3], [2], [2, 3], [1]]

        Notes
        -----
        This function was originally developed by Peter Jipsen and Franco Saliola
        for the SAGE project. It's included in NetworkX with permission from the
        authors. Original SAGE code at:

        https://github.com/sagemath/sage/blob/master/src/sage/combinat/posets/hasse_diagram.py

        References
        ----------
        .. [1] Free Lattices, by R. Freese, J. Jezek and J. B. Nation,
           AMS, Vol 42, 1995, p. 226.

    compute_v_structures(G, *, backend=None, **backend_kwargs)
        Yields 3-node tuples that represent the v-structures in `G`.

        .. deprecated:: 3.4

           `compute_v_structures` actually yields colliders. It will be removed in
           version 3.6. Use `nx.dag.v_structures` or `nx.dag.colliders` instead.

        Colliders are triples in the directed acyclic graph (DAG) where two parent nodes
        point to the same child node. V-structures are colliders where the two parent
        nodes are not adjacent. In a causal graph setting, the parents do not directly
        depend on each other, but conditioning on the child node provides an association.

        Parameters
        ----------
        G : graph
            A networkx `~networkx.DiGraph`.

        Yields
        ------
        A 3-tuple representation of a v-structure
            Each v-structure is a 3-tuple with the parent, collider, and other parent.

        Raises
        ------
        NetworkXNotImplemented
            If `G` is an undirected graph.

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (0, 4), (3, 1), (2, 4), (0, 5), (4, 5), (1, 5)])
        >>> nx.is_directed_acyclic_graph(G)
        True
        >>> list(nx.compute_v_structures(G))
        [(0, 4, 2), (0, 5, 4), (0, 5, 1), (4, 5, 1)]

        See Also
        --------
        v_structures
        colliders

        Notes
        -----
        This function was written to be used on DAGs, however it works on cyclic graphs
        too. Since colliders are referred to in the cyclic causal graph literature
        [2]_ we allow cyclic graphs in this function. It is suggested that you test if
        your input graph is acyclic as in the example if you want that property.

        References
        ----------
        .. [1]  `Pearl's PRIMER <https://bayes.cs.ucla.edu/PRIMER/primer-ch2.pdf>`_
                Ch-2 page 50: v-structures def.
        .. [2] A Hyttinen, P.O. Hoyer, F. Eberhardt, M J ̈arvisalo, (2013)
               "Discovering cyclic causal models with latent variables:
               a general SAT-based procedure", UAI'13: Proceedings of the Twenty-Ninth
               Conference on Uncertainty in Artificial Intelligence, pg 301–310,
               `doi:10.5555/3023638.3023669 <https://dl.acm.org/doi/10.5555/3023638.3023669>`_

    dag_longest_path(G, weight='weight', default_weight=1, topo_order=None, *, backend=None, **backend_kwargs)
        Returns the longest path in a directed acyclic graph (DAG).

        If `G` has edges with `weight` attribute the edge data are used as
        weight values.

        Parameters
        ----------
        G : NetworkX DiGraph
            A directed acyclic graph (DAG)

        weight : str, optional
            Edge data key to use for weight

        default_weight : int, optional
            The weight of edges that do not have a weight attribute

        topo_order: list or tuple, optional
            A topological order for `G` (if None, the function will compute one)

        Returns
        -------
        list
            Longest path

        Raises
        ------
        NetworkXNotImplemented
            If `G` is not directed

        Examples
        --------
        >>> DG = nx.DiGraph(
        ...     [(0, 1, {"cost": 1}), (1, 2, {"cost": 1}), (0, 2, {"cost": 42})]
        ... )
        >>> list(nx.all_simple_paths(DG, 0, 2))
        [[0, 1, 2], [0, 2]]
        >>> nx.dag_longest_path(DG)
        [0, 1, 2]
        >>> nx.dag_longest_path(DG, weight="cost")
        [0, 2]

        In the case where multiple valid topological orderings exist, `topo_order`
        can be used to specify a specific ordering:

        >>> DG = nx.DiGraph([(0, 1), (0, 2)])
        >>> sorted(nx.all_topological_sorts(DG))  # Valid topological orderings
        [[0, 1, 2], [0, 2, 1]]
        >>> nx.dag_longest_path(DG, topo_order=[0, 1, 2])
        [0, 1]
        >>> nx.dag_longest_path(DG, topo_order=[0, 2, 1])
        [0, 2]

        See also
        --------
        dag_longest_path_length

    dag_longest_path_length(G, weight='weight', default_weight=1, *, backend=None, **backend_kwargs)
        Returns the longest path length in a DAG

        Parameters
        ----------
        G : NetworkX DiGraph
            A directed acyclic graph (DAG)

        weight : string, optional
            Edge data key to use for weight

        default_weight : int, optional
            The weight of edges that do not have a weight attribute

        Returns
        -------
        int
            Longest path length

        Raises
        ------
        NetworkXNotImplemented
            If `G` is not directed

        Examples
        --------
        >>> DG = nx.DiGraph(
        ...     [(0, 1, {"cost": 1}), (1, 2, {"cost": 1}), (0, 2, {"cost": 42})]
        ... )
        >>> list(nx.all_simple_paths(DG, 0, 2))
        [[0, 1, 2], [0, 2]]
        >>> nx.dag_longest_path_length(DG)
        2
        >>> nx.dag_longest_path_length(DG, weight="cost")
        42

        See also
        --------
        dag_longest_path

    dag_to_branching(G, *, backend=None, **backend_kwargs)
        Returns a branching representing all (overlapping) paths from
        root nodes to leaf nodes in the given directed acyclic graph.

        As described in :mod:`networkx.algorithms.tree.recognition`, a
        *branching* is a directed forest in which each node has at most one
        parent. In other words, a branching is a disjoint union of
        *arborescences*. For this function, each node of in-degree zero in
        `G` becomes a root of one of the arborescences, and there will be
        one leaf node for each distinct path from that root to a leaf node
        in `G`.

        Each node `v` in `G` with *k* parents becomes *k* distinct nodes in
        the returned branching, one for each parent, and the sub-DAG rooted
        at `v` is duplicated for each copy. The algorithm then recurses on
        the children of each copy of `v`.

        Parameters
        ----------
        G : NetworkX graph
            A directed acyclic graph.

        Returns
        -------
        DiGraph
            The branching in which there is a bijection between root-to-leaf
            paths in `G` (in which multiple paths may share the same leaf)
            and root-to-leaf paths in the branching (in which there is a
            unique path from a root to a leaf).

            Each node has an attribute 'source' whose value is the original
            node to which this node corresponds. No other graph, node, or
            edge attributes are copied into this new graph.

        Raises
        ------
        NetworkXNotImplemented
            If `G` is not directed, or if `G` is a multigraph.

        HasACycle
            If `G` is not acyclic.

        Examples
        --------
        To examine which nodes in the returned branching were produced by
        which original node in the directed acyclic graph, we can collect
        the mapping from source node to new nodes into a dictionary. For
        example, consider the directed diamond graph::

            >>> from collections import defaultdict
            >>> from operator import itemgetter
            >>>
            >>> G = nx.DiGraph(nx.utils.pairwise("abd"))
            >>> G.add_edges_from(nx.utils.pairwise("acd"))
            >>> B = nx.dag_to_branching(G)
            >>>
            >>> sources = defaultdict(set)
            >>> for v, source in B.nodes(data="source"):
            ...     sources[source].add(v)
            >>> len(sources["a"])
            1
            >>> len(sources["d"])
            2

        To copy node attributes from the original graph to the new graph,
        you can use a dictionary like the one constructed in the above
        example::

            >>> for source, nodes in sources.items():
            ...     for v in nodes:
            ...         B.nodes[v].update(G.nodes[source])

        Notes
        -----
        This function is not idempotent in the sense that the node labels in
        the returned branching may be uniquely generated each time the
        function is invoked. In fact, the node labels may not be integers;
        in order to relabel the nodes to be more readable, you can use the
        :func:`networkx.convert_node_labels_to_integers` function.

        The current implementation of this function uses
        :func:`networkx.prefix_tree`, so it is subject to the limitations of
        that function.

    descendants(G, source, *, backend=None, **backend_kwargs)
        Returns all nodes reachable from `source` in `G`.

        Parameters
        ----------
        G : NetworkX Graph
        source : node in `G`

        Returns
        -------
        set()
            The descendants of `source` in `G`

        Raises
        ------
        NetworkXError
            If node `source` is not in `G`.

        Examples
        --------
        >>> DG = nx.path_graph(5, create_using=nx.DiGraph)
        >>> sorted(nx.descendants(DG, 2))
        [3, 4]

        The `source` node is not a descendant of itself, but can be included manually:

        >>> sorted(nx.descendants(DG, 2) | {2})
        [2, 3, 4]

        See also
        --------
        ancestors

    is_aperiodic(G, *, backend=None, **backend_kwargs)
        Returns True if `G` is aperiodic.

        A directed graph is aperiodic if there is no integer k > 1 that
        divides the length of every cycle in the graph.

        Parameters
        ----------
        G : NetworkX DiGraph
            A directed graph

        Returns
        -------
        bool
            True if the graph is aperiodic False otherwise

        Raises
        ------
        NetworkXError
            If `G` is not directed

        Examples
        --------
        A graph consisting of one cycle, the length of which is 2. Therefore ``k = 2``
        divides the length of every cycle in the graph and thus the graph
        is *not aperiodic*::

            >>> DG = nx.DiGraph([(1, 2), (2, 1)])
            >>> nx.is_aperiodic(DG)
            False

        A graph consisting of two cycles: one of length 2 and the other of length 3.
        The cycle lengths are coprime, so there is no single value of k where ``k > 1``
        that divides each cycle length and therefore the graph is *aperiodic*::

            >>> DG = nx.DiGraph([(1, 2), (2, 3), (3, 1), (1, 4), (4, 1)])
            >>> nx.is_aperiodic(DG)
            True

        A graph consisting of two cycles: one of length 2 and the other of length 4.
        The lengths of the cycles share a common factor ``k = 2``, and therefore
        the graph is *not aperiodic*::

            >>> DG = nx.DiGraph([(1, 2), (2, 1), (3, 4), (4, 5), (5, 6), (6, 3)])
            >>> nx.is_aperiodic(DG)
            False

        An acyclic graph, therefore the graph is *not aperiodic*::

            >>> DG = nx.DiGraph([(1, 2), (2, 3)])
            >>> nx.is_aperiodic(DG)
            False

        Notes
        -----
        This uses the method outlined in [1]_, which runs in $O(m)$ time
        given $m$ edges in `G`. Note that a graph is not aperiodic if it is
        acyclic as every integer trivial divides length 0 cycles.

        References
        ----------
        .. [1] Jarvis, J. P.; Shier, D. R. (1996),
           "Graph-theoretic analysis of finite Markov chains,"
           in Shier, D. R.; Wallenius, K. T., Applied Mathematical Modeling:
           A Multidisciplinary Approach, CRC Press.

    is_directed_acyclic_graph(G, *, backend=None, **backend_kwargs)
        Returns True if the graph `G` is a directed acyclic graph (DAG) or
        False if not.

        Parameters
        ----------
        G : NetworkX graph

        Returns
        -------
        bool
            True if `G` is a DAG, False otherwise

        Examples
        --------
        Undirected graph::

            >>> G = nx.Graph([(1, 2), (2, 3)])
            >>> nx.is_directed_acyclic_graph(G)
            False

        Directed graph with cycle::

            >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 1)])
            >>> nx.is_directed_acyclic_graph(G)
            False

        Directed acyclic graph::

            >>> G = nx.DiGraph([(1, 2), (2, 3)])
            >>> nx.is_directed_acyclic_graph(G)
            True

        See also
        --------
        topological_sort

    lexicographical_topological_sort(G, key=None, *, backend=None, **backend_kwargs)
        Generate the nodes in the unique lexicographical topological sort order.

        Generates a unique ordering of nodes by first sorting topologically (for which there are often
        multiple valid orderings) and then additionally by sorting lexicographically.

        A topological sort arranges the nodes of a directed graph so that the
        upstream node of each directed edge precedes the downstream node.
        It is always possible to find a solution for directed graphs that have no cycles.
        There may be more than one valid solution.

        Lexicographical sorting is just sorting alphabetically. It is used here to break ties in the
        topological sort and to determine a single, unique ordering.  This can be useful in comparing
        sort results.

        The lexicographical order can be customized by providing a function to the `key=` parameter.
        The definition of the key function is the same as used in python's built-in `sort()`.
        The function takes a single argument and returns a key to use for sorting purposes.

        Lexicographical sorting can fail if the node names are un-sortable. See the example below.
        The solution is to provide a function to the `key=` argument that returns sortable keys.


        Parameters
        ----------
        G : NetworkX digraph
            A directed acyclic graph (DAG)

        key : function, optional
            A function of one argument that converts a node name to a comparison key.
            It defines and resolves ambiguities in the sort order.  Defaults to the identity function.

        Yields
        ------
        nodes
            Yields the nodes of G in lexicographical topological sort order.

        Raises
        ------
        NetworkXError
            Topological sort is defined for directed graphs only. If the graph `G`
            is undirected, a :exc:`NetworkXError` is raised.

        NetworkXUnfeasible
            If `G` is not a directed acyclic graph (DAG) no topological sort exists
            and a :exc:`NetworkXUnfeasible` exception is raised.  This can also be
            raised if `G` is changed while the returned iterator is being processed

        RuntimeError
            If `G` is changed while the returned iterator is being processed.

        TypeError
            Results from un-sortable node names.
            Consider using `key=` parameter to resolve ambiguities in the sort order.

        Examples
        --------
        >>> DG = nx.DiGraph([(2, 1), (2, 5), (1, 3), (1, 4), (5, 4)])
        >>> list(nx.lexicographical_topological_sort(DG))
        [2, 1, 3, 5, 4]
        >>> list(nx.lexicographical_topological_sort(DG, key=lambda x: -x))
        [2, 5, 1, 4, 3]

        The sort will fail for any graph with integer and string nodes. Comparison of integer to strings
        is not defined in python.  Is 3 greater or less than 'red'?

        >>> DG = nx.DiGraph([(1, "red"), (3, "red"), (1, "green"), (2, "blue")])
        >>> list(nx.lexicographical_topological_sort(DG))
        Traceback (most recent call last):
        ...
        TypeError: '<' not supported between instances of 'str' and 'int'
        ...

        Incomparable nodes can be resolved using a `key` function. This example function
        allows comparison of integers and strings by returning a tuple where the first
        element is True for `str`, False otherwise. The second element is the node name.
        This groups the strings and integers separately so they can be compared only among themselves.

        >>> key = lambda node: (isinstance(node, str), node)
        >>> list(nx.lexicographical_topological_sort(DG, key=key))
        [1, 2, 3, 'blue', 'green', 'red']

        Notes
        -----
        This algorithm is based on a description and proof in
        "Introduction to Algorithms: A Creative Approach" [1]_ .

        See also
        --------
        topological_sort

        References
        ----------
        .. [1] Manber, U. (1989).
           *Introduction to Algorithms - A Creative Approach.* Addison-Wesley.

    topological_generations(G, *, backend=None, **backend_kwargs)
        Stratifies a DAG into generations.

        A topological generation is node collection in which ancestors of a node in each
        generation are guaranteed to be in a previous generation, and any descendants of
        a node are guaranteed to be in a following generation. Nodes are guaranteed to
        be in the earliest possible generation that they can belong to.

        Parameters
        ----------
        G : NetworkX digraph
            A directed acyclic graph (DAG)

        Yields
        ------
        sets of nodes
            Yields sets of nodes representing each generation.

        Raises
        ------
        NetworkXError
            Generations are defined for directed graphs only. If the graph
            `G` is undirected, a :exc:`NetworkXError` is raised.

        NetworkXUnfeasible
            If `G` is not a directed acyclic graph (DAG) no topological generations
            exist and a :exc:`NetworkXUnfeasible` exception is raised.  This can also
            be raised if `G` is changed while the returned iterator is being processed

        RuntimeError
            If `G` is changed while the returned iterator is being processed.

        Examples
        --------
        >>> DG = nx.DiGraph([(2, 1), (3, 1)])
        >>> [sorted(generation) for generation in nx.topological_generations(DG)]
        [[2, 3], [1]]

        Notes
        -----
        The generation in which a node resides can also be determined by taking the
        max-path-distance from the node to the farthest leaf node. That value can
        be obtained with this function using `enumerate(topological_generations(G))`.

        See also
        --------
        topological_sort

    topological_sort(G, *, backend=None, **backend_kwargs)
        Returns a generator of nodes in topologically sorted order.

        A topological sort is a nonunique permutation of the nodes of a
        directed graph such that an edge from u to v implies that u
        appears before v in the topological sort order. This ordering is
        valid only if the graph has no directed cycles.

        Parameters
        ----------
        G : NetworkX digraph
            A directed acyclic graph (DAG)

        Yields
        ------
        nodes
            Yields the nodes in topological sorted order.

        Raises
        ------
        NetworkXError
            Topological sort is defined for directed graphs only. If the graph `G`
            is undirected, a :exc:`NetworkXError` is raised.

        NetworkXUnfeasible
            If `G` is not a directed acyclic graph (DAG) no topological sort exists
            and a :exc:`NetworkXUnfeasible` exception is raised.  This can also be
            raised if `G` is changed while the returned iterator is being processed

        RuntimeError
            If `G` is changed while the returned iterator is being processed.

        Examples
        --------
        To get the reverse order of the topological sort:

        >>> DG = nx.DiGraph([(1, 2), (2, 3)])
        >>> list(reversed(list(nx.topological_sort(DG))))
        [3, 2, 1]

        If your DiGraph naturally has the edges representing tasks/inputs
        and nodes representing people/processes that initiate tasks, then
        topological_sort is not quite what you need. You will have to change
        the tasks to nodes with dependence reflected by edges. The result is
        a kind of topological sort of the edges. This can be done
        with :func:`networkx.line_graph` as follows:

        >>> list(nx.topological_sort(nx.line_graph(DG)))
        [(1, 2), (2, 3)]

        Notes
        -----
        This algorithm is based on a description and proof in
        "Introduction to Algorithms: A Creative Approach" [1]_ .

        See also
        --------
        is_directed_acyclic_graph, lexicographical_topological_sort

        References
        ----------
        .. [1] Manber, U. (1989).
           *Introduction to Algorithms - A Creative Approach.* Addison-Wesley.

    transitive_closure(G, reflexive=False, *, backend=None, **backend_kwargs)
        Returns transitive closure of a graph

        The transitive closure of G = (V,E) is a graph G+ = (V,E+) such that
        for all v, w in V there is an edge (v, w) in E+ if and only if there
        is a path from v to w in G.

        Handling of paths from v to v has some flexibility within this definition.
        A reflexive transitive closure creates a self-loop for the path
        from v to v of length 0. The usual transitive closure creates a
        self-loop only if a cycle exists (a path from v to v with length > 0).
        We also allow an option for no self-loops.

        Parameters
        ----------
        G : NetworkX Graph
            A directed/undirected graph/multigraph.
        reflexive : Bool or None, optional (default: False)
            Determines when cycles create self-loops in the Transitive Closure.
            If True, trivial cycles (length 0) create self-loops. The result
            is a reflexive transitive closure of G.
            If False (the default) non-trivial cycles create self-loops.
            If None, self-loops are not created.

        Returns
        -------
        NetworkX graph
            The transitive closure of `G`

        Raises
        ------
        NetworkXError
            If `reflexive` not in `{None, True, False}`

        Examples
        --------
        The treatment of trivial (i.e. length 0) cycles is controlled by the
        `reflexive` parameter.

        Trivial (i.e. length 0) cycles do not create self-loops when
        ``reflexive=False`` (the default)::

            >>> DG = nx.DiGraph([(1, 2), (2, 3)])
            >>> TC = nx.transitive_closure(DG, reflexive=False)
            >>> TC.edges()
            OutEdgeView([(1, 2), (1, 3), (2, 3)])

        However, nontrivial (i.e. length greater than 0) cycles create self-loops
        when ``reflexive=False`` (the default)::

            >>> DG = nx.DiGraph([(1, 2), (2, 3), (3, 1)])
            >>> TC = nx.transitive_closure(DG, reflexive=False)
            >>> TC.edges()
            OutEdgeView([(1, 2), (1, 3), (1, 1), (2, 3), (2, 1), (2, 2), (3, 1), (3, 2), (3, 3)])

        Trivial cycles (length 0) create self-loops when ``reflexive=True``::

            >>> DG = nx.DiGraph([(1, 2), (2, 3)])
            >>> TC = nx.transitive_closure(DG, reflexive=True)
            >>> TC.edges()
            OutEdgeView([(1, 2), (1, 1), (1, 3), (2, 3), (2, 2), (3, 3)])

        And the third option is not to create self-loops at all when ``reflexive=None``::

            >>> DG = nx.DiGraph([(1, 2), (2, 3), (3, 1)])
            >>> TC = nx.transitive_closure(DG, reflexive=None)
            >>> TC.edges()
            OutEdgeView([(1, 2), (1, 3), (2, 3), (2, 1), (3, 1), (3, 2)])

        References
        ----------
        .. [1] https://www.ics.uci.edu/~eppstein/PADS/PartialOrder.py

    transitive_closure_dag(G, topo_order=None, *, backend=None, **backend_kwargs)
        Returns the transitive closure of a directed acyclic graph.

        This function is faster than the function `transitive_closure`, but fails
        if the graph has a cycle.

        The transitive closure of G = (V,E) is a graph G+ = (V,E+) such that
        for all v, w in V there is an edge (v, w) in E+ if and only if there
        is a non-null path from v to w in G.

        Parameters
        ----------
        G : NetworkX DiGraph
            A directed acyclic graph (DAG)

        topo_order: list or tuple, optional
            A topological order for G (if None, the function will compute one)

        Returns
        -------
        NetworkX DiGraph
            The transitive closure of `G`

        Raises
        ------
        NetworkXNotImplemented
            If `G` is not directed
        NetworkXUnfeasible
            If `G` has a cycle

        Examples
        --------
        >>> DG = nx.DiGraph([(1, 2), (2, 3)])
        >>> TC = nx.transitive_closure_dag(DG)
        >>> TC.edges()
        OutEdgeView([(1, 2), (1, 3), (2, 3)])

        Notes
        -----
        This algorithm is probably simple enough to be well-known but I didn't find
        a mention in the literature.

    transitive_reduction(G, *, backend=None, **backend_kwargs)
        Returns transitive reduction of a directed graph

        The transitive reduction of G = (V,E) is a graph G- = (V,E-) such that
        for all v,w in V there is an edge (v,w) in E- if and only if (v,w) is
        in E and there is no path from v to w in G with length greater than 1.

        Parameters
        ----------
        G : NetworkX DiGraph
            A directed acyclic graph (DAG)

        Returns
        -------
        NetworkX DiGraph
            The transitive reduction of `G`

        Raises
        ------
        NetworkXError
            If `G` is not a directed acyclic graph (DAG) transitive reduction is
            not uniquely defined and a :exc:`NetworkXError` exception is raised.

        Examples
        --------
        To perform transitive reduction on a DiGraph:

        >>> DG = nx.DiGraph([(1, 2), (2, 3), (1, 3)])
        >>> TR = nx.transitive_reduction(DG)
        >>> list(TR.edges)
        [(1, 2), (2, 3)]

        To avoid unnecessary data copies, this implementation does not return a
        DiGraph with node/edge data.
        To perform transitive reduction on a DiGraph and transfer node/edge data:

        >>> DG = nx.DiGraph()
        >>> DG.add_edges_from([(1, 2), (2, 3), (1, 3)], color="red")
        >>> TR = nx.transitive_reduction(DG)
        >>> TR.add_nodes_from(DG.nodes(data=True))
        >>> TR.add_edges_from((u, v, DG.edges[u, v]) for u, v in TR.edges)
        >>> list(TR.edges(data=True))
        [(1, 2, {'color': 'red'}), (2, 3, {'color': 'red'})]

        References
        ----------
        https://en.wikipedia.org/wiki/Transitive_reduction

DATA
    __all__ = ['descendants', 'ancestors', 'topological_sort', 'lexicograp...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\dag.py

networkx.dag_longest_path
Python Library Documentation: function dag_longest_path in module networkx.algorithms.dag

dag_longest_path(G, weight='weight', default_weight=1, topo_order=None, *, backend=None, **backend_kwargs)
    Returns the longest path in a directed acyclic graph (DAG).

    If `G` has edges with `weight` attribute the edge data are used as
    weight values.

    Parameters
    ----------
    G : NetworkX DiGraph
        A directed acyclic graph (DAG)

    weight : str, optional
        Edge data key to use for weight

    default_weight : int, optional
        The weight of edges that do not have a weight attribute

    topo_order: list or tuple, optional
        A topological order for `G` (if None, the function will compute one)

    Returns
    -------
    list
        Longest path

    Raises
    ------
    NetworkXNotImplemented
        If `G` is not directed

    Examples
    --------
    >>> DG = nx.DiGraph(
    ...     [(0, 1, {"cost": 1}), (1, 2, {"cost": 1}), (0, 2, {"cost": 42})]
    ... )
    >>> list(nx.all_simple_paths(DG, 0, 2))
    [[0, 1, 2], [0, 2]]
    >>> nx.dag_longest_path(DG)
    [0, 1, 2]
    >>> nx.dag_longest_path(DG, weight="cost")
    [0, 2]

    In the case where multiple valid topological orderings exist, `topo_order`
    can be used to specify a specific ordering:

    >>> DG = nx.DiGraph([(0, 1), (0, 2)])
    >>> sorted(nx.all_topological_sorts(DG))  # Valid topological orderings
    [[0, 1, 2], [0, 2, 1]]
    >>> nx.dag_longest_path(DG, topo_order=[0, 1, 2])
    [0, 1]
    >>> nx.dag_longest_path(DG, topo_order=[0, 2, 1])
    [0, 2]

    See also
    --------
    dag_longest_path_length
networkx.dag_longest_path_length
Python Library Documentation: function dag_longest_path_length in module networkx.algorithms.dag

dag_longest_path_length(G, weight='weight', default_weight=1, *, backend=None, **backend_kwargs)
    Returns the longest path length in a DAG

    Parameters
    ----------
    G : NetworkX DiGraph
        A directed acyclic graph (DAG)

    weight : string, optional
        Edge data key to use for weight

    default_weight : int, optional
        The weight of edges that do not have a weight attribute

    Returns
    -------
    int
        Longest path length

    Raises
    ------
    NetworkXNotImplemented
        If `G` is not directed

    Examples
    --------
    >>> DG = nx.DiGraph(
    ...     [(0, 1, {"cost": 1}), (1, 2, {"cost": 1}), (0, 2, {"cost": 42})]
    ... )
    >>> list(nx.all_simple_paths(DG, 0, 2))
    [[0, 1, 2], [0, 2]]
    >>> nx.dag_longest_path_length(DG)
    2
    >>> nx.dag_longest_path_length(DG, weight="cost")
    42

    See also
    --------
    dag_longest_path
networkx.dag_to_branching
Python Library Documentation: function dag_to_branching in module networkx.algorithms.dag

dag_to_branching(G, *, backend=None, **backend_kwargs)
    Returns a branching representing all (overlapping) paths from
    root nodes to leaf nodes in the given directed acyclic graph.

    As described in :mod:`networkx.algorithms.tree.recognition`, a
    *branching* is a directed forest in which each node has at most one
    parent. In other words, a branching is a disjoint union of
    *arborescences*. For this function, each node of in-degree zero in
    `G` becomes a root of one of the arborescences, and there will be
    one leaf node for each distinct path from that root to a leaf node
    in `G`.

    Each node `v` in `G` with *k* parents becomes *k* distinct nodes in
    the returned branching, one for each parent, and the sub-DAG rooted
    at `v` is duplicated for each copy. The algorithm then recurses on
    the children of each copy of `v`.

    Parameters
    ----------
    G : NetworkX graph
        A directed acyclic graph.

    Returns
    -------
    DiGraph
        The branching in which there is a bijection between root-to-leaf
        paths in `G` (in which multiple paths may share the same leaf)
        and root-to-leaf paths in the branching (in which there is a
        unique path from a root to a leaf).

        Each node has an attribute 'source' whose value is the original
        node to which this node corresponds. No other graph, node, or
        edge attributes are copied into this new graph.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is not directed, or if `G` is a multigraph.

    HasACycle
        If `G` is not acyclic.

    Examples
    --------
    To examine which nodes in the returned branching were produced by
    which original node in the directed acyclic graph, we can collect
    the mapping from source node to new nodes into a dictionary. For
    example, consider the directed diamond graph::

        >>> from collections import defaultdict
        >>> from operator import itemgetter
        >>>
        >>> G = nx.DiGraph(nx.utils.pairwise("abd"))
        >>> G.add_edges_from(nx.utils.pairwise("acd"))
        >>> B = nx.dag_to_branching(G)
        >>>
        >>> sources = defaultdict(set)
        >>> for v, source in B.nodes(data="source"):
        ...     sources[source].add(v)
        >>> len(sources["a"])
        1
        >>> len(sources["d"])
        2

    To copy node attributes from the original graph to the new graph,
    you can use a dictionary like the one constructed in the above
    example::

        >>> for source, nodes in sources.items():
        ...     for v in nodes:
        ...         B.nodes[v].update(G.nodes[source])

    Notes
    -----
    This function is not idempotent in the sense that the node labels in
    the returned branching may be uniquely generated each time the
    function is invoked. In fact, the node labels may not be integers;
    in order to relabel the nodes to be more readable, you can use the
    :func:`networkx.convert_node_labels_to_integers` function.

    The current implementation of this function uses
    :func:`networkx.prefix_tree`, so it is subject to the limitations of
    that function.
networkx.davis_southern_women_graph
Python Library Documentation: function davis_southern_women_graph in module networkx.generators.social

davis_southern_women_graph(*, backend=None, **backend_kwargs)
    Returns Davis Southern women social network.

    This is a bipartite graph.

    References
    ----------
    .. [1] A. Davis, Gardner, B. B., Gardner, M. R., 1941. Deep South.
        University of Chicago Press, Chicago, IL.
networkx.dedensify
Python Library Documentation: function dedensify in module networkx.algorithms.summarization

dedensify(G, threshold, prefix=None, copy=True, *, backend=None, **backend_kwargs)
    Compresses neighborhoods around high-degree nodes

    Reduces the number of edges to high-degree nodes by adding compressor nodes
    that summarize multiple edges of the same type to high-degree nodes (nodes
    with a degree greater than a given threshold).  Dedensification also has
    the added benefit of reducing the number of edges around high-degree nodes.
    The implementation currently supports graphs with a single edge type.

    Parameters
    ----------
    G: graph
       A networkx graph
    threshold: int
       Minimum degree threshold of a node to be considered a high degree node.
       The threshold must be greater than or equal to 2.
    prefix: str or None, optional (default: None)
       An optional prefix for denoting compressor nodes
    copy: bool, optional (default: True)
       Indicates if dedensification should be done inplace

    Returns
    -------
    dedensified networkx graph : (graph, set)
        2-tuple of the dedensified graph and set of compressor nodes

    Notes
    -----
    According to the algorithm in [1]_, removes edges in a graph by
    compressing/decompressing the neighborhoods around high degree nodes by
    adding compressor nodes that summarize multiple edges of the same type
    to high-degree nodes.  Dedensification will only add a compressor node when
    doing so will reduce the total number of edges in the given graph. This
    implementation currently supports graphs with a single edge type.

    Examples
    --------
    Dedensification will only add compressor nodes when doing so would result
    in fewer edges::

        >>> original_graph = nx.DiGraph()
        >>> original_graph.add_nodes_from(
        ...     ["1", "2", "3", "4", "5", "6", "A", "B", "C"]
        ... )
        >>> original_graph.add_edges_from(
        ...     [
        ...         ("1", "C"), ("1", "B"),
        ...         ("2", "C"), ("2", "B"), ("2", "A"),
        ...         ("3", "B"), ("3", "A"), ("3", "6"),
        ...         ("4", "C"), ("4", "B"), ("4", "A"),
        ...         ("5", "B"), ("5", "A"),
        ...         ("6", "5"),
        ...         ("A", "6")
        ...     ]
        ... )
        >>> c_graph, c_nodes = nx.dedensify(original_graph, threshold=2)
        >>> original_graph.number_of_edges()
        15
        >>> c_graph.number_of_edges()
        14

    A dedensified, directed graph can be "densified" to reconstruct the
    original graph::

        >>> original_graph = nx.DiGraph()
        >>> original_graph.add_nodes_from(
        ...     ["1", "2", "3", "4", "5", "6", "A", "B", "C"]
        ... )
        >>> original_graph.add_edges_from(
        ...     [
        ...         ("1", "C"), ("1", "B"),
        ...         ("2", "C"), ("2", "B"), ("2", "A"),
        ...         ("3", "B"), ("3", "A"), ("3", "6"),
        ...         ("4", "C"), ("4", "B"), ("4", "A"),
        ...         ("5", "B"), ("5", "A"),
        ...         ("6", "5"),
        ...         ("A", "6")
        ...     ]
        ... )
        >>> c_graph, c_nodes = nx.dedensify(original_graph, threshold=2)
        >>> # re-densifies the compressed graph into the original graph
        >>> for c_node in c_nodes:
        ...     all_neighbors = set(nx.all_neighbors(c_graph, c_node))
        ...     out_neighbors = set(c_graph.neighbors(c_node))
        ...     for out_neighbor in out_neighbors:
        ...         c_graph.remove_edge(c_node, out_neighbor)
        ...     in_neighbors = all_neighbors - out_neighbors
        ...     for in_neighbor in in_neighbors:
        ...         c_graph.remove_edge(in_neighbor, c_node)
        ...         for out_neighbor in out_neighbors:
        ...             c_graph.add_edge(in_neighbor, out_neighbor)
        ...     c_graph.remove_node(c_node)
        ...
        >>> nx.is_isomorphic(original_graph, c_graph)
        True

    References
    ----------
    .. [1] Maccioni, A., & Abadi, D. J. (2016, August).
       Scalable pattern matching over compressed graphs via dedensification.
       In Proceedings of the 22nd ACM SIGKDD International Conference on
       Knowledge Discovery and Data Mining (pp. 1755-1764).
       http://www.cs.umd.edu/~abadi/papers/graph-dedense.pdf
networkx.degree
Python Library Documentation: function degree in module networkx.classes.function

degree(G, nbunch=None, weight=None)
    Returns a degree view of single node or of nbunch of nodes.
    If nbunch is omitted, then return degrees of *all* nodes.

    This function wraps the :func:`G.degree <networkx.Graph.degree>` property.
networkx.degree_alg
Python Library Documentation: module networkx.algorithms.centrality.degree_alg in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.degree_alg - Degree centrality measures.

FUNCTIONS
    degree_centrality(G, *, backend=None, **backend_kwargs)
        Compute the degree centrality for nodes.

        The degree centrality for a node v is the fraction of nodes it
        is connected to.

        Parameters
        ----------
        G : graph
          A networkx graph

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with degree centrality as the value.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
        >>> nx.degree_centrality(G)
        {0: 1.0, 1: 1.0, 2: 0.6666666666666666, 3: 0.6666666666666666}

        See Also
        --------
        betweenness_centrality, load_centrality, eigenvector_centrality

        Notes
        -----
        The degree centrality values are normalized by dividing by the maximum
        possible degree in a simple graph n-1 where n is the number of nodes in G.

        For multigraphs or graphs with self loops the maximum degree might
        be higher than n-1 and values of degree centrality greater than 1
        are possible.

    in_degree_centrality(G, *, backend=None, **backend_kwargs)
        Compute the in-degree centrality for nodes.

        The in-degree centrality for a node v is the fraction of nodes its
        incoming edges are connected to.

        Parameters
        ----------
        G : graph
            A NetworkX graph

        Returns
        -------
        nodes : dictionary
            Dictionary of nodes with in-degree centrality as values.

        Raises
        ------
        NetworkXNotImplemented
            If G is undirected.

        Examples
        --------
        >>> G = nx.DiGraph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
        >>> nx.in_degree_centrality(G)
        {0: 0.0, 1: 0.3333333333333333, 2: 0.6666666666666666, 3: 0.6666666666666666}

        See Also
        --------
        degree_centrality, out_degree_centrality

        Notes
        -----
        The degree centrality values are normalized by dividing by the maximum
        possible degree in a simple graph n-1 where n is the number of nodes in G.

        For multigraphs or graphs with self loops the maximum degree might
        be higher than n-1 and values of degree centrality greater than 1
        are possible.

    out_degree_centrality(G, *, backend=None, **backend_kwargs)
        Compute the out-degree centrality for nodes.

        The out-degree centrality for a node v is the fraction of nodes its
        outgoing edges are connected to.

        Parameters
        ----------
        G : graph
            A NetworkX graph

        Returns
        -------
        nodes : dictionary
            Dictionary of nodes with out-degree centrality as values.

        Raises
        ------
        NetworkXNotImplemented
            If G is undirected.

        Examples
        --------
        >>> G = nx.DiGraph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
        >>> nx.out_degree_centrality(G)
        {0: 1.0, 1: 0.6666666666666666, 2: 0.0, 3: 0.0}

        See Also
        --------
        degree_centrality, in_degree_centrality

        Notes
        -----
        The degree centrality values are normalized by dividing by the maximum
        possible degree in a simple graph n-1 where n is the number of nodes in G.

        For multigraphs or graphs with self loops the maximum degree might
        be higher than n-1 and values of degree centrality greater than 1
        are possible.

DATA
    __all__ = ['degree_centrality', 'in_degree_centrality', 'out_degree_ce...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\degree_alg.py

networkx.degree_assortativity_coefficient
Python Library Documentation: function degree_assortativity_coefficient in module networkx.algorithms.assortativity.correlation

degree_assortativity_coefficient(G, x='out', y='in', weight=None, nodes=None, *, backend=None, **backend_kwargs)
    Compute degree assortativity of graph.

    Assortativity measures the similarity of connections
    in the graph with respect to the node degree.

    Parameters
    ----------
    G : NetworkX graph

    x: string ('in','out')
       The degree type for source node (directed graphs only).

    y: string ('in','out')
       The degree type for target node (directed graphs only).

    weight: string or None, optional (default=None)
       The edge attribute that holds the numerical value used
       as a weight.  If None, then each edge has weight 1.
       The degree is the sum of the edge weights adjacent to the node.

    nodes: list or iterable (optional)
        Compute degree assortativity only for nodes in container.
        The default is all nodes.

    Returns
    -------
    r : float
       Assortativity of graph by degree.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> r = nx.degree_assortativity_coefficient(G)
    >>> print(f"{r:3.1f}")
    -0.5

    See Also
    --------
    attribute_assortativity_coefficient
    numeric_assortativity_coefficient
    degree_mixing_dict
    degree_mixing_matrix

    Notes
    -----
    This computes Eq. (21) in Ref. [1]_ , where e is the joint
    probability distribution (mixing matrix) of the degrees.  If G is
    directed than the matrix e is the joint probability of the
    user-specified degree type for the source and target.

    References
    ----------
    .. [1] M. E. J. Newman, Mixing patterns in networks,
       Physical Review E, 67 026126, 2003
    .. [2] Foster, J.G., Foster, D.V., Grassberger, P. & Paczuski, M.
       Edge direction and the structure of networks, PNAS 107, 10815-20 (2010).
networkx.degree_centrality
Python Library Documentation: function degree_centrality in module networkx.algorithms.centrality.degree_alg

degree_centrality(G, *, backend=None, **backend_kwargs)
    Compute the degree centrality for nodes.

    The degree centrality for a node v is the fraction of nodes it
    is connected to.

    Parameters
    ----------
    G : graph
      A networkx graph

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with degree centrality as the value.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
    >>> nx.degree_centrality(G)
    {0: 1.0, 1: 1.0, 2: 0.6666666666666666, 3: 0.6666666666666666}

    See Also
    --------
    betweenness_centrality, load_centrality, eigenvector_centrality

    Notes
    -----
    The degree centrality values are normalized by dividing by the maximum
    possible degree in a simple graph n-1 where n is the number of nodes in G.

    For multigraphs or graphs with self loops the maximum degree might
    be higher than n-1 and values of degree centrality greater than 1
    are possible.
networkx.degree_histogram
Python Library Documentation: function degree_histogram in module networkx.classes.function

degree_histogram(G)
    Returns a list of the frequency of each degree value.

    Parameters
    ----------
    G : Networkx graph
       A graph

    Returns
    -------
    hist : list
       A list of frequencies of degrees.
       The degree values are the index in the list.

    Notes
    -----
    Note: the bins are width one, hence len(list) can be large
    (Order(number_of_edges))
networkx.degree_mixing_dict
Python Library Documentation: function degree_mixing_dict in module networkx.algorithms.assortativity.mixing

degree_mixing_dict(G, x='out', y='in', weight=None, nodes=None, normalized=False, *, backend=None, **backend_kwargs)
    Returns dictionary representation of mixing matrix for degree.

    Parameters
    ----------
    G : graph
        NetworkX graph object.

    x: string ('in','out')
       The degree type for source node (directed graphs only).

    y: string ('in','out')
       The degree type for target node (directed graphs only).

    weight: string or None, optional (default=None)
       The edge attribute that holds the numerical value used
       as a weight.  If None, then each edge has weight 1.
       The degree is the sum of the edge weights adjacent to the node.

    normalized : bool (default=False)
        Return counts if False or probabilities if True.

    Returns
    -------
    d: dictionary
       Counts or joint probability of occurrence of degree pairs.
networkx.degree_mixing_matrix
Python Library Documentation: function degree_mixing_matrix in module networkx.algorithms.assortativity.mixing

degree_mixing_matrix(G, x='out', y='in', weight=None, nodes=None, normalized=True, mapping=None, *, backend=None, **backend_kwargs)
    Returns mixing matrix for attribute.

    Parameters
    ----------
    G : graph
       NetworkX graph object.

    x: string ('in','out')
       The degree type for source node (directed graphs only).

    y: string ('in','out')
       The degree type for target node (directed graphs only).

    nodes: list or iterable (optional)
        Build the matrix using only nodes in container.
        The default is all nodes.

    weight: string or None, optional (default=None)
       The edge attribute that holds the numerical value used
       as a weight.  If None, then each edge has weight 1.
       The degree is the sum of the edge weights adjacent to the node.

    normalized : bool (default=True)
       Return counts if False or probabilities if True.

    mapping : dictionary, optional
       Mapping from node degree to integer index in matrix.
       If not specified, an arbitrary ordering will be used.

    Returns
    -------
    m: numpy array
       Counts, or joint probability, of occurrence of node degree.

    Notes
    -----
    Definitions of degree mixing matrix vary on whether the matrix
    should include rows for degree values that don't arise. Here we
    do not include such empty-rows. But you can force them to appear
    by inputting a `mapping` that includes those values. See examples.

    Examples
    --------
    >>> G = nx.star_graph(3)
    >>> mix_mat = nx.degree_mixing_matrix(G)
    >>> mix_mat
    array([[0. , 0.5],
           [0.5, 0. ]])

    If you want every possible degree to appear as a row, even if no nodes
    have that degree, use `mapping` as follows,

    >>> max_degree = max(deg for n, deg in G.degree)
    >>> mapping = {x: x for x in range(max_degree + 1)}  # identity mapping
    >>> mix_mat = nx.degree_mixing_matrix(G, mapping=mapping)
    >>> mix_mat
    array([[0. , 0. , 0. , 0. ],
           [0. , 0. , 0. , 0.5],
           [0. , 0. , 0. , 0. ],
           [0. , 0.5, 0. , 0. ]])
networkx.degree_pearson_correlation_coefficient
Python Library Documentation: function degree_pearson_correlation_coefficient in module networkx.algorithms.assortativity.correlation

degree_pearson_correlation_coefficient(G, x='out', y='in', weight=None, nodes=None, *, backend=None, **backend_kwargs)
    Compute degree assortativity of graph.

    Assortativity measures the similarity of connections
    in the graph with respect to the node degree.

    This is the same as degree_assortativity_coefficient but uses the
    potentially faster scipy.stats.pearsonr function.

    Parameters
    ----------
    G : NetworkX graph

    x: string ('in','out')
       The degree type for source node (directed graphs only).

    y: string ('in','out')
       The degree type for target node (directed graphs only).

    weight: string or None, optional (default=None)
       The edge attribute that holds the numerical value used
       as a weight.  If None, then each edge has weight 1.
       The degree is the sum of the edge weights adjacent to the node.

    nodes: list or iterable (optional)
        Compute pearson correlation of degrees only for specified nodes.
        The default is all nodes.

    Returns
    -------
    r : float
       Assortativity of graph by degree.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> r = nx.degree_pearson_correlation_coefficient(G)
    >>> print(f"{r:3.1f}")
    -0.5

    Notes
    -----
    This calls scipy.stats.pearsonr.

    References
    ----------
    .. [1] M. E. J. Newman, Mixing patterns in networks
           Physical Review E, 67 026126, 2003
    .. [2] Foster, J.G., Foster, D.V., Grassberger, P. & Paczuski, M.
       Edge direction and the structure of networks, PNAS 107, 10815-20 (2010).
networkx.degree_seq
Python Library Documentation: module networkx.generators.degree_seq in networkx.generators

NAME
    networkx.generators.degree_seq - Generate graphs with a given degree sequence or expected degree sequence.

FUNCTIONS
    configuration_model(deg_sequence, create_using=None, seed=None, *, backend=None, **backend_kwargs)
        Returns a random graph with the given degree sequence.

        The configuration model generates a random pseudograph (graph with
        parallel edges and self loops) by randomly assigning edges to
        match the given degree sequence.

        Parameters
        ----------
        deg_sequence :  list of nonnegative integers
            Each list entry corresponds to the degree of a node.
        create_using : NetworkX graph constructor, optional (default MultiGraph)
            Graph type to create. If graph instance, then cleared before populated.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        G : MultiGraph
            A graph with the specified degree sequence.
            Nodes are labeled starting at 0 with an index
            corresponding to the position in deg_sequence.

        Raises
        ------
        NetworkXError
            If the degree sequence does not have an even sum.

        See Also
        --------
        is_graphical

        Notes
        -----
        As described by Newman [1]_.

        A non-graphical degree sequence (not realizable by some simple
        graph) is allowed since this function returns graphs with self
        loops and parallel edges.  An exception is raised if the degree
        sequence does not have an even sum.

        This configuration model construction process can lead to
        duplicate edges and loops.  You can remove the self-loops and
        parallel edges (see below) which will likely result in a graph
        that doesn't have the exact degree sequence specified.

        The density of self-loops and parallel edges tends to decrease as
        the number of nodes increases. However, typically the number of
        self-loops will approach a Poisson distribution with a nonzero mean,
        and similarly for the number of parallel edges.  Consider a node
        with *k* stubs. The probability of being joined to another stub of
        the same node is basically (*k* - *1*) / *N*, where *k* is the
        degree and *N* is the number of nodes. So the probability of a
        self-loop scales like *c* / *N* for some constant *c*. As *N* grows,
        this means we expect *c* self-loops. Similarly for parallel edges.

        References
        ----------
        .. [1] M.E.J. Newman, "The structure and function of complex networks",
           SIAM REVIEW 45-2, pp 167-256, 2003.

        Examples
        --------
        You can create a degree sequence following a particular distribution
        by using the one of the distribution functions in
        :mod:`~networkx.utils.random_sequence` (or one of your own). For
        example, to create an undirected multigraph on one hundred nodes
        with degree sequence chosen from the power law distribution:

        >>> sequence = nx.random_powerlaw_tree_sequence(100, tries=5000)
        >>> G = nx.configuration_model(sequence)
        >>> len(G)
        100
        >>> actual_degrees = [d for v, d in G.degree()]
        >>> actual_degrees == sequence
        True

        The returned graph is a multigraph, which may have parallel
        edges. To remove any parallel edges from the returned graph:

        >>> G = nx.Graph(G)

        Similarly, to remove self-loops:

        >>> G.remove_edges_from(nx.selfloop_edges(G))

    degree_sequence_tree(deg_sequence, create_using=None, *, backend=None, **backend_kwargs)
        Make a tree for the given degree sequence.

        A tree has #nodes-#edges=1 so
        the degree sequence must have
        len(deg_sequence)-sum(deg_sequence)/2=1

    directed_configuration_model(in_degree_sequence, out_degree_sequence, create_using=None, seed=None, *, backend=None, **backend_kwargs)
        Returns a directed_random graph with the given degree sequences.

        The configuration model generates a random directed pseudograph
        (graph with parallel edges and self loops) by randomly assigning
        edges to match the given degree sequences.

        Parameters
        ----------
        in_degree_sequence :  list of nonnegative integers
           Each list entry corresponds to the in-degree of a node.
        out_degree_sequence :  list of nonnegative integers
           Each list entry corresponds to the out-degree of a node.
        create_using : NetworkX graph constructor, optional (default MultiDiGraph)
            Graph type to create. If graph instance, then cleared before populated.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        G : MultiDiGraph
            A graph with the specified degree sequences.
            Nodes are labeled starting at 0 with an index
            corresponding to the position in deg_sequence.

        Raises
        ------
        NetworkXError
            If the degree sequences do not have the same sum.

        See Also
        --------
        configuration_model

        Notes
        -----
        Algorithm as described by Newman [1]_.

        A non-graphical degree sequence (not realizable by some simple
        graph) is allowed since this function returns graphs with self
        loops and parallel edges.  An exception is raised if the degree
        sequences does not have the same sum.

        This configuration model construction process can lead to
        duplicate edges and loops.  You can remove the self-loops and
        parallel edges (see below) which will likely result in a graph
        that doesn't have the exact degree sequence specified.  This
        "finite-size effect" decreases as the size of the graph increases.

        References
        ----------
        .. [1] Newman, M. E. J. and Strogatz, S. H. and Watts, D. J.
           Random graphs with arbitrary degree distributions and their applications
           Phys. Rev. E, 64, 026118 (2001)

        Examples
        --------
        One can modify the in- and out-degree sequences from an existing
        directed graph in order to create a new directed graph. For example,
        here we modify the directed path graph:

        >>> D = nx.DiGraph([(0, 1), (1, 2), (2, 3)])
        >>> din = list(d for n, d in D.in_degree())
        >>> dout = list(d for n, d in D.out_degree())
        >>> din.append(1)
        >>> dout[0] = 2
        >>> # We now expect an edge from node 0 to a new node, node 3.
        ... D = nx.directed_configuration_model(din, dout)

        The returned graph is a directed multigraph, which may have parallel
        edges. To remove any parallel edges from the returned graph:

        >>> D = nx.DiGraph(D)

        Similarly, to remove self-loops:

        >>> D.remove_edges_from(nx.selfloop_edges(D))

    directed_havel_hakimi_graph(in_deg_sequence, out_deg_sequence, create_using=None, *, backend=None, **backend_kwargs)
        Returns a directed graph with the given degree sequences.

        Parameters
        ----------
        in_deg_sequence :  list of integers
            Each list entry corresponds to the in-degree of a node.
        out_deg_sequence : list of integers
            Each list entry corresponds to the out-degree of a node.
        create_using : NetworkX graph constructor, optional (default DiGraph)
            Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : DiGraph
            A graph with the specified degree sequences.
            Nodes are labeled starting at 0 with an index
            corresponding to the position in deg_sequence

        Raises
        ------
        NetworkXError
            If the degree sequences are not digraphical.

        See Also
        --------
        configuration_model

        Notes
        -----
        Algorithm as described by Kleitman and Wang [1]_.

        References
        ----------
        .. [1] D.J. Kleitman and D.L. Wang
           Algorithms for Constructing Graphs and Digraphs with Given Valences
           and Factors Discrete Mathematics, 6(1), pp. 79-88 (1973)

    expected_degree_graph(w, seed=None, selfloops=True, *, backend=None, **backend_kwargs)
        Returns a random graph with given expected degrees.

        Given a sequence of expected degrees $W=(w_0,w_1,\ldots,w_{n-1})$
        of length $n$ this algorithm assigns an edge between node $u$ and
        node $v$ with probability

        .. math::

           p_{uv} = \frac{w_u w_v}{\sum_k w_k} .

        Parameters
        ----------
        w : list
            The list of expected degrees.
        selfloops: bool (default=True)
            Set to False to remove the possibility of self-loop edges.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        Graph

        Examples
        --------
        >>> z = [10 for i in range(100)]
        >>> G = nx.expected_degree_graph(z)

        Notes
        -----
        The nodes have integer labels corresponding to index of expected degrees
        input sequence.

        The complexity of this algorithm is $\mathcal{O}(n+m)$ where $n$ is the
        number of nodes and $m$ is the expected number of edges.

        The model in [1]_ includes the possibility of self-loop edges.
        Set selfloops=False to produce a graph without self loops.

        For finite graphs this model doesn't produce exactly the given
        expected degree sequence.  Instead the expected degrees are as
        follows.

        For the case without self loops (selfloops=False),

        .. math::

           E[deg(u)] = \sum_{v \ne u} p_{uv}
                    = w_u \left( 1 - \frac{w_u}{\sum_k w_k} \right) .


        NetworkX uses the standard convention that a self-loop edge counts 2
        in the degree of a node, so with self loops (selfloops=True),

        .. math::

           E[deg(u)] =  \sum_{v \ne u} p_{uv}  + 2 p_{uu}
                    = w_u \left( 1 + \frac{w_u}{\sum_k w_k} \right) .

        References
        ----------
        .. [1] Fan Chung and L. Lu, Connected components in random graphs with
           given expected degree sequences, Ann. Combinatorics, 6,
           pp. 125-145, 2002.
        .. [2] Joel Miller and Aric Hagberg,
           Efficient generation of networks with given expected degrees,
           in Algorithms and Models for the Web-Graph (WAW 2011),
           Alan Frieze, Paul Horn, and Paweł Prałat (Eds), LNCS 6732,
           pp. 115-126, 2011.

    havel_hakimi_graph(deg_sequence, create_using=None, *, backend=None, **backend_kwargs)
        Returns a simple graph with given degree sequence constructed
        using the Havel-Hakimi algorithm.

        Parameters
        ----------
        deg_sequence: list of integers
            Each integer corresponds to the degree of a node (need not be sorted).
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Directed graphs are not allowed.

        Raises
        ------
        NetworkXException
            For a non-graphical degree sequence (i.e. one
            not realizable by some simple graph).

        Notes
        -----
        The Havel-Hakimi algorithm constructs a simple graph by
        successively connecting the node of highest degree to other nodes
        of highest degree, resorting remaining nodes by degree, and
        repeating the process. The resulting graph has a high
        degree-associativity.  Nodes are labeled 1,.., len(deg_sequence),
        corresponding to their position in deg_sequence.

        The basic algorithm is from Hakimi [1]_ and was generalized by
        Kleitman and Wang [2]_.

        References
        ----------
        .. [1] Hakimi S., On Realizability of a Set of Integers as
           Degrees of the Vertices of a Linear Graph. I,
           Journal of SIAM, 10(3), pp. 496-506 (1962)
        .. [2] Kleitman D.J. and Wang D.L.
           Algorithms for Constructing Graphs and Digraphs with Given Valences
           and Factors  Discrete Mathematics, 6(1), pp. 79-88 (1973)

    random_degree_sequence_graph(sequence, seed=None, tries=10, *, backend=None, **backend_kwargs)
        Returns a simple random graph with the given degree sequence.

        If the maximum degree $d_m$ in the sequence is $O(m^{1/4})$ then the
        algorithm produces almost uniform random graphs in $O(m d_m)$ time
        where $m$ is the number of edges.

        Parameters
        ----------
        sequence :  list of integers
            Sequence of degrees
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        tries : int, optional
            Maximum number of tries to create a graph

        Returns
        -------
        G : Graph
            A graph with the specified degree sequence.
            Nodes are labeled starting at 0 with an index
            corresponding to the position in the sequence.

        Raises
        ------
        NetworkXUnfeasible
            If the degree sequence is not graphical.
        NetworkXError
            If a graph is not produced in specified number of tries

        See Also
        --------
        is_graphical, configuration_model

        Notes
        -----
        The generator algorithm [1]_ is not guaranteed to produce a graph.

        References
        ----------
        .. [1] Moshen Bayati, Jeong Han Kim, and Amin Saberi,
           A sequential algorithm for generating random graphs.
           Algorithmica, Volume 58, Number 4, 860-910,
           DOI: 10.1007/s00453-009-9340-1

        Examples
        --------
        >>> sequence = [1, 2, 2, 3]
        >>> G = nx.random_degree_sequence_graph(sequence, seed=42)
        >>> sorted(d for n, d in G.degree())
        [1, 2, 2, 3]

DATA
    __all__ = ['configuration_model', 'directed_configuration_model', 'exp...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\degree_seq.py

networkx.degree_sequence_tree
Python Library Documentation: function degree_sequence_tree in module networkx.generators.degree_seq

degree_sequence_tree(deg_sequence, create_using=None, *, backend=None, **backend_kwargs)
    Make a tree for the given degree sequence.

    A tree has #nodes-#edges=1 so
    the degree sequence must have
    len(deg_sequence)-sum(deg_sequence)/2=1
networkx.dense
Python Library Documentation: module networkx.algorithms.shortest_paths.dense in networkx.algorithms.shortest_paths

NAME
    networkx.algorithms.shortest_paths.dense - Floyd-Warshall algorithm for shortest paths.

FUNCTIONS
    floyd_warshall(G, weight='weight', *, backend=None, **backend_kwargs)
        Find all-pairs shortest path lengths using Floyd's algorithm.

        Parameters
        ----------
        G : NetworkX graph

        weight: string, optional (default= 'weight')
           Edge data key corresponding to the edge weight.


        Returns
        -------
        distance : dict
           A dictionary,  keyed by source and target, of shortest paths distances
           between nodes.

        Examples
        --------
        >>> G = nx.DiGraph()
        >>> G.add_weighted_edges_from(
        ...     [(0, 1, 5), (1, 2, 2), (2, 3, -3), (1, 3, 10), (3, 2, 8)]
        ... )
        >>> fw = nx.floyd_warshall(G, weight="weight")
        >>> results = {a: dict(b) for a, b in fw.items()}
        >>> print(results)
        {0: {0: 0, 1: 5, 2: 7, 3: 4}, 1: {1: 0, 2: 2, 3: -1, 0: inf}, 2: {2: 0, 3: -3, 0: inf, 1: inf}, 3: {3: 0, 2: 8, 0: inf, 1: inf}}

        Notes
        -----
        Floyd's algorithm is appropriate for finding shortest paths
        in dense graphs or graphs with negative weights when Dijkstra's algorithm
        fails.  This algorithm can still fail if there are negative cycles.
        It has running time $O(n^3)$ with running space of $O(n^2)$.

        See Also
        --------
        floyd_warshall_predecessor_and_distance
        floyd_warshall_numpy
        all_pairs_shortest_path
        all_pairs_shortest_path_length

    floyd_warshall_numpy(G, nodelist=None, weight='weight', *, backend=None, **backend_kwargs)
        Find all-pairs shortest path lengths using Floyd's algorithm.

        This algorithm for finding shortest paths takes advantage of
        matrix representations of a graph and works well for dense
        graphs where all-pairs shortest path lengths are desired.
        The results are returned as a NumPy array, distance[i, j],
        where i and j are the indexes of two nodes in nodelist.
        The entry distance[i, j] is the distance along a shortest
        path from i to j. If no path exists the distance is Inf.

        Parameters
        ----------
        G : NetworkX graph

        nodelist : list, optional (default=G.nodes)
           The rows and columns are ordered by the nodes in nodelist.
           If nodelist is None then the ordering is produced by G.nodes.
           Nodelist should include all nodes in G.

        weight: string, optional (default='weight')
           Edge data key corresponding to the edge weight.

        Returns
        -------
        distance : 2D numpy.ndarray
            A numpy array of shortest path distances between nodes.
            If there is no path between two nodes the value is Inf.

        Examples
        --------
        >>> G = nx.DiGraph()
        >>> G.add_weighted_edges_from(
        ...     [(0, 1, 5), (1, 2, 2), (2, 3, -3), (1, 3, 10), (3, 2, 8)]
        ... )
        >>> nx.floyd_warshall_numpy(G)
        array([[ 0.,  5.,  7.,  4.],
               [inf,  0.,  2., -1.],
               [inf, inf,  0., -3.],
               [inf, inf,  8.,  0.]])

        Notes
        -----
        Floyd's algorithm is appropriate for finding shortest paths in
        dense graphs or graphs with negative weights when Dijkstra's
        algorithm fails. This algorithm can still fail if there are negative
        cycles. It has running time $O(n^3)$ with running space of $O(n^2)$.

        Raises
        ------
        NetworkXError
            If nodelist is not a list of the nodes in G.

    floyd_warshall_predecessor_and_distance(G, weight='weight', *, backend=None, **backend_kwargs)
        Find all-pairs shortest path lengths using Floyd's algorithm.

        Parameters
        ----------
        G : NetworkX graph

        weight: string, optional (default= 'weight')
           Edge data key corresponding to the edge weight.

        Returns
        -------
        predecessor,distance : dictionaries
           Dictionaries, keyed by source and target, of predecessors and distances
           in the shortest path.

        Examples
        --------
        >>> G = nx.DiGraph()
        >>> G.add_weighted_edges_from(
        ...     [
        ...         ("s", "u", 10),
        ...         ("s", "x", 5),
        ...         ("u", "v", 1),
        ...         ("u", "x", 2),
        ...         ("v", "y", 1),
        ...         ("x", "u", 3),
        ...         ("x", "v", 5),
        ...         ("x", "y", 2),
        ...         ("y", "s", 7),
        ...         ("y", "v", 6),
        ...     ]
        ... )
        >>> predecessors, _ = nx.floyd_warshall_predecessor_and_distance(G)
        >>> print(nx.reconstruct_path("s", "v", predecessors))
        ['s', 'x', 'u', 'v']

        Notes
        -----
        Floyd's algorithm is appropriate for finding shortest paths
        in dense graphs or graphs with negative weights when Dijkstra's algorithm
        fails.  This algorithm can still fail if there are negative cycles.
        It has running time $O(n^3)$ with running space of $O(n^2)$.

        See Also
        --------
        floyd_warshall
        floyd_warshall_numpy
        all_pairs_shortest_path
        all_pairs_shortest_path_length

    reconstruct_path(source, target, predecessors, *, backend=None, **backend_kwargs)
        Reconstruct a path from source to target using the predecessors
        dict as returned by floyd_warshall_predecessor_and_distance

        Parameters
        ----------
        source : node
           Starting node for path

        target : node
           Ending node for path

        predecessors: dictionary
           Dictionary, keyed by source and target, of predecessors in the
           shortest path, as returned by floyd_warshall_predecessor_and_distance

        Returns
        -------
        path : list
           A list of nodes containing the shortest path from source to target

           If source and target are the same, an empty list is returned

        Notes
        -----
        This function is meant to give more applicability to the
        floyd_warshall_predecessor_and_distance function

        See Also
        --------
        floyd_warshall_predecessor_and_distance

DATA
    __all__ = ['floyd_warshall', 'floyd_warshall_predecessor_and_distance'...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\shortest_paths\dense.py

networkx.dense_gnm_random_graph
Python Library Documentation: function dense_gnm_random_graph in module networkx.generators.random_graphs

dense_gnm_random_graph(n, m, seed=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns a $G_{n,m}$ random graph.

    In the $G_{n,m}$ model, a graph is chosen uniformly at random from the set
    of all graphs with $n$ nodes and $m$ edges.

    This algorithm should be faster than :func:`gnm_random_graph` for dense
    graphs.

    Parameters
    ----------
    n : int
        The number of nodes.
    m : int
        The number of edges.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    See Also
    --------
    gnm_random_graph

    Notes
    -----
    Algorithm by Keith M. Briggs Mar 31, 2006.
    Inspired by Knuth's Algorithm S (Selection sampling technique),
    in section 3.4.2 of [1]_.

    References
    ----------
    .. [1] Donald E. Knuth, The Art of Computer Programming,
        Volume 2/Seminumerical algorithms, Third Edition, Addison-Wesley, 1997.
networkx.density
Python Library Documentation: function density in module networkx.classes.function

density(G)
    Returns the density of a graph.

    The density for undirected graphs is

    .. math::

       d = \frac{2m}{n(n-1)},

    and for directed graphs is

    .. math::

       d = \frac{m}{n(n-1)},

    where `n` is the number of nodes and `m`  is the number of edges in `G`.

    Notes
    -----
    The density is 0 for a graph without edges and 1 for a complete graph.
    The density of multigraphs can be higher than 1.

    Self loops are counted in the total number of edges so graphs with self
    loops can have density higher than 1.
networkx.desargues_graph
Python Library Documentation: function desargues_graph in module networkx.generators.small

desargues_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Desargues Graph

    The Desargues Graph is a non-planar, distance-transitive cubic graph
    with 20 nodes and 30 edges [1]_.
    It is a symmetric graph. It can be represented in LCF notation
    as [5,-5,9,-9]^5 [2]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Desargues Graph with 20 nodes and 30 edges

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Desargues_graph
    .. [2] https://mathworld.wolfram.com/DesarguesGraph.html
networkx.descendants
Python Library Documentation: function descendants in module networkx.algorithms.dag

descendants(G, source, *, backend=None, **backend_kwargs)
    Returns all nodes reachable from `source` in `G`.

    Parameters
    ----------
    G : NetworkX Graph
    source : node in `G`

    Returns
    -------
    set()
        The descendants of `source` in `G`

    Raises
    ------
    NetworkXError
        If node `source` is not in `G`.

    Examples
    --------
    >>> DG = nx.path_graph(5, create_using=nx.DiGraph)
    >>> sorted(nx.descendants(DG, 2))
    [3, 4]

    The `source` node is not a descendant of itself, but can be included manually:

    >>> sorted(nx.descendants(DG, 2) | {2})
    [2, 3, 4]

    See also
    --------
    ancestors
networkx.descendants_at_distance
Python Library Documentation: function descendants_at_distance in module networkx.algorithms.traversal.breadth_first_search

descendants_at_distance(G, source, distance, *, backend=None, **backend_kwargs)
    Returns all nodes at a fixed `distance` from `source` in `G`.

    Parameters
    ----------
    G : NetworkX graph
        A graph
    source : node in `G`
    distance : the distance of the wanted nodes from `source`

    Returns
    -------
    set()
        The descendants of `source` in `G` at the given `distance` from `source`

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> nx.descendants_at_distance(G, 2, 2)
    {0, 4}
    >>> H = nx.DiGraph()
    >>> H.add_edges_from([(0, 1), (0, 2), (1, 3), (1, 4), (2, 5), (2, 6)])
    >>> nx.descendants_at_distance(H, 0, 2)
    {3, 4, 5, 6}
    >>> nx.descendants_at_distance(H, 5, 0)
    {5}
    >>> nx.descendants_at_distance(H, 5, 1)
    set()
networkx.dfs_edges
Python Library Documentation: function dfs_edges in module networkx.algorithms.traversal.depth_first_search

dfs_edges(G, source=None, depth_limit=None, *, sort_neighbors=None, backend=None, **backend_kwargs)
    Iterate over edges in a depth-first-search (DFS).

    Perform a depth-first-search over the nodes of `G` and yield
    the edges in order. This may not generate all edges in `G`
    (see `~networkx.algorithms.traversal.edgedfs.edge_dfs`).

    Parameters
    ----------
    G : NetworkX graph

    source : node, optional
       Specify starting node for depth-first search and yield edges in
       the component reachable from source.

    depth_limit : int, optional (default=len(G))
       Specify the maximum search depth.

    sort_neighbors : function (default=None)
        A function that takes an iterator over nodes as the input, and
        returns an iterable of the same nodes with a custom ordering.
        For example, `sorted` will sort the nodes in increasing order.

    Yields
    ------
    edge: 2-tuple of nodes
       Yields edges resulting from the depth-first-search.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> list(nx.dfs_edges(G, source=0))
    [(0, 1), (1, 2), (2, 3), (3, 4)]
    >>> list(nx.dfs_edges(G, source=0, depth_limit=2))
    [(0, 1), (1, 2)]

    Notes
    -----
    If a source is not specified then a source is chosen arbitrarily and
    repeatedly until all components in the graph are searched.

    The implementation of this function is adapted from David Eppstein's
    depth-first search function in PADS [1]_, with modifications
    to allow depth limits based on the Wikipedia article
    "Depth-limited search" [2]_.

    See Also
    --------
    dfs_preorder_nodes
    dfs_postorder_nodes
    dfs_labeled_edges
    :func:`~networkx.algorithms.traversal.edgedfs.edge_dfs`
    :func:`~networkx.algorithms.traversal.breadth_first_search.bfs_edges`

    References
    ----------
    .. [1] http://www.ics.uci.edu/~eppstein/PADS
    .. [2] https://en.wikipedia.org/wiki/Depth-limited_search
networkx.dfs_labeled_edges
Python Library Documentation: function dfs_labeled_edges in module networkx.algorithms.traversal.depth_first_search

dfs_labeled_edges(G, source=None, depth_limit=None, *, sort_neighbors=None, backend=None, **backend_kwargs)
    Iterate over edges in a depth-first-search (DFS) labeled by type.

    Parameters
    ----------
    G : NetworkX graph

    source : node, optional
       Specify starting node for depth-first search and return edges in
       the component reachable from source.

    depth_limit : int, optional (default=len(G))
       Specify the maximum search depth.

    sort_neighbors : function (default=None)
        A function that takes an iterator over nodes as the input, and
        returns an iterable of the same nodes with a custom ordering.
        For example, `sorted` will sort the nodes in increasing order.

    Returns
    -------
    edges: generator
       A generator of triples of the form (*u*, *v*, *d*), where (*u*,
       *v*) is the edge being explored in the depth-first search and *d*
       is one of the strings 'forward', 'nontree', 'reverse', or 'reverse-depth_limit'.
       A 'forward' edge is one in which *u* has been visited but *v* has
       not. A 'nontree' edge is one in which both *u* and *v* have been
       visited but the edge is not in the DFS tree. A 'reverse' edge is
       one in which both *u* and *v* have been visited and the edge is in
       the DFS tree. When the `depth_limit` is reached via a 'forward' edge,
       a 'reverse' edge is immediately generated rather than the subtree
       being explored. To indicate this flavor of 'reverse' edge, the string
       yielded is 'reverse-depth_limit'.

    Examples
    --------

    The labels reveal the complete transcript of the depth-first search
    algorithm in more detail than, for example, :func:`dfs_edges`::

        >>> from pprint import pprint
        >>>
        >>> G = nx.DiGraph([(0, 1), (1, 2), (2, 1)])
        >>> pprint(list(nx.dfs_labeled_edges(G, source=0)))
        [(0, 0, 'forward'),
         (0, 1, 'forward'),
         (1, 2, 'forward'),
         (2, 1, 'nontree'),
         (1, 2, 'reverse'),
         (0, 1, 'reverse'),
         (0, 0, 'reverse')]

    Notes
    -----
    If a source is not specified then a source is chosen arbitrarily and
    repeatedly until all components in the graph are searched.

    The implementation of this function is adapted from David Eppstein's
    depth-first search function in `PADS`_, with modifications
    to allow depth limits based on the Wikipedia article
    "`Depth-limited search`_".

    .. _PADS: http://www.ics.uci.edu/~eppstein/PADS
    .. _Depth-limited search: https://en.wikipedia.org/wiki/Depth-limited_search

    See Also
    --------
    dfs_edges
    dfs_preorder_nodes
    dfs_postorder_nodes
networkx.dfs_postorder_nodes
Python Library Documentation: function dfs_postorder_nodes in module networkx.algorithms.traversal.depth_first_search

dfs_postorder_nodes(G, source=None, depth_limit=None, *, sort_neighbors=None, backend=None, **backend_kwargs)
    Generate nodes in a depth-first-search post-ordering starting at source.

    Parameters
    ----------
    G : NetworkX graph

    source : node, optional
       Specify starting node for depth-first search.

    depth_limit : int, optional (default=len(G))
       Specify the maximum search depth.

    sort_neighbors : function (default=None)
        A function that takes an iterator over nodes as the input, and
        returns an iterable of the same nodes with a custom ordering.
        For example, `sorted` will sort the nodes in increasing order.

    Returns
    -------
    nodes: generator
       A generator of nodes in a depth-first-search post-ordering.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> list(nx.dfs_postorder_nodes(G, source=0))
    [4, 3, 2, 1, 0]
    >>> list(nx.dfs_postorder_nodes(G, source=0, depth_limit=2))
    [1, 0]

    Notes
    -----
    If a source is not specified then a source is chosen arbitrarily and
    repeatedly until all components in the graph are searched.

    The implementation of this function is adapted from David Eppstein's
    depth-first search function in `PADS`_, with modifications
    to allow depth limits based on the Wikipedia article
    "`Depth-limited search`_".

    .. _PADS: http://www.ics.uci.edu/~eppstein/PADS
    .. _Depth-limited search: https://en.wikipedia.org/wiki/Depth-limited_search

    See Also
    --------
    dfs_edges
    dfs_preorder_nodes
    dfs_labeled_edges
    :func:`~networkx.algorithms.traversal.edgedfs.edge_dfs`
    :func:`~networkx.algorithms.traversal.breadth_first_search.bfs_tree`
networkx.dfs_predecessors
Python Library Documentation: function dfs_predecessors in module networkx.algorithms.traversal.depth_first_search

dfs_predecessors(G, source=None, depth_limit=None, *, sort_neighbors=None, backend=None, **backend_kwargs)
    Returns dictionary of predecessors in depth-first-search from source.

    Parameters
    ----------
    G : NetworkX graph

    source : node, optional
       Specify starting node for depth-first search.
       Note that you will get predecessors for all nodes in the
       component containing `source`. This input only specifies
       where the DFS starts.

    depth_limit : int, optional (default=len(G))
       Specify the maximum search depth.

    sort_neighbors : function (default=None)
        A function that takes an iterator over nodes as the input, and
        returns an iterable of the same nodes with a custom ordering.
        For example, `sorted` will sort the nodes in increasing order.

    Returns
    -------
    pred: dict
       A dictionary with nodes as keys and predecessor nodes as values.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.dfs_predecessors(G, source=0)
    {1: 0, 2: 1, 3: 2}
    >>> nx.dfs_predecessors(G, source=0, depth_limit=2)
    {1: 0, 2: 1}

    Notes
    -----
    If a source is not specified then a source is chosen arbitrarily and
    repeatedly until all components in the graph are searched.

    The implementation of this function is adapted from David Eppstein's
    depth-first search function in `PADS`_, with modifications
    to allow depth limits based on the Wikipedia article
    "`Depth-limited search`_".

    .. _PADS: http://www.ics.uci.edu/~eppstein/PADS
    .. _Depth-limited search: https://en.wikipedia.org/wiki/Depth-limited_search

    See Also
    --------
    dfs_preorder_nodes
    dfs_postorder_nodes
    dfs_labeled_edges
    :func:`~networkx.algorithms.traversal.edgedfs.edge_dfs`
    :func:`~networkx.algorithms.traversal.breadth_first_search.bfs_tree`
networkx.dfs_preorder_nodes
Python Library Documentation: function dfs_preorder_nodes in module networkx.algorithms.traversal.depth_first_search

dfs_preorder_nodes(G, source=None, depth_limit=None, *, sort_neighbors=None, backend=None, **backend_kwargs)
    Generate nodes in a depth-first-search pre-ordering starting at source.

    Parameters
    ----------
    G : NetworkX graph

    source : node, optional
       Specify starting node for depth-first search and return nodes in
       the component reachable from source.

    depth_limit : int, optional (default=len(G))
       Specify the maximum search depth.

    sort_neighbors : function (default=None)
        A function that takes an iterator over nodes as the input, and
        returns an iterable of the same nodes with a custom ordering.
        For example, `sorted` will sort the nodes in increasing order.

    Returns
    -------
    nodes: generator
       A generator of nodes in a depth-first-search pre-ordering.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> list(nx.dfs_preorder_nodes(G, source=0))
    [0, 1, 2, 3, 4]
    >>> list(nx.dfs_preorder_nodes(G, source=0, depth_limit=2))
    [0, 1, 2]

    Notes
    -----
    If a source is not specified then a source is chosen arbitrarily and
    repeatedly until all components in the graph are searched.

    The implementation of this function is adapted from David Eppstein's
    depth-first search function in `PADS`_, with modifications
    to allow depth limits based on the Wikipedia article
    "`Depth-limited search`_".

    .. _PADS: http://www.ics.uci.edu/~eppstein/PADS
    .. _Depth-limited search: https://en.wikipedia.org/wiki/Depth-limited_search

    See Also
    --------
    dfs_edges
    dfs_postorder_nodes
    dfs_labeled_edges
    :func:`~networkx.algorithms.traversal.breadth_first_search.bfs_edges`
networkx.dfs_successors
Python Library Documentation: function dfs_successors in module networkx.algorithms.traversal.depth_first_search

dfs_successors(G, source=None, depth_limit=None, *, sort_neighbors=None, backend=None, **backend_kwargs)
    Returns dictionary of successors in depth-first-search from source.

    Parameters
    ----------
    G : NetworkX graph

    source : node, optional
       Specify starting node for depth-first search.
       Note that you will get successors for all nodes in the
       component containing `source`. This input only specifies
       where the DFS starts.

    depth_limit : int, optional (default=len(G))
       Specify the maximum search depth.

    sort_neighbors : function (default=None)
        A function that takes an iterator over nodes as the input, and
        returns an iterable of the same nodes with a custom ordering.
        For example, `sorted` will sort the nodes in increasing order.

    Returns
    -------
    succ: dict
       A dictionary with nodes as keys and list of successor nodes as values.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> nx.dfs_successors(G, source=0)
    {0: [1], 1: [2], 2: [3], 3: [4]}
    >>> nx.dfs_successors(G, source=0, depth_limit=2)
    {0: [1], 1: [2]}

    Notes
    -----
    If a source is not specified then a source is chosen arbitrarily and
    repeatedly until all components in the graph are searched.

    The implementation of this function is adapted from David Eppstein's
    depth-first search function in `PADS`_, with modifications
    to allow depth limits based on the Wikipedia article
    "`Depth-limited search`_".

    .. _PADS: http://www.ics.uci.edu/~eppstein/PADS
    .. _Depth-limited search: https://en.wikipedia.org/wiki/Depth-limited_search

    See Also
    --------
    dfs_preorder_nodes
    dfs_postorder_nodes
    dfs_labeled_edges
    :func:`~networkx.algorithms.traversal.edgedfs.edge_dfs`
    :func:`~networkx.algorithms.traversal.breadth_first_search.bfs_tree`
networkx.dfs_tree
Python Library Documentation: function dfs_tree in module networkx.algorithms.traversal.depth_first_search

dfs_tree(G, source=None, depth_limit=None, *, sort_neighbors=None, backend=None, **backend_kwargs)
    Returns oriented tree constructed from a depth-first-search from source.

    Parameters
    ----------
    G : NetworkX graph

    source : node, optional
       Specify starting node for depth-first search.

    depth_limit : int, optional (default=len(G))
       Specify the maximum search depth.

    sort_neighbors : function (default=None)
        A function that takes an iterator over nodes as the input, and
        returns an iterable of the same nodes with a custom ordering.
        For example, `sorted` will sort the nodes in increasing order.

    Returns
    -------
    T : NetworkX DiGraph
       An oriented tree

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> T = nx.dfs_tree(G, source=0, depth_limit=2)
    >>> list(T.edges())
    [(0, 1), (1, 2)]
    >>> T = nx.dfs_tree(G, source=0)
    >>> list(T.edges())
    [(0, 1), (1, 2), (2, 3), (3, 4)]

    See Also
    --------
    dfs_preorder_nodes
    dfs_postorder_nodes
    dfs_labeled_edges
    :func:`~networkx.algorithms.traversal.edgedfs.edge_dfs`
    :func:`~networkx.algorithms.traversal.breadth_first_search.bfs_tree`
networkx.diameter
Python Library Documentation: function diameter in module networkx.algorithms.distance_measures

diameter(G, e=None, usebounds=False, weight=None, *, backend=None, **backend_kwargs)
    Returns the diameter of the graph G.

    The diameter is the maximum eccentricity.

    Parameters
    ----------
    G : NetworkX graph
       A graph

    e : eccentricity dictionary, optional
      A precomputed dictionary of eccentricities.

    weight : string, function, or None
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

        If this is None, every edge has weight/distance/cost 1.

        Weights stored as floating point values can lead to small round-off
        errors in distances. Use integer weights to avoid this.

        Weights should be positive, since they are distances.

    Returns
    -------
    d : integer
       Diameter of graph

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
    >>> nx.diameter(G)
    3

    See Also
    --------
    eccentricity
networkx.diamond_graph
Python Library Documentation: function diamond_graph in module networkx.generators.small

diamond_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Diamond graph

    The Diamond Graph is  planar undirected graph with 4 nodes and 5 edges.
    It is also sometimes known as the double triangle graph or kite graph [1]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Diamond Graph with 4 nodes and 5 edges

    References
    ----------
    .. [1] https://mathworld.wolfram.com/DiamondGraph.html
networkx.difference
Python Library Documentation: function difference in module networkx.algorithms.operators.binary

difference(G, H, *, backend=None, **backend_kwargs)
    Returns a new graph that contains the edges that exist in G but not in H.

    The node sets of H and G must be the same.

    Parameters
    ----------
    G,H : graph
       A NetworkX graph. G and H must have the same node sets.

    Returns
    -------
    D : A new graph with the same type as G.

    Notes
    -----
    Attributes from the graph, nodes, and edges are not copied to the new
    graph.  If you want a new graph of the difference of G and H with
    the attributes (including edge data) from G use remove_nodes_from()
    as follows:

    >>> G = nx.path_graph(3)
    >>> H = nx.path_graph(5)
    >>> R = G.copy()
    >>> R.remove_nodes_from(n for n in G if n in H)

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (1, 2), (1, 3)])
    >>> H = nx.Graph([(0, 1), (1, 2), (0, 3)])
    >>> R = nx.difference(G, H)
    >>> R.nodes
    NodeView((0, 1, 2, 3))
    >>> R.edges
    EdgeView([(0, 2), (1, 3)])
networkx.digraph
Python Library Documentation: module networkx.classes.digraph in networkx.classes

NAME
    networkx.classes.digraph - Base class for directed graphs.

CLASSES
    networkx.classes.graph.Graph(builtins.object)
        DiGraph

    class DiGraph(networkx.classes.graph.Graph)
     |  DiGraph(incoming_graph_data=None, **attr)
     |
     |  Base class for directed graphs.
     |
     |  A DiGraph stores nodes and edges with optional data, or attributes.
     |
     |  DiGraphs hold directed edges.  Self loops are allowed but multiple
     |  (parallel) edges are not.
     |
     |  Nodes can be arbitrary (hashable) Python objects with optional
     |  key/value attributes. By convention `None` is not used as a node.
     |
     |  Edges are represented as links between nodes with optional
     |  key/value attributes.
     |
     |  Parameters
     |  ----------
     |  incoming_graph_data : input graph (optional, default: None)
     |      Data to initialize graph. If None (default) an empty
     |      graph is created.  The data can be any format that is supported
     |      by the to_networkx_graph() function, currently including edge list,
     |      dict of dicts, dict of lists, NetworkX graph, 2D NumPy array, SciPy
     |      sparse matrix, or PyGraphviz graph.
     |
     |  attr : keyword arguments, optional (default= no attributes)
     |      Attributes to add to graph as key=value pairs.
     |
     |  See Also
     |  --------
     |  Graph
     |  MultiGraph
     |  MultiDiGraph
     |
     |  Examples
     |  --------
     |  Create an empty graph structure (a "null graph") with no nodes and
     |  no edges.
     |
     |  >>> G = nx.DiGraph()
     |
     |  G can be grown in several ways.
     |
     |  **Nodes:**
     |
     |  Add one node at a time:
     |
     |  >>> G.add_node(1)
     |
     |  Add the nodes from any container (a list, dict, set or
     |  even the lines from a file or the nodes from another graph).
     |
     |  >>> G.add_nodes_from([2, 3])
     |  >>> G.add_nodes_from(range(100, 110))
     |  >>> H = nx.path_graph(10)
     |  >>> G.add_nodes_from(H)
     |
     |  In addition to strings and integers any hashable Python object
     |  (except None) can represent a node, e.g. a customized node object,
     |  or even another Graph.
     |
     |  >>> G.add_node(H)
     |
     |  **Edges:**
     |
     |  G can also be grown by adding edges.
     |
     |  Add one edge,
     |
     |  >>> G.add_edge(1, 2)
     |
     |  a list of edges,
     |
     |  >>> G.add_edges_from([(1, 2), (1, 3)])
     |
     |  or a collection of edges,
     |
     |  >>> G.add_edges_from(H.edges)
     |
     |  If some edges connect nodes not yet in the graph, the nodes
     |  are added automatically.  There are no errors when adding
     |  nodes or edges that already exist.
     |
     |  **Attributes:**
     |
     |  Each graph, node, and edge can hold key/value attribute pairs
     |  in an associated attribute dictionary (the keys must be hashable).
     |  By default these are empty, but can be added or changed using
     |  add_edge, add_node or direct manipulation of the attribute
     |  dictionaries named graph, node and edge respectively.
     |
     |  >>> G = nx.DiGraph(day="Friday")
     |  >>> G.graph
     |  {'day': 'Friday'}
     |
     |  Add node attributes using add_node(), add_nodes_from() or G.nodes
     |
     |  >>> G.add_node(1, time="5pm")
     |  >>> G.add_nodes_from([3], time="2pm")
     |  >>> G.nodes[1]
     |  {'time': '5pm'}
     |  >>> G.nodes[1]["room"] = 714
     |  >>> del G.nodes[1]["room"]  # remove attribute
     |  >>> list(G.nodes(data=True))
     |  [(1, {'time': '5pm'}), (3, {'time': '2pm'})]
     |
     |  Add edge attributes using add_edge(), add_edges_from(), subscript
     |  notation, or G.edges.
     |
     |  >>> G.add_edge(1, 2, weight=4.7)
     |  >>> G.add_edges_from([(3, 4), (4, 5)], color="red")
     |  >>> G.add_edges_from([(1, 2, {"color": "blue"}), (2, 3, {"weight": 8})])
     |  >>> G[1][2]["weight"] = 4.7
     |  >>> G.edges[1, 2]["weight"] = 4
     |
     |  Warning: we protect the graph data structure by making `G.edges[1, 2]` a
     |  read-only dict-like structure. However, you can assign to attributes
     |  in e.g. `G.edges[1, 2]`. Thus, use 2 sets of brackets to add/change
     |  data attributes: `G.edges[1, 2]['weight'] = 4`
     |  (For multigraphs: `MG.edges[u, v, key][name] = value`).
     |
     |  **Shortcuts:**
     |
     |  Many common graph features allow python syntax to speed reporting.
     |
     |  >>> 1 in G  # check if node in graph
     |  True
     |  >>> [n for n in G if n < 3]  # iterate through nodes
     |  [1, 2]
     |  >>> len(G)  # number of nodes in graph
     |  5
     |
     |  Often the best way to traverse all edges of a graph is via the neighbors.
     |  The neighbors are reported as an adjacency-dict `G.adj` or `G.adjacency()`
     |
     |  >>> for n, nbrsdict in G.adjacency():
     |  ...     for nbr, eattr in nbrsdict.items():
     |  ...         if "weight" in eattr:
     |  ...             # Do something useful with the edges
     |  ...             pass
     |
     |  But the edges reporting object is often more convenient:
     |
     |  >>> for u, v, weight in G.edges(data="weight"):
     |  ...     if weight is not None:
     |  ...         # Do something useful with the edges
     |  ...         pass
     |
     |  **Reporting:**
     |
     |  Simple graph information is obtained using object-attributes and methods.
     |  Reporting usually provides views instead of containers to reduce memory
     |  usage. The views update as the graph is updated similarly to dict-views.
     |  The objects `nodes`, `edges` and `adj` provide access to data attributes
     |  via lookup (e.g. `nodes[n]`, `edges[u, v]`, `adj[u][v]`) and iteration
     |  (e.g. `nodes.items()`, `nodes.data('color')`,
     |  `nodes.data('color', default='blue')` and similarly for `edges`)
     |  Views exist for `nodes`, `edges`, `neighbors()`/`adj` and `degree`.
     |
     |  For details on these and other miscellaneous methods, see below.
     |
     |  **Subclasses (Advanced):**
     |
     |  The Graph class uses a dict-of-dict-of-dict data structure.
     |  The outer dict (node_dict) holds adjacency information keyed by node.
     |  The next dict (adjlist_dict) represents the adjacency information and holds
     |  edge data keyed by neighbor.  The inner dict (edge_attr_dict) represents
     |  the edge data and holds edge attribute values keyed by attribute names.
     |
     |  Each of these three dicts can be replaced in a subclass by a user defined
     |  dict-like object. In general, the dict-like features should be
     |  maintained but extra features can be added. To replace one of the
     |  dicts create a new graph class by changing the class(!) variable
     |  holding the factory for that dict-like structure. The variable names are
     |  node_dict_factory, node_attr_dict_factory, adjlist_inner_dict_factory,
     |  adjlist_outer_dict_factory, edge_attr_dict_factory and graph_attr_dict_factory.
     |
     |  node_dict_factory : function, (default: dict)
     |      Factory function to be used to create the dict containing node
     |      attributes, keyed by node id.
     |      It should require no arguments and return a dict-like object
     |
     |  node_attr_dict_factory: function, (default: dict)
     |      Factory function to be used to create the node attribute
     |      dict which holds attribute values keyed by attribute name.
     |      It should require no arguments and return a dict-like object
     |
     |  adjlist_outer_dict_factory : function, (default: dict)
     |      Factory function to be used to create the outer-most dict
     |      in the data structure that holds adjacency info keyed by node.
     |      It should require no arguments and return a dict-like object.
     |
     |  adjlist_inner_dict_factory : function, optional (default: dict)
     |      Factory function to be used to create the adjacency list
     |      dict which holds edge data keyed by neighbor.
     |      It should require no arguments and return a dict-like object
     |
     |  edge_attr_dict_factory : function, optional (default: dict)
     |      Factory function to be used to create the edge attribute
     |      dict which holds attribute values keyed by attribute name.
     |      It should require no arguments and return a dict-like object.
     |
     |  graph_attr_dict_factory : function, (default: dict)
     |      Factory function to be used to create the graph attribute
     |      dict which holds attribute values keyed by attribute name.
     |      It should require no arguments and return a dict-like object.
     |
     |  Typically, if your extension doesn't impact the data structure all
     |  methods will inherited without issue except: `to_directed/to_undirected`.
     |  By default these methods create a DiGraph/Graph class and you probably
     |  want them to create your extension of a DiGraph/Graph. To facilitate
     |  this we define two class variables that you can set in your subclass.
     |
     |  to_directed_class : callable, (default: DiGraph or MultiDiGraph)
     |      Class to create a new graph structure in the `to_directed` method.
     |      If `None`, a NetworkX class (DiGraph or MultiDiGraph) is used.
     |
     |  to_undirected_class : callable, (default: Graph or MultiGraph)
     |      Class to create a new graph structure in the `to_undirected` method.
     |      If `None`, a NetworkX class (Graph or MultiGraph) is used.
     |
     |  **Subclassing Example**
     |
     |  Create a low memory graph class that effectively disallows edge
     |  attributes by using a single attribute dict for all edges.
     |  This reduces the memory used, but you lose edge attributes.
     |
     |  >>> class ThinGraph(nx.Graph):
     |  ...     all_edge_dict = {"weight": 1}
     |  ...
     |  ...     def single_edge_dict(self):
     |  ...         return self.all_edge_dict
     |  ...
     |  ...     edge_attr_dict_factory = single_edge_dict
     |  >>> G = ThinGraph()
     |  >>> G.add_edge(2, 1)
     |  >>> G[2][1]
     |  {'weight': 1}
     |  >>> G.add_edge(2, 2)
     |  >>> G[2][1] is G[2][2]
     |  True
     |
     |  Method resolution order:
     |      DiGraph
     |      networkx.classes.graph.Graph
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __init__(self, incoming_graph_data=None, **attr)
     |      Initialize a graph with edges, name, or graph attributes.
     |
     |      Parameters
     |      ----------
     |      incoming_graph_data : input graph (optional, default: None)
     |          Data to initialize graph.  If None (default) an empty
     |          graph is created.  The data can be an edge list, or any
     |          NetworkX graph object.  If the corresponding optional Python
     |          packages are installed the data can also be a 2D NumPy array, a
     |          SciPy sparse array, or a PyGraphviz graph.
     |
     |      attr : keyword arguments, optional (default= no attributes)
     |          Attributes to add to graph as key=value pairs.
     |
     |      See Also
     |      --------
     |      convert
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G = nx.Graph(name="my graph")
     |      >>> e = [(1, 2), (2, 3), (3, 4)]  # list of edges
     |      >>> G = nx.Graph(e)
     |
     |      Arbitrary graph attribute pairs (key=value) may be assigned
     |
     |      >>> G = nx.Graph(e, day="Friday")
     |      >>> G.graph
     |      {'day': 'Friday'}
     |
     |  add_edge(self, u_of_edge, v_of_edge, **attr)
     |      Add an edge between u and v.
     |
     |      The nodes u and v will be automatically added if they are
     |      not already in the graph.
     |
     |      Edge attributes can be specified with keywords or by directly
     |      accessing the edge's attribute dictionary. See examples below.
     |
     |      Parameters
     |      ----------
     |      u_of_edge, v_of_edge : nodes
     |          Nodes can be, for example, strings or numbers.
     |          Nodes must be hashable (and not None) Python objects.
     |      attr : keyword arguments, optional
     |          Edge data (or labels or objects) can be assigned using
     |          keyword arguments.
     |
     |      See Also
     |      --------
     |      add_edges_from : add a collection of edges
     |
     |      Notes
     |      -----
     |      Adding an edge that already exists updates the edge data.
     |
     |      Many NetworkX algorithms designed for weighted graphs use
     |      an edge attribute (by default `weight`) to hold a numerical value.
     |
     |      Examples
     |      --------
     |      The following all add the edge e=(1, 2) to graph G:
     |
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> e = (1, 2)
     |      >>> G.add_edge(1, 2)  # explicit two-node form
     |      >>> G.add_edge(*e)  # single edge as tuple of two nodes
     |      >>> G.add_edges_from([(1, 2)])  # add edges from iterable container
     |
     |      Associate data to edges using keywords:
     |
     |      >>> G.add_edge(1, 2, weight=3)
     |      >>> G.add_edge(1, 3, weight=7, capacity=15, length=342.7)
     |
     |      For non-string attribute keys, use subscript notation.
     |
     |      >>> G.add_edge(1, 2)
     |      >>> G[1][2].update({0: 5})
     |      >>> G.edges[1, 2].update({0: 5})
     |
     |  add_edges_from(self, ebunch_to_add, **attr)
     |      Add all the edges in ebunch_to_add.
     |
     |      Parameters
     |      ----------
     |      ebunch_to_add : container of edges
     |          Each edge given in the container will be added to the
     |          graph. The edges must be given as 2-tuples (u, v) or
     |          3-tuples (u, v, d) where d is a dictionary containing edge data.
     |      attr : keyword arguments, optional
     |          Edge data (or labels or objects) can be assigned using
     |          keyword arguments.
     |
     |      See Also
     |      --------
     |      add_edge : add a single edge
     |      add_weighted_edges_from : convenient way to add weighted edges
     |
     |      Notes
     |      -----
     |      Adding the same edge twice has no effect but any edge data
     |      will be updated when each duplicate edge is added.
     |
     |      Edge attributes specified in an ebunch take precedence over
     |      attributes specified via keyword arguments.
     |
     |      When adding edges from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_edges)`, and pass this
     |      object to `G.add_edges_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_edges_from([(0, 1), (1, 2)])  # using a list of edge tuples
     |      >>> e = zip(range(0, 3), range(1, 4))
     |      >>> G.add_edges_from(e)  # Add the path graph 0-1-2-3
     |
     |      Associate data to edges
     |
     |      >>> G.add_edges_from([(1, 2), (2, 3)], weight=3)
     |      >>> G.add_edges_from([(3, 4), (1, 4)], label="WN2898")
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 4)])
     |      >>> # Grow graph by one new node, adding edges to all existing nodes.
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_edges_from(((5, n) for n in G.nodes))
     |      >>> # right way - note that there will be no self-edge for node 5
     |      >>> G.add_edges_from(list((5, n) for n in G.nodes))
     |
     |  add_node(self, node_for_adding, **attr)
     |      Add a single node `node_for_adding` and update node attributes.
     |
     |      Parameters
     |      ----------
     |      node_for_adding : node
     |          A node can be any hashable Python object except None.
     |      attr : keyword arguments, optional
     |          Set or change node attributes using key=value.
     |
     |      See Also
     |      --------
     |      add_nodes_from
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_node(1)
     |      >>> G.add_node("Hello")
     |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
     |      >>> G.add_node(K3)
     |      >>> G.number_of_nodes()
     |      3
     |
     |      Use keywords set/change node attributes:
     |
     |      >>> G.add_node(1, size=10)
     |      >>> G.add_node(3, weight=0.4, UTM=("13S", 382871, 3972649))
     |
     |      Notes
     |      -----
     |      A hashable object is one that can be used as a key in a Python
     |      dictionary. This includes strings, numbers, tuples of strings
     |      and numbers, etc.
     |
     |      On many platforms hashable items also include mutables such as
     |      NetworkX Graphs, though one should be careful that the hash
     |      doesn't change on mutables.
     |
     |  add_nodes_from(self, nodes_for_adding, **attr)
     |      Add multiple nodes.
     |
     |      Parameters
     |      ----------
     |      nodes_for_adding : iterable container
     |          A container of nodes (list, dict, set, etc.).
     |          OR
     |          A container of (node, attribute dict) tuples.
     |          Node attributes are updated using the attribute dict.
     |      attr : keyword arguments, optional (default= no attributes)
     |          Update attributes for all nodes in nodes.
     |          Node attributes specified in nodes as a tuple take
     |          precedence over attributes specified via keyword arguments.
     |
     |      See Also
     |      --------
     |      add_node
     |
     |      Notes
     |      -----
     |      When adding nodes from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
     |      object to `G.add_nodes_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_nodes_from("Hello")
     |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
     |      >>> G.add_nodes_from(K3)
     |      >>> sorted(G.nodes(), key=str)
     |      [0, 1, 2, 'H', 'e', 'l', 'o']
     |
     |      Use keywords to update specific node attributes for every node.
     |
     |      >>> G.add_nodes_from([1, 2], size=10)
     |      >>> G.add_nodes_from([3, 4], weight=0.4)
     |
     |      Use (node, attrdict) tuples to update attributes for specific nodes.
     |
     |      >>> G.add_nodes_from([(1, dict(size=11)), (2, {"color": "blue"})])
     |      >>> G.nodes[1]["size"]
     |      11
     |      >>> H = nx.Graph()
     |      >>> H.add_nodes_from(G.nodes(data=True))
     |      >>> H.nodes[1]["size"]
     |      11
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.DiGraph([(0, 1), (1, 2), (3, 4)])
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_nodes_from(n + 1 for n in G.nodes)
     |      >>> # correct way
     |      >>> G.add_nodes_from(list(n + 1 for n in G.nodes))
     |
     |  adj = <functools.cached_property object>
     |      Graph adjacency object holding the neighbors of each node.
     |
     |      This object is a read-only dict-like structure with node keys
     |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
     |      to the edge-data-dict.  So `G.adj[3][2]['color'] = 'blue'` sets
     |      the color of the edge `(3, 2)` to `"blue"`.
     |
     |      Iterating over G.adj behaves like a dict. Useful idioms include
     |      `for nbr, datadict in G.adj[n].items():`.
     |
     |      The neighbor information is also provided by subscripting the graph.
     |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
     |
     |      For directed graphs, `G.adj` holds outgoing (successor) info.
     |
     |  clear(self)
     |      Remove all nodes and edges from the graph.
     |
     |      This also removes the name, and all graph, node, and edge attributes.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.clear()
     |      >>> list(G.nodes)
     |      []
     |      >>> list(G.edges)
     |      []
     |
     |  clear_edges(self)
     |      Remove all edges from the graph without altering nodes.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.clear_edges()
     |      >>> list(G.nodes)
     |      [0, 1, 2, 3]
     |      >>> list(G.edges)
     |      []
     |
     |  degree = <functools.cached_property object>
     |      A DegreeView for the Graph as G.degree or G.degree().
     |
     |      The node degree is the number of edges adjacent to the node.
     |      The weighted node degree is the sum of the edge weights for
     |      edges incident to that node.
     |
     |      This object provides an iterator for (node, degree) as well as
     |      lookup for the degree for a single node.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      weight : string or None, optional (default=None)
     |         The name of an edge attribute that holds the numerical value used
     |         as a weight.  If None, then each edge has weight 1.
     |         The degree is the sum of the edge weights adjacent to the node.
     |
     |      Returns
     |      -------
     |      DiDegreeView or int
     |          If multiple nodes are requested (the default), returns a `DiDegreeView`
     |          mapping nodes to their degree.
     |          If a single node is requested, returns the degree of the node as an integer.
     |
     |      See Also
     |      --------
     |      in_degree, out_degree
     |
     |      Examples
     |      --------
     |      >>> G = nx.DiGraph()  # or MultiDiGraph
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.degree(0)  # node 0 with degree 1
     |      1
     |      >>> list(G.degree([0, 1, 2]))
     |      [(0, 1), (1, 2), (2, 2)]
     |
     |  edges = <functools.cached_property object>
     |      An OutEdgeView of the DiGraph as G.edges or G.edges().
     |
     |      edges(self, nbunch=None, data=False, default=None)
     |
     |      The OutEdgeView provides set-like operations on the edge-tuples
     |      as well as edge attribute lookup. When called, it also provides
     |      an EdgeDataView object which allows control of access to edge
     |      attributes (but does not provide set-like operations).
     |      Hence, `G.edges[u, v]['color']` provides the value of the color
     |      attribute for edge `(u, v)` while
     |      `for (u, v, c) in G.edges.data('color', default='red'):`
     |      iterates through all the edges yielding the color attribute
     |      with default `'red'` if no color attribute exists.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges from these nodes.
     |      data : string or bool, optional (default=False)
     |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
     |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
     |          If False, return 2-tuple (u, v).
     |      default : value, optional (default=None)
     |          Value used for edges that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      edges : OutEdgeView
     |          A view of edge attributes, usually it iterates over (u, v)
     |          or (u, v, d) tuples of edges, but can also be used for
     |          attribute lookup as `edges[u, v]['foo']`.
     |
     |      See Also
     |      --------
     |      in_edges, out_edges
     |
     |      Notes
     |      -----
     |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
     |      For directed graphs this returns the out-edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
     |      >>> nx.add_path(G, [0, 1, 2])
     |      >>> G.add_edge(2, 3, weight=5)
     |      >>> [e for e in G.edges]
     |      [(0, 1), (1, 2), (2, 3)]
     |      >>> G.edges.data()  # default data is {} (empty dict)
     |      OutEdgeDataView([(0, 1, {}), (1, 2, {}), (2, 3, {'weight': 5})])
     |      >>> G.edges.data("weight", default=1)
     |      OutEdgeDataView([(0, 1, 1), (1, 2, 1), (2, 3, 5)])
     |      >>> G.edges([0, 2])  # only edges originating from these nodes
     |      OutEdgeDataView([(0, 1), (2, 3)])
     |      >>> G.edges(0)  # only edges from node 0
     |      OutEdgeDataView([(0, 1)])
     |
     |  has_predecessor(self, u, v)
     |      Returns True if node u has predecessor v.
     |
     |      This is true if graph has the edge u<-v.
     |
     |  has_successor(self, u, v)
     |      Returns True if node u has successor v.
     |
     |      This is true if graph has the edge u->v.
     |
     |  in_degree = <functools.cached_property object>
     |      An InDegreeView for (node, in_degree) or in_degree for single node.
     |
     |      The node in_degree is the number of edges pointing to the node.
     |      The weighted node degree is the sum of the edge weights for
     |      edges incident to that node.
     |
     |      This object provides an iteration over (node, in_degree) as well as
     |      lookup for the degree for a single node.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      weight : string or None, optional (default=None)
     |         The name of an edge attribute that holds the numerical value used
     |         as a weight.  If None, then each edge has weight 1.
     |         The degree is the sum of the edge weights adjacent to the node.
     |
     |      Returns
     |      -------
     |      If a single node is requested
     |      deg : int
     |          In-degree of the node
     |
     |      OR if multiple nodes are requested
     |      nd_iter : iterator
     |          The iterator returns two-tuples of (node, in-degree).
     |
     |      See Also
     |      --------
     |      degree, out_degree
     |
     |      Examples
     |      --------
     |      >>> G = nx.DiGraph()
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.in_degree(0)  # node 0 with degree 0
     |      0
     |      >>> list(G.in_degree([0, 1, 2]))
     |      [(0, 0), (1, 1), (2, 1)]
     |
     |  in_edges = <functools.cached_property object>
     |      A view of the in edges of the graph as G.in_edges or G.in_edges().
     |
     |      in_edges(self, nbunch=None, data=False, default=None):
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |      data : string or bool, optional (default=False)
     |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
     |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
     |          If False, return 2-tuple (u, v).
     |      default : value, optional (default=None)
     |          Value used for edges that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      in_edges : InEdgeView or InEdgeDataView
     |          A view of edge attributes, usually it iterates over (u, v)
     |          or (u, v, d) tuples of edges, but can also be used for
     |          attribute lookup as `edges[u, v]['foo']`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.DiGraph()
     |      >>> G.add_edge(1, 2, color="blue")
     |      >>> G.in_edges()
     |      InEdgeView([(1, 2)])
     |      >>> G.in_edges(nbunch=2)
     |      InEdgeDataView([(1, 2)])
     |
     |      See Also
     |      --------
     |      edges
     |
     |  is_directed(self)
     |      Returns True if graph is directed, False otherwise.
     |
     |  is_multigraph(self)
     |      Returns True if graph is a multigraph, False otherwise.
     |
     |  neighbors = successors(self, n)
     |
     |  out_degree = <functools.cached_property object>
     |      An OutDegreeView for (node, out_degree)
     |
     |      The node out_degree is the number of edges pointing out of the node.
     |      The weighted node degree is the sum of the edge weights for
     |      edges incident to that node.
     |
     |      This object provides an iterator over (node, out_degree) as well as
     |      lookup for the degree for a single node.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      weight : string or None, optional (default=None)
     |         The name of an edge attribute that holds the numerical value used
     |         as a weight.  If None, then each edge has weight 1.
     |         The degree is the sum of the edge weights adjacent to the node.
     |
     |      Returns
     |      -------
     |      If a single node is requested
     |      deg : int
     |          Out-degree of the node
     |
     |      OR if multiple nodes are requested
     |      nd_iter : iterator
     |          The iterator returns two-tuples of (node, out-degree).
     |
     |      See Also
     |      --------
     |      degree, in_degree
     |
     |      Examples
     |      --------
     |      >>> G = nx.DiGraph()
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.out_degree(0)  # node 0 with degree 1
     |      1
     |      >>> list(G.out_degree([0, 1, 2]))
     |      [(0, 1), (1, 1), (2, 1)]
     |
     |  out_edges = <functools.cached_property object>
     |      An OutEdgeView of the DiGraph as G.edges or G.edges().
     |
     |      edges(self, nbunch=None, data=False, default=None)
     |
     |      The OutEdgeView provides set-like operations on the edge-tuples
     |      as well as edge attribute lookup. When called, it also provides
     |      an EdgeDataView object which allows control of access to edge
     |      attributes (but does not provide set-like operations).
     |      Hence, `G.edges[u, v]['color']` provides the value of the color
     |      attribute for edge `(u, v)` while
     |      `for (u, v, c) in G.edges.data('color', default='red'):`
     |      iterates through all the edges yielding the color attribute
     |      with default `'red'` if no color attribute exists.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges from these nodes.
     |      data : string or bool, optional (default=False)
     |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
     |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
     |          If False, return 2-tuple (u, v).
     |      default : value, optional (default=None)
     |          Value used for edges that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      edges : OutEdgeView
     |          A view of edge attributes, usually it iterates over (u, v)
     |          or (u, v, d) tuples of edges, but can also be used for
     |          attribute lookup as `edges[u, v]['foo']`.
     |
     |      See Also
     |      --------
     |      in_edges, out_edges
     |
     |      Notes
     |      -----
     |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
     |      For directed graphs this returns the out-edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
     |      >>> nx.add_path(G, [0, 1, 2])
     |      >>> G.add_edge(2, 3, weight=5)
     |      >>> [e for e in G.edges]
     |      [(0, 1), (1, 2), (2, 3)]
     |      >>> G.edges.data()  # default data is {} (empty dict)
     |      OutEdgeDataView([(0, 1, {}), (1, 2, {}), (2, 3, {'weight': 5})])
     |      >>> G.edges.data("weight", default=1)
     |      OutEdgeDataView([(0, 1, 1), (1, 2, 1), (2, 3, 5)])
     |      >>> G.edges([0, 2])  # only edges originating from these nodes
     |      OutEdgeDataView([(0, 1), (2, 3)])
     |      >>> G.edges(0)  # only edges from node 0
     |      OutEdgeDataView([(0, 1)])
     |
     |  pred = <functools.cached_property object>
     |      Graph adjacency object holding the predecessors of each node.
     |
     |      This object is a read-only dict-like structure with node keys
     |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
     |      to the edge-data-dict.  So `G.pred[2][3]['color'] = 'blue'` sets
     |      the color of the edge `(3, 2)` to `"blue"`.
     |
     |      Iterating over G.pred behaves like a dict. Useful idioms include
     |      `for nbr, datadict in G.pred[n].items():`.  A data-view not provided
     |      by dicts also exists: `for nbr, foovalue in G.pred[node].data('foo'):`
     |      A default can be set via a `default` argument to the `data` method.
     |
     |  predecessors(self, n)
     |      Returns an iterator over predecessor nodes of n.
     |
     |      A predecessor of n is a node m such that there exists a directed
     |      edge from m to n.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Raises
     |      ------
     |      NetworkXError
     |         If n is not in the graph.
     |
     |      See Also
     |      --------
     |      successors
     |
     |  remove_edge(self, u, v)
     |      Remove the edge between u and v.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |          Remove the edge between nodes u and v.
     |
     |      Raises
     |      ------
     |      NetworkXError
     |          If there is not an edge between u and v.
     |
     |      See Also
     |      --------
     |      remove_edges_from : remove a collection of edges
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, etc
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.remove_edge(0, 1)
     |      >>> e = (1, 2)
     |      >>> G.remove_edge(*e)  # unpacks e from an edge tuple
     |      >>> e = (2, 3, {"weight": 7})  # an edge with attribute data
     |      >>> G.remove_edge(*e[:2])  # select first part of edge tuple
     |
     |  remove_edges_from(self, ebunch)
     |      Remove all edges specified in ebunch.
     |
     |      Parameters
     |      ----------
     |      ebunch: list or container of edge tuples
     |          Each edge given in the list or container will be removed
     |          from the graph. The edges can be:
     |
     |              - 2-tuples (u, v) edge between u and v.
     |              - 3-tuples (u, v, k) where k is ignored.
     |
     |      See Also
     |      --------
     |      remove_edge : remove a single edge
     |
     |      Notes
     |      -----
     |      Will fail silently if an edge in ebunch is not in the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> ebunch = [(1, 2), (2, 3)]
     |      >>> G.remove_edges_from(ebunch)
     |
     |  remove_node(self, n)
     |      Remove node n.
     |
     |      Removes the node n and all adjacent edges.
     |      Attempting to remove a nonexistent node will raise an exception.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Raises
     |      ------
     |      NetworkXError
     |         If n is not in the graph.
     |
     |      See Also
     |      --------
     |      remove_nodes_from
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> list(G.edges)
     |      [(0, 1), (1, 2)]
     |      >>> G.remove_node(1)
     |      >>> list(G.edges)
     |      []
     |
     |  remove_nodes_from(self, nodes)
     |      Remove multiple nodes.
     |
     |      Parameters
     |      ----------
     |      nodes : iterable container
     |          A container of nodes (list, dict, set, etc.).  If a node
     |          in the container is not in the graph it is silently ignored.
     |
     |      See Also
     |      --------
     |      remove_node
     |
     |      Notes
     |      -----
     |      When removing nodes from an iterator over the graph you are changing,
     |      a `RuntimeError` will be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
     |      object to `G.remove_nodes_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> e = list(G.nodes)
     |      >>> e
     |      [0, 1, 2]
     |      >>> G.remove_nodes_from(e)
     |      >>> list(G.nodes)
     |      []
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.DiGraph([(0, 1), (1, 2), (3, 4)])
     |      >>> # this command will fail, as the graph's dict is modified during iteration
     |      >>> # G.remove_nodes_from(n for n in G.nodes if n < 2)
     |      >>> # this command will work, since the dictionary underlying graph is not modified
     |      >>> G.remove_nodes_from(list(n for n in G.nodes if n < 2))
     |
     |  reverse(self, copy=True)
     |      Returns the reverse of the graph.
     |
     |      The reverse is a graph with the same nodes and edges
     |      but with the directions of the edges reversed.
     |
     |      Parameters
     |      ----------
     |      copy : bool optional (default=True)
     |          If True, return a new DiGraph holding the reversed edges.
     |          If False, the reverse graph is created using a view of
     |          the original graph.
     |
     |  succ = <functools.cached_property object>
     |      Graph adjacency object holding the successors of each node.
     |
     |      This object is a read-only dict-like structure with node keys
     |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
     |      to the edge-data-dict.  So `G.succ[3][2]['color'] = 'blue'` sets
     |      the color of the edge `(3, 2)` to `"blue"`.
     |
     |      Iterating over G.succ behaves like a dict. Useful idioms include
     |      `for nbr, datadict in G.succ[n].items():`.  A data-view not provided
     |      by dicts also exists: `for nbr, foovalue in G.succ[node].data('foo'):`
     |      and a default can be set via a `default` argument to the `data` method.
     |
     |      The neighbor information is also provided by subscripting the graph.
     |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
     |
     |      For directed graphs, `G.adj` is identical to `G.succ`.
     |
     |  successors(self, n)
     |      Returns an iterator over successor nodes of n.
     |
     |      A successor of n is a node m such that there exists a directed
     |      edge from n to m.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Raises
     |      ------
     |      NetworkXError
     |         If n is not in the graph.
     |
     |      See Also
     |      --------
     |      predecessors
     |
     |      Notes
     |      -----
     |      neighbors() and successors() are the same.
     |
     |  to_undirected(self, reciprocal=False, as_view=False)
     |      Returns an undirected representation of the digraph.
     |
     |      Parameters
     |      ----------
     |      reciprocal : bool (optional)
     |        If True only keep edges that appear in both directions
     |        in the original digraph.
     |      as_view : bool (optional, default=False)
     |        If True return an undirected view of the original directed graph.
     |
     |      Returns
     |      -------
     |      G : Graph
     |          An undirected graph with the same name and nodes and
     |          with edge (u, v, data) if either (u, v, data) or (v, u, data)
     |          is in the digraph.  If both edges exist in digraph and
     |          their edge data is different, only one edge is created
     |          with an arbitrary choice of which edge data to use.
     |          You must check and correct for this manually if desired.
     |
     |      See Also
     |      --------
     |      Graph, copy, add_edge, add_edges_from
     |
     |      Notes
     |      -----
     |      If edges in both directions (u, v) and (v, u) exist in the
     |      graph, attributes for the new undirected edge will be a combination of
     |      the attributes of the directed edges.  The edge data is updated
     |      in the (arbitrary) order that the edges are encountered.  For
     |      more customized control of the edge attributes use add_edge().
     |
     |      This returns a "deepcopy" of the edge, node, and
     |      graph attributes which attempts to completely copy
     |      all of the data and references.
     |
     |      This is in contrast to the similar G=DiGraph(D) which returns a
     |      shallow copy of the data.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Warning: If you have subclassed DiGraph to use dict-like objects
     |      in the data structure, those changes do not transfer to the
     |      Graph created by this method.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(2)  # or MultiGraph, etc
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1), (1, 0)]
     |      >>> G2 = H.to_undirected()
     |      >>> list(G2.edges)
     |      [(0, 1)]
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from networkx.classes.graph.Graph:
     |
     |  __contains__(self, n)
     |      Returns True if n is a node, False otherwise. Use: 'n in G'.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> 1 in G
     |      True
     |
     |  __getitem__(self, n)
     |      Returns a dict of neighbors of node n.  Use: 'G[n]'.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph.
     |
     |      Returns
     |      -------
     |      adj_dict : dictionary
     |         The adjacency dictionary for nodes connected to n.
     |
     |      Notes
     |      -----
     |      G[n] is the same as G.adj[n] and similar to G.neighbors(n)
     |      (which is an iterator over G.adj[n])
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G[0]
     |      AtlasView({1: {}})
     |
     |  __iter__(self)
     |      Iterate over the nodes. Use: 'for n in G'.
     |
     |      Returns
     |      -------
     |      niter : iterator
     |          An iterator over all nodes in the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> [n for n in G]
     |      [0, 1, 2, 3]
     |      >>> list(G)
     |      [0, 1, 2, 3]
     |
     |  __len__(self)
     |      Returns the number of nodes in the graph. Use: 'len(G)'.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      number_of_nodes: identical method
     |      order: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> len(G)
     |      4
     |
     |  __str__(self)
     |      Returns a short summary of the graph.
     |
     |      Returns
     |      -------
     |      info : string
     |          Graph information including the graph name (if any), graph type, and the
     |          number of nodes and edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph(name="foo")
     |      >>> str(G)
     |      "Graph named 'foo' with 0 nodes and 0 edges"
     |
     |      >>> G = nx.path_graph(3)
     |      >>> str(G)
     |      'Graph with 3 nodes and 2 edges'
     |
     |  add_weighted_edges_from(self, ebunch_to_add, weight='weight', **attr)
     |      Add weighted edges in `ebunch_to_add` with specified weight attr
     |
     |      Parameters
     |      ----------
     |      ebunch_to_add : container of edges
     |          Each edge given in the list or container will be added
     |          to the graph. The edges must be given as 3-tuples (u, v, w)
     |          where w is a number.
     |      weight : string, optional (default= 'weight')
     |          The attribute name for the edge weights to be added.
     |      attr : keyword arguments, optional (default= no attributes)
     |          Edge attributes to add/update for all edges.
     |
     |      See Also
     |      --------
     |      add_edge : add a single edge
     |      add_edges_from : add multiple edges
     |
     |      Notes
     |      -----
     |      Adding the same edge twice for Graph/DiGraph simply updates
     |      the edge data. For MultiGraph/MultiDiGraph, duplicate edges
     |      are stored.
     |
     |      When adding edges from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_edges)`, and pass this
     |      object to `G.add_weighted_edges_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_weighted_edges_from([(0, 1, 3.0), (1, 2, 7.5)])
     |
     |      Evaluate an iterator over edges before passing it
     |
     |      >>> G = nx.Graph([(1, 2), (2, 3), (3, 4)])
     |      >>> weight = 0.1
     |      >>> # Grow graph by one new node, adding edges to all existing nodes.
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_weighted_edges_from(((5, n, weight) for n in G.nodes))
     |      >>> # correct way - note that there will be no self-edge for node 5
     |      >>> G.add_weighted_edges_from(list((5, n, weight) for n in G.nodes))
     |
     |  adjacency(self)
     |      Returns an iterator over (node, adjacency dict) tuples for all nodes.
     |
     |      For directed graphs, only outgoing neighbors/adjacencies are included.
     |
     |      Returns
     |      -------
     |      adj_iter : iterator
     |         An iterator over (node, adjacency dictionary) for all nodes in
     |         the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> [(n, nbrdict) for n, nbrdict in G.adjacency()]
     |      [(0, {1: {}}), (1, {0: {}, 2: {}}), (2, {1: {}, 3: {}}), (3, {2: {}})]
     |
     |  copy(self, as_view=False)
     |      Returns a copy of the graph.
     |
     |      The copy method by default returns an independent shallow copy
     |      of the graph and attributes. That is, if an attribute is a
     |      container, that container is shared by the original an the copy.
     |      Use Python's `copy.deepcopy` for new containers.
     |
     |      If `as_view` is True then a view is returned instead of a copy.
     |
     |      Notes
     |      -----
     |      All copies reproduce the graph structure, but data attributes
     |      may be handled in different ways. There are four types of copies
     |      of a graph that people might want.
     |
     |      Deepcopy -- A "deepcopy" copies the graph structure as well as
     |      all data attributes and any objects they might contain.
     |      The entire graph object is new so that changes in the copy
     |      do not affect the original object. (see Python's copy.deepcopy)
     |
     |      Data Reference (Shallow) -- For a shallow copy the graph structure
     |      is copied but the edge, node and graph attribute dicts are
     |      references to those in the original graph. This saves
     |      time and memory but could cause confusion if you change an attribute
     |      in one graph and it changes the attribute in the other.
     |      NetworkX does not provide this level of shallow copy.
     |
     |      Independent Shallow -- This copy creates new independent attribute
     |      dicts and then does a shallow copy of the attributes. That is, any
     |      attributes that are containers are shared between the new graph
     |      and the original. This is exactly what `dict.copy()` provides.
     |      You can obtain this style copy using:
     |
     |          >>> G = nx.path_graph(5)
     |          >>> H = G.copy()
     |          >>> H = G.copy(as_view=False)
     |          >>> H = nx.Graph(G)
     |          >>> H = G.__class__(G)
     |
     |      Fresh Data -- For fresh data, the graph structure is copied while
     |      new empty data attribute dicts are created. The resulting graph
     |      is independent of the original and it has no edge, node or graph
     |      attributes. Fresh copies are not enabled. Instead use:
     |
     |          >>> H = G.__class__()
     |          >>> H.add_nodes_from(G)
     |          >>> H.add_edges_from(G.edges)
     |
     |      View -- Inspired by dict-views, graph-views act like read-only
     |      versions of the original graph, providing a copy of the original
     |      structure without requiring any memory for copying the information.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Parameters
     |      ----------
     |      as_view : bool, optional (default=False)
     |          If True, the returned graph-view provides a read-only view
     |          of the original graph without actually copying any data.
     |
     |      Returns
     |      -------
     |      G : Graph
     |          A copy of the graph.
     |
     |      See Also
     |      --------
     |      to_directed: return a directed copy of the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> H = G.copy()
     |
     |  edge_subgraph(self, edges)
     |      Returns the subgraph induced by the specified edges.
     |
     |      The induced subgraph contains each edge in `edges` and each
     |      node incident to any one of those edges.
     |
     |      Parameters
     |      ----------
     |      edges : iterable
     |          An iterable of edges in this graph.
     |
     |      Returns
     |      -------
     |      G : Graph
     |          An edge-induced subgraph of this graph with the same edge
     |          attributes.
     |
     |      Notes
     |      -----
     |      The graph, edge, and node attributes in the returned subgraph
     |      view are references to the corresponding attributes in the original
     |      graph. The view is read-only.
     |
     |      To create a full graph version of the subgraph with its own copy
     |      of the edge or node attributes, use::
     |
     |          G.edge_subgraph(edges).copy()
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(5)
     |      >>> H = G.edge_subgraph([(0, 1), (3, 4)])
     |      >>> list(H.nodes)
     |      [0, 1, 3, 4]
     |      >>> list(H.edges)
     |      [(0, 1), (3, 4)]
     |
     |  get_edge_data(self, u, v, default=None)
     |      Returns the attribute dictionary associated with edge (u, v).
     |
     |      This is identical to `G[u][v]` except the default is returned
     |      instead of an exception if the edge doesn't exist.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |      default:  any Python object (default=None)
     |          Value to return if the edge (u, v) is not found.
     |
     |      Returns
     |      -------
     |      edge_dict : dictionary
     |          The edge attribute dictionary.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G[0][1]
     |      {}
     |
     |      Warning: Assigning to `G[u][v]` is not permitted.
     |      But it is safe to assign attributes `G[u][v]['foo']`
     |
     |      >>> G[0][1]["weight"] = 7
     |      >>> G[0][1]["weight"]
     |      7
     |      >>> G[1][0]["weight"]
     |      7
     |
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.get_edge_data(0, 1)  # default edge data is {}
     |      {}
     |      >>> e = (0, 1)
     |      >>> G.get_edge_data(*e)  # tuple form
     |      {}
     |      >>> G.get_edge_data("a", "b", default=0)  # edge not in graph, return 0
     |      0
     |
     |  has_edge(self, u, v)
     |      Returns True if the edge (u, v) is in the graph.
     |
     |      This is the same as `v in G[u]` without KeyError exceptions.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |          Nodes can be, for example, strings or numbers.
     |          Nodes must be hashable (and not None) Python objects.
     |
     |      Returns
     |      -------
     |      edge_ind : bool
     |          True if edge is in the graph, False otherwise.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.has_edge(0, 1)  # using two nodes
     |      True
     |      >>> e = (0, 1)
     |      >>> G.has_edge(*e)  #  e is a 2-tuple (u, v)
     |      True
     |      >>> e = (0, 1, {"weight": 7})
     |      >>> G.has_edge(*e[:2])  # e is a 3-tuple (u, v, data_dictionary)
     |      True
     |
     |      The following syntax are equivalent:
     |
     |      >>> G.has_edge(0, 1)
     |      True
     |      >>> 1 in G[0]  # though this gives KeyError if 0 not in G
     |      True
     |
     |  has_node(self, n)
     |      Returns True if the graph contains the node n.
     |
     |      Identical to `n in G`
     |
     |      Parameters
     |      ----------
     |      n : node
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.has_node(0)
     |      True
     |
     |      It is more readable and simpler to use
     |
     |      >>> 0 in G
     |      True
     |
     |  nbunch_iter(self, nbunch=None)
     |      Returns an iterator over nodes contained in nbunch that are
     |      also in the graph.
     |
     |      The nodes in nbunch are checked for membership in the graph
     |      and if not are silently ignored.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      Returns
     |      -------
     |      niter : iterator
     |          An iterator over nodes in nbunch that are also in the graph.
     |          If nbunch is None, iterate over all nodes in the graph.
     |
     |      Raises
     |      ------
     |      NetworkXError
     |          If nbunch is not a node or sequence of nodes.
     |          If a node in nbunch is not hashable.
     |
     |      See Also
     |      --------
     |      Graph.__iter__
     |
     |      Notes
     |      -----
     |      When nbunch is an iterator, the returned iterator yields values
     |      directly from nbunch, becoming exhausted when nbunch is exhausted.
     |
     |      To test whether nbunch is a single node, one can use
     |      "if nbunch in self:", even after processing with this routine.
     |
     |      If nbunch is not a node or a (possibly empty) sequence/iterator
     |      or None, a :exc:`NetworkXError` is raised.  Also, if any object in
     |      nbunch is not hashable, a :exc:`NetworkXError` is raised.
     |
     |  nodes = <functools.cached_property object>
     |      A NodeView of the Graph as G.nodes or G.nodes().
     |
     |      Can be used as `G.nodes` for data lookup and for set-like operations.
     |      Can also be used as `G.nodes(data='color', default=None)` to return a
     |      NodeDataView which reports specific node data but no set operations.
     |      It presents a dict-like interface as well with `G.nodes.items()`
     |      iterating over `(node, nodedata)` 2-tuples and `G.nodes[3]['foo']`
     |      providing the value of the `foo` attribute for node `3`. In addition,
     |      a view `G.nodes.data('foo')` provides a dict-like interface to the
     |      `foo` attribute of each node. `G.nodes.data('foo', default=1)`
     |      provides a default for nodes that do not have attribute `foo`.
     |
     |      Parameters
     |      ----------
     |      data : string or bool, optional (default=False)
     |          The node attribute returned in 2-tuple (n, ddict[data]).
     |          If True, return entire node attribute dict as (n, ddict).
     |          If False, return just the nodes n.
     |
     |      default : value, optional (default=None)
     |          Value used for nodes that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      NodeView
     |          Allows set-like operations over the nodes as well as node
     |          attribute dict lookup and calling to get a NodeDataView.
     |          A NodeDataView iterates over `(n, data)` and has no set operations.
     |          A NodeView iterates over `n` and includes set operations.
     |
     |          When called, if data is False, an iterator over nodes.
     |          Otherwise an iterator of 2-tuples (node, attribute value)
     |          where the attribute is specified in `data`.
     |          If data is True then the attribute becomes the
     |          entire data dictionary.
     |
     |      Notes
     |      -----
     |      If your node data is not needed, it is simpler and equivalent
     |      to use the expression ``for n in G``, or ``list(G)``.
     |
     |      Examples
     |      --------
     |      There are two simple ways of getting a list of all nodes in the graph:
     |
     |      >>> G = nx.path_graph(3)
     |      >>> list(G.nodes)
     |      [0, 1, 2]
     |      >>> list(G)
     |      [0, 1, 2]
     |
     |      To get the node data along with the nodes:
     |
     |      >>> G.add_node(1, time="5pm")
     |      >>> G.nodes[0]["foo"] = "bar"
     |      >>> list(G.nodes(data=True))
     |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
     |      >>> list(G.nodes.data())
     |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
     |
     |      >>> list(G.nodes(data="foo"))
     |      [(0, 'bar'), (1, None), (2, None)]
     |      >>> list(G.nodes.data("foo"))
     |      [(0, 'bar'), (1, None), (2, None)]
     |
     |      >>> list(G.nodes(data="time"))
     |      [(0, None), (1, '5pm'), (2, None)]
     |      >>> list(G.nodes.data("time"))
     |      [(0, None), (1, '5pm'), (2, None)]
     |
     |      >>> list(G.nodes(data="time", default="Not Available"))
     |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
     |      >>> list(G.nodes.data("time", default="Not Available"))
     |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
     |
     |      If some of your nodes have an attribute and the rest are assumed
     |      to have a default attribute value you can create a dictionary
     |      from node/attribute pairs using the `default` keyword argument
     |      to guarantee the value is never None::
     |
     |          >>> G = nx.Graph()
     |          >>> G.add_node(0)
     |          >>> G.add_node(1, weight=2)
     |          >>> G.add_node(2, weight=3)
     |          >>> dict(G.nodes(data="weight", default=1))
     |          {0: 1, 1: 2, 2: 3}
     |
     |  number_of_edges(self, u=None, v=None)
     |      Returns the number of edges between two nodes.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes, optional (default=all edges)
     |          If u and v are specified, return the number of edges between
     |          u and v. Otherwise return the total number of all edges.
     |
     |      Returns
     |      -------
     |      nedges : int
     |          The number of edges in the graph.  If nodes `u` and `v` are
     |          specified return the number of edges between those nodes. If
     |          the graph is directed, this only returns the number of edges
     |          from `u` to `v`.
     |
     |      See Also
     |      --------
     |      size
     |
     |      Examples
     |      --------
     |      For undirected graphs, this method counts the total number of
     |      edges in the graph:
     |
     |      >>> G = nx.path_graph(4)
     |      >>> G.number_of_edges()
     |      3
     |
     |      If you specify two nodes, this counts the total number of edges
     |      joining the two nodes:
     |
     |      >>> G.number_of_edges(0, 1)
     |      1
     |
     |      For directed graphs, this method can count the total number of
     |      directed edges from `u` to `v`:
     |
     |      >>> G = nx.DiGraph()
     |      >>> G.add_edge(0, 1)
     |      >>> G.add_edge(1, 0)
     |      >>> G.number_of_edges(0, 1)
     |      1
     |
     |  number_of_nodes(self)
     |      Returns the number of nodes in the graph.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      order: identical method
     |      __len__: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.number_of_nodes()
     |      3
     |
     |  order(self)
     |      Returns the number of nodes in the graph.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      number_of_nodes: identical method
     |      __len__: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.order()
     |      3
     |
     |  size(self, weight=None)
     |      Returns the number of edges or total of all edge weights.
     |
     |      Parameters
     |      ----------
     |      weight : string or None, optional (default=None)
     |          The edge attribute that holds the numerical value used
     |          as a weight. If None, then each edge has weight 1.
     |
     |      Returns
     |      -------
     |      size : numeric
     |          The number of edges or
     |          (if weight keyword is provided) the total weight sum.
     |
     |          If weight is None, returns an int. Otherwise a float
     |          (or more general numeric if the weights are more general).
     |
     |      See Also
     |      --------
     |      number_of_edges
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.size()
     |      3
     |
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_edge("a", "b", weight=2)
     |      >>> G.add_edge("b", "c", weight=4)
     |      >>> G.size()
     |      2
     |      >>> G.size(weight="weight")
     |      6.0
     |
     |  subgraph(self, nodes)
     |      Returns a SubGraph view of the subgraph induced on `nodes`.
     |
     |      The induced subgraph of the graph contains the nodes in `nodes`
     |      and the edges between those nodes.
     |
     |      Parameters
     |      ----------
     |      nodes : list, iterable
     |          A container of nodes which will be iterated through once.
     |
     |      Returns
     |      -------
     |      G : SubGraph View
     |          A subgraph view of the graph. The graph structure cannot be
     |          changed but node/edge attributes can and are shared with the
     |          original graph.
     |
     |      Notes
     |      -----
     |      The graph, edge and node attributes are shared with the original graph.
     |      Changes to the graph structure is ruled out by the view, but changes
     |      to attributes are reflected in the original graph.
     |
     |      To create a subgraph with its own copy of the edge/node attributes use:
     |      G.subgraph(nodes).copy()
     |
     |      For an inplace reduction of a graph to a subgraph you can remove nodes:
     |      G.remove_nodes_from([n for n in G if n not in set(nodes)])
     |
     |      Subgraph views are sometimes NOT what you want. In most cases where
     |      you want to do more than simply look at the induced edges, it makes
     |      more sense to just create the subgraph as its own graph with code like:
     |
     |      ::
     |
     |          # Create a subgraph SG based on a (possibly multigraph) G
     |          SG = G.__class__()
     |          SG.add_nodes_from((n, G.nodes[n]) for n in largest_wcc)
     |          if SG.is_multigraph():
     |              SG.add_edges_from(
     |                  (n, nbr, key, d)
     |                  for n, nbrs in G.adj.items()
     |                  if n in largest_wcc
     |                  for nbr, keydict in nbrs.items()
     |                  if nbr in largest_wcc
     |                  for key, d in keydict.items()
     |              )
     |          else:
     |              SG.add_edges_from(
     |                  (n, nbr, d)
     |                  for n, nbrs in G.adj.items()
     |                  if n in largest_wcc
     |                  for nbr, d in nbrs.items()
     |                  if nbr in largest_wcc
     |              )
     |          SG.graph.update(G.graph)
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> H = G.subgraph([0, 1, 2])
     |      >>> list(H.edges)
     |      [(0, 1), (1, 2)]
     |
     |  to_directed(self, as_view=False)
     |      Returns a directed representation of the graph.
     |
     |      Returns
     |      -------
     |      G : DiGraph
     |          A directed graph with the same name, same nodes, and with
     |          each edge (u, v, data) replaced by two directed edges
     |          (u, v, data) and (v, u, data).
     |
     |      Notes
     |      -----
     |      This returns a "deepcopy" of the edge, node, and
     |      graph attributes which attempts to completely copy
     |      all of the data and references.
     |
     |      This is in contrast to the similar D=DiGraph(G) which returns a
     |      shallow copy of the data.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Warning: If you have subclassed Graph to use dict-like objects
     |      in the data structure, those changes do not transfer to the
     |      DiGraph created by this method.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or MultiGraph, etc
     |      >>> G.add_edge(0, 1)
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1), (1, 0)]
     |
     |      If already directed, return a (deep) copy
     |
     |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
     |      >>> G.add_edge(0, 1)
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1)]
     |
     |  to_directed_class(self)
     |      Returns the class to use for empty directed copies.
     |
     |      If you subclass the base classes, use this to designate
     |      what directed class to use for `to_directed()` copies.
     |
     |  to_undirected_class(self)
     |      Returns the class to use for empty undirected copies.
     |
     |      If you subclass the base classes, use this to designate
     |      what directed class to use for `to_directed()` copies.
     |
     |  update(self, edges=None, nodes=None)
     |      Update the graph using nodes/edges/graphs as input.
     |
     |      Like dict.update, this method takes a graph as input, adding the
     |      graph's nodes and edges to this graph. It can also take two inputs:
     |      edges and nodes. Finally it can take either edges or nodes.
     |      To specify only nodes the keyword `nodes` must be used.
     |
     |      The collections of edges and nodes are treated similarly to
     |      the add_edges_from/add_nodes_from methods. When iterated, they
     |      should yield 2-tuples (u, v) or 3-tuples (u, v, datadict).
     |
     |      Parameters
     |      ----------
     |      edges : Graph object, collection of edges, or None
     |          The first parameter can be a graph or some edges. If it has
     |          attributes `nodes` and `edges`, then it is taken to be a
     |          Graph-like object and those attributes are used as collections
     |          of nodes and edges to be added to the graph.
     |          If the first parameter does not have those attributes, it is
     |          treated as a collection of edges and added to the graph.
     |          If the first argument is None, no edges are added.
     |      nodes : collection of nodes, or None
     |          The second parameter is treated as a collection of nodes
     |          to be added to the graph unless it is None.
     |          If `edges is None` and `nodes is None` an exception is raised.
     |          If the first parameter is a Graph, then `nodes` is ignored.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(5)
     |      >>> G.update(nx.complete_graph(range(4, 10)))
     |      >>> from itertools import combinations
     |      >>> edges = (
     |      ...     (u, v, {"power": u * v})
     |      ...     for u, v in combinations(range(10, 20), 2)
     |      ...     if u * v < 225
     |      ... )
     |      >>> nodes = [1000]  # for singleton, use a container
     |      >>> G.update(edges, nodes)
     |
     |      Notes
     |      -----
     |      It you want to update the graph using an adjacency structure
     |      it is straightforward to obtain the edges/nodes from adjacency.
     |      The following examples provide common cases, your adjacency may
     |      be slightly different and require tweaks of these examples::
     |
     |      >>> # dict-of-set/list/tuple
     |      >>> adj = {1: {2, 3}, 2: {1, 3}, 3: {1, 2}}
     |      >>> e = [(u, v) for u, nbrs in adj.items() for v in nbrs]
     |      >>> G.update(edges=e, nodes=adj)
     |
     |      >>> DG = nx.DiGraph()
     |      >>> # dict-of-dict-of-attribute
     |      >>> adj = {1: {2: 1.3, 3: 0.7}, 2: {1: 1.4}, 3: {1: 0.7}}
     |      >>> e = [
     |      ...     (u, v, {"weight": d})
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, d in nbrs.items()
     |      ... ]
     |      >>> DG.update(edges=e, nodes=adj)
     |
     |      >>> # dict-of-dict-of-dict
     |      >>> adj = {1: {2: {"weight": 1.3}, 3: {"color": 0.7, "weight": 1.2}}}
     |      >>> e = [
     |      ...     (u, v, {"weight": d})
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, d in nbrs.items()
     |      ... ]
     |      >>> DG.update(edges=e, nodes=adj)
     |
     |      >>> # predecessor adjacency (dict-of-set)
     |      >>> pred = {1: {2, 3}, 2: {3}, 3: {3}}
     |      >>> e = [(v, u) for u, nbrs in pred.items() for v in nbrs]
     |
     |      >>> # MultiGraph dict-of-dict-of-dict-of-attribute
     |      >>> MDG = nx.MultiDiGraph()
     |      >>> adj = {
     |      ...     1: {2: {0: {"weight": 1.3}, 1: {"weight": 1.2}}},
     |      ...     3: {2: {0: {"weight": 0.7}}},
     |      ... }
     |      >>> e = [
     |      ...     (u, v, ekey, d)
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, keydict in nbrs.items()
     |      ...     for ekey, d in keydict.items()
     |      ... ]
     |      >>> MDG.update(edges=e)
     |
     |      See Also
     |      --------
     |      add_edges_from: add multiple edges to a graph
     |      add_nodes_from: add multiple nodes to a graph
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from networkx.classes.graph.Graph:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  name
     |      String identifier of the graph.
     |
     |      This graph attribute appears in the attribute dict G.graph
     |      keyed by the string `"name"`. as well as an attribute (technically
     |      a property) `G.name`. This is entirely user controlled.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from networkx.classes.graph.Graph:
     |
     |  __networkx_backend__ = 'networkx'
     |
     |  adjlist_inner_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  adjlist_outer_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  edge_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  graph_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  node_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  node_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)

DATA
    __all__ = ['DiGraph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\classes\digraph.py

networkx.dijkstra_path
Python Library Documentation: function dijkstra_path in module networkx.algorithms.shortest_paths.weighted

dijkstra_path(G, source, target, weight='weight', *, backend=None, **backend_kwargs)
    Returns the shortest weighted path from source to target in G.

    Uses Dijkstra's Method to compute the shortest weighted path
    between two nodes in a graph.

    Parameters
    ----------
    G : NetworkX graph

    source : node
        Starting node

    target : node
        Ending node

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Returns
    -------
    path : list
        List of nodes in a shortest path.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    NetworkXNoPath
        If no path exists between source and target.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> print(nx.dijkstra_path(G, 0, 4))
    [0, 1, 2, 3, 4]

    Find edges of shortest path in Multigraph

    >>> G = nx.MultiDiGraph()
    >>> G.add_weighted_edges_from([(1, 2, 0.75), (1, 2, 0.5), (2, 3, 0.5), (1, 3, 1.5)])
    >>> nodes = nx.dijkstra_path(G, 1, 3)
    >>> edges = nx.utils.pairwise(nodes)
    >>> list(
    ...     (u, v, min(G[u][v], key=lambda k: G[u][v][k].get("weight", 1)))
    ...     for u, v in edges
    ... )
    [(1, 2, 1), (2, 3, 0)]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The weight function can be used to hide edges by returning None.
    So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
    will find the shortest red path.

    The weight function can be used to include node weights.

    >>> def func(u, v, d):
    ...     node_u_wt = G.nodes[u].get("node_weight", 1)
    ...     node_v_wt = G.nodes[v].get("node_weight", 1)
    ...     edge_wt = d.get("weight", 1)
    ...     return node_u_wt / 2 + node_v_wt / 2 + edge_wt

    In this example we take the average of start and end node
    weights of an edge and add it to the weight of the edge.

    The function :func:`single_source_dijkstra` computes both
    path and length-of-path if you need both, use that.

    See Also
    --------
    bidirectional_dijkstra
    bellman_ford_path
    single_source_dijkstra
networkx.dijkstra_path_length
Python Library Documentation: function dijkstra_path_length in module networkx.algorithms.shortest_paths.weighted

dijkstra_path_length(G, source, target, weight='weight', *, backend=None, **backend_kwargs)
    Returns the shortest weighted path length in G from source to target.

    Uses Dijkstra's Method to compute the shortest weighted path length
    between two nodes in a graph.

    Parameters
    ----------
    G : NetworkX graph

    source : node label
        starting node for path

    target : node label
        ending node for path

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Returns
    -------
    length : number
        Shortest path length.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    NetworkXNoPath
        If no path exists between source and target.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> nx.dijkstra_path_length(G, 0, 4)
    4

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The weight function can be used to hide edges by returning None.
    So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
    will find the shortest red path.

    The function :func:`single_source_dijkstra` computes both
    path and length-of-path if you need both, use that.

    See Also
    --------
    bidirectional_dijkstra
    bellman_ford_path_length
    single_source_dijkstra
networkx.dijkstra_predecessor_and_distance
Python Library Documentation: function dijkstra_predecessor_and_distance in module networkx.algorithms.shortest_paths.weighted

dijkstra_predecessor_and_distance(G, source, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
    Compute weighted shortest path length and predecessors.

    Uses Dijkstra's Method to obtain the shortest weighted paths
    and return dictionaries of predecessors for each node and
    distance for each node from the `source`.

    Parameters
    ----------
    G : NetworkX graph

    source : node label
        Starting node for path

    cutoff : integer or float, optional
        Length (sum of edge weights) at which the search is stopped.
        If cutoff is provided, only return paths with summed weight <= cutoff.

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Returns
    -------
    pred, distance : dictionaries
        Returns two dictionaries representing a list of predecessors
        of a node and the distance to each node.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The list of predecessors contains more than one element only when
    there are more than one shortest paths to the key node.

    Examples
    --------
    >>> G = nx.path_graph(5, create_using=nx.DiGraph())
    >>> pred, dist = nx.dijkstra_predecessor_and_distance(G, 0)
    >>> sorted(pred.items())
    [(0, []), (1, [0]), (2, [1]), (3, [2]), (4, [3])]
    >>> sorted(dist.items())
    [(0, 0), (1, 1), (2, 2), (3, 3), (4, 4)]

    >>> pred, dist = nx.dijkstra_predecessor_and_distance(G, 0, 1)
    >>> sorted(pred.items())
    [(0, []), (1, [0])]
    >>> sorted(dist.items())
    [(0, 0), (1, 1)]
networkx.directed
Python Library Documentation: module networkx.generators.directed in networkx.generators

NAME
    networkx.generators.directed

DESCRIPTION
    Generators for some directed graphs, including growing network (GN) graphs and
    scale-free graphs.

FUNCTIONS
    gn_graph(n, kernel=None, create_using=None, seed=None, *, backend=None, **backend_kwargs)
        Returns the growing network (GN) digraph with `n` nodes.

        The GN graph is built by adding nodes one at a time with a link to one
        previously added node.  The target node for the link is chosen with
        probability based on degree.  The default attachment kernel is a linear
        function of the degree of a node.

        The graph is always a (directed) tree.

        Parameters
        ----------
        n : int
            The number of nodes for the generated graph.
        kernel : function
            The attachment kernel.
        create_using : NetworkX graph constructor, optional (default DiGraph)
            Graph type to create. If graph instance, then cleared before populated.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Examples
        --------
        To create the undirected GN graph, use the :meth:`~DiGraph.to_directed`
        method::

        >>> D = nx.gn_graph(10)  # the GN graph
        >>> G = D.to_undirected()  # the undirected version

        To specify an attachment kernel, use the `kernel` keyword argument::

        >>> D = nx.gn_graph(10, kernel=lambda x: x**1.5)  # A_k = k^1.5

        References
        ----------
        .. [1] P. L. Krapivsky and S. Redner,
               Organization of Growing Random Networks,
               Phys. Rev. E, 63, 066123, 2001.

    gnc_graph(n, create_using=None, seed=None, *, backend=None, **backend_kwargs)
        Returns the growing network with copying (GNC) digraph with `n` nodes.

        The GNC graph is built by adding nodes one at a time with a link to one
        previously added node (chosen uniformly at random) and to all of that
        node's successors.

        Parameters
        ----------
        n : int
            The number of nodes for the generated graph.
        create_using : NetworkX graph constructor, optional (default DiGraph)
            Graph type to create. If graph instance, then cleared before populated.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        References
        ----------
        .. [1] P. L. Krapivsky and S. Redner,
               Network Growth by Copying,
               Phys. Rev. E, 71, 036118, 2005k.},

    gnr_graph(n, p, create_using=None, seed=None, *, backend=None, **backend_kwargs)
        Returns the growing network with redirection (GNR) digraph with `n`
        nodes and redirection probability `p`.

        The GNR graph is built by adding nodes one at a time with a link to one
        previously added node.  The previous target node is chosen uniformly at
        random.  With probability `p` the link is instead "redirected" to the
        successor node of the target.

        The graph is always a (directed) tree.

        Parameters
        ----------
        n : int
            The number of nodes for the generated graph.
        p : float
            The redirection probability.
        create_using : NetworkX graph constructor, optional (default DiGraph)
            Graph type to create. If graph instance, then cleared before populated.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Examples
        --------
        To create the undirected GNR graph, use the :meth:`~DiGraph.to_directed`
        method::

        >>> D = nx.gnr_graph(10, 0.5)  # the GNR graph
        >>> G = D.to_undirected()  # the undirected version

        References
        ----------
        .. [1] P. L. Krapivsky and S. Redner,
               Organization of Growing Random Networks,
               Phys. Rev. E, 63, 066123, 2001.

    random_k_out_graph(n, k, alpha, self_loops=True, seed=None, *, backend=None, **backend_kwargs)
        Returns a random `k`-out graph with preferential attachment.

        A random `k`-out graph with preferential attachment is a
        multidigraph generated by the following algorithm.

        1. Begin with an empty digraph, and initially set each node to have
           weight `alpha`.
        2. Choose a node `u` with out-degree less than `k` uniformly at
           random.
        3. Choose a node `v` from with probability proportional to its
           weight.
        4. Add a directed edge from `u` to `v`, and increase the weight
           of `v` by one.
        5. If each node has out-degree `k`, halt, otherwise repeat from
           step 2.

        For more information on this model of random graph, see [1].

        Parameters
        ----------
        n : int
            The number of nodes in the returned graph.

        k : int
            The out-degree of each node in the returned graph.

        alpha : float
            A positive :class:`float` representing the initial weight of
            each vertex. A higher number means that in step 3 above, nodes
            will be chosen more like a true uniformly random sample, and a
            lower number means that nodes are more likely to be chosen as
            their in-degree increases. If this parameter is not positive, a
            :exc:`ValueError` is raised.

        self_loops : bool
            If True, self-loops are allowed when generating the graph.

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        :class:`~networkx.classes.MultiDiGraph`
            A `k`-out-regular multidigraph generated according to the above
            algorithm.

        Raises
        ------
        ValueError
            If `alpha` is not positive.

        Notes
        -----
        The returned multidigraph may not be strongly connected, or even
        weakly connected.

        References
        ----------
        [1]: Peterson, Nicholas R., and Boris Pittel.
             "Distance between two random `k`-out digraphs, with and without
             preferential attachment."
             arXiv preprint arXiv:1311.5961 (2013).
             <https://arxiv.org/abs/1311.5961>

    scale_free_graph(n, alpha=0.41, beta=0.54, gamma=0.05, delta_in=0.2, delta_out=0, seed=None, initial_graph=None, *, backend=None, **backend_kwargs)
        Returns a scale-free directed graph.

        Parameters
        ----------
        n : integer
            Number of nodes in graph
        alpha : float
            Probability for adding a new node connected to an existing node
            chosen randomly according to the in-degree distribution.
        beta : float
            Probability for adding an edge between two existing nodes.
            One existing node is chosen randomly according the in-degree
            distribution and the other chosen randomly according to the out-degree
            distribution.
        gamma : float
            Probability for adding a new node connected to an existing node
            chosen randomly according to the out-degree distribution.
        delta_in : float
            Bias for choosing nodes from in-degree distribution.
        delta_out : float
            Bias for choosing nodes from out-degree distribution.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        initial_graph : MultiDiGraph instance, optional
            Build the scale-free graph starting from this initial MultiDiGraph,
            if provided.

        Returns
        -------
        MultiDiGraph

        Examples
        --------
        Create a scale-free graph on one hundred nodes::

        >>> G = nx.scale_free_graph(100)

        Notes
        -----
        The sum of `alpha`, `beta`, and `gamma` must be 1.

        References
        ----------
        .. [1] B. Bollobás, C. Borgs, J. Chayes, and O. Riordan,
               Directed scale-free graphs,
               Proceedings of the fourteenth annual ACM-SIAM Symposium on
               Discrete Algorithms, 132--139, 2003.

DATA
    __all__ = ['gn_graph', 'gnc_graph', 'gnr_graph', 'random_k_out_graph',...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\directed.py

networkx.directed_combinatorial_laplacian_matrix
Python Library Documentation: function directed_combinatorial_laplacian_matrix in module networkx.linalg.laplacianmatrix

directed_combinatorial_laplacian_matrix(G, nodelist=None, weight='weight', walk_type=None, alpha=0.95, *, backend=None, **backend_kwargs)
    Return the directed combinatorial Laplacian matrix of G.

    The graph directed combinatorial Laplacian is the matrix

    .. math::

        L = \Phi - \frac{1}{2} \left (\Phi P + P^T \Phi \right)

    where `P` is the transition matrix of the graph and `\Phi` a matrix
    with the Perron vector of `P` in the diagonal and zeros elsewhere [1]_.

    Depending on the value of walk_type, `P` can be the transition matrix
    induced by a random walk, a lazy random walk, or a random walk with
    teleportation (PageRank).

    Parameters
    ----------
    G : DiGraph
       A NetworkX graph

    nodelist : list, optional
       The rows and columns are ordered according to the nodes in nodelist.
       If nodelist is None, then the ordering is produced by G.nodes().

    weight : string or None, optional (default='weight')
       The edge data key used to compute each value in the matrix.
       If None, then each edge has weight 1.

    walk_type : string or None, optional (default=None)
        One of ``"random"``, ``"lazy"``, or ``"pagerank"``. If ``walk_type=None``
        (the default), then a value is selected according to the properties of `G`:
        - ``walk_type="random"`` if `G` is strongly connected and aperiodic
        - ``walk_type="lazy"`` if `G` is strongly connected but not aperiodic
        - ``walk_type="pagerank"`` for all other cases.

    alpha : real
       (1 - alpha) is the teleportation probability used with pagerank

    Returns
    -------
    L : NumPy matrix
      Combinatorial Laplacian of G.

    Notes
    -----
    Only implemented for DiGraphs

    The result is always a symmetric matrix.

    This calculation uses the out-degree of the graph `G`. To use the
    in-degree for calculations instead, use `G.reverse(copy=False)` and
    take the transpose.

    See Also
    --------
    laplacian_matrix
    normalized_laplacian_matrix
    directed_laplacian_matrix

    References
    ----------
    .. [1] Fan Chung (2005).
       Laplacians and the Cheeger inequality for directed graphs.
       Annals of Combinatorics, 9(1), 2005
networkx.directed_configuration_model
Python Library Documentation: function directed_configuration_model in module networkx.generators.degree_seq

directed_configuration_model(in_degree_sequence, out_degree_sequence, create_using=None, seed=None, *, backend=None, **backend_kwargs)
    Returns a directed_random graph with the given degree sequences.

    The configuration model generates a random directed pseudograph
    (graph with parallel edges and self loops) by randomly assigning
    edges to match the given degree sequences.

    Parameters
    ----------
    in_degree_sequence :  list of nonnegative integers
       Each list entry corresponds to the in-degree of a node.
    out_degree_sequence :  list of nonnegative integers
       Each list entry corresponds to the out-degree of a node.
    create_using : NetworkX graph constructor, optional (default MultiDiGraph)
        Graph type to create. If graph instance, then cleared before populated.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : MultiDiGraph
        A graph with the specified degree sequences.
        Nodes are labeled starting at 0 with an index
        corresponding to the position in deg_sequence.

    Raises
    ------
    NetworkXError
        If the degree sequences do not have the same sum.

    See Also
    --------
    configuration_model

    Notes
    -----
    Algorithm as described by Newman [1]_.

    A non-graphical degree sequence (not realizable by some simple
    graph) is allowed since this function returns graphs with self
    loops and parallel edges.  An exception is raised if the degree
    sequences does not have the same sum.

    This configuration model construction process can lead to
    duplicate edges and loops.  You can remove the self-loops and
    parallel edges (see below) which will likely result in a graph
    that doesn't have the exact degree sequence specified.  This
    "finite-size effect" decreases as the size of the graph increases.

    References
    ----------
    .. [1] Newman, M. E. J. and Strogatz, S. H. and Watts, D. J.
       Random graphs with arbitrary degree distributions and their applications
       Phys. Rev. E, 64, 026118 (2001)

    Examples
    --------
    One can modify the in- and out-degree sequences from an existing
    directed graph in order to create a new directed graph. For example,
    here we modify the directed path graph:

    >>> D = nx.DiGraph([(0, 1), (1, 2), (2, 3)])
    >>> din = list(d for n, d in D.in_degree())
    >>> dout = list(d for n, d in D.out_degree())
    >>> din.append(1)
    >>> dout[0] = 2
    >>> # We now expect an edge from node 0 to a new node, node 3.
    ... D = nx.directed_configuration_model(din, dout)

    The returned graph is a directed multigraph, which may have parallel
    edges. To remove any parallel edges from the returned graph:

    >>> D = nx.DiGraph(D)

    Similarly, to remove self-loops:

    >>> D.remove_edges_from(nx.selfloop_edges(D))
networkx.directed_edge_swap
Python Library Documentation: function directed_edge_swap in module networkx.algorithms.swap

directed_edge_swap(G, *, nswap=1, max_tries=100, seed=None, backend=None, **backend_kwargs)
    Swap three edges in a directed graph while keeping the node degrees fixed.

    A directed edge swap swaps three edges such that a -> b -> c -> d becomes
    a -> c -> b -> d. This pattern of swapping allows all possible states with the
    same in- and out-degree distribution in a directed graph to be reached.

    If the swap would create parallel edges (e.g. if a -> c already existed in the
    previous example), another attempt is made to find a suitable trio of edges.

    Parameters
    ----------
    G : DiGraph
       A directed graph

    nswap : integer (optional, default=1)
       Number of three-edge (directed) swaps to perform

    max_tries : integer (optional, default=100)
       Maximum number of attempts to swap edges

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : DiGraph
       The graph after the edges are swapped.

    Raises
    ------
    NetworkXError
        If `G` is not directed, or
        If nswap > max_tries, or
        If there are fewer than 4 nodes or 3 edges in `G`.
    NetworkXAlgorithmError
        If the number of swap attempts exceeds `max_tries` before `nswap` swaps are made

    Notes
    -----
    Does not enforce any connectivity constraints.

    The graph G is modified in place.

    A later swap is allowed to undo a previous swap.

    References
    ----------
    .. [1] Erdős, Péter L., et al. “A Simple Havel-Hakimi Type Algorithm to Realize
           Graphical Degree Sequences of Directed Graphs.” ArXiv:0905.4913 [Math],
           Jan. 2010. https://doi.org/10.48550/arXiv.0905.4913.
           Published  2010 in Elec. J. Combinatorics (17(1)). R66.
           http://www.combinatorics.org/Volume_17/PDF/v17i1r66.pdf
    .. [2] “Combinatorics - Reaching All Possible Simple Directed Graphs with a given
           Degree Sequence with 2-Edge Swaps.” Mathematics Stack Exchange,
           https://math.stackexchange.com/questions/22272/. Accessed 30 May 2022.
networkx.directed_havel_hakimi_graph
Python Library Documentation: function directed_havel_hakimi_graph in module networkx.generators.degree_seq

directed_havel_hakimi_graph(in_deg_sequence, out_deg_sequence, create_using=None, *, backend=None, **backend_kwargs)
    Returns a directed graph with the given degree sequences.

    Parameters
    ----------
    in_deg_sequence :  list of integers
        Each list entry corresponds to the in-degree of a node.
    out_deg_sequence : list of integers
        Each list entry corresponds to the out-degree of a node.
    create_using : NetworkX graph constructor, optional (default DiGraph)
        Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : DiGraph
        A graph with the specified degree sequences.
        Nodes are labeled starting at 0 with an index
        corresponding to the position in deg_sequence

    Raises
    ------
    NetworkXError
        If the degree sequences are not digraphical.

    See Also
    --------
    configuration_model

    Notes
    -----
    Algorithm as described by Kleitman and Wang [1]_.

    References
    ----------
    .. [1] D.J. Kleitman and D.L. Wang
       Algorithms for Constructing Graphs and Digraphs with Given Valences
       and Factors Discrete Mathematics, 6(1), pp. 79-88 (1973)
networkx.directed_joint_degree_graph
Python Library Documentation: function directed_joint_degree_graph in module networkx.generators.joint_degree_seq

directed_joint_degree_graph(in_degrees, out_degrees, nkk, seed=None, *, backend=None, **backend_kwargs)
    Generates a random simple directed graph with the joint degree.

    Parameters
    ----------
    degree_seq :  list of tuples (of size 3)
        degree sequence contains tuples of nodes with node id, in degree and
        out degree.
    nkk  :  dictionary of dictionary of integers
        directed joint degree dictionary, for nodes of out degree k (first
        level of dict) and nodes of in degree l (second level of dict)
        describes the number of edges.
    seed : hashable object, optional
        Seed for random number generator.

    Returns
    -------
    G : Graph
        A directed graph with the specified inputs.

    Raises
    ------
    NetworkXError
        If degree_seq and nkk are not realizable as a simple directed graph.


    Notes
    -----
    Similarly to the undirected version:
    In each iteration of the "while loop" the algorithm picks two disconnected
    nodes v and w, of degree k and l correspondingly,  for which nkk[k][l] has
    not reached its target yet i.e. (for given k,l): n_edges_add < nkk[k][l].
    It then adds edge (v,w) and always increases the number of edges in graph G
    by one.

    The intelligence of the algorithm lies in the fact that  it is always
    possible to add an edge between disconnected nodes v and w, for which
    nkk[degree(v)][degree(w)] has not reached its target, even if one or both
    nodes do not have free stubs. If either node v or w does not have a free
    stub, we perform a "neighbor switch", an edge rewiring move that releases a
    free stub while keeping nkk the same.

    The difference for the directed version lies in the fact that neighbor
    switches might not be able to rewire, but in these cases unsaturated nodes
    can be reassigned to use instead, see [1] for detailed description and
    proofs.

    The algorithm continues for E (number of edges in the graph) iterations of
    the "while loop", at which point all entries of the given nkk[k][l] have
    reached their target values and the construction is complete.

    References
    ----------
    [1] B. Tillman, A. Markopoulou, C. T. Butts & M. Gjoka,
        "Construction of Directed 2K Graphs". In Proc. of KDD 2017.

    Examples
    --------
    >>> in_degrees = [0, 1, 1, 2]
    >>> out_degrees = [1, 1, 1, 1]
    >>> nkk = {1: {1: 2, 2: 2}}
    >>> G = nx.directed_joint_degree_graph(in_degrees, out_degrees, nkk)
    >>>
networkx.directed_laplacian_matrix
Python Library Documentation: function directed_laplacian_matrix in module networkx.linalg.laplacianmatrix

directed_laplacian_matrix(G, nodelist=None, weight='weight', walk_type=None, alpha=0.95, *, backend=None, **backend_kwargs)
    Returns the directed Laplacian matrix of G.

    The graph directed Laplacian is the matrix

    .. math::

        L = I - \frac{1}{2} \left (\Phi^{1/2} P \Phi^{-1/2} + \Phi^{-1/2} P^T \Phi^{1/2} \right )

    where `I` is the identity matrix, `P` is the transition matrix of the
    graph, and `\Phi` a matrix with the Perron vector of `P` in the diagonal and
    zeros elsewhere [1]_.

    Depending on the value of walk_type, `P` can be the transition matrix
    induced by a random walk, a lazy random walk, or a random walk with
    teleportation (PageRank).

    Parameters
    ----------
    G : DiGraph
       A NetworkX graph

    nodelist : list, optional
       The rows and columns are ordered according to the nodes in nodelist.
       If nodelist is None, then the ordering is produced by G.nodes().

    weight : string or None, optional (default='weight')
       The edge data key used to compute each value in the matrix.
       If None, then each edge has weight 1.

    walk_type : string or None, optional (default=None)
       One of ``"random"``, ``"lazy"``, or ``"pagerank"``. If ``walk_type=None``
       (the default), then a value is selected according to the properties of `G`:
       - ``walk_type="random"`` if `G` is strongly connected and aperiodic
       - ``walk_type="lazy"`` if `G` is strongly connected but not aperiodic
       - ``walk_type="pagerank"`` for all other cases.

    alpha : real
       (1 - alpha) is the teleportation probability used with pagerank

    Returns
    -------
    L : NumPy matrix
      Normalized Laplacian of G.

    Notes
    -----
    Only implemented for DiGraphs

    The result is always a symmetric matrix.

    This calculation uses the out-degree of the graph `G`. To use the
    in-degree for calculations instead, use `G.reverse(copy=False)` and
    take the transpose.

    See Also
    --------
    laplacian_matrix
    normalized_laplacian_matrix
    directed_combinatorial_laplacian_matrix

    References
    ----------
    .. [1] Fan Chung (2005).
       Laplacians and the Cheeger inequality for directed graphs.
       Annals of Combinatorics, 9(1), 2005
networkx.directed_modularity_matrix
Python Library Documentation: function directed_modularity_matrix in module networkx.linalg.modularitymatrix

directed_modularity_matrix(G, nodelist=None, weight=None, *, backend=None, **backend_kwargs)
    Returns the directed modularity matrix of G.

    The modularity matrix is the matrix B = A - <A>, where A is the adjacency
    matrix and <A> is the expected adjacency matrix, assuming that the graph
    is described by the configuration model.

    More specifically, the element B_ij of B is defined as

    .. math::
        B_{ij} = A_{ij} - k_i^{out} k_j^{in} / m

    where :math:`k_i^{in}` is the in degree of node i, and :math:`k_j^{out}` is the out degree
    of node j, with m the number of edges in the graph. When weight is set
    to a name of an attribute edge, Aij, k_i, k_j and m are computed using
    its value.

    Parameters
    ----------
    G : DiGraph
       A NetworkX DiGraph

    nodelist : list, optional
       The rows and columns are ordered according to the nodes in nodelist.
       If nodelist is None, then the ordering is produced by G.nodes().

    weight : string or None, optional (default=None)
       The edge attribute that holds the numerical value used for
       the edge weight.  If None then all edge weights are 1.

    Returns
    -------
    B : Numpy array
      The modularity matrix of G.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_edges_from(
    ...     (
    ...         (1, 2),
    ...         (1, 3),
    ...         (3, 1),
    ...         (3, 2),
    ...         (3, 5),
    ...         (4, 5),
    ...         (4, 6),
    ...         (5, 4),
    ...         (5, 6),
    ...         (6, 4),
    ...     )
    ... )
    >>> B = nx.directed_modularity_matrix(G)


    Notes
    -----
    NetworkX defines the element A_ij of the adjacency matrix as 1 if there
    is a link going from node i to node j. Leicht and Newman use the opposite
    definition. This explains the different expression for B_ij.

    See Also
    --------
    to_numpy_array
    modularity_spectrum
    adjacency_matrix
    modularity_matrix

    References
    ----------
    .. [1] E. A. Leicht, M. E. J. Newman,
        "Community structure in directed networks",
        Phys. Rev Lett., vol. 100, no. 11, p. 118703, 2008.
networkx.disjoint_union
Python Library Documentation: function disjoint_union in module networkx.algorithms.operators.binary

disjoint_union(G, H, *, backend=None, **backend_kwargs)
    Combine graphs G and H. The nodes are assumed to be unique (disjoint).

    This algorithm automatically relabels nodes to avoid name collisions.

    Parameters
    ----------
    G,H : graph
       A NetworkX graph

    Returns
    -------
    U : A union graph with the same type as G.

    See Also
    --------
    union
    compose
    :func:`~networkx.Graph.update`

    Notes
    -----
    A new graph is created, of the same class as G.  It is recommended
    that G and H be either both directed or both undirected.

    The nodes of G are relabeled 0 to len(G)-1, and the nodes of H are
    relabeled len(G) to len(G)+len(H)-1.

    Renumbering forces G and H to be disjoint, so no exception is ever raised for a name collision.
    To preserve the check for common nodes, use union().

    Edge and node attributes are propagated from G and H to the union graph.
    Graph attributes are also propagated, but if they are present in both G and H,
    then the value from H is used.

    To combine graphs that have common nodes, consider compose(G, H)
    or the method, Graph.update().

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (1, 2)])
    >>> H = nx.Graph([(0, 3), (1, 2), (2, 3)])
    >>> G.nodes[0]["key1"] = 5
    >>> H.nodes[0]["key2"] = 10
    >>> U = nx.disjoint_union(G, H)
    >>> U.nodes(data=True)
    NodeDataView({0: {'key1': 5}, 1: {}, 2: {}, 3: {'key2': 10}, 4: {}, 5: {}, 6: {}})
    >>> U.edges
    EdgeView([(0, 1), (0, 2), (1, 2), (3, 4), (4, 6), (5, 6)])
networkx.disjoint_union_all
Python Library Documentation: function disjoint_union_all in module networkx.algorithms.operators.all

disjoint_union_all(graphs, *, backend=None, **backend_kwargs)
    Returns the disjoint union of all graphs.

    This operation forces distinct integer node labels starting with 0
    for the first graph in the list and numbering consecutively.

    Parameters
    ----------
    graphs : iterable
       Iterable of NetworkX graphs

    Returns
    -------
    U : A graph with the same type as the first graph in list

    Raises
    ------
    ValueError
       If `graphs` is an empty list.

    NetworkXError
        In case of mixed type graphs, like MultiGraph and Graph, or directed and undirected graphs.

    Examples
    --------
    >>> G1 = nx.Graph([(1, 2), (2, 3)])
    >>> G2 = nx.Graph([(4, 5), (5, 6)])
    >>> U = nx.disjoint_union_all([G1, G2])
    >>> list(U.nodes())
    [0, 1, 2, 3, 4, 5]
    >>> list(U.edges())
    [(0, 1), (1, 2), (3, 4), (4, 5)]

    Notes
    -----
    For operating on mixed type graphs, they should be converted to the same type.

    Graph, edge, and node attributes are propagated to the union graph.
    If a graph attribute is present in multiple graphs, then the value
    from the last graph in the list with that attribute is used.
networkx.dispersion
Python Library Documentation: function dispersion in module networkx.algorithms.centrality.dispersion

dispersion(G, u=None, v=None, normalized=True, alpha=1.0, b=0.0, c=0.0, *, backend=None, **backend_kwargs)
    Calculate dispersion between `u` and `v` in `G`.

    A link between two actors (`u` and `v`) has a high dispersion when their
    mutual ties (`s` and `t`) are not well connected with each other.

    Parameters
    ----------
    G : graph
        A NetworkX graph.
    u : node, optional
        The source for the dispersion score (e.g. ego node of the network).
    v : node, optional
        The target of the dispersion score if specified.
    normalized : bool
        If True (default) normalize by the embeddedness of the nodes (u and v).
    alpha, b, c : float
        Parameters for the normalization procedure. When `normalized` is True,
        the dispersion value is normalized by::

            result = ((dispersion + b) ** alpha) / (embeddedness + c)

        as long as the denominator is nonzero.

    Returns
    -------
    nodes : dictionary
        If u (v) is specified, returns a dictionary of nodes with dispersion
        score for all "target" ("source") nodes. If neither u nor v is
        specified, returns a dictionary of dictionaries for all nodes 'u' in the
        graph with a dispersion score for each node 'v'.

    Notes
    -----
    This implementation follows Lars Backstrom and Jon Kleinberg [1]_. Typical
    usage would be to run dispersion on the ego network $G_u$ if $u$ were
    specified.  Running :func:`dispersion` with neither $u$ nor $v$ specified
    can take some time to complete.

    References
    ----------
    .. [1] Romantic Partnerships and the Dispersion of Social Ties:
        A Network Analysis of Relationship Status on Facebook.
        Lars Backstrom, Jon Kleinberg.
        https://arxiv.org/pdf/1310.6753v1.pdf
networkx.distance_measures
Python Library Documentation: module networkx.algorithms.distance_measures in networkx.algorithms

NAME
    networkx.algorithms.distance_measures - Graph diameter, radius, eccentricity and other properties.

FUNCTIONS
    barycenter(G, weight=None, attr=None, sp=None, *, backend=None, **backend_kwargs)
        Calculate barycenter of a connected graph, optionally with edge weights.

        The :dfn:`barycenter` a
        :func:`connected <networkx.algorithms.components.is_connected>` graph
        :math:`G` is the subgraph induced by the set of its nodes :math:`v`
        minimizing the objective function

        .. math::

            \sum_{u \in V(G)} d_G(u, v),

        where :math:`d_G` is the (possibly weighted) :func:`path length
        <networkx.algorithms.shortest_paths.generic.shortest_path_length>`.
        The barycenter is also called the :dfn:`median`. See [West01]_, p. 78.

        Parameters
        ----------
        G : :class:`networkx.Graph`
            The connected graph :math:`G`.
        weight : :class:`str`, optional
            Passed through to
            :func:`~networkx.algorithms.shortest_paths.generic.shortest_path_length`.
        attr : :class:`str`, optional
            If given, write the value of the objective function to each node's
            `attr` attribute. Otherwise do not store the value.
        sp : dict of dicts, optional
           All pairs shortest path lengths as a dictionary of dictionaries

        Returns
        -------
        list
            Nodes of `G` that induce the barycenter of `G`.

        Raises
        ------
        NetworkXNoPath
            If `G` is disconnected. `G` may appear disconnected to
            :func:`barycenter` if `sp` is given but is missing shortest path
            lengths for any pairs.
        ValueError
            If `sp` and `weight` are both given.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
        >>> nx.barycenter(G)
        [1, 3, 4]

        See Also
        --------
        center
        periphery

    center(G, e=None, usebounds=False, weight=None, *, backend=None, **backend_kwargs)
        Returns the center of the graph G.

        The center is the set of nodes with eccentricity equal to radius.

        Parameters
        ----------
        G : NetworkX graph
           A graph

        e : eccentricity dictionary, optional
          A precomputed dictionary of eccentricities.

        weight : string, function, or None
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

            If this is None, every edge has weight/distance/cost 1.

            Weights stored as floating point values can lead to small round-off
            errors in distances. Use integer weights to avoid this.

            Weights should be positive, since they are distances.

        Returns
        -------
        c : list
           List of nodes in center

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
        >>> list(nx.center(G))
        [1, 3, 4]

        See Also
        --------
        barycenter
        periphery

    diameter(G, e=None, usebounds=False, weight=None, *, backend=None, **backend_kwargs)
        Returns the diameter of the graph G.

        The diameter is the maximum eccentricity.

        Parameters
        ----------
        G : NetworkX graph
           A graph

        e : eccentricity dictionary, optional
          A precomputed dictionary of eccentricities.

        weight : string, function, or None
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

            If this is None, every edge has weight/distance/cost 1.

            Weights stored as floating point values can lead to small round-off
            errors in distances. Use integer weights to avoid this.

            Weights should be positive, since they are distances.

        Returns
        -------
        d : integer
           Diameter of graph

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
        >>> nx.diameter(G)
        3

        See Also
        --------
        eccentricity

    eccentricity(G, v=None, sp=None, weight=None, *, backend=None, **backend_kwargs)
        Returns the eccentricity of nodes in G.

        The eccentricity of a node v is the maximum distance from v to
        all other nodes in G.

        Parameters
        ----------
        G : NetworkX graph
           A graph

        v : node, optional
           Return value of specified node

        sp : dict of dicts, optional
           All pairs shortest path lengths as a dictionary of dictionaries

        weight : string, function, or None (default=None)
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

            If this is None, every edge has weight/distance/cost 1.

            Weights stored as floating point values can lead to small round-off
            errors in distances. Use integer weights to avoid this.

            Weights should be positive, since they are distances.

        Returns
        -------
        ecc : dictionary
           A dictionary of eccentricity values keyed by node.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
        >>> dict(nx.eccentricity(G))
        {1: 2, 2: 3, 3: 2, 4: 2, 5: 3}

        >>> dict(
        ...     nx.eccentricity(G, v=[1, 5])
        ... )  # This returns the eccentricity of node 1 & 5
        {1: 2, 5: 3}

    effective_graph_resistance(G, weight=None, invert_weight=True, *, backend=None, **backend_kwargs)
        Returns the Effective graph resistance of G.

        Also known as the Kirchhoff index.

        The effective graph resistance is defined as the sum
        of the resistance distance of every node pair in G [1]_.

        If weight is not provided, then a weight of 1 is used for all edges.

        The effective graph resistance of a disconnected graph is infinite.

        Parameters
        ----------
        G : NetworkX graph
           A graph

        weight : string or None, optional (default=None)
           The edge data key used to compute the effective graph resistance.
           If None, then each edge has weight 1.

        invert_weight : boolean (default=True)
            Proper calculation of resistance distance requires building the
            Laplacian matrix with the reciprocal of the weight. Not required
            if the weight is already inverted. Weight cannot be zero.

        Returns
        -------
        RG : float
            The effective graph resistance of `G`.

        Raises
        ------
        NetworkXNotImplemented
            If `G` is a directed graph.

        NetworkXError
            If `G` does not contain any nodes.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
        >>> round(nx.effective_graph_resistance(G), 10)
        10.25

        Notes
        -----
        The implementation is based on Theorem 2.2 in [2]_. Self-loops are ignored.
        Multi-edges are contracted in one edge with weight equal to the harmonic sum of the weights.

        References
        ----------
        .. [1] Wolfram
           "Kirchhoff Index."
           https://mathworld.wolfram.com/KirchhoffIndex.html
        .. [2] W. Ellens, F. M. Spieksma, P. Van Mieghem, A. Jamakovic, R. E. Kooij.
            Effective graph resistance.
            Lin. Alg. Appl. 435:2491-2506, 2011.

    harmonic_diameter(G, sp=None, *, backend=None, **backend_kwargs)
        Returns the harmonic diameter of the graph G.

        The harmonic diameter of a graph is the harmonic mean of the distances
        between all pairs of distinct vertices. Graphs that are not strongly
        connected have infinite diameter and mean distance, making such
        measures not useful. Restricting the diameter or mean distance to
        finite distances yields paradoxical values (e.g., a perfect match
        would have diameter one). The harmonic mean handles gracefully
        infinite distances (e.g., a perfect match has harmonic diameter equal
        to the number of vertices minus one), making it possible to assign a
        meaningful value to all graphs.

        Note that in [1] the harmonic diameter is called "connectivity length":
        however, "harmonic diameter" is a more standard name from the
        theory of metric spaces. The name "harmonic mean distance" is perhaps
        a more descriptive name, but is not used in the literature, so we use the
        name "harmonic diameter" here.

        Parameters
        ----------
        G : NetworkX graph
           A graph

        sp : dict of dicts, optional
           All-pairs shortest path lengths as a dictionary of dictionaries

        Returns
        -------
        hd : float
           Harmonic diameter of graph

        References
        ----------
        .. [1] Massimo Marchiori and Vito Latora, "Harmony in the small-world".
               *Physica A: Statistical Mechanics and Its Applications*
               285(3-4), pages 539-546, 2000.
               <https://doi.org/10.1016/S0378-4371(00)00311-3>

    kemeny_constant(G, *, weight=None, backend=None, **backend_kwargs)
        Returns the Kemeny constant of the given graph.

        The *Kemeny constant* (or Kemeny's constant) of a graph `G`
        can be computed by regarding the graph as a Markov chain.
        The Kemeny constant is then the expected number of time steps
        to transition from a starting state i to a random destination state
        sampled from the Markov chain's stationary distribution.
        The Kemeny constant is independent of the chosen initial state [1]_.

        The Kemeny constant measures the time needed for spreading
        across a graph. Low values indicate a closely connected graph
        whereas high values indicate a spread-out graph.

        If weight is not provided, then a weight of 1 is used for all edges.

        Since `G` represents a Markov chain, the weights must be positive.

        Parameters
        ----------
        G : NetworkX graph

        weight : string or None, optional (default=None)
           The edge data key used to compute the Kemeny constant.
           If None, then each edge has weight 1.

        Returns
        -------
        float
            The Kemeny constant of the graph `G`.

        Raises
        ------
        NetworkXNotImplemented
            If the graph `G` is directed.

        NetworkXError
            If the graph `G` is not connected, or contains no nodes,
            or has edges with negative weights.

        Examples
        --------
        >>> G = nx.complete_graph(5)
        >>> round(nx.kemeny_constant(G), 10)
        3.2

        Notes
        -----
        The implementation is based on equation (3.3) in [2]_.
        Self-loops are allowed and indicate a Markov chain where
        the state can remain the same. Multi-edges are contracted
        in one edge with weight equal to the sum of the weights.

        References
        ----------
        .. [1] Wikipedia
           "Kemeny's constant."
           https://en.wikipedia.org/wiki/Kemeny%27s_constant
        .. [2] Lovász L.
            Random walks on graphs: A survey.
            Paul Erdös is Eighty, vol. 2, Bolyai Society,
            Mathematical Studies, Keszthely, Hungary (1993), pp. 1-46

    periphery(G, e=None, usebounds=False, weight=None, *, backend=None, **backend_kwargs)
        Returns the periphery of the graph G.

        The periphery is the set of nodes with eccentricity equal to the diameter.

        Parameters
        ----------
        G : NetworkX graph
           A graph

        e : eccentricity dictionary, optional
          A precomputed dictionary of eccentricities.

        weight : string, function, or None
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

            If this is None, every edge has weight/distance/cost 1.

            Weights stored as floating point values can lead to small round-off
            errors in distances. Use integer weights to avoid this.

            Weights should be positive, since they are distances.

        Returns
        -------
        p : list
           List of nodes in periphery

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
        >>> nx.periphery(G)
        [2, 5]

        See Also
        --------
        barycenter
        center

    radius(G, e=None, usebounds=False, weight=None, *, backend=None, **backend_kwargs)
        Returns the radius of the graph G.

        The radius is the minimum eccentricity.

        Parameters
        ----------
        G : NetworkX graph
           A graph

        e : eccentricity dictionary, optional
          A precomputed dictionary of eccentricities.

        weight : string, function, or None
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

            If this is None, every edge has weight/distance/cost 1.

            Weights stored as floating point values can lead to small round-off
            errors in distances. Use integer weights to avoid this.

            Weights should be positive, since they are distances.

        Returns
        -------
        r : integer
           Radius of graph

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
        >>> nx.radius(G)
        2

    resistance_distance(G, nodeA=None, nodeB=None, weight=None, invert_weight=True, *, backend=None, **backend_kwargs)
        Returns the resistance distance between pairs of nodes in graph G.

        The resistance distance between two nodes of a graph is akin to treating
        the graph as a grid of resistors with a resistance equal to the provided
        weight [1]_, [2]_.

        If weight is not provided, then a weight of 1 is used for all edges.

        If two nodes are the same, the resistance distance is zero.

        Parameters
        ----------
        G : NetworkX graph
           A graph

        nodeA : node or None, optional (default=None)
          A node within graph G.
          If None, compute resistance distance using all nodes as source nodes.

        nodeB : node or None, optional (default=None)
          A node within graph G.
          If None, compute resistance distance using all nodes as target nodes.

        weight : string or None, optional (default=None)
           The edge data key used to compute the resistance distance.
           If None, then each edge has weight 1.

        invert_weight : boolean (default=True)
            Proper calculation of resistance distance requires building the
            Laplacian matrix with the reciprocal of the weight. Not required
            if the weight is already inverted. Weight cannot be zero.

        Returns
        -------
        rd : dict or float
           If `nodeA` and `nodeB` are given, resistance distance between `nodeA`
           and `nodeB`. If `nodeA` or `nodeB` is unspecified (the default), a
           dictionary of nodes with resistance distances as the value.

        Raises
        ------
        NetworkXNotImplemented
            If `G` is a directed graph.

        NetworkXError
            If `G` is not connected, or contains no nodes,
            or `nodeA` is not in `G` or `nodeB` is not in `G`.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
        >>> round(nx.resistance_distance(G, 1, 3), 10)
        0.625

        Notes
        -----
        The implementation is based on Theorem A in [2]_. Self-loops are ignored.
        Multi-edges are contracted in one edge with weight equal to the harmonic sum of the weights.

        References
        ----------
        .. [1] Wikipedia
           "Resistance distance."
           https://en.wikipedia.org/wiki/Resistance_distance
        .. [2] D. J. Klein and M. Randic.
            Resistance distance.
            J. of Math. Chem. 12:81-95, 1993.

DATA
    __all__ = ['eccentricity', 'diameter', 'harmonic_diameter', 'radius', ...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\distance_measures.py

networkx.distance_regular
Python Library Documentation: module networkx.algorithms.distance_regular in networkx.algorithms

NAME
    networkx.algorithms.distance_regular

DESCRIPTION
    =======================
    Distance-regular graphs
    =======================

FUNCTIONS
    global_parameters(b, c)
        Returns global parameters for a given intersection array.

        Given a distance-regular graph G with integers b_i, c_i,i = 0,....,d
        such that for any 2 vertices x,y in G at a distance i=d(x,y), there
        are exactly c_i neighbors of y at a distance of i-1 from x and b_i
        neighbors of y at a distance of i+1 from x.

        Thus, a distance regular graph has the global parameters,
        [[c_0,a_0,b_0],[c_1,a_1,b_1],......,[c_d,a_d,b_d]] for the
        intersection array  [b_0,b_1,.....b_{d-1};c_1,c_2,.....c_d]
        where a_i+b_i+c_i=k , k= degree of every vertex.

        Parameters
        ----------
        b : list

        c : list

        Returns
        -------
        iterable
           An iterable over three tuples.

        Examples
        --------
        >>> G = nx.dodecahedral_graph()
        >>> b, c = nx.intersection_array(G)
        >>> list(nx.global_parameters(b, c))
        [(0, 0, 3), (1, 0, 2), (1, 1, 1), (1, 1, 1), (2, 0, 1), (3, 0, 0)]

        References
        ----------
        .. [1] Weisstein, Eric W. "Global Parameters."
           From MathWorld--A Wolfram Web Resource.
           http://mathworld.wolfram.com/GlobalParameters.html

        See Also
        --------
        intersection_array

    intersection_array(G, *, backend=None, **backend_kwargs)
        Returns the intersection array of a distance-regular graph.

        Given a distance-regular graph G with integers b_i, c_i,i = 0,....,d
        such that for any 2 vertices x,y in G at a distance i=d(x,y), there
        are exactly c_i neighbors of y at a distance of i-1 from x and b_i
        neighbors of y at a distance of i+1 from x.

        A distance regular graph's intersection array is given by,
        [b_0,b_1,.....b_{d-1};c_1,c_2,.....c_d]

        Parameters
        ----------
        G: Networkx graph (undirected)

        Returns
        -------
        b,c: tuple of lists

        Examples
        --------
        >>> G = nx.icosahedral_graph()
        >>> nx.intersection_array(G)
        ([5, 2, 1], [1, 2, 5])

        References
        ----------
        .. [1] Weisstein, Eric W. "Intersection Array."
           From MathWorld--A Wolfram Web Resource.
           http://mathworld.wolfram.com/IntersectionArray.html

        See Also
        --------
        global_parameters

    is_distance_regular(G, *, backend=None, **backend_kwargs)
        Returns True if the graph is distance regular, False otherwise.

        A connected graph G is distance-regular if for any nodes x,y
        and any integers i,j=0,1,...,d (where d is the graph
        diameter), the number of vertices at distance i from x and
        distance j from y depends only on i,j and the graph distance
        between x and y, independently of the choice of x and y.

        Parameters
        ----------
        G: Networkx graph (undirected)

        Returns
        -------
        bool
          True if the graph is Distance Regular, False otherwise

        Examples
        --------
        >>> G = nx.hypercube_graph(6)
        >>> nx.is_distance_regular(G)
        True

        See Also
        --------
        intersection_array, global_parameters

        Notes
        -----
        For undirected and simple graphs only

        References
        ----------
        .. [1] Brouwer, A. E.; Cohen, A. M.; and Neumaier, A.
            Distance-Regular Graphs. New York: Springer-Verlag, 1989.
        .. [2] Weisstein, Eric W. "Distance-Regular Graph."
            http://mathworld.wolfram.com/Distance-RegularGraph.html

    is_strongly_regular(G, *, backend=None, **backend_kwargs)
        Returns True if and only if the given graph is strongly
        regular.

        An undirected graph is *strongly regular* if

        * it is regular,
        * each pair of adjacent vertices has the same number of neighbors in
          common,
        * each pair of nonadjacent vertices has the same number of neighbors
          in common.

        Each strongly regular graph is a distance-regular graph.
        Conversely, if a distance-regular graph has diameter two, then it is
        a strongly regular graph. For more information on distance-regular
        graphs, see :func:`is_distance_regular`.

        Parameters
        ----------
        G : NetworkX graph
            An undirected graph.

        Returns
        -------
        bool
            Whether `G` is strongly regular.

        Examples
        --------

        The cycle graph on five vertices is strongly regular. It is
        two-regular, each pair of adjacent vertices has no shared neighbors,
        and each pair of nonadjacent vertices has one shared neighbor::

            >>> G = nx.cycle_graph(5)
            >>> nx.is_strongly_regular(G)
            True

DATA
    __all__ = ['is_distance_regular', 'is_strongly_regular', 'intersection...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\distance_regular.py

networkx.dodecahedral_graph
Python Library Documentation: function dodecahedral_graph in module networkx.generators.small

dodecahedral_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Platonic Dodecahedral graph.

    The dodecahedral graph has 20 nodes and 30 edges. The skeleton of the
    dodecahedron forms a graph. It is one of 5 Platonic graphs [1]_.
    It can be described in LCF notation as:
    ``[10, 7, 4, -4, -7, 10, -4, 7, -7, 4]^2`` [2]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Dodecahedral Graph with 20 nodes and 30 edges

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Regular_dodecahedron#Dodecahedral_graph
    .. [2] https://mathworld.wolfram.com/DodecahedralGraph.html
networkx.dominance
Python Library Documentation: module networkx.algorithms.dominance in networkx.algorithms

NAME
    networkx.algorithms.dominance - Dominance algorithms.

FUNCTIONS
    dominance_frontiers(G, start, *, backend=None, **backend_kwargs)
        Returns the dominance frontiers of all nodes of a directed graph.

        Parameters
        ----------
        G : a DiGraph or MultiDiGraph
            The graph where dominance is to be computed.

        start : node
            The start node of dominance computation.

        Returns
        -------
        df : dict keyed by nodes
            A dict containing the dominance frontiers of each node reachable from
            `start` as lists.

        Raises
        ------
        NetworkXNotImplemented
            If `G` is undirected.

        NetworkXError
            If `start` is not in `G`.

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (1, 3), (2, 5), (3, 4), (4, 5)])
        >>> sorted((u, sorted(df)) for u, df in nx.dominance_frontiers(G, 1).items())
        [(1, []), (2, [5]), (3, [5]), (4, [5]), (5, [])]

        References
        ----------
        .. [1] Cooper, Keith D., Harvey, Timothy J. and Kennedy, Ken.
               "A simple, fast dominance algorithm." (2006).
               https://hdl.handle.net/1911/96345

    immediate_dominators(G, start, *, backend=None, **backend_kwargs)
        Returns the immediate dominators of all nodes of a directed graph.

        Parameters
        ----------
        G : a DiGraph or MultiDiGraph
            The graph where dominance is to be computed.

        start : node
            The start node of dominance computation.

        Returns
        -------
        idom : dict keyed by nodes
            A dict containing the immediate dominators of each node reachable from
            `start`.

        Raises
        ------
        NetworkXNotImplemented
            If `G` is undirected.

        NetworkXError
            If `start` is not in `G`.

        Notes
        -----
        Except for `start`, the immediate dominators are the parents of their
        corresponding nodes in the dominator tree.

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (1, 3), (2, 5), (3, 4), (4, 5)])
        >>> sorted(nx.immediate_dominators(G, 1).items())
        [(1, 1), (2, 1), (3, 1), (4, 3), (5, 1)]

        References
        ----------
        .. [1] Cooper, Keith D., Harvey, Timothy J. and Kennedy, Ken.
               "A simple, fast dominance algorithm." (2006).
               https://hdl.handle.net/1911/96345

DATA
    __all__ = ['immediate_dominators', 'dominance_frontiers']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\dominance.py

networkx.dominance_frontiers
Python Library Documentation: function dominance_frontiers in module networkx.algorithms.dominance

dominance_frontiers(G, start, *, backend=None, **backend_kwargs)
    Returns the dominance frontiers of all nodes of a directed graph.

    Parameters
    ----------
    G : a DiGraph or MultiDiGraph
        The graph where dominance is to be computed.

    start : node
        The start node of dominance computation.

    Returns
    -------
    df : dict keyed by nodes
        A dict containing the dominance frontiers of each node reachable from
        `start` as lists.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is undirected.

    NetworkXError
        If `start` is not in `G`.

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (1, 3), (2, 5), (3, 4), (4, 5)])
    >>> sorted((u, sorted(df)) for u, df in nx.dominance_frontiers(G, 1).items())
    [(1, []), (2, [5]), (3, [5]), (4, [5]), (5, [])]

    References
    ----------
    .. [1] Cooper, Keith D., Harvey, Timothy J. and Kennedy, Ken.
           "A simple, fast dominance algorithm." (2006).
           https://hdl.handle.net/1911/96345
networkx.dominating
Python Library Documentation: module networkx.algorithms.dominating in networkx.algorithms

NAME
    networkx.algorithms.dominating - Functions for computing dominating sets in a graph.

FUNCTIONS
    dominating_set(G, start_with=None, *, backend=None, **backend_kwargs)
        Finds a dominating set for the graph G.

        A *dominating set* for a graph with node set *V* is a subset *D* of
        *V* such that every node not in *D* is adjacent to at least one
        member of *D* [1]_.

        Parameters
        ----------
        G : NetworkX graph

        start_with : node (default=None)
            Node to use as a starting point for the algorithm.

        Returns
        -------
        D : set
            A dominating set for G.

        Notes
        -----
        This function is an implementation of algorithm 7 in [2]_ which
        finds some dominating set, not necessarily the smallest one.

        See also
        --------
        is_dominating_set

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Dominating_set

        .. [2] Abdol-Hossein Esfahanian. Connectivity Algorithms.
            http://www.cse.msu.edu/~cse835/Papers/Graph_connectivity_revised.pdf

    is_dominating_set(G, nbunch, *, backend=None, **backend_kwargs)
        Checks if `nbunch` is a dominating set for `G`.

        A *dominating set* for a graph with node set *V* is a subset *D* of
        *V* such that every node not in *D* is adjacent to at least one
        member of *D* [1]_.

        Parameters
        ----------
        G : NetworkX graph

        nbunch : iterable
            An iterable of nodes in the graph `G`.

        See also
        --------
        dominating_set

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Dominating_set

DATA
    __all__ = ['dominating_set', 'is_dominating_set']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\dominating.py

networkx.dominating_set
Python Library Documentation: function dominating_set in module networkx.algorithms.dominating

dominating_set(G, start_with=None, *, backend=None, **backend_kwargs)
    Finds a dominating set for the graph G.

    A *dominating set* for a graph with node set *V* is a subset *D* of
    *V* such that every node not in *D* is adjacent to at least one
    member of *D* [1]_.

    Parameters
    ----------
    G : NetworkX graph

    start_with : node (default=None)
        Node to use as a starting point for the algorithm.

    Returns
    -------
    D : set
        A dominating set for G.

    Notes
    -----
    This function is an implementation of algorithm 7 in [2]_ which
    finds some dominating set, not necessarily the smallest one.

    See also
    --------
    is_dominating_set

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Dominating_set

    .. [2] Abdol-Hossein Esfahanian. Connectivity Algorithms.
        http://www.cse.msu.edu/~cse835/Papers/Graph_connectivity_revised.pdf
networkx.dorogovtsev_goltsev_mendes_graph
Python Library Documentation: function dorogovtsev_goltsev_mendes_graph in module networkx.generators.classic

dorogovtsev_goltsev_mendes_graph(n, create_using=None, *, backend=None, **backend_kwargs)
    Returns the hierarchically constructed Dorogovtsev--Goltsev--Mendes graph.

    The Dorogovtsev--Goltsev--Mendes [1]_ procedure deterministically produces a
    scale-free graph with ``3/2 * (3**(n-1) + 1)`` nodes
    and ``3**n`` edges for a given `n`.

    Note that `n` denotes the number of times the state transition is applied,
    starting from the base graph with ``n = 0`` (no transitions), as in [2]_.
    This is different from the parameter ``t = n - 1`` in [1]_.

    .. plot::

        >>> nx.draw(nx.dorogovtsev_goltsev_mendes_graph(3))

    Parameters
    ----------
    n : integer
        The generation number.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
        Graph type to create. Directed graphs and multigraphs are not supported.

    Returns
    -------
    G : NetworkX `Graph`

    Raises
    ------
    NetworkXError
        If `n` is less than zero.

        If `create_using` is a directed graph or multigraph.

    Examples
    --------
    >>> G = nx.dorogovtsev_goltsev_mendes_graph(3)
    >>> G.number_of_nodes()
    15
    >>> G.number_of_edges()
    27
    >>> nx.is_planar(G)
    True

    References
    ----------
    .. [1] S. N. Dorogovtsev, A. V. Goltsev and J. F. F. Mendes,
        "Pseudofractal scale-free web", Physical Review E 65, 066122, 2002.
        https://arxiv.org/pdf/cond-mat/0112143.pdf
    .. [2] Weisstein, Eric W. "Dorogovtsev--Goltsev--Mendes Graph".
        From MathWorld--A Wolfram Web Resource.
        https://mathworld.wolfram.com/Dorogovtsev-Goltsev-MendesGraph.html
networkx.double_edge_swap
Python Library Documentation: function double_edge_swap in module networkx.algorithms.swap

double_edge_swap(G, nswap=1, max_tries=100, seed=None, *, backend=None, **backend_kwargs)
    Swap two edges in the graph while keeping the node degrees fixed.

    A double-edge swap removes two randomly chosen edges u-v and x-y
    and creates the new edges u-x and v-y::

     u--v            u  v
            becomes  |  |
     x--y            x  y

    If either the edge u-x or v-y already exist no swap is performed
    and another attempt is made to find a suitable edge pair.

    Parameters
    ----------
    G : graph
       An undirected graph

    nswap : integer (optional, default=1)
       Number of double-edge swaps to perform

    max_tries : integer (optional)
       Maximum number of attempts to swap edges

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : graph
       The graph after double edge swaps.

    Raises
    ------
    NetworkXError
        If `G` is directed, or
        If `nswap` > `max_tries`, or
        If there are fewer than 4 nodes or 2 edges in `G`.
    NetworkXAlgorithmError
        If the number of swap attempts exceeds `max_tries` before `nswap` swaps are made

    Notes
    -----
    Does not enforce any connectivity constraints.

    The graph G is modified in place.
networkx.draw
Python Library Documentation: function draw in module networkx.drawing.nx_pylab

draw(G, pos=None, ax=None, **kwds)
    Draw the graph G with Matplotlib.

    Draw the graph as a simple representation with no node
    labels or edge labels and using the full Matplotlib figure area
    and no axis labels by default.  See draw_networkx() for more
    full-featured drawing that allows title, axis labels etc.

    Parameters
    ----------
    G : graph
        A networkx graph

    pos : dictionary, optional
        A dictionary with nodes as keys and positions as values.
        If not specified a spring layout positioning will be computed.
        See :py:mod:`networkx.drawing.layout` for functions that
        compute node positions.

    ax : Matplotlib Axes object, optional
        Draw the graph in specified Matplotlib axes.

    kwds : optional keywords
        See networkx.draw_networkx() for a description of optional keywords.

    Examples
    --------
    >>> G = nx.dodecahedral_graph()
    >>> nx.draw(G)
    >>> nx.draw(G, pos=nx.spring_layout(G))  # use spring layout

    See Also
    --------
    draw_networkx
    draw_networkx_nodes
    draw_networkx_edges
    draw_networkx_labels
    draw_networkx_edge_labels

    Notes
    -----
    This function has the same name as pylab.draw and pyplot.draw
    so beware when using `from networkx import *`

    since you might overwrite the pylab.draw function.

    With pyplot use

    >>> import matplotlib.pyplot as plt
    >>> G = nx.dodecahedral_graph()
    >>> nx.draw(G)  # networkx draw()
    >>> plt.draw()  # pyplot draw()

    Also see the NetworkX drawing examples at
    https://networkx.org/documentation/latest/auto_examples/index.html
networkx.draw_circular
Python Library Documentation: function draw_circular in module networkx.drawing.nx_pylab

draw_circular(G, **kwargs)
    Draw the graph `G` with a circular layout.

    This is a convenience function equivalent to::

        nx.draw(G, pos=nx.circular_layout(G), **kwargs)

    Parameters
    ----------
    G : graph
        A networkx graph

    kwargs : optional keywords
        See `draw_networkx` for a description of optional keywords.

    Notes
    -----
    The layout is computed each time this function is called. For
    repeated drawing it is much more efficient to call
    `~networkx.drawing.layout.circular_layout` directly and reuse the result::

        >>> G = nx.complete_graph(5)
        >>> pos = nx.circular_layout(G)
        >>> nx.draw(G, pos=pos)  # Draw the original graph
        >>> # Draw a subgraph, reusing the same node positions
        >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> nx.draw_circular(G)

    See Also
    --------
    :func:`~networkx.drawing.layout.circular_layout`
networkx.draw_forceatlas2
Python Library Documentation: function draw_forceatlas2 in module networkx.drawing.nx_pylab

draw_forceatlas2(G, **kwargs)
    Draw a networkx graph with forceatlas2 layout.

    This is a convenience function equivalent to::

       nx.draw(G, pos=nx.forceatlas2_layout(G), **kwargs)

    Parameters
    ----------
    G : graph
       A networkx graph

    kwargs : optional keywords
       See networkx.draw_networkx() for a description of optional keywords,
       with the exception of the pos parameter which is not used by this
       function.
networkx.draw_kamada_kawai
Python Library Documentation: function draw_kamada_kawai in module networkx.drawing.nx_pylab

draw_kamada_kawai(G, **kwargs)
    Draw the graph `G` with a Kamada-Kawai force-directed layout.

    This is a convenience function equivalent to::

        nx.draw(G, pos=nx.kamada_kawai_layout(G), **kwargs)

    Parameters
    ----------
    G : graph
        A networkx graph

    kwargs : optional keywords
        See `draw_networkx` for a description of optional keywords.

    Notes
    -----
    The layout is computed each time this function is called.
    For repeated drawing it is much more efficient to call
    `~networkx.drawing.layout.kamada_kawai_layout` directly and reuse the
    result::

        >>> G = nx.complete_graph(5)
        >>> pos = nx.kamada_kawai_layout(G)
        >>> nx.draw(G, pos=pos)  # Draw the original graph
        >>> # Draw a subgraph, reusing the same node positions
        >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> nx.draw_kamada_kawai(G)

    See Also
    --------
    :func:`~networkx.drawing.layout.kamada_kawai_layout`
networkx.draw_networkx
Python Library Documentation: function draw_networkx in module networkx.drawing.nx_pylab

draw_networkx(G, pos=None, arrows=None, with_labels=True, **kwds)
    Draw the graph G using Matplotlib.

    Draw the graph with Matplotlib with options for node positions,
    labeling, titles, and many other drawing features.
    See draw() for simple drawing without labels or axes.

    Parameters
    ----------
    G : graph
        A networkx graph

    pos : dictionary, optional
        A dictionary with nodes as keys and positions as values.
        If not specified a spring layout positioning will be computed.
        See :py:mod:`networkx.drawing.layout` for functions that
        compute node positions.

    arrows : bool or None, optional (default=None)
        If `None`, directed graphs draw arrowheads with
        `~matplotlib.patches.FancyArrowPatch`, while undirected graphs draw edges
        via `~matplotlib.collections.LineCollection` for speed.
        If `True`, draw arrowheads with FancyArrowPatches (bendable and stylish).
        If `False`, draw edges using LineCollection (linear and fast).
        For directed graphs, if True draw arrowheads.
        Note: Arrows will be the same color as edges.

    arrowstyle : str (default='-\|>' for directed graphs)
        For directed graphs, choose the style of the arrowsheads.
        For undirected graphs default to '-'

        See `matplotlib.patches.ArrowStyle` for more options.

    arrowsize : int or list (default=10)
        For directed graphs, choose the size of the arrow head's length and
        width. A list of values can be passed in to assign a different size for arrow head's length and width.
        See `matplotlib.patches.FancyArrowPatch` for attribute `mutation_scale`
        for more info.

    with_labels :  bool (default=True)
        Set to True to draw labels on the nodes.

    ax : Matplotlib Axes object, optional
        Draw the graph in the specified Matplotlib axes.

    nodelist : list (default=list(G))
        Draw only specified nodes

    edgelist : list (default=list(G.edges()))
        Draw only specified edges

    node_size : scalar or array (default=300)
        Size of nodes.  If an array is specified it must be the
        same length as nodelist.

    node_color : color or array of colors (default='#1f78b4')
        Node color. Can be a single color or a sequence of colors with the same
        length as nodelist. Color can be string or rgb (or rgba) tuple of
        floats from 0-1. If numeric values are specified they will be
        mapped to colors using the cmap and vmin,vmax parameters. See
        matplotlib.scatter for more details.

    node_shape :  string (default='o')
        The shape of the node.  Specification is as matplotlib.scatter
        marker, one of 'so^>v<dph8'.

    alpha : float or None (default=None)
        The node and edge transparency

    cmap : Matplotlib colormap, optional
        Colormap for mapping intensities of nodes

    vmin,vmax : float, optional
        Minimum and maximum for node colormap scaling

    linewidths : scalar or sequence (default=1.0)
        Line width of symbol border

    width : float or array of floats (default=1.0)
        Line width of edges

    edge_color : color or array of colors (default='k')
        Edge color. Can be a single color or a sequence of colors with the same
        length as edgelist. Color can be string or rgb (or rgba) tuple of
        floats from 0-1. If numeric values are specified they will be
        mapped to colors using the edge_cmap and edge_vmin,edge_vmax parameters.

    edge_cmap : Matplotlib colormap, optional
        Colormap for mapping intensities of edges

    edge_vmin,edge_vmax : floats, optional
        Minimum and maximum for edge colormap scaling

    style : string (default=solid line)
        Edge line style e.g.: '-', '--', '-.', ':'
        or words like 'solid' or 'dashed'.
        (See `matplotlib.patches.FancyArrowPatch`: `linestyle`)

    labels : dictionary (default=None)
        Node labels in a dictionary of text labels keyed by node

    font_size : int (default=12 for nodes, 10 for edges)
        Font size for text labels

    font_color : color (default='k' black)
        Font color string. Color can be string or rgb (or rgba) tuple of
        floats from 0-1.

    font_weight : string (default='normal')
        Font weight

    font_family : string (default='sans-serif')
        Font family

    label : string, optional
        Label for graph legend

    hide_ticks : bool, optional
        Hide ticks of axes. When `True` (the default), ticks and ticklabels
        are removed from the axes. To set ticks and tick labels to the pyplot default,
        use ``hide_ticks=False``.

    kwds : optional keywords
        See networkx.draw_networkx_nodes(), networkx.draw_networkx_edges(), and
        networkx.draw_networkx_labels() for a description of optional keywords.

    Notes
    -----
    For directed graphs, arrows  are drawn at the head end.  Arrows can be
    turned off with keyword arrows=False.

    Examples
    --------
    >>> G = nx.dodecahedral_graph()
    >>> nx.draw(G)
    >>> nx.draw(G, pos=nx.spring_layout(G))  # use spring layout

    >>> import matplotlib.pyplot as plt
    >>> limits = plt.axis("off")  # turn off axis

    Also see the NetworkX drawing examples at
    https://networkx.org/documentation/latest/auto_examples/index.html

    See Also
    --------
    draw
    draw_networkx_nodes
    draw_networkx_edges
    draw_networkx_labels
    draw_networkx_edge_labels
networkx.draw_networkx_edge_labels
Python Library Documentation: function draw_networkx_edge_labels in module networkx.drawing.nx_pylab

draw_networkx_edge_labels(G, pos, edge_labels=None, label_pos=0.5, font_size=10, font_color='k', font_family='sans-serif', font_weight='normal', alpha=None, bbox=None, horizontalalignment='center', verticalalignment='center', ax=None, rotate=True, clip_on=True, node_size=300, nodelist=None, connectionstyle='arc3', hide_ticks=True)
    Draw edge labels.

    Parameters
    ----------
    G : graph
        A networkx graph

    pos : dictionary
        A dictionary with nodes as keys and positions as values.
        Positions should be sequences of length 2.

    edge_labels : dictionary (default=None)
        Edge labels in a dictionary of labels keyed by edge two-tuple.
        Only labels for the keys in the dictionary are drawn.

    label_pos : float (default=0.5)
        Position of edge label along edge (0=head, 0.5=center, 1=tail)

    font_size : int (default=10)
        Font size for text labels

    font_color : color (default='k' black)
        Font color string. Color can be string or rgb (or rgba) tuple of
        floats from 0-1.

    font_weight : string (default='normal')
        Font weight

    font_family : string (default='sans-serif')
        Font family

    alpha : float or None (default=None)
        The text transparency

    bbox : Matplotlib bbox, optional
        Specify text box properties (e.g. shape, color etc.) for edge labels.
        Default is {boxstyle='round', ec=(1.0, 1.0, 1.0), fc=(1.0, 1.0, 1.0)}.

    horizontalalignment : string (default='center')
        Horizontal alignment {'center', 'right', 'left'}

    verticalalignment : string (default='center')
        Vertical alignment {'center', 'top', 'bottom', 'baseline', 'center_baseline'}

    ax : Matplotlib Axes object, optional
        Draw the graph in the specified Matplotlib axes.

    rotate : bool (default=True)
        Rotate edge labels to lie parallel to edges

    clip_on : bool (default=True)
        Turn on clipping of edge labels at axis boundaries

    node_size : scalar or array (default=300)
        Size of nodes.  If an array it must be the same length as nodelist.

    nodelist : list, optional (default=G.nodes())
       This provides the node order for the `node_size` array (if it is an array).

    connectionstyle : string or iterable of strings (default="arc3")
        Pass the connectionstyle parameter to create curved arc of rounding
        radius rad. For example, connectionstyle='arc3,rad=0.2'.
        See `matplotlib.patches.ConnectionStyle` and
        `matplotlib.patches.FancyArrowPatch` for more info.
        If Iterable, index indicates i'th edge key of MultiGraph

    hide_ticks : bool, optional
        Hide ticks of axes. When `True` (the default), ticks and ticklabels
        are removed from the axes. To set ticks and tick labels to the pyplot default,
        use ``hide_ticks=False``.

    Returns
    -------
    dict
        `dict` of labels keyed by edge

    Examples
    --------
    >>> G = nx.dodecahedral_graph()
    >>> edge_labels = nx.draw_networkx_edge_labels(G, pos=nx.spring_layout(G))

    Also see the NetworkX drawing examples at
    https://networkx.org/documentation/latest/auto_examples/index.html

    See Also
    --------
    draw
    draw_networkx
    draw_networkx_nodes
    draw_networkx_edges
    draw_networkx_labels
networkx.draw_networkx_edges
Python Library Documentation: function draw_networkx_edges in module networkx.drawing.nx_pylab

draw_networkx_edges(G, pos, edgelist=None, width=1.0, edge_color='k', style='solid', alpha=None, arrowstyle=None, arrowsize=10, edge_cmap=None, edge_vmin=None, edge_vmax=None, ax=None, arrows=None, label=None, node_size=300, nodelist=None, node_shape='o', connectionstyle='arc3', min_source_margin=0, min_target_margin=0, hide_ticks=True)
    Draw the edges of the graph G.

    This draws only the edges of the graph G.

    Parameters
    ----------
    G : graph
        A networkx graph

    pos : dictionary
        A dictionary with nodes as keys and positions as values.
        Positions should be sequences of length 2.

    edgelist : collection of edge tuples (default=G.edges())
        Draw only specified edges

    width : float or array of floats (default=1.0)
        Line width of edges

    edge_color : color or array of colors (default='k')
        Edge color. Can be a single color or a sequence of colors with the same
        length as edgelist. Color can be string or rgb (or rgba) tuple of
        floats from 0-1. If numeric values are specified they will be
        mapped to colors using the edge_cmap and edge_vmin,edge_vmax parameters.

    style : string or array of strings (default='solid')
        Edge line style e.g.: '-', '--', '-.', ':'
        or words like 'solid' or 'dashed'.
        Can be a single style or a sequence of styles with the same
        length as the edge list.
        If less styles than edges are given the styles will cycle.
        If more styles than edges are given the styles will be used sequentially
        and not be exhausted.
        Also, `(offset, onoffseq)` tuples can be used as style instead of a strings.
        (See `matplotlib.patches.FancyArrowPatch`: `linestyle`)

    alpha : float or array of floats (default=None)
        The edge transparency.  This can be a single alpha value,
        in which case it will be applied to all specified edges. Otherwise,
        if it is an array, the elements of alpha will be applied to the colors
        in order (cycling through alpha multiple times if necessary).

    edge_cmap : Matplotlib colormap, optional
        Colormap for mapping intensities of edges

    edge_vmin,edge_vmax : floats, optional
        Minimum and maximum for edge colormap scaling

    ax : Matplotlib Axes object, optional
        Draw the graph in the specified Matplotlib axes.

    arrows : bool or None, optional (default=None)
        If `None`, directed graphs draw arrowheads with
        `~matplotlib.patches.FancyArrowPatch`, while undirected graphs draw edges
        via `~matplotlib.collections.LineCollection` for speed.
        If `True`, draw arrowheads with FancyArrowPatches (bendable and stylish).
        If `False`, draw edges using LineCollection (linear and fast).

        Note: Arrowheads will be the same color as edges.

    arrowstyle : str or list of strs (default='-\|>' for directed graphs)
        For directed graphs and `arrows==True` defaults to '-\|>',
        For undirected graphs default to '-'.

        See `matplotlib.patches.ArrowStyle` for more options.

    arrowsize : int or list of ints(default=10)
        For directed graphs, choose the size of the arrow head's length and
        width. See `matplotlib.patches.FancyArrowPatch` for attribute
        `mutation_scale` for more info.

    connectionstyle : string or iterable of strings (default="arc3")
        Pass the connectionstyle parameter to create curved arc of rounding
        radius rad. For example, connectionstyle='arc3,rad=0.2'.
        See `matplotlib.patches.ConnectionStyle` and
        `matplotlib.patches.FancyArrowPatch` for more info.
        If Iterable, index indicates i'th edge key of MultiGraph

    node_size : scalar or array (default=300)
        Size of nodes. Though the nodes are not drawn with this function, the
        node size is used in determining edge positioning.

    nodelist : list, optional (default=G.nodes())
       This provides the node order for the `node_size` array (if it is an array).

    node_shape :  string (default='o')
        The marker used for nodes, used in determining edge positioning.
        Specification is as a `matplotlib.markers` marker, e.g. one of 'so^>v<dph8'.

    label : None or string
        Label for legend

    min_source_margin : int or list of ints (default=0)
        The minimum margin (gap) at the beginning of the edge at the source.

    min_target_margin : int or list of ints (default=0)
        The minimum margin (gap) at the end of the edge at the target.

    hide_ticks : bool, optional
        Hide ticks of axes. When `True` (the default), ticks and ticklabels
        are removed from the axes. To set ticks and tick labels to the pyplot default,
        use ``hide_ticks=False``.

    Returns
    -------
     matplotlib.collections.LineCollection or a list of matplotlib.patches.FancyArrowPatch
        If ``arrows=True``, a list of FancyArrowPatches is returned.
        If ``arrows=False``, a LineCollection is returned.
        If ``arrows=None`` (the default), then a LineCollection is returned if
        `G` is undirected, otherwise returns a list of FancyArrowPatches.

    Notes
    -----
    For directed graphs, arrows are drawn at the head end.  Arrows can be
    turned off with keyword arrows=False or by passing an arrowstyle without
    an arrow on the end.

    Be sure to include `node_size` as a keyword argument; arrows are
    drawn considering the size of nodes.

    Self-loops are always drawn with `~matplotlib.patches.FancyArrowPatch`
    regardless of the value of `arrows` or whether `G` is directed.
    When ``arrows=False`` or ``arrows=None`` and `G` is undirected, the
    FancyArrowPatches corresponding to the self-loops are not explicitly
    returned. They should instead be accessed via the ``Axes.patches``
    attribute (see examples).

    Examples
    --------
    >>> G = nx.dodecahedral_graph()
    >>> edges = nx.draw_networkx_edges(G, pos=nx.spring_layout(G))

    >>> G = nx.DiGraph()
    >>> G.add_edges_from([(1, 2), (1, 3), (2, 3)])
    >>> arcs = nx.draw_networkx_edges(G, pos=nx.spring_layout(G))
    >>> alphas = [0.3, 0.4, 0.5]
    >>> for i, arc in enumerate(arcs):  # change alpha values of arcs
    ...     arc.set_alpha(alphas[i])

    The FancyArrowPatches corresponding to self-loops are not always
    returned, but can always be accessed via the ``patches`` attribute of the
    `matplotlib.Axes` object.

    >>> import matplotlib.pyplot as plt
    >>> fig, ax = plt.subplots()
    >>> G = nx.Graph([(0, 1), (0, 0)])  # Self-loop at node 0
    >>> edge_collection = nx.draw_networkx_edges(G, pos=nx.circular_layout(G), ax=ax)
    >>> self_loop_fap = ax.patches[0]

    Also see the NetworkX drawing examples at
    https://networkx.org/documentation/latest/auto_examples/index.html

    See Also
    --------
    draw
    draw_networkx
    draw_networkx_nodes
    draw_networkx_labels
    draw_networkx_edge_labels
networkx.draw_networkx_labels
Python Library Documentation: function draw_networkx_labels in module networkx.drawing.nx_pylab

draw_networkx_labels(G, pos, labels=None, font_size=12, font_color='k', font_family='sans-serif', font_weight='normal', alpha=None, bbox=None, horizontalalignment='center', verticalalignment='center', ax=None, clip_on=True, hide_ticks=True)
    Draw node labels on the graph G.

    Parameters
    ----------
    G : graph
        A networkx graph

    pos : dictionary
        A dictionary with nodes as keys and positions as values.
        Positions should be sequences of length 2.

    labels : dictionary (default={n: n for n in G})
        Node labels in a dictionary of text labels keyed by node.
        Node-keys in labels should appear as keys in `pos`.
        If needed use: `{n:lab for n,lab in labels.items() if n in pos}`

    font_size : int or dictionary of nodes to ints (default=12)
        Font size for text labels.

    font_color : color or dictionary of nodes to colors (default='k' black)
        Font color string. Color can be string or rgb (or rgba) tuple of
        floats from 0-1.

    font_weight : string or dictionary of nodes to strings (default='normal')
        Font weight.

    font_family : string or dictionary of nodes to strings (default='sans-serif')
        Font family.

    alpha : float or None or dictionary of nodes to floats (default=None)
        The text transparency.

    bbox : Matplotlib bbox, (default is Matplotlib's ax.text default)
        Specify text box properties (e.g. shape, color etc.) for node labels.

    horizontalalignment : string or array of strings (default='center')
        Horizontal alignment {'center', 'right', 'left'}. If an array is
        specified it must be the same length as `nodelist`.

    verticalalignment : string (default='center')
        Vertical alignment {'center', 'top', 'bottom', 'baseline', 'center_baseline'}.
        If an array is specified it must be the same length as `nodelist`.

    ax : Matplotlib Axes object, optional
        Draw the graph in the specified Matplotlib axes.

    clip_on : bool (default=True)
        Turn on clipping of node labels at axis boundaries

    hide_ticks : bool, optional
        Hide ticks of axes. When `True` (the default), ticks and ticklabels
        are removed from the axes. To set ticks and tick labels to the pyplot default,
        use ``hide_ticks=False``.

    Returns
    -------
    dict
        `dict` of labels keyed on the nodes

    Examples
    --------
    >>> G = nx.dodecahedral_graph()
    >>> labels = nx.draw_networkx_labels(G, pos=nx.spring_layout(G))

    Also see the NetworkX drawing examples at
    https://networkx.org/documentation/latest/auto_examples/index.html

    See Also
    --------
    draw
    draw_networkx
    draw_networkx_nodes
    draw_networkx_edges
    draw_networkx_edge_labels
networkx.draw_networkx_nodes
Python Library Documentation: function draw_networkx_nodes in module networkx.drawing.nx_pylab

draw_networkx_nodes(G, pos, nodelist=None, node_size=300, node_color='#1f78b4', node_shape='o', alpha=None, cmap=None, vmin=None, vmax=None, ax=None, linewidths=None, edgecolors=None, label=None, margins=None, hide_ticks=True)
    Draw the nodes of the graph G.

    This draws only the nodes of the graph G.

    Parameters
    ----------
    G : graph
        A networkx graph

    pos : dictionary
        A dictionary with nodes as keys and positions as values.
        Positions should be sequences of length 2.

    ax : Matplotlib Axes object, optional
        Draw the graph in the specified Matplotlib axes.

    nodelist : list (default list(G))
        Draw only specified nodes

    node_size : scalar or array (default=300)
        Size of nodes.  If an array it must be the same length as nodelist.

    node_color : color or array of colors (default='#1f78b4')
        Node color. Can be a single color or a sequence of colors with the same
        length as nodelist. Color can be string or rgb (or rgba) tuple of
        floats from 0-1. If numeric values are specified they will be
        mapped to colors using the cmap and vmin,vmax parameters. See
        matplotlib.scatter for more details.

    node_shape :  string (default='o')
        The shape of the node.  Specification is as matplotlib.scatter
        marker, one of 'so^>v<dph8'.

    alpha : float or array of floats (default=None)
        The node transparency.  This can be a single alpha value,
        in which case it will be applied to all the nodes of color. Otherwise,
        if it is an array, the elements of alpha will be applied to the colors
        in order (cycling through alpha multiple times if necessary).

    cmap : Matplotlib colormap (default=None)
        Colormap for mapping intensities of nodes

    vmin,vmax : floats or None (default=None)
        Minimum and maximum for node colormap scaling

    linewidths : [None | scalar | sequence] (default=1.0)
        Line width of symbol border

    edgecolors : [None | scalar | sequence] (default = node_color)
        Colors of node borders. Can be a single color or a sequence of colors with the
        same length as nodelist. Color can be string or rgb (or rgba) tuple of floats
        from 0-1. If numeric values are specified they will be mapped to colors
        using the cmap and vmin,vmax parameters. See `~matplotlib.pyplot.scatter` for more details.

    label : [None | string]
        Label for legend

    margins : float or 2-tuple, optional
        Sets the padding for axis autoscaling. Increase margin to prevent
        clipping for nodes that are near the edges of an image. Values should
        be in the range ``[0, 1]``. See :meth:`matplotlib.axes.Axes.margins`
        for details. The default is `None`, which uses the Matplotlib default.

    hide_ticks : bool, optional
        Hide ticks of axes. When `True` (the default), ticks and ticklabels
        are removed from the axes. To set ticks and tick labels to the pyplot default,
        use ``hide_ticks=False``.

    Returns
    -------
    matplotlib.collections.PathCollection
        `PathCollection` of the nodes.

    Examples
    --------
    >>> G = nx.dodecahedral_graph()
    >>> nodes = nx.draw_networkx_nodes(G, pos=nx.spring_layout(G))

    Also see the NetworkX drawing examples at
    https://networkx.org/documentation/latest/auto_examples/index.html

    See Also
    --------
    draw
    draw_networkx
    draw_networkx_edges
    draw_networkx_labels
    draw_networkx_edge_labels
networkx.draw_planar
Python Library Documentation: function draw_planar in module networkx.drawing.nx_pylab

draw_planar(G, **kwargs)
    Draw a planar networkx graph `G` with planar layout.

    This is a convenience function equivalent to::

        nx.draw(G, pos=nx.planar_layout(G), **kwargs)

    Parameters
    ----------
    G : graph
        A planar networkx graph

    kwargs : optional keywords
        See `draw_networkx` for a description of optional keywords.

    Raises
    ------
    NetworkXException
        When `G` is not planar

    Notes
    -----
    The layout is computed each time this function is called.
    For repeated drawing it is much more efficient to call
    `~networkx.drawing.layout.planar_layout` directly and reuse the result::

        >>> G = nx.path_graph(5)
        >>> pos = nx.planar_layout(G)
        >>> nx.draw(G, pos=pos)  # Draw the original graph
        >>> # Draw a subgraph, reusing the same node positions
        >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.draw_planar(G)

    See Also
    --------
    :func:`~networkx.drawing.layout.planar_layout`
networkx.draw_random
Python Library Documentation: function draw_random in module networkx.drawing.nx_pylab

draw_random(G, **kwargs)
    Draw the graph `G` with a random layout.

    This is a convenience function equivalent to::

        nx.draw(G, pos=nx.random_layout(G), **kwargs)

    Parameters
    ----------
    G : graph
        A networkx graph

    kwargs : optional keywords
        See `draw_networkx` for a description of optional keywords.

    Notes
    -----
    The layout is computed each time this function is called.
    For repeated drawing it is much more efficient to call
    `~networkx.drawing.layout.random_layout` directly and reuse the result::

        >>> G = nx.complete_graph(5)
        >>> pos = nx.random_layout(G)
        >>> nx.draw(G, pos=pos)  # Draw the original graph
        >>> # Draw a subgraph, reusing the same node positions
        >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

    Examples
    --------
    >>> G = nx.lollipop_graph(4, 3)
    >>> nx.draw_random(G)

    See Also
    --------
    :func:`~networkx.drawing.layout.random_layout`
networkx.draw_shell
Python Library Documentation: function draw_shell in module networkx.drawing.nx_pylab

draw_shell(G, nlist=None, **kwargs)
    Draw networkx graph `G` with shell layout.

    This is a convenience function equivalent to::

        nx.draw(G, pos=nx.shell_layout(G, nlist=nlist), **kwargs)

    Parameters
    ----------
    G : graph
        A networkx graph

    nlist : list of list of nodes, optional
        A list containing lists of nodes representing the shells.
        Default is `None`, meaning all nodes are in a single shell.
        See `~networkx.drawing.layout.shell_layout` for details.

    kwargs : optional keywords
        See `draw_networkx` for a description of optional keywords.

    Notes
    -----
    The layout is computed each time this function is called.
    For repeated drawing it is much more efficient to call
    `~networkx.drawing.layout.shell_layout` directly and reuse the result::

        >>> G = nx.complete_graph(5)
        >>> pos = nx.shell_layout(G)
        >>> nx.draw(G, pos=pos)  # Draw the original graph
        >>> # Draw a subgraph, reusing the same node positions
        >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> shells = [[0], [1, 2, 3]]
    >>> nx.draw_shell(G, nlist=shells)

    See Also
    --------
    :func:`~networkx.drawing.layout.shell_layout`
networkx.draw_spectral
Python Library Documentation: function draw_spectral in module networkx.drawing.nx_pylab

draw_spectral(G, **kwargs)
    Draw the graph `G` with a spectral 2D layout.

    This is a convenience function equivalent to::

        nx.draw(G, pos=nx.spectral_layout(G), **kwargs)

    For more information about how node positions are determined, see
    `~networkx.drawing.layout.spectral_layout`.

    Parameters
    ----------
    G : graph
        A networkx graph

    kwargs : optional keywords
        See `draw_networkx` for a description of optional keywords.

    Notes
    -----
    The layout is computed each time this function is called.
    For repeated drawing it is much more efficient to call
    `~networkx.drawing.layout.spectral_layout` directly and reuse the result::

        >>> G = nx.complete_graph(5)
        >>> pos = nx.spectral_layout(G)
        >>> nx.draw(G, pos=pos)  # Draw the original graph
        >>> # Draw a subgraph, reusing the same node positions
        >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> nx.draw_spectral(G)

    See Also
    --------
    :func:`~networkx.drawing.layout.spectral_layout`
networkx.draw_spring
Python Library Documentation: function draw_spring in module networkx.drawing.nx_pylab

draw_spring(G, **kwargs)
    Draw the graph `G` with a spring layout.

    This is a convenience function equivalent to::

        nx.draw(G, pos=nx.spring_layout(G), **kwargs)

    Parameters
    ----------
    G : graph
        A networkx graph

    kwargs : optional keywords
        See `draw_networkx` for a description of optional keywords.

    Notes
    -----
    `~networkx.drawing.layout.spring_layout` is also the default layout for
    `draw`, so this function is equivalent to `draw`.

    The layout is computed each time this function is called.
    For repeated drawing it is much more efficient to call
    `~networkx.drawing.layout.spring_layout` directly and reuse the result::

        >>> G = nx.complete_graph(5)
        >>> pos = nx.spring_layout(G)
        >>> nx.draw(G, pos=pos)  # Draw the original graph
        >>> # Draw a subgraph, reusing the same node positions
        >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

    Examples
    --------
    >>> G = nx.path_graph(20)
    >>> nx.draw_spring(G)

    See Also
    --------
    draw
    :func:`~networkx.drawing.layout.spring_layout`
networkx.drawing
Python Library Documentation: package networkx.drawing in networkx

NAME
    networkx.drawing - # graph drawing and interface to graphviz

PACKAGE CONTENTS
    layout
    nx_agraph
    nx_latex
    nx_pydot
    nx_pylab
    tests (package)

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\drawing\__init__.py

networkx.dual_barabasi_albert_graph
Python Library Documentation: function dual_barabasi_albert_graph in module networkx.generators.random_graphs

dual_barabasi_albert_graph(n, m1, m2, p, seed=None, initial_graph=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns a random graph using dual Barabási–Albert preferential attachment

    A graph of $n$ nodes is grown by attaching new nodes each with either $m_1$
    edges (with probability $p$) or $m_2$ edges (with probability $1-p$) that
    are preferentially attached to existing nodes with high degree.

    Parameters
    ----------
    n : int
        Number of nodes
    m1 : int
        Number of edges to link each new node to existing nodes with probability $p$
    m2 : int
        Number of edges to link each new node to existing nodes with probability $1-p$
    p : float
        The probability of attaching $m_1$ edges (as opposed to $m_2$ edges)
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    initial_graph : Graph or None (default)
        Initial network for Barabási–Albert algorithm.
        A copy of `initial_graph` is used.
        It should be connected for most use cases.
        If None, starts from an star graph on max(m1, m2) + 1 nodes.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Returns
    -------
    G : Graph

    Raises
    ------
    NetworkXError
        If `m1` and `m2` do not satisfy ``1 <= m1,m2 < n``, or
        `p` does not satisfy ``0 <= p <= 1``, or
        the initial graph number of nodes m0 does not satisfy m1, m2 <= m0 <= n.

    References
    ----------
    .. [1] N. Moshiri "The dual-Barabasi-Albert model", arXiv:1810.10538.
networkx.duplication
Python Library Documentation: module networkx.generators.duplication in networkx.generators

NAME
    networkx.generators.duplication - Functions for generating graphs based on the "duplication" method.

DESCRIPTION
    These graph generators start with a small initial graph then duplicate
    nodes and (partially) duplicate their edges. These functions are
    generally inspired by biological networks.

FUNCTIONS
    duplication_divergence_graph(n, p, seed=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns an undirected graph using the duplication-divergence model.

        A graph of `n` nodes is created by duplicating the initial nodes
        and retaining edges incident to the original nodes with a retention
        probability `p`.

        Parameters
        ----------
        n : int
            The desired number of nodes in the graph.
        p : float
            The probability for retaining the edge of the replicated node.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Returns
        -------
        G : Graph

        Raises
        ------
        NetworkXError
            If `p` is not a valid probability.
            If `n` is less than 2.

        Notes
        -----
        This algorithm appears in [1].

        This implementation disallows the possibility of generating
        disconnected graphs.

        References
        ----------
        .. [1] I. Ispolatov, P. L. Krapivsky, A. Yuryev,
           "Duplication-divergence model of protein interaction network",
           Phys. Rev. E, 71, 061911, 2005.

    partial_duplication_graph(N, n, p, q, seed=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns a random graph using the partial duplication model.

        Parameters
        ----------
        N : int
            The total number of nodes in the final graph.

        n : int
            The number of nodes in the initial clique.

        p : float
            The probability of joining each neighbor of a node to the
            duplicate node. Must be a number in the between zero and one,
            inclusive.

        q : float
            The probability of joining the source node to the duplicate
            node. Must be a number in the between zero and one, inclusive.

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Notes
        -----
        A graph of nodes is grown by creating a fully connected graph
        of size `n`. The following procedure is then repeated until
        a total of `N` nodes have been reached.

        1. A random node, *u*, is picked and a new node, *v*, is created.
        2. For each neighbor of *u* an edge from the neighbor to *v* is created
           with probability `p`.
        3. An edge from *u* to *v* is created with probability `q`.

        This algorithm appears in [1].

        This implementation allows the possibility of generating
        disconnected graphs.

        References
        ----------
        .. [1] Knudsen Michael, and Carsten Wiuf. "A Markov chain approach to
               randomly grown graphs." Journal of Applied Mathematics 2008.
               <https://doi.org/10.1155/2008/190836>

DATA
    __all__ = ['partial_duplication_graph', 'duplication_divergence_graph'...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\duplication.py

networkx.duplication_divergence_graph
Python Library Documentation: function duplication_divergence_graph in module networkx.generators.duplication

duplication_divergence_graph(n, p, seed=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns an undirected graph using the duplication-divergence model.

    A graph of `n` nodes is created by duplicating the initial nodes
    and retaining edges incident to the original nodes with a retention
    probability `p`.

    Parameters
    ----------
    n : int
        The desired number of nodes in the graph.
    p : float
        The probability for retaining the edge of the replicated node.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Returns
    -------
    G : Graph

    Raises
    ------
    NetworkXError
        If `p` is not a valid probability.
        If `n` is less than 2.

    Notes
    -----
    This algorithm appears in [1].

    This implementation disallows the possibility of generating
    disconnected graphs.

    References
    ----------
    .. [1] I. Ispolatov, P. L. Krapivsky, A. Yuryev,
       "Duplication-divergence model of protein interaction network",
       Phys. Rev. E, 71, 061911, 2005.
networkx.eccentricity
Python Library Documentation: function eccentricity in module networkx.algorithms.distance_measures

eccentricity(G, v=None, sp=None, weight=None, *, backend=None, **backend_kwargs)
    Returns the eccentricity of nodes in G.

    The eccentricity of a node v is the maximum distance from v to
    all other nodes in G.

    Parameters
    ----------
    G : NetworkX graph
       A graph

    v : node, optional
       Return value of specified node

    sp : dict of dicts, optional
       All pairs shortest path lengths as a dictionary of dictionaries

    weight : string, function, or None (default=None)
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

        If this is None, every edge has weight/distance/cost 1.

        Weights stored as floating point values can lead to small round-off
        errors in distances. Use integer weights to avoid this.

        Weights should be positive, since they are distances.

    Returns
    -------
    ecc : dictionary
       A dictionary of eccentricity values keyed by node.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
    >>> dict(nx.eccentricity(G))
    {1: 2, 2: 3, 3: 2, 4: 2, 5: 3}

    >>> dict(
    ...     nx.eccentricity(G, v=[1, 5])
    ... )  # This returns the eccentricity of node 1 & 5
    {1: 2, 5: 3}
networkx.edge_betweenness_centrality
Python Library Documentation: function edge_betweenness_centrality in module networkx.algorithms.centrality.betweenness

edge_betweenness_centrality(G, k=None, normalized=True, weight=None, seed=None, *, backend=None, **backend_kwargs)
    Compute betweenness centrality for edges.

    Betweenness centrality of an edge $e$ is the sum of the
    fraction of all-pairs shortest paths that pass through $e$

    .. math::

       c_B(e) =\sum_{s,t \in V} \frac{\sigma(s, t|e)}{\sigma(s, t)}

    where $V$ is the set of nodes, $\sigma(s, t)$ is the number of
    shortest $(s, t)$-paths, and $\sigma(s, t|e)$ is the number of
    those paths passing through edge $e$ [2]_.

    Parameters
    ----------
    G : graph
      A NetworkX graph.

    k : int, optional (default=None)
      If k is not None use k node samples to estimate betweenness.
      The value of k <= n where n is the number of nodes in the graph.
      Higher values give better approximation.

    normalized : bool, optional
      If True the betweenness values are normalized by $2/(n(n-1))$
      for graphs, and $1/(n(n-1))$ for directed graphs where $n$
      is the number of nodes in G.

    weight : None or string, optional (default=None)
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.
      Weights are used to calculate weighted shortest paths, so they are
      interpreted as distances.

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
        Note that this is only used if k is not None.

    Returns
    -------
    edges : dictionary
       Dictionary of edges with betweenness centrality as the value.

    See Also
    --------
    betweenness_centrality
    edge_load

    Notes
    -----
    The algorithm is from Ulrik Brandes [1]_.

    For weighted graphs the edge weights must be greater than zero.
    Zero edge weights can produce an infinite number of equal length
    paths between pairs of nodes.

    References
    ----------
    .. [1]  A Faster Algorithm for Betweenness Centrality. Ulrik Brandes,
       Journal of Mathematical Sociology 25(2):163-177, 2001.
       https://doi.org/10.1080/0022250X.2001.9990249
    .. [2] Ulrik Brandes: On Variants of Shortest-Path Betweenness
       Centrality and their Generic Computation.
       Social Networks 30(2):136-145, 2008.
       https://doi.org/10.1016/j.socnet.2007.11.001
networkx.edge_betweenness_centrality_subset
Python Library Documentation: function edge_betweenness_centrality_subset in module networkx.algorithms.centrality.betweenness_subset

edge_betweenness_centrality_subset(G, sources, targets, normalized=False, weight=None, *, backend=None, **backend_kwargs)
    Compute betweenness centrality for edges for a subset of nodes.

    .. math::

       c_B(v) =\sum_{s\in S,t \in T} \frac{\sigma(s, t|e)}{\sigma(s, t)}

    where $S$ is the set of sources, $T$ is the set of targets,
    $\sigma(s, t)$ is the number of shortest $(s, t)$-paths,
    and $\sigma(s, t|e)$ is the number of those paths
    passing through edge $e$ [2]_.

    Parameters
    ----------
    G : graph
      A networkx graph.

    sources: list of nodes
      Nodes to use as sources for shortest paths in betweenness

    targets: list of nodes
      Nodes to use as targets for shortest paths in betweenness

    normalized : bool, optional
      If True the betweenness values are normalized by `2/(n(n-1))`
      for graphs, and `1/(n(n-1))` for directed graphs where `n`
      is the number of nodes in G.

    weight : None or string, optional (default=None)
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.
      Weights are used to calculate weighted shortest paths, so they are
      interpreted as distances.

    Returns
    -------
    edges : dictionary
       Dictionary of edges with Betweenness centrality as the value.

    See Also
    --------
    betweenness_centrality
    edge_load

    Notes
    -----
    The basic algorithm is from [1]_.

    For weighted graphs the edge weights must be greater than zero.
    Zero edge weights can produce an infinite number of equal length
    paths between pairs of nodes.

    The normalization might seem a little strange but it is the same
    as in edge_betweenness_centrality() and is designed to make
    edge_betweenness_centrality(G) be the same as
    edge_betweenness_centrality_subset(G,sources=G.nodes(),targets=G.nodes()).

    References
    ----------
    .. [1] Ulrik Brandes, A Faster Algorithm for Betweenness Centrality.
       Journal of Mathematical Sociology 25(2):163-177, 2001.
       https://doi.org/10.1080/0022250X.2001.9990249
    .. [2] Ulrik Brandes: On Variants of Shortest-Path Betweenness
       Centrality and their Generic Computation.
       Social Networks 30(2):136-145, 2008.
       https://doi.org/10.1016/j.socnet.2007.11.001
networkx.edge_bfs
Python Library Documentation: function edge_bfs in module networkx.algorithms.traversal.edgebfs

edge_bfs(G, source=None, orientation=None, *, backend=None, **backend_kwargs)
    A directed, breadth-first-search of edges in `G`, beginning at `source`.

    Yield the edges of G in a breadth-first-search order continuing until
    all edges are generated.

    Parameters
    ----------
    G : graph
        A directed/undirected graph/multigraph.

    source : node, list of nodes
        The node from which the traversal begins. If None, then a source
        is chosen arbitrarily and repeatedly until all edges from each node in
        the graph are searched.

    orientation : None | 'original' | 'reverse' | 'ignore' (default: None)
        For directed graphs and directed multigraphs, edge traversals need not
        respect the original orientation of the edges.
        When set to 'reverse' every edge is traversed in the reverse direction.
        When set to 'ignore', every edge is treated as undirected.
        When set to 'original', every edge is treated as directed.
        In all three cases, the yielded edge tuples add a last entry to
        indicate the direction in which that edge was traversed.
        If orientation is None, the yielded edge has no direction indicated.
        The direction is respected, but not reported.

    Yields
    ------
    edge : directed edge
        A directed edge indicating the path taken by the breadth-first-search.
        For graphs, `edge` is of the form `(u, v)` where `u` and `v`
        are the tail and head of the edge as determined by the traversal.
        For multigraphs, `edge` is of the form `(u, v, key)`, where `key` is
        the key of the edge. When the graph is directed, then `u` and `v`
        are always in the order of the actual directed edge.
        If orientation is not None then the edge tuple is extended to include
        the direction of traversal ('forward' or 'reverse') on that edge.

    Examples
    --------
    >>> nodes = [0, 1, 2, 3]
    >>> edges = [(0, 1), (1, 0), (1, 0), (2, 0), (2, 1), (3, 1)]

    >>> list(nx.edge_bfs(nx.Graph(edges), nodes))
    [(0, 1), (0, 2), (1, 2), (1, 3)]

    >>> list(nx.edge_bfs(nx.DiGraph(edges), nodes))
    [(0, 1), (1, 0), (2, 0), (2, 1), (3, 1)]

    >>> list(nx.edge_bfs(nx.MultiGraph(edges), nodes))
    [(0, 1, 0), (0, 1, 1), (0, 1, 2), (0, 2, 0), (1, 2, 0), (1, 3, 0)]

    >>> list(nx.edge_bfs(nx.MultiDiGraph(edges), nodes))
    [(0, 1, 0), (1, 0, 0), (1, 0, 1), (2, 0, 0), (2, 1, 0), (3, 1, 0)]

    >>> list(nx.edge_bfs(nx.DiGraph(edges), nodes, orientation="ignore"))
    [(0, 1, 'forward'), (1, 0, 'reverse'), (2, 0, 'reverse'), (2, 1, 'reverse'), (3, 1, 'reverse')]

    >>> list(nx.edge_bfs(nx.MultiDiGraph(edges), nodes, orientation="ignore"))
    [(0, 1, 0, 'forward'), (1, 0, 0, 'reverse'), (1, 0, 1, 'reverse'), (2, 0, 0, 'reverse'), (2, 1, 0, 'reverse'), (3, 1, 0, 'reverse')]

    Notes
    -----
    The goal of this function is to visit edges. It differs from the more
    familiar breadth-first-search of nodes, as provided by
    :func:`networkx.algorithms.traversal.breadth_first_search.bfs_edges`, in
    that it does not stop once every node has been visited. In a directed graph
    with edges [(0, 1), (1, 2), (2, 1)], the edge (2, 1) would not be visited
    if not for the functionality provided by this function.

    The naming of this function is very similar to bfs_edges. The difference
    is that 'edge_bfs' yields edges even if they extend back to an already
    explored node while 'bfs_edges' yields the edges of the tree that results
    from a breadth-first-search (BFS) so no edges are reported if they extend
    to already explored nodes. That means 'edge_bfs' reports all edges while
    'bfs_edges' only report those traversed by a node-based BFS. Yet another
    description is that 'bfs_edges' reports the edges traversed during BFS
    while 'edge_bfs' reports all edges in the order they are explored.

    See Also
    --------
    bfs_edges
    bfs_tree
    edge_dfs
networkx.edge_boundary
Python Library Documentation: function edge_boundary in module networkx.algorithms.boundary

edge_boundary(G, nbunch1, nbunch2=None, data=False, keys=False, default=None, *, backend=None, **backend_kwargs)
    Returns the edge boundary of `nbunch1`.

    The *edge boundary* of a set *S* with respect to a set *T* is the
    set of edges (*u*, *v*) such that *u* is in *S* and *v* is in *T*.
    If *T* is not specified, it is assumed to be the set of all nodes
    not in *S*.

    Parameters
    ----------
    G : NetworkX graph

    nbunch1 : iterable
        Iterable of nodes in the graph representing the set of nodes
        whose edge boundary will be returned. (This is the set *S* from
        the definition above.)

    nbunch2 : iterable
        Iterable of nodes representing the target (or "exterior") set of
        nodes. (This is the set *T* from the definition above.) If not
        specified, this is assumed to be the set of all nodes in `G`
        not in `nbunch1`.

    keys : bool
        This parameter has the same meaning as in
        :meth:`MultiGraph.edges`.

    data : bool or object
        This parameter has the same meaning as in
        :meth:`MultiGraph.edges`.

    default : object
        This parameter has the same meaning as in
        :meth:`MultiGraph.edges`.

    Returns
    -------
    iterator
        An iterator over the edges in the boundary of `nbunch1` with
        respect to `nbunch2`. If `keys`, `data`, or `default`
        are specified and `G` is a multigraph, then edges are returned
        with keys and/or data, as in :meth:`MultiGraph.edges`.

    Examples
    --------
    >>> G = nx.wheel_graph(6)

    When nbunch2=None:

    >>> list(nx.edge_boundary(G, (1, 3)))
    [(1, 0), (1, 2), (1, 5), (3, 0), (3, 2), (3, 4)]

    When nbunch2 is given:

    >>> list(nx.edge_boundary(G, (1, 3), (2, 0)))
    [(1, 0), (1, 2), (3, 0), (3, 2)]

    Notes
    -----
    Any element of `nbunch` that is not in the graph `G` will be
    ignored.

    `nbunch1` and `nbunch2` are usually meant to be disjoint, but in
    the interest of speed and generality, that is not required here.
networkx.edge_connectivity
Python Library Documentation: function edge_connectivity in module networkx.algorithms.connectivity.connectivity

edge_connectivity(G, s=None, t=None, flow_func=None, cutoff=None, *, backend=None, **backend_kwargs)
    Returns the edge connectivity of the graph or digraph G.

    The edge connectivity is equal to the minimum number of edges that
    must be removed to disconnect G or render it trivial. If source
    and target nodes are provided, this function returns the local edge
    connectivity: the minimum number of edges that must be removed to
    break all paths from source to target in G.

    Parameters
    ----------
    G : NetworkX graph
        Undirected or directed graph

    s : node
        Source node. Optional. Default value: None.

    t : node
        Target node. Optional. Default value: None.

    flow_func : function
        A function for computing the maximum flow among a pair of nodes.
        The function has to accept at least three parameters: a Digraph,
        a source node, and a target node. And return a residual network
        that follows NetworkX conventions (see :meth:`maximum_flow` for
        details). If flow_func is None, the default maximum flow function
        (:meth:`edmonds_karp`) is used. See below for details. The
        choice of the default function may change from version
        to version and should not be relied on. Default value: None.

    cutoff : integer, float, or None (default: None)
        If specified, the maximum flow algorithm will terminate when the
        flow value reaches or exceeds the cutoff. This only works for flows
        that support the cutoff parameter (most do) and is ignored otherwise.

    Returns
    -------
    K : integer
        Edge connectivity for G, or local edge connectivity if source
        and target were provided

    Examples
    --------
    >>> # Platonic icosahedral graph is 5-edge-connected
    >>> G = nx.icosahedral_graph()
    >>> nx.edge_connectivity(G)
    5

    You can use alternative flow algorithms for the underlying
    maximum flow computation. In dense networks the algorithm
    :meth:`shortest_augmenting_path` will usually perform better
    than the default :meth:`edmonds_karp`, which is faster for
    sparse networks with highly skewed degree distributions.
    Alternative flow functions have to be explicitly imported
    from the flow package.

    >>> from networkx.algorithms.flow import shortest_augmenting_path
    >>> nx.edge_connectivity(G, flow_func=shortest_augmenting_path)
    5

    If you specify a pair of nodes (source and target) as parameters,
    this function returns the value of local edge connectivity.

    >>> nx.edge_connectivity(G, 3, 7)
    5

    If you need to perform several local computations among different
    pairs of nodes on the same graph, it is recommended that you reuse
    the data structures used in the maximum flow computations. See
    :meth:`local_edge_connectivity` for details.

    Notes
    -----
    This is a flow based implementation of global edge connectivity.
    For undirected graphs the algorithm works by finding a 'small'
    dominating set of nodes of G (see algorithm 7 in [1]_ ) and
    computing local maximum flow (see :meth:`local_edge_connectivity`)
    between an arbitrary node in the dominating set and the rest of
    nodes in it. This is an implementation of algorithm 6 in [1]_ .
    For directed graphs, the algorithm does n calls to the maximum
    flow function. This is an implementation of algorithm 8 in [1]_ .

    See also
    --------
    :meth:`local_edge_connectivity`
    :meth:`local_node_connectivity`
    :meth:`node_connectivity`
    :meth:`maximum_flow`
    :meth:`edmonds_karp`
    :meth:`preflow_push`
    :meth:`shortest_augmenting_path`
    :meth:`k_edge_components`
    :meth:`k_edge_subgraphs`

    References
    ----------
    .. [1] Abdol-Hossein Esfahanian. Connectivity Algorithms.
        http://www.cse.msu.edu/~cse835/Papers/Graph_connectivity_revised.pdf
networkx.edge_current_flow_betweenness_centrality
Python Library Documentation: function edge_current_flow_betweenness_centrality in module networkx.algorithms.centrality.current_flow_betweenness

edge_current_flow_betweenness_centrality(G, normalized=True, weight=None, dtype=<class 'float'>, solver='full', *, backend=None, **backend_kwargs)
    Compute current-flow betweenness centrality for edges.

    Current-flow betweenness centrality uses an electrical current
    model for information spreading in contrast to betweenness
    centrality which uses shortest paths.

    Current-flow betweenness centrality is also known as
    random-walk betweenness centrality [2]_.

    Parameters
    ----------
    G : graph
      A NetworkX graph

    normalized : bool, optional (default=True)
      If True the betweenness values are normalized by 2/[(n-1)(n-2)] where
      n is the number of nodes in G.

    weight : string or None, optional (default=None)
      Key for edge data used as the edge weight.
      If None, then use 1 as each edge weight.
      The weight reflects the capacity or the strength of the
      edge.

    dtype : data type (default=float)
      Default data type for internal matrices.
      Set to np.float32 for lower memory consumption.

    solver : string (default='full')
       Type of linear solver to use for computing the flow matrix.
       Options are "full" (uses most memory), "lu" (recommended), and
       "cg" (uses least memory).

    Returns
    -------
    nodes : dictionary
       Dictionary of edge tuples with betweenness centrality as the value.

    Raises
    ------
    NetworkXError
        The algorithm does not support DiGraphs.
        If the input graph is an instance of DiGraph class, NetworkXError
        is raised.

    See Also
    --------
    betweenness_centrality
    edge_betweenness_centrality
    current_flow_betweenness_centrality

    Notes
    -----
    Current-flow betweenness can be computed in $O(I(n-1)+mn \log n)$
    time [1]_, where $I(n-1)$ is the time needed to compute the
    inverse Laplacian.  For a full matrix this is $O(n^3)$ but using
    sparse methods you can achieve $O(nm{\sqrt k})$ where $k$ is the
    Laplacian matrix condition number.

    The space required is $O(nw)$ where $w$ is the width of the sparse
    Laplacian matrix.  Worse case is $w=n$ for $O(n^2)$.

    If the edges have a 'weight' attribute they will be used as
    weights in this algorithm.  Unspecified weights are set to 1.

    References
    ----------
    .. [1] Centrality Measures Based on Current Flow.
       Ulrik Brandes and Daniel Fleischer,
       Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
       LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
       https://doi.org/10.1007/978-3-540-31856-9_44

    .. [2] A measure of betweenness centrality based on random walks,
       M. E. J. Newman, Social Networks 27, 39-54 (2005).
networkx.edge_current_flow_betweenness_centrality_subset
Python Library Documentation: function edge_current_flow_betweenness_centrality_subset in module networkx.algorithms.centrality.current_flow_betweenness_subset

edge_current_flow_betweenness_centrality_subset(G, sources, targets, normalized=True, weight=None, dtype=<class 'float'>, solver='lu', *, backend=None, **backend_kwargs)
    Compute current-flow betweenness centrality for edges using subsets
    of nodes.

    Current-flow betweenness centrality uses an electrical current
    model for information spreading in contrast to betweenness
    centrality which uses shortest paths.

    Current-flow betweenness centrality is also known as
    random-walk betweenness centrality [2]_.

    Parameters
    ----------
    G : graph
      A NetworkX graph

    sources: list of nodes
      Nodes to use as sources for current

    targets: list of nodes
      Nodes to use as sinks for current

    normalized : bool, optional (default=True)
      If True the betweenness values are normalized by b=b/(n-1)(n-2) where
      n is the number of nodes in G.

    weight : string or None, optional (default=None)
      Key for edge data used as the edge weight.
      If None, then use 1 as each edge weight.
      The weight reflects the capacity or the strength of the
      edge.

    dtype: data type (float)
      Default data type for internal matrices.
      Set to np.float32 for lower memory consumption.

    solver: string (default='lu')
       Type of linear solver to use for computing the flow matrix.
       Options are "full" (uses most memory), "lu" (recommended), and
       "cg" (uses least memory).

    Returns
    -------
    nodes : dict
       Dictionary of edge tuples with betweenness centrality as the value.

    See Also
    --------
    betweenness_centrality
    edge_betweenness_centrality
    current_flow_betweenness_centrality

    Notes
    -----
    Current-flow betweenness can be computed in $O(I(n-1)+mn \log n)$
    time [1]_, where $I(n-1)$ is the time needed to compute the
    inverse Laplacian.  For a full matrix this is $O(n^3)$ but using
    sparse methods you can achieve $O(nm{\sqrt k})$ where $k$ is the
    Laplacian matrix condition number.

    The space required is $O(nw)$ where $w$ is the width of the sparse
    Laplacian matrix.  Worse case is $w=n$ for $O(n^2)$.

    If the edges have a 'weight' attribute they will be used as
    weights in this algorithm.  Unspecified weights are set to 1.

    References
    ----------
    .. [1] Centrality Measures Based on Current Flow.
       Ulrik Brandes and Daniel Fleischer,
       Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
       LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
       https://doi.org/10.1007/978-3-540-31856-9_44

    .. [2] A measure of betweenness centrality based on random walks,
       M. E. J. Newman, Social Networks 27, 39-54 (2005).
networkx.edge_dfs
Python Library Documentation: function edge_dfs in module networkx.algorithms.traversal.edgedfs

edge_dfs(G, source=None, orientation=None, *, backend=None, **backend_kwargs)
    A directed, depth-first-search of edges in `G`, beginning at `source`.

    Yield the edges of G in a depth-first-search order continuing until
    all edges are generated.

    Parameters
    ----------
    G : graph
        A directed/undirected graph/multigraph.

    source : node, list of nodes
        The node from which the traversal begins. If None, then a source
        is chosen arbitrarily and repeatedly until all edges from each node in
        the graph are searched.

    orientation : None | 'original' | 'reverse' | 'ignore' (default: None)
        For directed graphs and directed multigraphs, edge traversals need not
        respect the original orientation of the edges.
        When set to 'reverse' every edge is traversed in the reverse direction.
        When set to 'ignore', every edge is treated as undirected.
        When set to 'original', every edge is treated as directed.
        In all three cases, the yielded edge tuples add a last entry to
        indicate the direction in which that edge was traversed.
        If orientation is None, the yielded edge has no direction indicated.
        The direction is respected, but not reported.

    Yields
    ------
    edge : directed edge
        A directed edge indicating the path taken by the depth-first traversal.
        For graphs, `edge` is of the form `(u, v)` where `u` and `v`
        are the tail and head of the edge as determined by the traversal.
        For multigraphs, `edge` is of the form `(u, v, key)`, where `key` is
        the key of the edge. When the graph is directed, then `u` and `v`
        are always in the order of the actual directed edge.
        If orientation is not None then the edge tuple is extended to include
        the direction of traversal ('forward' or 'reverse') on that edge.

    Examples
    --------
    >>> nodes = [0, 1, 2, 3]
    >>> edges = [(0, 1), (1, 0), (1, 0), (2, 1), (3, 1)]

    >>> list(nx.edge_dfs(nx.Graph(edges), nodes))
    [(0, 1), (1, 2), (1, 3)]

    >>> list(nx.edge_dfs(nx.DiGraph(edges), nodes))
    [(0, 1), (1, 0), (2, 1), (3, 1)]

    >>> list(nx.edge_dfs(nx.MultiGraph(edges), nodes))
    [(0, 1, 0), (1, 0, 1), (0, 1, 2), (1, 2, 0), (1, 3, 0)]

    >>> list(nx.edge_dfs(nx.MultiDiGraph(edges), nodes))
    [(0, 1, 0), (1, 0, 0), (1, 0, 1), (2, 1, 0), (3, 1, 0)]

    >>> list(nx.edge_dfs(nx.DiGraph(edges), nodes, orientation="ignore"))
    [(0, 1, 'forward'), (1, 0, 'forward'), (2, 1, 'reverse'), (3, 1, 'reverse')]

    >>> list(nx.edge_dfs(nx.MultiDiGraph(edges), nodes, orientation="ignore"))
    [(0, 1, 0, 'forward'), (1, 0, 0, 'forward'), (1, 0, 1, 'reverse'), (2, 1, 0, 'reverse'), (3, 1, 0, 'reverse')]

    Notes
    -----
    The goal of this function is to visit edges. It differs from the more
    familiar depth-first traversal of nodes, as provided by
    :func:`~networkx.algorithms.traversal.depth_first_search.dfs_edges`, in
    that it does not stop once every node has been visited. In a directed graph
    with edges [(0, 1), (1, 2), (2, 1)], the edge (2, 1) would not be visited
    if not for the functionality provided by this function.

    See Also
    --------
    :func:`~networkx.algorithms.traversal.depth_first_search.dfs_edges`
networkx.edge_disjoint_paths
Python Library Documentation: function edge_disjoint_paths in module networkx.algorithms.connectivity.disjoint_paths

edge_disjoint_paths(G, s, t, flow_func=None, cutoff=None, auxiliary=None, residual=None, *, backend=None, **backend_kwargs)
    Returns the edges disjoint paths between source and target.

    Edge disjoint paths are paths that do not share any edge. The
    number of edge disjoint paths between source and target is equal
    to their edge connectivity.

    Parameters
    ----------
    G : NetworkX graph

    s : node
        Source node for the flow.

    t : node
        Sink node for the flow.

    flow_func : function
        A function for computing the maximum flow among a pair of nodes.
        The function has to accept at least three parameters: a Digraph,
        a source node, and a target node. And return a residual network
        that follows NetworkX conventions (see :meth:`maximum_flow` for
        details). If flow_func is None, the default maximum flow function
        (:meth:`edmonds_karp`) is used. The choice of the default function
        may change from version to version and should not be relied on.
        Default value: None.

    cutoff : integer or None (default: None)
        Maximum number of paths to yield. If specified, the maximum flow
        algorithm will terminate when the flow value reaches or exceeds the
        cutoff. This only works for flows that support the cutoff parameter
        (most do) and is ignored otherwise.

    auxiliary : NetworkX DiGraph
        Auxiliary digraph to compute flow based edge connectivity. It has
        to have a graph attribute called mapping with a dictionary mapping
        node names in G and in the auxiliary digraph. If provided
        it will be reused instead of recreated. Default value: None.

    residual : NetworkX DiGraph
        Residual network to compute maximum flow. If provided it will be
        reused instead of recreated. Default value: None.

    Returns
    -------
    paths : generator
        A generator of edge independent paths.

    Raises
    ------
    NetworkXNoPath
        If there is no path between source and target.

    NetworkXError
        If source or target are not in the graph G.

    See also
    --------
    :meth:`node_disjoint_paths`
    :meth:`edge_connectivity`
    :meth:`maximum_flow`
    :meth:`edmonds_karp`
    :meth:`preflow_push`
    :meth:`shortest_augmenting_path`

    Examples
    --------
    We use in this example the platonic icosahedral graph, which has node
    edge connectivity 5, thus there are 5 edge disjoint paths between any
    pair of nodes.

    >>> G = nx.icosahedral_graph()
    >>> len(list(nx.edge_disjoint_paths(G, 0, 6)))
    5


    If you need to compute edge disjoint paths on several pairs of
    nodes in the same graph, it is recommended that you reuse the
    data structures that NetworkX uses in the computation: the
    auxiliary digraph for edge connectivity, and the residual
    network for the underlying maximum flow computation.

    Example of how to compute edge disjoint paths among all pairs of
    nodes of the platonic icosahedral graph reusing the data
    structures.

    >>> import itertools
    >>> # You also have to explicitly import the function for
    >>> # building the auxiliary digraph from the connectivity package
    >>> from networkx.algorithms.connectivity import build_auxiliary_edge_connectivity
    >>> H = build_auxiliary_edge_connectivity(G)
    >>> # And the function for building the residual network from the
    >>> # flow package
    >>> from networkx.algorithms.flow import build_residual_network
    >>> # Note that the auxiliary digraph has an edge attribute named capacity
    >>> R = build_residual_network(H, "capacity")
    >>> result = {n: {} for n in G}
    >>> # Reuse the auxiliary digraph and the residual network by passing them
    >>> # as arguments
    >>> for u, v in itertools.combinations(G, 2):
    ...     k = len(list(nx.edge_disjoint_paths(G, u, v, auxiliary=H, residual=R)))
    ...     result[u][v] = k
    >>> all(result[u][v] == 5 for u, v in itertools.combinations(G, 2))
    True

    You can also use alternative flow algorithms for computing edge disjoint
    paths. For instance, in dense networks the algorithm
    :meth:`shortest_augmenting_path` will usually perform better than
    the default :meth:`edmonds_karp` which is faster for sparse
    networks with highly skewed degree distributions. Alternative flow
    functions have to be explicitly imported from the flow package.

    >>> from networkx.algorithms.flow import shortest_augmenting_path
    >>> len(list(nx.edge_disjoint_paths(G, 0, 6, flow_func=shortest_augmenting_path)))
    5

    Notes
    -----
    This is a flow based implementation of edge disjoint paths. We compute
    the maximum flow between source and target on an auxiliary directed
    network. The saturated edges in the residual network after running the
    maximum flow algorithm correspond to edge disjoint paths between source
    and target in the original network. This function handles both directed
    and undirected graphs, and can use all flow algorithms from NetworkX flow
    package.
networkx.edge_expansion
Python Library Documentation: function edge_expansion in module networkx.algorithms.cuts

edge_expansion(G, S, T=None, weight=None, *, backend=None, **backend_kwargs)
    Returns the edge expansion between two node sets.

    The *edge expansion* is the quotient of the cut size and the smaller
    of the cardinalities of the two sets. [1]

    Parameters
    ----------
    G : NetworkX graph

    S : collection
        A collection of nodes in `G`.

    T : collection
        A collection of nodes in `G`.

    weight : object
        Edge attribute key to use as weight. If not specified, edges
        have weight one.

    Returns
    -------
    number
        The edge expansion between the two sets `S` and `T`.

    See also
    --------
    boundary_expansion
    mixing_expansion
    node_expansion

    References
    ----------
    .. [1] Fan Chung.
           *Spectral Graph Theory*.
           (CBMS Regional Conference Series in Mathematics, No. 92),
           American Mathematical Society, 1997, ISBN 0-8218-0315-8
           <http://www.math.ucsd.edu/~fan/research/revised.html>
networkx.edge_load_centrality
Python Library Documentation: function edge_load_centrality in module networkx.algorithms.centrality.load

edge_load_centrality(G, cutoff=False, *, backend=None, **backend_kwargs)
    Compute edge load.

    WARNING: This concept of edge load has not been analysed
    or discussed outside of NetworkX that we know of.
    It is based loosely on load_centrality in the sense that
    it counts the number of shortest paths which cross each edge.
    This function is for demonstration and testing purposes.

    Parameters
    ----------
    G : graph
        A networkx graph

    cutoff : bool, optional (default=False)
        If specified, only consider paths of length <= cutoff.

    Returns
    -------
    A dict keyed by edge 2-tuple to the number of shortest paths
    which use that edge. Where more than one path is shortest
    the count is divided equally among paths.
networkx.edge_subgraph
Python Library Documentation: function edge_subgraph in module networkx.classes.function

edge_subgraph(G, edges)
    Returns a view of the subgraph induced by the specified edges.

    The induced subgraph contains each edge in `edges` and each
    node incident to any of those edges.

    Parameters
    ----------
    G : NetworkX Graph
    edges : iterable
        An iterable of edges. Edges not present in `G` are ignored.

    Returns
    -------
    subgraph : SubGraph View
        A read-only edge-induced subgraph of `G`.
        Changes to `G` are reflected in the view.

    Notes
    -----
    To create a mutable subgraph with its own copies of nodes
    edges and attributes use `subgraph.copy()` or `Graph(subgraph)`

    If you create a subgraph of a subgraph recursively you can end up
    with a chain of subgraphs that becomes very slow with about 15
    nested subgraph views. Luckily the edge_subgraph filter nests
    nicely so you can use the original graph as G in this function
    to avoid chains. We do not rule out chains programmatically so
    that odd cases like an `edge_subgraph` of a `restricted_view`
    can be created.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> H = G.edge_subgraph([(0, 1), (3, 4)])
    >>> list(H.nodes)
    [0, 1, 3, 4]
    >>> list(H.edges)
    [(0, 1), (3, 4)]
networkx.edgebfs
Python Library Documentation: module networkx.algorithms.traversal.edgebfs in networkx.algorithms.traversal

NAME
    networkx.algorithms.traversal.edgebfs

DESCRIPTION
    =============================
    Breadth First Search on Edges
    =============================

    Algorithms for a breadth-first traversal of edges in a graph.

FUNCTIONS
    edge_bfs(G, source=None, orientation=None, *, backend=None, **backend_kwargs)
        A directed, breadth-first-search of edges in `G`, beginning at `source`.

        Yield the edges of G in a breadth-first-search order continuing until
        all edges are generated.

        Parameters
        ----------
        G : graph
            A directed/undirected graph/multigraph.

        source : node, list of nodes
            The node from which the traversal begins. If None, then a source
            is chosen arbitrarily and repeatedly until all edges from each node in
            the graph are searched.

        orientation : None | 'original' | 'reverse' | 'ignore' (default: None)
            For directed graphs and directed multigraphs, edge traversals need not
            respect the original orientation of the edges.
            When set to 'reverse' every edge is traversed in the reverse direction.
            When set to 'ignore', every edge is treated as undirected.
            When set to 'original', every edge is treated as directed.
            In all three cases, the yielded edge tuples add a last entry to
            indicate the direction in which that edge was traversed.
            If orientation is None, the yielded edge has no direction indicated.
            The direction is respected, but not reported.

        Yields
        ------
        edge : directed edge
            A directed edge indicating the path taken by the breadth-first-search.
            For graphs, `edge` is of the form `(u, v)` where `u` and `v`
            are the tail and head of the edge as determined by the traversal.
            For multigraphs, `edge` is of the form `(u, v, key)`, where `key` is
            the key of the edge. When the graph is directed, then `u` and `v`
            are always in the order of the actual directed edge.
            If orientation is not None then the edge tuple is extended to include
            the direction of traversal ('forward' or 'reverse') on that edge.

        Examples
        --------
        >>> nodes = [0, 1, 2, 3]
        >>> edges = [(0, 1), (1, 0), (1, 0), (2, 0), (2, 1), (3, 1)]

        >>> list(nx.edge_bfs(nx.Graph(edges), nodes))
        [(0, 1), (0, 2), (1, 2), (1, 3)]

        >>> list(nx.edge_bfs(nx.DiGraph(edges), nodes))
        [(0, 1), (1, 0), (2, 0), (2, 1), (3, 1)]

        >>> list(nx.edge_bfs(nx.MultiGraph(edges), nodes))
        [(0, 1, 0), (0, 1, 1), (0, 1, 2), (0, 2, 0), (1, 2, 0), (1, 3, 0)]

        >>> list(nx.edge_bfs(nx.MultiDiGraph(edges), nodes))
        [(0, 1, 0), (1, 0, 0), (1, 0, 1), (2, 0, 0), (2, 1, 0), (3, 1, 0)]

        >>> list(nx.edge_bfs(nx.DiGraph(edges), nodes, orientation="ignore"))
        [(0, 1, 'forward'), (1, 0, 'reverse'), (2, 0, 'reverse'), (2, 1, 'reverse'), (3, 1, 'reverse')]

        >>> list(nx.edge_bfs(nx.MultiDiGraph(edges), nodes, orientation="ignore"))
        [(0, 1, 0, 'forward'), (1, 0, 0, 'reverse'), (1, 0, 1, 'reverse'), (2, 0, 0, 'reverse'), (2, 1, 0, 'reverse'), (3, 1, 0, 'reverse')]

        Notes
        -----
        The goal of this function is to visit edges. It differs from the more
        familiar breadth-first-search of nodes, as provided by
        :func:`networkx.algorithms.traversal.breadth_first_search.bfs_edges`, in
        that it does not stop once every node has been visited. In a directed graph
        with edges [(0, 1), (1, 2), (2, 1)], the edge (2, 1) would not be visited
        if not for the functionality provided by this function.

        The naming of this function is very similar to bfs_edges. The difference
        is that 'edge_bfs' yields edges even if they extend back to an already
        explored node while 'bfs_edges' yields the edges of the tree that results
        from a breadth-first-search (BFS) so no edges are reported if they extend
        to already explored nodes. That means 'edge_bfs' reports all edges while
        'bfs_edges' only report those traversed by a node-based BFS. Yet another
        description is that 'bfs_edges' reports the edges traversed during BFS
        while 'edge_bfs' reports all edges in the order they are explored.

        See Also
        --------
        bfs_edges
        bfs_tree
        edge_dfs

DATA
    __all__ = ['edge_bfs']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\traversal\edgebfs.py

networkx.edgedfs
Python Library Documentation: module networkx.algorithms.traversal.edgedfs in networkx.algorithms.traversal

NAME
    networkx.algorithms.traversal.edgedfs

DESCRIPTION
    ===========================
    Depth First Search on Edges
    ===========================

    Algorithms for a depth-first traversal of edges in a graph.

FUNCTIONS
    edge_dfs(G, source=None, orientation=None, *, backend=None, **backend_kwargs)
        A directed, depth-first-search of edges in `G`, beginning at `source`.

        Yield the edges of G in a depth-first-search order continuing until
        all edges are generated.

        Parameters
        ----------
        G : graph
            A directed/undirected graph/multigraph.

        source : node, list of nodes
            The node from which the traversal begins. If None, then a source
            is chosen arbitrarily and repeatedly until all edges from each node in
            the graph are searched.

        orientation : None | 'original' | 'reverse' | 'ignore' (default: None)
            For directed graphs and directed multigraphs, edge traversals need not
            respect the original orientation of the edges.
            When set to 'reverse' every edge is traversed in the reverse direction.
            When set to 'ignore', every edge is treated as undirected.
            When set to 'original', every edge is treated as directed.
            In all three cases, the yielded edge tuples add a last entry to
            indicate the direction in which that edge was traversed.
            If orientation is None, the yielded edge has no direction indicated.
            The direction is respected, but not reported.

        Yields
        ------
        edge : directed edge
            A directed edge indicating the path taken by the depth-first traversal.
            For graphs, `edge` is of the form `(u, v)` where `u` and `v`
            are the tail and head of the edge as determined by the traversal.
            For multigraphs, `edge` is of the form `(u, v, key)`, where `key` is
            the key of the edge. When the graph is directed, then `u` and `v`
            are always in the order of the actual directed edge.
            If orientation is not None then the edge tuple is extended to include
            the direction of traversal ('forward' or 'reverse') on that edge.

        Examples
        --------
        >>> nodes = [0, 1, 2, 3]
        >>> edges = [(0, 1), (1, 0), (1, 0), (2, 1), (3, 1)]

        >>> list(nx.edge_dfs(nx.Graph(edges), nodes))
        [(0, 1), (1, 2), (1, 3)]

        >>> list(nx.edge_dfs(nx.DiGraph(edges), nodes))
        [(0, 1), (1, 0), (2, 1), (3, 1)]

        >>> list(nx.edge_dfs(nx.MultiGraph(edges), nodes))
        [(0, 1, 0), (1, 0, 1), (0, 1, 2), (1, 2, 0), (1, 3, 0)]

        >>> list(nx.edge_dfs(nx.MultiDiGraph(edges), nodes))
        [(0, 1, 0), (1, 0, 0), (1, 0, 1), (2, 1, 0), (3, 1, 0)]

        >>> list(nx.edge_dfs(nx.DiGraph(edges), nodes, orientation="ignore"))
        [(0, 1, 'forward'), (1, 0, 'forward'), (2, 1, 'reverse'), (3, 1, 'reverse')]

        >>> list(nx.edge_dfs(nx.MultiDiGraph(edges), nodes, orientation="ignore"))
        [(0, 1, 0, 'forward'), (1, 0, 0, 'forward'), (1, 0, 1, 'reverse'), (2, 1, 0, 'reverse'), (3, 1, 0, 'reverse')]

        Notes
        -----
        The goal of this function is to visit edges. It differs from the more
        familiar depth-first traversal of nodes, as provided by
        :func:`~networkx.algorithms.traversal.depth_first_search.dfs_edges`, in
        that it does not stop once every node has been visited. In a directed graph
        with edges [(0, 1), (1, 2), (2, 1)], the edge (2, 1) would not be visited
        if not for the functionality provided by this function.

        See Also
        --------
        :func:`~networkx.algorithms.traversal.depth_first_search.dfs_edges`

DATA
    __all__ = ['edge_dfs']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\traversal\edgedfs.py

networkx.edgelist
Python Library Documentation: module networkx.readwrite.edgelist in networkx.readwrite

NAME
    networkx.readwrite.edgelist

DESCRIPTION
    **********
    Edge Lists
    **********
    Read and write NetworkX graphs as edge lists.

    The multi-line adjacency list format is useful for graphs with nodes
    that can be meaningfully represented as strings.  With the edgelist
    format simple edge data can be stored but node or graph data is not.
    There is no way of representing isolated nodes unless the node has a
    self-loop edge.

    Format
    ------
    You can read or write three formats of edge lists with these functions.

    Node pairs with no data::

     1 2

    Python dictionary as data::

     1 2 {'weight':7, 'color':'green'}

    Arbitrary data::

     1 2 7 green

FUNCTIONS
    generate_edgelist(G, delimiter=' ', data=True)
        Generate a single line of the graph G in edge list format.

        Parameters
        ----------
        G : NetworkX graph

        delimiter : string, optional
           Separator for node labels

        data : bool or list of keys
           If False generate no edge data.  If True use a dictionary
           representation of edge data.  If a list of keys use a list of data
           values corresponding to the keys.

        Returns
        -------
        lines : string
            Lines of data in adjlist format.

        Examples
        --------
        >>> G = nx.lollipop_graph(4, 3)
        >>> G[1][2]["weight"] = 3
        >>> G[3][4]["capacity"] = 12
        >>> for line in nx.generate_edgelist(G, data=False):
        ...     print(line)
        0 1
        0 2
        0 3
        1 2
        1 3
        2 3
        3 4
        4 5
        5 6

        >>> for line in nx.generate_edgelist(G):
        ...     print(line)
        0 1 {}
        0 2 {}
        0 3 {}
        1 2 {'weight': 3}
        1 3 {}
        2 3 {}
        3 4 {'capacity': 12}
        4 5 {}
        5 6 {}

        >>> for line in nx.generate_edgelist(G, data=["weight"]):
        ...     print(line)
        0 1
        0 2
        0 3
        1 2 3
        1 3
        2 3
        3 4
        4 5
        5 6

        See Also
        --------
        write_adjlist, read_adjlist

    parse_edgelist(lines, comments='#', delimiter=None, create_using=None, nodetype=None, data=True, *, backend=None, **backend_kwargs)
        Parse lines of an edge list representation of a graph.

        Parameters
        ----------
        lines : list or iterator of strings
            Input data in edgelist format
        comments : string, optional
           Marker for comment lines. Default is `'#'`. To specify that no character
           should be treated as a comment, use ``comments=None``.
        delimiter : string, optional
           Separator for node labels. Default is `None`, meaning any whitespace.
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.
        nodetype : Python type, optional
           Convert nodes to this type. Default is `None`, meaning no conversion is
           performed.
        data : bool or list of (label,type) tuples
           If `False` generate no edge data or if `True` use a dictionary
           representation of edge data or a list tuples specifying dictionary
           key names and types for edge data.

        Returns
        -------
        G: NetworkX Graph
            The graph corresponding to lines

        Examples
        --------
        Edgelist with no data:

        >>> lines = ["1 2", "2 3", "3 4"]
        >>> G = nx.parse_edgelist(lines, nodetype=int)
        >>> list(G)
        [1, 2, 3, 4]
        >>> list(G.edges())
        [(1, 2), (2, 3), (3, 4)]

        Edgelist with data in Python dictionary representation:

        >>> lines = ["1 2 {'weight': 3}", "2 3 {'weight': 27}", "3 4 {'weight': 3.0}"]
        >>> G = nx.parse_edgelist(lines, nodetype=int)
        >>> list(G)
        [1, 2, 3, 4]
        >>> list(G.edges(data=True))
        [(1, 2, {'weight': 3}), (2, 3, {'weight': 27}), (3, 4, {'weight': 3.0})]

        Edgelist with data in a list:

        >>> lines = ["1 2 3", "2 3 27", "3 4 3.0"]
        >>> G = nx.parse_edgelist(lines, nodetype=int, data=(("weight", float),))
        >>> list(G)
        [1, 2, 3, 4]
        >>> list(G.edges(data=True))
        [(1, 2, {'weight': 3.0}), (2, 3, {'weight': 27.0}), (3, 4, {'weight': 3.0})]

        See Also
        --------
        read_weighted_edgelist

    read_edgelist(path, comments='#', delimiter=None, create_using=None, nodetype=None, data=True, edgetype=None, encoding='utf-8', *, backend=None, **backend_kwargs)
        Read a graph from a list of edges.

        Parameters
        ----------
        path : file or string
           File or filename to read. If a file is provided, it must be
           opened in 'rb' mode.
           Filenames ending in .gz or .bz2 will be uncompressed.
        comments : string, optional
           The character used to indicate the start of a comment. To specify that
           no character should be treated as a comment, use ``comments=None``.
        delimiter : string, optional
           The string used to separate values.  The default is whitespace.
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.
        nodetype : int, float, str, Python type, optional
           Convert node data from strings to specified type
        data : bool or list of (label,type) tuples
           Tuples specifying dictionary key names and types for edge data
        edgetype : int, float, str, Python type, optional OBSOLETE
           Convert edge data from strings to specified type and use as 'weight'
        encoding: string, optional
           Specify which encoding to use when reading file.

        Returns
        -------
        G : graph
           A networkx Graph or other type specified with create_using

        Examples
        --------
        >>> nx.write_edgelist(nx.path_graph(4), "test.edgelist")
        >>> G = nx.read_edgelist("test.edgelist")

        >>> fh = open("test.edgelist", "rb")
        >>> G = nx.read_edgelist(fh)
        >>> fh.close()

        >>> G = nx.read_edgelist("test.edgelist", nodetype=int)
        >>> G = nx.read_edgelist("test.edgelist", create_using=nx.DiGraph)

        Edgelist with data in a list:

        >>> textline = "1 2 3"
        >>> fh = open("test.edgelist", "w")
        >>> d = fh.write(textline)
        >>> fh.close()
        >>> G = nx.read_edgelist("test.edgelist", nodetype=int, data=(("weight", float),))
        >>> list(G)
        [1, 2]
        >>> list(G.edges(data=True))
        [(1, 2, {'weight': 3.0})]

        See parse_edgelist() for more examples of formatting.

        See Also
        --------
        parse_edgelist
        write_edgelist

        Notes
        -----
        Since nodes must be hashable, the function nodetype must return hashable
        types (e.g. int, float, str, frozenset - or tuples of those, etc.)

    read_weighted_edgelist(path, comments='#', delimiter=None, create_using=None, nodetype=None, encoding='utf-8', *, backend=None, **backend_kwargs)
        Read a graph as list of edges with numeric weights.

        Parameters
        ----------
        path : file or string
           File or filename to read. If a file is provided, it must be
           opened in 'rb' mode.
           Filenames ending in .gz or .bz2 will be uncompressed.
        comments : string, optional
           The character used to indicate the start of a comment.
        delimiter : string, optional
           The string used to separate values.  The default is whitespace.
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.
        nodetype : int, float, str, Python type, optional
           Convert node data from strings to specified type
        encoding: string, optional
           Specify which encoding to use when reading file.

        Returns
        -------
        G : graph
           A networkx Graph or other type specified with create_using

        Notes
        -----
        Since nodes must be hashable, the function nodetype must return hashable
        types (e.g. int, float, str, frozenset - or tuples of those, etc.)

        Example edgelist file format.

        With numeric edge data::

         # read with
         # >>> G=nx.read_weighted_edgelist(fh)
         # source target data
         a b 1
         a c 3.14159
         d e 42

        See Also
        --------
        write_weighted_edgelist

    write_edgelist(G, path, comments='#', delimiter=' ', data=True, encoding='utf-8')
        Write graph as a list of edges.

        Parameters
        ----------
        G : graph
           A NetworkX graph
        path : file or string
           File or filename to write. If a file is provided, it must be
           opened in 'wb' mode. Filenames ending in .gz or .bz2 will be compressed.
        comments : string, optional
           The character used to indicate the start of a comment
        delimiter : string, optional
           The string used to separate values.  The default is whitespace.
        data : bool or list, optional
           If False write no edge data.
           If True write a string representation of the edge data dictionary..
           If a list (or other iterable) is provided, write the  keys specified
           in the list.
        encoding: string, optional
           Specify which encoding to use when writing file.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_edgelist(G, "test.edgelist")
        >>> G = nx.path_graph(4)
        >>> fh = open("test.edgelist", "wb")
        >>> nx.write_edgelist(G, fh)
        >>> nx.write_edgelist(G, "test.edgelist.gz")
        >>> nx.write_edgelist(G, "test.edgelist.gz", data=False)

        >>> G = nx.Graph()
        >>> G.add_edge(1, 2, weight=7, color="red")
        >>> nx.write_edgelist(G, "test.edgelist", data=False)
        >>> nx.write_edgelist(G, "test.edgelist", data=["color"])
        >>> nx.write_edgelist(G, "test.edgelist", data=["color", "weight"])

        See Also
        --------
        read_edgelist
        write_weighted_edgelist

    write_weighted_edgelist(G, path, comments='#', delimiter=' ', encoding='utf-8')
        Write graph G as a list of edges with numeric weights.

        Parameters
        ----------
        G : graph
           A NetworkX graph
        path : file or string
           File or filename to write. If a file is provided, it must be
           opened in 'wb' mode.
           Filenames ending in .gz or .bz2 will be compressed.
        comments : string, optional
           The character used to indicate the start of a comment
        delimiter : string, optional
           The string used to separate values.  The default is whitespace.
        encoding: string, optional
           Specify which encoding to use when writing file.

        Examples
        --------
        >>> G = nx.Graph()
        >>> G.add_edge(1, 2, weight=7)
        >>> nx.write_weighted_edgelist(G, "test.weighted.edgelist")

        See Also
        --------
        read_edgelist
        write_edgelist
        read_weighted_edgelist

DATA
    __all__ = ['generate_edgelist', 'write_edgelist', 'parse_edgelist', 'r...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\edgelist.py

networkx.edges
Python Library Documentation: function edges in module networkx.classes.function

edges(G, nbunch=None)
    Returns an edge view of edges incident to nodes in nbunch.

    Return all edges if nbunch is unspecified or nbunch=None.

    For digraphs, edges=out_edges

    This function wraps the :func:`G.edges <networkx.Graph.edges>` property.
networkx.effective_graph_resistance
Python Library Documentation: function effective_graph_resistance in module networkx.algorithms.distance_measures

effective_graph_resistance(G, weight=None, invert_weight=True, *, backend=None, **backend_kwargs)
    Returns the Effective graph resistance of G.

    Also known as the Kirchhoff index.

    The effective graph resistance is defined as the sum
    of the resistance distance of every node pair in G [1]_.

    If weight is not provided, then a weight of 1 is used for all edges.

    The effective graph resistance of a disconnected graph is infinite.

    Parameters
    ----------
    G : NetworkX graph
       A graph

    weight : string or None, optional (default=None)
       The edge data key used to compute the effective graph resistance.
       If None, then each edge has weight 1.

    invert_weight : boolean (default=True)
        Proper calculation of resistance distance requires building the
        Laplacian matrix with the reciprocal of the weight. Not required
        if the weight is already inverted. Weight cannot be zero.

    Returns
    -------
    RG : float
        The effective graph resistance of `G`.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a directed graph.

    NetworkXError
        If `G` does not contain any nodes.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
    >>> round(nx.effective_graph_resistance(G), 10)
    10.25

    Notes
    -----
    The implementation is based on Theorem 2.2 in [2]_. Self-loops are ignored.
    Multi-edges are contracted in one edge with weight equal to the harmonic sum of the weights.

    References
    ----------
    .. [1] Wolfram
       "Kirchhoff Index."
       https://mathworld.wolfram.com/KirchhoffIndex.html
    .. [2] W. Ellens, F. M. Spieksma, P. Van Mieghem, A. Jamakovic, R. E. Kooij.
        Effective graph resistance.
        Lin. Alg. Appl. 435:2491-2506, 2011.
networkx.effective_size
Python Library Documentation: function effective_size in module networkx.algorithms.structuralholes

effective_size(G, nodes=None, weight=None, *, backend=None, **backend_kwargs)
    Returns the effective size of all nodes in the graph ``G``.

    The *effective size* of a node's ego network is based on the concept
    of redundancy. A person's ego network has redundancy to the extent
    that her contacts are connected to each other as well. The
    nonredundant part of a person's relationships is the effective
    size of her ego network [1]_.  Formally, the effective size of a
    node $u$, denoted $e(u)$, is defined by

    .. math::

       e(u) = \sum_{v \in N(u) \setminus \{u\}}
       \left(1 - \sum_{w \in N(v)} p_{uw} m_{vw}\right)

    where $N(u)$ is the set of neighbors of $u$ and $p_{uw}$ is the
    normalized mutual weight of the (directed or undirected) edges
    joining $u$ and $v$, for each vertex $u$ and $v$ [1]_. And $m_{vw}$
    is the mutual weight of $v$ and $w$ divided by $v$ highest mutual
    weight with any of its neighbors. The *mutual weight* of $u$ and $v$
    is the sum of the weights of edges joining them (edge weights are
    assumed to be one if the graph is unweighted).

    For the case of unweighted and undirected graphs, Borgatti proposed
    a simplified formula to compute effective size [2]_

    .. math::

       e(u) = n - \frac{2t}{n}

    where `t` is the number of ties in the ego network (not including
    ties to ego) and `n` is the number of nodes (excluding ego).

    Parameters
    ----------
    G : NetworkX graph
        The graph containing ``v``. Directed graphs are treated like
        undirected graphs when computing neighbors of ``v``.

    nodes : container, optional
        Container of nodes in the graph ``G`` to compute the effective size.
        If None, the effective size of every node is computed.

    weight : None or string, optional
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.

    Returns
    -------
    dict
        Dictionary with nodes as keys and the effective size of the node as values.

    Notes
    -----
    Burt also defined the related concept of *efficiency* of a node's ego
    network, which is its effective size divided by the degree of that
    node [1]_. So you can easily compute efficiency:

    >>> G = nx.DiGraph()
    >>> G.add_edges_from([(0, 1), (0, 2), (1, 0), (2, 1)])
    >>> esize = nx.effective_size(G)
    >>> efficiency = {n: v / G.degree(n) for n, v in esize.items()}

    See also
    --------
    constraint

    References
    ----------
    .. [1] Burt, Ronald S.
           *Structural Holes: The Social Structure of Competition.*
           Cambridge: Harvard University Press, 1995.

    .. [2] Borgatti, S.
           "Structural Holes: Unpacking Burt's Redundancy Measures"
           CONNECTIONS 20(1):35-38.
           http://www.analytictech.com/connections/v20(1)/holes.htm
networkx.efficiency
Python Library Documentation: function efficiency in module networkx.algorithms.efficiency_measures

efficiency(G, u, v, *, backend=None, **backend_kwargs)
    Returns the efficiency of a pair of nodes in a graph.

    The *efficiency* of a pair of nodes is the multiplicative inverse of the
    shortest path distance between the nodes [1]_. Returns 0 if no path
    between nodes.

    Parameters
    ----------
    G : :class:`networkx.Graph`
        An undirected graph for which to compute the average local efficiency.
    u, v : node
        Nodes in the graph ``G``.

    Returns
    -------
    float
        Multiplicative inverse of the shortest path distance between the nodes.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
    >>> nx.efficiency(G, 2, 3)  # this gives efficiency for node 2 and 3
    0.5

    Notes
    -----
    Edge weights are ignored when computing the shortest path distances.

    See also
    --------
    local_efficiency
    global_efficiency

    References
    ----------
    .. [1] Latora, Vito, and Massimo Marchiori.
           "Efficient behavior of small-world networks."
           *Physical Review Letters* 87.19 (2001): 198701.
           <https://doi.org/10.1103/PhysRevLett.87.198701>
networkx.efficiency_measures
Python Library Documentation: module networkx.algorithms.efficiency_measures in networkx.algorithms

NAME
    networkx.algorithms.efficiency_measures - Provides functions for computing the efficiency of nodes and graphs.

FUNCTIONS
    efficiency(G, u, v, *, backend=None, **backend_kwargs)
        Returns the efficiency of a pair of nodes in a graph.

        The *efficiency* of a pair of nodes is the multiplicative inverse of the
        shortest path distance between the nodes [1]_. Returns 0 if no path
        between nodes.

        Parameters
        ----------
        G : :class:`networkx.Graph`
            An undirected graph for which to compute the average local efficiency.
        u, v : node
            Nodes in the graph ``G``.

        Returns
        -------
        float
            Multiplicative inverse of the shortest path distance between the nodes.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
        >>> nx.efficiency(G, 2, 3)  # this gives efficiency for node 2 and 3
        0.5

        Notes
        -----
        Edge weights are ignored when computing the shortest path distances.

        See also
        --------
        local_efficiency
        global_efficiency

        References
        ----------
        .. [1] Latora, Vito, and Massimo Marchiori.
               "Efficient behavior of small-world networks."
               *Physical Review Letters* 87.19 (2001): 198701.
               <https://doi.org/10.1103/PhysRevLett.87.198701>

    global_efficiency(G, *, backend=None, **backend_kwargs)
        Returns the average global efficiency of the graph.

        The *efficiency* of a pair of nodes in a graph is the multiplicative
        inverse of the shortest path distance between the nodes. The *average
        global efficiency* of a graph is the average efficiency of all pairs of
        nodes [1]_.

        Parameters
        ----------
        G : :class:`networkx.Graph`
            An undirected graph for which to compute the average global efficiency.

        Returns
        -------
        float
            The average global efficiency of the graph.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
        >>> round(nx.global_efficiency(G), 12)
        0.916666666667

        Notes
        -----
        Edge weights are ignored when computing the shortest path distances.

        See also
        --------
        local_efficiency

        References
        ----------
        .. [1] Latora, Vito, and Massimo Marchiori.
               "Efficient behavior of small-world networks."
               *Physical Review Letters* 87.19 (2001): 198701.
               <https://doi.org/10.1103/PhysRevLett.87.198701>

    local_efficiency(G, *, backend=None, **backend_kwargs)
        Returns the average local efficiency of the graph.

        The *efficiency* of a pair of nodes in a graph is the multiplicative
        inverse of the shortest path distance between the nodes. The *local
        efficiency* of a node in the graph is the average global efficiency of the
        subgraph induced by the neighbors of the node. The *average local
        efficiency* is the average of the local efficiencies of each node [1]_.

        Parameters
        ----------
        G : :class:`networkx.Graph`
            An undirected graph for which to compute the average local efficiency.

        Returns
        -------
        float
            The average local efficiency of the graph.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
        >>> nx.local_efficiency(G)
        0.9166666666666667

        Notes
        -----
        Edge weights are ignored when computing the shortest path distances.

        See also
        --------
        global_efficiency

        References
        ----------
        .. [1] Latora, Vito, and Massimo Marchiori.
               "Efficient behavior of small-world networks."
               *Physical Review Letters* 87.19 (2001): 198701.
               <https://doi.org/10.1103/PhysRevLett.87.198701>

DATA
    __all__ = ['efficiency', 'local_efficiency', 'global_efficiency']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\efficiency_measures.py

networkx.ego
Python Library Documentation: module networkx.generators.ego in networkx.generators

NAME
    networkx.generators.ego - Ego graph.

FUNCTIONS
    ego_graph(G, n, radius=1, center=True, undirected=False, distance=None, *, backend=None, **backend_kwargs)
        Returns induced subgraph of neighbors centered at node n within
        a given radius.

        Parameters
        ----------
        G : graph
          A NetworkX Graph or DiGraph

        n : node
          A single node

        radius : number, optional
          Include all neighbors of distance<=radius from n.

        center : bool, optional
          If False, do not include center node in graph

        undirected : bool, optional
          If True use both in- and out-neighbors of directed graphs.

        distance : key, optional
          Use specified edge data key as distance.  For example, setting
          distance='weight' will use the edge weight to measure the
          distance from the node n.

        Notes
        -----
        For directed graphs D this produces the "out" neighborhood
        or successors.  If you want the neighborhood of predecessors
        first reverse the graph with D.reverse().  If you want both
        directions use the keyword argument undirected=True.

        Node, edge, and graph attributes are copied to the returned subgraph.

DATA
    __all__ = ['ego_graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\ego.py

networkx.ego_graph
Python Library Documentation: function ego_graph in module networkx.generators.ego

ego_graph(G, n, radius=1, center=True, undirected=False, distance=None, *, backend=None, **backend_kwargs)
    Returns induced subgraph of neighbors centered at node n within
    a given radius.

    Parameters
    ----------
    G : graph
      A NetworkX Graph or DiGraph

    n : node
      A single node

    radius : number, optional
      Include all neighbors of distance<=radius from n.

    center : bool, optional
      If False, do not include center node in graph

    undirected : bool, optional
      If True use both in- and out-neighbors of directed graphs.

    distance : key, optional
      Use specified edge data key as distance.  For example, setting
      distance='weight' will use the edge weight to measure the
      distance from the node n.

    Notes
    -----
    For directed graphs D this produces the "out" neighborhood
    or successors.  If you want the neighborhood of predecessors
    first reverse the graph with D.reverse().  If you want both
    directions use the keyword argument undirected=True.

    Node, edge, and graph attributes are copied to the returned subgraph.
networkx.eigenvector
Python Library Documentation: module networkx.algorithms.centrality.eigenvector in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.eigenvector - Functions for computing eigenvector centrality.

FUNCTIONS
    eigenvector_centrality(G, max_iter=100, tol=1e-06, nstart=None, weight=None, *, backend=None, **backend_kwargs)
        Compute the eigenvector centrality for the graph G.

        Eigenvector centrality computes the centrality for a node by adding
        the centrality of its predecessors. The centrality for node $i$ is the
        $i$-th element of a left eigenvector associated with the eigenvalue $\lambda$
        of maximum modulus that is positive. Such an eigenvector $x$ is
        defined up to a multiplicative constant by the equation

        .. math::

             \lambda x^T = x^T A,

        where $A$ is the adjacency matrix of the graph G. By definition of
        row-column product, the equation above is equivalent to

        .. math::

            \lambda x_i = \sum_{j\to i}x_j.

        That is, adding the eigenvector centralities of the predecessors of
        $i$ one obtains the eigenvector centrality of $i$ multiplied by
        $\lambda$. In the case of undirected graphs, $x$ also solves the familiar
        right-eigenvector equation $Ax = \lambda x$.

        By virtue of the Perron–Frobenius theorem [1]_, if G is strongly
        connected there is a unique eigenvector $x$, and all its entries
        are strictly positive.

        If G is not strongly connected there might be several left
        eigenvectors associated with $\lambda$, and some of their elements
        might be zero.

        Parameters
        ----------
        G : graph
          A networkx graph.

        max_iter : integer, optional (default=100)
          Maximum number of power iterations.

        tol : float, optional (default=1.0e-6)
          Error tolerance (in Euclidean norm) used to check convergence in
          power iteration.

        nstart : dictionary, optional (default=None)
          Starting value of power iteration for each node. Must have a nonzero
          projection on the desired eigenvector for the power method to converge.
          If None, this implementation uses an all-ones vector, which is a safe
          choice.

        weight : None or string, optional (default=None)
          If None, all edge weights are considered equal. Otherwise holds the
          name of the edge attribute used as weight. In this measure the
          weight is interpreted as the connection strength.

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with eigenvector centrality as the value. The
           associated vector has unit Euclidean norm and the values are
           nonegative.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> centrality = nx.eigenvector_centrality(G)
        >>> sorted((v, f"{c:0.2f}") for v, c in centrality.items())
        [(0, '0.37'), (1, '0.60'), (2, '0.60'), (3, '0.37')]

        Raises
        ------
        NetworkXPointlessConcept
            If the graph G is the null graph.

        NetworkXError
            If each value in `nstart` is zero.

        PowerIterationFailedConvergence
            If the algorithm fails to converge to the specified tolerance
            within the specified number of iterations of the power iteration
            method.

        See Also
        --------
        eigenvector_centrality_numpy
        :func:`~networkx.algorithms.link_analysis.pagerank_alg.pagerank`
        :func:`~networkx.algorithms.link_analysis.hits_alg.hits`

        Notes
        -----
        Eigenvector centrality was introduced by Landau [2]_ for chess
        tournaments. It was later rediscovered by Wei [3]_ and then
        popularized by Kendall [4]_ in the context of sport ranking. Berge
        introduced a general definition for graphs based on social connections
        [5]_. Bonacich [6]_ reintroduced again eigenvector centrality and made
        it popular in link analysis.

        This function computes the left dominant eigenvector, which corresponds
        to adding the centrality of predecessors: this is the usual approach.
        To add the centrality of successors first reverse the graph with
        ``G.reverse()``.

        The implementation uses power iteration [7]_ to compute a dominant
        eigenvector starting from the provided vector `nstart`. Convergence is
        guaranteed as long as `nstart` has a nonzero projection on a dominant
        eigenvector, which certainly happens using the default value.

        The method stops when the change in the computed vector between two
        iterations is smaller than an error tolerance of ``G.number_of_nodes()
        * tol`` or after ``max_iter`` iterations, but in the second case it
        raises an exception.

        This implementation uses $(A + I)$ rather than the adjacency matrix
        $A$ because the change preserves eigenvectors, but it shifts the
        spectrum, thus guaranteeing convergence even for networks with
        negative eigenvalues of maximum modulus.

        References
        ----------
        .. [1] Abraham Berman and Robert J. Plemmons.
           "Nonnegative Matrices in the Mathematical Sciences."
           Classics in Applied Mathematics. SIAM, 1994.

        .. [2] Edmund Landau.
           "Zur relativen Wertbemessung der Turnierresultate."
           Deutsches Wochenschach, 11:366–369, 1895.

        .. [3] Teh-Hsing Wei.
           "The Algebraic Foundations of Ranking Theory."
           PhD thesis, University of Cambridge, 1952.

        .. [4] Maurice G. Kendall.
           "Further contributions to the theory of paired comparisons."
           Biometrics, 11(1):43–62, 1955.
           https://www.jstor.org/stable/3001479

        .. [5] Claude Berge
           "Théorie des graphes et ses applications."
           Dunod, Paris, France, 1958.

        .. [6] Phillip Bonacich.
           "Technique for analyzing overlapping memberships."
           Sociological Methodology, 4:176–185, 1972.
           https://www.jstor.org/stable/270732

        .. [7] Power iteration:: https://en.wikipedia.org/wiki/Power_iteration

    eigenvector_centrality_numpy(G, weight=None, max_iter=50, tol=0, *, backend=None, **backend_kwargs)
        Compute the eigenvector centrality for the graph `G`.

        Eigenvector centrality computes the centrality for a node by adding
        the centrality of its predecessors. The centrality for node $i$ is the
        $i$-th element of a left eigenvector associated with the eigenvalue $\lambda$
        of maximum modulus that is positive. Such an eigenvector $x$ is
        defined up to a multiplicative constant by the equation

        .. math::

             \lambda x^T = x^T A,

        where $A$ is the adjacency matrix of the graph `G`. By definition of
        row-column product, the equation above is equivalent to

        .. math::

            \lambda x_i = \sum_{j\to i}x_j.

        That is, adding the eigenvector centralities of the predecessors of
        $i$ one obtains the eigenvector centrality of $i$ multiplied by
        $\lambda$. In the case of undirected graphs, $x$ also solves the familiar
        right-eigenvector equation $Ax = \lambda x$.

        By virtue of the Perron--Frobenius theorem [1]_, if `G` is (strongly)
        connected, there is a unique eigenvector $x$, and all its entries
        are strictly positive.

        However, if `G` is not (strongly) connected, there might be several left
        eigenvectors associated with $\lambda$, and some of their elements
        might be zero.
        Depending on the method used to choose eigenvectors, round-off error can affect
        which of the infinitely many eigenvectors is reported.
        This can lead to inconsistent results for the same graph,
        which the underlying implementation is not robust to.
        For this reason, only (strongly) connected graphs are accepted.

        Parameters
        ----------
        G : graph
            A connected NetworkX graph.

        weight : None or string, optional (default=None)
            If ``None``, all edge weights are considered equal. Otherwise holds the
            name of the edge attribute used as weight. In this measure the
            weight is interpreted as the connection strength.

        max_iter : integer, optional (default=50)
            Maximum number of Arnoldi update iterations allowed.

        tol : float, optional (default=0)
            Relative accuracy for eigenvalues (stopping criterion).
            The default value of 0 implies machine precision.

        Returns
        -------
        nodes : dict of nodes
            Dictionary of nodes with eigenvector centrality as the value. The
            associated vector has unit Euclidean norm and the values are
            nonnegative.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> centrality = nx.eigenvector_centrality_numpy(G)
        >>> print([f"{node} {centrality[node]:0.2f}" for node in centrality])
        ['0 0.37', '1 0.60', '2 0.60', '3 0.37']

        Raises
        ------
        NetworkXPointlessConcept
            If the graph `G` is the null graph.

        ArpackNoConvergence
            When the requested convergence is not obtained. The currently
            converged eigenvalues and eigenvectors can be found as
            eigenvalues and eigenvectors attributes of the exception object.

        AmbiguousSolution
            If `G` is not connected.

        See Also
        --------
        :func:`scipy.sparse.linalg.eigs`
        eigenvector_centrality
        :func:`~networkx.algorithms.link_analysis.pagerank_alg.pagerank`
        :func:`~networkx.algorithms.link_analysis.hits_alg.hits`

        Notes
        -----
        Eigenvector centrality was introduced by Landau [2]_ for chess
        tournaments. It was later rediscovered by Wei [3]_ and then
        popularized by Kendall [4]_ in the context of sport ranking. Berge
        introduced a general definition for graphs based on social connections
        [5]_. Bonacich [6]_ reintroduced again eigenvector centrality and made
        it popular in link analysis.

        This function computes the left dominant eigenvector, which corresponds
        to adding the centrality of predecessors: this is the usual approach.
        To add the centrality of successors first reverse the graph with
        ``G.reverse()``.

        This implementation uses the
        :func:`SciPy sparse eigenvalue solver<scipy.sparse.linalg.eigs>` (ARPACK)
        to find the largest eigenvalue/eigenvector pair using Arnoldi iterations
        [7]_.

        References
        ----------
        .. [1] Abraham Berman and Robert J. Plemmons.
           "Nonnegative Matrices in the Mathematical Sciences".
           Classics in Applied Mathematics. SIAM, 1994.

        .. [2] Edmund Landau.
           "Zur relativen Wertbemessung der Turnierresultate".
           Deutsches Wochenschach, 11:366--369, 1895.

        .. [3] Teh-Hsing Wei.
           "The Algebraic Foundations of Ranking Theory".
           PhD thesis, University of Cambridge, 1952.

        .. [4] Maurice G. Kendall.
           "Further contributions to the theory of paired comparisons".
           Biometrics, 11(1):43--62, 1955.
           https://www.jstor.org/stable/3001479

        .. [5] Claude Berge.
           "Théorie des graphes et ses applications".
           Dunod, Paris, France, 1958.

        .. [6] Phillip Bonacich.
           "Technique for analyzing overlapping memberships".
           Sociological Methodology, 4:176--185, 1972.
           https://www.jstor.org/stable/270732

        .. [7] Arnoldi, W. E. (1951).
           "The principle of minimized iterations in the solution of the matrix eigenvalue problem".
           Quarterly of Applied Mathematics. 9 (1): 17--29.
           https://doi.org/10.1090/qam/42792

DATA
    __all__ = ['eigenvector_centrality', 'eigenvector_centrality_numpy']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\eigenvector.py

networkx.eigenvector_centrality
Python Library Documentation: function eigenvector_centrality in module networkx.algorithms.centrality.eigenvector

eigenvector_centrality(G, max_iter=100, tol=1e-06, nstart=None, weight=None, *, backend=None, **backend_kwargs)
    Compute the eigenvector centrality for the graph G.

    Eigenvector centrality computes the centrality for a node by adding
    the centrality of its predecessors. The centrality for node $i$ is the
    $i$-th element of a left eigenvector associated with the eigenvalue $\lambda$
    of maximum modulus that is positive. Such an eigenvector $x$ is
    defined up to a multiplicative constant by the equation

    .. math::

         \lambda x^T = x^T A,

    where $A$ is the adjacency matrix of the graph G. By definition of
    row-column product, the equation above is equivalent to

    .. math::

        \lambda x_i = \sum_{j\to i}x_j.

    That is, adding the eigenvector centralities of the predecessors of
    $i$ one obtains the eigenvector centrality of $i$ multiplied by
    $\lambda$. In the case of undirected graphs, $x$ also solves the familiar
    right-eigenvector equation $Ax = \lambda x$.

    By virtue of the Perron–Frobenius theorem [1]_, if G is strongly
    connected there is a unique eigenvector $x$, and all its entries
    are strictly positive.

    If G is not strongly connected there might be several left
    eigenvectors associated with $\lambda$, and some of their elements
    might be zero.

    Parameters
    ----------
    G : graph
      A networkx graph.

    max_iter : integer, optional (default=100)
      Maximum number of power iterations.

    tol : float, optional (default=1.0e-6)
      Error tolerance (in Euclidean norm) used to check convergence in
      power iteration.

    nstart : dictionary, optional (default=None)
      Starting value of power iteration for each node. Must have a nonzero
      projection on the desired eigenvector for the power method to converge.
      If None, this implementation uses an all-ones vector, which is a safe
      choice.

    weight : None or string, optional (default=None)
      If None, all edge weights are considered equal. Otherwise holds the
      name of the edge attribute used as weight. In this measure the
      weight is interpreted as the connection strength.

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with eigenvector centrality as the value. The
       associated vector has unit Euclidean norm and the values are
       nonegative.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> centrality = nx.eigenvector_centrality(G)
    >>> sorted((v, f"{c:0.2f}") for v, c in centrality.items())
    [(0, '0.37'), (1, '0.60'), (2, '0.60'), (3, '0.37')]

    Raises
    ------
    NetworkXPointlessConcept
        If the graph G is the null graph.

    NetworkXError
        If each value in `nstart` is zero.

    PowerIterationFailedConvergence
        If the algorithm fails to converge to the specified tolerance
        within the specified number of iterations of the power iteration
        method.

    See Also
    --------
    eigenvector_centrality_numpy
    :func:`~networkx.algorithms.link_analysis.pagerank_alg.pagerank`
    :func:`~networkx.algorithms.link_analysis.hits_alg.hits`

    Notes
    -----
    Eigenvector centrality was introduced by Landau [2]_ for chess
    tournaments. It was later rediscovered by Wei [3]_ and then
    popularized by Kendall [4]_ in the context of sport ranking. Berge
    introduced a general definition for graphs based on social connections
    [5]_. Bonacich [6]_ reintroduced again eigenvector centrality and made
    it popular in link analysis.

    This function computes the left dominant eigenvector, which corresponds
    to adding the centrality of predecessors: this is the usual approach.
    To add the centrality of successors first reverse the graph with
    ``G.reverse()``.

    The implementation uses power iteration [7]_ to compute a dominant
    eigenvector starting from the provided vector `nstart`. Convergence is
    guaranteed as long as `nstart` has a nonzero projection on a dominant
    eigenvector, which certainly happens using the default value.

    The method stops when the change in the computed vector between two
    iterations is smaller than an error tolerance of ``G.number_of_nodes()
    * tol`` or after ``max_iter`` iterations, but in the second case it
    raises an exception.

    This implementation uses $(A + I)$ rather than the adjacency matrix
    $A$ because the change preserves eigenvectors, but it shifts the
    spectrum, thus guaranteeing convergence even for networks with
    negative eigenvalues of maximum modulus.

    References
    ----------
    .. [1] Abraham Berman and Robert J. Plemmons.
       "Nonnegative Matrices in the Mathematical Sciences."
       Classics in Applied Mathematics. SIAM, 1994.

    .. [2] Edmund Landau.
       "Zur relativen Wertbemessung der Turnierresultate."
       Deutsches Wochenschach, 11:366–369, 1895.

    .. [3] Teh-Hsing Wei.
       "The Algebraic Foundations of Ranking Theory."
       PhD thesis, University of Cambridge, 1952.

    .. [4] Maurice G. Kendall.
       "Further contributions to the theory of paired comparisons."
       Biometrics, 11(1):43–62, 1955.
       https://www.jstor.org/stable/3001479

    .. [5] Claude Berge
       "Théorie des graphes et ses applications."
       Dunod, Paris, France, 1958.

    .. [6] Phillip Bonacich.
       "Technique for analyzing overlapping memberships."
       Sociological Methodology, 4:176–185, 1972.
       https://www.jstor.org/stable/270732

    .. [7] Power iteration:: https://en.wikipedia.org/wiki/Power_iteration
networkx.eigenvector_centrality_numpy
Python Library Documentation: function eigenvector_centrality_numpy in module networkx.algorithms.centrality.eigenvector

eigenvector_centrality_numpy(G, weight=None, max_iter=50, tol=0, *, backend=None, **backend_kwargs)
    Compute the eigenvector centrality for the graph `G`.

    Eigenvector centrality computes the centrality for a node by adding
    the centrality of its predecessors. The centrality for node $i$ is the
    $i$-th element of a left eigenvector associated with the eigenvalue $\lambda$
    of maximum modulus that is positive. Such an eigenvector $x$ is
    defined up to a multiplicative constant by the equation

    .. math::

         \lambda x^T = x^T A,

    where $A$ is the adjacency matrix of the graph `G`. By definition of
    row-column product, the equation above is equivalent to

    .. math::

        \lambda x_i = \sum_{j\to i}x_j.

    That is, adding the eigenvector centralities of the predecessors of
    $i$ one obtains the eigenvector centrality of $i$ multiplied by
    $\lambda$. In the case of undirected graphs, $x$ also solves the familiar
    right-eigenvector equation $Ax = \lambda x$.

    By virtue of the Perron--Frobenius theorem [1]_, if `G` is (strongly)
    connected, there is a unique eigenvector $x$, and all its entries
    are strictly positive.

    However, if `G` is not (strongly) connected, there might be several left
    eigenvectors associated with $\lambda$, and some of their elements
    might be zero.
    Depending on the method used to choose eigenvectors, round-off error can affect
    which of the infinitely many eigenvectors is reported.
    This can lead to inconsistent results for the same graph,
    which the underlying implementation is not robust to.
    For this reason, only (strongly) connected graphs are accepted.

    Parameters
    ----------
    G : graph
        A connected NetworkX graph.

    weight : None or string, optional (default=None)
        If ``None``, all edge weights are considered equal. Otherwise holds the
        name of the edge attribute used as weight. In this measure the
        weight is interpreted as the connection strength.

    max_iter : integer, optional (default=50)
        Maximum number of Arnoldi update iterations allowed.

    tol : float, optional (default=0)
        Relative accuracy for eigenvalues (stopping criterion).
        The default value of 0 implies machine precision.

    Returns
    -------
    nodes : dict of nodes
        Dictionary of nodes with eigenvector centrality as the value. The
        associated vector has unit Euclidean norm and the values are
        nonnegative.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> centrality = nx.eigenvector_centrality_numpy(G)
    >>> print([f"{node} {centrality[node]:0.2f}" for node in centrality])
    ['0 0.37', '1 0.60', '2 0.60', '3 0.37']

    Raises
    ------
    NetworkXPointlessConcept
        If the graph `G` is the null graph.

    ArpackNoConvergence
        When the requested convergence is not obtained. The currently
        converged eigenvalues and eigenvectors can be found as
        eigenvalues and eigenvectors attributes of the exception object.

    AmbiguousSolution
        If `G` is not connected.

    See Also
    --------
    :func:`scipy.sparse.linalg.eigs`
    eigenvector_centrality
    :func:`~networkx.algorithms.link_analysis.pagerank_alg.pagerank`
    :func:`~networkx.algorithms.link_analysis.hits_alg.hits`

    Notes
    -----
    Eigenvector centrality was introduced by Landau [2]_ for chess
    tournaments. It was later rediscovered by Wei [3]_ and then
    popularized by Kendall [4]_ in the context of sport ranking. Berge
    introduced a general definition for graphs based on social connections
    [5]_. Bonacich [6]_ reintroduced again eigenvector centrality and made
    it popular in link analysis.

    This function computes the left dominant eigenvector, which corresponds
    to adding the centrality of predecessors: this is the usual approach.
    To add the centrality of successors first reverse the graph with
    ``G.reverse()``.

    This implementation uses the
    :func:`SciPy sparse eigenvalue solver<scipy.sparse.linalg.eigs>` (ARPACK)
    to find the largest eigenvalue/eigenvector pair using Arnoldi iterations
    [7]_.

    References
    ----------
    .. [1] Abraham Berman and Robert J. Plemmons.
       "Nonnegative Matrices in the Mathematical Sciences".
       Classics in Applied Mathematics. SIAM, 1994.

    .. [2] Edmund Landau.
       "Zur relativen Wertbemessung der Turnierresultate".
       Deutsches Wochenschach, 11:366--369, 1895.

    .. [3] Teh-Hsing Wei.
       "The Algebraic Foundations of Ranking Theory".
       PhD thesis, University of Cambridge, 1952.

    .. [4] Maurice G. Kendall.
       "Further contributions to the theory of paired comparisons".
       Biometrics, 11(1):43--62, 1955.
       https://www.jstor.org/stable/3001479

    .. [5] Claude Berge.
       "Théorie des graphes et ses applications".
       Dunod, Paris, France, 1958.

    .. [6] Phillip Bonacich.
       "Technique for analyzing overlapping memberships".
       Sociological Methodology, 4:176--185, 1972.
       https://www.jstor.org/stable/270732

    .. [7] Arnoldi, W. E. (1951).
       "The principle of minimized iterations in the solution of the matrix eigenvalue problem".
       Quarterly of Applied Mathematics. 9 (1): 17--29.
       https://doi.org/10.1090/qam/42792
networkx.empty_graph
Python Library Documentation: function empty_graph in module networkx.generators.classic

empty_graph(n=0, create_using=None, default=<class 'networkx.classes.graph.Graph'>, *, backend=None, **backend_kwargs)
    Returns the empty graph with n nodes and zero edges.

    .. plot::

        >>> nx.draw(nx.empty_graph(5))

    Parameters
    ----------
    n : int or iterable container of nodes (default = 0)
        If n is an integer, nodes are from `range(n)`.
        If n is a container of nodes, those nodes appear in the graph.
    create_using : Graph Instance, Constructor or None
        Indicator of type of graph to return.
        If a Graph-type instance, then clear and use it.
        If None, use the `default` constructor.
        If a constructor, call it to create an empty graph.
    default : Graph constructor (optional, default = nx.Graph)
        The constructor to use if create_using is None.
        If None, then nx.Graph is used.
        This is used when passing an unknown `create_using` value
        through your home-grown function to `empty_graph` and
        you want a default constructor other than nx.Graph.

    Examples
    --------
    >>> G = nx.empty_graph(10)
    >>> G.number_of_nodes()
    10
    >>> G.number_of_edges()
    0
    >>> G = nx.empty_graph("ABC")
    >>> G.number_of_nodes()
    3
    >>> sorted(G)
    ['A', 'B', 'C']

    Notes
    -----
    The variable create_using should be a Graph Constructor or a
    "graph"-like object. Constructors, e.g. `nx.Graph` or `nx.MultiGraph`
    will be used to create the returned graph. "graph"-like objects
    will be cleared (nodes and edges will be removed) and refitted as
    an empty "graph" with nodes specified in n. This capability
    is useful for specifying the class-nature of the resulting empty
    "graph" (i.e. Graph, DiGraph, MyWeirdGraphClass, etc.).

    The variable create_using has three main uses:
    Firstly, the variable create_using can be used to create an
    empty digraph, multigraph, etc.  For example,

    >>> n = 10
    >>> G = nx.empty_graph(n, create_using=nx.DiGraph)

    will create an empty digraph on n nodes.

    Secondly, one can pass an existing graph (digraph, multigraph,
    etc.) via create_using. For example, if G is an existing graph
    (resp. digraph, multigraph, etc.), then empty_graph(n, create_using=G)
    will empty G (i.e. delete all nodes and edges using G.clear())
    and then add n nodes and zero edges, and return the modified graph.

    Thirdly, when constructing your home-grown graph creation function
    you can use empty_graph to construct the graph by passing a user
    defined create_using to empty_graph. In this case, if you want the
    default constructor to be other than nx.Graph, specify `default`.

    >>> def mygraph(n, create_using=None):
    ...     G = nx.empty_graph(n, create_using, nx.MultiGraph)
    ...     G.add_edges_from([(0, 1), (0, 1)])
    ...     return G
    >>> G = mygraph(3)
    >>> G.is_multigraph()
    True
    >>> G = mygraph(3, nx.Graph)
    >>> G.is_multigraph()
    False

    See also create_empty_copy(G).
networkx.enumerate_all_cliques
Python Library Documentation: function enumerate_all_cliques in module networkx.algorithms.clique

enumerate_all_cliques(G, *, backend=None, **backend_kwargs)
    Returns all cliques in an undirected graph.

    This function returns an iterator over cliques, each of which is a
    list of nodes. The iteration is ordered by cardinality of the
    cliques: first all cliques of size one, then all cliques of size
    two, etc.

    Parameters
    ----------
    G : NetworkX graph
        An undirected graph.

    Returns
    -------
    iterator
        An iterator over cliques, each of which is a list of nodes in
        `G`. The cliques are ordered according to size.

    Notes
    -----
    To obtain a list of all cliques, use
    `list(enumerate_all_cliques(G))`. However, be aware that in the
    worst-case, the length of this list can be exponential in the number
    of nodes in the graph (for example, when the graph is the complete
    graph). This function avoids storing all cliques in memory by only
    keeping current candidate node lists in memory during its search.

    The implementation is adapted from the algorithm by Zhang, et
    al. (2005) [1]_ to output all cliques discovered.

    This algorithm ignores self-loops and parallel edges, since cliques
    are not conventionally defined with such edges.

    References
    ----------
    .. [1] Yun Zhang, Abu-Khzam, F.N., Baldwin, N.E., Chesler, E.J.,
           Langston, M.A., Samatova, N.F.,
           "Genome-Scale Computational Approaches to Memory-Intensive
           Applications in Systems Biology".
           *Supercomputing*, 2005. Proceedings of the ACM/IEEE SC 2005
           Conference, pp. 12, 12--18 Nov. 2005.
           <https://doi.org/10.1109/SC.2005.29>.
networkx.equitable_color
Python Library Documentation: function equitable_color in module networkx.algorithms.coloring.equitable_coloring

equitable_color(G, num_colors, *, backend=None, **backend_kwargs)
    Provides an equitable coloring for nodes of `G`.

    Attempts to color a graph using `num_colors` colors, where no neighbors of
    a node can have same color as the node itself and the number of nodes with
    each color differ by at most 1. `num_colors` must be greater than the
    maximum degree of `G`. The algorithm is described in [1]_ and has
    complexity O(num_colors * n**2).

    Parameters
    ----------
    G : networkX graph
       The nodes of this graph will be colored.

    num_colors : number of colors to use
       This number must be at least one more than the maximum degree of nodes
       in the graph.

    Returns
    -------
    A dictionary with keys representing nodes and values representing
    corresponding coloring.

    Examples
    --------
    >>> G = nx.cycle_graph(4)
    >>> nx.coloring.equitable_color(G, num_colors=3)  # doctest: +SKIP
    {0: 2, 1: 1, 2: 2, 3: 0}

    Raises
    ------
    NetworkXAlgorithmError
        If `num_colors` is not at least the maximum degree of the graph `G`

    References
    ----------
    .. [1] Kierstead, H. A., Kostochka, A. V., Mydlarz, M., & Szemerédi, E.
        (2010). A fast algorithm for equitable coloring. Combinatorica, 30(2),
        217-224.
networkx.equivalence_classes
Python Library Documentation: function equivalence_classes in module networkx.algorithms.minors.contraction

equivalence_classes(iterable, relation)
    Returns equivalence classes of `relation` when applied to `iterable`.

    The equivalence classes, or blocks, consist of objects from `iterable`
    which are all equivalent. They are defined to be equivalent if the
    `relation` function returns `True` when passed any two objects from that
    class, and `False` otherwise. To define an equivalence relation the
    function must be reflexive, symmetric and transitive.

    Parameters
    ----------
    iterable : list, tuple, or set
        An iterable of elements/nodes.

    relation : function
        A Boolean-valued function that implements an equivalence relation
        (reflexive, symmetric, transitive binary relation) on the elements
        of `iterable` - it must take two elements and return `True` if
        they are related, or `False` if not.

    Returns
    -------
    set of frozensets
        A set of frozensets representing the partition induced by the equivalence
        relation function `relation` on the elements of `iterable`. Each
        member set in the return set represents an equivalence class, or
        block, of the partition.

        Duplicate elements will be ignored so it makes the most sense for
        `iterable` to be a :class:`set`.

    Notes
    -----
    This function does not check that `relation` represents an equivalence
    relation. You can check that your equivalence classes provide a partition
    using `is_partition`.

    Examples
    --------
    Let `X` be the set of integers from `0` to `9`, and consider an equivalence
    relation `R` on `X` of congruence modulo `3`: this means that two integers
    `x` and `y` in `X` are equivalent under `R` if they leave the same
    remainder when divided by `3`, i.e. `(x - y) mod 3 = 0`.

    The equivalence classes of this relation are `{0, 3, 6, 9}`, `{1, 4, 7}`,
    `{2, 5, 8}`: `0`, `3`, `6`, `9` are all divisible by `3` and leave zero
    remainder; `1`, `4`, `7` leave remainder `1`; while `2`, `5` and `8` leave
    remainder `2`. We can see this by calling `equivalence_classes` with
    `X` and a function implementation of `R`.

    >>> X = set(range(10))
    >>> def mod3(x, y):
    ...     return (x - y) % 3 == 0
    >>> equivalence_classes(X, mod3)  # doctest: +SKIP
    {frozenset({1, 4, 7}), frozenset({8, 2, 5}), frozenset({0, 9, 3, 6})}
networkx.erdos_renyi_graph
Python Library Documentation: function gnp_random_graph in module networkx.generators.random_graphs

gnp_random_graph(n, p, seed=None, directed=False, *, create_using=None, backend=None, **backend_kwargs)
    Returns a $G_{n,p}$ random graph, also known as an Erdős-Rényi graph
    or a binomial graph.

    The $G_{n,p}$ model chooses each of the possible edges with probability $p$.

    Parameters
    ----------
    n : int
        The number of nodes.
    p : float
        Probability for edge creation.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    directed : bool, optional (default=False)
        If True, this function returns a directed graph.
    create_using : Graph constructor, optional (default=nx.Graph or nx.DiGraph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph types are not supported and raise a ``NetworkXError``.
        By default NetworkX Graph or DiGraph are used depending on `directed`.

    See Also
    --------
    fast_gnp_random_graph

    Notes
    -----
    This algorithm [2]_ runs in $O(n^2)$ time.  For sparse graphs (that is, for
    small values of $p$), :func:`fast_gnp_random_graph` is a faster algorithm.

    :func:`binomial_graph` and :func:`erdos_renyi_graph` are
    aliases for :func:`gnp_random_graph`.

    >>> nx.binomial_graph is nx.gnp_random_graph
    True
    >>> nx.erdos_renyi_graph is nx.gnp_random_graph
    True

    References
    ----------
    .. [1] P. Erdős and A. Rényi, On Random Graphs, Publ. Math. 6, 290 (1959).
    .. [2] E. N. Gilbert, Random Graphs, Ann. Math. Stat., 30, 1141 (1959).
networkx.estrada_index
Python Library Documentation: function estrada_index in module networkx.algorithms.centrality.subgraph_alg

estrada_index(G, *, backend=None, **backend_kwargs)
    Returns the Estrada index of a the graph G.

    The Estrada Index is a topological index of folding or 3D "compactness" ([1]_).

    Parameters
    ----------
    G: graph

    Returns
    -------
    estrada index: float

    Raises
    ------
    NetworkXError
        If the graph is not undirected and simple.

    Notes
    -----
    Let `G=(V,E)` be a simple undirected graph with `n` nodes  and let
    `\lambda_{1}\leq\lambda_{2}\leq\cdots\lambda_{n}`
    be a non-increasing ordering of the eigenvalues of its adjacency
    matrix `A`. The Estrada index is ([1]_, [2]_)

    .. math::
        EE(G)=\sum_{j=1}^n e^{\lambda _j}.

    References
    ----------
    .. [1] E. Estrada, "Characterization of 3D molecular structure",
       Chem. Phys. Lett. 319, 713 (2000).
       https://doi.org/10.1016/S0009-2614(00)00158-5
    .. [2] José Antonio de la Peñaa, Ivan Gutman, Juan Rada,
       "Estimating the Estrada index",
       Linear Algebra and its Applications. 427, 1 (2007).
       https://doi.org/10.1016/j.laa.2007.06.020

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (1, 2), (1, 5), (5, 4), (2, 4), (2, 3), (4, 3), (3, 6)])
    >>> ei = nx.estrada_index(G)
    >>> print(f"{ei:0.5}")
    20.55
networkx.euler
Python Library Documentation: module networkx.algorithms.euler in networkx.algorithms

NAME
    networkx.algorithms.euler - Eulerian circuits and graphs.

FUNCTIONS
    eulerian_circuit(G, source=None, keys=False, *, backend=None, **backend_kwargs)
        Returns an iterator over the edges of an Eulerian circuit in `G`.

        An *Eulerian circuit* is a closed walk that includes each edge of a
        graph exactly once.

        Parameters
        ----------
        G : NetworkX graph
           A graph, either directed or undirected.

        source : node, optional
           Starting node for circuit.

        keys : bool
           If False, edges generated by this function will be of the form
           ``(u, v)``. Otherwise, edges will be of the form ``(u, v, k)``.
           This option is ignored unless `G` is a multigraph.

        Returns
        -------
        edges : iterator
           An iterator over edges in the Eulerian circuit.

        Raises
        ------
        NetworkXError
           If the graph is not Eulerian.

        See Also
        --------
        is_eulerian

        Notes
        -----
        This is a linear time implementation of an algorithm adapted from [1]_.

        For general information about Euler tours, see [2]_.

        References
        ----------
        .. [1] J. Edmonds, E. L. Johnson.
           Matching, Euler tours and the Chinese postman.
           Mathematical programming, Volume 5, Issue 1 (1973), 111-114.
        .. [2] https://en.wikipedia.org/wiki/Eulerian_path

        Examples
        --------
        To get an Eulerian circuit in an undirected graph::

            >>> G = nx.complete_graph(3)
            >>> list(nx.eulerian_circuit(G))
            [(0, 2), (2, 1), (1, 0)]
            >>> list(nx.eulerian_circuit(G, source=1))
            [(1, 2), (2, 0), (0, 1)]

        To get the sequence of vertices in an Eulerian circuit::

            >>> [u for u, v in nx.eulerian_circuit(G)]
            [0, 2, 1]

    eulerian_path(G, source=None, keys=False, *, backend=None, **backend_kwargs)
        Return an iterator over the edges of an Eulerian path in `G`.

        Parameters
        ----------
        G : NetworkX Graph
            The graph in which to look for an eulerian path.
        source : node or None (default: None)
            The node at which to start the search. None means search over all
            starting nodes.
        keys : Bool (default: False)
            Indicates whether to yield edge 3-tuples (u, v, edge_key).
            The default yields edge 2-tuples

        Yields
        ------
        Edge tuples along the eulerian path.

        Warning: If `source` provided is not the start node of an Euler path
        will raise error even if an Euler Path exists.

    eulerize(G, *, backend=None, **backend_kwargs)
        Transforms a graph into an Eulerian graph.

        If `G` is Eulerian the result is `G` as a MultiGraph, otherwise the result is a smallest
        (in terms of the number of edges) multigraph whose underlying simple graph is `G`.

        Parameters
        ----------
        G : NetworkX graph
           An undirected graph

        Returns
        -------
        G : NetworkX multigraph

        Raises
        ------
        NetworkXError
           If the graph is not connected.

        See Also
        --------
        is_eulerian
        eulerian_circuit

        References
        ----------
        .. [1] J. Edmonds, E. L. Johnson.
           Matching, Euler tours and the Chinese postman.
           Mathematical programming, Volume 5, Issue 1 (1973), 111-114.
        .. [2] https://en.wikipedia.org/wiki/Eulerian_path
        .. [3] http://web.math.princeton.edu/math_alive/5/Notes1.pdf

        Examples
        --------
            >>> G = nx.complete_graph(10)
            >>> H = nx.eulerize(G)
            >>> nx.is_eulerian(H)
            True

    has_eulerian_path(G, source=None, *, backend=None, **backend_kwargs)
        Return True iff `G` has an Eulerian path.

        An Eulerian path is a path in a graph which uses each edge of a graph
        exactly once. If `source` is specified, then this function checks
        whether an Eulerian path that starts at node `source` exists.

        A directed graph has an Eulerian path iff:
            - at most one vertex has out_degree - in_degree = 1,
            - at most one vertex has in_degree - out_degree = 1,
            - every other vertex has equal in_degree and out_degree,
            - and all of its vertices belong to a single connected
              component of the underlying undirected graph.

        If `source` is not None, an Eulerian path starting at `source` exists if no
        other node has out_degree - in_degree = 1. This is equivalent to either
        there exists an Eulerian circuit or `source` has out_degree - in_degree = 1
        and the conditions above hold.

        An undirected graph has an Eulerian path iff:
            - exactly zero or two vertices have odd degree,
            - and all of its vertices belong to a single connected component.

        If `source` is not None, an Eulerian path starting at `source` exists if
        either there exists an Eulerian circuit or `source` has an odd degree and the
        conditions above hold.

        Graphs with isolated vertices (i.e. vertices with zero degree) are not considered
        to have an Eulerian path. Therefore, if the graph is not connected (or not strongly
        connected, for directed graphs), this function returns False.

        Parameters
        ----------
        G : NetworkX Graph
            The graph to find an euler path in.

        source : node, optional
            Starting node for path.

        Returns
        -------
        Bool : True if G has an Eulerian path.

        Examples
        --------
        If you prefer to allow graphs with isolated vertices to have Eulerian path,
        you can first remove such vertices and then call `has_eulerian_path` as below example shows.

        >>> G = nx.Graph([(0, 1), (1, 2), (0, 2)])
        >>> G.add_node(3)
        >>> nx.has_eulerian_path(G)
        False

        >>> G.remove_nodes_from(list(nx.isolates(G)))
        >>> nx.has_eulerian_path(G)
        True

        See Also
        --------
        is_eulerian
        eulerian_path

    is_eulerian(G, *, backend=None, **backend_kwargs)
        Returns True if and only if `G` is Eulerian.

        A graph is *Eulerian* if it has an Eulerian circuit. An *Eulerian
        circuit* is a closed walk that includes each edge of a graph exactly
        once.

        Graphs with isolated vertices (i.e. vertices with zero degree) are not
        considered to have Eulerian circuits. Therefore, if the graph is not
        connected (or not strongly connected, for directed graphs), this function
        returns False.

        Parameters
        ----------
        G : NetworkX graph
           A graph, either directed or undirected.

        Examples
        --------
        >>> nx.is_eulerian(nx.DiGraph({0: [3], 1: [2], 2: [3], 3: [0, 1]}))
        True
        >>> nx.is_eulerian(nx.complete_graph(5))
        True
        >>> nx.is_eulerian(nx.petersen_graph())
        False

        If you prefer to allow graphs with isolated vertices to have Eulerian circuits,
        you can first remove such vertices and then call `is_eulerian` as below example shows.

        >>> G = nx.Graph([(0, 1), (1, 2), (0, 2)])
        >>> G.add_node(3)
        >>> nx.is_eulerian(G)
        False

        >>> G.remove_nodes_from(list(nx.isolates(G)))
        >>> nx.is_eulerian(G)
        True

    is_semieulerian(G, *, backend=None, **backend_kwargs)
        Return True iff `G` is semi-Eulerian.

        G is semi-Eulerian if it has an Eulerian path but no Eulerian circuit.

        See Also
        --------
        has_eulerian_path
        is_eulerian

DATA
    __all__ = ['is_eulerian', 'eulerian_circuit', 'eulerize', 'is_semieule...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\euler.py

networkx.eulerian_circuit
Python Library Documentation: function eulerian_circuit in module networkx.algorithms.euler

eulerian_circuit(G, source=None, keys=False, *, backend=None, **backend_kwargs)
    Returns an iterator over the edges of an Eulerian circuit in `G`.

    An *Eulerian circuit* is a closed walk that includes each edge of a
    graph exactly once.

    Parameters
    ----------
    G : NetworkX graph
       A graph, either directed or undirected.

    source : node, optional
       Starting node for circuit.

    keys : bool
       If False, edges generated by this function will be of the form
       ``(u, v)``. Otherwise, edges will be of the form ``(u, v, k)``.
       This option is ignored unless `G` is a multigraph.

    Returns
    -------
    edges : iterator
       An iterator over edges in the Eulerian circuit.

    Raises
    ------
    NetworkXError
       If the graph is not Eulerian.

    See Also
    --------
    is_eulerian

    Notes
    -----
    This is a linear time implementation of an algorithm adapted from [1]_.

    For general information about Euler tours, see [2]_.

    References
    ----------
    .. [1] J. Edmonds, E. L. Johnson.
       Matching, Euler tours and the Chinese postman.
       Mathematical programming, Volume 5, Issue 1 (1973), 111-114.
    .. [2] https://en.wikipedia.org/wiki/Eulerian_path

    Examples
    --------
    To get an Eulerian circuit in an undirected graph::

        >>> G = nx.complete_graph(3)
        >>> list(nx.eulerian_circuit(G))
        [(0, 2), (2, 1), (1, 0)]
        >>> list(nx.eulerian_circuit(G, source=1))
        [(1, 2), (2, 0), (0, 1)]

    To get the sequence of vertices in an Eulerian circuit::

        >>> [u for u, v in nx.eulerian_circuit(G)]
        [0, 2, 1]
networkx.eulerian_path
Python Library Documentation: function eulerian_path in module networkx.algorithms.euler

eulerian_path(G, source=None, keys=False, *, backend=None, **backend_kwargs)
    Return an iterator over the edges of an Eulerian path in `G`.

    Parameters
    ----------
    G : NetworkX Graph
        The graph in which to look for an eulerian path.
    source : node or None (default: None)
        The node at which to start the search. None means search over all
        starting nodes.
    keys : Bool (default: False)
        Indicates whether to yield edge 3-tuples (u, v, edge_key).
        The default yields edge 2-tuples

    Yields
    ------
    Edge tuples along the eulerian path.

    Warning: If `source` provided is not the start node of an Euler path
    will raise error even if an Euler Path exists.
networkx.eulerize
Python Library Documentation: function eulerize in module networkx.algorithms.euler

eulerize(G, *, backend=None, **backend_kwargs)
    Transforms a graph into an Eulerian graph.

    If `G` is Eulerian the result is `G` as a MultiGraph, otherwise the result is a smallest
    (in terms of the number of edges) multigraph whose underlying simple graph is `G`.

    Parameters
    ----------
    G : NetworkX graph
       An undirected graph

    Returns
    -------
    G : NetworkX multigraph

    Raises
    ------
    NetworkXError
       If the graph is not connected.

    See Also
    --------
    is_eulerian
    eulerian_circuit

    References
    ----------
    .. [1] J. Edmonds, E. L. Johnson.
       Matching, Euler tours and the Chinese postman.
       Mathematical programming, Volume 5, Issue 1 (1973), 111-114.
    .. [2] https://en.wikipedia.org/wiki/Eulerian_path
    .. [3] http://web.math.princeton.edu/math_alive/5/Notes1.pdf

    Examples
    --------
        >>> G = nx.complete_graph(10)
        >>> H = nx.eulerize(G)
        >>> nx.is_eulerian(H)
        True
networkx.exception
Python Library Documentation: module networkx.exception in networkx

NAME
    networkx.exception

DESCRIPTION
    **********
    Exceptions
    **********

    Base exceptions and errors for NetworkX.

CLASSES
    builtins.Exception(builtins.BaseException)
        NetworkXException
            AmbiguousSolution
            ExceededMaxIterations
                PowerIterationFailedConvergence
            HasACycle
            NetworkXAlgorithmError
                NetworkXUnbounded
                NetworkXUnfeasible
                    NetworkXNoCycle
                    NetworkXNoPath
            NetworkXError
            NetworkXNotImplemented
            NetworkXPointlessConcept
            NodeNotFound

    class AmbiguousSolution(NetworkXException)
     |  Raised if more than one valid solution exists for an intermediary step
     |  of an algorithm.
     |
     |  In the face of ambiguity, refuse the temptation to guess.
     |  This may occur, for example, when trying to determine the
     |  bipartite node sets in a disconnected bipartite graph when
     |  computing bipartite matchings.
     |
     |  Method resolution order:
     |      AmbiguousSolution
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class ExceededMaxIterations(NetworkXException)
     |  Raised if a loop iterates too many times without breaking.
     |
     |  This may occur, for example, in an algorithm that computes
     |  progressively better approximations to a value but exceeds an
     |  iteration bound specified by the user.
     |
     |  Method resolution order:
     |      ExceededMaxIterations
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class HasACycle(NetworkXException)
     |  Raised if a graph has a cycle when an algorithm expects that it
     |  will have no cycles.
     |
     |  Method resolution order:
     |      HasACycle
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class NetworkXAlgorithmError(NetworkXException)
     |  Exception for unexpected termination of algorithms.
     |
     |  Method resolution order:
     |      NetworkXAlgorithmError
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class NetworkXError(NetworkXException)
     |  Exception for a serious error in NetworkX
     |
     |  Method resolution order:
     |      NetworkXError
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class NetworkXException(builtins.Exception)
     |  Base class for exceptions in NetworkX.
     |
     |  Method resolution order:
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors defined here:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class NetworkXNoCycle(NetworkXUnfeasible)
     |  Exception for algorithms that should return a cycle when running
     |  on graphs where such a cycle does not exist.
     |
     |  Method resolution order:
     |      NetworkXNoCycle
     |      NetworkXUnfeasible
     |      NetworkXAlgorithmError
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class NetworkXNoPath(NetworkXUnfeasible)
     |  Exception for algorithms that should return a path when running
     |  on graphs where such a path does not exist.
     |
     |  Method resolution order:
     |      NetworkXNoPath
     |      NetworkXUnfeasible
     |      NetworkXAlgorithmError
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class NetworkXNotImplemented(NetworkXException)
     |  Exception raised by algorithms not implemented for a type of graph.
     |
     |  Method resolution order:
     |      NetworkXNotImplemented
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class NetworkXPointlessConcept(NetworkXException)
     |  Raised when a null graph is provided as input to an algorithm
     |  that cannot use it.
     |
     |  The null graph is sometimes considered a pointless concept [1]_,
     |  thus the name of the exception.
     |
     |  Notes
     |  -----
     |  Null graphs and empty graphs are often used interchangeably but they
     |  are well defined in NetworkX. An ``empty_graph`` is a graph with ``n`` nodes
     |  and 0 edges, and a ``null_graph`` is a graph with 0 nodes and 0 edges.
     |
     |  References
     |  ----------
     |  .. [1] Harary, F. and Read, R. "Is the Null Graph a Pointless
     |     Concept?"  In Graphs and Combinatorics Conference, George
     |     Washington University.  New York: Springer-Verlag, 1973.
     |
     |  Method resolution order:
     |      NetworkXPointlessConcept
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class NetworkXUnbounded(NetworkXAlgorithmError)
     |  Exception raised by algorithms trying to solve a maximization
     |  or a minimization problem instance that is unbounded.
     |
     |  Method resolution order:
     |      NetworkXUnbounded
     |      NetworkXAlgorithmError
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class NetworkXUnfeasible(NetworkXAlgorithmError)
     |  Exception raised by algorithms trying to solve a problem
     |  instance that has no feasible solution.
     |
     |  Method resolution order:
     |      NetworkXUnfeasible
     |      NetworkXAlgorithmError
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class NodeNotFound(NetworkXException)
     |  Exception raised if requested node is not present in the graph
     |
     |  Method resolution order:
     |      NodeNotFound
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.Exception:
     |
     |  __init__(self, /, *args, **kwargs)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

    class PowerIterationFailedConvergence(ExceededMaxIterations)
     |  PowerIterationFailedConvergence(num_iterations, *args, **kw)
     |
     |  Raised when the power iteration method fails to converge within a
     |  specified iteration limit.
     |
     |  `num_iterations` is the number of iterations that have been
     |  completed when this exception was raised.
     |
     |  Method resolution order:
     |      PowerIterationFailedConvergence
     |      ExceededMaxIterations
     |      NetworkXException
     |      builtins.Exception
     |      builtins.BaseException
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __init__(self, num_iterations, *args, **kw)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from NetworkXException:
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Static methods inherited from builtins.Exception:
     |
     |  __new__(*args, **kwargs) class method of builtins.Exception
     |      Create and return a new object.  See help(type) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from builtins.BaseException:
     |
     |  __getattribute__(self, name, /)
     |      Return getattr(self, name).
     |
     |  __reduce__(...)
     |      Helper for pickle.
     |
     |  __repr__(self, /)
     |      Return repr(self).
     |
     |  __setstate__(...)
     |
     |  __str__(self, /)
     |      Return str(self).
     |
     |  add_note(...)
     |      Exception.add_note(note) --
     |      add a note to the exception
     |
     |  with_traceback(...)
     |      Exception.with_traceback(tb) --
     |      set self.__traceback__ to tb and return self.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from builtins.BaseException:
     |
     |  __cause__
     |      exception cause
     |
     |  __context__
     |      exception context
     |
     |  __dict__
     |
     |  __suppress_context__
     |
     |  __traceback__
     |
     |  args

DATA
    __all__ = ['HasACycle', 'NodeNotFound', 'PowerIterationFailedConvergen...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\exception.py

networkx.expanders
Python Library Documentation: module networkx.generators.expanders in networkx.generators

NAME
    networkx.generators.expanders - Provides explicit constructions of expander graphs.

FUNCTIONS
    chordal_cycle_graph(p, create_using=None, *, backend=None, **backend_kwargs)
        Returns the chordal cycle graph on `p` nodes.

        The returned graph is a cycle graph on `p` nodes with chords joining each
        vertex `x` to its inverse modulo `p`. This graph is a (mildly explicit)
        3-regular expander [1]_.

        `p` *must* be a prime number.

        Parameters
        ----------
        p : a prime number

            The number of vertices in the graph. This also indicates where the
            chordal edges in the cycle will be created.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : graph
            The constructed undirected multigraph.

        Raises
        ------
        NetworkXError

            If `create_using` indicates directed or not a multigraph.

        References
        ----------

        .. [1] Theorem 4.4.2 in A. Lubotzky. "Discrete groups, expanding graphs and
               invariant measures", volume 125 of Progress in Mathematics.
               Birkhäuser Verlag, Basel, 1994.

    is_regular_expander(G, *, epsilon=0, backend=None, **backend_kwargs)
        Determines whether the graph G is a regular expander. [1]_

        An expander graph is a sparse graph with strong connectivity properties.

        More precisely, this helper checks whether the graph is a
        regular $(n, d, \lambda)$-expander with $\lambda$ close to
        the Alon-Boppana bound and given by
        $\lambda = 2 \sqrt{d - 1} + \epsilon$. [2]_

        In the case where $\epsilon = 0$ then if the graph successfully passes the test
        it is a Ramanujan graph. [3]_

        A Ramanujan graph has spectral gap almost as large as possible, which makes them
        excellent expanders.

        Parameters
        ----------
        G : NetworkX graph
        epsilon : int, float, default=0

        Returns
        -------
        bool
            Whether the given graph is a regular $(n, d, \lambda)$-expander
            where $\lambda = 2 \sqrt{d - 1} + \epsilon$.

        Examples
        --------
        >>> G = nx.random_regular_expander_graph(20, 4)
        >>> nx.is_regular_expander(G)
        True

        See Also
        --------
        maybe_regular_expander
        random_regular_expander_graph

        References
        ----------
        .. [1] Expander graph, https://en.wikipedia.org/wiki/Expander_graph
        .. [2] Alon-Boppana bound, https://en.wikipedia.org/wiki/Alon%E2%80%93Boppana_bound
        .. [3] Ramanujan graphs, https://en.wikipedia.org/wiki/Ramanujan_graph

    margulis_gabber_galil_graph(n, create_using=None, *, backend=None, **backend_kwargs)
        Returns the Margulis-Gabber-Galil undirected MultiGraph on `n^2` nodes.

        The undirected MultiGraph is regular with degree `8`. Nodes are integer
        pairs. The second-largest eigenvalue of the adjacency matrix of the graph
        is at most `5 \sqrt{2}`, regardless of `n`.

        Parameters
        ----------
        n : int
            Determines the number of nodes in the graph: `n^2`.
        create_using : NetworkX graph constructor, optional (default MultiGraph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : graph
            The constructed undirected multigraph.

        Raises
        ------
        NetworkXError
            If the graph is directed or not a multigraph.

    maybe_regular_expander(n, d, *, create_using=None, max_tries=100, seed=None, backend=None, **backend_kwargs)
        Utility for creating a random regular expander.

        Returns a random $d$-regular graph on $n$ nodes which is an expander
        graph with very good probability.

        Parameters
        ----------
        n : int
          The number of nodes.
        d : int
          The degree of each node.
        create_using : Graph Instance or Constructor
          Indicator of type of graph to return.
          If a Graph-type instance, then clear and use it.
          If a constructor, call it to create an empty graph.
          Use the Graph constructor by default.
        max_tries : int. (default: 100)
          The number of allowed loops when generating each independent cycle
        seed : (default: None)
          Seed used to set random number generation state. See :ref`Randomness<randomness>`.

        Notes
        -----
        The nodes are numbered from $0$ to $n - 1$.

        The graph is generated by taking $d / 2$ random independent cycles.

        Joel Friedman proved that in this model the resulting
        graph is an expander with probability
        $1 - O(n^{-\tau})$ where $\tau = \lceil (\sqrt{d - 1}) / 2 \rceil - 1$. [1]_

        Examples
        --------
        >>> G = nx.maybe_regular_expander(n=200, d=6, seed=8020)

        Returns
        -------
        G : graph
            The constructed undirected graph.

        Raises
        ------
        NetworkXError
            If $d % 2 != 0$ as the degree must be even.
            If $n - 1$ is less than $ 2d $ as the graph is complete at most.
            If max_tries is reached

        See Also
        --------
        is_regular_expander
        random_regular_expander_graph

        References
        ----------
        .. [1] Joel Friedman,
           A Proof of Alon’s Second Eigenvalue Conjecture and Related Problems, 2004
           https://arxiv.org/abs/cs/0405020

    paley_graph(p, create_using=None, *, backend=None, **backend_kwargs)
        Returns the Paley $\frac{(p-1)}{2}$ -regular graph on $p$ nodes.

        The returned graph is a graph on $\mathbb{Z}/p\mathbb{Z}$ with edges between $x$ and $y$
        if and only if $x-y$ is a nonzero square in $\mathbb{Z}/p\mathbb{Z}$.

        If $p \equiv 1  \pmod 4$, $-1$ is a square in $\mathbb{Z}/p\mathbb{Z}$ and therefore $x-y$ is a square if and
        only if $y-x$ is also a square, i.e the edges in the Paley graph are symmetric.

        If $p \equiv 3 \pmod 4$, $-1$ is not a square in $\mathbb{Z}/p\mathbb{Z}$ and therefore either $x-y$ or $y-x$
        is a square in $\mathbb{Z}/p\mathbb{Z}$ but not both.

        Note that a more general definition of Paley graphs extends this construction
        to graphs over $q=p^n$ vertices, by using the finite field $F_q$ instead of $\mathbb{Z}/p\mathbb{Z}$.
        This construction requires to compute squares in general finite fields and is
        not what is implemented here (i.e `paley_graph(25)` does not return the true
        Paley graph associated with $5^2$).

        Parameters
        ----------
        p : int, an odd prime number.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : graph
            The constructed directed graph.

        Raises
        ------
        NetworkXError
            If the graph is a multigraph.

        References
        ----------
        Chapter 13 in B. Bollobas, Random Graphs. Second edition.
        Cambridge Studies in Advanced Mathematics, 73.
        Cambridge University Press, Cambridge (2001).

    random_regular_expander_graph(n, d, *, epsilon=0, create_using=None, max_tries=100, seed=None, backend=None, **backend_kwargs)
        Returns a random regular expander graph on $n$ nodes with degree $d$.

        An expander graph is a sparse graph with strong connectivity properties. [1]_

        More precisely the returned graph is a $(n, d, \lambda)$-expander with
        $\lambda = 2 \sqrt{d - 1} + \epsilon$, close to the Alon-Boppana bound. [2]_

        In the case where $\epsilon = 0$ it returns a Ramanujan graph.
        A Ramanujan graph has spectral gap almost as large as possible,
        which makes them excellent expanders. [3]_

        Parameters
        ----------
        n : int
          The number of nodes.
        d : int
          The degree of each node.
        epsilon : int, float, default=0
        max_tries : int, (default: 100)
          The number of allowed loops, also used in the maybe_regular_expander utility
        seed : (default: None)
          Seed used to set random number generation state. See :ref`Randomness<randomness>`.

        Raises
        ------
        NetworkXError
            If max_tries is reached

        Examples
        --------
        >>> G = nx.random_regular_expander_graph(20, 4)
        >>> nx.is_regular_expander(G)
        True

        Notes
        -----
        This loops over `maybe_regular_expander` and can be slow when
        $n$ is too big or $\epsilon$ too small.

        See Also
        --------
        maybe_regular_expander
        is_regular_expander

        References
        ----------
        .. [1] Expander graph, https://en.wikipedia.org/wiki/Expander_graph
        .. [2] Alon-Boppana bound, https://en.wikipedia.org/wiki/Alon%E2%80%93Boppana_bound
        .. [3] Ramanujan graphs, https://en.wikipedia.org/wiki/Ramanujan_graph

DATA
    __all__ = ['margulis_gabber_galil_graph', 'chordal_cycle_graph', 'pale...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\expanders.py

networkx.expected_degree_graph
Python Library Documentation: function expected_degree_graph in module networkx.generators.degree_seq

expected_degree_graph(w, seed=None, selfloops=True, *, backend=None, **backend_kwargs)
    Returns a random graph with given expected degrees.

    Given a sequence of expected degrees $W=(w_0,w_1,\ldots,w_{n-1})$
    of length $n$ this algorithm assigns an edge between node $u$ and
    node $v$ with probability

    .. math::

       p_{uv} = \frac{w_u w_v}{\sum_k w_k} .

    Parameters
    ----------
    w : list
        The list of expected degrees.
    selfloops: bool (default=True)
        Set to False to remove the possibility of self-loop edges.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    Graph

    Examples
    --------
    >>> z = [10 for i in range(100)]
    >>> G = nx.expected_degree_graph(z)

    Notes
    -----
    The nodes have integer labels corresponding to index of expected degrees
    input sequence.

    The complexity of this algorithm is $\mathcal{O}(n+m)$ where $n$ is the
    number of nodes and $m$ is the expected number of edges.

    The model in [1]_ includes the possibility of self-loop edges.
    Set selfloops=False to produce a graph without self loops.

    For finite graphs this model doesn't produce exactly the given
    expected degree sequence.  Instead the expected degrees are as
    follows.

    For the case without self loops (selfloops=False),

    .. math::

       E[deg(u)] = \sum_{v \ne u} p_{uv}
                = w_u \left( 1 - \frac{w_u}{\sum_k w_k} \right) .


    NetworkX uses the standard convention that a self-loop edge counts 2
    in the degree of a node, so with self loops (selfloops=True),

    .. math::

       E[deg(u)] =  \sum_{v \ne u} p_{uv}  + 2 p_{uu}
                = w_u \left( 1 + \frac{w_u}{\sum_k w_k} \right) .

    References
    ----------
    .. [1] Fan Chung and L. Lu, Connected components in random graphs with
       given expected degree sequences, Ann. Combinatorics, 6,
       pp. 125-145, 2002.
    .. [2] Joel Miller and Aric Hagberg,
       Efficient generation of networks with given expected degrees,
       in Algorithms and Models for the Web-Graph (WAW 2011),
       Alan Frieze, Paul Horn, and Paweł Prałat (Eds), LNCS 6732,
       pp. 115-126, 2011.
networkx.extended_barabasi_albert_graph
Python Library Documentation: function extended_barabasi_albert_graph in module networkx.generators.random_graphs

extended_barabasi_albert_graph(n, m, p, q, seed=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns an extended Barabási–Albert model graph.

    An extended Barabási–Albert model graph is a random graph constructed
    using preferential attachment. The extended model allows new edges,
    rewired edges or new nodes. Based on the probabilities $p$ and $q$
    with $p + q < 1$, the growing behavior of the graph is determined as:

    1) With $p$ probability, $m$ new edges are added to the graph,
    starting from randomly chosen existing nodes and attached preferentially at the
    other end.

    2) With $q$ probability, $m$ existing edges are rewired
    by randomly choosing an edge and rewiring one end to a preferentially chosen node.

    3) With $(1 - p - q)$ probability, $m$ new nodes are added to the graph
    with edges attached preferentially.

    When $p = q = 0$, the model behaves just like the Barabási–Alber model.

    Parameters
    ----------
    n : int
        Number of nodes
    m : int
        Number of edges with which a new node attaches to existing nodes
    p : float
        Probability value for adding an edge between existing nodes. p + q < 1
    q : float
        Probability value of rewiring of existing edges. p + q < 1
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Returns
    -------
    G : Graph

    Raises
    ------
    NetworkXError
        If `m` does not satisfy ``1 <= m < n`` or ``1 >= p + q``

    References
    ----------
    .. [1] Albert, R., & Barabási, A. L. (2000)
       Topology of evolving networks: local events and universality
       Physical review letters, 85(24), 5234.
networkx.fast_could_be_isomorphic
Python Library Documentation: function fast_could_be_isomorphic in module networkx.algorithms.isomorphism.isomorph

fast_could_be_isomorphic(G1, G2, *, backend=None, **backend_kwargs)
    Returns False if graphs are definitely not isomorphic.

    True does NOT guarantee isomorphism.

    Parameters
    ----------
    G1, G2 : graphs
       The two graphs G1 and G2 must be the same type.

    Notes
    -----
    Checks for matching degree and triangle sequences. The triangle
    sequence contains the number of triangles each node is part of.
networkx.fast_gnp_random_graph
Python Library Documentation: function fast_gnp_random_graph in module networkx.generators.random_graphs

fast_gnp_random_graph(n, p, seed=None, directed=False, *, create_using=None, backend=None, **backend_kwargs)
    Returns a $G_{n,p}$ random graph, also known as an Erdős-Rényi graph or
    a binomial graph.

    Parameters
    ----------
    n : int
        The number of nodes.
    p : float
        Probability for edge creation.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    directed : bool, optional (default=False)
        If True, this function returns a directed graph.
    create_using : Graph constructor, optional (default=nx.Graph or nx.DiGraph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph types are not supported and raise a ``NetworkXError``.
        By default NetworkX Graph or DiGraph are used depending on `directed`.

    Notes
    -----
    The $G_{n,p}$ graph algorithm chooses each of the $[n (n - 1)] / 2$
    (undirected) or $n (n - 1)$ (directed) possible edges with probability $p$.

    This algorithm [1]_ runs in $O(n + m)$ time, where `m` is the expected number of
    edges, which equals $p n (n - 1) / 2$. This should be faster than
    :func:`gnp_random_graph` when $p$ is small and the expected number of edges
    is small (that is, the graph is sparse).

    See Also
    --------
    gnp_random_graph

    References
    ----------
    .. [1] Vladimir Batagelj and Ulrik Brandes,
       "Efficient generation of large random networks",
       Phys. Rev. E, 71, 036113, 2005.
networkx.faster_could_be_isomorphic
Python Library Documentation: function faster_could_be_isomorphic in module networkx.algorithms.isomorphism.isomorph

faster_could_be_isomorphic(G1, G2, *, backend=None, **backend_kwargs)
    Returns False if graphs are definitely not isomorphic.

    True does NOT guarantee isomorphism.

    Parameters
    ----------
    G1, G2 : graphs
       The two graphs G1 and G2 must be the same type.

    Notes
    -----
    Checks for matching degree sequences.
networkx.fiedler_vector
Python Library Documentation: function fiedler_vector in module networkx.linalg.algebraicconnectivity

fiedler_vector(G, weight='weight', normalized=False, tol=1e-08, method='tracemin_pcg', seed=None, *, backend=None, **backend_kwargs)
    Returns the Fiedler vector of a connected undirected graph.

    The Fiedler vector of a connected undirected graph is the eigenvector
    corresponding to the second smallest eigenvalue of the Laplacian matrix
    of the graph.

    Parameters
    ----------
    G : NetworkX graph
        An undirected graph.

    weight : object, optional (default: None)
        The data key used to determine the weight of each edge. If None, then
        each edge has unit weight.

    normalized : bool, optional (default: False)
        Whether the normalized Laplacian matrix is used.

    tol : float, optional (default: 1e-8)
        Tolerance of relative residual in eigenvalue computation.

    method : string, optional (default: 'tracemin_pcg')
        Method of eigenvalue computation. It must be one of the tracemin
        options shown below (TraceMIN), 'lanczos' (Lanczos iteration)
        or 'lobpcg' (LOBPCG).

        The TraceMIN algorithm uses a linear system solver. The following
        values allow specifying the solver to be used.

        =============== ========================================
        Value           Solver
        =============== ========================================
        'tracemin_pcg'  Preconditioned conjugate gradient method
        'tracemin_lu'   LU factorization
        =============== ========================================

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    fiedler_vector : NumPy array of floats.
        Fiedler vector.

    Raises
    ------
    NetworkXNotImplemented
        If G is directed.

    NetworkXError
        If G has less than two nodes or is not connected.

    Notes
    -----
    Edge weights are interpreted by their absolute values. For MultiGraph's,
    weights of parallel edges are summed. Zero-weighted edges are ignored.

    See Also
    --------
    laplacian_matrix

    Examples
    --------
    Given a connected graph the signs of the values in the Fiedler vector can be
    used to partition the graph into two components.

    >>> G = nx.barbell_graph(5, 0)
    >>> nx.fiedler_vector(G, normalized=True, seed=1)
    array([-0.32864129, -0.32864129, -0.32864129, -0.32864129, -0.26072899,
            0.26072899,  0.32864129,  0.32864129,  0.32864129,  0.32864129])

    The connected components are the two 5-node cliques of the barbell graph.
networkx.filters
Python Library Documentation: module networkx.classes.filters in networkx.classes

NAME
    networkx.classes.filters - Filter factories to hide or show sets of nodes and edges.

DESCRIPTION
    These filters return the function used when creating `SubGraph`.

CLASSES
    builtins.object
        show_nodes

    class show_nodes(builtins.object)
     |  show_nodes(nodes)
     |
     |  Filter class to show specific nodes.
     |
     |  Attach the set of nodes as an attribute to speed up this commonly used filter
     |
     |  Note that another allowed attribute for filters is to store the number of nodes
     |  on the filter as attribute `length` (used in `__len__`). It is a user
     |  responsibility to ensure this attribute is accurate if present.
     |
     |  Methods defined here:
     |
     |  __call__(self, node)
     |      Call self as a function.
     |
     |  __init__(self, nodes)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors defined here:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

FUNCTIONS
    hide_diedges(edges)
        Returns a filter function that hides specific directed edges.

    hide_edges(edges)
        Returns a filter function that hides specific undirected edges.

    hide_multidiedges(edges)
        Returns a filter function that hides specific multi-directed edges.

    hide_multiedges(edges)
        Returns a filter function that hides specific multi-undirected edges.

    hide_nodes(nodes)
        Returns a filter function that hides specific nodes.

    no_filter(*items)
        Returns a filter function that always evaluates to True.

    show_diedges(edges)
        Returns a filter function that shows specific directed edges.

    show_edges(edges)
        Returns a filter function that shows specific undirected edges.

    show_multidiedges(edges)
        Returns a filter function that shows specific multi-directed edges.

    show_multiedges(edges)
        Returns a filter function that shows specific multi-undirected edges.

DATA
    __all__ = ['no_filter', 'hide_nodes', 'hide_edges', 'hide_multiedges',...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\classes\filters.py

networkx.find_asteroidal_triple
Python Library Documentation: function find_asteroidal_triple in module networkx.algorithms.asteroidal

find_asteroidal_triple(G, *, backend=None, **backend_kwargs)
    Find an asteroidal triple in the given graph.

    An asteroidal triple is a triple of non-adjacent vertices such that
    there exists a path between any two of them which avoids the closed
    neighborhood of the third. It checks all independent triples of vertices
    and whether they are an asteroidal triple or not. This is done with the
    help of a data structure called a component structure.
    A component structure encodes information about which vertices belongs to
    the same connected component when the closed neighborhood of a given vertex
    is removed from the graph. The algorithm used to check is the trivial
    one, outlined in [1]_, which has a runtime of
    :math:`O(|V||\overline{E} + |V||E|)`, where the second term is the
    creation of the component structure.

    Parameters
    ----------
    G : NetworkX Graph
        The graph to check whether is AT-free or not

    Returns
    -------
    list or None
        An asteroidal triple is returned as a list of nodes. If no asteroidal
        triple exists, i.e. the graph is AT-free, then None is returned.
        The returned value depends on the certificate parameter. The default
        option is a bool which is True if the graph is AT-free, i.e. the
        given graph contains no asteroidal triples, and False otherwise, i.e.
        if the graph contains at least one asteroidal triple.

    Notes
    -----
    The component structure and the algorithm is described in [1]_. The current
    implementation implements the trivial algorithm for simple graphs.

    References
    ----------
    .. [1] Ekkehard Köhler,
       "Recognizing Graphs without asteroidal triples",
       Journal of Discrete Algorithms 2, pages 439-452, 2004.
       https://www.sciencedirect.com/science/article/pii/S157086670400019X
networkx.find_cliques
Python Library Documentation: function find_cliques in module networkx.algorithms.clique

find_cliques(G, nodes=None, *, backend=None, **backend_kwargs)
    Returns all maximal cliques in an undirected graph.

    For each node *n*, a *maximal clique for n* is a largest complete
    subgraph containing *n*. The largest maximal clique is sometimes
    called the *maximum clique*.

    This function returns an iterator over cliques, each of which is a
    list of nodes. It is an iterative implementation, so should not
    suffer from recursion depth issues.

    This function accepts a list of `nodes` and only the maximal cliques
    containing all of these `nodes` are returned. It can considerably speed up
    the running time if some specific cliques are desired.

    Parameters
    ----------
    G : NetworkX graph
        An undirected graph.

    nodes : list, optional (default=None)
        If provided, only yield *maximal cliques* containing all nodes in `nodes`.
        If `nodes` isn't a clique itself, a ValueError is raised.

    Returns
    -------
    iterator
        An iterator over maximal cliques, each of which is a list of
        nodes in `G`. If `nodes` is provided, only the maximal cliques
        containing all the nodes in `nodes` are returned. The order of
        cliques is arbitrary.

    Raises
    ------
    ValueError
        If `nodes` is not a clique.

    Examples
    --------
    >>> from pprint import pprint  # For nice dict formatting
    >>> G = nx.karate_club_graph()
    >>> sum(1 for c in nx.find_cliques(G))  # The number of maximal cliques in G
    36
    >>> max(nx.find_cliques(G), key=len)  # The largest maximal clique in G
    [0, 1, 2, 3, 13]

    The size of the largest maximal clique is known as the *clique number* of
    the graph, which can be found directly with:

    >>> max(len(c) for c in nx.find_cliques(G))
    5

    One can also compute the number of maximal cliques in `G` that contain a given
    node. The following produces a dictionary keyed by node whose
    values are the number of maximal cliques in `G` that contain the node:

    >>> pprint({n: sum(1 for c in nx.find_cliques(G) if n in c) for n in G})
    {0: 13,
     1: 6,
     2: 7,
     3: 3,
     4: 2,
     5: 3,
     6: 3,
     7: 1,
     8: 3,
     9: 2,
     10: 2,
     11: 1,
     12: 1,
     13: 2,
     14: 1,
     15: 1,
     16: 1,
     17: 1,
     18: 1,
     19: 2,
     20: 1,
     21: 1,
     22: 1,
     23: 3,
     24: 2,
     25: 2,
     26: 1,
     27: 3,
     28: 2,
     29: 2,
     30: 2,
     31: 4,
     32: 9,
     33: 14}

    Or, similarly, the maximal cliques in `G` that contain a given node.
    For example, the 4 maximal cliques that contain node 31:

    >>> [c for c in nx.find_cliques(G) if 31 in c]
    [[0, 31], [33, 32, 31], [33, 28, 31], [24, 25, 31]]

    See Also
    --------
    find_cliques_recursive
        A recursive version of the same algorithm.

    Notes
    -----
    To obtain a list of all maximal cliques, use
    `list(find_cliques(G))`. However, be aware that in the worst-case,
    the length of this list can be exponential in the number of nodes in
    the graph. This function avoids storing all cliques in memory by
    only keeping current candidate node lists in memory during its search.

    This implementation is based on the algorithm published by Bron and
    Kerbosch (1973) [1]_, as adapted by Tomita, Tanaka and Takahashi
    (2006) [2]_ and discussed in Cazals and Karande (2008) [3]_. It
    essentially unrolls the recursion used in the references to avoid
    issues of recursion stack depth (for a recursive implementation, see
    :func:`find_cliques_recursive`).

    This algorithm ignores self-loops and parallel edges, since cliques
    are not conventionally defined with such edges.

    References
    ----------
    .. [1] Bron, C. and Kerbosch, J.
       "Algorithm 457: finding all cliques of an undirected graph".
       *Communications of the ACM* 16, 9 (Sep. 1973), 575--577.
       <http://portal.acm.org/citation.cfm?doid=362342.362367>

    .. [2] Etsuji Tomita, Akira Tanaka, Haruhisa Takahashi,
       "The worst-case time complexity for generating all maximal
       cliques and computational experiments",
       *Theoretical Computer Science*, Volume 363, Issue 1,
       Computing and Combinatorics,
       10th Annual International Conference on
       Computing and Combinatorics (COCOON 2004), 25 October 2006, Pages 28--42
       <https://doi.org/10.1016/j.tcs.2006.06.015>

    .. [3] F. Cazals, C. Karande,
       "A note on the problem of reporting maximal cliques",
       *Theoretical Computer Science*,
       Volume 407, Issues 1--3, 6 November 2008, Pages 564--568,
       <https://doi.org/10.1016/j.tcs.2008.05.010>
networkx.find_cliques_recursive
Python Library Documentation: function find_cliques_recursive in module networkx.algorithms.clique

find_cliques_recursive(G, nodes=None, *, backend=None, **backend_kwargs)
    Returns all maximal cliques in a graph.

    For each node *v*, a *maximal clique for v* is a largest complete
    subgraph containing *v*. The largest maximal clique is sometimes
    called the *maximum clique*.

    This function returns an iterator over cliques, each of which is a
    list of nodes. It is a recursive implementation, so may suffer from
    recursion depth issues, but is included for pedagogical reasons.
    For a non-recursive implementation, see :func:`find_cliques`.

    This function accepts a list of `nodes` and only the maximal cliques
    containing all of these `nodes` are returned. It can considerably speed up
    the running time if some specific cliques are desired.

    Parameters
    ----------
    G : NetworkX graph

    nodes : list, optional (default=None)
        If provided, only yield *maximal cliques* containing all nodes in `nodes`.
        If `nodes` isn't a clique itself, a ValueError is raised.

    Returns
    -------
    iterator
        An iterator over maximal cliques, each of which is a list of
        nodes in `G`. If `nodes` is provided, only the maximal cliques
        containing all the nodes in `nodes` are yielded. The order of
        cliques is arbitrary.

    Raises
    ------
    ValueError
        If `nodes` is not a clique.

    See Also
    --------
    find_cliques
        An iterative version of the same algorithm. See docstring for examples.

    Notes
    -----
    To obtain a list of all maximal cliques, use
    `list(find_cliques_recursive(G))`. However, be aware that in the
    worst-case, the length of this list can be exponential in the number
    of nodes in the graph. This function avoids storing all cliques in memory
    by only keeping current candidate node lists in memory during its search.

    This implementation is based on the algorithm published by Bron and
    Kerbosch (1973) [1]_, as adapted by Tomita, Tanaka and Takahashi
    (2006) [2]_ and discussed in Cazals and Karande (2008) [3]_. For a
    non-recursive implementation, see :func:`find_cliques`.

    This algorithm ignores self-loops and parallel edges, since cliques
    are not conventionally defined with such edges.

    References
    ----------
    .. [1] Bron, C. and Kerbosch, J.
       "Algorithm 457: finding all cliques of an undirected graph".
       *Communications of the ACM* 16, 9 (Sep. 1973), 575--577.
       <http://portal.acm.org/citation.cfm?doid=362342.362367>

    .. [2] Etsuji Tomita, Akira Tanaka, Haruhisa Takahashi,
       "The worst-case time complexity for generating all maximal
       cliques and computational experiments",
       *Theoretical Computer Science*, Volume 363, Issue 1,
       Computing and Combinatorics,
       10th Annual International Conference on
       Computing and Combinatorics (COCOON 2004), 25 October 2006, Pages 28--42
       <https://doi.org/10.1016/j.tcs.2006.06.015>

    .. [3] F. Cazals, C. Karande,
       "A note on the problem of reporting maximal cliques",
       *Theoretical Computer Science*,
       Volume 407, Issues 1--3, 6 November 2008, Pages 564--568,
       <https://doi.org/10.1016/j.tcs.2008.05.010>
networkx.find_cycle
Python Library Documentation: function find_cycle in module networkx.algorithms.cycles

find_cycle(G, source=None, orientation=None, *, backend=None, **backend_kwargs)
    Returns a cycle found via depth-first traversal.

    The cycle is a list of edges indicating the cyclic path.
    Orientation of directed edges is controlled by `orientation`.

    Parameters
    ----------
    G : graph
        A directed/undirected graph/multigraph.

    source : node, list of nodes
        The node from which the traversal begins. If None, then a source
        is chosen arbitrarily and repeatedly until all edges from each node in
        the graph are searched.

    orientation : None | 'original' | 'reverse' | 'ignore' (default: None)
        For directed graphs and directed multigraphs, edge traversals need not
        respect the original orientation of the edges.
        When set to 'reverse' every edge is traversed in the reverse direction.
        When set to 'ignore', every edge is treated as undirected.
        When set to 'original', every edge is treated as directed.
        In all three cases, the yielded edge tuples add a last entry to
        indicate the direction in which that edge was traversed.
        If orientation is None, the yielded edge has no direction indicated.
        The direction is respected, but not reported.

    Returns
    -------
    edges : directed edges
        A list of directed edges indicating the path taken for the loop.
        If no cycle is found, then an exception is raised.
        For graphs, an edge is of the form `(u, v)` where `u` and `v`
        are the tail and head of the edge as determined by the traversal.
        For multigraphs, an edge is of the form `(u, v, key)`, where `key` is
        the key of the edge. When the graph is directed, then `u` and `v`
        are always in the order of the actual directed edge.
        If orientation is not None then the edge tuple is extended to include
        the direction of traversal ('forward' or 'reverse') on that edge.

    Raises
    ------
    NetworkXNoCycle
        If no cycle was found.

    Examples
    --------
    In this example, we construct a DAG and find, in the first call, that there
    are no directed cycles, and so an exception is raised. In the second call,
    we ignore edge orientations and find that there is an undirected cycle.
    Note that the second call finds a directed cycle while effectively
    traversing an undirected graph, and so, we found an "undirected cycle".
    This means that this DAG structure does not form a directed tree (which
    is also known as a polytree).

    >>> G = nx.DiGraph([(0, 1), (0, 2), (1, 2)])
    >>> nx.find_cycle(G, orientation="original")
    Traceback (most recent call last):
        ...
    networkx.exception.NetworkXNoCycle: No cycle found.
    >>> list(nx.find_cycle(G, orientation="ignore"))
    [(0, 1, 'forward'), (1, 2, 'forward'), (0, 2, 'reverse')]

    See Also
    --------
    simple_cycles
networkx.find_induced_nodes
Python Library Documentation: function find_induced_nodes in module networkx.algorithms.chordal

find_induced_nodes(G, s, t, treewidth_bound=9223372036854775807, *, backend=None, **backend_kwargs)
    Returns the set of induced nodes in the path from s to t.

    Parameters
    ----------
    G : graph
      A chordal NetworkX graph
    s : node
        Source node to look for induced nodes
    t : node
        Destination node to look for induced nodes
    treewidth_bound: float
        Maximum treewidth acceptable for the graph H. The search
        for induced nodes will end as soon as the treewidth_bound is exceeded.

    Returns
    -------
    induced_nodes : Set of nodes
        The set of induced nodes in the path from s to t in G

    Raises
    ------
    NetworkXError
        The algorithm does not support DiGraph, MultiGraph and MultiDiGraph.
        If the input graph is an instance of one of these classes, a
        :exc:`NetworkXError` is raised.
        The algorithm can only be applied to chordal graphs. If the input
        graph is found to be non-chordal, a :exc:`NetworkXError` is raised.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G = nx.generators.classic.path_graph(10)
    >>> induced_nodes = nx.find_induced_nodes(G, 1, 9, 2)
    >>> sorted(induced_nodes)
    [1, 2, 3, 4, 5, 6, 7, 8, 9]

    Notes
    -----
    G must be a chordal graph and (s,t) an edge that is not in G.

    If a treewidth_bound is provided, the search for induced nodes will end
    as soon as the treewidth_bound is exceeded.

    The algorithm is inspired by Algorithm 4 in [1]_.
    A formal definition of induced node can also be found on that reference.

    Self Loops are ignored

    References
    ----------
    .. [1] Learning Bounded Treewidth Bayesian Networks.
       Gal Elidan, Stephen Gould; JMLR, 9(Dec):2699--2731, 2008.
       http://jmlr.csail.mit.edu/papers/volume9/elidan08a/elidan08a.pdf
networkx.find_minimal_d_separator
Python Library Documentation: function find_minimal_d_separator in module networkx.algorithms.d_separation

find_minimal_d_separator(G, x, y, *, included=None, restricted=None, backend=None, **backend_kwargs)
    Returns a minimal d-separating set between `x` and `y` if possible

    A d-separating set in a DAG is a set of nodes that blocks all
    paths between the two sets of nodes, `x` and `y`. This function
    constructs a d-separating set that is "minimal", meaning no nodes can
    be removed without it losing the d-separating property for `x` and `y`.
    If no d-separating sets exist for `x` and `y`, this returns `None`.

    In a DAG there may be more than one minimal d-separator between two
    sets of nodes. Minimal d-separators are not always unique. This function
    returns one minimal d-separator, or `None` if no d-separator exists.

    Uses the algorithm presented in [1]_. The complexity of the algorithm
    is :math:`O(m)`, where :math:`m` stands for the number of edges in
    the subgraph of G consisting of only the ancestors of `x` and `y`.
    For full details, see [1]_.

    Parameters
    ----------
    G : graph
        A networkx DAG.
    x : set | node
        A node or set of nodes in the graph.
    y : set | node
        A node or set of nodes in the graph.
    included : set | node | None
        A node or set of nodes which must be included in the found separating set,
        default is None, which means the empty set.
    restricted : set | node | None
        Restricted node or set of nodes to consider. Only these nodes can be in
        the found separating set, default is None meaning all nodes in ``G``.

    Returns
    -------
    z : set | None
        The minimal d-separating set, if at least one d-separating set exists,
        otherwise None.

    Raises
    ------
    NetworkXError
        Raises a :exc:`NetworkXError` if the input graph is not a DAG
        or if node sets `x`, `y`, and `included` are not disjoint.

    NodeNotFound
        If any of the input nodes are not found in the graph,
        a :exc:`NodeNotFound` exception is raised.

    References
    ----------
    .. [1] van der Zander, Benito, and Maciej Liśkiewicz. "Finding
        minimal d-separators in linear time and applications." In
        Uncertainty in Artificial Intelligence, pp. 637-647. PMLR, 2020.
networkx.find_negative_cycle
Python Library Documentation: function find_negative_cycle in module networkx.algorithms.shortest_paths.weighted

find_negative_cycle(G, source, weight='weight', *, backend=None, **backend_kwargs)
    Returns a cycle with negative total weight if it exists.

    Bellman-Ford is used to find shortest_paths. That algorithm
    stops if there exists a negative cycle. This algorithm
    picks up from there and returns the found negative cycle.

    The cycle consists of a list of nodes in the cycle order. The last
    node equals the first to make it a cycle.
    You can look up the edge weights in the original graph. In the case
    of multigraphs the relevant edge is the minimal weight edge between
    the nodes in the 2-tuple.

    If the graph has no negative cycle, a NetworkXError is raised.

    Parameters
    ----------
    G : NetworkX graph

    source: node label
        The search for the negative cycle will start from this node.

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_weighted_edges_from(
    ...     [(0, 1, 2), (1, 2, 2), (2, 0, 1), (1, 4, 2), (4, 0, -5)]
    ... )
    >>> nx.find_negative_cycle(G, 0)
    [4, 0, 1, 4]

    Returns
    -------
    cycle : list
        A list of nodes in the order of the cycle found. The last node
        equals the first to indicate a cycle.

    Raises
    ------
    NetworkXError
        If no negative cycle is found.
networkx.florentine_families_graph
Python Library Documentation: function florentine_families_graph in module networkx.generators.social

florentine_families_graph(*, backend=None, **backend_kwargs)
    Returns Florentine families graph.

    References
    ----------
    .. [1] Ronald L. Breiger and Philippa E. Pattison
       Cumulated social roles: The duality of persons and their algebras,1
       Social Networks, Volume 8, Issue 3, September 1986, Pages 215-256
networkx.flow
Python Library Documentation: package networkx.algorithms.flow in networkx.algorithms

NAME
    networkx.algorithms.flow

PACKAGE CONTENTS
    boykovkolmogorov
    capacityscaling
    dinitz_alg
    edmondskarp
    gomory_hu
    maxflow
    mincost
    networksimplex
    preflowpush
    shortestaugmentingpath
    tests (package)
    utils

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\flow\__init__.py

networkx.flow_hierarchy
Python Library Documentation: function flow_hierarchy in module networkx.algorithms.hierarchy

flow_hierarchy(G, weight=None, *, backend=None, **backend_kwargs)
    Returns the flow hierarchy of a directed network.

    Flow hierarchy is defined as the fraction of edges not participating
    in cycles in a directed graph [1]_.

    Parameters
    ----------
    G : DiGraph or MultiDiGraph
       A directed graph

    weight : string, optional (default=None)
       Attribute to use for edge weights. If None the weight defaults to 1.

    Returns
    -------
    h : float
       Flow hierarchy value

    Raises
    ------
    NetworkXError
       If `G` is not a directed graph or if `G` has no edges.

    Notes
    -----
    The algorithm described in [1]_ computes the flow hierarchy through
    exponentiation of the adjacency matrix.  This function implements an
    alternative approach that finds strongly connected components.
    An edge is in a cycle if and only if it is in a strongly connected
    component, which can be found in $O(m)$ time using Tarjan's algorithm.

    References
    ----------
    .. [1] Luo, J.; Magee, C.L. (2011),
       Detecting evolving patterns of self-organizing networks by flow
       hierarchy measurement, Complexity, Volume 16 Issue 6 53-61.
       DOI: 10.1002/cplx.20368
       http://web.mit.edu/~cmagee/www/documents/28-DetectingEvolvingPatterns_FlowHierarchy.pdf
networkx.flow_matrix
Python Library Documentation: module networkx.algorithms.centrality.flow_matrix in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.flow_matrix

DESCRIPTION
    # Helpers for current-flow betweenness and current-flow closeness
    # Lazy computations for inverse Laplacian and flow-matrix rows.

CLASSES
    builtins.object
        InverseLaplacian
            CGInverseLaplacian
            FullInverseLaplacian
            SuperLUInverseLaplacian

    class CGInverseLaplacian(InverseLaplacian)
     |  CGInverseLaplacian(L, width=None, dtype=None)
     |
     |  Method resolution order:
     |      CGInverseLaplacian
     |      InverseLaplacian
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  init_solver(self, L)
     |
     |  solve(self, rhs)
     |
     |  solve_inverse(self, r)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from InverseLaplacian:
     |
     |  __init__(self, L, width=None, dtype=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  get_row(self, r)
     |
     |  get_rows(self, r1, r2)
     |
     |  width(self, L)
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from InverseLaplacian:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class FullInverseLaplacian(InverseLaplacian)
     |  FullInverseLaplacian(L, width=None, dtype=None)
     |
     |  Method resolution order:
     |      FullInverseLaplacian
     |      InverseLaplacian
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  init_solver(self, L)
     |
     |  solve(self, rhs)
     |
     |  solve_inverse(self, r)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from InverseLaplacian:
     |
     |  __init__(self, L, width=None, dtype=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  get_row(self, r)
     |
     |  get_rows(self, r1, r2)
     |
     |  width(self, L)
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from InverseLaplacian:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class InverseLaplacian(builtins.object)
     |  InverseLaplacian(L, width=None, dtype=None)
     |
     |  # Class to compute the inverse laplacian only for specified rows
     |  # Allows computation of the current-flow matrix without storing entire
     |  # inverse laplacian matrix
     |
     |  Methods defined here:
     |
     |  __init__(self, L, width=None, dtype=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  get_row(self, r)
     |
     |  get_rows(self, r1, r2)
     |
     |  init_solver(self, L)
     |
     |  solve(self, r)
     |
     |  solve_inverse(self, r)
     |
     |  width(self, L)
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors defined here:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class SuperLUInverseLaplacian(InverseLaplacian)
     |  SuperLUInverseLaplacian(L, width=None, dtype=None)
     |
     |  Method resolution order:
     |      SuperLUInverseLaplacian
     |      InverseLaplacian
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  init_solver(self, L)
     |
     |  solve(self, rhs)
     |
     |  solve_inverse(self, r)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from InverseLaplacian:
     |
     |  __init__(self, L, width=None, dtype=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  get_row(self, r)
     |
     |  get_rows(self, r1, r2)
     |
     |  width(self, L)
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from InverseLaplacian:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

FUNCTIONS
    flow_matrix_row(G, weight=None, dtype=<class 'float'>, solver='lu', *, backend=None, **backend_kwargs)

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\flow_matrix.py

networkx.floyd_warshall
Python Library Documentation: function floyd_warshall in module networkx.algorithms.shortest_paths.dense

floyd_warshall(G, weight='weight', *, backend=None, **backend_kwargs)
    Find all-pairs shortest path lengths using Floyd's algorithm.

    Parameters
    ----------
    G : NetworkX graph

    weight: string, optional (default= 'weight')
       Edge data key corresponding to the edge weight.


    Returns
    -------
    distance : dict
       A dictionary,  keyed by source and target, of shortest paths distances
       between nodes.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_weighted_edges_from(
    ...     [(0, 1, 5), (1, 2, 2), (2, 3, -3), (1, 3, 10), (3, 2, 8)]
    ... )
    >>> fw = nx.floyd_warshall(G, weight="weight")
    >>> results = {a: dict(b) for a, b in fw.items()}
    >>> print(results)
    {0: {0: 0, 1: 5, 2: 7, 3: 4}, 1: {1: 0, 2: 2, 3: -1, 0: inf}, 2: {2: 0, 3: -3, 0: inf, 1: inf}, 3: {3: 0, 2: 8, 0: inf, 1: inf}}

    Notes
    -----
    Floyd's algorithm is appropriate for finding shortest paths
    in dense graphs or graphs with negative weights when Dijkstra's algorithm
    fails.  This algorithm can still fail if there are negative cycles.
    It has running time $O(n^3)$ with running space of $O(n^2)$.

    See Also
    --------
    floyd_warshall_predecessor_and_distance
    floyd_warshall_numpy
    all_pairs_shortest_path
    all_pairs_shortest_path_length
networkx.floyd_warshall_numpy
Python Library Documentation: function floyd_warshall_numpy in module networkx.algorithms.shortest_paths.dense

floyd_warshall_numpy(G, nodelist=None, weight='weight', *, backend=None, **backend_kwargs)
    Find all-pairs shortest path lengths using Floyd's algorithm.

    This algorithm for finding shortest paths takes advantage of
    matrix representations of a graph and works well for dense
    graphs where all-pairs shortest path lengths are desired.
    The results are returned as a NumPy array, distance[i, j],
    where i and j are the indexes of two nodes in nodelist.
    The entry distance[i, j] is the distance along a shortest
    path from i to j. If no path exists the distance is Inf.

    Parameters
    ----------
    G : NetworkX graph

    nodelist : list, optional (default=G.nodes)
       The rows and columns are ordered by the nodes in nodelist.
       If nodelist is None then the ordering is produced by G.nodes.
       Nodelist should include all nodes in G.

    weight: string, optional (default='weight')
       Edge data key corresponding to the edge weight.

    Returns
    -------
    distance : 2D numpy.ndarray
        A numpy array of shortest path distances between nodes.
        If there is no path between two nodes the value is Inf.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_weighted_edges_from(
    ...     [(0, 1, 5), (1, 2, 2), (2, 3, -3), (1, 3, 10), (3, 2, 8)]
    ... )
    >>> nx.floyd_warshall_numpy(G)
    array([[ 0.,  5.,  7.,  4.],
           [inf,  0.,  2., -1.],
           [inf, inf,  0., -3.],
           [inf, inf,  8.,  0.]])

    Notes
    -----
    Floyd's algorithm is appropriate for finding shortest paths in
    dense graphs or graphs with negative weights when Dijkstra's
    algorithm fails. This algorithm can still fail if there are negative
    cycles. It has running time $O(n^3)$ with running space of $O(n^2)$.

    Raises
    ------
    NetworkXError
        If nodelist is not a list of the nodes in G.
networkx.floyd_warshall_predecessor_and_distance
Python Library Documentation: function floyd_warshall_predecessor_and_distance in module networkx.algorithms.shortest_paths.dense

floyd_warshall_predecessor_and_distance(G, weight='weight', *, backend=None, **backend_kwargs)
    Find all-pairs shortest path lengths using Floyd's algorithm.

    Parameters
    ----------
    G : NetworkX graph

    weight: string, optional (default= 'weight')
       Edge data key corresponding to the edge weight.

    Returns
    -------
    predecessor,distance : dictionaries
       Dictionaries, keyed by source and target, of predecessors and distances
       in the shortest path.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_weighted_edges_from(
    ...     [
    ...         ("s", "u", 10),
    ...         ("s", "x", 5),
    ...         ("u", "v", 1),
    ...         ("u", "x", 2),
    ...         ("v", "y", 1),
    ...         ("x", "u", 3),
    ...         ("x", "v", 5),
    ...         ("x", "y", 2),
    ...         ("y", "s", 7),
    ...         ("y", "v", 6),
    ...     ]
    ... )
    >>> predecessors, _ = nx.floyd_warshall_predecessor_and_distance(G)
    >>> print(nx.reconstruct_path("s", "v", predecessors))
    ['s', 'x', 'u', 'v']

    Notes
    -----
    Floyd's algorithm is appropriate for finding shortest paths
    in dense graphs or graphs with negative weights when Dijkstra's algorithm
    fails.  This algorithm can still fail if there are negative cycles.
    It has running time $O(n^3)$ with running space of $O(n^2)$.

    See Also
    --------
    floyd_warshall
    floyd_warshall_numpy
    all_pairs_shortest_path
    all_pairs_shortest_path_length
networkx.forceatlas2_layout
Python Library Documentation: function forceatlas2_layout in module networkx.drawing.layout

forceatlas2_layout(G, pos=None, *, max_iter=100, jitter_tolerance=1.0, scaling_ratio=2.0, gravity=1.0, distributed_action=False, strong_gravity=False, node_mass=None, node_size=None, weight=None, dissuade_hubs=False, linlog=False, seed=None, dim=2)
    Position nodes using the ForceAtlas2 force-directed layout algorithm.

    This function applies the ForceAtlas2 layout algorithm [1]_ to a NetworkX graph,
    positioning the nodes in a way that visually represents the structure of the graph.
    The algorithm uses physical simulation to minimize the energy of the system,
    resulting in a more readable layout.

    Parameters
    ----------
    G : nx.Graph
        A NetworkX graph to be laid out.
    pos : dict or None, optional
        Initial positions of the nodes. If None, random initial positions are used.
    max_iter : int (default: 100)
        Number of iterations for the layout optimization.
    jitter_tolerance : float (default: 1.0)
        Controls the tolerance for adjusting the speed of layout generation.
    scaling_ratio : float (default: 2.0)
        Determines the scaling of attraction and repulsion forces.
    distributed_attraction : bool (default: False)
        Distributes the attraction force evenly among nodes.
    strong_gravity : bool (default: False)
        Applies a strong gravitational pull towards the center.
    node_mass : dict or None, optional
        Maps nodes to their masses, influencing the attraction to other nodes.
    node_size : dict or None, optional
        Maps nodes to their sizes, preventing crowding by creating a halo effect.
    dissuade_hubs : bool (default: False)
        Prevents the clustering of hub nodes.
    linlog : bool (default: False)
        Uses logarithmic attraction instead of linear.
    seed : int, RandomState instance or None  optional (default=None)
        Used only for the initial positions in the algorithm.
        Set the random state for deterministic node layouts.
        If int, `seed` is the seed used by the random number generator,
        if numpy.random.RandomState instance, `seed` is the random
        number generator,
        if None, the random number generator is the RandomState instance used
        by numpy.random.
    dim : int (default: 2)
        Sets the dimensions for the layout. Ignored if `pos` is provided.

    Examples
    --------
    >>> import networkx as nx
    >>> G = nx.florentine_families_graph()
    >>> pos = nx.forceatlas2_layout(G)
    >>> nx.draw(G, pos=pos)

    References
    ----------
    .. [1] Jacomy, M., Venturini, T., Heymann, S., & Bastian, M. (2014).
           ForceAtlas2, a continuous graph layout algorithm for handy network
           visualization designed for the Gephi software. PloS one, 9(6), e98679.
           https://doi.org/10.1371/journal.pone.0098679
networkx.freeze
Python Library Documentation: function freeze in module networkx.classes.function

freeze(G)
    Modify graph to prevent further change by adding or removing
    nodes or edges.

    Node and edge data can still be modified.

    Parameters
    ----------
    G : graph
      A NetworkX graph

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> G = nx.freeze(G)
    >>> try:
    ...     G.add_edge(4, 5)
    ... except nx.NetworkXError as err:
    ...     print(str(err))
    Frozen graph can't be modified

    Notes
    -----
    To "unfreeze" a graph you must make a copy by creating a new graph object:

    >>> graph = nx.path_graph(4)
    >>> frozen_graph = nx.freeze(graph)
    >>> unfrozen_graph = nx.Graph(frozen_graph)
    >>> nx.is_frozen(unfrozen_graph)
    False

    See Also
    --------
    is_frozen
networkx.from_dict_of_dicts
Python Library Documentation: function from_dict_of_dicts in module networkx.convert

from_dict_of_dicts(d, create_using=None, multigraph_input=False, *, backend=None, **backend_kwargs)
    Returns a graph from a dictionary of dictionaries.

    Parameters
    ----------
    d : dictionary of dictionaries
      A dictionary of dictionaries adjacency representation.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.

    multigraph_input : bool (default False)
       When True, the dict `d` is assumed
       to be a dict-of-dict-of-dict-of-dict structure keyed by
       node to neighbor to edge keys to edge data for multi-edges.
       Otherwise this routine assumes dict-of-dict-of-dict keyed by
       node to neighbor to edge data.

    Examples
    --------
    >>> dod = {0: {1: {"weight": 1}}}  # single edge (0,1)
    >>> G = nx.from_dict_of_dicts(dod)

    or

    >>> G = nx.Graph(dod)  # use Graph constructor
networkx.from_dict_of_lists
Python Library Documentation: function from_dict_of_lists in module networkx.convert

from_dict_of_lists(d, create_using=None, *, backend=None, **backend_kwargs)
    Returns a graph from a dictionary of lists.

    Parameters
    ----------
    d : dictionary of lists
      A dictionary of lists adjacency representation.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.

    Examples
    --------
    >>> dol = {0: [1]}  # single edge (0,1)
    >>> G = nx.from_dict_of_lists(dol)

    or

    >>> G = nx.Graph(dol)  # use Graph constructor
networkx.from_edgelist
Python Library Documentation: function from_edgelist in module networkx.convert

from_edgelist(edgelist, create_using=None, *, backend=None, **backend_kwargs)
    Returns a graph from a list of edges.

    Parameters
    ----------
    edgelist : list or iterator
      Edge tuples

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.

    Examples
    --------
    >>> edgelist = [(0, 1)]  # single edge (0,1)
    >>> G = nx.from_edgelist(edgelist)

    or

    >>> G = nx.Graph(edgelist)  # use Graph constructor
networkx.from_graph6_bytes
Python Library Documentation: function from_graph6_bytes in module networkx.readwrite.graph6

from_graph6_bytes(bytes_in, *, backend=None, **backend_kwargs)
    Read a simple undirected graph in graph6 format from bytes.

    Parameters
    ----------
    bytes_in : bytes
       Data in graph6 format, without a trailing newline.

    Returns
    -------
    G : Graph

    Raises
    ------
    NetworkXError
        If bytes_in is unable to be parsed in graph6 format

    ValueError
        If any character ``c`` in bytes_in does not satisfy
        ``63 <= ord(c) < 127``.

    Examples
    --------
    >>> G = nx.from_graph6_bytes(b"A_")
    >>> sorted(G.edges())
    [(0, 1)]

    See Also
    --------
    read_graph6, write_graph6

    References
    ----------
    .. [1] Graph6 specification
           <http://users.cecs.anu.edu.au/~bdm/data/formats.html>
networkx.from_nested_tuple
Python Library Documentation: function from_nested_tuple in module networkx.algorithms.tree.coding

from_nested_tuple(sequence, sensible_relabeling=False, *, backend=None, **backend_kwargs)
    Returns the rooted tree corresponding to the given nested tuple.

    The nested tuple representation of a tree is defined
    recursively. The tree with one node and no edges is represented by
    the empty tuple, ``()``. A tree with ``k`` subtrees is represented
    by a tuple of length ``k`` in which each element is the nested tuple
    representation of a subtree.

    Parameters
    ----------
    sequence : tuple
        A nested tuple representing a rooted tree.

    sensible_relabeling : bool
        Whether to relabel the nodes of the tree so that nodes are
        labeled in increasing order according to their breadth-first
        search order from the root node.

    Returns
    -------
    NetworkX graph
        The tree corresponding to the given nested tuple, whose root
        node is node 0. If ``sensible_labeling`` is ``True``, nodes will
        be labeled in breadth-first search order starting from the root
        node.

    Notes
    -----
    This function is *not* the inverse of :func:`to_nested_tuple`; the
    only guarantee is that the rooted trees are isomorphic.

    See also
    --------
    to_nested_tuple
    from_prufer_sequence

    Examples
    --------
    Sensible relabeling ensures that the nodes are labeled from the root
    starting at 0::

        >>> balanced = (((), ()), ((), ()))
        >>> T = nx.from_nested_tuple(balanced, sensible_relabeling=True)
        >>> edges = [(0, 1), (0, 2), (1, 3), (1, 4), (2, 5), (2, 6)]
        >>> all((u, v) in T.edges() or (v, u) in T.edges() for (u, v) in edges)
        True
networkx.from_numpy_array
Python Library Documentation: function from_numpy_array in module networkx.convert_matrix

from_numpy_array(A, parallel_edges=False, create_using=None, edge_attr='weight', *, nodelist=None, backend=None, **backend_kwargs)
    Returns a graph from a 2D NumPy array.

    The 2D NumPy array is interpreted as an adjacency matrix for the graph.

    Parameters
    ----------
    A : a 2D numpy.ndarray
        An adjacency matrix representation of a graph

    parallel_edges : Boolean
        If this is True, `create_using` is a multigraph, and `A` is an
        integer array, then entry *(i, j)* in the array is interpreted as the
        number of parallel edges joining vertices *i* and *j* in the graph.
        If it is False, then the entries in the array are interpreted as
        the weight of a single edge joining the vertices.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    edge_attr : String, optional (default="weight")
        The attribute to which the array values are assigned on each edge. If
        it is None, edge attributes will not be assigned.

    nodelist : sequence of nodes, optional
        A sequence of objects to use as the nodes in the graph. If provided, the
        list of nodes must be the same length as the dimensions of `A`. The
        default is `None`, in which case the nodes are drawn from ``range(n)``.

    Notes
    -----
    For directed graphs, explicitly mention create_using=nx.DiGraph,
    and entry i,j of A corresponds to an edge from i to j.

    If `create_using` is :class:`networkx.MultiGraph` or
    :class:`networkx.MultiDiGraph`, `parallel_edges` is True, and the
    entries of `A` are of type :class:`int`, then this function returns a
    multigraph (of the same type as `create_using`) with parallel edges.

    If `create_using` indicates an undirected multigraph, then only the edges
    indicated by the upper triangle of the array `A` will be added to the
    graph.

    If `edge_attr` is Falsy (False or None), edge attributes will not be
    assigned, and the array data will be treated like a binary mask of
    edge presence or absence. Otherwise, the attributes will be assigned
    as follows:

    If the NumPy array has a single data type for each array entry it
    will be converted to an appropriate Python data type.

    If the NumPy array has a user-specified compound data type the names
    of the data fields will be used as attribute keys in the resulting
    NetworkX graph.

    See Also
    --------
    to_numpy_array

    Examples
    --------
    Simple integer weights on edges:

    >>> import numpy as np
    >>> A = np.array([[1, 1], [2, 1]])
    >>> G = nx.from_numpy_array(A)
    >>> G.edges(data=True)
    EdgeDataView([(0, 0, {'weight': 1}), (0, 1, {'weight': 2}), (1, 1, {'weight': 1})])

    If `create_using` indicates a multigraph and the array has only integer
    entries and `parallel_edges` is False, then the entries will be treated
    as weights for edges joining the nodes (without creating parallel edges):

    >>> A = np.array([[1, 1], [1, 2]])
    >>> G = nx.from_numpy_array(A, create_using=nx.MultiGraph)
    >>> G[1][1]
    AtlasView({0: {'weight': 2}})

    If `create_using` indicates a multigraph and the array has only integer
    entries and `parallel_edges` is True, then the entries will be treated
    as the number of parallel edges joining those two vertices:

    >>> A = np.array([[1, 1], [1, 2]])
    >>> temp = nx.MultiGraph()
    >>> G = nx.from_numpy_array(A, parallel_edges=True, create_using=temp)
    >>> G[1][1]
    AtlasView({0: {'weight': 1}, 1: {'weight': 1}})

    User defined compound data type on edges:

    >>> dt = [("weight", float), ("cost", int)]
    >>> A = np.array([[(1.0, 2)]], dtype=dt)
    >>> G = nx.from_numpy_array(A)
    >>> G.edges()
    EdgeView([(0, 0)])
    >>> G[0][0]["cost"]
    2
    >>> G[0][0]["weight"]
    1.0
networkx.from_pandas_adjacency
Python Library Documentation: function from_pandas_adjacency in module networkx.convert_matrix

from_pandas_adjacency(df, create_using=None, *, backend=None, **backend_kwargs)
    Returns a graph from Pandas DataFrame.

    The Pandas DataFrame is interpreted as an adjacency matrix for the graph.

    Parameters
    ----------
    df : Pandas DataFrame
      An adjacency matrix representation of a graph

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Notes
    -----
    For directed graphs, explicitly mention create_using=nx.DiGraph,
    and entry i,j of df corresponds to an edge from i to j.

    If `df` has a single data type for each entry it will be converted to an
    appropriate Python data type.

    If you have node attributes stored in a separate dataframe `df_nodes`,
    you can load those attributes to the graph `G` using the following code:

    ```
    df_nodes = pd.DataFrame({"node_id": [1, 2, 3], "attribute1": ["A", "B", "C"]})
    G.add_nodes_from((n, dict(d)) for n, d in df_nodes.iterrows())
    ```

    If `df` has a user-specified compound data type the names
    of the data fields will be used as attribute keys in the resulting
    NetworkX graph.

    See Also
    --------
    to_pandas_adjacency

    Examples
    --------
    Simple integer weights on edges:

    >>> import pandas as pd
    >>> pd.options.display.max_columns = 20
    >>> df = pd.DataFrame([[1, 1], [2, 1]])
    >>> df
       0  1
    0  1  1
    1  2  1
    >>> G = nx.from_pandas_adjacency(df)
    >>> G.name = "Graph from pandas adjacency matrix"
    >>> print(G)
    Graph named 'Graph from pandas adjacency matrix' with 2 nodes and 3 edges
networkx.from_pandas_edgelist
Python Library Documentation: function from_pandas_edgelist in module networkx.convert_matrix

from_pandas_edgelist(df, source='source', target='target', edge_attr=None, create_using=None, edge_key=None, *, backend=None, **backend_kwargs)
    Returns a graph from Pandas DataFrame containing an edge list.

    The Pandas DataFrame should contain at least two columns of node names and
    zero or more columns of edge attributes. Each row will be processed as one
    edge instance.

    Note: This function iterates over DataFrame.values, which is not
    guaranteed to retain the data type across columns in the row. This is only
    a problem if your row is entirely numeric and a mix of ints and floats. In
    that case, all values will be returned as floats. See the
    DataFrame.iterrows documentation for an example.

    Parameters
    ----------
    df : Pandas DataFrame
        An edge list representation of a graph

    source : str or int
        A valid column name (string or integer) for the source nodes (for the
        directed case).

    target : str or int
        A valid column name (string or integer) for the target nodes (for the
        directed case).

    edge_attr : str or int, iterable, True, or None
        A valid column name (str or int) or iterable of column names that are
        used to retrieve items and add them to the graph as edge attributes.
        If `True`, all columns will be added except `source`, `target` and `edge_key`.
        If `None`, no edge attributes are added to the graph.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.

    edge_key : str or None, optional (default=None)
        A valid column name for the edge keys (for a MultiGraph). The values in
        this column are used for the edge keys when adding edges if create_using
        is a multigraph.

    If you have node attributes stored in a separate dataframe `df_nodes`,
    you can load those attributes to the graph `G` using the following code:

    ```
    df_nodes = pd.DataFrame({"node_id": [1, 2, 3], "attribute1": ["A", "B", "C"]})
    G.add_nodes_from((n, dict(d)) for n, d in df_nodes.iterrows())
    ```

    See Also
    --------
    to_pandas_edgelist

    Examples
    --------
    Simple integer weights on edges:

    >>> import pandas as pd
    >>> pd.options.display.max_columns = 20
    >>> import numpy as np
    >>> rng = np.random.RandomState(seed=5)
    >>> ints = rng.randint(1, 11, size=(3, 2))
    >>> a = ["A", "B", "C"]
    >>> b = ["D", "A", "E"]
    >>> df = pd.DataFrame(ints, columns=["weight", "cost"])
    >>> df[0] = a
    >>> df["b"] = b
    >>> df[["weight", "cost", 0, "b"]]
       weight  cost  0  b
    0       4     7  A  D
    1       7     1  B  A
    2      10     9  C  E
    >>> G = nx.from_pandas_edgelist(df, 0, "b", ["weight", "cost"])
    >>> G["E"]["C"]["weight"]
    10
    >>> G["E"]["C"]["cost"]
    9
    >>> edges = pd.DataFrame(
    ...     {
    ...         "source": [0, 1, 2],
    ...         "target": [2, 2, 3],
    ...         "weight": [3, 4, 5],
    ...         "color": ["red", "blue", "blue"],
    ...     }
    ... )
    >>> G = nx.from_pandas_edgelist(edges, edge_attr=True)
    >>> G[0][2]["color"]
    'red'

    Build multigraph with custom keys:

    >>> edges = pd.DataFrame(
    ...     {
    ...         "source": [0, 1, 2, 0],
    ...         "target": [2, 2, 3, 2],
    ...         "my_edge_key": ["A", "B", "C", "D"],
    ...         "weight": [3, 4, 5, 6],
    ...         "color": ["red", "blue", "blue", "blue"],
    ...     }
    ... )
    >>> G = nx.from_pandas_edgelist(
    ...     edges,
    ...     edge_key="my_edge_key",
    ...     edge_attr=["weight", "color"],
    ...     create_using=nx.MultiGraph(),
    ... )
    >>> G[0][2]
    AtlasView({'A': {'weight': 3, 'color': 'red'}, 'D': {'weight': 6, 'color': 'blue'}})
networkx.from_prufer_sequence
Python Library Documentation: function from_prufer_sequence in module networkx.algorithms.tree.coding

from_prufer_sequence(sequence, *, backend=None, **backend_kwargs)
    Returns the tree corresponding to the given Prüfer sequence.

    A *Prüfer sequence* is a list of *n* - 2 numbers between 0 and
    *n* - 1, inclusive. The tree corresponding to a given Prüfer
    sequence can be recovered by repeatedly joining a node in the
    sequence with a node with the smallest potential degree according to
    the sequence.

    Parameters
    ----------
    sequence : list
        A Prüfer sequence, which is a list of *n* - 2 integers between
        zero and *n* - 1, inclusive.

    Returns
    -------
    NetworkX graph
        The tree corresponding to the given Prüfer sequence.

    Raises
    ------
    NetworkXError
        If the Prüfer sequence is not valid.

    Notes
    -----
    There is a bijection from labeled trees to Prüfer sequences. This
    function is the inverse of the :func:`from_prufer_sequence` function.

    Sometimes Prüfer sequences use nodes labeled from 1 to *n* instead
    of from 0 to *n* - 1. This function requires nodes to be labeled in
    the latter form. You can use :func:`networkx.relabel_nodes` to
    relabel the nodes of your tree to the appropriate format.

    This implementation is from [1]_ and has a running time of
    $O(n)$.

    References
    ----------
    .. [1] Wang, Xiaodong, Lei Wang, and Yingjie Wu.
           "An optimal algorithm for Prufer codes."
           *Journal of Software Engineering and Applications* 2.02 (2009): 111.
           <https://doi.org/10.4236/jsea.2009.22016>

    See also
    --------
    from_nested_tuple
    to_prufer_sequence

    Examples
    --------
    There is a bijection between Prüfer sequences and labeled trees, so
    this function is the inverse of the :func:`to_prufer_sequence`
    function:

    >>> edges = [(0, 3), (1, 3), (2, 3), (3, 4), (4, 5)]
    >>> tree = nx.Graph(edges)
    >>> sequence = nx.to_prufer_sequence(tree)
    >>> sequence
    [3, 3, 3, 4]
    >>> tree2 = nx.from_prufer_sequence(sequence)
    >>> list(tree2.edges()) == edges
    True
networkx.from_scipy_sparse_array
Python Library Documentation: function from_scipy_sparse_array in module networkx.convert_matrix

from_scipy_sparse_array(A, parallel_edges=False, create_using=None, edge_attribute='weight', *, backend=None, **backend_kwargs)
    Creates a new graph from an adjacency matrix given as a SciPy sparse
    array.

    Parameters
    ----------
    A: scipy.sparse array
      An adjacency matrix representation of a graph

    parallel_edges : Boolean
      If this is True, `create_using` is a multigraph, and `A` is an
      integer matrix, then entry *(i, j)* in the matrix is interpreted as the
      number of parallel edges joining vertices *i* and *j* in the graph.
      If it is False, then the entries in the matrix are interpreted as
      the weight of a single edge joining the vertices.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    edge_attribute: string
       Name of edge attribute to store matrix numeric value. The data will
       have the same type as the matrix entry (int, float, (real,imag)).

    Notes
    -----
    For directed graphs, explicitly mention create_using=nx.DiGraph,
    and entry i,j of A corresponds to an edge from i to j.

    If `create_using` is :class:`networkx.MultiGraph` or
    :class:`networkx.MultiDiGraph`, `parallel_edges` is True, and the
    entries of `A` are of type :class:`int`, then this function returns a
    multigraph (constructed from `create_using`) with parallel edges.
    In this case, `edge_attribute` will be ignored.

    If `create_using` indicates an undirected multigraph, then only the edges
    indicated by the upper triangle of the matrix `A` will be added to the
    graph.

    Examples
    --------
    >>> import scipy as sp
    >>> A = sp.sparse.eye(2, 2, 1)
    >>> G = nx.from_scipy_sparse_array(A)

    If `create_using` indicates a multigraph and the matrix has only integer
    entries and `parallel_edges` is False, then the entries will be treated
    as weights for edges joining the nodes (without creating parallel edges):

    >>> A = sp.sparse.csr_array([[1, 1], [1, 2]])
    >>> G = nx.from_scipy_sparse_array(A, create_using=nx.MultiGraph)
    >>> G[1][1]
    AtlasView({0: {'weight': 2}})

    If `create_using` indicates a multigraph and the matrix has only integer
    entries and `parallel_edges` is True, then the entries will be treated
    as the number of parallel edges joining those two vertices:

    >>> A = sp.sparse.csr_array([[1, 1], [1, 2]])
    >>> G = nx.from_scipy_sparse_array(
    ...     A, parallel_edges=True, create_using=nx.MultiGraph
    ... )
    >>> G[1][1]
    AtlasView({0: {'weight': 1}, 1: {'weight': 1}})
networkx.from_sparse6_bytes
Python Library Documentation: function from_sparse6_bytes in module networkx.readwrite.sparse6

from_sparse6_bytes(string, *, backend=None, **backend_kwargs)
    Read an undirected graph in sparse6 format from string.

    Parameters
    ----------
    string : string
       Data in sparse6 format

    Returns
    -------
    G : Graph

    Raises
    ------
    NetworkXError
        If the string is unable to be parsed in sparse6 format

    Examples
    --------
    >>> G = nx.from_sparse6_bytes(b":A_")
    >>> sorted(G.edges())
    [(0, 1), (0, 1), (0, 1)]

    See Also
    --------
    read_sparse6, write_sparse6

    References
    ----------
    .. [1] Sparse6 specification
           <https://users.cecs.anu.edu.au/~bdm/data/formats.html>
networkx.frucht_graph
Python Library Documentation: function frucht_graph in module networkx.generators.small

frucht_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Frucht Graph.

    The Frucht Graph is the smallest cubical graph whose
    automorphism group consists only of the identity element [1]_.
    It has 12 nodes and 18 edges and no nontrivial symmetries.
    It is planar and Hamiltonian [2]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Frucht Graph with 12 nodes and 18 edges

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Frucht_graph
    .. [2] https://mathworld.wolfram.com/FruchtGraph.html
networkx.fruchterman_reingold_layout
Python Library Documentation: function spring_layout in module networkx.drawing.layout

spring_layout(G, k=None, pos=None, fixed=None, iterations=50, threshold=0.0001, weight='weight', scale=1, center=None, dim=2, seed=None)
    Position nodes using Fruchterman-Reingold force-directed algorithm.

    The algorithm simulates a force-directed representation of the network
    treating edges as springs holding nodes close, while treating nodes
    as repelling objects, sometimes called an anti-gravity force.
    Simulation continues until the positions are close to an equilibrium.

    There are some hard-coded values: minimal distance between
    nodes (0.01) and "temperature" of 0.1 to ensure nodes don't fly away.
    During the simulation, `k` helps determine the distance between nodes,
    though `scale` and `center` determine the size and place after
    rescaling occurs at the end of the simulation.

    Fixing some nodes doesn't allow them to move in the simulation.
    It also turns off the rescaling feature at the simulation's end.
    In addition, setting `scale` to `None` turns off rescaling.

    Parameters
    ----------
    G : NetworkX graph or list of nodes
        A position will be assigned to every node in G.

    k : float (default=None)
        Optimal distance between nodes.  If None the distance is set to
        1/sqrt(n) where n is the number of nodes.  Increase this value
        to move nodes farther apart.

    pos : dict or None  optional (default=None)
        Initial positions for nodes as a dictionary with node as keys
        and values as a coordinate list or tuple.  If None, then use
        random initial positions.

    fixed : list or None  optional (default=None)
        Nodes to keep fixed at initial position.
        Nodes not in ``G.nodes`` are ignored.
        ValueError raised if `fixed` specified and `pos` not.

    iterations : int  optional (default=50)
        Maximum number of iterations taken

    threshold: float optional (default = 1e-4)
        Threshold for relative error in node position changes.
        The iteration stops if the error is below this threshold.

    weight : string or None   optional (default='weight')
        The edge attribute that holds the numerical value used for
        the edge weight.  Larger means a stronger attractive force.
        If None, then all edge weights are 1.

    scale : number or None (default: 1)
        Scale factor for positions. Not used unless `fixed is None`.
        If scale is None, no rescaling is performed.

    center : array-like or None
        Coordinate pair around which to center the layout.
        Not used unless `fixed is None`.

    dim : int
        Dimension of layout.

    seed : int, RandomState instance or None  optional (default=None)
        Used only for the initial positions in the algorithm.
        Set the random state for deterministic node layouts.
        If int, `seed` is the seed used by the random number generator,
        if numpy.random.RandomState instance, `seed` is the random
        number generator,
        if None, the random number generator is the RandomState instance used
        by numpy.random.

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> pos = nx.spring_layout(G)

    # The same using longer but equivalent function name
    >>> pos = nx.fruchterman_reingold_layout(G)
networkx.full_join
Python Library Documentation: function full_join in module networkx.algorithms.operators.binary

full_join(G, H, rename=(None, None), *, backend=None, **backend_kwargs)
    Returns the full join of graphs G and H.

    Full join is the union of G and H in which all edges between
    G and H are added.
    The node sets of G and H must be disjoint,
    otherwise an exception is raised.

    Parameters
    ----------
    G, H : graph
       A NetworkX graph

    rename : tuple , default=(None, None)
       Node names of G and H can be changed by specifying the tuple
       rename=('G-','H-') (for example).  Node "u" in G is then renamed
       "G-u" and "v" in H is renamed "H-v".

    Returns
    -------
    U : The full join graph with the same type as G.

    Notes
    -----
    It is recommended that G and H be either both directed or both undirected.

    If G is directed, then edges from G to H are added as well as from H to G.

    Note that full_join() does not produce parallel edges for MultiGraphs.

    The full join operation of graphs G and H is the same as getting
    their complement, performing a disjoint union, and finally getting
    the complement of the resulting graph.

    Graph, edge, and node attributes are propagated from G and H
    to the union graph.  If a graph attribute is present in both
    G and H the value from H is used.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2)])
    >>> H = nx.Graph([(3, 4)])
    >>> R = nx.full_join(G, H, rename=("G", "H"))
    >>> R.nodes
    NodeView(('G0', 'G1', 'G2', 'H3', 'H4'))
    >>> R.edges
    EdgeView([('G0', 'G1'), ('G0', 'G2'), ('G0', 'H3'), ('G0', 'H4'), ('G1', 'H3'), ('G1', 'H4'), ('G2', 'H3'), ('G2', 'H4'), ('H3', 'H4')])

    See Also
    --------
    union
    disjoint_union
networkx.full_rary_tree
Python Library Documentation: function full_rary_tree in module networkx.generators.classic

full_rary_tree(r, n, create_using=None, *, backend=None, **backend_kwargs)
    Creates a full r-ary tree of `n` nodes.

    Sometimes called a k-ary, n-ary, or m-ary tree.
    "... all non-leaf nodes have exactly r children and all levels
    are full except for some rightmost position of the bottom level
    (if a leaf at the bottom level is missing, then so are all of the
    leaves to its right." [1]_

    .. plot::

        >>> nx.draw(nx.full_rary_tree(2, 10))

    Parameters
    ----------
    r : int
        branching factor of the tree
    n : int
        Number of nodes in the tree
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        An r-ary tree with n nodes

    References
    ----------
    .. [1] An introduction to data structures and algorithms,
           James Andrew Storer,  Birkhauser Boston 2001, (page 225).
networkx.function
Python Library Documentation: module networkx.classes.function in networkx.classes

NAME
    networkx.classes.function - Functional interface to graph methods and assorted utilities.

FUNCTIONS
    add_cycle(G_to_add_to, nodes_for_cycle, **attr)
        Add a cycle to the Graph G_to_add_to.

        Parameters
        ----------
        G_to_add_to : graph
            A NetworkX graph
        nodes_for_cycle: iterable container
            A container of nodes.  A cycle will be constructed from
            the nodes (in order) and added to the graph.
        attr : keyword arguments, optional (default= no attributes)
            Attributes to add to every edge in cycle.

        See Also
        --------
        add_path, add_star

        Examples
        --------
        >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
        >>> nx.add_cycle(G, [0, 1, 2, 3])
        >>> nx.add_cycle(G, [10, 11, 12], weight=7)

    add_path(G_to_add_to, nodes_for_path, **attr)
        Add a path to the Graph G_to_add_to.

        Parameters
        ----------
        G_to_add_to : graph
            A NetworkX graph
        nodes_for_path : iterable container
            A container of nodes.  A path will be constructed from
            the nodes (in order) and added to the graph.
        attr : keyword arguments, optional (default= no attributes)
            Attributes to add to every edge in path.

        See Also
        --------
        add_star, add_cycle

        Examples
        --------
        >>> G = nx.Graph()
        >>> nx.add_path(G, [0, 1, 2, 3])
        >>> nx.add_path(G, [10, 11, 12], weight=7)

    add_star(G_to_add_to, nodes_for_star, **attr)
        Add a star to Graph G_to_add_to.

        The first node in `nodes_for_star` is the middle of the star.
        It is connected to all other nodes.

        Parameters
        ----------
        G_to_add_to : graph
            A NetworkX graph
        nodes_for_star : iterable container
            A container of nodes.
        attr : keyword arguments, optional (default= no attributes)
            Attributes to add to every edge in star.

        See Also
        --------
        add_path, add_cycle

        Examples
        --------
        >>> G = nx.Graph()
        >>> nx.add_star(G, [0, 1, 2, 3])
        >>> nx.add_star(G, [10, 11, 12], weight=2)

    all_neighbors(graph, node)
        Returns all of the neighbors of a node in the graph.

        If the graph is directed returns predecessors as well as successors.

        Parameters
        ----------
        graph : NetworkX graph
            Graph to find neighbors.

        node : node
            The node whose neighbors will be returned.

        Returns
        -------
        neighbors : iterator
            Iterator of neighbors

    common_neighbors(G, u, v)
        Returns the common neighbors of two nodes in a graph.

        Parameters
        ----------
        G : graph
            A NetworkX undirected graph.

        u, v : nodes
            Nodes in the graph.

        Returns
        -------
        cnbors : set
            Set of common neighbors of u and v in the graph.

        Raises
        ------
        NetworkXError
            If u or v is not a node in the graph.

        Examples
        --------
        >>> G = nx.complete_graph(5)
        >>> sorted(nx.common_neighbors(G, 0, 1))
        [2, 3, 4]

    create_empty_copy(G, with_data=True)
        Returns a copy of the graph G with all of the edges removed.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        with_data :  bool (default=True)
           Propagate Graph and Nodes data to the new graph.

        See Also
        --------
        empty_graph

    degree(G, nbunch=None, weight=None)
        Returns a degree view of single node or of nbunch of nodes.
        If nbunch is omitted, then return degrees of *all* nodes.

        This function wraps the :func:`G.degree <networkx.Graph.degree>` property.

    degree_histogram(G)
        Returns a list of the frequency of each degree value.

        Parameters
        ----------
        G : Networkx graph
           A graph

        Returns
        -------
        hist : list
           A list of frequencies of degrees.
           The degree values are the index in the list.

        Notes
        -----
        Note: the bins are width one, hence len(list) can be large
        (Order(number_of_edges))

    density(G)
        Returns the density of a graph.

        The density for undirected graphs is

        .. math::

           d = \frac{2m}{n(n-1)},

        and for directed graphs is

        .. math::

           d = \frac{m}{n(n-1)},

        where `n` is the number of nodes and `m`  is the number of edges in `G`.

        Notes
        -----
        The density is 0 for a graph without edges and 1 for a complete graph.
        The density of multigraphs can be higher than 1.

        Self loops are counted in the total number of edges so graphs with self
        loops can have density higher than 1.

    edge_subgraph(G, edges)
        Returns a view of the subgraph induced by the specified edges.

        The induced subgraph contains each edge in `edges` and each
        node incident to any of those edges.

        Parameters
        ----------
        G : NetworkX Graph
        edges : iterable
            An iterable of edges. Edges not present in `G` are ignored.

        Returns
        -------
        subgraph : SubGraph View
            A read-only edge-induced subgraph of `G`.
            Changes to `G` are reflected in the view.

        Notes
        -----
        To create a mutable subgraph with its own copies of nodes
        edges and attributes use `subgraph.copy()` or `Graph(subgraph)`

        If you create a subgraph of a subgraph recursively you can end up
        with a chain of subgraphs that becomes very slow with about 15
        nested subgraph views. Luckily the edge_subgraph filter nests
        nicely so you can use the original graph as G in this function
        to avoid chains. We do not rule out chains programmatically so
        that odd cases like an `edge_subgraph` of a `restricted_view`
        can be created.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> H = G.edge_subgraph([(0, 1), (3, 4)])
        >>> list(H.nodes)
        [0, 1, 3, 4]
        >>> list(H.edges)
        [(0, 1), (3, 4)]

    edges(G, nbunch=None)
        Returns an edge view of edges incident to nodes in nbunch.

        Return all edges if nbunch is unspecified or nbunch=None.

        For digraphs, edges=out_edges

        This function wraps the :func:`G.edges <networkx.Graph.edges>` property.

    freeze(G)
        Modify graph to prevent further change by adding or removing
        nodes or edges.

        Node and edge data can still be modified.

        Parameters
        ----------
        G : graph
          A NetworkX graph

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> G = nx.freeze(G)
        >>> try:
        ...     G.add_edge(4, 5)
        ... except nx.NetworkXError as err:
        ...     print(str(err))
        Frozen graph can't be modified

        Notes
        -----
        To "unfreeze" a graph you must make a copy by creating a new graph object:

        >>> graph = nx.path_graph(4)
        >>> frozen_graph = nx.freeze(graph)
        >>> unfrozen_graph = nx.Graph(frozen_graph)
        >>> nx.is_frozen(unfrozen_graph)
        False

        See Also
        --------
        is_frozen

    get_edge_attributes(G, name, default=None)
        Get edge attributes from graph

        Parameters
        ----------
        G : NetworkX Graph

        name : string
           Attribute name

        default: object (default=None)
           Default value of the edge attribute if there is no value set for that
           edge in graph. If `None` then edges without this attribute are not
           included in the returned dict.

        Returns
        -------
        Dictionary of attributes keyed by edge. For (di)graphs, the keys are
        2-tuples of the form: (u, v). For multi(di)graphs, the keys are 3-tuples of
        the form: (u, v, key).

        Examples
        --------
        >>> G = nx.Graph()
        >>> nx.add_path(G, [1, 2, 3], color="red")
        >>> color = nx.get_edge_attributes(G, "color")
        >>> color[(1, 2)]
        'red'
        >>> G.add_edge(3, 4)
        >>> color = nx.get_edge_attributes(G, "color", default="yellow")
        >>> color[(3, 4)]
        'yellow'

    get_node_attributes(G, name, default=None)
        Get node attributes from graph

        Parameters
        ----------
        G : NetworkX Graph

        name : string
           Attribute name

        default: object (default=None)
           Default value of the node attribute if there is no value set for that
           node in graph. If `None` then nodes without this attribute are not
           included in the returned dict.

        Returns
        -------
        Dictionary of attributes keyed by node.

        Examples
        --------
        >>> G = nx.Graph()
        >>> G.add_nodes_from([1, 2, 3], color="red")
        >>> color = nx.get_node_attributes(G, "color")
        >>> color[1]
        'red'
        >>> G.add_node(4)
        >>> color = nx.get_node_attributes(G, "color", default="yellow")
        >>> color[4]
        'yellow'

    induced_subgraph(G, nbunch)
        Returns a SubGraph view of `G` showing only nodes in nbunch.

        The induced subgraph of a graph on a set of nodes N is the
        graph with nodes N and edges from G which have both ends in N.

        Parameters
        ----------
        G : NetworkX Graph
        nbunch : node, container of nodes or None (for all nodes)

        Returns
        -------
        subgraph : SubGraph View
            A read-only view of the subgraph in `G` induced by the nodes.
            Changes to the graph `G` will be reflected in the view.

        Notes
        -----
        To create a mutable subgraph with its own copies of nodes
        edges and attributes use `subgraph.copy()` or `Graph(subgraph)`

        For an inplace reduction of a graph to a subgraph you can remove nodes:
        `G.remove_nodes_from(n in G if n not in set(nbunch))`

        If you are going to compute subgraphs of your subgraphs you could
        end up with a chain of views that can be very slow once the chain
        has about 15 views in it. If they are all induced subgraphs, you
        can short-cut the chain by making them all subgraphs of the original
        graph. The graph class method `G.subgraph` does this when `G` is
        a subgraph. In contrast, this function allows you to choose to build
        chains or not, as you wish. The returned subgraph is a view on `G`.

        Examples
        --------
        >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
        >>> H = nx.induced_subgraph(G, [0, 1, 3])
        >>> list(H.edges)
        [(0, 1)]
        >>> list(H.nodes)
        [0, 1, 3]

    is_directed(G)
        Return True if graph is directed.

    is_empty(G)
        Returns True if `G` has no edges.

        Parameters
        ----------
        G : graph
            A NetworkX graph.

        Returns
        -------
        bool
            True if `G` has no edges, and False otherwise.

        Notes
        -----
        An empty graph can have nodes but not edges. The empty graph with zero
        nodes is known as the null graph. This is an $O(n)$ operation where n
        is the number of nodes in the graph.

    is_frozen(G)
        Returns True if graph is frozen.

        Parameters
        ----------
        G : graph
          A NetworkX graph

        See Also
        --------
        freeze

    is_negatively_weighted(G, edge=None, weight='weight', *, backend=None, **backend_kwargs)
        Returns True if `G` has negatively weighted edges.

        Parameters
        ----------
        G : graph
            A NetworkX graph.

        edge : tuple, optional
            A 2-tuple specifying the only edge in `G` that will be tested. If
            None, then every edge in `G` is tested.

        weight: string, optional
            The attribute name used to query for edge weights.

        Returns
        -------
        bool
            A boolean signifying if `G`, or the specified edge, is negatively
            weighted.

        Raises
        ------
        NetworkXError
            If the specified edge does not exist.

        Examples
        --------
        >>> G = nx.Graph()
        >>> G.add_edges_from([(1, 3), (2, 4), (2, 6)])
        >>> G.add_edge(1, 2, weight=4)
        >>> nx.is_negatively_weighted(G, (1, 2))
        False
        >>> G[2][4]["weight"] = -2
        >>> nx.is_negatively_weighted(G)
        True
        >>> G = nx.DiGraph()
        >>> edges = [("0", "3", 3), ("0", "1", -5), ("1", "0", -2)]
        >>> G.add_weighted_edges_from(edges)
        >>> nx.is_negatively_weighted(G)
        True

    is_path(G, path)
        Returns whether or not the specified path exists.

        For it to return True, every node on the path must exist and
        each consecutive pair must be connected via one or more edges.

        Parameters
        ----------
        G : graph
            A NetworkX graph.

        path : list
            A list of nodes which defines the path to traverse

        Returns
        -------
        bool
            True if `path` is a valid path in `G`

    is_weighted(G, edge=None, weight='weight')
        Returns True if `G` has weighted edges.

        Parameters
        ----------
        G : graph
            A NetworkX graph.

        edge : tuple, optional
            A 2-tuple specifying the only edge in `G` that will be tested. If
            None, then every edge in `G` is tested.

        weight: string, optional
            The attribute name used to query for edge weights.

        Returns
        -------
        bool
            A boolean signifying if `G`, or the specified edge, is weighted.

        Raises
        ------
        NetworkXError
            If the specified edge does not exist.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.is_weighted(G)
        False
        >>> nx.is_weighted(G, (2, 3))
        False

        >>> G = nx.DiGraph()
        >>> G.add_edge(1, 2, weight=1)
        >>> nx.is_weighted(G)
        True

    neighbors(G, n)
        Returns an iterator over all neighbors of node n.

        This function wraps the :func:`G.neighbors <networkx.Graph.neighbors>` function.

    nodes(G)
        Returns a NodeView over the graph nodes.

        This function wraps the :func:`G.nodes <networkx.Graph.nodes>` property.

    nodes_with_selfloops(G)
        Returns an iterator over nodes with self loops.

        A node with a self loop has an edge with both ends adjacent
        to that node.

        Returns
        -------
        nodelist : iterator
            A iterator over nodes with self loops.

        See Also
        --------
        selfloop_edges, number_of_selfloops

        Examples
        --------
        >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
        >>> G.add_edge(1, 1)
        >>> G.add_edge(1, 2)
        >>> list(nx.nodes_with_selfloops(G))
        [1]

    non_edges(graph)
        Returns the nonexistent edges in the graph.

        Parameters
        ----------
        graph : NetworkX graph.
            Graph to find nonexistent edges.

        Returns
        -------
        non_edges : iterator
            Iterator of edges that are not in the graph.

    non_neighbors(graph, node)
        Returns the non-neighbors of the node in the graph.

        Parameters
        ----------
        graph : NetworkX graph
            Graph to find neighbors.

        node : node
            The node whose neighbors will be returned.

        Returns
        -------
        non_neighbors : set
            Set of nodes in the graph that are not neighbors of the node.

    number_of_edges(G)
        Returns the number of edges in the graph.

        This function wraps the :func:`G.number_of_edges <networkx.Graph.number_of_edges>` function.

    number_of_nodes(G)
        Returns the number of nodes in the graph.

        This function wraps the :func:`G.number_of_nodes <networkx.Graph.number_of_nodes>` function.

    number_of_selfloops(G)
        Returns the number of selfloop edges.

        A selfloop edge has the same node at both ends.

        Returns
        -------
        nloops : int
            The number of selfloops.

        See Also
        --------
        nodes_with_selfloops, selfloop_edges

        Examples
        --------
        >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
        >>> G.add_edge(1, 1)
        >>> G.add_edge(1, 2)
        >>> nx.number_of_selfloops(G)
        1

    path_weight(G, path, weight)
        Returns total cost associated with specified path and weight

        Parameters
        ----------
        G : graph
            A NetworkX graph.

        path: list
            A list of node labels which defines the path to traverse

        weight: string
            A string indicating which edge attribute to use for path cost

        Returns
        -------
        cost: int or float
            An integer or a float representing the total cost with respect to the
            specified weight of the specified path

        Raises
        ------
        NetworkXNoPath
            If the specified edge does not exist.

    remove_edge_attributes(G, *attr_names, ebunch=None)
        Remove edge attributes from all edges in the graph.

        Parameters
        ----------
        G : NetworkX Graph

        *attr_names : List of Strings
            The attribute names to remove from the graph.

        Examples
        --------
        >>> G = nx.path_graph(3)
        >>> nx.set_edge_attributes(G, {(u, v): u + v for u, v in G.edges()}, name="weight")
        >>> nx.get_edge_attributes(G, "weight")
        {(0, 1): 1, (1, 2): 3}
        >>> remove_edge_attributes(G, "weight")
        >>> nx.get_edge_attributes(G, "weight")
        {}

    remove_node_attributes(G, *attr_names, nbunch=None)
        Remove node attributes from all nodes in the graph.

        Parameters
        ----------
        G : NetworkX Graph

        *attr_names : List of Strings
            The attribute names to remove from the graph.

        nbunch : List of Nodes
            Remove the node attributes only from the nodes in this list.

        Examples
        --------
        >>> G = nx.Graph()
        >>> G.add_nodes_from([1, 2, 3], color="blue")
        >>> nx.get_node_attributes(G, "color")
        {1: 'blue', 2: 'blue', 3: 'blue'}
        >>> nx.remove_node_attributes(G, "color")
        >>> nx.get_node_attributes(G, "color")
        {}

    restricted_view(G, nodes, edges)
        Returns a view of `G` with hidden nodes and edges.

        The resulting subgraph filters out node `nodes` and edges `edges`.
        Filtered out nodes also filter out any of their edges.

        Parameters
        ----------
        G : NetworkX Graph
        nodes : iterable
            An iterable of nodes. Nodes not present in `G` are ignored.
        edges : iterable
            An iterable of edges. Edges not present in `G` are ignored.

        Returns
        -------
        subgraph : SubGraph View
            A read-only restricted view of `G` filtering out nodes and edges.
            Changes to `G` are reflected in the view.

        Notes
        -----
        To create a mutable subgraph with its own copies of nodes
        edges and attributes use `subgraph.copy()` or `Graph(subgraph)`

        If you create a subgraph of a subgraph recursively you may end up
        with a chain of subgraph views. Such chains can get quite slow
        for lengths near 15. To avoid long chains, try to make your subgraph
        based on the original graph.  We do not rule out chains programmatically
        so that odd cases like an `edge_subgraph` of a `restricted_view`
        can be created.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> H = nx.restricted_view(G, [0], [(1, 2), (3, 4)])
        >>> list(H.nodes)
        [1, 2, 3, 4]
        >>> list(H.edges)
        [(2, 3)]

    selfloop_edges(G, data=False, keys=False, default=None)
        Returns an iterator over selfloop edges.

        A selfloop edge has the same node at both ends.

        Parameters
        ----------
        G : graph
            A NetworkX graph.
        data : string or bool, optional (default=False)
            Return selfloop edges as two tuples (u, v) (data=False)
            or three-tuples (u, v, datadict) (data=True)
            or three-tuples (u, v, datavalue) (data='attrname')
        keys : bool, optional (default=False)
            If True, return edge keys with each edge.
        default : value, optional (default=None)
            Value used for edges that don't have the requested attribute.
            Only relevant if data is not True or False.

        Returns
        -------
        edgeiter : iterator over edge tuples
            An iterator over all selfloop edges.

        See Also
        --------
        nodes_with_selfloops, number_of_selfloops

        Examples
        --------
        >>> G = nx.MultiGraph()  # or Graph, DiGraph, MultiDiGraph, etc
        >>> ekey = G.add_edge(1, 1)
        >>> ekey = G.add_edge(1, 2)
        >>> list(nx.selfloop_edges(G))
        [(1, 1)]
        >>> list(nx.selfloop_edges(G, data=True))
        [(1, 1, {})]
        >>> list(nx.selfloop_edges(G, keys=True))
        [(1, 1, 0)]
        >>> list(nx.selfloop_edges(G, keys=True, data=True))
        [(1, 1, 0, {})]

    set_edge_attributes(G, values, name=None)
        Sets edge attributes from a given value or dictionary of values.

        .. Warning:: The call order of arguments `values` and `name`
            switched between v1.x & v2.x.

        Parameters
        ----------
        G : NetworkX Graph

        values : scalar value, dict-like
            What the edge attribute should be set to.  If `values` is
            not a dictionary, then it is treated as a single attribute value
            that is then applied to every edge in `G`.  This means that if
            you provide a mutable object, like a list, updates to that object
            will be reflected in the edge attribute for each edge.  The attribute
            name will be `name`.

            If `values` is a dict or a dict of dict, it should be keyed
            by edge tuple to either an attribute value or a dict of attribute
            key/value pairs used to update the edge's attributes.
            For multigraphs, the edge tuples must be of the form ``(u, v, key)``,
            where `u` and `v` are nodes and `key` is the edge key.
            For non-multigraphs, the keys must be tuples of the form ``(u, v)``.

        name : string (optional, default=None)
            Name of the edge attribute to set if values is a scalar.

        Examples
        --------
        After computing some property of the edges of a graph, you may want
        to assign a edge attribute to store the value of that property for
        each edge::

            >>> G = nx.path_graph(3)
            >>> bb = nx.edge_betweenness_centrality(G, normalized=False)
            >>> nx.set_edge_attributes(G, bb, "betweenness")
            >>> G.edges[1, 2]["betweenness"]
            2.0

        If you provide a list as the second argument, updates to the list
        will be reflected in the edge attribute for each edge::

            >>> labels = []
            >>> nx.set_edge_attributes(G, labels, "labels")
            >>> labels.append("foo")
            >>> G.edges[0, 1]["labels"]
            ['foo']
            >>> G.edges[1, 2]["labels"]
            ['foo']

        If you provide a dictionary of dictionaries as the second argument,
        the entire dictionary will be used to update edge attributes::

            >>> G = nx.path_graph(3)
            >>> attrs = {(0, 1): {"attr1": 20, "attr2": "nothing"}, (1, 2): {"attr2": 3}}
            >>> nx.set_edge_attributes(G, attrs)
            >>> G[0][1]["attr1"]
            20
            >>> G[0][1]["attr2"]
            'nothing'
            >>> G[1][2]["attr2"]
            3

        The attributes of one Graph can be used to set those of another.

            >>> H = nx.path_graph(3)
            >>> nx.set_edge_attributes(H, G.edges)

        Note that if the dict contains edges that are not in `G`, they are
        silently ignored::

            >>> G = nx.Graph([(0, 1)])
            >>> nx.set_edge_attributes(G, {(1, 2): {"weight": 2.0}})
            >>> (1, 2) in G.edges()
            False

        For multigraphs, the `values` dict is expected to be keyed by 3-tuples
        including the edge key::

            >>> MG = nx.MultiGraph()
            >>> edges = [(0, 1), (0, 1)]
            >>> MG.add_edges_from(edges)  # Returns list of edge keys
            [0, 1]
            >>> attributes = {(0, 1, 0): {"cost": 21}, (0, 1, 1): {"cost": 7}}
            >>> nx.set_edge_attributes(MG, attributes)
            >>> MG[0][1][0]["cost"]
            21
            >>> MG[0][1][1]["cost"]
            7

        If MultiGraph attributes are desired for a Graph, you must convert the 3-tuple
        multiedge to a 2-tuple edge and the last multiedge's attribute value will
        overwrite the previous values. Continuing from the previous case we get::

            >>> H = nx.path_graph([0, 1, 2])
            >>> nx.set_edge_attributes(H, {(u, v): ed for u, v, ed in MG.edges.data()})
            >>> nx.get_edge_attributes(H, "cost")
            {(0, 1): 7}

    set_node_attributes(G, values, name=None)
        Sets node attributes from a given value or dictionary of values.

        .. Warning:: The call order of arguments `values` and `name`
            switched between v1.x & v2.x.

        Parameters
        ----------
        G : NetworkX Graph

        values : scalar value, dict-like
            What the node attribute should be set to.  If `values` is
            not a dictionary, then it is treated as a single attribute value
            that is then applied to every node in `G`.  This means that if
            you provide a mutable object, like a list, updates to that object
            will be reflected in the node attribute for every node.
            The attribute name will be `name`.

            If `values` is a dict or a dict of dict, it should be keyed
            by node to either an attribute value or a dict of attribute key/value
            pairs used to update the node's attributes.

        name : string (optional, default=None)
            Name of the node attribute to set if values is a scalar.

        Examples
        --------
        After computing some property of the nodes of a graph, you may want
        to assign a node attribute to store the value of that property for
        each node::

            >>> G = nx.path_graph(3)
            >>> bb = nx.betweenness_centrality(G)
            >>> isinstance(bb, dict)
            True
            >>> nx.set_node_attributes(G, bb, "betweenness")
            >>> G.nodes[1]["betweenness"]
            1.0

        If you provide a list as the second argument, updates to the list
        will be reflected in the node attribute for each node::

            >>> G = nx.path_graph(3)
            >>> labels = []
            >>> nx.set_node_attributes(G, labels, "labels")
            >>> labels.append("foo")
            >>> G.nodes[0]["labels"]
            ['foo']
            >>> G.nodes[1]["labels"]
            ['foo']
            >>> G.nodes[2]["labels"]
            ['foo']

        If you provide a dictionary of dictionaries as the second argument,
        the outer dictionary is assumed to be keyed by node to an inner
        dictionary of node attributes for that node::

            >>> G = nx.path_graph(3)
            >>> attrs = {0: {"attr1": 20, "attr2": "nothing"}, 1: {"attr2": 3}}
            >>> nx.set_node_attributes(G, attrs)
            >>> G.nodes[0]["attr1"]
            20
            >>> G.nodes[0]["attr2"]
            'nothing'
            >>> G.nodes[1]["attr2"]
            3
            >>> G.nodes[2]
            {}

        Note that if the dictionary contains nodes that are not in `G`, the
        values are silently ignored::

            >>> G = nx.Graph()
            >>> G.add_node(0)
            >>> nx.set_node_attributes(G, {0: "red", 1: "blue"}, name="color")
            >>> G.nodes[0]["color"]
            'red'
            >>> 1 in G.nodes
            False

    subgraph(G, nbunch)
        Returns the subgraph induced on nodes in nbunch.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        nbunch : list, iterable
           A container of nodes that will be iterated through once (thus
           it should be an iterator or be iterable).  Each element of the
           container should be a valid node type: any hashable type except
           None.  If nbunch is None, return all edges data in the graph.
           Nodes in nbunch that are not in the graph will be (quietly)
           ignored.

        Notes
        -----
        subgraph(G) calls G.subgraph()

    to_directed(graph)
        Returns a directed view of the graph `graph`.

        Identical to graph.to_directed(as_view=True)
        Note that graph.to_directed defaults to `as_view=False`
        while this function always provides a view.

    to_undirected(graph)
        Returns an undirected view of the graph `graph`.

        Identical to graph.to_undirected(as_view=True)
        Note that graph.to_undirected defaults to `as_view=False`
        while this function always provides a view.

DATA
    __all__ = ['nodes', 'edges', 'degree', 'degree_histogram', 'neighbors'...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\classes\function.py

networkx.gaussian_random_partition_graph
Python Library Documentation: function gaussian_random_partition_graph in module networkx.generators.community

gaussian_random_partition_graph(n, s, v, p_in, p_out, directed=False, seed=None, *, backend=None, **backend_kwargs)
    Generate a Gaussian random partition graph.

    A Gaussian random partition graph is created by creating k partitions
    each with a size drawn from a normal distribution with mean s and variance
    s/v. Nodes are connected within clusters with probability p_in and
    between clusters with probability p_out[1]

    Parameters
    ----------
    n : int
      Number of nodes in the graph
    s : float
      Mean cluster size
    v : float
      Shape parameter. The variance of cluster size distribution is s/v.
    p_in : float
      Probability of intra cluster connection.
    p_out : float
      Probability of inter cluster connection.
    directed : boolean, optional default=False
      Whether to create a directed graph or not
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : NetworkX Graph or DiGraph
      gaussian random partition graph

    Raises
    ------
    NetworkXError
      If s is > n
      If p_in or p_out is not in [0,1]

    Notes
    -----
    Note the number of partitions is dependent on s,v and n, and that the
    last partition may be considerably smaller, as it is sized to simply
    fill out the nodes [1]

    See Also
    --------
    random_partition_graph

    Examples
    --------
    >>> G = nx.gaussian_random_partition_graph(100, 10, 10, 0.25, 0.1)
    >>> len(G)
    100

    References
    ----------
    .. [1] Ulrik Brandes, Marco Gaertler, Dorothea Wagner,
       Experiments on Graph Clustering Algorithms,
       In the proceedings of the 11th Europ. Symp. Algorithms, 2003.
networkx.general_random_intersection_graph
Python Library Documentation: function general_random_intersection_graph in module networkx.generators.intersection

general_random_intersection_graph(n, m, p, seed=None, *, backend=None, **backend_kwargs)
    Returns a random intersection graph with independent probabilities
    for connections between node and attribute sets.

    Parameters
    ----------
    n : int
        The number of nodes in the first bipartite set (nodes)
    m : int
        The number of nodes in the second bipartite set (attributes)
    p : list of floats of length m
        Probabilities for connecting nodes to each attribute
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    See Also
    --------
    gnp_random_graph, uniform_random_intersection_graph

    References
    ----------
    .. [1] Nikoletseas, S. E., Raptopoulos, C., and Spirakis, P. G.
       The existence and efficient construction of large independent sets
       in general random intersection graphs. In ICALP (2004), J. D´ıaz,
       J. Karhum¨aki, A. Lepist¨o, and D. Sannella, Eds., vol. 3142
       of Lecture Notes in Computer Science, Springer, pp. 1029–1040.
networkx.generalized_degree
Python Library Documentation: function generalized_degree in module networkx.algorithms.cluster

generalized_degree(G, nodes=None, *, backend=None, **backend_kwargs)
    Compute the generalized degree for nodes.

    For each node, the generalized degree shows how many edges of given
    triangle multiplicity the node is connected to. The triangle multiplicity
    of an edge is the number of triangles an edge participates in. The
    generalized degree of node :math:`i` can be written as a vector
    :math:`\mathbf{k}_i=(k_i^{(0)}, \dotsc, k_i^{(N-2)})` where
    :math:`k_i^{(j)}` is the number of edges attached to node :math:`i` that
    participate in :math:`j` triangles.

    Parameters
    ----------
    G : graph

    nodes : container of nodes, optional (default=all nodes in G)
       Compute the generalized degree for nodes in this container.

    Returns
    -------
    out : Counter, or dictionary of Counters
       Generalized degree of specified nodes. The Counter is keyed by edge
       triangle multiplicity.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> print(nx.generalized_degree(G, 0))
    Counter({3: 4})
    >>> print(nx.generalized_degree(G))
    {0: Counter({3: 4}), 1: Counter({3: 4}), 2: Counter({3: 4}), 3: Counter({3: 4}), 4: Counter({3: 4})}

    To recover the number of triangles attached to a node:

    >>> k1 = nx.generalized_degree(G, 0)
    >>> sum([k * v for k, v in k1.items()]) / 2 == nx.triangles(G, 0)
    True

    Notes
    -----
    Self loops are ignored.

    In a network of N nodes, the highest triangle multiplicity an edge can have
    is N-2.

    The return value does not include a `zero` entry if no edges of a
    particular triangle multiplicity are present.

    The number of triangles node :math:`i` is attached to can be recovered from
    the generalized degree :math:`\mathbf{k}_i=(k_i^{(0)}, \dotsc,
    k_i^{(N-2)})` by :math:`(k_i^{(1)}+2k_i^{(2)}+\dotsc +(N-2)k_i^{(N-2)})/2`.

    References
    ----------
    .. [1] Networks with arbitrary edge multiplicities by V. Zlatić,
        D. Garlaschelli and G. Caldarelli, EPL (Europhysics Letters),
        Volume 97, Number 2 (2012).
        https://iopscience.iop.org/article/10.1209/0295-5075/97/28005
networkx.generate_adjlist
Python Library Documentation: function generate_adjlist in module networkx.readwrite.adjlist

generate_adjlist(G, delimiter=' ')
    Generate a single line of the graph G in adjacency list format.

    Parameters
    ----------
    G : NetworkX graph

    delimiter : string, optional
       Separator for node labels

    Returns
    -------
    lines : string
        Lines of data in adjlist format.

    Examples
    --------
    >>> G = nx.lollipop_graph(4, 3)
    >>> for line in nx.generate_adjlist(G):
    ...     print(line)
    0 1 2 3
    1 2 3
    2 3
    3 4
    4 5
    5 6
    6

    See Also
    --------
    write_adjlist, read_adjlist

    Notes
    -----
    The default `delimiter=" "` will result in unexpected results if node names contain
    whitespace characters. To avoid this problem, specify an alternate delimiter when spaces are
    valid in node names.

    NB: This option is not available for data that isn't user-generated.
networkx.generate_edgelist
Python Library Documentation: function generate_edgelist in module networkx.readwrite.edgelist

generate_edgelist(G, delimiter=' ', data=True)
    Generate a single line of the graph G in edge list format.

    Parameters
    ----------
    G : NetworkX graph

    delimiter : string, optional
       Separator for node labels

    data : bool or list of keys
       If False generate no edge data.  If True use a dictionary
       representation of edge data.  If a list of keys use a list of data
       values corresponding to the keys.

    Returns
    -------
    lines : string
        Lines of data in adjlist format.

    Examples
    --------
    >>> G = nx.lollipop_graph(4, 3)
    >>> G[1][2]["weight"] = 3
    >>> G[3][4]["capacity"] = 12
    >>> for line in nx.generate_edgelist(G, data=False):
    ...     print(line)
    0 1
    0 2
    0 3
    1 2
    1 3
    2 3
    3 4
    4 5
    5 6

    >>> for line in nx.generate_edgelist(G):
    ...     print(line)
    0 1 {}
    0 2 {}
    0 3 {}
    1 2 {'weight': 3}
    1 3 {}
    2 3 {}
    3 4 {'capacity': 12}
    4 5 {}
    5 6 {}

    >>> for line in nx.generate_edgelist(G, data=["weight"]):
    ...     print(line)
    0 1
    0 2
    0 3
    1 2 3
    1 3
    2 3
    3 4
    4 5
    5 6

    See Also
    --------
    write_adjlist, read_adjlist
networkx.generate_gexf
Python Library Documentation: function generate_gexf in module networkx.readwrite.gexf

generate_gexf(G, encoding='utf-8', prettyprint=True, version='1.2draft')
    Generate lines of GEXF format representation of G.

    "GEXF (Graph Exchange XML Format) is a language for describing
    complex networks structures, their associated data and dynamics" [1]_.

    Parameters
    ----------
    G : graph
    A NetworkX graph
    encoding : string (optional, default: 'utf-8')
    Encoding for text data.
    prettyprint : bool (optional, default: True)
    If True use line breaks and indenting in output XML.
    version : string (default: 1.2draft)
    Version of GEFX File Format (see http://gexf.net/schema.html)
    Supported values: "1.1draft", "1.2draft"


    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> linefeed = chr(10)  # linefeed=

    >>> s = linefeed.join(nx.generate_gexf(G))
    >>> for line in nx.generate_gexf(G):  # doctest: +SKIP
    ...     print(line)

    Notes
    -----
    This implementation does not support mixed graphs (directed and undirected
    edges together).

    The node id attribute is set to be the string of the node label.
    If you want to specify an id use set it as node data, e.g.
    node['a']['id']=1 to set the id of node 'a' to 1.

    References
    ----------
    .. [1] GEXF File Format, https://gephi.org/gexf/format/
networkx.generate_gml
Python Library Documentation: function generate_gml in module networkx.readwrite.gml

generate_gml(G, stringizer=None)
    Generate a single entry of the graph `G` in GML format.

    Parameters
    ----------
    G : NetworkX graph
        The graph to be converted to GML.

    stringizer : callable, optional
        A `stringizer` which converts non-int/non-float/non-dict values into
        strings. If it cannot convert a value into a string, it should raise a
        `ValueError` to indicate that. Default value: None.

    Returns
    -------
    lines: generator of strings
        Lines of GML data. Newlines are not appended.

    Raises
    ------
    NetworkXError
        If `stringizer` cannot convert a value into a string, or the value to
        convert is not a string while `stringizer` is None.

    See Also
    --------
    literal_stringizer

    Notes
    -----
    Graph attributes named 'directed', 'multigraph', 'node' or
    'edge', node attributes named 'id' or 'label', edge attributes
    named 'source' or 'target' (or 'key' if `G` is a multigraph)
    are ignored because these attribute names are used to encode the graph
    structure.

    GML files are stored using a 7-bit ASCII encoding with any extended
    ASCII characters (iso8859-1) appearing as HTML character entities.
    Without specifying a `stringizer`/`destringizer`, the code is capable of
    writing `int`/`float`/`str`/`dict`/`list` data as required by the GML
    specification.  For writing other data types, and for reading data other
    than `str` you need to explicitly supply a `stringizer`/`destringizer`.

    For additional documentation on the GML file format, please see the
    `GML url <https://web.archive.org/web/20190207140002/http://www.fim.uni-passau.de/index.php?id=17297&L=1>`_.

    See the module docstring :mod:`networkx.readwrite.gml` for more details.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_node("1")
    >>> print("\n".join(nx.generate_gml(G)))
    graph [
      node [
        id 0
        label "1"
      ]
    ]
    >>> G = nx.MultiGraph([("a", "b"), ("a", "b")])
    >>> print("\n".join(nx.generate_gml(G)))
    graph [
      multigraph 1
      node [
        id 0
        label "a"
      ]
      node [
        id 1
        label "b"
      ]
      edge [
        source 0
        target 1
        key 0
      ]
      edge [
        source 0
        target 1
        key 1
      ]
    ]
networkx.generate_graphml
Python Library Documentation: function generate_graphml in module networkx.readwrite.graphml

generate_graphml(G, encoding='utf-8', prettyprint=True, named_key_ids=False, edge_id_from_attribute=None)
    Generate GraphML lines for G

    Parameters
    ----------
    G : graph
       A networkx graph
    encoding : string (optional)
       Encoding for text data.
    prettyprint : bool (optional)
       If True use line breaks and indenting in output XML.
    named_key_ids : bool (optional)
       If True use attr.name as value for key elements' id attribute.
    edge_id_from_attribute : dict key (optional)
        If provided, the graphml edge id is set by looking up the corresponding
        edge data attribute keyed by this parameter. If `None` or the key does not exist in edge data,
        the edge id is set by the edge key if `G` is a MultiGraph, else the edge id is left unset.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> linefeed = chr(10)  # linefeed =

    >>> s = linefeed.join(nx.generate_graphml(G))
    >>> for line in nx.generate_graphml(G):  # doctest: +SKIP
    ...     print(line)

    Notes
    -----
    This implementation does not support mixed graphs (directed and unidirected
    edges together) hyperedges, nested graphs, or ports.
networkx.generate_multiline_adjlist
Python Library Documentation: function generate_multiline_adjlist in module networkx.readwrite.multiline_adjlist

generate_multiline_adjlist(G, delimiter=' ')
    Generate a single line of the graph G in multiline adjacency list format.

    Parameters
    ----------
    G : NetworkX graph

    delimiter : string, optional
       Separator for node labels

    Returns
    -------
    lines : string
        Lines of data in multiline adjlist format.

    Examples
    --------
    >>> G = nx.lollipop_graph(4, 3)
    >>> for line in nx.generate_multiline_adjlist(G):
    ...     print(line)
    0 3
    1 {}
    2 {}
    3 {}
    1 2
    2 {}
    3 {}
    2 1
    3 {}
    3 1
    4 {}
    4 1
    5 {}
    5 1
    6 {}
    6 0

    See Also
    --------
    write_multiline_adjlist, read_multiline_adjlist
networkx.generate_network_text
Python Library Documentation: function generate_network_text in module networkx.readwrite.text

generate_network_text(graph, with_labels=True, sources=None, max_depth=None, ascii_only=False, vertical_chains=False)
    Generate lines in the "network text" format

    This works via a depth-first traversal of the graph and writing a line for
    each unique node encountered. Non-tree edges are written to the right of
    each node, and connection to a non-tree edge is indicated with an ellipsis.
    This representation works best when the input graph is a forest, but any
    graph can be represented.

    This notation is original to networkx, although it is simple enough that it
    may be known in existing literature. See #5602 for details. The procedure
    is summarized as follows:

    1. Given a set of source nodes (which can be specified, or automatically
    discovered via finding the (strongly) connected components and choosing one
    node with minimum degree from each), we traverse the graph in depth first
    order.

    2. Each reachable node will be printed exactly once on it's own line.

    3. Edges are indicated in one of four ways:

        a. a parent "L-style" connection on the upper left. This corresponds to
        a traversal in the directed DFS tree.

        b. a backref "<-style" connection shown directly on the right. For
        directed graphs, these are drawn for any incoming edges to a node that
        is not a parent edge. For undirected graphs, these are drawn for only
        the non-parent edges that have already been represented (The edges that
        have not been represented will be handled in the recursive case).

        c. a child "L-style" connection on the lower right. Drawing of the
        children are handled recursively.

        d. if ``vertical_chains`` is true, and a parent node only has one child
        a "vertical-style" edge is drawn between them.

    4. The children of each node (wrt the directed DFS tree) are drawn
    underneath and to the right of it. In the case that a child node has already
    been drawn the connection is replaced with an ellipsis ("...") to indicate
    that there is one or more connections represented elsewhere.

    5. If a maximum depth is specified, an edge to nodes past this maximum
    depth will be represented by an ellipsis.

    6. If a node has a truthy "collapse" value, then we do not traverse past
    that node.

    Parameters
    ----------
    graph : nx.DiGraph | nx.Graph
        Graph to represent

    with_labels : bool | str
        If True will use the "label" attribute of a node to display if it
        exists otherwise it will use the node value itself. If given as a
        string, then that attribute name will be used instead of "label".
        Defaults to True.

    sources : List
        Specifies which nodes to start traversal from. Note: nodes that are not
        reachable from one of these sources may not be shown. If unspecified,
        the minimal set of nodes needed to reach all others will be used.

    max_depth : int | None
        The maximum depth to traverse before stopping. Defaults to None.

    ascii_only : Boolean
        If True only ASCII characters are used to construct the visualization

    vertical_chains : Boolean
        If True, chains of nodes will be drawn vertically when possible.

    Yields
    ------
    str : a line of generated text

    Examples
    --------
    >>> graph = nx.path_graph(10)
    >>> graph.add_node("A")
    >>> graph.add_node("B")
    >>> graph.add_node("C")
    >>> graph.add_node("D")
    >>> graph.add_edge(9, "A")
    >>> graph.add_edge(9, "B")
    >>> graph.add_edge(9, "C")
    >>> graph.add_edge("C", "D")
    >>> graph.add_edge("C", "E")
    >>> graph.add_edge("C", "F")
    >>> nx.write_network_text(graph)
    ╙── 0
        └── 1
            └── 2
                └── 3
                    └── 4
                        └── 5
                            └── 6
                                └── 7
                                    └── 8
                                        └── 9
                                            ├── A
                                            ├── B
                                            └── C
                                                ├── D
                                                ├── E
                                                └── F
    >>> nx.write_network_text(graph, vertical_chains=True)
    ╙── 0
        │
        1
        │
        2
        │
        3
        │
        4
        │
        5
        │
        6
        │
        7
        │
        8
        │
        9
        ├── A
        ├── B
        └── C
            ├── D
            ├── E
            └── F
networkx.generate_pajek
Python Library Documentation: function generate_pajek in module networkx.readwrite.pajek

generate_pajek(G)
    Generate lines in Pajek graph format.

    Parameters
    ----------
    G : graph
       A Networkx graph

    References
    ----------
    See http://vlado.fmf.uni-lj.si/pub/networks/pajek/doc/draweps.htm
    for format information.
networkx.generate_random_paths
Python Library Documentation: function generate_random_paths in module networkx.algorithms.similarity

generate_random_paths(G, sample_size, path_length=5, index_map=None, weight='weight', seed=None, *, backend=None, **backend_kwargs)
    Randomly generate `sample_size` paths of length `path_length`.

    Parameters
    ----------
    G : NetworkX graph
        A NetworkX graph
    sample_size : integer
        The number of paths to generate. This is ``R`` in [1]_.
    path_length : integer (default = 5)
        The maximum size of the path to randomly generate.
        This is ``T`` in [1]_. According to the paper, ``T >= 5`` is
        recommended.
    index_map : dictionary, optional
        If provided, this will be populated with the inverted
        index of nodes mapped to the set of generated random path
        indices within ``paths``.
    weight : string or None, optional (default="weight")
        The name of an edge attribute that holds the numerical value
        used as a weight. If None then each edge has weight 1.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    paths : generator of lists
        Generator of `sample_size` paths each with length `path_length`.

    Examples
    --------
    Note that the return value is the list of paths:

    >>> G = nx.star_graph(3)
    >>> random_path = nx.generate_random_paths(G, 2)

    By passing a dictionary into `index_map`, it will build an
    inverted index mapping of nodes to the paths in which that node is present:

    >>> G = nx.star_graph(3)
    >>> index_map = {}
    >>> random_path = nx.generate_random_paths(G, 3, index_map=index_map)
    >>> paths_containing_node_0 = [
    ...     random_path[path_idx] for path_idx in index_map.get(0, [])
    ... ]

    References
    ----------
    .. [1] Zhang, J., Tang, J., Ma, C., Tong, H., Jing, Y., & Li, J.
           Panther: Fast top-k similarity search on large networks.
           In Proceedings of the ACM SIGKDD International Conference
           on Knowledge Discovery and Data Mining (Vol. 2015-August, pp. 1445–1454).
           Association for Computing Machinery. https://doi.org/10.1145/2783258.2783267.
networkx.generators
Python Library Documentation: package networkx.generators in networkx

NAME
    networkx.generators - A package for generating various graphs in networkx.

PACKAGE CONTENTS
    atlas
    classic
    cographs
    community
    degree_seq
    directed
    duplication
    ego
    expanders
    geometric
    harary_graph
    internet_as_graphs
    intersection
    interval_graph
    joint_degree_seq
    lattice
    line
    mycielski
    nonisomorphic_trees
    random_clustered
    random_graphs
    small
    social
    spectral_graph_forge
    stochastic
    sudoku
    tests (package)
    time_series
    trees
    triads

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\__init__.py

networkx.generic
Python Library Documentation: module networkx.algorithms.shortest_paths.generic in networkx.algorithms.shortest_paths

NAME
    networkx.algorithms.shortest_paths.generic - Compute the shortest paths and path lengths between nodes in the graph.

DESCRIPTION
    These algorithms work with undirected and directed graphs.

FUNCTIONS
    all_pairs_all_shortest_paths(G, weight=None, method='dijkstra', *, backend=None, **backend_kwargs)
        Compute all shortest paths between all nodes.

        Parameters
        ----------
        G : NetworkX graph

        weight : None, string or function, optional (default = None)
            If None, every edge has weight/distance/cost 1.
            If a string, use this edge attribute as the edge weight.
            Any edge attribute not present defaults to 1.
            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly
            three positional arguments: the two endpoints of an edge and
            the dictionary of edge attributes for that edge.
            The function must return a number.

        method : string, optional (default = 'dijkstra')
           The algorithm to use to compute the path lengths.
           Supported options: 'dijkstra', 'bellman-ford'.
           Other inputs produce a ValueError.
           If `weight` is None, unweighted graph methods are used, and this
           suggestion is ignored.

        Returns
        -------
        paths : generator of dictionary
            Dictionary of arrays, keyed by source and target, of all shortest paths.

        Raises
        ------
        ValueError
            If `method` is not among the supported options.

        Examples
        --------
        >>> G = nx.cycle_graph(4)
        >>> dict(nx.all_pairs_all_shortest_paths(G))[0][2]
        [[0, 1, 2], [0, 3, 2]]
        >>> dict(nx.all_pairs_all_shortest_paths(G))[0][3]
        [[0, 3]]

        Notes
        -----
        There may be multiple shortest paths with equal lengths. Unlike
        all_pairs_shortest_path, this method returns all shortest paths.

        See Also
        --------
        all_pairs_shortest_path
        single_source_all_shortest_paths

    all_shortest_paths(G, source, target, weight=None, method='dijkstra', *, backend=None, **backend_kwargs)
        Compute all shortest simple paths in the graph.

        Parameters
        ----------
        G : NetworkX graph

        source : node
           Starting node for path.

        target : node
           Ending node for path.

        weight : None, string or function, optional (default = None)
            If None, every edge has weight/distance/cost 1.
            If a string, use this edge attribute as the edge weight.
            Any edge attribute not present defaults to 1.
            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly
            three positional arguments: the two endpoints of an edge and
            the dictionary of edge attributes for that edge.
            The function must return a number.

        method : string, optional (default = 'dijkstra')
           The algorithm to use to compute the path lengths.
           Supported options: 'dijkstra', 'bellman-ford'.
           Other inputs produce a ValueError.
           If `weight` is None, unweighted graph methods are used, and this
           suggestion is ignored.

        Returns
        -------
        paths : generator of lists
            A generator of all paths between source and target.

        Raises
        ------
        ValueError
            If `method` is not among the supported options.

        NetworkXNoPath
            If `target` cannot be reached from `source`.

        Examples
        --------
        >>> G = nx.Graph()
        >>> nx.add_path(G, [0, 1, 2])
        >>> nx.add_path(G, [0, 10, 2])
        >>> print([p for p in nx.all_shortest_paths(G, source=0, target=2)])
        [[0, 1, 2], [0, 10, 2]]

        Notes
        -----
        There may be many shortest paths between the source and target.  If G
        contains zero-weight cycles, this function will not produce all shortest
        paths because doing so would produce infinitely many paths of unbounded
        length -- instead, we only produce the shortest simple paths.

        See Also
        --------
        shortest_path
        single_source_shortest_path
        all_pairs_shortest_path

    average_shortest_path_length(G, weight=None, method=None, *, backend=None, **backend_kwargs)
        Returns the average shortest path length.

        The average shortest path length is

        .. math::

           a =\sum_{\substack{s,t \in V \\ s\neq t}} \frac{d(s, t)}{n(n-1)}

        where `V` is the set of nodes in `G`,
        `d(s, t)` is the shortest path from `s` to `t`,
        and `n` is the number of nodes in `G`.

        .. versionchanged:: 3.0
           An exception is raised for directed graphs that are not strongly
           connected.

        Parameters
        ----------
        G : NetworkX graph

        weight : None, string or function, optional (default = None)
            If None, every edge has weight/distance/cost 1.
            If a string, use this edge attribute as the edge weight.
            Any edge attribute not present defaults to 1.
            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly
            three positional arguments: the two endpoints of an edge and
            the dictionary of edge attributes for that edge.
            The function must return a number.

        method : string, optional (default = 'unweighted' or 'dijkstra')
            The algorithm to use to compute the path lengths.
            Supported options are 'unweighted', 'dijkstra', 'bellman-ford',
            'floyd-warshall' and 'floyd-warshall-numpy'.
            Other method values produce a ValueError.
            The default method is 'unweighted' if `weight` is None,
            otherwise the default method is 'dijkstra'.

        Raises
        ------
        NetworkXPointlessConcept
            If `G` is the null graph (that is, the graph on zero nodes).

        NetworkXError
            If `G` is not connected (or not strongly connected, in the case
            of a directed graph).

        ValueError
            If `method` is not among the supported options.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> nx.average_shortest_path_length(G)
        2.0

        For disconnected graphs, you can compute the average shortest path
        length for each component

        >>> G = nx.Graph([(1, 2), (3, 4)])
        >>> for C in (G.subgraph(c).copy() for c in nx.connected_components(G)):
        ...     print(nx.average_shortest_path_length(C))
        1.0
        1.0

    has_path(G, source, target, *, backend=None, **backend_kwargs)
        Returns *True* if *G* has a path from *source* to *target*.

        Parameters
        ----------
        G : NetworkX graph

        source : node
           Starting node for path

        target : node
           Ending node for path

    shortest_path(G, source=None, target=None, weight=None, method='dijkstra', *, backend=None, **backend_kwargs)
        Compute shortest paths in the graph.

        Parameters
        ----------
        G : NetworkX graph

        source : node, optional
            Starting node for path. If not specified, compute shortest
            paths for each possible starting node.

        target : node, optional
            Ending node for path. If not specified, compute shortest
            paths to all possible nodes.

        weight : None, string or function, optional (default = None)
            If None, every edge has weight/distance/cost 1.
            If a string, use this edge attribute as the edge weight.
            Any edge attribute not present defaults to 1.
            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly
            three positional arguments: the two endpoints of an edge and
            the dictionary of edge attributes for that edge.
            The function must return a number.

        method : string, optional (default = 'dijkstra')
            The algorithm to use to compute the path.
            Supported options: 'dijkstra', 'bellman-ford'.
            Other inputs produce a ValueError.
            If `weight` is None, unweighted graph methods are used, and this
            suggestion is ignored.

        Returns
        -------
        path: list or dictionary
            All returned paths include both the source and target in the path.

            If the source and target are both specified, return a single list
            of nodes in a shortest path from the source to the target.

            If only the source is specified, return a dictionary keyed by
            targets with a list of nodes in a shortest path from the source
            to one of the targets.

            If only the target is specified, return a dictionary keyed by
            sources with a list of nodes in a shortest path from one of the
            sources to the target.

            If neither the source nor target are specified return a dictionary
            of dictionaries with path[source][target]=[list of nodes in path].

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        ValueError
            If `method` is not among the supported options.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> print(nx.shortest_path(G, source=0, target=4))
        [0, 1, 2, 3, 4]
        >>> p = nx.shortest_path(G, source=0)  # target not specified
        >>> p[3]  # shortest path from source=0 to target=3
        [0, 1, 2, 3]
        >>> p = nx.shortest_path(G, target=4)  # source not specified
        >>> p[1]  # shortest path from source=1 to target=4
        [1, 2, 3, 4]
        >>> p = dict(nx.shortest_path(G))  # source, target not specified
        >>> p[2][4]  # shortest path from source=2 to target=4
        [2, 3, 4]

        Notes
        -----
        There may be more than one shortest path between a source and target.
        This returns only one of them.

        See Also
        --------
        all_pairs_shortest_path
        all_pairs_dijkstra_path
        all_pairs_bellman_ford_path
        single_source_shortest_path
        single_source_dijkstra_path
        single_source_bellman_ford_path

    shortest_path_length(G, source=None, target=None, weight=None, method='dijkstra', *, backend=None, **backend_kwargs)
        Compute shortest path lengths in the graph.

        Parameters
        ----------
        G : NetworkX graph

        source : node, optional
            Starting node for path.
            If not specified, compute shortest path lengths using all nodes as
            source nodes.

        target : node, optional
            Ending node for path.
            If not specified, compute shortest path lengths using all nodes as
            target nodes.

        weight : None, string or function, optional (default = None)
            If None, every edge has weight/distance/cost 1.
            If a string, use this edge attribute as the edge weight.
            Any edge attribute not present defaults to 1.
            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly
            three positional arguments: the two endpoints of an edge and
            the dictionary of edge attributes for that edge.
            The function must return a number.

        method : string, optional (default = 'dijkstra')
            The algorithm to use to compute the path length.
            Supported options: 'dijkstra', 'bellman-ford'.
            Other inputs produce a ValueError.
            If `weight` is None, unweighted graph methods are used, and this
            suggestion is ignored.

        Returns
        -------
        length: number or iterator
            If the source and target are both specified, return the length of
            the shortest path from the source to the target.

            If only the source is specified, return a dict keyed by target
            to the shortest path length from the source to that target.

            If only the target is specified, return a dict keyed by source
            to the shortest path length from that source to the target.

            If neither the source nor target are specified, return an iterator
            over (source, dictionary) where dictionary is keyed by target to
            shortest path length from source to that target.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        NetworkXNoPath
            If no path exists between source and target.

        ValueError
            If `method` is not among the supported options.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> nx.shortest_path_length(G, source=0, target=4)
        4
        >>> p = nx.shortest_path_length(G, source=0)  # target not specified
        >>> p[4]
        4
        >>> p = nx.shortest_path_length(G, target=4)  # source not specified
        >>> p[0]
        4
        >>> p = dict(nx.shortest_path_length(G))  # source,target not specified
        >>> p[0][4]
        4

        Notes
        -----
        The length of the path is always 1 less than the number of nodes involved
        in the path since the length measures the number of edges followed.

        For digraphs this returns the shortest directed path length. To find path
        lengths in the reverse direction use G.reverse(copy=False) first to flip
        the edge orientation.

        See Also
        --------
        all_pairs_shortest_path_length
        all_pairs_dijkstra_path_length
        all_pairs_bellman_ford_path_length
        single_source_shortest_path_length
        single_source_dijkstra_path_length
        single_source_bellman_ford_path_length

    single_source_all_shortest_paths(G, source, weight=None, method='dijkstra', *, backend=None, **backend_kwargs)
        Compute all shortest simple paths from the given source in the graph.

        Parameters
        ----------
        G : NetworkX graph

        source : node
           Starting node for path.

        weight : None, string or function, optional (default = None)
            If None, every edge has weight/distance/cost 1.
            If a string, use this edge attribute as the edge weight.
            Any edge attribute not present defaults to 1.
            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly
            three positional arguments: the two endpoints of an edge and
            the dictionary of edge attributes for that edge.
            The function must return a number.

        method : string, optional (default = 'dijkstra')
           The algorithm to use to compute the path lengths.
           Supported options: 'dijkstra', 'bellman-ford'.
           Other inputs produce a ValueError.
           If `weight` is None, unweighted graph methods are used, and this
           suggestion is ignored.

        Returns
        -------
        paths : generator of dictionary
            A generator of all paths between source and all nodes in the graph.

        Raises
        ------
        ValueError
            If `method` is not among the supported options.

        Examples
        --------
        >>> G = nx.Graph()
        >>> nx.add_path(G, [0, 1, 2, 3, 0])
        >>> dict(nx.single_source_all_shortest_paths(G, source=0))
        {0: [[0]], 1: [[0, 1]], 2: [[0, 1, 2], [0, 3, 2]], 3: [[0, 3]]}

        Notes
        -----
        There may be many shortest paths between the source and target.  If G
        contains zero-weight cycles, this function will not produce all shortest
        paths because doing so would produce infinitely many paths of unbounded
        length -- instead, we only produce the shortest simple paths.

        See Also
        --------
        shortest_path
        all_shortest_paths
        single_source_shortest_path
        all_pairs_shortest_path
        all_pairs_all_shortest_paths

DATA
    __all__ = ['shortest_path', 'all_shortest_paths', 'single_source_all_s...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\shortest_paths\generic.py

networkx.generic_bfs_edges
Python Library Documentation: function generic_bfs_edges in module networkx.algorithms.traversal.breadth_first_search

generic_bfs_edges(G, source, neighbors=None, depth_limit=None, *, backend=None, **backend_kwargs)
    Iterate over edges in a breadth-first search.

    The breadth-first search begins at `source` and enqueues the
    neighbors of newly visited nodes specified by the `neighbors`
    function.

    Parameters
    ----------
    G : NetworkX graph

    source : node
        Starting node for the breadth-first search; this function
        iterates over only those edges in the component reachable from
        this node.

    neighbors : function
        A function that takes a newly visited node of the graph as input
        and returns an *iterator* (not just a list) of nodes that are
        neighbors of that node with custom ordering. If not specified, this is
        just the ``G.neighbors`` method, but in general it can be any function
        that returns an iterator over some or all of the neighbors of a
        given node, in any order.

    depth_limit : int, optional(default=len(G))
        Specify the maximum search depth.

    Yields
    ------
    edge
        Edges in the breadth-first search starting from `source`.

    Examples
    --------
    >>> G = nx.path_graph(7)
    >>> list(nx.generic_bfs_edges(G, source=0))
    [(0, 1), (1, 2), (2, 3), (3, 4), (4, 5), (5, 6)]
    >>> list(nx.generic_bfs_edges(G, source=2))
    [(2, 1), (2, 3), (1, 0), (3, 4), (4, 5), (5, 6)]
    >>> list(nx.generic_bfs_edges(G, source=2, depth_limit=2))
    [(2, 1), (2, 3), (1, 0), (3, 4)]

    The `neighbors` param can be used to specify the visitation order of each
    node's neighbors generically. In the following example, we modify the default
    neighbor to return *odd* nodes first:

    >>> def odd_first(n):
    ...     return sorted(G.neighbors(n), key=lambda x: x % 2, reverse=True)

    >>> G = nx.star_graph(5)
    >>> list(nx.generic_bfs_edges(G, source=0))  # Default neighbor ordering
    [(0, 1), (0, 2), (0, 3), (0, 4), (0, 5)]
    >>> list(nx.generic_bfs_edges(G, source=0, neighbors=odd_first))
    [(0, 1), (0, 3), (0, 5), (0, 2), (0, 4)]

    Notes
    -----
    This implementation is from `PADS`_, which was in the public domain
    when it was first accessed in July, 2004.  The modifications
    to allow depth limits are based on the Wikipedia article
    "`Depth-limited-search`_".

    .. _PADS: http://www.ics.uci.edu/~eppstein/PADS/BFS.py
    .. _Depth-limited-search: https://en.wikipedia.org/wiki/Depth-limited_search
networkx.geographical_threshold_graph
Python Library Documentation: function geographical_threshold_graph in module networkx.generators.geometric

geographical_threshold_graph(n, theta, dim=2, pos=None, weight=None, metric=None, p_dist=None, seed=None, *, pos_name='pos', weight_name='weight', backend=None, **backend_kwargs)
    Returns a geographical threshold graph.

    The geographical threshold graph model places $n$ nodes uniformly at
    random in a rectangular domain.  Each node $u$ is assigned a weight
    $w_u$. Two nodes $u$ and $v$ are joined by an edge if

    .. math::

       (w_u + w_v)p_{dist}(r) \ge \theta

    where `r` is the distance between `u` and `v`, `p_dist` is any function of
    `r`, and :math:`\theta` as the threshold parameter. `p_dist` is used to
    give weight to the distance between nodes when deciding whether or not
    they should be connected. The larger `p_dist` is, the more prone nodes
    separated by `r` are to be connected, and vice versa.

    Parameters
    ----------
    n : int or iterable
        Number of nodes or iterable of nodes
    theta: float
        Threshold value
    dim : int, optional
        Dimension of graph
    pos : dict
        Node positions as a dictionary of tuples keyed by node.
    weight : dict
        Node weights as a dictionary of numbers keyed by node.
    metric : function
        A metric on vectors of numbers (represented as lists or
        tuples). This must be a function that accepts two lists (or
        tuples) as input and yields a number as output. The function
        must also satisfy the four requirements of a `metric`_.
        Specifically, if $d$ is the function and $x$, $y$,
        and $z$ are vectors in the graph, then $d$ must satisfy

        1. $d(x, y) \ge 0$,
        2. $d(x, y) = 0$ if and only if $x = y$,
        3. $d(x, y) = d(y, x)$,
        4. $d(x, z) \le d(x, y) + d(y, z)$.

        If this argument is not specified, the Euclidean distance metric is
        used.

        .. _metric: https://en.wikipedia.org/wiki/Metric_%28mathematics%29
    p_dist : function, optional
        Any function used to give weight to the distance between nodes when
        deciding whether or not they should be connected. `p_dist` was
        originally conceived as a probability density function giving the
        probability of connecting two nodes that are of metric distance `r`
        apart. The implementation here allows for more arbitrary definitions
        of `p_dist` that do not need to correspond to valid probability
        density functions. The :mod:`scipy.stats` package has many
        probability density functions implemented and tools for custom
        probability density definitions, and passing the ``.pdf`` method of
        scipy.stats distributions can be used here. If ``p_dist=None``
        (the default), the exponential function :math:`r^{-2}` is used.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    pos_name : string, default="pos"
        The name of the node attribute which represents the position
        in 2D coordinates of the node in the returned graph.
    weight_name : string, default="weight"
        The name of the node attribute which represents the weight
        of the node in the returned graph.

    Returns
    -------
    Graph
        A random geographic threshold graph, undirected and without
        self-loops.

        Each node has a node attribute ``pos`` that stores the
        position of that node in Euclidean space as provided by the
        ``pos`` keyword argument or, if ``pos`` was not provided, as
        generated by this function. Similarly, each node has a node
        attribute ``weight`` that stores the weight of that node as
        provided or as generated.

    Examples
    --------
    Specify an alternate distance metric using the ``metric`` keyword
    argument. For example, to use the `taxicab metric`_ instead of the
    default `Euclidean metric`_::

        >>> dist = lambda x, y: sum(abs(a - b) for a, b in zip(x, y))
        >>> G = nx.geographical_threshold_graph(10, 0.1, metric=dist)

    .. _taxicab metric: https://en.wikipedia.org/wiki/Taxicab_geometry
    .. _Euclidean metric: https://en.wikipedia.org/wiki/Euclidean_distance

    Notes
    -----
    If weights are not specified they are assigned to nodes by drawing randomly
    from the exponential distribution with rate parameter $\lambda=1$.
    To specify weights from a different distribution, use the `weight` keyword
    argument::

    >>> import random
    >>> n = 20
    >>> w = {i: random.expovariate(5.0) for i in range(n)}
    >>> G = nx.geographical_threshold_graph(20, 50, weight=w)

    If node positions are not specified they are randomly assigned from the
    uniform distribution.

    References
    ----------
    .. [1] Masuda, N., Miwa, H., Konno, N.:
       Geographical threshold graphs with small-world and scale-free
       properties.
       Physical Review E 71, 036108 (2005)
    .. [2]  Milan Bradonjić, Aric Hagberg and Allon G. Percus,
       Giant component and connectivity in geographical threshold graphs,
       in Algorithms and Models for the Web-Graph (WAW 2007),
       Antony Bonato and Fan Chung (Eds), pp. 209--216, 2007
networkx.geometric
Python Library Documentation: module networkx.generators.geometric in networkx.generators

NAME
    networkx.generators.geometric - Generators for geometric graphs.

FUNCTIONS
    geographical_threshold_graph(n, theta, dim=2, pos=None, weight=None, metric=None, p_dist=None, seed=None, *, pos_name='pos', weight_name='weight', backend=None, **backend_kwargs)
        Returns a geographical threshold graph.

        The geographical threshold graph model places $n$ nodes uniformly at
        random in a rectangular domain.  Each node $u$ is assigned a weight
        $w_u$. Two nodes $u$ and $v$ are joined by an edge if

        .. math::

           (w_u + w_v)p_{dist}(r) \ge \theta

        where `r` is the distance between `u` and `v`, `p_dist` is any function of
        `r`, and :math:`\theta` as the threshold parameter. `p_dist` is used to
        give weight to the distance between nodes when deciding whether or not
        they should be connected. The larger `p_dist` is, the more prone nodes
        separated by `r` are to be connected, and vice versa.

        Parameters
        ----------
        n : int or iterable
            Number of nodes or iterable of nodes
        theta: float
            Threshold value
        dim : int, optional
            Dimension of graph
        pos : dict
            Node positions as a dictionary of tuples keyed by node.
        weight : dict
            Node weights as a dictionary of numbers keyed by node.
        metric : function
            A metric on vectors of numbers (represented as lists or
            tuples). This must be a function that accepts two lists (or
            tuples) as input and yields a number as output. The function
            must also satisfy the four requirements of a `metric`_.
            Specifically, if $d$ is the function and $x$, $y$,
            and $z$ are vectors in the graph, then $d$ must satisfy

            1. $d(x, y) \ge 0$,
            2. $d(x, y) = 0$ if and only if $x = y$,
            3. $d(x, y) = d(y, x)$,
            4. $d(x, z) \le d(x, y) + d(y, z)$.

            If this argument is not specified, the Euclidean distance metric is
            used.

            .. _metric: https://en.wikipedia.org/wiki/Metric_%28mathematics%29
        p_dist : function, optional
            Any function used to give weight to the distance between nodes when
            deciding whether or not they should be connected. `p_dist` was
            originally conceived as a probability density function giving the
            probability of connecting two nodes that are of metric distance `r`
            apart. The implementation here allows for more arbitrary definitions
            of `p_dist` that do not need to correspond to valid probability
            density functions. The :mod:`scipy.stats` package has many
            probability density functions implemented and tools for custom
            probability density definitions, and passing the ``.pdf`` method of
            scipy.stats distributions can be used here. If ``p_dist=None``
            (the default), the exponential function :math:`r^{-2}` is used.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        pos_name : string, default="pos"
            The name of the node attribute which represents the position
            in 2D coordinates of the node in the returned graph.
        weight_name : string, default="weight"
            The name of the node attribute which represents the weight
            of the node in the returned graph.

        Returns
        -------
        Graph
            A random geographic threshold graph, undirected and without
            self-loops.

            Each node has a node attribute ``pos`` that stores the
            position of that node in Euclidean space as provided by the
            ``pos`` keyword argument or, if ``pos`` was not provided, as
            generated by this function. Similarly, each node has a node
            attribute ``weight`` that stores the weight of that node as
            provided or as generated.

        Examples
        --------
        Specify an alternate distance metric using the ``metric`` keyword
        argument. For example, to use the `taxicab metric`_ instead of the
        default `Euclidean metric`_::

            >>> dist = lambda x, y: sum(abs(a - b) for a, b in zip(x, y))
            >>> G = nx.geographical_threshold_graph(10, 0.1, metric=dist)

        .. _taxicab metric: https://en.wikipedia.org/wiki/Taxicab_geometry
        .. _Euclidean metric: https://en.wikipedia.org/wiki/Euclidean_distance

        Notes
        -----
        If weights are not specified they are assigned to nodes by drawing randomly
        from the exponential distribution with rate parameter $\lambda=1$.
        To specify weights from a different distribution, use the `weight` keyword
        argument::

        >>> import random
        >>> n = 20
        >>> w = {i: random.expovariate(5.0) for i in range(n)}
        >>> G = nx.geographical_threshold_graph(20, 50, weight=w)

        If node positions are not specified they are randomly assigned from the
        uniform distribution.

        References
        ----------
        .. [1] Masuda, N., Miwa, H., Konno, N.:
           Geographical threshold graphs with small-world and scale-free
           properties.
           Physical Review E 71, 036108 (2005)
        .. [2]  Milan Bradonjić, Aric Hagberg and Allon G. Percus,
           Giant component and connectivity in geographical threshold graphs,
           in Algorithms and Models for the Web-Graph (WAW 2007),
           Antony Bonato and Fan Chung (Eds), pp. 209--216, 2007

    geometric_edges(G, radius, p=2, *, pos_name='pos', backend=None, **backend_kwargs)
        Returns edge list of node pairs within `radius` of each other.

        Parameters
        ----------
        G : networkx graph
            The graph from which to generate the edge list. The nodes in `G` should
            have an attribute ``pos`` corresponding to the node position, which is
            used to compute the distance to other nodes.
        radius : scalar
            The distance threshold. Edges are included in the edge list if the
            distance between the two nodes is less than `radius`.
        pos_name : string, default="pos"
            The name of the node attribute which represents the position of each
            node in 2D coordinates. Every node in the Graph must have this attribute.
        p : scalar, default=2
            The `Minkowski distance metric
            <https://en.wikipedia.org/wiki/Minkowski_distance>`_ used to compute
            distances. The default value is 2, i.e. Euclidean distance.

        Returns
        -------
        edges : list
            List of edges whose distances are less than `radius`

        Notes
        -----
        Radius uses Minkowski distance metric `p`.
        If scipy is available, `scipy.spatial.cKDTree` is used to speed computation.

        Examples
        --------
        Create a graph with nodes that have a "pos" attribute representing 2D
        coordinates.

        >>> G = nx.Graph()
        >>> G.add_nodes_from(
        ...     [
        ...         (0, {"pos": (0, 0)}),
        ...         (1, {"pos": (3, 0)}),
        ...         (2, {"pos": (8, 0)}),
        ...     ]
        ... )
        >>> nx.geometric_edges(G, radius=1)
        []
        >>> nx.geometric_edges(G, radius=4)
        [(0, 1)]
        >>> nx.geometric_edges(G, radius=6)
        [(0, 1), (1, 2)]
        >>> nx.geometric_edges(G, radius=9)
        [(0, 1), (0, 2), (1, 2)]

    geometric_soft_configuration_graph(*, beta, n=None, gamma=None, mean_degree=None, kappas=None, seed=None, backend=None, **backend_kwargs)
        Returns a random graph from the geometric soft configuration model.

        The $\mathbb{S}^1$ model [1]_ is the geometric soft configuration model
        which is able to explain many fundamental features of real networks such as
        small-world property, heteregenous degree distributions, high level of
        clustering, and self-similarity.

        In the geometric soft configuration model, a node $i$ is assigned two hidden
        variables: a hidden degree $\kappa_i$, quantifying its popularity, influence,
        or importance, and an angular position $\theta_i$ in a circle abstracting the
        similarity space, where angular distances between nodes are a proxy for their
        similarity. Focusing on the angular position, this model is often called
        the $\mathbb{S}^1$ model (a one-dimensional sphere). The circle's radius is
        adjusted to $R = N/2\pi$, where $N$ is the number of nodes, so that the density
        is set to 1 without loss of generality.

        The connection probability between any pair of nodes increases with
        the product of their hidden degrees (i.e., their combined popularities),
        and decreases with the angular distance between the two nodes.
        Specifically, nodes $i$ and $j$ are connected with the probability

        $p_{ij} = \frac{1}{1 + \frac{d_{ij}^\beta}{\left(\mu \kappa_i \kappa_j\right)^{\max(1, \beta)}}}$

        where $d_{ij} = R\Delta\theta_{ij}$ is the arc length of the circle between
        nodes $i$ and $j$ separated by an angular distance $\Delta\theta_{ij}$.
        Parameters $\mu$ and $\beta$ (also called inverse temperature) control the
        average degree and the clustering coefficient, respectively.

        It can be shown [2]_ that the model undergoes a structural phase transition
        at $\beta=1$ so that for $\beta<1$ networks are unclustered in the thermodynamic
        limit (when $N\to \infty$) whereas for $\beta>1$ the ensemble generates
        networks with finite clustering coefficient.

        The $\mathbb{S}^1$ model can be expressed as a purely geometric model
        $\mathbb{H}^2$ in the hyperbolic plane [3]_ by mapping the hidden degree of
        each node into a radial coordinate as

        $r_i = \hat{R} - \frac{2 \max(1, \beta)}{\beta \zeta} \ln \left(\frac{\kappa_i}{\kappa_0}\right)$

        where $\hat{R}$ is the radius of the hyperbolic disk and $\zeta$ is the curvature,

        $\hat{R} = \frac{2}{\zeta} \ln \left(\frac{N}{\pi}\right)
        - \frac{2\max(1, \beta)}{\beta \zeta} \ln (\mu \kappa_0^2)$

        The connection probability then reads

        $p_{ij} = \frac{1}{1 + \exp\left({\frac{\beta\zeta}{2} (x_{ij} - \hat{R})}\right)}$

        where

        $x_{ij} = r_i + r_j + \frac{2}{\zeta} \ln \frac{\Delta\theta_{ij}}{2}$

        is a good approximation of the hyperbolic distance between two nodes separated
        by an angular distance $\Delta\theta_{ij}$ with radial coordinates $r_i$ and $r_j$.
        For $\beta > 1$, the curvature $\zeta = 1$, for $\beta < 1$, $\zeta = \beta^{-1}$.


        Parameters
        ----------
        Either `n`, `gamma`, `mean_degree` are provided or `kappas`. The values of
        `n`, `gamma`, `mean_degree` (if provided) are used to construct a random
        kappa-dict keyed by node with values sampled from a power-law distribution.

        beta : positive number
            Inverse temperature, controlling the clustering coefficient.
        n : int (default: None)
            Size of the network (number of nodes).
            If not provided, `kappas` must be provided and holds the nodes.
        gamma : float (default: None)
            Exponent of the power-law distribution for hidden degrees `kappas`.
            If not provided, `kappas` must be provided directly.
        mean_degree : float (default: None)
            The mean degree in the network.
            If not provided, `kappas` must be provided directly.
        kappas : dict (default: None)
            A dict keyed by node to its hidden degree value.
            If not provided, random values are computed based on a power-law
            distribution using `n`, `gamma` and `mean_degree`.
        seed : int, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        Graph
            A random geometric soft configuration graph (undirected with no self-loops).
            Each node has three node-attributes:

            - ``kappa`` that represents the hidden degree.

            - ``theta`` the position in the similarity space ($\mathbb{S}^1$) which is
              also the angular position in the hyperbolic plane.

            - ``radius`` the radial position in the hyperbolic plane
              (based on the hidden degree).


        Examples
        --------
        Generate a network with specified parameters:

        >>> G = nx.geometric_soft_configuration_graph(
        ...     beta=1.5, n=100, gamma=2.7, mean_degree=5
        ... )

        Create a geometric soft configuration graph with 100 nodes. The $\beta$ parameter
        is set to 1.5 and the exponent of the powerlaw distribution of the hidden
        degrees is 2.7 with mean value of 5.

        Generate a network with predefined hidden degrees:

        >>> kappas = {i: 10 for i in range(100)}
        >>> G = nx.geometric_soft_configuration_graph(beta=2.5, kappas=kappas)

        Create a geometric soft configuration graph with 100 nodes. The $\beta$ parameter
        is set to 2.5 and all nodes with hidden degree $\kappa=10$.


        References
        ----------
        .. [1] Serrano, M. Á., Krioukov, D., & Boguñá, M. (2008). Self-similarity
           of complex networks and hidden metric spaces. Physical review letters, 100(7), 078701.

        .. [2] van der Kolk, J., Serrano, M. Á., & Boguñá, M. (2022). An anomalous
           topological phase transition in spatial random graphs. Communications Physics, 5(1), 245.

        .. [3] Krioukov, D., Papadopoulos, F., Kitsak, M., Vahdat, A., & Boguná, M. (2010).
           Hyperbolic geometry of complex networks. Physical Review E, 82(3), 036106.

    navigable_small_world_graph(n, p=1, q=1, r=2, dim=2, seed=None, *, backend=None, **backend_kwargs)
        Returns a navigable small-world graph.

        A navigable small-world graph is a directed grid with additional long-range
        connections that are chosen randomly.

          [...] we begin with a set of nodes [...] that are identified with the set
          of lattice points in an $n \times n$ square,
          $\{(i, j): i \in \{1, 2, \ldots, n\}, j \in \{1, 2, \ldots, n\}\}$,
          and we define the *lattice distance* between two nodes $(i, j)$ and
          $(k, l)$ to be the number of "lattice steps" separating them:
          $d((i, j), (k, l)) = |k - i| + |l - j|$.

          For a universal constant $p >= 1$, the node $u$ has a directed edge to
          every other node within lattice distance $p$---these are its *local
          contacts*. For universal constants $q >= 0$ and $r >= 0$ we also
          construct directed edges from $u$ to $q$ other nodes (the *long-range
          contacts*) using independent random trials; the $i$th directed edge from
          $u$ has endpoint $v$ with probability proportional to $[d(u,v)]^{-r}$.

          -- [1]_

        Parameters
        ----------
        n : int
            The length of one side of the lattice; the number of nodes in
            the graph is therefore $n^2$.
        p : int
            The diameter of short range connections. Each node is joined with every
            other node within this lattice distance.
        q : int
            The number of long-range connections for each node.
        r : float
            Exponent for decaying probability of connections.  The probability of
            connecting to a node at lattice distance $d$ is $1/d^r$.
        dim : int
            Dimension of grid
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        References
        ----------
        .. [1] J. Kleinberg. The small-world phenomenon: An algorithmic
           perspective. Proc. 32nd ACM Symposium on Theory of Computing, 2000.

    random_geometric_graph(n, radius, dim=2, pos=None, p=2, seed=None, *, pos_name='pos', backend=None, **backend_kwargs)
        Returns a random geometric graph in the unit cube of dimensions `dim`.

        The random geometric graph model places `n` nodes uniformly at
        random in the unit cube. Two nodes are joined by an edge if the
        distance between the nodes is at most `radius`.

        Edges are determined using a KDTree when SciPy is available.
        This reduces the time complexity from $O(n^2)$ to $O(n)$.

        Parameters
        ----------
        n : int or iterable
            Number of nodes or iterable of nodes
        radius: float
            Distance threshold value
        dim : int, optional
            Dimension of graph
        pos : dict, optional
            A dictionary keyed by node with node positions as values.
        p : float, optional
            Which Minkowski distance metric to use.  `p` has to meet the condition
            ``1 <= p <= infinity``.

            If this argument is not specified, the :math:`L^2` metric
            (the Euclidean distance metric), p = 2 is used.
            This should not be confused with the `p` of an Erdős-Rényi random
            graph, which represents probability.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        pos_name : string, default="pos"
            The name of the node attribute which represents the position
            in 2D coordinates of the node in the returned graph.

        Returns
        -------
        Graph
            A random geometric graph, undirected and without self-loops.
            Each node has a node attribute ``'pos'`` that stores the
            position of that node in Euclidean space as provided by the
            ``pos`` keyword argument or, if ``pos`` was not provided, as
            generated by this function.

        Examples
        --------
        Create a random geometric graph on twenty nodes where nodes are joined by
        an edge if their distance is at most 0.1::

        >>> G = nx.random_geometric_graph(20, 0.1)

        Notes
        -----
        This uses a *k*-d tree to build the graph.

        The `pos` keyword argument can be used to specify node positions so you
        can create an arbitrary distribution and domain for positions.

        For example, to use a 2D Gaussian distribution of node positions with mean
        (0, 0) and standard deviation 2::

        >>> import random
        >>> n = 20
        >>> pos = {i: (random.gauss(0, 2), random.gauss(0, 2)) for i in range(n)}
        >>> G = nx.random_geometric_graph(n, 0.2, pos=pos)

        References
        ----------
        .. [1] Penrose, Mathew, *Random Geometric Graphs*,
               Oxford Studies in Probability, 5, 2003.

    soft_random_geometric_graph(n, radius, dim=2, pos=None, p=2, p_dist=None, seed=None, *, pos_name='pos', backend=None, **backend_kwargs)
        Returns a soft random geometric graph in the unit cube.

        The soft random geometric graph [1] model places `n` nodes uniformly at
        random in the unit cube in dimension `dim`. Two nodes of distance, `dist`,
        computed by the `p`-Minkowski distance metric are joined by an edge with
        probability `p_dist` if the computed distance metric value of the nodes
        is at most `radius`, otherwise they are not joined.

        Edges within `radius` of each other are determined using a KDTree when
        SciPy is available. This reduces the time complexity from :math:`O(n^2)`
        to :math:`O(n)`.

        Parameters
        ----------
        n : int or iterable
            Number of nodes or iterable of nodes
        radius: float
            Distance threshold value
        dim : int, optional
            Dimension of graph
        pos : dict, optional
            A dictionary keyed by node with node positions as values.
        p : float, optional
            Which Minkowski distance metric to use.
            `p` has to meet the condition ``1 <= p <= infinity``.

            If this argument is not specified, the :math:`L^2` metric
            (the Euclidean distance metric), p = 2 is used.

            This should not be confused with the `p` of an Erdős-Rényi random
            graph, which represents probability.
        p_dist : function, optional
            A probability density function computing the probability of
            connecting two nodes that are of distance, dist, computed by the
            Minkowski distance metric. The probability density function, `p_dist`,
            must be any function that takes the metric value as input
            and outputs a single probability value between 0-1. The scipy.stats
            package has many probability distribution functions implemented and
            tools for custom probability distribution definitions [2], and passing
            the .pdf method of scipy.stats distributions can be used here.  If the
            probability function, `p_dist`, is not supplied, the default function
            is an exponential distribution with rate parameter :math:`\lambda=1`.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        pos_name : string, default="pos"
            The name of the node attribute which represents the position
            in 2D coordinates of the node in the returned graph.

        Returns
        -------
        Graph
            A soft random geometric graph, undirected and without self-loops.
            Each node has a node attribute ``'pos'`` that stores the
            position of that node in Euclidean space as provided by the
            ``pos`` keyword argument or, if ``pos`` was not provided, as
            generated by this function.

        Examples
        --------
        Default Graph:

        G = nx.soft_random_geometric_graph(50, 0.2)

        Custom Graph:

        Create a soft random geometric graph on 100 uniformly distributed nodes
        where nodes are joined by an edge with probability computed from an
        exponential distribution with rate parameter :math:`\lambda=1` if their
        Euclidean distance is at most 0.2.

        Notes
        -----
        This uses a *k*-d tree to build the graph.

        The `pos` keyword argument can be used to specify node positions so you
        can create an arbitrary distribution and domain for positions.

        For example, to use a 2D Gaussian distribution of node positions with mean
        (0, 0) and standard deviation 2

        The scipy.stats package can be used to define the probability distribution
        with the .pdf method used as `p_dist`.

        ::

        >>> import random
        >>> import math
        >>> n = 100
        >>> pos = {i: (random.gauss(0, 2), random.gauss(0, 2)) for i in range(n)}
        >>> p_dist = lambda dist: math.exp(-dist)
        >>> G = nx.soft_random_geometric_graph(n, 0.2, pos=pos, p_dist=p_dist)

        References
        ----------
        .. [1] Penrose, Mathew D. "Connectivity of soft random geometric graphs."
               The Annals of Applied Probability 26.2 (2016): 986-1028.
        .. [2] scipy.stats -
               https://docs.scipy.org/doc/scipy/reference/tutorial/stats.html

    thresholded_random_geometric_graph(n, radius, theta, dim=2, pos=None, weight=None, p=2, seed=None, *, pos_name='pos', weight_name='weight', backend=None, **backend_kwargs)
        Returns a thresholded random geometric graph in the unit cube.

        The thresholded random geometric graph [1] model places `n` nodes
        uniformly at random in the unit cube of dimensions `dim`. Each node
        `u` is assigned a weight :math:`w_u`. Two nodes `u` and `v` are
        joined by an edge if they are within the maximum connection distance,
        `radius` computed by the `p`-Minkowski distance and the summation of
        weights :math:`w_u` + :math:`w_v` is greater than or equal
        to the threshold parameter `theta`.

        Edges within `radius` of each other are determined using a KDTree when
        SciPy is available. This reduces the time complexity from :math:`O(n^2)`
        to :math:`O(n)`.

        Parameters
        ----------
        n : int or iterable
            Number of nodes or iterable of nodes
        radius: float
            Distance threshold value
        theta: float
            Threshold value
        dim : int, optional
            Dimension of graph
        pos : dict, optional
            A dictionary keyed by node with node positions as values.
        weight : dict, optional
            Node weights as a dictionary of numbers keyed by node.
        p : float, optional (default 2)
            Which Minkowski distance metric to use.  `p` has to meet the condition
            ``1 <= p <= infinity``.

            If this argument is not specified, the :math:`L^2` metric
            (the Euclidean distance metric), p = 2 is used.

            This should not be confused with the `p` of an Erdős-Rényi random
            graph, which represents probability.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        pos_name : string, default="pos"
            The name of the node attribute which represents the position
            in 2D coordinates of the node in the returned graph.
        weight_name : string, default="weight"
            The name of the node attribute which represents the weight
            of the node in the returned graph.

        Returns
        -------
        Graph
            A thresholded random geographic graph, undirected and without
            self-loops.

            Each node has a node attribute ``'pos'`` that stores the
            position of that node in Euclidean space as provided by the
            ``pos`` keyword argument or, if ``pos`` was not provided, as
            generated by this function. Similarly, each node has a nodethre
            attribute ``'weight'`` that stores the weight of that node as
            provided or as generated.

        Examples
        --------
        Default Graph:

        G = nx.thresholded_random_geometric_graph(50, 0.2, 0.1)

        Custom Graph:

        Create a thresholded random geometric graph on 50 uniformly distributed
        nodes where nodes are joined by an edge if their sum weights drawn from
        a exponential distribution with rate = 5 are >= theta = 0.1 and their
        Euclidean distance is at most 0.2.

        Notes
        -----
        This uses a *k*-d tree to build the graph.

        The `pos` keyword argument can be used to specify node positions so you
        can create an arbitrary distribution and domain for positions.

        For example, to use a 2D Gaussian distribution of node positions with mean
        (0, 0) and standard deviation 2

        If weights are not specified they are assigned to nodes by drawing randomly
        from the exponential distribution with rate parameter :math:`\lambda=1`.
        To specify weights from a different distribution, use the `weight` keyword
        argument::

        ::

        >>> import random
        >>> import math
        >>> n = 50
        >>> pos = {i: (random.gauss(0, 2), random.gauss(0, 2)) for i in range(n)}
        >>> w = {i: random.expovariate(5.0) for i in range(n)}
        >>> G = nx.thresholded_random_geometric_graph(n, 0.2, 0.1, 2, pos, w)

        References
        ----------
        .. [1] http://cole-maclean.github.io/blog/files/thesis.pdf

    waxman_graph(n, beta=0.4, alpha=0.1, L=None, domain=(0, 0, 1, 1), metric=None, seed=None, *, pos_name='pos', backend=None, **backend_kwargs)
        Returns a Waxman random graph.

        The Waxman random graph model places `n` nodes uniformly at random
        in a rectangular domain. Each pair of nodes at distance `d` is
        joined by an edge with probability

        .. math::
                p = \beta \exp(-d / \alpha L).

        This function implements both Waxman models, using the `L` keyword
        argument.

        * Waxman-1: if `L` is not specified, it is set to be the maximum distance
          between any pair of nodes.
        * Waxman-2: if `L` is specified, the distance between a pair of nodes is
          chosen uniformly at random from the interval `[0, L]`.

        Parameters
        ----------
        n : int or iterable
            Number of nodes or iterable of nodes
        beta: float
            Model parameter
        alpha: float
            Model parameter
        L : float, optional
            Maximum distance between nodes.  If not specified, the actual distance
            is calculated.
        domain : four-tuple of numbers, optional
            Domain size, given as a tuple of the form `(x_min, y_min, x_max,
            y_max)`.
        metric : function
            A metric on vectors of numbers (represented as lists or
            tuples). This must be a function that accepts two lists (or
            tuples) as input and yields a number as output. The function
            must also satisfy the four requirements of a `metric`_.
            Specifically, if $d$ is the function and $x$, $y$,
            and $z$ are vectors in the graph, then $d$ must satisfy

            1. $d(x, y) \ge 0$,
            2. $d(x, y) = 0$ if and only if $x = y$,
            3. $d(x, y) = d(y, x)$,
            4. $d(x, z) \le d(x, y) + d(y, z)$.

            If this argument is not specified, the Euclidean distance metric is
            used.

            .. _metric: https://en.wikipedia.org/wiki/Metric_%28mathematics%29

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        pos_name : string, default="pos"
            The name of the node attribute which represents the position
            in 2D coordinates of the node in the returned graph.

        Returns
        -------
        Graph
            A random Waxman graph, undirected and without self-loops. Each
            node has a node attribute ``'pos'`` that stores the position of
            that node in Euclidean space as generated by this function.

        Examples
        --------
        Specify an alternate distance metric using the ``metric`` keyword
        argument. For example, to use the "`taxicab metric`_" instead of the
        default `Euclidean metric`_::

            >>> dist = lambda x, y: sum(abs(a - b) for a, b in zip(x, y))
            >>> G = nx.waxman_graph(10, 0.5, 0.1, metric=dist)

        .. _taxicab metric: https://en.wikipedia.org/wiki/Taxicab_geometry
        .. _Euclidean metric: https://en.wikipedia.org/wiki/Euclidean_distance

        Notes
        -----
        Starting in NetworkX 2.0 the parameters alpha and beta align with their
        usual roles in the probability distribution. In earlier versions their
        positions in the expression were reversed. Their position in the calling
        sequence reversed as well to minimize backward incompatibility.

        References
        ----------
        .. [1]  B. M. Waxman, *Routing of multipoint connections*.
           IEEE J. Select. Areas Commun. 6(9),(1988) 1617--1622.

DATA
    __all__ = ['geometric_edges', 'geographical_threshold_graph', 'navigab...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\geometric.py

networkx.geometric_edges
Python Library Documentation: function geometric_edges in module networkx.generators.geometric

geometric_edges(G, radius, p=2, *, pos_name='pos', backend=None, **backend_kwargs)
    Returns edge list of node pairs within `radius` of each other.

    Parameters
    ----------
    G : networkx graph
        The graph from which to generate the edge list. The nodes in `G` should
        have an attribute ``pos`` corresponding to the node position, which is
        used to compute the distance to other nodes.
    radius : scalar
        The distance threshold. Edges are included in the edge list if the
        distance between the two nodes is less than `radius`.
    pos_name : string, default="pos"
        The name of the node attribute which represents the position of each
        node in 2D coordinates. Every node in the Graph must have this attribute.
    p : scalar, default=2
        The `Minkowski distance metric
        <https://en.wikipedia.org/wiki/Minkowski_distance>`_ used to compute
        distances. The default value is 2, i.e. Euclidean distance.

    Returns
    -------
    edges : list
        List of edges whose distances are less than `radius`

    Notes
    -----
    Radius uses Minkowski distance metric `p`.
    If scipy is available, `scipy.spatial.cKDTree` is used to speed computation.

    Examples
    --------
    Create a graph with nodes that have a "pos" attribute representing 2D
    coordinates.

    >>> G = nx.Graph()
    >>> G.add_nodes_from(
    ...     [
    ...         (0, {"pos": (0, 0)}),
    ...         (1, {"pos": (3, 0)}),
    ...         (2, {"pos": (8, 0)}),
    ...     ]
    ... )
    >>> nx.geometric_edges(G, radius=1)
    []
    >>> nx.geometric_edges(G, radius=4)
    [(0, 1)]
    >>> nx.geometric_edges(G, radius=6)
    [(0, 1), (1, 2)]
    >>> nx.geometric_edges(G, radius=9)
    [(0, 1), (0, 2), (1, 2)]
networkx.geometric_soft_configuration_graph
Python Library Documentation: function geometric_soft_configuration_graph in module networkx.generators.geometric

geometric_soft_configuration_graph(*, beta, n=None, gamma=None, mean_degree=None, kappas=None, seed=None, backend=None, **backend_kwargs)
    Returns a random graph from the geometric soft configuration model.

    The $\mathbb{S}^1$ model [1]_ is the geometric soft configuration model
    which is able to explain many fundamental features of real networks such as
    small-world property, heteregenous degree distributions, high level of
    clustering, and self-similarity.

    In the geometric soft configuration model, a node $i$ is assigned two hidden
    variables: a hidden degree $\kappa_i$, quantifying its popularity, influence,
    or importance, and an angular position $\theta_i$ in a circle abstracting the
    similarity space, where angular distances between nodes are a proxy for their
    similarity. Focusing on the angular position, this model is often called
    the $\mathbb{S}^1$ model (a one-dimensional sphere). The circle's radius is
    adjusted to $R = N/2\pi$, where $N$ is the number of nodes, so that the density
    is set to 1 without loss of generality.

    The connection probability between any pair of nodes increases with
    the product of their hidden degrees (i.e., their combined popularities),
    and decreases with the angular distance between the two nodes.
    Specifically, nodes $i$ and $j$ are connected with the probability

    $p_{ij} = \frac{1}{1 + \frac{d_{ij}^\beta}{\left(\mu \kappa_i \kappa_j\right)^{\max(1, \beta)}}}$

    where $d_{ij} = R\Delta\theta_{ij}$ is the arc length of the circle between
    nodes $i$ and $j$ separated by an angular distance $\Delta\theta_{ij}$.
    Parameters $\mu$ and $\beta$ (also called inverse temperature) control the
    average degree and the clustering coefficient, respectively.

    It can be shown [2]_ that the model undergoes a structural phase transition
    at $\beta=1$ so that for $\beta<1$ networks are unclustered in the thermodynamic
    limit (when $N\to \infty$) whereas for $\beta>1$ the ensemble generates
    networks with finite clustering coefficient.

    The $\mathbb{S}^1$ model can be expressed as a purely geometric model
    $\mathbb{H}^2$ in the hyperbolic plane [3]_ by mapping the hidden degree of
    each node into a radial coordinate as

    $r_i = \hat{R} - \frac{2 \max(1, \beta)}{\beta \zeta} \ln \left(\frac{\kappa_i}{\kappa_0}\right)$

    where $\hat{R}$ is the radius of the hyperbolic disk and $\zeta$ is the curvature,

    $\hat{R} = \frac{2}{\zeta} \ln \left(\frac{N}{\pi}\right)
    - \frac{2\max(1, \beta)}{\beta \zeta} \ln (\mu \kappa_0^2)$

    The connection probability then reads

    $p_{ij} = \frac{1}{1 + \exp\left({\frac{\beta\zeta}{2} (x_{ij} - \hat{R})}\right)}$

    where

    $x_{ij} = r_i + r_j + \frac{2}{\zeta} \ln \frac{\Delta\theta_{ij}}{2}$

    is a good approximation of the hyperbolic distance between two nodes separated
    by an angular distance $\Delta\theta_{ij}$ with radial coordinates $r_i$ and $r_j$.
    For $\beta > 1$, the curvature $\zeta = 1$, for $\beta < 1$, $\zeta = \beta^{-1}$.


    Parameters
    ----------
    Either `n`, `gamma`, `mean_degree` are provided or `kappas`. The values of
    `n`, `gamma`, `mean_degree` (if provided) are used to construct a random
    kappa-dict keyed by node with values sampled from a power-law distribution.

    beta : positive number
        Inverse temperature, controlling the clustering coefficient.
    n : int (default: None)
        Size of the network (number of nodes).
        If not provided, `kappas` must be provided and holds the nodes.
    gamma : float (default: None)
        Exponent of the power-law distribution for hidden degrees `kappas`.
        If not provided, `kappas` must be provided directly.
    mean_degree : float (default: None)
        The mean degree in the network.
        If not provided, `kappas` must be provided directly.
    kappas : dict (default: None)
        A dict keyed by node to its hidden degree value.
        If not provided, random values are computed based on a power-law
        distribution using `n`, `gamma` and `mean_degree`.
    seed : int, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    Graph
        A random geometric soft configuration graph (undirected with no self-loops).
        Each node has three node-attributes:

        - ``kappa`` that represents the hidden degree.

        - ``theta`` the position in the similarity space ($\mathbb{S}^1$) which is
          also the angular position in the hyperbolic plane.

        - ``radius`` the radial position in the hyperbolic plane
          (based on the hidden degree).


    Examples
    --------
    Generate a network with specified parameters:

    >>> G = nx.geometric_soft_configuration_graph(
    ...     beta=1.5, n=100, gamma=2.7, mean_degree=5
    ... )

    Create a geometric soft configuration graph with 100 nodes. The $\beta$ parameter
    is set to 1.5 and the exponent of the powerlaw distribution of the hidden
    degrees is 2.7 with mean value of 5.

    Generate a network with predefined hidden degrees:

    >>> kappas = {i: 10 for i in range(100)}
    >>> G = nx.geometric_soft_configuration_graph(beta=2.5, kappas=kappas)

    Create a geometric soft configuration graph with 100 nodes. The $\beta$ parameter
    is set to 2.5 and all nodes with hidden degree $\kappa=10$.


    References
    ----------
    .. [1] Serrano, M. Á., Krioukov, D., & Boguñá, M. (2008). Self-similarity
       of complex networks and hidden metric spaces. Physical review letters, 100(7), 078701.

    .. [2] van der Kolk, J., Serrano, M. Á., & Boguñá, M. (2022). An anomalous
       topological phase transition in spatial random graphs. Communications Physics, 5(1), 245.

    .. [3] Krioukov, D., Papadopoulos, F., Kitsak, M., Vahdat, A., & Boguná, M. (2010).
       Hyperbolic geometry of complex networks. Physical Review E, 82(3), 036106.
networkx.get_edge_attributes
Python Library Documentation: function get_edge_attributes in module networkx.classes.function

get_edge_attributes(G, name, default=None)
    Get edge attributes from graph

    Parameters
    ----------
    G : NetworkX Graph

    name : string
       Attribute name

    default: object (default=None)
       Default value of the edge attribute if there is no value set for that
       edge in graph. If `None` then edges without this attribute are not
       included in the returned dict.

    Returns
    -------
    Dictionary of attributes keyed by edge. For (di)graphs, the keys are
    2-tuples of the form: (u, v). For multi(di)graphs, the keys are 3-tuples of
    the form: (u, v, key).

    Examples
    --------
    >>> G = nx.Graph()
    >>> nx.add_path(G, [1, 2, 3], color="red")
    >>> color = nx.get_edge_attributes(G, "color")
    >>> color[(1, 2)]
    'red'
    >>> G.add_edge(3, 4)
    >>> color = nx.get_edge_attributes(G, "color", default="yellow")
    >>> color[(3, 4)]
    'yellow'
networkx.get_node_attributes
Python Library Documentation: function get_node_attributes in module networkx.classes.function

get_node_attributes(G, name, default=None)
    Get node attributes from graph

    Parameters
    ----------
    G : NetworkX Graph

    name : string
       Attribute name

    default: object (default=None)
       Default value of the node attribute if there is no value set for that
       node in graph. If `None` then nodes without this attribute are not
       included in the returned dict.

    Returns
    -------
    Dictionary of attributes keyed by node.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_nodes_from([1, 2, 3], color="red")
    >>> color = nx.get_node_attributes(G, "color")
    >>> color[1]
    'red'
    >>> G.add_node(4)
    >>> color = nx.get_node_attributes(G, "color", default="yellow")
    >>> color[4]
    'yellow'
networkx.gexf
Python Library Documentation: module networkx.readwrite.gexf in networkx.readwrite

NAME
    networkx.readwrite.gexf - Read and write graphs in GEXF format.

DESCRIPTION
    .. warning::
        This parser uses the standard xml library present in Python, which is
        insecure - see :external+python:mod:`xml` for additional information.
        Only parse GEFX files you trust.

    GEXF (Graph Exchange XML Format) is a language for describing complex
    network structures, their associated data and dynamics.

    This implementation does not support mixed graphs (directed and
    undirected edges together).

    Format
    ------
    GEXF is an XML format.  See http://gexf.net/schema.html for the
    specification and http://gexf.net/basic.html for examples.

FUNCTIONS
    generate_gexf(G, encoding='utf-8', prettyprint=True, version='1.2draft')
        Generate lines of GEXF format representation of G.

        "GEXF (Graph Exchange XML Format) is a language for describing
        complex networks structures, their associated data and dynamics" [1]_.

        Parameters
        ----------
        G : graph
        A NetworkX graph
        encoding : string (optional, default: 'utf-8')
        Encoding for text data.
        prettyprint : bool (optional, default: True)
        If True use line breaks and indenting in output XML.
        version : string (default: 1.2draft)
        Version of GEFX File Format (see http://gexf.net/schema.html)
        Supported values: "1.1draft", "1.2draft"


        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> linefeed = chr(10)  # linefeed=

        >>> s = linefeed.join(nx.generate_gexf(G))
        >>> for line in nx.generate_gexf(G):  # doctest: +SKIP
        ...     print(line)

        Notes
        -----
        This implementation does not support mixed graphs (directed and undirected
        edges together).

        The node id attribute is set to be the string of the node label.
        If you want to specify an id use set it as node data, e.g.
        node['a']['id']=1 to set the id of node 'a' to 1.

        References
        ----------
        .. [1] GEXF File Format, https://gephi.org/gexf/format/

    read_gexf(path, node_type=None, relabel=False, version='1.2draft', *, backend=None, **backend_kwargs)
        Read graph in GEXF format from path.

        "GEXF (Graph Exchange XML Format) is a language for describing
        complex networks structures, their associated data and dynamics" [1]_.

        Parameters
        ----------
        path : file or string
           File or file name to read.
           File names ending in .gz or .bz2 will be decompressed.
        node_type: Python type (default: None)
           Convert node ids to this type if not None.
        relabel : bool (default: False)
           If True relabel the nodes to use the GEXF node "label" attribute
           instead of the node "id" attribute as the NetworkX node label.
        version : string (default: 1.2draft)
        Version of GEFX File Format (see http://gexf.net/schema.html)
           Supported values: "1.1draft", "1.2draft"

        Returns
        -------
        graph: NetworkX graph
            If no parallel edges are found a Graph or DiGraph is returned.
            Otherwise a MultiGraph or MultiDiGraph is returned.

        Notes
        -----
        This implementation does not support mixed graphs (directed and undirected
        edges together).

        References
        ----------
        .. [1] GEXF File Format, http://gexf.net/

    relabel_gexf_graph(G)
        Relabel graph using "label" node keyword for node label.

        Parameters
        ----------
        G : graph
           A NetworkX graph read from GEXF data

        Returns
        -------
        H : graph
          A NetworkX graph with relabeled nodes

        Raises
        ------
        NetworkXError
            If node labels are missing or not unique while relabel=True.

        Notes
        -----
        This function relabels the nodes in a NetworkX graph with the
        "label" attribute.  It also handles relabeling the specific GEXF
        node attributes "parents", and "pid".

    write_gexf(G, path, encoding='utf-8', prettyprint=True, version='1.2draft')
        Write G in GEXF format to path.

        "GEXF (Graph Exchange XML Format) is a language for describing
        complex networks structures, their associated data and dynamics" [1]_.

        Node attributes are checked according to the version of the GEXF
        schemas used for parameters which are not user defined,
        e.g. visualization 'viz' [2]_. See example for usage.

        Parameters
        ----------
        G : graph
           A NetworkX graph
        path : file or string
           File or file name to write.
           File names ending in .gz or .bz2 will be compressed.
        encoding : string (optional, default: 'utf-8')
           Encoding for text data.
        prettyprint : bool (optional, default: True)
           If True use line breaks and indenting in output XML.
        version: string (optional, default: '1.2draft')
           The version of GEXF to be used for nodes attributes checking

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_gexf(G, "test.gexf")

        # visualization data
        >>> G.nodes[0]["viz"] = {"size": 54}
        >>> G.nodes[0]["viz"]["position"] = {"x": 0, "y": 1}
        >>> G.nodes[0]["viz"]["color"] = {"r": 0, "g": 0, "b": 256}


        Notes
        -----
        This implementation does not support mixed graphs (directed and undirected
        edges together).

        The node id attribute is set to be the string of the node label.
        If you want to specify an id use set it as node data, e.g.
        node['a']['id']=1 to set the id of node 'a' to 1.

        References
        ----------
        .. [1] GEXF File Format, http://gexf.net/
        .. [2] GEXF schema, http://gexf.net/schema.html

DATA
    __all__ = ['write_gexf', 'read_gexf', 'relabel_gexf_graph', 'generate_...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\gexf.py

networkx.girth
Python Library Documentation: function girth in module networkx.algorithms.cycles

girth(G, *, backend=None, **backend_kwargs)
    Returns the girth of the graph.

    The girth of a graph is the length of its shortest cycle, or infinity if
    the graph is acyclic. The algorithm follows the description given on the
    Wikipedia page [1]_, and runs in time O(mn) on a graph with m edges and n
    nodes.

    Parameters
    ----------
    G : NetworkX Graph

    Returns
    -------
    int or math.inf

    Examples
    --------
    All examples below (except P_5) can easily be checked using Wikipedia,
    which has a page for each of these famous graphs.

    >>> nx.girth(nx.chvatal_graph())
    4
    >>> nx.girth(nx.tutte_graph())
    4
    >>> nx.girth(nx.petersen_graph())
    5
    >>> nx.girth(nx.heawood_graph())
    6
    >>> nx.girth(nx.pappus_graph())
    6
    >>> nx.girth(nx.path_graph(5))
    inf

    References
    ----------
    .. [1] `Wikipedia: Girth <https://en.wikipedia.org/wiki/Girth_(graph_theory)>`_
networkx.global_efficiency
Python Library Documentation: function global_efficiency in module networkx.algorithms.efficiency_measures

global_efficiency(G, *, backend=None, **backend_kwargs)
    Returns the average global efficiency of the graph.

    The *efficiency* of a pair of nodes in a graph is the multiplicative
    inverse of the shortest path distance between the nodes. The *average
    global efficiency* of a graph is the average efficiency of all pairs of
    nodes [1]_.

    Parameters
    ----------
    G : :class:`networkx.Graph`
        An undirected graph for which to compute the average global efficiency.

    Returns
    -------
    float
        The average global efficiency of the graph.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
    >>> round(nx.global_efficiency(G), 12)
    0.916666666667

    Notes
    -----
    Edge weights are ignored when computing the shortest path distances.

    See also
    --------
    local_efficiency

    References
    ----------
    .. [1] Latora, Vito, and Massimo Marchiori.
           "Efficient behavior of small-world networks."
           *Physical Review Letters* 87.19 (2001): 198701.
           <https://doi.org/10.1103/PhysRevLett.87.198701>
networkx.global_parameters
Python Library Documentation: function global_parameters in module networkx.algorithms.distance_regular

global_parameters(b, c)
    Returns global parameters for a given intersection array.

    Given a distance-regular graph G with integers b_i, c_i,i = 0,....,d
    such that for any 2 vertices x,y in G at a distance i=d(x,y), there
    are exactly c_i neighbors of y at a distance of i-1 from x and b_i
    neighbors of y at a distance of i+1 from x.

    Thus, a distance regular graph has the global parameters,
    [[c_0,a_0,b_0],[c_1,a_1,b_1],......,[c_d,a_d,b_d]] for the
    intersection array  [b_0,b_1,.....b_{d-1};c_1,c_2,.....c_d]
    where a_i+b_i+c_i=k , k= degree of every vertex.

    Parameters
    ----------
    b : list

    c : list

    Returns
    -------
    iterable
       An iterable over three tuples.

    Examples
    --------
    >>> G = nx.dodecahedral_graph()
    >>> b, c = nx.intersection_array(G)
    >>> list(nx.global_parameters(b, c))
    [(0, 0, 3), (1, 0, 2), (1, 1, 1), (1, 1, 1), (2, 0, 1), (3, 0, 0)]

    References
    ----------
    .. [1] Weisstein, Eric W. "Global Parameters."
       From MathWorld--A Wolfram Web Resource.
       http://mathworld.wolfram.com/GlobalParameters.html

    See Also
    --------
    intersection_array
networkx.global_reaching_centrality
Python Library Documentation: function global_reaching_centrality in module networkx.algorithms.centrality.reaching

global_reaching_centrality(G, weight=None, normalized=True, *, backend=None, **backend_kwargs)
    Returns the global reaching centrality of a directed graph.

    The *global reaching centrality* of a weighted directed graph is the
    average over all nodes of the difference between the local reaching
    centrality of the node and the greatest local reaching centrality of
    any node in the graph [1]_. For more information on the local
    reaching centrality, see :func:`local_reaching_centrality`.
    Informally, the local reaching centrality is the proportion of the
    graph that is reachable from the neighbors of the node.

    Parameters
    ----------
    G : DiGraph
        A networkx DiGraph.

    weight : None or string, optional (default=None)
        Attribute to use for edge weights. If ``None``, each edge weight
        is assumed to be one. A higher weight implies a stronger
        connection between nodes and a *shorter* path length.

    normalized : bool, optional (default=True)
        Whether to normalize the edge weights by the total sum of edge
        weights.

    Returns
    -------
    h : float
        The global reaching centrality of the graph.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_edge(1, 2)
    >>> G.add_edge(1, 3)
    >>> nx.global_reaching_centrality(G)
    1.0
    >>> G.add_edge(3, 2)
    >>> nx.global_reaching_centrality(G)
    0.75

    See also
    --------
    local_reaching_centrality

    References
    ----------
    .. [1] Mones, Enys, Lilla Vicsek, and Tamás Vicsek.
           "Hierarchy Measure for Complex Networks."
           *PLoS ONE* 7.3 (2012): e33799.
           https://doi.org/10.1371/journal.pone.0033799
networkx.gml
Python Library Documentation: module networkx.readwrite.gml in networkx.readwrite

NAME
    networkx.readwrite.gml - Read graphs in GML format.

DESCRIPTION
    "GML, the Graph Modelling Language, is our proposal for a portable
    file format for graphs. GML's key features are portability, simple
    syntax, extensibility and flexibility. A GML file consists of a
    hierarchical key-value lists. Graphs can be annotated with arbitrary
    data structures. The idea for a common file format was born at the
    GD'95; this proposal is the outcome of many discussions. GML is the
    standard file format in the Graphlet graph editor system. It has been
    overtaken and adapted by several other systems for drawing graphs."

    GML files are stored using a 7-bit ASCII encoding with any extended
    ASCII characters (iso8859-1) appearing as HTML character entities.
    You will need to give some thought into how the exported data should
    interact with different languages and even different Python versions.
    Re-importing from gml is also a concern.

    Without specifying a `stringizer`/`destringizer`, the code is capable of
    writing `int`/`float`/`str`/`dict`/`list` data as required by the GML
    specification.  For writing other data types, and for reading data other
    than `str` you need to explicitly supply a `stringizer`/`destringizer`.

    For additional documentation on the GML file format, please see the
    `GML website <https://web.archive.org/web/20190207140002/http://www.fim.uni-passau.de/index.php?id=17297&L=1>`_.

    Several example graphs in GML format may be found on Mark Newman's
    `Network data page <http://www-personal.umich.edu/~mejn/netdata/>`_.

FUNCTIONS
    generate_gml(G, stringizer=None)
        Generate a single entry of the graph `G` in GML format.

        Parameters
        ----------
        G : NetworkX graph
            The graph to be converted to GML.

        stringizer : callable, optional
            A `stringizer` which converts non-int/non-float/non-dict values into
            strings. If it cannot convert a value into a string, it should raise a
            `ValueError` to indicate that. Default value: None.

        Returns
        -------
        lines: generator of strings
            Lines of GML data. Newlines are not appended.

        Raises
        ------
        NetworkXError
            If `stringizer` cannot convert a value into a string, or the value to
            convert is not a string while `stringizer` is None.

        See Also
        --------
        literal_stringizer

        Notes
        -----
        Graph attributes named 'directed', 'multigraph', 'node' or
        'edge', node attributes named 'id' or 'label', edge attributes
        named 'source' or 'target' (or 'key' if `G` is a multigraph)
        are ignored because these attribute names are used to encode the graph
        structure.

        GML files are stored using a 7-bit ASCII encoding with any extended
        ASCII characters (iso8859-1) appearing as HTML character entities.
        Without specifying a `stringizer`/`destringizer`, the code is capable of
        writing `int`/`float`/`str`/`dict`/`list` data as required by the GML
        specification.  For writing other data types, and for reading data other
        than `str` you need to explicitly supply a `stringizer`/`destringizer`.

        For additional documentation on the GML file format, please see the
        `GML url <https://web.archive.org/web/20190207140002/http://www.fim.uni-passau.de/index.php?id=17297&L=1>`_.

        See the module docstring :mod:`networkx.readwrite.gml` for more details.

        Examples
        --------
        >>> G = nx.Graph()
        >>> G.add_node("1")
        >>> print("\n".join(nx.generate_gml(G)))
        graph [
          node [
            id 0
            label "1"
          ]
        ]
        >>> G = nx.MultiGraph([("a", "b"), ("a", "b")])
        >>> print("\n".join(nx.generate_gml(G)))
        graph [
          multigraph 1
          node [
            id 0
            label "a"
          ]
          node [
            id 1
            label "b"
          ]
          edge [
            source 0
            target 1
            key 0
          ]
          edge [
            source 0
            target 1
            key 1
          ]
        ]

    parse_gml(lines, label='label', destringizer=None, *, backend=None, **backend_kwargs)
        Parse GML graph from a string or iterable.

        Parameters
        ----------
        lines : string or iterable of strings
           Data in GML format.

        label : string, optional
            If not None, the parsed nodes will be renamed according to node
            attributes indicated by `label`. Default value: 'label'.

        destringizer : callable, optional
            A `destringizer` that recovers values stored as strings in GML. If it
            cannot convert a string to a value, a `ValueError` is raised. Default
            value : None.

        Returns
        -------
        G : NetworkX graph
            The parsed graph.

        Raises
        ------
        NetworkXError
            If the input cannot be parsed.

        See Also
        --------
        write_gml, read_gml

        Notes
        -----
        This stores nested GML attributes as dictionaries in the NetworkX graph,
        node, and edge attribute structures.

        GML files are stored using a 7-bit ASCII encoding with any extended
        ASCII characters (iso8859-1) appearing as HTML character entities.
        Without specifying a `stringizer`/`destringizer`, the code is capable of
        writing `int`/`float`/`str`/`dict`/`list` data as required by the GML
        specification.  For writing other data types, and for reading data other
        than `str` you need to explicitly supply a `stringizer`/`destringizer`.

        For additional documentation on the GML file format, please see the
        `GML url <https://web.archive.org/web/20190207140002/http://www.fim.uni-passau.de/index.php?id=17297&L=1>`_.

        See the module docstring :mod:`networkx.readwrite.gml` for more details.

    read_gml(path, label='label', destringizer=None, *, backend=None, **backend_kwargs)
        Read graph in GML format from `path`.

        Parameters
        ----------
        path : filename or filehandle
            The filename or filehandle to read from.

        label : string, optional
            If not None, the parsed nodes will be renamed according to node
            attributes indicated by `label`. Default value: 'label'.

        destringizer : callable, optional
            A `destringizer` that recovers values stored as strings in GML. If it
            cannot convert a string to a value, a `ValueError` is raised. Default
            value : None.

        Returns
        -------
        G : NetworkX graph
            The parsed graph.

        Raises
        ------
        NetworkXError
            If the input cannot be parsed.

        See Also
        --------
        write_gml, parse_gml
        literal_destringizer

        Notes
        -----
        GML files are stored using a 7-bit ASCII encoding with any extended
        ASCII characters (iso8859-1) appearing as HTML character entities.
        Without specifying a `stringizer`/`destringizer`, the code is capable of
        writing `int`/`float`/`str`/`dict`/`list` data as required by the GML
        specification.  For writing other data types, and for reading data other
        than `str` you need to explicitly supply a `stringizer`/`destringizer`.

        For additional documentation on the GML file format, please see the
        `GML url <https://web.archive.org/web/20190207140002/http://www.fim.uni-passau.de/index.php?id=17297&L=1>`_.

        See the module docstring :mod:`networkx.readwrite.gml` for more details.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_gml(G, "test.gml")

        GML values are interpreted as strings by default:

        >>> H = nx.read_gml("test.gml")
        >>> H.nodes
        NodeView(('0', '1', '2', '3'))

        When a `destringizer` is provided, GML values are converted to the provided type.
        For example, integer nodes can be recovered as shown below:

        >>> J = nx.read_gml("test.gml", destringizer=int)
        >>> J.nodes
        NodeView((0, 1, 2, 3))

    write_gml(G, path, stringizer=None)
        Write a graph `G` in GML format to the file or file handle `path`.

        Parameters
        ----------
        G : NetworkX graph
            The graph to be converted to GML.

        path : filename or filehandle
            The filename or filehandle to write. Files whose names end with .gz or
            .bz2 will be compressed.

        stringizer : callable, optional
            A `stringizer` which converts non-int/non-float/non-dict values into
            strings. If it cannot convert a value into a string, it should raise a
            `ValueError` to indicate that. Default value: None.

        Raises
        ------
        NetworkXError
            If `stringizer` cannot convert a value into a string, or the value to
            convert is not a string while `stringizer` is None.

        See Also
        --------
        read_gml, generate_gml
        literal_stringizer

        Notes
        -----
        Graph attributes named 'directed', 'multigraph', 'node' or
        'edge', node attributes named 'id' or 'label', edge attributes
        named 'source' or 'target' (or 'key' if `G` is a multigraph)
        are ignored because these attribute names are used to encode the graph
        structure.

        GML files are stored using a 7-bit ASCII encoding with any extended
        ASCII characters (iso8859-1) appearing as HTML character entities.
        Without specifying a `stringizer`/`destringizer`, the code is capable of
        writing `int`/`float`/`str`/`dict`/`list` data as required by the GML
        specification.  For writing other data types, and for reading data other
        than `str` you need to explicitly supply a `stringizer`/`destringizer`.

        Note that while we allow non-standard GML to be read from a file, we make
        sure to write GML format. In particular, underscores are not allowed in
        attribute names.
        For additional documentation on the GML file format, please see the
        `GML url <https://web.archive.org/web/20190207140002/http://www.fim.uni-passau.de/index.php?id=17297&L=1>`_.

        See the module docstring :mod:`networkx.readwrite.gml` for more details.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_gml(G, "test.gml")

        Filenames ending in .gz or .bz2 will be compressed.

        >>> nx.write_gml(G, "test.gml.gz")

DATA
    __all__ = ['read_gml', 'parse_gml', 'generate_gml', 'write_gml']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\gml.py

networkx.gn_graph
Python Library Documentation: function gn_graph in module networkx.generators.directed

gn_graph(n, kernel=None, create_using=None, seed=None, *, backend=None, **backend_kwargs)
    Returns the growing network (GN) digraph with `n` nodes.

    The GN graph is built by adding nodes one at a time with a link to one
    previously added node.  The target node for the link is chosen with
    probability based on degree.  The default attachment kernel is a linear
    function of the degree of a node.

    The graph is always a (directed) tree.

    Parameters
    ----------
    n : int
        The number of nodes for the generated graph.
    kernel : function
        The attachment kernel.
    create_using : NetworkX graph constructor, optional (default DiGraph)
        Graph type to create. If graph instance, then cleared before populated.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Examples
    --------
    To create the undirected GN graph, use the :meth:`~DiGraph.to_directed`
    method::

    >>> D = nx.gn_graph(10)  # the GN graph
    >>> G = D.to_undirected()  # the undirected version

    To specify an attachment kernel, use the `kernel` keyword argument::

    >>> D = nx.gn_graph(10, kernel=lambda x: x**1.5)  # A_k = k^1.5

    References
    ----------
    .. [1] P. L. Krapivsky and S. Redner,
           Organization of Growing Random Networks,
           Phys. Rev. E, 63, 066123, 2001.
networkx.gnc_graph
Python Library Documentation: function gnc_graph in module networkx.generators.directed

gnc_graph(n, create_using=None, seed=None, *, backend=None, **backend_kwargs)
    Returns the growing network with copying (GNC) digraph with `n` nodes.

    The GNC graph is built by adding nodes one at a time with a link to one
    previously added node (chosen uniformly at random) and to all of that
    node's successors.

    Parameters
    ----------
    n : int
        The number of nodes for the generated graph.
    create_using : NetworkX graph constructor, optional (default DiGraph)
        Graph type to create. If graph instance, then cleared before populated.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    References
    ----------
    .. [1] P. L. Krapivsky and S. Redner,
           Network Growth by Copying,
           Phys. Rev. E, 71, 036118, 2005k.},
networkx.gnm_random_graph
Python Library Documentation: function gnm_random_graph in module networkx.generators.random_graphs

gnm_random_graph(n, m, seed=None, directed=False, *, create_using=None, backend=None, **backend_kwargs)
    Returns a $G_{n,m}$ random graph.

    In the $G_{n,m}$ model, a graph is chosen uniformly at random from the set
    of all graphs with $n$ nodes and $m$ edges.

    This algorithm should be faster than :func:`dense_gnm_random_graph` for
    sparse graphs.

    Parameters
    ----------
    n : int
        The number of nodes.
    m : int
        The number of edges.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    directed : bool, optional (default=False)
        If True return a directed graph
    create_using : Graph constructor, optional (default=nx.Graph or nx.DiGraph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph types are not supported and raise a ``NetworkXError``.
        By default NetworkX Graph or DiGraph are used depending on `directed`.

    See also
    --------
    dense_gnm_random_graph
networkx.gnp_random_graph
Python Library Documentation: function gnp_random_graph in module networkx.generators.random_graphs

gnp_random_graph(n, p, seed=None, directed=False, *, create_using=None, backend=None, **backend_kwargs)
    Returns a $G_{n,p}$ random graph, also known as an Erdős-Rényi graph
    or a binomial graph.

    The $G_{n,p}$ model chooses each of the possible edges with probability $p$.

    Parameters
    ----------
    n : int
        The number of nodes.
    p : float
        Probability for edge creation.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    directed : bool, optional (default=False)
        If True, this function returns a directed graph.
    create_using : Graph constructor, optional (default=nx.Graph or nx.DiGraph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph types are not supported and raise a ``NetworkXError``.
        By default NetworkX Graph or DiGraph are used depending on `directed`.

    See Also
    --------
    fast_gnp_random_graph

    Notes
    -----
    This algorithm [2]_ runs in $O(n^2)$ time.  For sparse graphs (that is, for
    small values of $p$), :func:`fast_gnp_random_graph` is a faster algorithm.

    :func:`binomial_graph` and :func:`erdos_renyi_graph` are
    aliases for :func:`gnp_random_graph`.

    >>> nx.binomial_graph is nx.gnp_random_graph
    True
    >>> nx.erdos_renyi_graph is nx.gnp_random_graph
    True

    References
    ----------
    .. [1] P. Erdős and A. Rényi, On Random Graphs, Publ. Math. 6, 290 (1959).
    .. [2] E. N. Gilbert, Random Graphs, Ann. Math. Stat., 30, 1141 (1959).
networkx.gnr_graph
Python Library Documentation: function gnr_graph in module networkx.generators.directed

gnr_graph(n, p, create_using=None, seed=None, *, backend=None, **backend_kwargs)
    Returns the growing network with redirection (GNR) digraph with `n`
    nodes and redirection probability `p`.

    The GNR graph is built by adding nodes one at a time with a link to one
    previously added node.  The previous target node is chosen uniformly at
    random.  With probability `p` the link is instead "redirected" to the
    successor node of the target.

    The graph is always a (directed) tree.

    Parameters
    ----------
    n : int
        The number of nodes for the generated graph.
    p : float
        The redirection probability.
    create_using : NetworkX graph constructor, optional (default DiGraph)
        Graph type to create. If graph instance, then cleared before populated.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Examples
    --------
    To create the undirected GNR graph, use the :meth:`~DiGraph.to_directed`
    method::

    >>> D = nx.gnr_graph(10, 0.5)  # the GNR graph
    >>> G = D.to_undirected()  # the undirected version

    References
    ----------
    .. [1] P. L. Krapivsky and S. Redner,
           Organization of Growing Random Networks,
           Phys. Rev. E, 63, 066123, 2001.
networkx.goldberg_radzik
Python Library Documentation: function goldberg_radzik in module networkx.algorithms.shortest_paths.weighted

goldberg_radzik(G, source, weight='weight', *, backend=None, **backend_kwargs)
    Compute shortest path lengths and predecessors on shortest paths
    in weighted graphs.

    The algorithm has a running time of $O(mn)$ where $n$ is the number of
    nodes and $m$ is the number of edges.  It is slower than Dijkstra but
    can handle negative edge weights.

    Parameters
    ----------
    G : NetworkX graph
        The algorithm works for all types of graphs, including directed
        graphs and multigraphs.

    source: node label
        Starting node for path

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

    Returns
    -------
    pred, dist : dictionaries
        Returns two dictionaries keyed by node to predecessor in the
        path and to the distance from the source respectively.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    NetworkXUnbounded
        If the (di)graph contains a negative (di)cycle, the
        algorithm raises an exception to indicate the presence of the
        negative (di)cycle.  Note: any negative weight edge in an
        undirected graph is a negative cycle.

        As of NetworkX v3.2, a zero weight cycle is no longer
        incorrectly reported as a negative weight cycle.


    Examples
    --------
    >>> G = nx.path_graph(5, create_using=nx.DiGraph())
    >>> pred, dist = nx.goldberg_radzik(G, 0)
    >>> sorted(pred.items())
    [(0, None), (1, 0), (2, 1), (3, 2), (4, 3)]
    >>> sorted(dist.items())
    [(0, 0), (1, 1), (2, 2), (3, 3), (4, 4)]

    >>> G = nx.cycle_graph(5, create_using=nx.DiGraph())
    >>> G[1][2]["weight"] = -7
    >>> nx.goldberg_radzik(G, 0)
    Traceback (most recent call last):
        ...
    networkx.exception.NetworkXUnbounded: Negative cycle detected.

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The dictionaries returned only have keys for nodes reachable from
    the source.

    In the case where the (di)graph is not connected, if a component
    not containing the source contains a negative (di)cycle, it
    will not be detected.
networkx.gomory_hu_tree
Python Library Documentation: function gomory_hu_tree in module networkx.algorithms.flow.gomory_hu

gomory_hu_tree(G, capacity='capacity', flow_func=None, *, backend=None, **backend_kwargs)
    Returns the Gomory-Hu tree of an undirected graph G.

    A Gomory-Hu tree of an undirected graph with capacities is a
    weighted tree that represents the minimum s-t cuts for all s-t
    pairs in the graph.

    It only requires `n-1` minimum cut computations instead of the
    obvious `n(n-1)/2`. The tree represents all s-t cuts as the
    minimum cut value among any pair of nodes is the minimum edge
    weight in the shortest path between the two nodes in the
    Gomory-Hu tree.

    The Gomory-Hu tree also has the property that removing the
    edge with the minimum weight in the shortest path between
    any two nodes leaves two connected components that form
    a partition of the nodes in G that defines the minimum s-t
    cut.

    See Examples section below for details.

    Parameters
    ----------
    G : NetworkX graph
        Undirected graph

    capacity : string
        Edges of the graph G are expected to have an attribute capacity
        that indicates how much flow the edge can support. If this
        attribute is not present, the edge is considered to have
        infinite capacity. Default value: 'capacity'.

    flow_func : function
        Function to perform the underlying flow computations. Default value
        :func:`edmonds_karp`. This function performs better in sparse graphs
        with right tailed degree distributions.
        :func:`shortest_augmenting_path` will perform better in denser
        graphs.

    Returns
    -------
    Tree : NetworkX graph
        A NetworkX graph representing the Gomory-Hu tree of the input graph.

    Raises
    ------
    NetworkXNotImplemented
        Raised if the input graph is directed.

    NetworkXError
        Raised if the input graph is an empty Graph.

    Examples
    --------
    >>> G = nx.karate_club_graph()
    >>> nx.set_edge_attributes(G, 1, "capacity")
    >>> T = nx.gomory_hu_tree(G)
    >>> # The value of the minimum cut between any pair
    ... # of nodes in G is the minimum edge weight in the
    ... # shortest path between the two nodes in the
    ... # Gomory-Hu tree.
    ... def minimum_edge_weight_in_shortest_path(T, u, v):
    ...     path = nx.shortest_path(T, u, v, weight="weight")
    ...     return min((T[u][v]["weight"], (u, v)) for (u, v) in zip(path, path[1:]))
    >>> u, v = 0, 33
    >>> cut_value, edge = minimum_edge_weight_in_shortest_path(T, u, v)
    >>> cut_value
    10
    >>> nx.minimum_cut_value(G, u, v)
    10
    >>> # The Gomory-Hu tree also has the property that removing the
    ... # edge with the minimum weight in the shortest path between
    ... # any two nodes leaves two connected components that form
    ... # a partition of the nodes in G that defines the minimum s-t
    ... # cut.
    ... cut_value, edge = minimum_edge_weight_in_shortest_path(T, u, v)
    >>> T.remove_edge(*edge)
    >>> U, V = list(nx.connected_components(T))
    >>> # Thus U and V form a partition that defines a minimum cut
    ... # between u and v in G. You can compute the edge cut set,
    ... # that is, the set of edges that if removed from G will
    ... # disconnect u from v in G, with this information:
    ... cutset = set()
    >>> for x, nbrs in ((n, G[n]) for n in U):
    ...     cutset.update((x, y) for y in nbrs if y in V)
    >>> # Because we have set the capacities of all edges to 1
    ... # the cutset contains ten edges
    ... len(cutset)
    10
    >>> # You can use any maximum flow algorithm for the underlying
    ... # flow computations using the argument flow_func
    ... from networkx.algorithms import flow
    >>> T = nx.gomory_hu_tree(G, flow_func=flow.boykov_kolmogorov)
    >>> cut_value, edge = minimum_edge_weight_in_shortest_path(T, u, v)
    >>> cut_value
    10
    >>> nx.minimum_cut_value(G, u, v, flow_func=flow.boykov_kolmogorov)
    10

    Notes
    -----
    This implementation is based on Gusfield approach [1]_ to compute
    Gomory-Hu trees, which does not require node contractions and has
    the same computational complexity than the original method.

    See also
    --------
    :func:`minimum_cut`
    :func:`maximum_flow`

    References
    ----------
    .. [1] Gusfield D: Very simple methods for all pairs network flow analysis.
           SIAM J Comput 19(1):143-155, 1990.
networkx.google_matrix
Python Library Documentation: function google_matrix in module networkx.algorithms.link_analysis.pagerank_alg

google_matrix(G, alpha=0.85, personalization=None, nodelist=None, weight='weight', dangling=None, *, backend=None, **backend_kwargs)
    Returns the Google matrix of the graph.

    Parameters
    ----------
    G : graph
      A NetworkX graph.  Undirected graphs will be converted to a directed
      graph with two directed edges for each undirected edge.

    alpha : float
      The damping factor.

    personalization: dict, optional
      The "personalization vector" consisting of a dictionary with a
      key some subset of graph nodes and personalization value each of those.
      At least one personalization value must be non-zero.
      If not specified, a nodes personalization value will be zero.
      By default, a uniform distribution is used.

    nodelist : list, optional
      The rows and columns are ordered according to the nodes in nodelist.
      If nodelist is None, then the ordering is produced by G.nodes().

    weight : key, optional
      Edge data key to use as weight.  If None weights are set to 1.

    dangling: dict, optional
      The outedges to be assigned to any "dangling" nodes, i.e., nodes without
      any outedges. The dict key is the node the outedge points to and the dict
      value is the weight of that outedge. By default, dangling nodes are given
      outedges according to the personalization vector (uniform if not
      specified) This must be selected to result in an irreducible transition
      matrix (see notes below). It may be common to have the dangling dict to
      be the same as the personalization dict.

    Returns
    -------
    A : 2D NumPy ndarray
       Google matrix of the graph

    Notes
    -----
    The array returned represents the transition matrix that describes the
    Markov chain used in PageRank. For PageRank to converge to a unique
    solution (i.e., a unique stationary distribution in a Markov chain), the
    transition matrix must be irreducible. In other words, it must be that
    there exists a path between every pair of nodes in the graph, or else there
    is the potential of "rank sinks."

    This implementation works with Multi(Di)Graphs. For multigraphs the
    weight between two nodes is set to be the sum of all edge weights
    between those nodes.

    See Also
    --------
    pagerank
networkx.graph
Python Library Documentation: module networkx.classes.graph in networkx.classes

NAME
    networkx.classes.graph - Base class for undirected graphs.

DESCRIPTION
    The Graph class allows any hashable object as a node
    and can associate key/value attribute pairs with each undirected edge.

    Self-loops are allowed but multiple edges are not (see MultiGraph).

    For directed graphs see DiGraph and MultiDiGraph.

CLASSES
    builtins.object
        Graph

    class Graph(builtins.object)
     |  Graph(incoming_graph_data=None, **attr)
     |
     |  Base class for undirected graphs.
     |
     |  A Graph stores nodes and edges with optional data, or attributes.
     |
     |  Graphs hold undirected edges.  Self loops are allowed but multiple
     |  (parallel) edges are not.
     |
     |  Nodes can be arbitrary (hashable) Python objects with optional
     |  key/value attributes, except that `None` is not allowed as a node.
     |
     |  Edges are represented as links between nodes with optional
     |  key/value attributes.
     |
     |  Parameters
     |  ----------
     |  incoming_graph_data : input graph (optional, default: None)
     |      Data to initialize graph. If None (default) an empty
     |      graph is created.  The data can be any format that is supported
     |      by the to_networkx_graph() function, currently including edge list,
     |      dict of dicts, dict of lists, NetworkX graph, 2D NumPy array, SciPy
     |      sparse matrix, or PyGraphviz graph.
     |
     |  attr : keyword arguments, optional (default= no attributes)
     |      Attributes to add to graph as key=value pairs.
     |
     |  See Also
     |  --------
     |  DiGraph
     |  MultiGraph
     |  MultiDiGraph
     |
     |  Examples
     |  --------
     |  Create an empty graph structure (a "null graph") with no nodes and
     |  no edges.
     |
     |  >>> G = nx.Graph()
     |
     |  G can be grown in several ways.
     |
     |  **Nodes:**
     |
     |  Add one node at a time:
     |
     |  >>> G.add_node(1)
     |
     |  Add the nodes from any container (a list, dict, set or
     |  even the lines from a file or the nodes from another graph).
     |
     |  >>> G.add_nodes_from([2, 3])
     |  >>> G.add_nodes_from(range(100, 110))
     |  >>> H = nx.path_graph(10)
     |  >>> G.add_nodes_from(H)
     |
     |  In addition to strings and integers any hashable Python object
     |  (except None) can represent a node, e.g. a customized node object,
     |  or even another Graph.
     |
     |  >>> G.add_node(H)
     |
     |  **Edges:**
     |
     |  G can also be grown by adding edges.
     |
     |  Add one edge,
     |
     |  >>> G.add_edge(1, 2)
     |
     |  a list of edges,
     |
     |  >>> G.add_edges_from([(1, 2), (1, 3)])
     |
     |  or a collection of edges,
     |
     |  >>> G.add_edges_from(H.edges)
     |
     |  If some edges connect nodes not yet in the graph, the nodes
     |  are added automatically.  There are no errors when adding
     |  nodes or edges that already exist.
     |
     |  **Attributes:**
     |
     |  Each graph, node, and edge can hold key/value attribute pairs
     |  in an associated attribute dictionary (the keys must be hashable).
     |  By default these are empty, but can be added or changed using
     |  add_edge, add_node or direct manipulation of the attribute
     |  dictionaries named graph, node and edge respectively.
     |
     |  >>> G = nx.Graph(day="Friday")
     |  >>> G.graph
     |  {'day': 'Friday'}
     |
     |  Add node attributes using add_node(), add_nodes_from() or G.nodes
     |
     |  >>> G.add_node(1, time="5pm")
     |  >>> G.add_nodes_from([3], time="2pm")
     |  >>> G.nodes[1]
     |  {'time': '5pm'}
     |  >>> G.nodes[1]["room"] = 714  # node must exist already to use G.nodes
     |  >>> del G.nodes[1]["room"]  # remove attribute
     |  >>> list(G.nodes(data=True))
     |  [(1, {'time': '5pm'}), (3, {'time': '2pm'})]
     |
     |  Add edge attributes using add_edge(), add_edges_from(), subscript
     |  notation, or G.edges.
     |
     |  >>> G.add_edge(1, 2, weight=4.7)
     |  >>> G.add_edges_from([(3, 4), (4, 5)], color="red")
     |  >>> G.add_edges_from([(1, 2, {"color": "blue"}), (2, 3, {"weight": 8})])
     |  >>> G[1][2]["weight"] = 4.7
     |  >>> G.edges[1, 2]["weight"] = 4
     |
     |  Warning: we protect the graph data structure by making `G.edges` a
     |  read-only dict-like structure. However, you can assign to attributes
     |  in e.g. `G.edges[1, 2]`. Thus, use 2 sets of brackets to add/change
     |  data attributes: `G.edges[1, 2]['weight'] = 4`
     |  (For multigraphs: `MG.edges[u, v, key][name] = value`).
     |
     |  **Shortcuts:**
     |
     |  Many common graph features allow python syntax to speed reporting.
     |
     |  >>> 1 in G  # check if node in graph
     |  True
     |  >>> [n for n in G if n < 3]  # iterate through nodes
     |  [1, 2]
     |  >>> len(G)  # number of nodes in graph
     |  5
     |
     |  Often the best way to traverse all edges of a graph is via the neighbors.
     |  The neighbors are reported as an adjacency-dict `G.adj` or `G.adjacency()`
     |
     |  >>> for n, nbrsdict in G.adjacency():
     |  ...     for nbr, eattr in nbrsdict.items():
     |  ...         if "weight" in eattr:
     |  ...             # Do something useful with the edges
     |  ...             pass
     |
     |  But the edges() method is often more convenient:
     |
     |  >>> for u, v, weight in G.edges.data("weight"):
     |  ...     if weight is not None:
     |  ...         # Do something useful with the edges
     |  ...         pass
     |
     |  **Reporting:**
     |
     |  Simple graph information is obtained using object-attributes and methods.
     |  Reporting typically provides views instead of containers to reduce memory
     |  usage. The views update as the graph is updated similarly to dict-views.
     |  The objects `nodes`, `edges` and `adj` provide access to data attributes
     |  via lookup (e.g. `nodes[n]`, `edges[u, v]`, `adj[u][v]`) and iteration
     |  (e.g. `nodes.items()`, `nodes.data('color')`,
     |  `nodes.data('color', default='blue')` and similarly for `edges`)
     |  Views exist for `nodes`, `edges`, `neighbors()`/`adj` and `degree`.
     |
     |  For details on these and other miscellaneous methods, see below.
     |
     |  **Subclasses (Advanced):**
     |
     |  The Graph class uses a dict-of-dict-of-dict data structure.
     |  The outer dict (node_dict) holds adjacency information keyed by node.
     |  The next dict (adjlist_dict) represents the adjacency information and holds
     |  edge data keyed by neighbor.  The inner dict (edge_attr_dict) represents
     |  the edge data and holds edge attribute values keyed by attribute names.
     |
     |  Each of these three dicts can be replaced in a subclass by a user defined
     |  dict-like object. In general, the dict-like features should be
     |  maintained but extra features can be added. To replace one of the
     |  dicts create a new graph class by changing the class(!) variable
     |  holding the factory for that dict-like structure.
     |
     |  node_dict_factory : function, (default: dict)
     |      Factory function to be used to create the dict containing node
     |      attributes, keyed by node id.
     |      It should require no arguments and return a dict-like object
     |
     |  node_attr_dict_factory: function, (default: dict)
     |      Factory function to be used to create the node attribute
     |      dict which holds attribute values keyed by attribute name.
     |      It should require no arguments and return a dict-like object
     |
     |  adjlist_outer_dict_factory : function, (default: dict)
     |      Factory function to be used to create the outer-most dict
     |      in the data structure that holds adjacency info keyed by node.
     |      It should require no arguments and return a dict-like object.
     |
     |  adjlist_inner_dict_factory : function, (default: dict)
     |      Factory function to be used to create the adjacency list
     |      dict which holds edge data keyed by neighbor.
     |      It should require no arguments and return a dict-like object
     |
     |  edge_attr_dict_factory : function, (default: dict)
     |      Factory function to be used to create the edge attribute
     |      dict which holds attribute values keyed by attribute name.
     |      It should require no arguments and return a dict-like object.
     |
     |  graph_attr_dict_factory : function, (default: dict)
     |      Factory function to be used to create the graph attribute
     |      dict which holds attribute values keyed by attribute name.
     |      It should require no arguments and return a dict-like object.
     |
     |  Typically, if your extension doesn't impact the data structure all
     |  methods will inherit without issue except: `to_directed/to_undirected`.
     |  By default these methods create a DiGraph/Graph class and you probably
     |  want them to create your extension of a DiGraph/Graph. To facilitate
     |  this we define two class variables that you can set in your subclass.
     |
     |  to_directed_class : callable, (default: DiGraph or MultiDiGraph)
     |      Class to create a new graph structure in the `to_directed` method.
     |      If `None`, a NetworkX class (DiGraph or MultiDiGraph) is used.
     |
     |  to_undirected_class : callable, (default: Graph or MultiGraph)
     |      Class to create a new graph structure in the `to_undirected` method.
     |      If `None`, a NetworkX class (Graph or MultiGraph) is used.
     |
     |  **Subclassing Example**
     |
     |  Create a low memory graph class that effectively disallows edge
     |  attributes by using a single attribute dict for all edges.
     |  This reduces the memory used, but you lose edge attributes.
     |
     |  >>> class ThinGraph(nx.Graph):
     |  ...     all_edge_dict = {"weight": 1}
     |  ...
     |  ...     def single_edge_dict(self):
     |  ...         return self.all_edge_dict
     |  ...
     |  ...     edge_attr_dict_factory = single_edge_dict
     |  >>> G = ThinGraph()
     |  >>> G.add_edge(2, 1)
     |  >>> G[2][1]
     |  {'weight': 1}
     |  >>> G.add_edge(2, 2)
     |  >>> G[2][1] is G[2][2]
     |  True
     |
     |  Methods defined here:
     |
     |  __contains__(self, n)
     |      Returns True if n is a node, False otherwise. Use: 'n in G'.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> 1 in G
     |      True
     |
     |  __getitem__(self, n)
     |      Returns a dict of neighbors of node n.  Use: 'G[n]'.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph.
     |
     |      Returns
     |      -------
     |      adj_dict : dictionary
     |         The adjacency dictionary for nodes connected to n.
     |
     |      Notes
     |      -----
     |      G[n] is the same as G.adj[n] and similar to G.neighbors(n)
     |      (which is an iterator over G.adj[n])
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G[0]
     |      AtlasView({1: {}})
     |
     |  __init__(self, incoming_graph_data=None, **attr)
     |      Initialize a graph with edges, name, or graph attributes.
     |
     |      Parameters
     |      ----------
     |      incoming_graph_data : input graph (optional, default: None)
     |          Data to initialize graph. If None (default) an empty
     |          graph is created.  The data can be an edge list, or any
     |          NetworkX graph object.  If the corresponding optional Python
     |          packages are installed the data can also be a 2D NumPy array, a
     |          SciPy sparse array, or a PyGraphviz graph.
     |
     |      attr : keyword arguments, optional (default= no attributes)
     |          Attributes to add to graph as key=value pairs.
     |
     |      See Also
     |      --------
     |      convert
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G = nx.Graph(name="my graph")
     |      >>> e = [(1, 2), (2, 3), (3, 4)]  # list of edges
     |      >>> G = nx.Graph(e)
     |
     |      Arbitrary graph attribute pairs (key=value) may be assigned
     |
     |      >>> G = nx.Graph(e, day="Friday")
     |      >>> G.graph
     |      {'day': 'Friday'}
     |
     |  __iter__(self)
     |      Iterate over the nodes. Use: 'for n in G'.
     |
     |      Returns
     |      -------
     |      niter : iterator
     |          An iterator over all nodes in the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> [n for n in G]
     |      [0, 1, 2, 3]
     |      >>> list(G)
     |      [0, 1, 2, 3]
     |
     |  __len__(self)
     |      Returns the number of nodes in the graph. Use: 'len(G)'.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      number_of_nodes: identical method
     |      order: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> len(G)
     |      4
     |
     |  __str__(self)
     |      Returns a short summary of the graph.
     |
     |      Returns
     |      -------
     |      info : string
     |          Graph information including the graph name (if any), graph type, and the
     |          number of nodes and edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph(name="foo")
     |      >>> str(G)
     |      "Graph named 'foo' with 0 nodes and 0 edges"
     |
     |      >>> G = nx.path_graph(3)
     |      >>> str(G)
     |      'Graph with 3 nodes and 2 edges'
     |
     |  add_edge(self, u_of_edge, v_of_edge, **attr)
     |      Add an edge between u and v.
     |
     |      The nodes u and v will be automatically added if they are
     |      not already in the graph.
     |
     |      Edge attributes can be specified with keywords or by directly
     |      accessing the edge's attribute dictionary. See examples below.
     |
     |      Parameters
     |      ----------
     |      u_of_edge, v_of_edge : nodes
     |          Nodes can be, for example, strings or numbers.
     |          Nodes must be hashable (and not None) Python objects.
     |      attr : keyword arguments, optional
     |          Edge data (or labels or objects) can be assigned using
     |          keyword arguments.
     |
     |      See Also
     |      --------
     |      add_edges_from : add a collection of edges
     |
     |      Notes
     |      -----
     |      Adding an edge that already exists updates the edge data.
     |
     |      Many NetworkX algorithms designed for weighted graphs use
     |      an edge attribute (by default `weight`) to hold a numerical value.
     |
     |      Examples
     |      --------
     |      The following all add the edge e=(1, 2) to graph G:
     |
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> e = (1, 2)
     |      >>> G.add_edge(1, 2)  # explicit two-node form
     |      >>> G.add_edge(*e)  # single edge as tuple of two nodes
     |      >>> G.add_edges_from([(1, 2)])  # add edges from iterable container
     |
     |      Associate data to edges using keywords:
     |
     |      >>> G.add_edge(1, 2, weight=3)
     |      >>> G.add_edge(1, 3, weight=7, capacity=15, length=342.7)
     |
     |      For non-string attribute keys, use subscript notation.
     |
     |      >>> G.add_edge(1, 2)
     |      >>> G[1][2].update({0: 5})
     |      >>> G.edges[1, 2].update({0: 5})
     |
     |  add_edges_from(self, ebunch_to_add, **attr)
     |      Add all the edges in ebunch_to_add.
     |
     |      Parameters
     |      ----------
     |      ebunch_to_add : container of edges
     |          Each edge given in the container will be added to the
     |          graph. The edges must be given as 2-tuples (u, v) or
     |          3-tuples (u, v, d) where d is a dictionary containing edge data.
     |      attr : keyword arguments, optional
     |          Edge data (or labels or objects) can be assigned using
     |          keyword arguments.
     |
     |      See Also
     |      --------
     |      add_edge : add a single edge
     |      add_weighted_edges_from : convenient way to add weighted edges
     |
     |      Notes
     |      -----
     |      Adding the same edge twice has no effect but any edge data
     |      will be updated when each duplicate edge is added.
     |
     |      Edge attributes specified in an ebunch take precedence over
     |      attributes specified via keyword arguments.
     |
     |      When adding edges from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_edges)`, and pass this
     |      object to `G.add_edges_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_edges_from([(0, 1), (1, 2)])  # using a list of edge tuples
     |      >>> e = zip(range(0, 3), range(1, 4))
     |      >>> G.add_edges_from(e)  # Add the path graph 0-1-2-3
     |
     |      Associate data to edges
     |
     |      >>> G.add_edges_from([(1, 2), (2, 3)], weight=3)
     |      >>> G.add_edges_from([(3, 4), (1, 4)], label="WN2898")
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.Graph([(1, 2), (2, 3), (3, 4)])
     |      >>> # Grow graph by one new node, adding edges to all existing nodes.
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_edges_from(((5, n) for n in G.nodes))
     |      >>> # correct way - note that there will be no self-edge for node 5
     |      >>> G.add_edges_from(list((5, n) for n in G.nodes))
     |
     |  add_node(self, node_for_adding, **attr)
     |      Add a single node `node_for_adding` and update node attributes.
     |
     |      Parameters
     |      ----------
     |      node_for_adding : node
     |          A node can be any hashable Python object except None.
     |      attr : keyword arguments, optional
     |          Set or change node attributes using key=value.
     |
     |      See Also
     |      --------
     |      add_nodes_from
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_node(1)
     |      >>> G.add_node("Hello")
     |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
     |      >>> G.add_node(K3)
     |      >>> G.number_of_nodes()
     |      3
     |
     |      Use keywords set/change node attributes:
     |
     |      >>> G.add_node(1, size=10)
     |      >>> G.add_node(3, weight=0.4, UTM=("13S", 382871, 3972649))
     |
     |      Notes
     |      -----
     |      A hashable object is one that can be used as a key in a Python
     |      dictionary. This includes strings, numbers, tuples of strings
     |      and numbers, etc.
     |
     |      On many platforms hashable items also include mutables such as
     |      NetworkX Graphs, though one should be careful that the hash
     |      doesn't change on mutables.
     |
     |  add_nodes_from(self, nodes_for_adding, **attr)
     |      Add multiple nodes.
     |
     |      Parameters
     |      ----------
     |      nodes_for_adding : iterable container
     |          A container of nodes (list, dict, set, etc.).
     |          OR
     |          A container of (node, attribute dict) tuples.
     |          Node attributes are updated using the attribute dict.
     |      attr : keyword arguments, optional (default= no attributes)
     |          Update attributes for all nodes in nodes.
     |          Node attributes specified in nodes as a tuple take
     |          precedence over attributes specified via keyword arguments.
     |
     |      See Also
     |      --------
     |      add_node
     |
     |      Notes
     |      -----
     |      When adding nodes from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
     |      object to `G.add_nodes_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_nodes_from("Hello")
     |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
     |      >>> G.add_nodes_from(K3)
     |      >>> sorted(G.nodes(), key=str)
     |      [0, 1, 2, 'H', 'e', 'l', 'o']
     |
     |      Use keywords to update specific node attributes for every node.
     |
     |      >>> G.add_nodes_from([1, 2], size=10)
     |      >>> G.add_nodes_from([3, 4], weight=0.4)
     |
     |      Use (node, attrdict) tuples to update attributes for specific nodes.
     |
     |      >>> G.add_nodes_from([(1, dict(size=11)), (2, {"color": "blue"})])
     |      >>> G.nodes[1]["size"]
     |      11
     |      >>> H = nx.Graph()
     |      >>> H.add_nodes_from(G.nodes(data=True))
     |      >>> H.nodes[1]["size"]
     |      11
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.Graph([(0, 1), (1, 2), (3, 4)])
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_nodes_from(n + 1 for n in G.nodes)
     |      >>> # correct way
     |      >>> G.add_nodes_from(list(n + 1 for n in G.nodes))
     |
     |  add_weighted_edges_from(self, ebunch_to_add, weight='weight', **attr)
     |      Add weighted edges in `ebunch_to_add` with specified weight attr
     |
     |      Parameters
     |      ----------
     |      ebunch_to_add : container of edges
     |          Each edge given in the list or container will be added
     |          to the graph. The edges must be given as 3-tuples (u, v, w)
     |          where w is a number.
     |      weight : string, optional (default= 'weight')
     |          The attribute name for the edge weights to be added.
     |      attr : keyword arguments, optional (default= no attributes)
     |          Edge attributes to add/update for all edges.
     |
     |      See Also
     |      --------
     |      add_edge : add a single edge
     |      add_edges_from : add multiple edges
     |
     |      Notes
     |      -----
     |      Adding the same edge twice for Graph/DiGraph simply updates
     |      the edge data. For MultiGraph/MultiDiGraph, duplicate edges
     |      are stored.
     |
     |      When adding edges from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_edges)`, and pass this
     |      object to `G.add_weighted_edges_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_weighted_edges_from([(0, 1, 3.0), (1, 2, 7.5)])
     |
     |      Evaluate an iterator over edges before passing it
     |
     |      >>> G = nx.Graph([(1, 2), (2, 3), (3, 4)])
     |      >>> weight = 0.1
     |      >>> # Grow graph by one new node, adding edges to all existing nodes.
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_weighted_edges_from(((5, n, weight) for n in G.nodes))
     |      >>> # correct way - note that there will be no self-edge for node 5
     |      >>> G.add_weighted_edges_from(list((5, n, weight) for n in G.nodes))
     |
     |  adj = <functools.cached_property object>
     |      Graph adjacency object holding the neighbors of each node.
     |
     |      This object is a read-only dict-like structure with node keys
     |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
     |      to the edge-data-dict.  So `G.adj[3][2]['color'] = 'blue'` sets
     |      the color of the edge `(3, 2)` to `"blue"`.
     |
     |      Iterating over G.adj behaves like a dict. Useful idioms include
     |      `for nbr, datadict in G.adj[n].items():`.
     |
     |      The neighbor information is also provided by subscripting the graph.
     |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
     |
     |      For directed graphs, `G.adj` holds outgoing (successor) info.
     |
     |  adjacency(self)
     |      Returns an iterator over (node, adjacency dict) tuples for all nodes.
     |
     |      For directed graphs, only outgoing neighbors/adjacencies are included.
     |
     |      Returns
     |      -------
     |      adj_iter : iterator
     |         An iterator over (node, adjacency dictionary) for all nodes in
     |         the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> [(n, nbrdict) for n, nbrdict in G.adjacency()]
     |      [(0, {1: {}}), (1, {0: {}, 2: {}}), (2, {1: {}, 3: {}}), (3, {2: {}})]
     |
     |  clear(self)
     |      Remove all nodes and edges from the graph.
     |
     |      This also removes the name, and all graph, node, and edge attributes.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.clear()
     |      >>> list(G.nodes)
     |      []
     |      >>> list(G.edges)
     |      []
     |
     |  clear_edges(self)
     |      Remove all edges from the graph without altering nodes.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.clear_edges()
     |      >>> list(G.nodes)
     |      [0, 1, 2, 3]
     |      >>> list(G.edges)
     |      []
     |
     |  copy(self, as_view=False)
     |      Returns a copy of the graph.
     |
     |      The copy method by default returns an independent shallow copy
     |      of the graph and attributes. That is, if an attribute is a
     |      container, that container is shared by the original an the copy.
     |      Use Python's `copy.deepcopy` for new containers.
     |
     |      If `as_view` is True then a view is returned instead of a copy.
     |
     |      Notes
     |      -----
     |      All copies reproduce the graph structure, but data attributes
     |      may be handled in different ways. There are four types of copies
     |      of a graph that people might want.
     |
     |      Deepcopy -- A "deepcopy" copies the graph structure as well as
     |      all data attributes and any objects they might contain.
     |      The entire graph object is new so that changes in the copy
     |      do not affect the original object. (see Python's copy.deepcopy)
     |
     |      Data Reference (Shallow) -- For a shallow copy the graph structure
     |      is copied but the edge, node and graph attribute dicts are
     |      references to those in the original graph. This saves
     |      time and memory but could cause confusion if you change an attribute
     |      in one graph and it changes the attribute in the other.
     |      NetworkX does not provide this level of shallow copy.
     |
     |      Independent Shallow -- This copy creates new independent attribute
     |      dicts and then does a shallow copy of the attributes. That is, any
     |      attributes that are containers are shared between the new graph
     |      and the original. This is exactly what `dict.copy()` provides.
     |      You can obtain this style copy using:
     |
     |          >>> G = nx.path_graph(5)
     |          >>> H = G.copy()
     |          >>> H = G.copy(as_view=False)
     |          >>> H = nx.Graph(G)
     |          >>> H = G.__class__(G)
     |
     |      Fresh Data -- For fresh data, the graph structure is copied while
     |      new empty data attribute dicts are created. The resulting graph
     |      is independent of the original and it has no edge, node or graph
     |      attributes. Fresh copies are not enabled. Instead use:
     |
     |          >>> H = G.__class__()
     |          >>> H.add_nodes_from(G)
     |          >>> H.add_edges_from(G.edges)
     |
     |      View -- Inspired by dict-views, graph-views act like read-only
     |      versions of the original graph, providing a copy of the original
     |      structure without requiring any memory for copying the information.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Parameters
     |      ----------
     |      as_view : bool, optional (default=False)
     |          If True, the returned graph-view provides a read-only view
     |          of the original graph without actually copying any data.
     |
     |      Returns
     |      -------
     |      G : Graph
     |          A copy of the graph.
     |
     |      See Also
     |      --------
     |      to_directed: return a directed copy of the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> H = G.copy()
     |
     |  degree = <functools.cached_property object>
     |      A DegreeView for the Graph as G.degree or G.degree().
     |
     |      The node degree is the number of edges adjacent to the node.
     |      The weighted node degree is the sum of the edge weights for
     |      edges incident to that node.
     |
     |      This object provides an iterator for (node, degree) as well as
     |      lookup for the degree for a single node.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      weight : string or None, optional (default=None)
     |         The name of an edge attribute that holds the numerical value used
     |         as a weight.  If None, then each edge has weight 1.
     |         The degree is the sum of the edge weights adjacent to the node.
     |
     |      Returns
     |      -------
     |      DegreeView or int
     |          If multiple nodes are requested (the default), returns a `DegreeView`
     |          mapping nodes to their degree.
     |          If a single node is requested, returns the degree of the node as an integer.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.degree[0]  # node 0 has degree 1
     |      1
     |      >>> list(G.degree([0, 1, 2]))
     |      [(0, 1), (1, 2), (2, 2)]
     |
     |  edge_subgraph(self, edges)
     |      Returns the subgraph induced by the specified edges.
     |
     |      The induced subgraph contains each edge in `edges` and each
     |      node incident to any one of those edges.
     |
     |      Parameters
     |      ----------
     |      edges : iterable
     |          An iterable of edges in this graph.
     |
     |      Returns
     |      -------
     |      G : Graph
     |          An edge-induced subgraph of this graph with the same edge
     |          attributes.
     |
     |      Notes
     |      -----
     |      The graph, edge, and node attributes in the returned subgraph
     |      view are references to the corresponding attributes in the original
     |      graph. The view is read-only.
     |
     |      To create a full graph version of the subgraph with its own copy
     |      of the edge or node attributes, use::
     |
     |          G.edge_subgraph(edges).copy()
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(5)
     |      >>> H = G.edge_subgraph([(0, 1), (3, 4)])
     |      >>> list(H.nodes)
     |      [0, 1, 3, 4]
     |      >>> list(H.edges)
     |      [(0, 1), (3, 4)]
     |
     |  edges = <functools.cached_property object>
     |      An EdgeView of the Graph as G.edges or G.edges().
     |
     |      edges(self, nbunch=None, data=False, default=None)
     |
     |      The EdgeView provides set-like operations on the edge-tuples
     |      as well as edge attribute lookup. When called, it also provides
     |      an EdgeDataView object which allows control of access to edge
     |      attributes (but does not provide set-like operations).
     |      Hence, `G.edges[u, v]['color']` provides the value of the color
     |      attribute for edge `(u, v)` while
     |      `for (u, v, c) in G.edges.data('color', default='red'):`
     |      iterates through all the edges yielding the color attribute
     |      with default `'red'` if no color attribute exists.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges from these nodes.
     |      data : string or bool, optional (default=False)
     |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
     |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
     |          If False, return 2-tuple (u, v).
     |      default : value, optional (default=None)
     |          Value used for edges that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      edges : EdgeView
     |          A view of edge attributes, usually it iterates over (u, v)
     |          or (u, v, d) tuples of edges, but can also be used for
     |          attribute lookup as `edges[u, v]['foo']`.
     |
     |      Notes
     |      -----
     |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
     |      For directed graphs this returns the out-edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or MultiGraph, etc
     |      >>> G.add_edge(2, 3, weight=5)
     |      >>> [e for e in G.edges]
     |      [(0, 1), (1, 2), (2, 3)]
     |      >>> G.edges.data()  # default data is {} (empty dict)
     |      EdgeDataView([(0, 1, {}), (1, 2, {}), (2, 3, {'weight': 5})])
     |      >>> G.edges.data("weight", default=1)
     |      EdgeDataView([(0, 1, 1), (1, 2, 1), (2, 3, 5)])
     |      >>> G.edges([0, 3])  # only edges from these nodes
     |      EdgeDataView([(0, 1), (3, 2)])
     |      >>> G.edges(0)  # only edges from node 0
     |      EdgeDataView([(0, 1)])
     |
     |  get_edge_data(self, u, v, default=None)
     |      Returns the attribute dictionary associated with edge (u, v).
     |
     |      This is identical to `G[u][v]` except the default is returned
     |      instead of an exception if the edge doesn't exist.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |      default:  any Python object (default=None)
     |          Value to return if the edge (u, v) is not found.
     |
     |      Returns
     |      -------
     |      edge_dict : dictionary
     |          The edge attribute dictionary.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G[0][1]
     |      {}
     |
     |      Warning: Assigning to `G[u][v]` is not permitted.
     |      But it is safe to assign attributes `G[u][v]['foo']`
     |
     |      >>> G[0][1]["weight"] = 7
     |      >>> G[0][1]["weight"]
     |      7
     |      >>> G[1][0]["weight"]
     |      7
     |
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.get_edge_data(0, 1)  # default edge data is {}
     |      {}
     |      >>> e = (0, 1)
     |      >>> G.get_edge_data(*e)  # tuple form
     |      {}
     |      >>> G.get_edge_data("a", "b", default=0)  # edge not in graph, return 0
     |      0
     |
     |  has_edge(self, u, v)
     |      Returns True if the edge (u, v) is in the graph.
     |
     |      This is the same as `v in G[u]` without KeyError exceptions.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |          Nodes can be, for example, strings or numbers.
     |          Nodes must be hashable (and not None) Python objects.
     |
     |      Returns
     |      -------
     |      edge_ind : bool
     |          True if edge is in the graph, False otherwise.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.has_edge(0, 1)  # using two nodes
     |      True
     |      >>> e = (0, 1)
     |      >>> G.has_edge(*e)  #  e is a 2-tuple (u, v)
     |      True
     |      >>> e = (0, 1, {"weight": 7})
     |      >>> G.has_edge(*e[:2])  # e is a 3-tuple (u, v, data_dictionary)
     |      True
     |
     |      The following syntax are equivalent:
     |
     |      >>> G.has_edge(0, 1)
     |      True
     |      >>> 1 in G[0]  # though this gives KeyError if 0 not in G
     |      True
     |
     |  has_node(self, n)
     |      Returns True if the graph contains the node n.
     |
     |      Identical to `n in G`
     |
     |      Parameters
     |      ----------
     |      n : node
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.has_node(0)
     |      True
     |
     |      It is more readable and simpler to use
     |
     |      >>> 0 in G
     |      True
     |
     |  is_directed(self)
     |      Returns True if graph is directed, False otherwise.
     |
     |  is_multigraph(self)
     |      Returns True if graph is a multigraph, False otherwise.
     |
     |  nbunch_iter(self, nbunch=None)
     |      Returns an iterator over nodes contained in nbunch that are
     |      also in the graph.
     |
     |      The nodes in nbunch are checked for membership in the graph
     |      and if not are silently ignored.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      Returns
     |      -------
     |      niter : iterator
     |          An iterator over nodes in nbunch that are also in the graph.
     |          If nbunch is None, iterate over all nodes in the graph.
     |
     |      Raises
     |      ------
     |      NetworkXError
     |          If nbunch is not a node or sequence of nodes.
     |          If a node in nbunch is not hashable.
     |
     |      See Also
     |      --------
     |      Graph.__iter__
     |
     |      Notes
     |      -----
     |      When nbunch is an iterator, the returned iterator yields values
     |      directly from nbunch, becoming exhausted when nbunch is exhausted.
     |
     |      To test whether nbunch is a single node, one can use
     |      "if nbunch in self:", even after processing with this routine.
     |
     |      If nbunch is not a node or a (possibly empty) sequence/iterator
     |      or None, a :exc:`NetworkXError` is raised.  Also, if any object in
     |      nbunch is not hashable, a :exc:`NetworkXError` is raised.
     |
     |  neighbors(self, n)
     |      Returns an iterator over all neighbors of node n.
     |
     |      This is identical to `iter(G[n])`
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Returns
     |      -------
     |      neighbors : iterator
     |          An iterator over all neighbors of node n
     |
     |      Raises
     |      ------
     |      NetworkXError
     |          If the node n is not in the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> [n for n in G.neighbors(0)]
     |      [1]
     |
     |      Notes
     |      -----
     |      Alternate ways to access the neighbors are ``G.adj[n]`` or ``G[n]``:
     |
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_edge("a", "b", weight=7)
     |      >>> G["a"]
     |      AtlasView({'b': {'weight': 7}})
     |      >>> G = nx.path_graph(4)
     |      >>> [n for n in G[0]]
     |      [1]
     |
     |  nodes = <functools.cached_property object>
     |      A NodeView of the Graph as G.nodes or G.nodes().
     |
     |      Can be used as `G.nodes` for data lookup and for set-like operations.
     |      Can also be used as `G.nodes(data='color', default=None)` to return a
     |      NodeDataView which reports specific node data but no set operations.
     |      It presents a dict-like interface as well with `G.nodes.items()`
     |      iterating over `(node, nodedata)` 2-tuples and `G.nodes[3]['foo']`
     |      providing the value of the `foo` attribute for node `3`. In addition,
     |      a view `G.nodes.data('foo')` provides a dict-like interface to the
     |      `foo` attribute of each node. `G.nodes.data('foo', default=1)`
     |      provides a default for nodes that do not have attribute `foo`.
     |
     |      Parameters
     |      ----------
     |      data : string or bool, optional (default=False)
     |          The node attribute returned in 2-tuple (n, ddict[data]).
     |          If True, return entire node attribute dict as (n, ddict).
     |          If False, return just the nodes n.
     |
     |      default : value, optional (default=None)
     |          Value used for nodes that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      NodeView
     |          Allows set-like operations over the nodes as well as node
     |          attribute dict lookup and calling to get a NodeDataView.
     |          A NodeDataView iterates over `(n, data)` and has no set operations.
     |          A NodeView iterates over `n` and includes set operations.
     |
     |          When called, if data is False, an iterator over nodes.
     |          Otherwise an iterator of 2-tuples (node, attribute value)
     |          where the attribute is specified in `data`.
     |          If data is True then the attribute becomes the
     |          entire data dictionary.
     |
     |      Notes
     |      -----
     |      If your node data is not needed, it is simpler and equivalent
     |      to use the expression ``for n in G``, or ``list(G)``.
     |
     |      Examples
     |      --------
     |      There are two simple ways of getting a list of all nodes in the graph:
     |
     |      >>> G = nx.path_graph(3)
     |      >>> list(G.nodes)
     |      [0, 1, 2]
     |      >>> list(G)
     |      [0, 1, 2]
     |
     |      To get the node data along with the nodes:
     |
     |      >>> G.add_node(1, time="5pm")
     |      >>> G.nodes[0]["foo"] = "bar"
     |      >>> list(G.nodes(data=True))
     |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
     |      >>> list(G.nodes.data())
     |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
     |
     |      >>> list(G.nodes(data="foo"))
     |      [(0, 'bar'), (1, None), (2, None)]
     |      >>> list(G.nodes.data("foo"))
     |      [(0, 'bar'), (1, None), (2, None)]
     |
     |      >>> list(G.nodes(data="time"))
     |      [(0, None), (1, '5pm'), (2, None)]
     |      >>> list(G.nodes.data("time"))
     |      [(0, None), (1, '5pm'), (2, None)]
     |
     |      >>> list(G.nodes(data="time", default="Not Available"))
     |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
     |      >>> list(G.nodes.data("time", default="Not Available"))
     |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
     |
     |      If some of your nodes have an attribute and the rest are assumed
     |      to have a default attribute value you can create a dictionary
     |      from node/attribute pairs using the `default` keyword argument
     |      to guarantee the value is never None::
     |
     |          >>> G = nx.Graph()
     |          >>> G.add_node(0)
     |          >>> G.add_node(1, weight=2)
     |          >>> G.add_node(2, weight=3)
     |          >>> dict(G.nodes(data="weight", default=1))
     |          {0: 1, 1: 2, 2: 3}
     |
     |  number_of_edges(self, u=None, v=None)
     |      Returns the number of edges between two nodes.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes, optional (default=all edges)
     |          If u and v are specified, return the number of edges between
     |          u and v. Otherwise return the total number of all edges.
     |
     |      Returns
     |      -------
     |      nedges : int
     |          The number of edges in the graph.  If nodes `u` and `v` are
     |          specified return the number of edges between those nodes. If
     |          the graph is directed, this only returns the number of edges
     |          from `u` to `v`.
     |
     |      See Also
     |      --------
     |      size
     |
     |      Examples
     |      --------
     |      For undirected graphs, this method counts the total number of
     |      edges in the graph:
     |
     |      >>> G = nx.path_graph(4)
     |      >>> G.number_of_edges()
     |      3
     |
     |      If you specify two nodes, this counts the total number of edges
     |      joining the two nodes:
     |
     |      >>> G.number_of_edges(0, 1)
     |      1
     |
     |      For directed graphs, this method can count the total number of
     |      directed edges from `u` to `v`:
     |
     |      >>> G = nx.DiGraph()
     |      >>> G.add_edge(0, 1)
     |      >>> G.add_edge(1, 0)
     |      >>> G.number_of_edges(0, 1)
     |      1
     |
     |  number_of_nodes(self)
     |      Returns the number of nodes in the graph.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      order: identical method
     |      __len__: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.number_of_nodes()
     |      3
     |
     |  order(self)
     |      Returns the number of nodes in the graph.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      number_of_nodes: identical method
     |      __len__: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.order()
     |      3
     |
     |  remove_edge(self, u, v)
     |      Remove the edge between u and v.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |          Remove the edge between nodes u and v.
     |
     |      Raises
     |      ------
     |      NetworkXError
     |          If there is not an edge between u and v.
     |
     |      See Also
     |      --------
     |      remove_edges_from : remove a collection of edges
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, etc
     |      >>> G.remove_edge(0, 1)
     |      >>> e = (1, 2)
     |      >>> G.remove_edge(*e)  # unpacks e from an edge tuple
     |      >>> e = (2, 3, {"weight": 7})  # an edge with attribute data
     |      >>> G.remove_edge(*e[:2])  # select first part of edge tuple
     |
     |  remove_edges_from(self, ebunch)
     |      Remove all edges specified in ebunch.
     |
     |      Parameters
     |      ----------
     |      ebunch: list or container of edge tuples
     |          Each edge given in the list or container will be removed
     |          from the graph. The edges can be:
     |
     |              - 2-tuples (u, v) edge between u and v.
     |              - 3-tuples (u, v, k) where k is ignored.
     |
     |      See Also
     |      --------
     |      remove_edge : remove a single edge
     |
     |      Notes
     |      -----
     |      Will fail silently if an edge in ebunch is not in the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> ebunch = [(1, 2), (2, 3)]
     |      >>> G.remove_edges_from(ebunch)
     |
     |  remove_node(self, n)
     |      Remove node n.
     |
     |      Removes the node n and all adjacent edges.
     |      Attempting to remove a nonexistent node will raise an exception.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Raises
     |      ------
     |      NetworkXError
     |         If n is not in the graph.
     |
     |      See Also
     |      --------
     |      remove_nodes_from
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> list(G.edges)
     |      [(0, 1), (1, 2)]
     |      >>> G.remove_node(1)
     |      >>> list(G.edges)
     |      []
     |
     |  remove_nodes_from(self, nodes)
     |      Remove multiple nodes.
     |
     |      Parameters
     |      ----------
     |      nodes : iterable container
     |          A container of nodes (list, dict, set, etc.).  If a node
     |          in the container is not in the graph it is silently
     |          ignored.
     |
     |      See Also
     |      --------
     |      remove_node
     |
     |      Notes
     |      -----
     |      When removing nodes from an iterator over the graph you are changing,
     |      a `RuntimeError` will be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
     |      object to `G.remove_nodes_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> e = list(G.nodes)
     |      >>> e
     |      [0, 1, 2]
     |      >>> G.remove_nodes_from(e)
     |      >>> list(G.nodes)
     |      []
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.Graph([(0, 1), (1, 2), (3, 4)])
     |      >>> # this command will fail, as the graph's dict is modified during iteration
     |      >>> # G.remove_nodes_from(n for n in G.nodes if n < 2)
     |      >>> # this command will work, since the dictionary underlying graph is not modified
     |      >>> G.remove_nodes_from(list(n for n in G.nodes if n < 2))
     |
     |  size(self, weight=None)
     |      Returns the number of edges or total of all edge weights.
     |
     |      Parameters
     |      ----------
     |      weight : string or None, optional (default=None)
     |          The edge attribute that holds the numerical value used
     |          as a weight. If None, then each edge has weight 1.
     |
     |      Returns
     |      -------
     |      size : numeric
     |          The number of edges or
     |          (if weight keyword is provided) the total weight sum.
     |
     |          If weight is None, returns an int. Otherwise a float
     |          (or more general numeric if the weights are more general).
     |
     |      See Also
     |      --------
     |      number_of_edges
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.size()
     |      3
     |
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_edge("a", "b", weight=2)
     |      >>> G.add_edge("b", "c", weight=4)
     |      >>> G.size()
     |      2
     |      >>> G.size(weight="weight")
     |      6.0
     |
     |  subgraph(self, nodes)
     |      Returns a SubGraph view of the subgraph induced on `nodes`.
     |
     |      The induced subgraph of the graph contains the nodes in `nodes`
     |      and the edges between those nodes.
     |
     |      Parameters
     |      ----------
     |      nodes : list, iterable
     |          A container of nodes which will be iterated through once.
     |
     |      Returns
     |      -------
     |      G : SubGraph View
     |          A subgraph view of the graph. The graph structure cannot be
     |          changed but node/edge attributes can and are shared with the
     |          original graph.
     |
     |      Notes
     |      -----
     |      The graph, edge and node attributes are shared with the original graph.
     |      Changes to the graph structure is ruled out by the view, but changes
     |      to attributes are reflected in the original graph.
     |
     |      To create a subgraph with its own copy of the edge/node attributes use:
     |      G.subgraph(nodes).copy()
     |
     |      For an inplace reduction of a graph to a subgraph you can remove nodes:
     |      G.remove_nodes_from([n for n in G if n not in set(nodes)])
     |
     |      Subgraph views are sometimes NOT what you want. In most cases where
     |      you want to do more than simply look at the induced edges, it makes
     |      more sense to just create the subgraph as its own graph with code like:
     |
     |      ::
     |
     |          # Create a subgraph SG based on a (possibly multigraph) G
     |          SG = G.__class__()
     |          SG.add_nodes_from((n, G.nodes[n]) for n in largest_wcc)
     |          if SG.is_multigraph():
     |              SG.add_edges_from(
     |                  (n, nbr, key, d)
     |                  for n, nbrs in G.adj.items()
     |                  if n in largest_wcc
     |                  for nbr, keydict in nbrs.items()
     |                  if nbr in largest_wcc
     |                  for key, d in keydict.items()
     |              )
     |          else:
     |              SG.add_edges_from(
     |                  (n, nbr, d)
     |                  for n, nbrs in G.adj.items()
     |                  if n in largest_wcc
     |                  for nbr, d in nbrs.items()
     |                  if nbr in largest_wcc
     |              )
     |          SG.graph.update(G.graph)
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> H = G.subgraph([0, 1, 2])
     |      >>> list(H.edges)
     |      [(0, 1), (1, 2)]
     |
     |  to_directed(self, as_view=False)
     |      Returns a directed representation of the graph.
     |
     |      Returns
     |      -------
     |      G : DiGraph
     |          A directed graph with the same name, same nodes, and with
     |          each edge (u, v, data) replaced by two directed edges
     |          (u, v, data) and (v, u, data).
     |
     |      Notes
     |      -----
     |      This returns a "deepcopy" of the edge, node, and
     |      graph attributes which attempts to completely copy
     |      all of the data and references.
     |
     |      This is in contrast to the similar D=DiGraph(G) which returns a
     |      shallow copy of the data.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Warning: If you have subclassed Graph to use dict-like objects
     |      in the data structure, those changes do not transfer to the
     |      DiGraph created by this method.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or MultiGraph, etc
     |      >>> G.add_edge(0, 1)
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1), (1, 0)]
     |
     |      If already directed, return a (deep) copy
     |
     |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
     |      >>> G.add_edge(0, 1)
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1)]
     |
     |  to_directed_class(self)
     |      Returns the class to use for empty directed copies.
     |
     |      If you subclass the base classes, use this to designate
     |      what directed class to use for `to_directed()` copies.
     |
     |  to_undirected(self, as_view=False)
     |      Returns an undirected copy of the graph.
     |
     |      Parameters
     |      ----------
     |      as_view : bool (optional, default=False)
     |        If True return a view of the original undirected graph.
     |
     |      Returns
     |      -------
     |      G : Graph/MultiGraph
     |          A deepcopy of the graph.
     |
     |      See Also
     |      --------
     |      Graph, copy, add_edge, add_edges_from
     |
     |      Notes
     |      -----
     |      This returns a "deepcopy" of the edge, node, and
     |      graph attributes which attempts to completely copy
     |      all of the data and references.
     |
     |      This is in contrast to the similar `G = nx.DiGraph(D)` which returns a
     |      shallow copy of the data.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Warning: If you have subclassed DiGraph to use dict-like objects
     |      in the data structure, those changes do not transfer to the
     |      Graph created by this method.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(2)  # or MultiGraph, etc
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1), (1, 0)]
     |      >>> G2 = H.to_undirected()
     |      >>> list(G2.edges)
     |      [(0, 1)]
     |
     |  to_undirected_class(self)
     |      Returns the class to use for empty undirected copies.
     |
     |      If you subclass the base classes, use this to designate
     |      what directed class to use for `to_directed()` copies.
     |
     |  update(self, edges=None, nodes=None)
     |      Update the graph using nodes/edges/graphs as input.
     |
     |      Like dict.update, this method takes a graph as input, adding the
     |      graph's nodes and edges to this graph. It can also take two inputs:
     |      edges and nodes. Finally it can take either edges or nodes.
     |      To specify only nodes the keyword `nodes` must be used.
     |
     |      The collections of edges and nodes are treated similarly to
     |      the add_edges_from/add_nodes_from methods. When iterated, they
     |      should yield 2-tuples (u, v) or 3-tuples (u, v, datadict).
     |
     |      Parameters
     |      ----------
     |      edges : Graph object, collection of edges, or None
     |          The first parameter can be a graph or some edges. If it has
     |          attributes `nodes` and `edges`, then it is taken to be a
     |          Graph-like object and those attributes are used as collections
     |          of nodes and edges to be added to the graph.
     |          If the first parameter does not have those attributes, it is
     |          treated as a collection of edges and added to the graph.
     |          If the first argument is None, no edges are added.
     |      nodes : collection of nodes, or None
     |          The second parameter is treated as a collection of nodes
     |          to be added to the graph unless it is None.
     |          If `edges is None` and `nodes is None` an exception is raised.
     |          If the first parameter is a Graph, then `nodes` is ignored.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(5)
     |      >>> G.update(nx.complete_graph(range(4, 10)))
     |      >>> from itertools import combinations
     |      >>> edges = (
     |      ...     (u, v, {"power": u * v})
     |      ...     for u, v in combinations(range(10, 20), 2)
     |      ...     if u * v < 225
     |      ... )
     |      >>> nodes = [1000]  # for singleton, use a container
     |      >>> G.update(edges, nodes)
     |
     |      Notes
     |      -----
     |      It you want to update the graph using an adjacency structure
     |      it is straightforward to obtain the edges/nodes from adjacency.
     |      The following examples provide common cases, your adjacency may
     |      be slightly different and require tweaks of these examples::
     |
     |      >>> # dict-of-set/list/tuple
     |      >>> adj = {1: {2, 3}, 2: {1, 3}, 3: {1, 2}}
     |      >>> e = [(u, v) for u, nbrs in adj.items() for v in nbrs]
     |      >>> G.update(edges=e, nodes=adj)
     |
     |      >>> DG = nx.DiGraph()
     |      >>> # dict-of-dict-of-attribute
     |      >>> adj = {1: {2: 1.3, 3: 0.7}, 2: {1: 1.4}, 3: {1: 0.7}}
     |      >>> e = [
     |      ...     (u, v, {"weight": d})
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, d in nbrs.items()
     |      ... ]
     |      >>> DG.update(edges=e, nodes=adj)
     |
     |      >>> # dict-of-dict-of-dict
     |      >>> adj = {1: {2: {"weight": 1.3}, 3: {"color": 0.7, "weight": 1.2}}}
     |      >>> e = [
     |      ...     (u, v, {"weight": d})
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, d in nbrs.items()
     |      ... ]
     |      >>> DG.update(edges=e, nodes=adj)
     |
     |      >>> # predecessor adjacency (dict-of-set)
     |      >>> pred = {1: {2, 3}, 2: {3}, 3: {3}}
     |      >>> e = [(v, u) for u, nbrs in pred.items() for v in nbrs]
     |
     |      >>> # MultiGraph dict-of-dict-of-dict-of-attribute
     |      >>> MDG = nx.MultiDiGraph()
     |      >>> adj = {
     |      ...     1: {2: {0: {"weight": 1.3}, 1: {"weight": 1.2}}},
     |      ...     3: {2: {0: {"weight": 0.7}}},
     |      ... }
     |      >>> e = [
     |      ...     (u, v, ekey, d)
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, keydict in nbrs.items()
     |      ...     for ekey, d in keydict.items()
     |      ... ]
     |      >>> MDG.update(edges=e)
     |
     |      See Also
     |      --------
     |      add_edges_from: add multiple edges to a graph
     |      add_nodes_from: add multiple nodes to a graph
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors defined here:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  name
     |      String identifier of the graph.
     |
     |      This graph attribute appears in the attribute dict G.graph
     |      keyed by the string `"name"`. as well as an attribute (technically
     |      a property) `G.name`. This is entirely user controlled.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __networkx_backend__ = 'networkx'
     |
     |  adjlist_inner_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  adjlist_outer_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  edge_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  graph_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  node_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  node_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)

DATA
    __all__ = ['Graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\classes\graph.py

networkx.graph6
Python Library Documentation: module networkx.readwrite.graph6 in networkx.readwrite

NAME
    networkx.readwrite.graph6 - Functions for reading and writing graphs in the *graph6* format.

DESCRIPTION
    The *graph6* file format is suitable for small graphs or large dense
    graphs. For large sparse graphs, use the *sparse6* format.

    For more information, see the `graph6`_ homepage.

    .. _graph6: http://users.cecs.anu.edu.au/~bdm/data/formats.html

FUNCTIONS
    from_graph6_bytes(bytes_in, *, backend=None, **backend_kwargs)
        Read a simple undirected graph in graph6 format from bytes.

        Parameters
        ----------
        bytes_in : bytes
           Data in graph6 format, without a trailing newline.

        Returns
        -------
        G : Graph

        Raises
        ------
        NetworkXError
            If bytes_in is unable to be parsed in graph6 format

        ValueError
            If any character ``c`` in bytes_in does not satisfy
            ``63 <= ord(c) < 127``.

        Examples
        --------
        >>> G = nx.from_graph6_bytes(b"A_")
        >>> sorted(G.edges())
        [(0, 1)]

        See Also
        --------
        read_graph6, write_graph6

        References
        ----------
        .. [1] Graph6 specification
               <http://users.cecs.anu.edu.au/~bdm/data/formats.html>

    read_graph6(path, *, backend=None, **backend_kwargs)
        Read simple undirected graphs in graph6 format from path.

        Parameters
        ----------
        path : file or string
           File or filename to write.

        Returns
        -------
        G : Graph or list of Graphs
           If the file contains multiple lines then a list of graphs is returned

        Raises
        ------
        NetworkXError
            If the string is unable to be parsed in graph6 format

        Examples
        --------
        You can read a graph6 file by giving the path to the file::

            >>> import tempfile
            >>> with tempfile.NamedTemporaryFile(delete=False) as f:
            ...     _ = f.write(b">>graph6<<A_\n")
            ...     _ = f.seek(0)
            ...     G = nx.read_graph6(f.name)
            >>> list(G.edges())
            [(0, 1)]

        You can also read a graph6 file by giving an open file-like object::

            >>> import tempfile
            >>> with tempfile.NamedTemporaryFile() as f:
            ...     _ = f.write(b">>graph6<<A_\n")
            ...     _ = f.seek(0)
            ...     G = nx.read_graph6(f)
            >>> list(G.edges())
            [(0, 1)]

        See Also
        --------
        from_graph6_bytes, write_graph6

        References
        ----------
        .. [1] Graph6 specification
               <http://users.cecs.anu.edu.au/~bdm/data/formats.html>

    to_graph6_bytes(G, nodes=None, header=True)
        Convert a simple undirected graph to bytes in graph6 format.

        Parameters
        ----------
        G : Graph (undirected)

        nodes: list or iterable
           Nodes are labeled 0...n-1 in the order provided.  If None the ordering
           given by ``G.nodes()`` is used.

        header: bool
           If True add '>>graph6<<' bytes to head of data.

        Raises
        ------
        NetworkXNotImplemented
            If the graph is directed or is a multigraph.

        ValueError
            If the graph has at least ``2 ** 36`` nodes; the graph6 format
            is only defined for graphs of order less than ``2 ** 36``.

        Examples
        --------
        >>> nx.to_graph6_bytes(nx.path_graph(2))
        b'>>graph6<<A_\n'

        See Also
        --------
        from_graph6_bytes, read_graph6, write_graph6_bytes

        Notes
        -----
        The returned bytes end with a newline character.

        The format does not support edge or node labels, parallel edges or
        self loops. If self loops are present they are silently ignored.

        References
        ----------
        .. [1] Graph6 specification
               <http://users.cecs.anu.edu.au/~bdm/data/formats.html>

    write_graph6(G, path, nodes=None, header=True)
        Write a simple undirected graph to a path in graph6 format.

        Parameters
        ----------
        G : Graph (undirected)

        path : str
           The path naming the file to which to write the graph.

        nodes: list or iterable
           Nodes are labeled 0...n-1 in the order provided.  If None the ordering
           given by ``G.nodes()`` is used.

        header: bool
           If True add '>>graph6<<' string to head of data

        Raises
        ------
        NetworkXNotImplemented
            If the graph is directed or is a multigraph.

        ValueError
            If the graph has at least ``2 ** 36`` nodes; the graph6 format
            is only defined for graphs of order less than ``2 ** 36``.

        Examples
        --------
        You can write a graph6 file by giving the path to a file::

            >>> import tempfile
            >>> with tempfile.NamedTemporaryFile(delete=False) as f:
            ...     nx.write_graph6(nx.path_graph(2), f.name)
            ...     _ = f.seek(0)
            ...     print(f.read())
            b'>>graph6<<A_\n'

        See Also
        --------
        from_graph6_bytes, read_graph6

        Notes
        -----
        The function writes a newline character after writing the encoding
        of the graph.

        The format does not support edge or node labels, parallel edges or
        self loops.  If self loops are present they are silently ignored.

        References
        ----------
        .. [1] Graph6 specification
               <http://users.cecs.anu.edu.au/~bdm/data/formats.html>

DATA
    __all__ = ['from_graph6_bytes', 'read_graph6', 'to_graph6_bytes', 'wri...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\graph6.py

networkx.graph_atlas
Python Library Documentation: function graph_atlas in module networkx.generators.atlas

graph_atlas(i, *, backend=None, **backend_kwargs)
    Returns graph number `i` from the Graph Atlas.

    For more information, see :func:`.graph_atlas_g`.

    Parameters
    ----------
    i : int
        The index of the graph from the atlas to get. The graph at index
        0 is assumed to be the null graph.

    Returns
    -------
    list
        A list of :class:`~networkx.Graph` objects, the one at index *i*
        corresponding to the graph *i* in the Graph Atlas.

    See also
    --------
    graph_atlas_g

    Notes
    -----
    The time required by this function increases linearly with the
    argument `i`, since it reads a large file sequentially in order to
    generate the graph [1]_.

    References
    ----------
    .. [1] Ronald C. Read and Robin J. Wilson, *An Atlas of Graphs*.
           Oxford University Press, 1998.
networkx.graph_atlas_g
Python Library Documentation: function graph_atlas_g in module networkx.generators.atlas

graph_atlas_g(*, backend=None, **backend_kwargs)
    Returns the list of all graphs with up to seven nodes named in the
    Graph Atlas.

    The graphs are listed in increasing order by

    1. number of nodes,
    2. number of edges,
    3. degree sequence (for example 111223 < 112222),
    4. number of automorphisms,

    in that order, with three exceptions as described in the *Notes*
    section below. This causes the list to correspond with the index of
    the graphs in the Graph Atlas [atlas]_, with the first graph,
    ``G[0]``, being the null graph.

    Returns
    -------
    list
        A list of :class:`~networkx.Graph` objects, the one at index *i*
        corresponding to the graph *i* in the Graph Atlas.

    See also
    --------
    graph_atlas

    Notes
    -----
    This function may be expensive in both time and space, since it
    reads a large file sequentially in order to populate the list.

    Although the NetworkX atlas functions match the order of graphs
    given in the "Atlas of Graphs" book, there are (at least) three
    errors in the ordering described in the book. The following three
    pairs of nodes violate the lexicographically nondecreasing sorted
    degree sequence rule:

    - graphs 55 and 56 with degree sequences 001111 and 000112,
    - graphs 1007 and 1008 with degree sequences 3333444 and 3333336,
    - graphs 1012 and 1213 with degree sequences 1244555 and 1244456.

    References
    ----------
    .. [atlas] Ronald C. Read and Robin J. Wilson,
               *An Atlas of Graphs*.
               Oxford University Press, 1998.
networkx.graph_edit_distance
Python Library Documentation: function graph_edit_distance in module networkx.algorithms.similarity

graph_edit_distance(G1, G2, node_match=None, edge_match=None, node_subst_cost=None, node_del_cost=None, node_ins_cost=None, edge_subst_cost=None, edge_del_cost=None, edge_ins_cost=None, roots=None, upper_bound=None, timeout=None, *, backend=None, **backend_kwargs)
    Returns GED (graph edit distance) between graphs G1 and G2.

    Graph edit distance is a graph similarity measure analogous to
    Levenshtein distance for strings.  It is defined as minimum cost
    of edit path (sequence of node and edge edit operations)
    transforming graph G1 to graph isomorphic to G2.

    Parameters
    ----------
    G1, G2: graphs
        The two graphs G1 and G2 must be of the same type.

    node_match : callable
        A function that returns True if node n1 in G1 and n2 in G2
        should be considered equal during matching.

        The function will be called like

           node_match(G1.nodes[n1], G2.nodes[n2]).

        That is, the function will receive the node attribute
        dictionaries for n1 and n2 as inputs.

        Ignored if node_subst_cost is specified.  If neither
        node_match nor node_subst_cost are specified then node
        attributes are not considered.

    edge_match : callable
        A function that returns True if the edge attribute dictionaries
        for the pair of nodes (u1, v1) in G1 and (u2, v2) in G2 should
        be considered equal during matching.

        The function will be called like

           edge_match(G1[u1][v1], G2[u2][v2]).

        That is, the function will receive the edge attribute
        dictionaries of the edges under consideration.

        Ignored if edge_subst_cost is specified.  If neither
        edge_match nor edge_subst_cost are specified then edge
        attributes are not considered.

    node_subst_cost, node_del_cost, node_ins_cost : callable
        Functions that return the costs of node substitution, node
        deletion, and node insertion, respectively.

        The functions will be called like

           node_subst_cost(G1.nodes[n1], G2.nodes[n2]),
           node_del_cost(G1.nodes[n1]),
           node_ins_cost(G2.nodes[n2]).

        That is, the functions will receive the node attribute
        dictionaries as inputs.  The functions are expected to return
        positive numeric values.

        Function node_subst_cost overrides node_match if specified.
        If neither node_match nor node_subst_cost are specified then
        default node substitution cost of 0 is used (node attributes
        are not considered during matching).

        If node_del_cost is not specified then default node deletion
        cost of 1 is used.  If node_ins_cost is not specified then
        default node insertion cost of 1 is used.

    edge_subst_cost, edge_del_cost, edge_ins_cost : callable
        Functions that return the costs of edge substitution, edge
        deletion, and edge insertion, respectively.

        The functions will be called like

           edge_subst_cost(G1[u1][v1], G2[u2][v2]),
           edge_del_cost(G1[u1][v1]),
           edge_ins_cost(G2[u2][v2]).

        That is, the functions will receive the edge attribute
        dictionaries as inputs.  The functions are expected to return
        positive numeric values.

        Function edge_subst_cost overrides edge_match if specified.
        If neither edge_match nor edge_subst_cost are specified then
        default edge substitution cost of 0 is used (edge attributes
        are not considered during matching).

        If edge_del_cost is not specified then default edge deletion
        cost of 1 is used.  If edge_ins_cost is not specified then
        default edge insertion cost of 1 is used.

    roots : 2-tuple
        Tuple where first element is a node in G1 and the second
        is a node in G2.
        These nodes are forced to be matched in the comparison to
        allow comparison between rooted graphs.

    upper_bound : numeric
        Maximum edit distance to consider.  Return None if no edit
        distance under or equal to upper_bound exists.

    timeout : numeric
        Maximum number of seconds to execute.
        After timeout is met, the current best GED is returned.

    Examples
    --------
    >>> G1 = nx.cycle_graph(6)
    >>> G2 = nx.wheel_graph(7)
    >>> nx.graph_edit_distance(G1, G2)
    7.0

    >>> G1 = nx.star_graph(5)
    >>> G2 = nx.star_graph(5)
    >>> nx.graph_edit_distance(G1, G2, roots=(0, 0))
    0.0
    >>> nx.graph_edit_distance(G1, G2, roots=(1, 0))
    8.0

    See Also
    --------
    optimal_edit_paths, optimize_graph_edit_distance,

    is_isomorphic: test for graph edit distance of 0

    References
    ----------
    .. [1] Zeina Abu-Aisheh, Romain Raveaux, Jean-Yves Ramel, Patrick
       Martineau. An Exact Graph Edit Distance Algorithm for Solving
       Pattern Recognition Problems. 4th International Conference on
       Pattern Recognition Applications and Methods 2015, Jan 2015,
       Lisbon, Portugal. 2015,
       <10.5220/0005209202710278>. <hal-01168816>
       https://hal.archives-ouvertes.fr/hal-01168816
networkx.graph_hashing
Python Library Documentation: module networkx.algorithms.graph_hashing in networkx.algorithms

NAME
    networkx.algorithms.graph_hashing

DESCRIPTION
    Functions for hashing graphs to strings.
    Isomorphic graphs should be assigned identical hashes.
    For now, only Weisfeiler-Lehman hashing is implemented.

FUNCTIONS
    weisfeiler_lehman_graph_hash(G, edge_attr=None, node_attr=None, iterations=3, digest_size=16, *, backend=None, **backend_kwargs)
        Return Weisfeiler Lehman (WL) graph hash.

        The function iteratively aggregates and hashes neighborhoods of each node.
        After each node's neighbors are hashed to obtain updated node labels,
        a hashed histogram of resulting labels is returned as the final hash.

        Hashes are identical for isomorphic graphs and strong guarantees that
        non-isomorphic graphs will get different hashes. See [1]_ for details.

        If no node or edge attributes are provided, the degree of each node
        is used as its initial label.
        Otherwise, node and/or edge labels are used to compute the hash.

        Parameters
        ----------
        G : graph
            The graph to be hashed.
            Can have node and/or edge attributes. Can also have no attributes.
        edge_attr : string, optional (default=None)
            The key in edge attribute dictionary to be used for hashing.
            If None, edge labels are ignored.
        node_attr: string, optional (default=None)
            The key in node attribute dictionary to be used for hashing.
            If None, and no edge_attr given, use the degrees of the nodes as labels.
        iterations: int, optional (default=3)
            Number of neighbor aggregations to perform.
            Should be larger for larger graphs.
        digest_size: int, optional (default=16)
            Size (in bits) of blake2b hash digest to use for hashing node labels.

        Returns
        -------
        h : string
            Hexadecimal string corresponding to hash of the input graph.

        Examples
        --------
        Two graphs with edge attributes that are isomorphic, except for
        differences in the edge labels.

        >>> G1 = nx.Graph()
        >>> G1.add_edges_from(
        ...     [
        ...         (1, 2, {"label": "A"}),
        ...         (2, 3, {"label": "A"}),
        ...         (3, 1, {"label": "A"}),
        ...         (1, 4, {"label": "B"}),
        ...     ]
        ... )
        >>> G2 = nx.Graph()
        >>> G2.add_edges_from(
        ...     [
        ...         (5, 6, {"label": "B"}),
        ...         (6, 7, {"label": "A"}),
        ...         (7, 5, {"label": "A"}),
        ...         (7, 8, {"label": "A"}),
        ...     ]
        ... )

        Omitting the `edge_attr` option, results in identical hashes.

        >>> nx.weisfeiler_lehman_graph_hash(G1)
        '7bc4dde9a09d0b94c5097b219891d81a'
        >>> nx.weisfeiler_lehman_graph_hash(G2)
        '7bc4dde9a09d0b94c5097b219891d81a'

        With edge labels, the graphs are no longer assigned
        the same hash digest.

        >>> nx.weisfeiler_lehman_graph_hash(G1, edge_attr="label")
        'c653d85538bcf041d88c011f4f905f10'
        >>> nx.weisfeiler_lehman_graph_hash(G2, edge_attr="label")
        '3dcd84af1ca855d0eff3c978d88e7ec7'

        Notes
        -----
        To return the WL hashes of each subgraph of a graph, use
        `weisfeiler_lehman_subgraph_hashes`

        Similarity between hashes does not imply similarity between graphs.

        References
        ----------
        .. [1] Shervashidze, Nino, Pascal Schweitzer, Erik Jan Van Leeuwen,
           Kurt Mehlhorn, and Karsten M. Borgwardt. Weisfeiler Lehman
           Graph Kernels. Journal of Machine Learning Research. 2011.
           http://www.jmlr.org/papers/volume12/shervashidze11a/shervashidze11a.pdf

        See also
        --------
        weisfeiler_lehman_subgraph_hashes

    weisfeiler_lehman_subgraph_hashes(G, edge_attr=None, node_attr=None, iterations=3, digest_size=16, include_initial_labels=False, *, backend=None, **backend_kwargs)
        Return a dictionary of subgraph hashes by node.

        Dictionary keys are nodes in `G`, and values are a list of hashes.
        Each hash corresponds to a subgraph rooted at a given node u in `G`.
        Lists of subgraph hashes are sorted in increasing order of depth from
        their root node, with the hash at index i corresponding to a subgraph
        of nodes at most i edges distance from u. Thus, each list will contain
        `iterations` elements - a hash for a subgraph at each depth. If
        `include_initial_labels` is set to `True`, each list will additionally
        have contain a hash of the initial node label (or equivalently a
        subgraph of depth 0) prepended, totalling ``iterations + 1`` elements.

        The function iteratively aggregates and hashes neighborhoods of each node.
        This is achieved for each step by replacing for each node its label from
        the previous iteration with its hashed 1-hop neighborhood aggregate.
        The new node label is then appended to a list of node labels for each
        node.

        To aggregate neighborhoods for a node $u$ at each step, all labels of
        nodes adjacent to $u$ are concatenated. If the `edge_attr` parameter is set,
        labels for each neighboring node are prefixed with the value of this attribute
        along the connecting edge from this neighbor to node $u$. The resulting string
        is then hashed to compress this information into a fixed digest size.

        Thus, at the $i$-th iteration, nodes within $i$ hops influence any given
        hashed node label. We can therefore say that at depth $i$ for node $u$
        we have a hash for a subgraph induced by the $i$-hop neighborhood of $u$.

        The output can be used to create general Weisfeiler-Lehman graph kernels,
        or generate features for graphs or nodes - for example to generate 'words' in
        a graph as seen in the 'graph2vec' algorithm.
        See [1]_ & [2]_ respectively for details.

        Hashes are identical for isomorphic subgraphs and there exist strong
        guarantees that non-isomorphic graphs will get different hashes.
        See [1]_ for details.

        If no node or edge attributes are provided, the degree of each node
        is used as its initial label.
        Otherwise, node and/or edge labels are used to compute the hash.

        Parameters
        ----------
        G : graph
            The graph to be hashed.
            Can have node and/or edge attributes. Can also have no attributes.
        edge_attr : string, optional (default=None)
            The key in edge attribute dictionary to be used for hashing.
            If None, edge labels are ignored.
        node_attr : string, optional (default=None)
            The key in node attribute dictionary to be used for hashing.
            If None, and no edge_attr given, use the degrees of the nodes as labels.
            If None, and edge_attr is given, each node starts with an identical label.
        iterations : int, optional (default=3)
            Number of neighbor aggregations to perform.
            Should be larger for larger graphs.
        digest_size : int, optional (default=16)
            Size (in bits) of blake2b hash digest to use for hashing node labels.
            The default size is 16 bits.
        include_initial_labels : bool, optional (default=False)
            If True, include the hashed initial node label as the first subgraph
            hash for each node.

        Returns
        -------
        node_subgraph_hashes : dict
            A dictionary with each key given by a node in G, and each value given
            by the subgraph hashes in order of depth from the key node.

        Examples
        --------
        Finding similar nodes in different graphs:

        >>> G1 = nx.Graph()
        >>> G1.add_edges_from([(1, 2), (2, 3), (2, 4), (3, 5), (4, 6), (5, 7), (6, 7)])
        >>> G2 = nx.Graph()
        >>> G2.add_edges_from([(1, 3), (2, 3), (1, 6), (1, 5), (4, 6)])
        >>> g1_hashes = nx.weisfeiler_lehman_subgraph_hashes(
        ...     G1, iterations=3, digest_size=8
        ... )
        >>> g2_hashes = nx.weisfeiler_lehman_subgraph_hashes(
        ...     G2, iterations=3, digest_size=8
        ... )

        Even though G1 and G2 are not isomorphic (they have different numbers of edges),
        the hash sequence of depth 3 for node 1 in G1 and node 5 in G2 are similar:

        >>> g1_hashes[1]
        ['a93b64973cfc8897', 'db1b43ae35a1878f', '57872a7d2059c1c0']
        >>> g2_hashes[5]
        ['a93b64973cfc8897', 'db1b43ae35a1878f', '1716d2a4012fa4bc']

        The first 2 WL subgraph hashes match. From this we can conclude that it's very
        likely the neighborhood of 2 hops around these nodes are isomorphic.

        However the 3-hop neighborhoods of ``G1`` and ``G2`` are not isomorphic since the
        3rd hashes in the lists above are not equal.

        These nodes may be candidates to be classified together since their local topology
        is similar.

        Notes
        -----
        To hash the full graph when subgraph hashes are not needed, use
        `weisfeiler_lehman_graph_hash` for efficiency.

        Similarity between hashes does not imply similarity between graphs.

        References
        ----------
        .. [1] Shervashidze, Nino, Pascal Schweitzer, Erik Jan Van Leeuwen,
           Kurt Mehlhorn, and Karsten M. Borgwardt. Weisfeiler Lehman
           Graph Kernels. Journal of Machine Learning Research. 2011.
           http://www.jmlr.org/papers/volume12/shervashidze11a/shervashidze11a.pdf
        .. [2] Annamalai Narayanan, Mahinthan Chandramohan, Rajasekar Venkatesan,
           Lihui Chen, Yang Liu and Shantanu Jaiswa. graph2vec: Learning
           Distributed Representations of Graphs. arXiv. 2017
           https://arxiv.org/pdf/1707.05005.pdf

        See also
        --------
        weisfeiler_lehman_graph_hash

DATA
    __all__ = ['weisfeiler_lehman_graph_hash', 'weisfeiler_lehman_subgraph...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\graph_hashing.py

networkx.graphical
Python Library Documentation: module networkx.algorithms.graphical in networkx.algorithms

NAME
    networkx.algorithms.graphical - Test sequences for graphiness.

FUNCTIONS
    is_digraphical(in_sequence, out_sequence, *, backend=None, **backend_kwargs)
        Returns True if some directed graph can realize the in- and out-degree
        sequences.

        Parameters
        ----------
        in_sequence : list or iterable container
            A sequence of integer node in-degrees

        out_sequence : list or iterable container
            A sequence of integer node out-degrees

        Returns
        -------
        valid : bool
          True if in and out-sequences are digraphic False if not.

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (1, 3), (2, 3), (3, 4), (4, 2), (5, 1), (5, 4)])
        >>> in_seq = (d for n, d in G.in_degree())
        >>> out_seq = (d for n, d in G.out_degree())
        >>> nx.is_digraphical(in_seq, out_seq)
        True

        To test a non-digraphical scenario:
        >>> in_seq_list = [d for n, d in G.in_degree()]
        >>> in_seq_list[-1] += 1
        >>> nx.is_digraphical(in_seq_list, out_seq)
        False

        Notes
        -----
        This algorithm is from Kleitman and Wang [1]_.
        The worst case runtime is $O(s \times \log n)$ where $s$ and $n$ are the
        sum and length of the sequences respectively.

        References
        ----------
        .. [1] D.J. Kleitman and D.L. Wang
           Algorithms for Constructing Graphs and Digraphs with Given Valences
           and Factors, Discrete Mathematics, 6(1), pp. 79-88 (1973)

    is_graphical(sequence, method='eg', *, backend=None, **backend_kwargs)
        Returns True if sequence is a valid degree sequence.

        A degree sequence is valid if some graph can realize it.

        Parameters
        ----------
        sequence : list or iterable container
            A sequence of integer node degrees

        method : "eg" | "hh"  (default: 'eg')
            The method used to validate the degree sequence.
            "eg" corresponds to the Erdős-Gallai algorithm
            [EG1960]_, [choudum1986]_, and
            "hh" to the Havel-Hakimi algorithm
            [havel1955]_, [hakimi1962]_, [CL1996]_.

        Returns
        -------
        valid : bool
            True if the sequence is a valid degree sequence and False if not.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> sequence = (d for n, d in G.degree())
        >>> nx.is_graphical(sequence)
        True

        To test a non-graphical sequence:
        >>> sequence_list = [d for n, d in G.degree()]
        >>> sequence_list[-1] += 1
        >>> nx.is_graphical(sequence_list)
        False

        References
        ----------
        .. [EG1960] Erdős and Gallai, Mat. Lapok 11 264, 1960.
        .. [choudum1986] S.A. Choudum. "A simple proof of the Erdős-Gallai theorem on
           graph sequences." Bulletin of the Australian Mathematical Society, 33,
           pp 67-70, 1986. https://doi.org/10.1017/S0004972700002872
        .. [havel1955] Havel, V. "A Remark on the Existence of Finite Graphs"
           Casopis Pest. Mat. 80, 477-480, 1955.
        .. [hakimi1962] Hakimi, S. "On the Realizability of a Set of Integers as
           Degrees of the Vertices of a Graph." SIAM J. Appl. Math. 10, 496-506, 1962.
        .. [CL1996] G. Chartrand and L. Lesniak, "Graphs and Digraphs",
           Chapman and Hall/CRC, 1996.

    is_multigraphical(sequence, *, backend=None, **backend_kwargs)
        Returns True if some multigraph can realize the sequence.

        Parameters
        ----------
        sequence : list
            A list of integers

        Returns
        -------
        valid : bool
            True if deg_sequence is a multigraphic degree sequence and False if not.

        Examples
        --------
        >>> G = nx.MultiGraph([(1, 2), (1, 3), (2, 3), (3, 4), (4, 2), (5, 1), (5, 4)])
        >>> sequence = (d for _, d in G.degree())
        >>> nx.is_multigraphical(sequence)
        True

        To test a non-multigraphical sequence:
        >>> sequence_list = [d for _, d in G.degree()]
        >>> sequence_list[-1] += 1
        >>> nx.is_multigraphical(sequence_list)
        False

        Notes
        -----
        The worst-case run time is $O(n)$ where $n$ is the length of the sequence.

        References
        ----------
        .. [1] S. L. Hakimi. "On the realizability of a set of integers as
           degrees of the vertices of a linear graph", J. SIAM, 10, pp. 496-506
           (1962).

    is_pseudographical(sequence, *, backend=None, **backend_kwargs)
        Returns True if some pseudograph can realize the sequence.

        Every nonnegative integer sequence with an even sum is pseudographical
        (see [1]_).

        Parameters
        ----------
        sequence : list or iterable container
            A sequence of integer node degrees

        Returns
        -------
        valid : bool
          True if the sequence is a pseudographic degree sequence and False if not.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (3, 4), (4, 2), (5, 1), (5, 4)])
        >>> sequence = (d for _, d in G.degree())
        >>> nx.is_pseudographical(sequence)
        True

        To test a non-pseudographical sequence:
        >>> sequence_list = [d for _, d in G.degree()]
        >>> sequence_list[-1] += 1
        >>> nx.is_pseudographical(sequence_list)
        False

        Notes
        -----
        The worst-case run time is $O(n)$ where n is the length of the sequence.

        References
        ----------
        .. [1] F. Boesch and F. Harary. "Line removal algorithms for graphs
           and their degree lists", IEEE Trans. Circuits and Systems, CAS-23(12),
           pp. 778-782 (1976).

    is_valid_degree_sequence_erdos_gallai(deg_sequence, *, backend=None, **backend_kwargs)
        Returns True if deg_sequence can be realized by a simple graph.

        The validation is done using the Erdős-Gallai theorem [EG1960]_.

        Parameters
        ----------
        deg_sequence : list
            A list of integers

        Returns
        -------
        valid : bool
            True if deg_sequence is graphical and False if not.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (3, 4), (4, 2), (5, 1), (5, 4)])
        >>> sequence = (d for _, d in G.degree())
        >>> nx.is_valid_degree_sequence_erdos_gallai(sequence)
        True

        To test a non-valid sequence:
        >>> sequence_list = [d for _, d in G.degree()]
        >>> sequence_list[-1] += 1
        >>> nx.is_valid_degree_sequence_erdos_gallai(sequence_list)
        False

        Notes
        -----

        This implementation uses an equivalent form of the Erdős-Gallai criterion.
        Worst-case run time is $O(n)$ where $n$ is the length of the sequence.

        Specifically, a sequence d is graphical if and only if the
        sum of the sequence is even and for all strong indices k in the sequence,

         .. math::

           \sum_{i=1}^{k} d_i \leq k(k-1) + \sum_{j=k+1}^{n} \min(d_i,k)
                 = k(n-1) - ( k \sum_{j=0}^{k-1} n_j - \sum_{j=0}^{k-1} j n_j )

        A strong index k is any index where d_k >= k and the value n_j is the
        number of occurrences of j in d.  The maximal strong index is called the
        Durfee index.

        This particular rearrangement comes from the proof of Theorem 3 in [2]_.

        The ZZ condition says that for the sequence d if

        .. math::
            |d| >= \frac{(\max(d) + \min(d) + 1)^2}{4*\min(d)}

        then d is graphical.  This was shown in Theorem 6 in [2]_.

        References
        ----------
        .. [1] A. Tripathi and S. Vijay. "A note on a theorem of Erdős & Gallai",
           Discrete Mathematics, 265, pp. 417-420 (2003).
        .. [2] I.E. Zverovich and V.E. Zverovich. "Contributions to the theory
           of graphic sequences", Discrete Mathematics, 105, pp. 292-303 (1992).
        .. [EG1960] Erdős and Gallai, Mat. Lapok 11 264, 1960.

    is_valid_degree_sequence_havel_hakimi(deg_sequence, *, backend=None, **backend_kwargs)
        Returns True if deg_sequence can be realized by a simple graph.

        The validation proceeds using the Havel-Hakimi theorem
        [havel1955]_, [hakimi1962]_, [CL1996]_.
        Worst-case run time is $O(s)$ where $s$ is the sum of the sequence.

        Parameters
        ----------
        deg_sequence : list
            A list of integers where each element specifies the degree of a node
            in a graph.

        Returns
        -------
        valid : bool
            True if deg_sequence is graphical and False if not.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (3, 4), (4, 2), (5, 1), (5, 4)])
        >>> sequence = (d for _, d in G.degree())
        >>> nx.is_valid_degree_sequence_havel_hakimi(sequence)
        True

        To test a non-valid sequence:
        >>> sequence_list = [d for _, d in G.degree()]
        >>> sequence_list[-1] += 1
        >>> nx.is_valid_degree_sequence_havel_hakimi(sequence_list)
        False

        Notes
        -----
        The ZZ condition says that for the sequence d if

        .. math::
            |d| >= \frac{(\max(d) + \min(d) + 1)^2}{4*\min(d)}

        then d is graphical.  This was shown in Theorem 6 in [1]_.

        References
        ----------
        .. [1] I.E. Zverovich and V.E. Zverovich. "Contributions to the theory
           of graphic sequences", Discrete Mathematics, 105, pp. 292-303 (1992).
        .. [havel1955] Havel, V. "A Remark on the Existence of Finite Graphs"
           Casopis Pest. Mat. 80, 477-480, 1955.
        .. [hakimi1962] Hakimi, S. "On the Realizability of a Set of Integers as
           Degrees of the Vertices of a Graph." SIAM J. Appl. Math. 10, 496-506, 1962.
        .. [CL1996] G. Chartrand and L. Lesniak, "Graphs and Digraphs",
           Chapman and Hall/CRC, 1996.

DATA
    __all__ = ['is_graphical', 'is_multigraphical', 'is_pseudographical', ...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\graphical.py

networkx.graphmatrix
Python Library Documentation: module networkx.linalg.graphmatrix in networkx.linalg

NAME
    networkx.linalg.graphmatrix - Adjacency matrix and incidence matrix of graphs.

FUNCTIONS
    adjacency_matrix(G, nodelist=None, dtype=None, weight='weight', *, backend=None, **backend_kwargs)
        Returns adjacency matrix of `G`.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        nodelist : list, optional
           The rows and columns are ordered according to the nodes in `nodelist`.
           If ``nodelist=None`` (the default), then the ordering is produced by
           ``G.nodes()``.

        dtype : NumPy data-type, optional
            The desired data-type for the array.
            If `None`, then the NumPy default is used.

        weight : string or None, optional (default='weight')
           The edge data key used to provide each value in the matrix.
           If None, then each edge has weight 1.

        Returns
        -------
        A : SciPy sparse array
          Adjacency matrix representation of G.

        Notes
        -----
        For directed graphs, entry ``i, j`` corresponds to an edge from ``i`` to ``j``.

        If you want a pure Python adjacency matrix representation try
        :func:`~networkx.convert.to_dict_of_dicts` which will return a
        dictionary-of-dictionaries format that can be addressed as a
        sparse matrix.

        For multigraphs with parallel edges the weights are summed.
        See :func:`networkx.convert_matrix.to_numpy_array` for other options.

        The convention used for self-loop edges in graphs is to assign the
        diagonal matrix entry value to the edge weight attribute
        (or the number 1 if the edge has no weight attribute).  If the
        alternate convention of doubling the edge weight is desired the
        resulting SciPy sparse array can be modified as follows::

            >>> G = nx.Graph([(1, 1)])
            >>> A = nx.adjacency_matrix(G)
            >>> A.toarray()
            array([[1]])
            >>> A.setdiag(A.diagonal() * 2)
            >>> A.toarray()
            array([[2]])

        See Also
        --------
        to_numpy_array
        to_scipy_sparse_array
        to_dict_of_dicts
        adjacency_spectrum

    incidence_matrix(G, nodelist=None, edgelist=None, oriented=False, weight=None, *, dtype=None, backend=None, **backend_kwargs)
        Returns incidence matrix of G.

        The incidence matrix assigns each row to a node and each column to an edge.
        For a standard incidence matrix a 1 appears wherever a row's node is
        incident on the column's edge.  For an oriented incidence matrix each
        edge is assigned an orientation (arbitrarily for undirected and aligning to
        direction for directed).  A -1 appears for the source (tail) of an edge and
        1 for the destination (head) of the edge.  The elements are zero otherwise.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        nodelist : list, optional   (default= all nodes in G)
           The rows are ordered according to the nodes in nodelist.
           If nodelist is None, then the ordering is produced by G.nodes().

        edgelist : list, optional (default= all edges in G)
           The columns are ordered according to the edges in edgelist.
           If edgelist is None, then the ordering is produced by G.edges().

        oriented: bool, optional (default=False)
           If True, matrix elements are +1 or -1 for the head or tail node
           respectively of each edge.  If False, +1 occurs at both nodes.

        weight : string or None, optional (default=None)
           The edge data key used to provide each value in the matrix.
           If None, then each edge has weight 1.  Edge weights, if used,
           should be positive so that the orientation can provide the sign.

        dtype : a NumPy dtype or None (default=None)
            The dtype of the output sparse array. This type should be a compatible
            type of the weight argument, eg. if weight would return a float this
            argument should also be a float.
            If None, then the default for SciPy is used.

        Returns
        -------
        A : SciPy sparse array
          The incidence matrix of G.

        Notes
        -----
        For MultiGraph/MultiDiGraph, the edges in edgelist should be
        (u,v,key) 3-tuples.

        "Networks are the best discrete model for so many problems in
        applied mathematics" [1]_.

        References
        ----------
        .. [1] Gil Strang, Network applications: A = incidence matrix,
           http://videolectures.net/mit18085f07_strang_lec03/

DATA
    __all__ = ['incidence_matrix', 'adjacency_matrix']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\linalg\graphmatrix.py

networkx.graphml
Python Library Documentation: module networkx.readwrite.graphml in networkx.readwrite

NAME
    networkx.readwrite.graphml

DESCRIPTION
    *******
    GraphML
    *******
    Read and write graphs in GraphML format.

    .. warning::

        This parser uses the standard xml library present in Python, which is
        insecure - see :external+python:mod:`xml` for additional information.
        Only parse GraphML files you trust.

    This implementation does not support mixed graphs (directed and unidirected
    edges together), hyperedges, nested graphs, or ports.

    "GraphML is a comprehensive and easy-to-use file format for graphs. It
    consists of a language core to describe the structural properties of a
    graph and a flexible extension mechanism to add application-specific
    data. Its main features include support of

        * directed, undirected, and mixed graphs,
        * hypergraphs,
        * hierarchical graphs,
        * graphical representations,
        * references to external data,
        * application-specific attribute data, and
        * light-weight parsers.

    Unlike many other file formats for graphs, GraphML does not use a
    custom syntax. Instead, it is based on XML and hence ideally suited as
    a common denominator for all kinds of services generating, archiving,
    or processing graphs."

    http://graphml.graphdrawing.org/

    Format
    ------
    GraphML is an XML format.  See
    http://graphml.graphdrawing.org/specification.html for the specification and
    http://graphml.graphdrawing.org/primer/graphml-primer.html
    for examples.

CLASSES
    GraphML(builtins.object)
        GraphMLReader
        GraphMLWriter

    class GraphMLReader(GraphML)
     |  GraphMLReader(node_type=<class 'str'>, edge_key_type=<class 'int'>, force_multigraph=False)
     |
     |  Read a GraphML document.  Produces NetworkX graph objects.
     |
     |  Method resolution order:
     |      GraphMLReader
     |      GraphML
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __call__(self, path=None, string=None)
     |      Call self as a function.
     |
     |  __init__(self, node_type=<class 'str'>, edge_key_type=<class 'int'>, force_multigraph=False)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  add_edge(self, G, edge_element, graphml_keys)
     |      Add an edge to the graph.
     |
     |  add_node(self, G, node_xml, graphml_keys, defaults)
     |      Add a node to the graph.
     |
     |  decode_data_elements(self, graphml_keys, obj_xml)
     |      Use the key information to decode the data XML if present.
     |
     |  find_graphml_keys(self, graph_element)
     |      Extracts all the keys and key defaults from the xml.
     |
     |  make_graph(self, graph_xml, graphml_keys, defaults, G=None)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from GraphML:
     |
     |  construct_types(self)
     |
     |  get_xml_type(self, key)
     |      Wrapper around the xml_type dict that raises a more informative
     |      exception message when a user attempts to use data of a type not
     |      supported by GraphML.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from GraphML:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from GraphML:
     |
     |  NS_GRAPHML = 'http://graphml.graphdrawing.org/xmlns'
     |
     |  NS_XSI = 'http://www.w3.org/2001/XMLSchema-instance'
     |
     |  NS_Y = 'http://www.yworks.com/xml/graphml'
     |
     |  SCHEMALOCATION = 'http://graphml.graphdrawing.org/xmlns http://graphml...
     |
     |  convert_bool = {'true': True, 'false': False, '0': False, 0: False, '1...

    class GraphMLWriter(GraphML)
     |  GraphMLWriter(graph=None, encoding='utf-8', prettyprint=True, infer_numeric_types=False, named_key_ids=False, edge_id_from_attribute=None)
     |
     |  Method resolution order:
     |      GraphMLWriter
     |      GraphML
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __init__(self, graph=None, encoding='utf-8', prettyprint=True, infer_numeric_types=False, named_key_ids=False, edge_id_from_attribute=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  add_attributes(self, scope, xml_obj, data, default)
     |      Appends attribute data to edges or nodes, and stores type information
     |      to be added later. See add_graph_element.
     |
     |  add_data(self, name, element_type, value, scope='all', default=None)
     |      Make a data element for an edge or a node. Keep a log of the
     |      type in the keys table.
     |
     |  add_edges(self, G, graph_element)
     |
     |  add_graph_element(self, G)
     |      Serialize graph G in GraphML to the stream.
     |
     |  add_graphs(self, graph_list)
     |      Add many graphs to this GraphML document.
     |
     |  add_nodes(self, G, graph_element)
     |
     |  attr_type(self, name, scope, value)
     |      Infer the attribute type of data named name. Currently this only
     |      supports inference of numeric types.
     |
     |      If self.infer_numeric_types is false, type is used. Otherwise, pick the
     |      most general of types found across all values with name and scope. This
     |      means edges with data named 'weight' are treated separately from nodes
     |      with data named 'weight'.
     |
     |  dump(self, stream)
     |
     |  get_key(self, name, attr_type, scope, default)
     |
     |  indent(self, elem, level=0)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from GraphML:
     |
     |  construct_types(self)
     |
     |  get_xml_type(self, key)
     |      Wrapper around the xml_type dict that raises a more informative
     |      exception message when a user attempts to use data of a type not
     |      supported by GraphML.
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from GraphML:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from GraphML:
     |
     |  NS_GRAPHML = 'http://graphml.graphdrawing.org/xmlns'
     |
     |  NS_XSI = 'http://www.w3.org/2001/XMLSchema-instance'
     |
     |  NS_Y = 'http://www.yworks.com/xml/graphml'
     |
     |  SCHEMALOCATION = 'http://graphml.graphdrawing.org/xmlns http://graphml...
     |
     |  convert_bool = {'true': True, 'false': False, '0': False, 0: False, '1...

FUNCTIONS
    generate_graphml(G, encoding='utf-8', prettyprint=True, named_key_ids=False, edge_id_from_attribute=None)
        Generate GraphML lines for G

        Parameters
        ----------
        G : graph
           A networkx graph
        encoding : string (optional)
           Encoding for text data.
        prettyprint : bool (optional)
           If True use line breaks and indenting in output XML.
        named_key_ids : bool (optional)
           If True use attr.name as value for key elements' id attribute.
        edge_id_from_attribute : dict key (optional)
            If provided, the graphml edge id is set by looking up the corresponding
            edge data attribute keyed by this parameter. If `None` or the key does not exist in edge data,
            the edge id is set by the edge key if `G` is a MultiGraph, else the edge id is left unset.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> linefeed = chr(10)  # linefeed =

        >>> s = linefeed.join(nx.generate_graphml(G))
        >>> for line in nx.generate_graphml(G):  # doctest: +SKIP
        ...     print(line)

        Notes
        -----
        This implementation does not support mixed graphs (directed and unidirected
        edges together) hyperedges, nested graphs, or ports.

    parse_graphml(graphml_string, node_type=<class 'str'>, edge_key_type=<class 'int'>, force_multigraph=False, *, backend=None, **backend_kwargs)
        Read graph in GraphML format from string.

        Parameters
        ----------
        graphml_string : string
           String containing graphml information
           (e.g., contents of a graphml file).

        node_type: Python type (default: str)
           Convert node ids to this type

        edge_key_type: Python type (default: int)
           Convert graphml edge ids to this type. Multigraphs use id as edge key.
           Non-multigraphs add to edge attribute dict with name "id".

        force_multigraph : bool (default: False)
           If True, return a multigraph with edge keys. If False (the default)
           return a multigraph when multiedges are in the graph.


        Returns
        -------
        graph: NetworkX graph
            If no parallel edges are found a Graph or DiGraph is returned.
            Otherwise a MultiGraph or MultiDiGraph is returned.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> linefeed = chr(10)  # linefeed =

        >>> s = linefeed.join(nx.generate_graphml(G))
        >>> H = nx.parse_graphml(s)

        Notes
        -----
        Default node and edge attributes are not propagated to each node and edge.
        They can be obtained from `G.graph` and applied to node and edge attributes
        if desired using something like this:

        >>> default_color = G.graph["node_default"]["color"]  # doctest: +SKIP
        >>> for node, data in G.nodes(data=True):  # doctest: +SKIP
        ...     if "color" not in data:
        ...         data["color"] = default_color
        >>> default_color = G.graph["edge_default"]["color"]  # doctest: +SKIP
        >>> for u, v, data in G.edges(data=True):  # doctest: +SKIP
        ...     if "color" not in data:
        ...         data["color"] = default_color

        This implementation does not support mixed graphs (directed and unidirected
        edges together), hypergraphs, nested graphs, or ports.

        For multigraphs the GraphML edge "id" will be used as the edge
        key.  If not specified then they "key" attribute will be used.  If
        there is no "key" attribute a default NetworkX multigraph edge key
        will be provided.

    read_graphml(path, node_type=<class 'str'>, edge_key_type=<class 'int'>, force_multigraph=False, *, backend=None, **backend_kwargs)
        Read graph in GraphML format from path.

        Parameters
        ----------
        path : file or string
           File or filename to write.
           Filenames ending in .gz or .bz2 will be compressed.

        node_type: Python type (default: str)
           Convert node ids to this type

        edge_key_type: Python type (default: int)
           Convert graphml edge ids to this type. Multigraphs use id as edge key.
           Non-multigraphs add to edge attribute dict with name "id".

        force_multigraph : bool (default: False)
           If True, return a multigraph with edge keys. If False (the default)
           return a multigraph when multiedges are in the graph.

        Returns
        -------
        graph: NetworkX graph
            If parallel edges are present or `force_multigraph=True` then
            a MultiGraph or MultiDiGraph is returned. Otherwise a Graph/DiGraph.
            The returned graph is directed if the file indicates it should be.

        Notes
        -----
        Default node and edge attributes are not propagated to each node and edge.
        They can be obtained from `G.graph` and applied to node and edge attributes
        if desired using something like this:

        >>> default_color = G.graph["node_default"]["color"]  # doctest: +SKIP
        >>> for node, data in G.nodes(data=True):  # doctest: +SKIP
        ...     if "color" not in data:
        ...         data["color"] = default_color
        >>> default_color = G.graph["edge_default"]["color"]  # doctest: +SKIP
        >>> for u, v, data in G.edges(data=True):  # doctest: +SKIP
        ...     if "color" not in data:
        ...         data["color"] = default_color

        This implementation does not support mixed graphs (directed and unidirected
        edges together), hypergraphs, nested graphs, or ports.

        For multigraphs the GraphML edge "id" will be used as the edge
        key.  If not specified then they "key" attribute will be used.  If
        there is no "key" attribute a default NetworkX multigraph edge key
        will be provided.

        Files with the yEd "yfiles" extension can be read. The type of the node's
        shape is preserved in the `shape_type` node attribute.

        yEd compressed files ("file.graphmlz" extension) can be read by renaming
        the file to "file.graphml.gz".

    write_graphml = write_graphml_lxml(G, path, encoding='utf-8', prettyprint=True, infer_numeric_types=False, named_key_ids=False, edge_id_from_attribute=None)
        Write G in GraphML XML format to path

        This function uses the LXML framework and should be faster than
        the version using the xml library.

        Parameters
        ----------
        G : graph
           A networkx graph
        path : file or string
           File or filename to write.
           Filenames ending in .gz or .bz2 will be compressed.
        encoding : string (optional)
           Encoding for text data.
        prettyprint : bool (optional)
           If True use line breaks and indenting in output XML.
        infer_numeric_types : boolean
           Determine if numeric types should be generalized.
           For example, if edges have both int and float 'weight' attributes,
           we infer in GraphML that both are floats.
        named_key_ids : bool (optional)
           If True use attr.name as value for key elements' id attribute.
        edge_id_from_attribute : dict key (optional)
            If provided, the graphml edge id is set by looking up the corresponding
            edge data attribute keyed by this parameter. If `None` or the key does not exist in edge data,
            the edge id is set by the edge key if `G` is a MultiGraph, else the edge id is left unset.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_graphml_lxml(G, "fourpath.graphml")

        Notes
        -----
        This implementation does not support mixed graphs (directed
        and unidirected edges together) hyperedges, nested graphs, or ports.

    write_graphml_lxml(G, path, encoding='utf-8', prettyprint=True, infer_numeric_types=False, named_key_ids=False, edge_id_from_attribute=None)
        Write G in GraphML XML format to path

        This function uses the LXML framework and should be faster than
        the version using the xml library.

        Parameters
        ----------
        G : graph
           A networkx graph
        path : file or string
           File or filename to write.
           Filenames ending in .gz or .bz2 will be compressed.
        encoding : string (optional)
           Encoding for text data.
        prettyprint : bool (optional)
           If True use line breaks and indenting in output XML.
        infer_numeric_types : boolean
           Determine if numeric types should be generalized.
           For example, if edges have both int and float 'weight' attributes,
           we infer in GraphML that both are floats.
        named_key_ids : bool (optional)
           If True use attr.name as value for key elements' id attribute.
        edge_id_from_attribute : dict key (optional)
            If provided, the graphml edge id is set by looking up the corresponding
            edge data attribute keyed by this parameter. If `None` or the key does not exist in edge data,
            the edge id is set by the edge key if `G` is a MultiGraph, else the edge id is left unset.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_graphml_lxml(G, "fourpath.graphml")

        Notes
        -----
        This implementation does not support mixed graphs (directed
        and unidirected edges together) hyperedges, nested graphs, or ports.

    write_graphml_xml(G, path, encoding='utf-8', prettyprint=True, infer_numeric_types=False, named_key_ids=False, edge_id_from_attribute=None)
        Write G in GraphML XML format to path

        Parameters
        ----------
        G : graph
           A networkx graph
        path : file or string
           File or filename to write.
           Filenames ending in .gz or .bz2 will be compressed.
        encoding : string (optional)
           Encoding for text data.
        prettyprint : bool (optional)
           If True use line breaks and indenting in output XML.
        infer_numeric_types : boolean
           Determine if numeric types should be generalized.
           For example, if edges have both int and float 'weight' attributes,
           we infer in GraphML that both are floats.
        named_key_ids : bool (optional)
           If True use attr.name as value for key elements' id attribute.
        edge_id_from_attribute : dict key (optional)
            If provided, the graphml edge id is set by looking up the corresponding
            edge data attribute keyed by this parameter. If `None` or the key does not exist in edge data,
            the edge id is set by the edge key if `G` is a MultiGraph, else the edge id is left unset.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_graphml(G, "test.graphml")

        Notes
        -----
        This implementation does not support mixed graphs (directed
        and unidirected edges together) hyperedges, nested graphs, or ports.

DATA
    __all__ = ['write_graphml', 'read_graphml', 'generate_graphml', 'write...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\graphml.py

networkx.graphviews
Python Library Documentation: module networkx.classes.graphviews in networkx.classes

NAME
    networkx.classes.graphviews - View of Graphs as SubGraph, Reverse, Directed, Undirected.

DESCRIPTION
    In some algorithms it is convenient to temporarily morph
    a graph to exclude some nodes or edges. It should be better
    to do that via a view than to remove and then re-add.
    In other algorithms it is convenient to temporarily morph
    a graph to reverse directed edges, or treat a directed graph
    as undirected, etc. This module provides those graph views.

    The resulting views are essentially read-only graphs that
    report data from the original graph object. We provide an
    attribute G._graph which points to the underlying graph object.

    Note: Since graphviews look like graphs, one can end up with
    view-of-view-of-view chains. Be careful with chains because
    they become very slow with about 15 nested views.
    For the common simple case of node induced subgraphs created
    from the graph class, we short-cut the chain by returning a
    subgraph of the original graph directly rather than a subgraph
    of a subgraph. We are careful not to disrupt any edge filter in
    the middle subgraph. In general, determining how to short-cut
    the chain is tricky and much harder with restricted_views than
    with induced subgraphs.
    Often it is easiest to use .copy() to avoid chains.

FUNCTIONS
    generic_graph_view(G, create_using=None)
        Returns a read-only view of `G`.

        The graph `G` and its attributes are not copied but viewed through the new graph object
        of the same class as `G` (or of the class specified in `create_using`).

        Parameters
        ----------
        G : graph
            A directed/undirected graph/multigraph.

        create_using : NetworkX graph constructor, optional (default=None)
           Graph type to create. If graph instance, then cleared before populated.
           If `None`, then the appropriate Graph type is inferred from `G`.

        Returns
        -------
        newG : graph
            A view of the input graph `G` and its attributes as viewed through
            the `create_using` class.

        Raises
        ------
        NetworkXError
            If `G` is a multigraph (or multidigraph) but `create_using` is not, or vice versa.

        Notes
        -----
        The returned graph view is read-only (cannot modify the graph).
        Yet the view reflects any changes in `G`. The intent is to mimic dict views.

        Examples
        --------
        >>> G = nx.Graph()
        >>> G.add_edge(1, 2, weight=0.3)
        >>> G.add_edge(2, 3, weight=0.5)
        >>> G.edges(data=True)
        EdgeDataView([(1, 2, {'weight': 0.3}), (2, 3, {'weight': 0.5})])

        The view exposes the attributes from the original graph.

        >>> viewG = nx.graphviews.generic_graph_view(G)
        >>> viewG.edges(data=True)
        EdgeDataView([(1, 2, {'weight': 0.3}), (2, 3, {'weight': 0.5})])

        Changes to `G` are reflected in `viewG`.

        >>> G.remove_edge(2, 3)
        >>> G.edges(data=True)
        EdgeDataView([(1, 2, {'weight': 0.3})])

        >>> viewG.edges(data=True)
        EdgeDataView([(1, 2, {'weight': 0.3})])

        We can change the graph type with the `create_using` parameter.

        >>> type(G)
        <class 'networkx.classes.graph.Graph'>
        >>> viewDG = nx.graphviews.generic_graph_view(G, create_using=nx.DiGraph)
        >>> type(viewDG)
        <class 'networkx.classes.digraph.DiGraph'>

    reverse_view(G)
        View of `G` with edge directions reversed

        `reverse_view` returns a read-only view of the input graph where
        edge directions are reversed.

        Identical to digraph.reverse(copy=False)

        Parameters
        ----------
        G : networkx.DiGraph

        Returns
        -------
        graph : networkx.DiGraph

        Examples
        --------
        >>> G = nx.DiGraph()
        >>> G.add_edge(1, 2)
        >>> G.add_edge(2, 3)
        >>> G.edges()
        OutEdgeView([(1, 2), (2, 3)])

        >>> view = nx.reverse_view(G)
        >>> view.edges()
        OutEdgeView([(2, 1), (3, 2)])

    subgraph_view(G, *, filter_node=<function no_filter at 0x0000029EB2F0AFC0>, filter_edge=<function no_filter at 0x0000029EB2F0AFC0>)
        View of `G` applying a filter on nodes and edges.

        `subgraph_view` provides a read-only view of the input graph that excludes
        nodes and edges based on the outcome of two filter functions `filter_node`
        and `filter_edge`.

        The `filter_node` function takes one argument --- the node --- and returns
        `True` if the node should be included in the subgraph, and `False` if it
        should not be included.

        The `filter_edge` function takes two (or three arguments if `G` is a
        multi-graph) --- the nodes describing an edge, plus the edge-key if
        parallel edges are possible --- and returns `True` if the edge should be
        included in the subgraph, and `False` if it should not be included.

        Both node and edge filter functions are called on graph elements as they
        are queried, meaning there is no up-front cost to creating the view.

        Parameters
        ----------
        G : networkx.Graph
            A directed/undirected graph/multigraph

        filter_node : callable, optional
            A function taking a node as input, which returns `True` if the node
            should appear in the view.

        filter_edge : callable, optional
            A function taking as input the two nodes describing an edge (plus the
            edge-key if `G` is a multi-graph), which returns `True` if the edge
            should appear in the view.

        Returns
        -------
        graph : networkx.Graph
            A read-only graph view of the input graph.

        Examples
        --------
        >>> G = nx.path_graph(6)

        Filter functions operate on the node, and return `True` if the node should
        appear in the view:

        >>> def filter_node(n1):
        ...     return n1 != 5
        >>> view = nx.subgraph_view(G, filter_node=filter_node)
        >>> view.nodes()
        NodeView((0, 1, 2, 3, 4))

        We can use a closure pattern to filter graph elements based on additional
        data --- for example, filtering on edge data attached to the graph:

        >>> G[3][4]["cross_me"] = False
        >>> def filter_edge(n1, n2):
        ...     return G[n1][n2].get("cross_me", True)
        >>> view = nx.subgraph_view(G, filter_edge=filter_edge)
        >>> view.edges()
        EdgeView([(0, 1), (1, 2), (2, 3), (4, 5)])

        >>> view = nx.subgraph_view(
        ...     G,
        ...     filter_node=filter_node,
        ...     filter_edge=filter_edge,
        ... )
        >>> view.nodes()
        NodeView((0, 1, 2, 3, 4))
        >>> view.edges()
        EdgeView([(0, 1), (1, 2), (2, 3)])

DATA
    __all__ = ['generic_graph_view', 'subgraph_view', 'reverse_view']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\classes\graphviews.py

networkx.greedy_color
Python Library Documentation: function greedy_color in module networkx.algorithms.coloring.greedy_coloring

greedy_color(G, strategy='largest_first', interchange=False, *, backend=None, **backend_kwargs)
    Color a graph using various strategies of greedy graph coloring.

    Attempts to color a graph using as few colors as possible, where no
    neighbors of a node can have same color as the node itself. The
    given strategy determines the order in which nodes are colored.

    The strategies are described in [1]_, and smallest-last is based on
    [2]_.

    Parameters
    ----------
    G : NetworkX graph

    strategy : string or function(G, colors)
       A function (or a string representing a function) that provides
       the coloring strategy, by returning nodes in the ordering they
       should be colored. ``G`` is the graph, and ``colors`` is a
       dictionary of the currently assigned colors, keyed by nodes. The
       function must return an iterable over all the nodes in ``G``.

       If the strategy function is an iterator generator (that is, a
       function with ``yield`` statements), keep in mind that the
       ``colors`` dictionary will be updated after each ``yield``, since
       this function chooses colors greedily.

       If ``strategy`` is a string, it must be one of the following,
       each of which represents one of the built-in strategy functions.

       * ``'largest_first'``
       * ``'random_sequential'``
       * ``'smallest_last'``
       * ``'independent_set'``
       * ``'connected_sequential_bfs'``
       * ``'connected_sequential_dfs'``
       * ``'connected_sequential'`` (alias for the previous strategy)
       * ``'saturation_largest_first'``
       * ``'DSATUR'`` (alias for the previous strategy)

    interchange: bool
       Will use the color interchange algorithm described by [3]_ if set
       to ``True``.

       Note that ``saturation_largest_first`` and ``independent_set``
       do not work with interchange. Furthermore, if you use
       interchange with your own strategy function, you cannot rely
       on the values in the ``colors`` argument.

    Returns
    -------
    A dictionary with keys representing nodes and values representing
    corresponding coloring.

    Examples
    --------
    >>> G = nx.cycle_graph(4)
    >>> d = nx.coloring.greedy_color(G, strategy="largest_first")
    >>> d in [{0: 0, 1: 1, 2: 0, 3: 1}, {0: 1, 1: 0, 2: 1, 3: 0}]
    True

    Raises
    ------
    NetworkXPointlessConcept
        If ``strategy`` is ``saturation_largest_first`` or
        ``independent_set`` and ``interchange`` is ``True``.

    References
    ----------
    .. [1] Adrian Kosowski, and Krzysztof Manuszewski,
       Classical Coloring of Graphs, Graph Colorings, 2-19, 2004.
       ISBN 0-8218-3458-4.
    .. [2] David W. Matula, and Leland L. Beck, "Smallest-last
       ordering and clustering and graph coloring algorithms." *J. ACM* 30,
       3 (July 1983), 417–427. <https://doi.org/10.1145/2402.322385>
    .. [3] Maciej M. Sysło, Narsingh Deo, Janusz S. Kowalik,
       Discrete Optimization Algorithms with Pascal Programs, 415-424, 1983.
       ISBN 0-486-45353-7.
networkx.grid_2d_graph
Python Library Documentation: function grid_2d_graph in module networkx.generators.lattice

grid_2d_graph(m, n, periodic=False, create_using=None, *, backend=None, **backend_kwargs)
    Returns the two-dimensional grid graph.

    The grid graph has each node connected to its four nearest neighbors.

    Parameters
    ----------
    m, n : int or iterable container of nodes
        If an integer, nodes are from `range(n)`.
        If a container, elements become the coordinate of the nodes.

    periodic : bool or iterable
        If `periodic` is True, both dimensions are periodic. If False, none
        are periodic.  If `periodic` is iterable, it should yield 2 bool
        values indicating whether the 1st and 2nd axes, respectively, are
        periodic.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    NetworkX graph
        The (possibly periodic) grid graph of the specified dimensions.
networkx.grid_graph
Python Library Documentation: function grid_graph in module networkx.generators.lattice

grid_graph(dim, periodic=False, *, backend=None, **backend_kwargs)
    Returns the *n*-dimensional grid graph.

    The dimension *n* is the length of the list `dim` and the size in
    each dimension is the value of the corresponding list element.

    Parameters
    ----------
    dim : list or tuple of numbers or iterables of nodes
        'dim' is a tuple or list with, for each dimension, either a number
        that is the size of that dimension or an iterable of nodes for
        that dimension. The dimension of the grid_graph is the length
        of `dim`.

    periodic : bool or iterable
        If `periodic` is True, all dimensions are periodic. If False all
        dimensions are not periodic. If `periodic` is iterable, it should
        yield `dim` bool values each of which indicates whether the
        corresponding axis is periodic.

    Returns
    -------
    NetworkX graph
        The (possibly periodic) grid graph of the specified dimensions.

    Examples
    --------
    To produce a 2 by 3 by 4 grid graph, a graph on 24 nodes:

    >>> from networkx import grid_graph
    >>> G = grid_graph(dim=(2, 3, 4))
    >>> len(G)
    24
    >>> G = grid_graph(dim=(range(7, 9), range(3, 6)))
    >>> len(G)
    6
networkx.group
Python Library Documentation: module networkx.algorithms.centrality.group in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.group - Group centrality measures.

FUNCTIONS
    group_betweenness_centrality(G, C, normalized=True, weight=None, endpoints=False, *, backend=None, **backend_kwargs)
        Compute the group betweenness centrality for a group of nodes.

        Group betweenness centrality of a group of nodes $C$ is the sum of the
        fraction of all-pairs shortest paths that pass through any vertex in $C$

        .. math::

           c_B(v) =\sum_{s,t \in V} \frac{\sigma(s, t|v)}{\sigma(s, t)}

        where $V$ is the set of nodes, $\sigma(s, t)$ is the number of
        shortest $(s, t)$-paths, and $\sigma(s, t|C)$ is the number of
        those paths passing through some node in group $C$. Note that
        $(s, t)$ are not members of the group ($V-C$ is the set of nodes
        in $V$ that are not in $C$).

        Parameters
        ----------
        G : graph
          A NetworkX graph.

        C : list or set or list of lists or list of sets
          A group or a list of groups containing nodes which belong to G, for which group betweenness
          centrality is to be calculated.

        normalized : bool, optional (default=True)
          If True, group betweenness is normalized by `1/((|V|-|C|)(|V|-|C|-1))`
          where `|V|` is the number of nodes in G and `|C|` is the number of nodes in C.

        weight : None or string, optional (default=None)
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.
          The weight of an edge is treated as the length or distance between the two sides.

        endpoints : bool, optional (default=False)
          If True include the endpoints in the shortest path counts.

        Raises
        ------
        NodeNotFound
           If node(s) in C are not present in G.

        Returns
        -------
        betweenness : list of floats or float
           If C is a single group then return a float. If C is a list with
           several groups then return a list of group betweenness centralities.

        See Also
        --------
        betweenness_centrality

        Notes
        -----
        Group betweenness centrality is described in [1]_ and its importance discussed in [3]_.
        The initial implementation of the algorithm is mentioned in [2]_. This function uses
        an improved algorithm presented in [4]_.

        The number of nodes in the group must be a maximum of n - 2 where `n`
        is the total number of nodes in the graph.

        For weighted graphs the edge weights must be greater than zero.
        Zero edge weights can produce an infinite number of equal length
        paths between pairs of nodes.

        The total number of paths between source and target is counted
        differently for directed and undirected graphs. Directed paths
        between "u" and "v" are counted as two possible paths (one each
        direction) while undirected paths between "u" and "v" are counted
        as one path. Said another way, the sum in the expression above is
        over all ``s != t`` for directed graphs and for ``s < t`` for undirected graphs.


        References
        ----------
        .. [1] M G Everett and S P Borgatti:
           The Centrality of Groups and Classes.
           Journal of Mathematical Sociology. 23(3): 181-201. 1999.
           http://www.analytictech.com/borgatti/group_centrality.htm
        .. [2] Ulrik Brandes:
           On Variants of Shortest-Path Betweenness
           Centrality and their Generic Computation.
           Social Networks 30(2):136-145, 2008.
           http://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.72.9610&rep=rep1&type=pdf
        .. [3] Sourav Medya et. al.:
           Group Centrality Maximization via Network Design.
           SIAM International Conference on Data Mining, SDM 2018, 126–134.
           https://sites.cs.ucsb.edu/~arlei/pubs/sdm18.pdf
        .. [4] Rami Puzis, Yuval Elovici, and Shlomi Dolev.
           "Fast algorithm for successive computation of group betweenness centrality."
           https://journals.aps.org/pre/pdf/10.1103/PhysRevE.76.056709

    group_closeness_centrality(G, S, weight=None, *, backend=None, **backend_kwargs)
        Compute the group closeness centrality for a group of nodes.

        Group closeness centrality of a group of nodes $S$ is a measure
        of how close the group is to the other nodes in the graph.

        .. math::

           c_{close}(S) = \frac{|V-S|}{\sum_{v \in V-S} d_{S, v}}

           d_{S, v} = min_{u \in S} (d_{u, v})

        where $V$ is the set of nodes, $d_{S, v}$ is the distance of
        the group $S$ from $v$ defined as above. ($V-S$ is the set of nodes
        in $V$ that are not in $S$).

        Parameters
        ----------
        G : graph
           A NetworkX graph.

        S : list or set
           S is a group of nodes which belong to G, for which group closeness
           centrality is to be calculated.

        weight : None or string, optional (default=None)
           If None, all edge weights are considered equal.
           Otherwise holds the name of the edge attribute used as weight.
           The weight of an edge is treated as the length or distance between the two sides.

        Raises
        ------
        NodeNotFound
           If node(s) in S are not present in G.

        Returns
        -------
        closeness : float
           Group closeness centrality of the group S.

        See Also
        --------
        closeness_centrality

        Notes
        -----
        The measure was introduced in [1]_.
        The formula implemented here is described in [2]_.

        Higher values of closeness indicate greater centrality.

        It is assumed that 1 / 0 is 0 (required in the case of directed graphs,
        or when a shortest path length is 0).

        The number of nodes in the group must be a maximum of n - 1 where `n`
        is the total number of nodes in the graph.

        For directed graphs, the incoming distance is utilized here. To use the
        outward distance, act on `G.reverse()`.

        For weighted graphs the edge weights must be greater than zero.
        Zero edge weights can produce an infinite number of equal length
        paths between pairs of nodes.

        References
        ----------
        .. [1] M G Everett and S P Borgatti:
           The Centrality of Groups and Classes.
           Journal of Mathematical Sociology. 23(3): 181-201. 1999.
           http://www.analytictech.com/borgatti/group_centrality.htm
        .. [2] J. Zhao et. al.:
           Measuring and Maximizing Group Closeness Centrality over
           Disk Resident Graphs.
           WWWConference Proceedings, 2014. 689-694.
           https://doi.org/10.1145/2567948.2579356

    group_degree_centrality(G, S, *, backend=None, **backend_kwargs)
        Compute the group degree centrality for a group of nodes.

        Group degree centrality of a group of nodes $S$ is the fraction
        of non-group members connected to group members.

        Parameters
        ----------
        G : graph
           A NetworkX graph.

        S : list or set
           S is a group of nodes which belong to G, for which group degree
           centrality is to be calculated.

        Raises
        ------
        NetworkXError
           If node(s) in S are not in G.

        Returns
        -------
        centrality : float
           Group degree centrality of the group S.

        See Also
        --------
        degree_centrality
        group_in_degree_centrality
        group_out_degree_centrality

        Notes
        -----
        The measure was introduced in [1]_.

        The number of nodes in the group must be a maximum of n - 1 where `n`
        is the total number of nodes in the graph.

        References
        ----------
        .. [1] M G Everett and S P Borgatti:
           The Centrality of Groups and Classes.
           Journal of Mathematical Sociology. 23(3): 181-201. 1999.
           http://www.analytictech.com/borgatti/group_centrality.htm

    group_in_degree_centrality(G, S, *, backend=None, **backend_kwargs)
        Compute the group in-degree centrality for a group of nodes.

        Group in-degree centrality of a group of nodes $S$ is the fraction
        of non-group members connected to group members by incoming edges.

        Parameters
        ----------
        G : graph
           A NetworkX graph.

        S : list or set
           S is a group of nodes which belong to G, for which group in-degree
           centrality is to be calculated.

        Returns
        -------
        centrality : float
           Group in-degree centrality of the group S.

        Raises
        ------
        NetworkXNotImplemented
           If G is undirected.

        NodeNotFound
           If node(s) in S are not in G.

        See Also
        --------
        degree_centrality
        group_degree_centrality
        group_out_degree_centrality

        Notes
        -----
        The number of nodes in the group must be a maximum of n - 1 where `n`
        is the total number of nodes in the graph.

        `G.neighbors(i)` gives nodes with an outward edge from i, in a DiGraph,
        so for group in-degree centrality, the reverse graph is used.

    group_out_degree_centrality(G, S, *, backend=None, **backend_kwargs)
        Compute the group out-degree centrality for a group of nodes.

        Group out-degree centrality of a group of nodes $S$ is the fraction
        of non-group members connected to group members by outgoing edges.

        Parameters
        ----------
        G : graph
           A NetworkX graph.

        S : list or set
           S is a group of nodes which belong to G, for which group in-degree
           centrality is to be calculated.

        Returns
        -------
        centrality : float
           Group out-degree centrality of the group S.

        Raises
        ------
        NetworkXNotImplemented
           If G is undirected.

        NodeNotFound
           If node(s) in S are not in G.

        See Also
        --------
        degree_centrality
        group_degree_centrality
        group_in_degree_centrality

        Notes
        -----
        The number of nodes in the group must be a maximum of n - 1 where `n`
        is the total number of nodes in the graph.

        `G.neighbors(i)` gives nodes with an outward edge from i, in a DiGraph,
        so for group out-degree centrality, the graph itself is used.

    prominent_group(G, k, weight=None, C=None, endpoints=False, normalized=True, greedy=False, *, backend=None, **backend_kwargs)
        Find the prominent group of size $k$ in graph $G$. The prominence of the
        group is evaluated by the group betweenness centrality.

        Group betweenness centrality of a group of nodes $C$ is the sum of the
        fraction of all-pairs shortest paths that pass through any vertex in $C$

        .. math::

           c_B(v) =\sum_{s,t \in V} \frac{\sigma(s, t|v)}{\sigma(s, t)}

        where $V$ is the set of nodes, $\sigma(s, t)$ is the number of
        shortest $(s, t)$-paths, and $\sigma(s, t|C)$ is the number of
        those paths passing through some node in group $C$. Note that
        $(s, t)$ are not members of the group ($V-C$ is the set of nodes
        in $V$ that are not in $C$).

        Parameters
        ----------
        G : graph
           A NetworkX graph.

        k : int
           The number of nodes in the group.

        normalized : bool, optional (default=True)
           If True, group betweenness is normalized by ``1/((|V|-|C|)(|V|-|C|-1))``
           where ``|V|`` is the number of nodes in G and ``|C|`` is the number of
           nodes in C.

        weight : None or string, optional (default=None)
           If None, all edge weights are considered equal.
           Otherwise holds the name of the edge attribute used as weight.
           The weight of an edge is treated as the length or distance between the two sides.

        endpoints : bool, optional (default=False)
           If True include the endpoints in the shortest path counts.

        C : list or set, optional (default=None)
           list of nodes which won't be candidates of the prominent group.

        greedy : bool, optional (default=False)
           Using a naive greedy algorithm in order to find non-optimal prominent
           group. For scale free networks the results are negligibly below the optimal
           results.

        Raises
        ------
        NodeNotFound
           If node(s) in C are not present in G.

        Returns
        -------
        max_GBC : float
           The group betweenness centrality of the prominent group.

        max_group : list
            The list of nodes in the prominent group.

        See Also
        --------
        betweenness_centrality, group_betweenness_centrality

        Notes
        -----
        Group betweenness centrality is described in [1]_ and its importance discussed in [3]_.
        The algorithm is described in [2]_ and is based on techniques mentioned in [4]_.

        The number of nodes in the group must be a maximum of ``n - 2`` where ``n``
        is the total number of nodes in the graph.

        For weighted graphs the edge weights must be greater than zero.
        Zero edge weights can produce an infinite number of equal length
        paths between pairs of nodes.

        The total number of paths between source and target is counted
        differently for directed and undirected graphs. Directed paths
        between "u" and "v" are counted as two possible paths (one each
        direction) while undirected paths between "u" and "v" are counted
        as one path. Said another way, the sum in the expression above is
        over all ``s != t`` for directed graphs and for ``s < t`` for undirected graphs.

        References
        ----------
        .. [1] M G Everett and S P Borgatti:
           The Centrality of Groups and Classes.
           Journal of Mathematical Sociology. 23(3): 181-201. 1999.
           http://www.analytictech.com/borgatti/group_centrality.htm
        .. [2] Rami Puzis, Yuval Elovici, and Shlomi Dolev:
           "Finding the Most Prominent Group in Complex Networks"
           AI communications 20(4): 287-296, 2007.
           https://www.researchgate.net/profile/Rami_Puzis2/publication/220308855
        .. [3] Sourav Medya et. al.:
           Group Centrality Maximization via Network Design.
           SIAM International Conference on Data Mining, SDM 2018, 126–134.
           https://sites.cs.ucsb.edu/~arlei/pubs/sdm18.pdf
        .. [4] Rami Puzis, Yuval Elovici, and Shlomi Dolev.
           "Fast algorithm for successive computation of group betweenness centrality."
           https://journals.aps.org/pre/pdf/10.1103/PhysRevE.76.056709

DATA
    __all__ = ['group_betweenness_centrality', 'group_closeness_centrality...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\group.py

networkx.group_betweenness_centrality
Python Library Documentation: function group_betweenness_centrality in module networkx.algorithms.centrality.group

group_betweenness_centrality(G, C, normalized=True, weight=None, endpoints=False, *, backend=None, **backend_kwargs)
    Compute the group betweenness centrality for a group of nodes.

    Group betweenness centrality of a group of nodes $C$ is the sum of the
    fraction of all-pairs shortest paths that pass through any vertex in $C$

    .. math::

       c_B(v) =\sum_{s,t \in V} \frac{\sigma(s, t|v)}{\sigma(s, t)}

    where $V$ is the set of nodes, $\sigma(s, t)$ is the number of
    shortest $(s, t)$-paths, and $\sigma(s, t|C)$ is the number of
    those paths passing through some node in group $C$. Note that
    $(s, t)$ are not members of the group ($V-C$ is the set of nodes
    in $V$ that are not in $C$).

    Parameters
    ----------
    G : graph
      A NetworkX graph.

    C : list or set or list of lists or list of sets
      A group or a list of groups containing nodes which belong to G, for which group betweenness
      centrality is to be calculated.

    normalized : bool, optional (default=True)
      If True, group betweenness is normalized by `1/((|V|-|C|)(|V|-|C|-1))`
      where `|V|` is the number of nodes in G and `|C|` is the number of nodes in C.

    weight : None or string, optional (default=None)
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.
      The weight of an edge is treated as the length or distance between the two sides.

    endpoints : bool, optional (default=False)
      If True include the endpoints in the shortest path counts.

    Raises
    ------
    NodeNotFound
       If node(s) in C are not present in G.

    Returns
    -------
    betweenness : list of floats or float
       If C is a single group then return a float. If C is a list with
       several groups then return a list of group betweenness centralities.

    See Also
    --------
    betweenness_centrality

    Notes
    -----
    Group betweenness centrality is described in [1]_ and its importance discussed in [3]_.
    The initial implementation of the algorithm is mentioned in [2]_. This function uses
    an improved algorithm presented in [4]_.

    The number of nodes in the group must be a maximum of n - 2 where `n`
    is the total number of nodes in the graph.

    For weighted graphs the edge weights must be greater than zero.
    Zero edge weights can produce an infinite number of equal length
    paths between pairs of nodes.

    The total number of paths between source and target is counted
    differently for directed and undirected graphs. Directed paths
    between "u" and "v" are counted as two possible paths (one each
    direction) while undirected paths between "u" and "v" are counted
    as one path. Said another way, the sum in the expression above is
    over all ``s != t`` for directed graphs and for ``s < t`` for undirected graphs.


    References
    ----------
    .. [1] M G Everett and S P Borgatti:
       The Centrality of Groups and Classes.
       Journal of Mathematical Sociology. 23(3): 181-201. 1999.
       http://www.analytictech.com/borgatti/group_centrality.htm
    .. [2] Ulrik Brandes:
       On Variants of Shortest-Path Betweenness
       Centrality and their Generic Computation.
       Social Networks 30(2):136-145, 2008.
       http://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.72.9610&rep=rep1&type=pdf
    .. [3] Sourav Medya et. al.:
       Group Centrality Maximization via Network Design.
       SIAM International Conference on Data Mining, SDM 2018, 126–134.
       https://sites.cs.ucsb.edu/~arlei/pubs/sdm18.pdf
    .. [4] Rami Puzis, Yuval Elovici, and Shlomi Dolev.
       "Fast algorithm for successive computation of group betweenness centrality."
       https://journals.aps.org/pre/pdf/10.1103/PhysRevE.76.056709
networkx.group_closeness_centrality
Python Library Documentation: function group_closeness_centrality in module networkx.algorithms.centrality.group

group_closeness_centrality(G, S, weight=None, *, backend=None, **backend_kwargs)
    Compute the group closeness centrality for a group of nodes.

    Group closeness centrality of a group of nodes $S$ is a measure
    of how close the group is to the other nodes in the graph.

    .. math::

       c_{close}(S) = \frac{|V-S|}{\sum_{v \in V-S} d_{S, v}}

       d_{S, v} = min_{u \in S} (d_{u, v})

    where $V$ is the set of nodes, $d_{S, v}$ is the distance of
    the group $S$ from $v$ defined as above. ($V-S$ is the set of nodes
    in $V$ that are not in $S$).

    Parameters
    ----------
    G : graph
       A NetworkX graph.

    S : list or set
       S is a group of nodes which belong to G, for which group closeness
       centrality is to be calculated.

    weight : None or string, optional (default=None)
       If None, all edge weights are considered equal.
       Otherwise holds the name of the edge attribute used as weight.
       The weight of an edge is treated as the length or distance between the two sides.

    Raises
    ------
    NodeNotFound
       If node(s) in S are not present in G.

    Returns
    -------
    closeness : float
       Group closeness centrality of the group S.

    See Also
    --------
    closeness_centrality

    Notes
    -----
    The measure was introduced in [1]_.
    The formula implemented here is described in [2]_.

    Higher values of closeness indicate greater centrality.

    It is assumed that 1 / 0 is 0 (required in the case of directed graphs,
    or when a shortest path length is 0).

    The number of nodes in the group must be a maximum of n - 1 where `n`
    is the total number of nodes in the graph.

    For directed graphs, the incoming distance is utilized here. To use the
    outward distance, act on `G.reverse()`.

    For weighted graphs the edge weights must be greater than zero.
    Zero edge weights can produce an infinite number of equal length
    paths between pairs of nodes.

    References
    ----------
    .. [1] M G Everett and S P Borgatti:
       The Centrality of Groups and Classes.
       Journal of Mathematical Sociology. 23(3): 181-201. 1999.
       http://www.analytictech.com/borgatti/group_centrality.htm
    .. [2] J. Zhao et. al.:
       Measuring and Maximizing Group Closeness Centrality over
       Disk Resident Graphs.
       WWWConference Proceedings, 2014. 689-694.
       https://doi.org/10.1145/2567948.2579356
networkx.group_degree_centrality
Python Library Documentation: function group_degree_centrality in module networkx.algorithms.centrality.group

group_degree_centrality(G, S, *, backend=None, **backend_kwargs)
    Compute the group degree centrality for a group of nodes.

    Group degree centrality of a group of nodes $S$ is the fraction
    of non-group members connected to group members.

    Parameters
    ----------
    G : graph
       A NetworkX graph.

    S : list or set
       S is a group of nodes which belong to G, for which group degree
       centrality is to be calculated.

    Raises
    ------
    NetworkXError
       If node(s) in S are not in G.

    Returns
    -------
    centrality : float
       Group degree centrality of the group S.

    See Also
    --------
    degree_centrality
    group_in_degree_centrality
    group_out_degree_centrality

    Notes
    -----
    The measure was introduced in [1]_.

    The number of nodes in the group must be a maximum of n - 1 where `n`
    is the total number of nodes in the graph.

    References
    ----------
    .. [1] M G Everett and S P Borgatti:
       The Centrality of Groups and Classes.
       Journal of Mathematical Sociology. 23(3): 181-201. 1999.
       http://www.analytictech.com/borgatti/group_centrality.htm
networkx.group_in_degree_centrality
Python Library Documentation: function group_in_degree_centrality in module networkx.algorithms.centrality.group

group_in_degree_centrality(G, S, *, backend=None, **backend_kwargs)
    Compute the group in-degree centrality for a group of nodes.

    Group in-degree centrality of a group of nodes $S$ is the fraction
    of non-group members connected to group members by incoming edges.

    Parameters
    ----------
    G : graph
       A NetworkX graph.

    S : list or set
       S is a group of nodes which belong to G, for which group in-degree
       centrality is to be calculated.

    Returns
    -------
    centrality : float
       Group in-degree centrality of the group S.

    Raises
    ------
    NetworkXNotImplemented
       If G is undirected.

    NodeNotFound
       If node(s) in S are not in G.

    See Also
    --------
    degree_centrality
    group_degree_centrality
    group_out_degree_centrality

    Notes
    -----
    The number of nodes in the group must be a maximum of n - 1 where `n`
    is the total number of nodes in the graph.

    `G.neighbors(i)` gives nodes with an outward edge from i, in a DiGraph,
    so for group in-degree centrality, the reverse graph is used.
networkx.group_out_degree_centrality
Python Library Documentation: function group_out_degree_centrality in module networkx.algorithms.centrality.group

group_out_degree_centrality(G, S, *, backend=None, **backend_kwargs)
    Compute the group out-degree centrality for a group of nodes.

    Group out-degree centrality of a group of nodes $S$ is the fraction
    of non-group members connected to group members by outgoing edges.

    Parameters
    ----------
    G : graph
       A NetworkX graph.

    S : list or set
       S is a group of nodes which belong to G, for which group in-degree
       centrality is to be calculated.

    Returns
    -------
    centrality : float
       Group out-degree centrality of the group S.

    Raises
    ------
    NetworkXNotImplemented
       If G is undirected.

    NodeNotFound
       If node(s) in S are not in G.

    See Also
    --------
    degree_centrality
    group_degree_centrality
    group_in_degree_centrality

    Notes
    -----
    The number of nodes in the group must be a maximum of n - 1 where `n`
    is the total number of nodes in the graph.

    `G.neighbors(i)` gives nodes with an outward edge from i, in a DiGraph,
    so for group out-degree centrality, the graph itself is used.
networkx.gutman_index
Python Library Documentation: function gutman_index in module networkx.algorithms.wiener

gutman_index(G, weight=None, *, backend=None, **backend_kwargs)
    Returns the Gutman Index for the graph `G`.

    The *Gutman Index* measures the topology of networks, especially for molecule
    networks of atoms connected by bonds [1]_. It is also called the Schultz Index
    of the second kind [2]_.

    Consider an undirected graph `G` with node set ``V``.
    The Gutman Index of a graph is the sum over all (unordered) pairs of nodes
    of nodes ``(u, v)``, with distance ``dist(u, v)`` and degrees ``deg(u)``
    and ``deg(v)``, of ``dist(u, v) * deg(u) * deg(v)``

    Parameters
    ----------
    G : NetworkX graph

    weight : string or None, optional (default: None)
        If None, every edge has weight 1.
        If a string, use this edge attribute as the edge weight.
        Any edge attribute not present defaults to 1.
        The edge weights are used to computing shortest-path distances.

    Returns
    -------
    number
        The Gutman Index of the graph `G`.

    Examples
    --------
    The Gutman Index of the (unweighted) complete graph on *n* nodes
    equals the number of pairs of the *n* nodes times ``(n - 1) * (n - 1)``,
    since each pair of nodes is at distance one and the product of degree of two
    vertices is ``(n - 1) * (n - 1)``.

    >>> n = 10
    >>> G = nx.complete_graph(n)
    >>> nx.gutman_index(G) == (n * (n - 1) / 2) * ((n - 1) * (n - 1))
    True

    Graphs that are disconnected

    >>> G = nx.empty_graph(2)
    >>> nx.gutman_index(G)
    inf

    References
    ----------
    .. [1] M.V. Diudeaa and I. Gutman, Wiener-Type Topological Indices,
           Croatica Chemica Acta, 71 (1998), 21-51.
           https://hrcak.srce.hr/132323
    .. [2] I. Gutman, Selected properties of the Schultz molecular topological index,
           J. Chem. Inf. Comput. Sci. 34 (1994), 1087–1089.
           https://doi.org/10.1021/ci00021a009
networkx.harary_graph
Python Library Documentation: module networkx.generators.harary_graph in networkx.generators

NAME
    networkx.generators.harary_graph - Generators for Harary graphs

DESCRIPTION
    This module gives two generators for the Harary graph, which was
    introduced by the famous mathematician Frank Harary in his 1962 work [H]_.
    The first generator gives the Harary graph that maximizes the node
    connectivity with given number of nodes and given number of edges.
    The second generator gives the Harary graph that minimizes
    the number of edges in the graph with given node connectivity and
    number of nodes.

    References
    ----------
    .. [H] Harary, F. "The Maximum Connectivity of a Graph."
           Proc. Nat. Acad. Sci. USA 48, 1142-1146, 1962.

FUNCTIONS
    hkn_harary_graph(k, n, create_using=None, *, backend=None, **backend_kwargs)
        Returns the Harary graph with given node connectivity and node number.

        The Harary graph $H_{k,n}$ is the graph that minimizes the number of
        edges needed with given node connectivity $k$ and node number $n$.

        This smallest number of edges is known to be ceil($kn/2$) [1]_.

        Parameters
        ----------
        k: integer
           The node connectivity of the generated graph

        n: integer
           The number of nodes the generated graph is to contain

        create_using : NetworkX graph constructor, optional Graph type
         to create (default=nx.Graph). If graph instance, then cleared
         before populated.

        Returns
        -------
        NetworkX graph
            The Harary graph $H_{k,n}$.

        See Also
        --------
        hnm_harary_graph

        Notes
        -----
        This algorithm runs in $O(kn)$ time.
        It is implemented by following the Reference [2]_.

        References
        ----------
        .. [1] Weisstein, Eric W. "Harary Graph." From MathWorld--A Wolfram Web
         Resource. http://mathworld.wolfram.com/HararyGraph.html.

        .. [2] Harary, F. "The Maximum Connectivity of a Graph."
          Proc. Nat. Acad. Sci. USA 48, 1142-1146, 1962.

    hnm_harary_graph(n, m, create_using=None, *, backend=None, **backend_kwargs)
        Returns the Harary graph with given numbers of nodes and edges.

        The Harary graph $H_{n,m}$ is the graph that maximizes node connectivity
        with $n$ nodes and $m$ edges.

        This maximum node connectivity is known to be floor($2m/n$). [1]_

        Parameters
        ----------
        n: integer
           The number of nodes the generated graph is to contain

        m: integer
           The number of edges the generated graph is to contain

        create_using : NetworkX graph constructor, optional Graph type
         to create (default=nx.Graph). If graph instance, then cleared
         before populated.

        Returns
        -------
        NetworkX graph
            The Harary graph $H_{n,m}$.

        See Also
        --------
        hkn_harary_graph

        Notes
        -----
        This algorithm runs in $O(m)$ time.
        It is implemented by following the Reference [2]_.

        References
        ----------
        .. [1] F. T. Boesch, A. Satyanarayana, and C. L. Suffel,
           "A Survey of Some Network Reliability Analysis and Synthesis Results,"
           Networks, pp. 99-107, 2009.

        .. [2] Harary, F. "The Maximum Connectivity of a Graph."
           Proc. Nat. Acad. Sci. USA 48, 1142-1146, 1962.

DATA
    __all__ = ['hnm_harary_graph', 'hkn_harary_graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\harary_graph.py

networkx.harmonic
Python Library Documentation: module networkx.algorithms.centrality.harmonic in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.harmonic - Functions for computing the harmonic centrality of a graph.

FUNCTIONS
    harmonic_centrality(G, nbunch=None, distance=None, sources=None, *, backend=None, **backend_kwargs)
        Compute harmonic centrality for nodes.

        Harmonic centrality [1]_ of a node `u` is the sum of the reciprocal
        of the shortest path distances from all other nodes to `u`

        .. math::

            C(u) = \sum_{v \neq u} \frac{1}{d(v, u)}

        where `d(v, u)` is the shortest-path distance between `v` and `u`.

        If `sources` is given as an argument, the returned harmonic centrality
        values are calculated as the sum of the reciprocals of the shortest
        path distances from the nodes specified in `sources` to `u` instead
        of from all nodes to `u`.

        Notice that higher values indicate higher centrality.

        Parameters
        ----------
        G : graph
          A NetworkX graph

        nbunch : container (default: all nodes in G)
          Container of nodes for which harmonic centrality values are calculated.

        sources : container (default: all nodes in G)
          Container of nodes `v` over which reciprocal distances are computed.
          Nodes not in `G` are silently ignored.

        distance : edge attribute key, optional (default=None)
          Use the specified edge attribute as the edge distance in shortest
          path calculations.  If `None`, then each edge will have distance equal to 1.

        Returns
        -------
        nodes : dictionary
          Dictionary of nodes with harmonic centrality as the value.

        See Also
        --------
        betweenness_centrality, load_centrality, eigenvector_centrality,
        degree_centrality, closeness_centrality

        Notes
        -----
        If the 'distance' keyword is set to an edge attribute key then the
        shortest-path length will be computed using Dijkstra's algorithm with
        that edge attribute as the edge weight.

        References
        ----------
        .. [1] Boldi, Paolo, and Sebastiano Vigna. "Axioms for centrality."
               Internet Mathematics 10.3-4 (2014): 222-262.

DATA
    __all__ = ['harmonic_centrality']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\harmonic.py

networkx.harmonic_centrality
Python Library Documentation: function harmonic_centrality in module networkx.algorithms.centrality.harmonic

harmonic_centrality(G, nbunch=None, distance=None, sources=None, *, backend=None, **backend_kwargs)
    Compute harmonic centrality for nodes.

    Harmonic centrality [1]_ of a node `u` is the sum of the reciprocal
    of the shortest path distances from all other nodes to `u`

    .. math::

        C(u) = \sum_{v \neq u} \frac{1}{d(v, u)}

    where `d(v, u)` is the shortest-path distance between `v` and `u`.

    If `sources` is given as an argument, the returned harmonic centrality
    values are calculated as the sum of the reciprocals of the shortest
    path distances from the nodes specified in `sources` to `u` instead
    of from all nodes to `u`.

    Notice that higher values indicate higher centrality.

    Parameters
    ----------
    G : graph
      A NetworkX graph

    nbunch : container (default: all nodes in G)
      Container of nodes for which harmonic centrality values are calculated.

    sources : container (default: all nodes in G)
      Container of nodes `v` over which reciprocal distances are computed.
      Nodes not in `G` are silently ignored.

    distance : edge attribute key, optional (default=None)
      Use the specified edge attribute as the edge distance in shortest
      path calculations.  If `None`, then each edge will have distance equal to 1.

    Returns
    -------
    nodes : dictionary
      Dictionary of nodes with harmonic centrality as the value.

    See Also
    --------
    betweenness_centrality, load_centrality, eigenvector_centrality,
    degree_centrality, closeness_centrality

    Notes
    -----
    If the 'distance' keyword is set to an edge attribute key then the
    shortest-path length will be computed using Dijkstra's algorithm with
    that edge attribute as the edge weight.

    References
    ----------
    .. [1] Boldi, Paolo, and Sebastiano Vigna. "Axioms for centrality."
           Internet Mathematics 10.3-4 (2014): 222-262.
networkx.harmonic_diameter
Python Library Documentation: function harmonic_diameter in module networkx.algorithms.distance_measures

harmonic_diameter(G, sp=None, *, backend=None, **backend_kwargs)
    Returns the harmonic diameter of the graph G.

    The harmonic diameter of a graph is the harmonic mean of the distances
    between all pairs of distinct vertices. Graphs that are not strongly
    connected have infinite diameter and mean distance, making such
    measures not useful. Restricting the diameter or mean distance to
    finite distances yields paradoxical values (e.g., a perfect match
    would have diameter one). The harmonic mean handles gracefully
    infinite distances (e.g., a perfect match has harmonic diameter equal
    to the number of vertices minus one), making it possible to assign a
    meaningful value to all graphs.

    Note that in [1] the harmonic diameter is called "connectivity length":
    however, "harmonic diameter" is a more standard name from the
    theory of metric spaces. The name "harmonic mean distance" is perhaps
    a more descriptive name, but is not used in the literature, so we use the
    name "harmonic diameter" here.

    Parameters
    ----------
    G : NetworkX graph
       A graph

    sp : dict of dicts, optional
       All-pairs shortest path lengths as a dictionary of dictionaries

    Returns
    -------
    hd : float
       Harmonic diameter of graph

    References
    ----------
    .. [1] Massimo Marchiori and Vito Latora, "Harmony in the small-world".
           *Physica A: Statistical Mechanics and Its Applications*
           285(3-4), pages 539-546, 2000.
           <https://doi.org/10.1016/S0378-4371(00)00311-3>
networkx.has_bridges
Python Library Documentation: function has_bridges in module networkx.algorithms.bridges

has_bridges(G, root=None, *, backend=None, **backend_kwargs)
    Decide whether a graph has any bridges.

    A *bridge* in a graph is an edge whose removal causes the number of
    connected components of the graph to increase.

    Parameters
    ----------
    G : undirected graph

    root : node (optional)
       A node in the graph `G`. If specified, only the bridges in the
       connected component containing this node will be considered.

    Returns
    -------
    bool
       Whether the graph (or the connected component containing `root`)
       has any bridges.

    Raises
    ------
    NodeNotFound
       If `root` is not in the graph `G`.

    NetworkXNotImplemented
        If `G` is a directed graph.

    Examples
    --------
    The barbell graph with parameter zero has a single bridge::

        >>> G = nx.barbell_graph(10, 0)
        >>> nx.has_bridges(G)
        True

    On the other hand, the cycle graph has no bridges::

        >>> G = nx.cycle_graph(5)
        >>> nx.has_bridges(G)
        False

    Notes
    -----
    This implementation uses the :func:`networkx.bridges` function, so
    it shares its worst-case time complexity, $O(m + n)$, ignoring
    polylogarithmic factors, where $n$ is the number of nodes in the
    graph and $m$ is the number of edges.
networkx.has_eulerian_path
Python Library Documentation: function has_eulerian_path in module networkx.algorithms.euler

has_eulerian_path(G, source=None, *, backend=None, **backend_kwargs)
    Return True iff `G` has an Eulerian path.

    An Eulerian path is a path in a graph which uses each edge of a graph
    exactly once. If `source` is specified, then this function checks
    whether an Eulerian path that starts at node `source` exists.

    A directed graph has an Eulerian path iff:
        - at most one vertex has out_degree - in_degree = 1,
        - at most one vertex has in_degree - out_degree = 1,
        - every other vertex has equal in_degree and out_degree,
        - and all of its vertices belong to a single connected
          component of the underlying undirected graph.

    If `source` is not None, an Eulerian path starting at `source` exists if no
    other node has out_degree - in_degree = 1. This is equivalent to either
    there exists an Eulerian circuit or `source` has out_degree - in_degree = 1
    and the conditions above hold.

    An undirected graph has an Eulerian path iff:
        - exactly zero or two vertices have odd degree,
        - and all of its vertices belong to a single connected component.

    If `source` is not None, an Eulerian path starting at `source` exists if
    either there exists an Eulerian circuit or `source` has an odd degree and the
    conditions above hold.

    Graphs with isolated vertices (i.e. vertices with zero degree) are not considered
    to have an Eulerian path. Therefore, if the graph is not connected (or not strongly
    connected, for directed graphs), this function returns False.

    Parameters
    ----------
    G : NetworkX Graph
        The graph to find an euler path in.

    source : node, optional
        Starting node for path.

    Returns
    -------
    Bool : True if G has an Eulerian path.

    Examples
    --------
    If you prefer to allow graphs with isolated vertices to have Eulerian path,
    you can first remove such vertices and then call `has_eulerian_path` as below example shows.

    >>> G = nx.Graph([(0, 1), (1, 2), (0, 2)])
    >>> G.add_node(3)
    >>> nx.has_eulerian_path(G)
    False

    >>> G.remove_nodes_from(list(nx.isolates(G)))
    >>> nx.has_eulerian_path(G)
    True

    See Also
    --------
    is_eulerian
    eulerian_path
networkx.has_path
Python Library Documentation: function has_path in module networkx.algorithms.shortest_paths.generic

has_path(G, source, target, *, backend=None, **backend_kwargs)
    Returns *True* if *G* has a path from *source* to *target*.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Starting node for path

    target : node
       Ending node for path
networkx.havel_hakimi_graph
Python Library Documentation: function havel_hakimi_graph in module networkx.generators.degree_seq

havel_hakimi_graph(deg_sequence, create_using=None, *, backend=None, **backend_kwargs)
    Returns a simple graph with given degree sequence constructed
    using the Havel-Hakimi algorithm.

    Parameters
    ----------
    deg_sequence: list of integers
        Each integer corresponds to the degree of a node (need not be sorted).
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Directed graphs are not allowed.

    Raises
    ------
    NetworkXException
        For a non-graphical degree sequence (i.e. one
        not realizable by some simple graph).

    Notes
    -----
    The Havel-Hakimi algorithm constructs a simple graph by
    successively connecting the node of highest degree to other nodes
    of highest degree, resorting remaining nodes by degree, and
    repeating the process. The resulting graph has a high
    degree-associativity.  Nodes are labeled 1,.., len(deg_sequence),
    corresponding to their position in deg_sequence.

    The basic algorithm is from Hakimi [1]_ and was generalized by
    Kleitman and Wang [2]_.

    References
    ----------
    .. [1] Hakimi S., On Realizability of a Set of Integers as
       Degrees of the Vertices of a Linear Graph. I,
       Journal of SIAM, 10(3), pp. 496-506 (1962)
    .. [2] Kleitman D.J. and Wang D.L.
       Algorithms for Constructing Graphs and Digraphs with Given Valences
       and Factors  Discrete Mathematics, 6(1), pp. 79-88 (1973)
networkx.heawood_graph
Python Library Documentation: function heawood_graph in module networkx.generators.small

heawood_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Heawood Graph, a (3,6) cage.

    The Heawood Graph is an undirected graph with 14 nodes and 21 edges,
    named after Percy John Heawood [1]_.
    It is cubic symmetric, nonplanar, Hamiltonian, and can be represented
    in LCF notation as ``[5,-5]^7`` [2]_.
    It is the unique (3,6)-cage: the regular cubic graph of girth 6 with
    minimal number of vertices [3]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Heawood Graph with 14 nodes and 21 edges

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Heawood_graph
    .. [2] https://mathworld.wolfram.com/HeawoodGraph.html
    .. [3] https://www.win.tue.nl/~aeb/graphs/Heawood.html
networkx.hexagonal_lattice_graph
Python Library Documentation: function hexagonal_lattice_graph in module networkx.generators.lattice

hexagonal_lattice_graph(m, n, periodic=False, with_positions=True, create_using=None, *, backend=None, **backend_kwargs)
    Returns an `m` by `n` hexagonal lattice graph.

    The *hexagonal lattice graph* is a graph whose nodes and edges are
    the `hexagonal tiling`_ of the plane.

    The returned graph will have `m` rows and `n` columns of hexagons.
    `Odd numbered columns`_ are shifted up relative to even numbered columns.

    Positions of nodes are computed by default or `with_positions is True`.
    Node positions creating the standard embedding in the plane
    with sidelength 1 and are stored in the node attribute 'pos'.
    `pos = nx.get_node_attributes(G, 'pos')` creates a dict ready for drawing.

    .. _hexagonal tiling: https://en.wikipedia.org/wiki/Hexagonal_tiling
    .. _Odd numbered columns: http://www-cs-students.stanford.edu/~amitp/game-programming/grids/

    Parameters
    ----------
    m : int
        The number of rows of hexagons in the lattice.

    n : int
        The number of columns of hexagons in the lattice.

    periodic : bool
        Whether to make a periodic grid by joining the boundary vertices.
        For this to work `n` must be even and both `n > 1` and `m > 1`.
        The periodic connections create another row and column of hexagons
        so these graphs have fewer nodes as boundary nodes are identified.

    with_positions : bool (default: True)
        Store the coordinates of each node in the graph node attribute 'pos'.
        The coordinates provide a lattice with vertical columns of hexagons
        offset to interleave and cover the plane.
        Periodic positions shift the nodes vertically in a nonlinear way so
        the edges don't overlap so much.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        If graph is directed, edges will point up or right.

    Returns
    -------
    NetworkX graph
        The *m* by *n* hexagonal lattice graph.
networkx.hierarchy
Python Library Documentation: module networkx.algorithms.hierarchy in networkx.algorithms

NAME
    networkx.algorithms.hierarchy - Flow Hierarchy.

FUNCTIONS
    flow_hierarchy(G, weight=None, *, backend=None, **backend_kwargs)
        Returns the flow hierarchy of a directed network.

        Flow hierarchy is defined as the fraction of edges not participating
        in cycles in a directed graph [1]_.

        Parameters
        ----------
        G : DiGraph or MultiDiGraph
           A directed graph

        weight : string, optional (default=None)
           Attribute to use for edge weights. If None the weight defaults to 1.

        Returns
        -------
        h : float
           Flow hierarchy value

        Raises
        ------
        NetworkXError
           If `G` is not a directed graph or if `G` has no edges.

        Notes
        -----
        The algorithm described in [1]_ computes the flow hierarchy through
        exponentiation of the adjacency matrix.  This function implements an
        alternative approach that finds strongly connected components.
        An edge is in a cycle if and only if it is in a strongly connected
        component, which can be found in $O(m)$ time using Tarjan's algorithm.

        References
        ----------
        .. [1] Luo, J.; Magee, C.L. (2011),
           Detecting evolving patterns of self-organizing networks by flow
           hierarchy measurement, Complexity, Volume 16 Issue 6 53-61.
           DOI: 10.1002/cplx.20368
           http://web.mit.edu/~cmagee/www/documents/28-DetectingEvolvingPatterns_FlowHierarchy.pdf

DATA
    __all__ = ['flow_hierarchy']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\hierarchy.py

networkx.hits
Python Library Documentation: function hits in module networkx.algorithms.link_analysis.hits_alg

hits(G, max_iter=100, tol=1e-08, nstart=None, normalized=True, *, backend=None, **backend_kwargs)
    Returns HITS hubs and authorities values for nodes.

    The HITS algorithm computes two numbers for a node.
    Authorities estimates the node value based on the incoming links.
    Hubs estimates the node value based on outgoing links.

    Parameters
    ----------
    G : graph
      A NetworkX graph

    max_iter : integer, optional
      Maximum number of iterations in power method.

    tol : float, optional
      Error tolerance used to check convergence in power method iteration.

    nstart : dictionary, optional
      Starting value of each node for power method iteration.

    normalized : bool (default=True)
       Normalize results by the sum of all of the values.

    Returns
    -------
    (hubs,authorities) : two-tuple of dictionaries
       Two dictionaries keyed by node containing the hub and authority
       values.

    Raises
    ------
    PowerIterationFailedConvergence
        If the algorithm fails to converge to the specified tolerance
        within the specified number of iterations of the power iteration
        method.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> h, a = nx.hits(G)

    Notes
    -----
    The eigenvector calculation is done by the power iteration method
    and has no guarantee of convergence.  The iteration will stop
    after max_iter iterations or an error tolerance of
    number_of_nodes(G)*tol has been reached.

    The HITS algorithm was designed for directed graphs but this
    algorithm does not check if the input graph is directed and will
    execute on undirected graphs.

    References
    ----------
    .. [1] A. Langville and C. Meyer,
       "A survey of eigenvector methods of web information retrieval."
       http://citeseer.ist.psu.edu/713792.html
    .. [2] Jon Kleinberg,
       Authoritative sources in a hyperlinked environment
       Journal of the ACM 46 (5): 604-32, 1999.
       doi:10.1145/324133.324140.
       http://www.cs.cornell.edu/home/kleinber/auth.pdf.
networkx.hits_alg
Python Library Documentation: module networkx.algorithms.link_analysis.hits_alg in networkx.algorithms.link_analysis

NAME
    networkx.algorithms.link_analysis.hits_alg - Hubs and authorities analysis of graph structure.

FUNCTIONS
    hits(G, max_iter=100, tol=1e-08, nstart=None, normalized=True, *, backend=None, **backend_kwargs)
        Returns HITS hubs and authorities values for nodes.

        The HITS algorithm computes two numbers for a node.
        Authorities estimates the node value based on the incoming links.
        Hubs estimates the node value based on outgoing links.

        Parameters
        ----------
        G : graph
          A NetworkX graph

        max_iter : integer, optional
          Maximum number of iterations in power method.

        tol : float, optional
          Error tolerance used to check convergence in power method iteration.

        nstart : dictionary, optional
          Starting value of each node for power method iteration.

        normalized : bool (default=True)
           Normalize results by the sum of all of the values.

        Returns
        -------
        (hubs,authorities) : two-tuple of dictionaries
           Two dictionaries keyed by node containing the hub and authority
           values.

        Raises
        ------
        PowerIterationFailedConvergence
            If the algorithm fails to converge to the specified tolerance
            within the specified number of iterations of the power iteration
            method.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> h, a = nx.hits(G)

        Notes
        -----
        The eigenvector calculation is done by the power iteration method
        and has no guarantee of convergence.  The iteration will stop
        after max_iter iterations or an error tolerance of
        number_of_nodes(G)*tol has been reached.

        The HITS algorithm was designed for directed graphs but this
        algorithm does not check if the input graph is directed and will
        execute on undirected graphs.

        References
        ----------
        .. [1] A. Langville and C. Meyer,
           "A survey of eigenvector methods of web information retrieval."
           http://citeseer.ist.psu.edu/713792.html
        .. [2] Jon Kleinberg,
           Authoritative sources in a hyperlinked environment
           Journal of the ACM 46 (5): 604-32, 1999.
           doi:10.1145/324133.324140.
           http://www.cs.cornell.edu/home/kleinber/auth.pdf.

DATA
    __all__ = ['hits']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\link_analysis\hits_alg.py

networkx.hkn_harary_graph
Python Library Documentation: function hkn_harary_graph in module networkx.generators.harary_graph

hkn_harary_graph(k, n, create_using=None, *, backend=None, **backend_kwargs)
    Returns the Harary graph with given node connectivity and node number.

    The Harary graph $H_{k,n}$ is the graph that minimizes the number of
    edges needed with given node connectivity $k$ and node number $n$.

    This smallest number of edges is known to be ceil($kn/2$) [1]_.

    Parameters
    ----------
    k: integer
       The node connectivity of the generated graph

    n: integer
       The number of nodes the generated graph is to contain

    create_using : NetworkX graph constructor, optional Graph type
     to create (default=nx.Graph). If graph instance, then cleared
     before populated.

    Returns
    -------
    NetworkX graph
        The Harary graph $H_{k,n}$.

    See Also
    --------
    hnm_harary_graph

    Notes
    -----
    This algorithm runs in $O(kn)$ time.
    It is implemented by following the Reference [2]_.

    References
    ----------
    .. [1] Weisstein, Eric W. "Harary Graph." From MathWorld--A Wolfram Web
     Resource. http://mathworld.wolfram.com/HararyGraph.html.

    .. [2] Harary, F. "The Maximum Connectivity of a Graph."
      Proc. Nat. Acad. Sci. USA 48, 1142-1146, 1962.
networkx.hnm_harary_graph
Python Library Documentation: function hnm_harary_graph in module networkx.generators.harary_graph

hnm_harary_graph(n, m, create_using=None, *, backend=None, **backend_kwargs)
    Returns the Harary graph with given numbers of nodes and edges.

    The Harary graph $H_{n,m}$ is the graph that maximizes node connectivity
    with $n$ nodes and $m$ edges.

    This maximum node connectivity is known to be floor($2m/n$). [1]_

    Parameters
    ----------
    n: integer
       The number of nodes the generated graph is to contain

    m: integer
       The number of edges the generated graph is to contain

    create_using : NetworkX graph constructor, optional Graph type
     to create (default=nx.Graph). If graph instance, then cleared
     before populated.

    Returns
    -------
    NetworkX graph
        The Harary graph $H_{n,m}$.

    See Also
    --------
    hkn_harary_graph

    Notes
    -----
    This algorithm runs in $O(m)$ time.
    It is implemented by following the Reference [2]_.

    References
    ----------
    .. [1] F. T. Boesch, A. Satyanarayana, and C. L. Suffel,
       "A Survey of Some Network Reliability Analysis and Synthesis Results,"
       Networks, pp. 99-107, 2009.

    .. [2] Harary, F. "The Maximum Connectivity of a Graph."
       Proc. Nat. Acad. Sci. USA 48, 1142-1146, 1962.
networkx.hoffman_singleton_graph
Python Library Documentation: function hoffman_singleton_graph in module networkx.generators.small

hoffman_singleton_graph(*, backend=None, **backend_kwargs)
    Returns the Hoffman-Singleton Graph.

    The Hoffman–Singleton graph is a symmetrical undirected graph
    with 50 nodes and 175 edges.
    All indices lie in ``Z % 5``: that is, the integers mod 5 [1]_.
    It is the only regular graph of vertex degree 7, diameter 2, and girth 5.
    It is the unique (7,5)-cage graph and Moore graph, and contains many
    copies of the Petersen graph [2]_.

    Returns
    -------
    G : networkx Graph
        Hoffman–Singleton Graph with 50 nodes and 175 edges

    Notes
    -----
    Constructed from pentagon and pentagram as follows: Take five pentagons $P_h$
    and five pentagrams $Q_i$ . Join vertex $j$ of $P_h$ to vertex $h·i+j$ of $Q_i$ [3]_.

    References
    ----------
    .. [1] https://blogs.ams.org/visualinsight/2016/02/01/hoffman-singleton-graph/
    .. [2] https://mathworld.wolfram.com/Hoffman-SingletonGraph.html
    .. [3] https://en.wikipedia.org/wiki/Hoffman%E2%80%93Singleton_graph
networkx.house_graph
Python Library Documentation: function house_graph in module networkx.generators.small

house_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the House graph (square with triangle on top)

    The house graph is a simple undirected graph with
    5 nodes and 6 edges [1]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        House graph in the form of a square with a triangle on top

    References
    ----------
    .. [1] https://mathworld.wolfram.com/HouseGraph.html
networkx.house_x_graph
Python Library Documentation: function house_x_graph in module networkx.generators.small

house_x_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the House graph with a cross inside the house square.

    The House X-graph is the House graph plus the two edges connecting diagonally
    opposite vertices of the square base. It is also one of the two graphs
    obtained by removing two edges from the pentatope graph [1]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        House graph with diagonal vertices connected

    References
    ----------
    .. [1] https://mathworld.wolfram.com/HouseGraph.html
networkx.hybrid
Python Library Documentation: module networkx.algorithms.hybrid in networkx.algorithms

NAME
    networkx.algorithms.hybrid

DESCRIPTION
    Provides functions for finding and testing for locally `(k, l)`-connected
    graphs.

FUNCTIONS
    is_kl_connected(G, k, l, low_memory=False, *, backend=None, **backend_kwargs)
        Returns True if and only if `G` is locally `(k, l)`-connected.

        A graph is locally `(k, l)`-connected if for each edge `(u, v)` in the
        graph there are at least `l` edge-disjoint paths of length at most `k`
        joining `u` to `v`.

        Parameters
        ----------
        G : NetworkX graph
            The graph to test for local `(k, l)`-connectedness.

        k : integer
            The maximum length of paths to consider. A higher number means a looser
            connectivity requirement.

        l : integer
            The number of edge-disjoint paths. A higher number means a stricter
            connectivity requirement.

        low_memory : bool
            If this is True, this function uses an algorithm that uses slightly
            more time but less memory.

        Returns
        -------
        bool
            Whether the graph is locally `(k, l)`-connected subgraph.

        See also
        --------
        kl_connected_subgraph

        References
        ----------
        .. [1] Chung, Fan and Linyuan Lu. "The Small World Phenomenon in Hybrid
               Power Law Graphs." *Complex Networks*. Springer Berlin Heidelberg,
               2004. 89--104.

    kl_connected_subgraph(G, k, l, low_memory=False, same_as_graph=False, *, backend=None, **backend_kwargs)
        Returns the maximum locally `(k, l)`-connected subgraph of `G`.

        A graph is locally `(k, l)`-connected if for each edge `(u, v)` in the
        graph there are at least `l` edge-disjoint paths of length at most `k`
        joining `u` to `v`.

        Parameters
        ----------
        G : NetworkX graph
            The graph in which to find a maximum locally `(k, l)`-connected
            subgraph.

        k : integer
            The maximum length of paths to consider. A higher number means a looser
            connectivity requirement.

        l : integer
            The number of edge-disjoint paths. A higher number means a stricter
            connectivity requirement.

        low_memory : bool
            If this is True, this function uses an algorithm that uses slightly
            more time but less memory.

        same_as_graph : bool
            If True then return a tuple of the form `(H, is_same)`,
            where `H` is the maximum locally `(k, l)`-connected subgraph and
            `is_same` is a Boolean representing whether `G` is locally `(k,
            l)`-connected (and hence, whether `H` is simply a copy of the input
            graph `G`).

        Returns
        -------
        NetworkX graph or two-tuple
            If `same_as_graph` is True, then this function returns a
            two-tuple as described above. Otherwise, it returns only the maximum
            locally `(k, l)`-connected subgraph.

        See also
        --------
        is_kl_connected

        References
        ----------
        .. [1] Chung, Fan and Linyuan Lu. "The Small World Phenomenon in Hybrid
               Power Law Graphs." *Complex Networks*. Springer Berlin Heidelberg,
               2004. 89--104.

DATA
    __all__ = ['kl_connected_subgraph', 'is_kl_connected']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\hybrid.py

networkx.hypercube_graph
Python Library Documentation: function hypercube_graph in module networkx.generators.lattice

hypercube_graph(n, *, backend=None, **backend_kwargs)
    Returns the *n*-dimensional hypercube graph.

    The nodes are the integers between 0 and ``2 ** n - 1``, inclusive.

    For more information on the hypercube graph, see the Wikipedia
    article `Hypercube graph`_.

    .. _Hypercube graph: https://en.wikipedia.org/wiki/Hypercube_graph

    Parameters
    ----------
    n : int
        The dimension of the hypercube.
        The number of nodes in the graph will be ``2 ** n``.

    Returns
    -------
    NetworkX graph
        The hypercube graph of dimension *n*.
networkx.icosahedral_graph
Python Library Documentation: function icosahedral_graph in module networkx.generators.small

icosahedral_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Platonic Icosahedral graph.

    The icosahedral graph has 12 nodes and 30 edges. It is a Platonic graph
    whose nodes have the connectivity of the icosahedron. It is undirected,
    regular and Hamiltonian [1]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Icosahedral graph with 12 nodes and 30 edges.

    References
    ----------
    .. [1] https://mathworld.wolfram.com/IcosahedralGraph.html
networkx.identified_nodes
Python Library Documentation: function contracted_nodes in module networkx.algorithms.minors.contraction

contracted_nodes(G, u, v, self_loops=True, copy=True, *, backend=None, **backend_kwargs)
    Returns the graph that results from contracting `u` and `v`.

    Node contraction identifies the two nodes as a single node incident to any
    edge that was incident to the original two nodes.

    Parameters
    ----------
    G : NetworkX graph
        The graph whose nodes will be contracted.

    u, v : nodes
        Must be nodes in `G`.

    self_loops : Boolean
        If this is True, any edges joining `u` and `v` in `G` become
        self-loops on the new node in the returned graph.

    copy : Boolean
        If this is True (default True), make a copy of
        `G` and return that instead of directly changing `G`.


    Returns
    -------
    Networkx graph
        If Copy is True,
        A new graph object of the same type as `G` (leaving `G` unmodified)
        with `u` and `v` identified in a single node. The right node `v`
        will be merged into the node `u`, so only `u` will appear in the
        returned graph.
        If copy is False,
        Modifies `G` with `u` and `v` identified in a single node.
        The right node `v` will be merged into the node `u`, so
        only `u` will appear in the returned graph.

    Notes
    -----
    For multigraphs, the edge keys for the realigned edges may
    not be the same as the edge keys for the old edges. This is
    natural because edge keys are unique only within each pair of nodes.

    For non-multigraphs where `u` and `v` are adjacent to a third node
    `w`, the edge (`v`, `w`) will be contracted into the edge (`u`,
    `w`) with its attributes stored into a "contraction" attribute.

    This function is also available as `identified_nodes`.

    Examples
    --------
    Contracting two nonadjacent nodes of the cycle graph on four nodes `C_4`
    yields the path graph (ignoring parallel edges):

    >>> G = nx.cycle_graph(4)
    >>> M = nx.contracted_nodes(G, 1, 3)
    >>> P3 = nx.path_graph(3)
    >>> nx.is_isomorphic(M, P3)
    True

    >>> G = nx.MultiGraph(P3)
    >>> M = nx.contracted_nodes(G, 0, 2)
    >>> M.edges
    MultiEdgeView([(0, 1, 0), (0, 1, 1)])

    >>> G = nx.Graph([(1, 2), (2, 2)])
    >>> H = nx.contracted_nodes(G, 1, 2, self_loops=False)
    >>> list(H.nodes())
    [1]
    >>> list(H.edges())
    [(1, 1)]

    In a ``MultiDiGraph`` with a self loop, the in and out edges will
    be treated separately as edges, so while contracting a node which
    has a self loop the contraction will add multiple edges:

    >>> G = nx.MultiDiGraph([(1, 2), (2, 2)])
    >>> H = nx.contracted_nodes(G, 1, 2)
    >>> list(H.edges())  # edge 1->2, 2->2, 2<-2 from the original Graph G
    [(1, 1), (1, 1), (1, 1)]
    >>> H = nx.contracted_nodes(G, 1, 2, self_loops=False)
    >>> list(H.edges())  # edge 2->2, 2<-2 from the original Graph G
    [(1, 1), (1, 1)]

    See Also
    --------
    contracted_edge
    quotient_graph
networkx.immediate_dominators
Python Library Documentation: function immediate_dominators in module networkx.algorithms.dominance

immediate_dominators(G, start, *, backend=None, **backend_kwargs)
    Returns the immediate dominators of all nodes of a directed graph.

    Parameters
    ----------
    G : a DiGraph or MultiDiGraph
        The graph where dominance is to be computed.

    start : node
        The start node of dominance computation.

    Returns
    -------
    idom : dict keyed by nodes
        A dict containing the immediate dominators of each node reachable from
        `start`.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is undirected.

    NetworkXError
        If `start` is not in `G`.

    Notes
    -----
    Except for `start`, the immediate dominators are the parents of their
    corresponding nodes in the dominator tree.

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (1, 3), (2, 5), (3, 4), (4, 5)])
    >>> sorted(nx.immediate_dominators(G, 1).items())
    [(1, 1), (2, 1), (3, 1), (4, 3), (5, 1)]

    References
    ----------
    .. [1] Cooper, Keith D., Harvey, Timothy J. and Kennedy, Ken.
           "A simple, fast dominance algorithm." (2006).
           https://hdl.handle.net/1911/96345
networkx.in_degree_centrality
Python Library Documentation: function in_degree_centrality in module networkx.algorithms.centrality.degree_alg

in_degree_centrality(G, *, backend=None, **backend_kwargs)
    Compute the in-degree centrality for nodes.

    The in-degree centrality for a node v is the fraction of nodes its
    incoming edges are connected to.

    Parameters
    ----------
    G : graph
        A NetworkX graph

    Returns
    -------
    nodes : dictionary
        Dictionary of nodes with in-degree centrality as values.

    Raises
    ------
    NetworkXNotImplemented
        If G is undirected.

    Examples
    --------
    >>> G = nx.DiGraph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
    >>> nx.in_degree_centrality(G)
    {0: 0.0, 1: 0.3333333333333333, 2: 0.6666666666666666, 3: 0.6666666666666666}

    See Also
    --------
    degree_centrality, out_degree_centrality

    Notes
    -----
    The degree centrality values are normalized by dividing by the maximum
    possible degree in a simple graph n-1 where n is the number of nodes in G.

    For multigraphs or graphs with self loops the maximum degree might
    be higher than n-1 and values of degree centrality greater than 1
    are possible.
networkx.incidence_matrix
Python Library Documentation: function incidence_matrix in module networkx.linalg.graphmatrix

incidence_matrix(G, nodelist=None, edgelist=None, oriented=False, weight=None, *, dtype=None, backend=None, **backend_kwargs)
    Returns incidence matrix of G.

    The incidence matrix assigns each row to a node and each column to an edge.
    For a standard incidence matrix a 1 appears wherever a row's node is
    incident on the column's edge.  For an oriented incidence matrix each
    edge is assigned an orientation (arbitrarily for undirected and aligning to
    direction for directed).  A -1 appears for the source (tail) of an edge and
    1 for the destination (head) of the edge.  The elements are zero otherwise.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    nodelist : list, optional   (default= all nodes in G)
       The rows are ordered according to the nodes in nodelist.
       If nodelist is None, then the ordering is produced by G.nodes().

    edgelist : list, optional (default= all edges in G)
       The columns are ordered according to the edges in edgelist.
       If edgelist is None, then the ordering is produced by G.edges().

    oriented: bool, optional (default=False)
       If True, matrix elements are +1 or -1 for the head or tail node
       respectively of each edge.  If False, +1 occurs at both nodes.

    weight : string or None, optional (default=None)
       The edge data key used to provide each value in the matrix.
       If None, then each edge has weight 1.  Edge weights, if used,
       should be positive so that the orientation can provide the sign.

    dtype : a NumPy dtype or None (default=None)
        The dtype of the output sparse array. This type should be a compatible
        type of the weight argument, eg. if weight would return a float this
        argument should also be a float.
        If None, then the default for SciPy is used.

    Returns
    -------
    A : SciPy sparse array
      The incidence matrix of G.

    Notes
    -----
    For MultiGraph/MultiDiGraph, the edges in edgelist should be
    (u,v,key) 3-tuples.

    "Networks are the best discrete model for so many problems in
    applied mathematics" [1]_.

    References
    ----------
    .. [1] Gil Strang, Network applications: A = incidence matrix,
       http://videolectures.net/mit18085f07_strang_lec03/
networkx.incremental_closeness_centrality
Python Library Documentation: function incremental_closeness_centrality in module networkx.algorithms.centrality.closeness

incremental_closeness_centrality(G, edge, prev_cc=None, insertion=True, wf_improved=True, *, backend=None, **backend_kwargs)
    Incremental closeness centrality for nodes.

    Compute closeness centrality for nodes using level-based work filtering
    as described in Incremental Algorithms for Closeness Centrality by Sariyuce et al.

    Level-based work filtering detects unnecessary updates to the closeness
    centrality and filters them out.

    ---
    From "Incremental Algorithms for Closeness Centrality":

    Theorem 1: Let :math:`G = (V, E)` be a graph and u and v be two vertices in V
    such that there is no edge (u, v) in E. Let :math:`G' = (V, E \cup uv)`
    Then :math:`cc[s] = cc'[s]` if and only if :math:`\left|dG(s, u) - dG(s, v)\right| \leq 1`.

    Where :math:`dG(u, v)` denotes the length of the shortest path between
    two vertices u, v in a graph G, cc[s] is the closeness centrality for a
    vertex s in V, and cc'[s] is the closeness centrality for a
    vertex s in V, with the (u, v) edge added.
    ---

    We use Theorem 1 to filter out updates when adding or removing an edge.
    When adding an edge (u, v), we compute the shortest path lengths from all
    other nodes to u and to v before the node is added. When removing an edge,
    we compute the shortest path lengths after the edge is removed. Then we
    apply Theorem 1 to use previously computed closeness centrality for nodes
    where :math:`\left|dG(s, u) - dG(s, v)\right| \leq 1`. This works only for
    undirected, unweighted graphs; the distance argument is not supported.

    Closeness centrality [1]_ of a node `u` is the reciprocal of the
    sum of the shortest path distances from `u` to all `n-1` other nodes.
    Since the sum of distances depends on the number of nodes in the
    graph, closeness is normalized by the sum of minimum possible
    distances `n-1`.

    .. math::

        C(u) = \frac{n - 1}{\sum_{v=1}^{n-1} d(v, u)},

    where `d(v, u)` is the shortest-path distance between `v` and `u`,
    and `n` is the number of nodes in the graph.

    Notice that higher values of closeness indicate higher centrality.

    Parameters
    ----------
    G : graph
      A NetworkX graph

    edge : tuple
      The modified edge (u, v) in the graph.

    prev_cc : dictionary
      The previous closeness centrality for all nodes in the graph.

    insertion : bool, optional
      If True (default) the edge was inserted, otherwise it was deleted from the graph.

    wf_improved : bool, optional (default=True)
      If True, scale by the fraction of nodes reachable. This gives the
      Wasserman and Faust improved formula. For single component graphs
      it is the same as the original formula.

    Returns
    -------
    nodes : dictionary
      Dictionary of nodes with closeness centrality as the value.

    See Also
    --------
    betweenness_centrality, load_centrality, eigenvector_centrality,
    degree_centrality, closeness_centrality

    Notes
    -----
    The closeness centrality is normalized to `(n-1)/(|G|-1)` where
    `n` is the number of nodes in the connected part of graph
    containing the node.  If the graph is not completely connected,
    this algorithm computes the closeness centrality for each
    connected part separately.

    References
    ----------
    .. [1] Freeman, L.C., 1979. Centrality in networks: I.
       Conceptual clarification.  Social Networks 1, 215--239.
       https://doi.org/10.1016/0378-8733(78)90021-7
    .. [2] Sariyuce, A.E. ; Kaya, K. ; Saule, E. ; Catalyiirek, U.V. Incremental
       Algorithms for Closeness Centrality. 2013 IEEE International Conference on Big Data
       http://sariyuce.com/papers/bigdata13.pdf
networkx.induced_subgraph
Python Library Documentation: function induced_subgraph in module networkx.classes.function

induced_subgraph(G, nbunch)
    Returns a SubGraph view of `G` showing only nodes in nbunch.

    The induced subgraph of a graph on a set of nodes N is the
    graph with nodes N and edges from G which have both ends in N.

    Parameters
    ----------
    G : NetworkX Graph
    nbunch : node, container of nodes or None (for all nodes)

    Returns
    -------
    subgraph : SubGraph View
        A read-only view of the subgraph in `G` induced by the nodes.
        Changes to the graph `G` will be reflected in the view.

    Notes
    -----
    To create a mutable subgraph with its own copies of nodes
    edges and attributes use `subgraph.copy()` or `Graph(subgraph)`

    For an inplace reduction of a graph to a subgraph you can remove nodes:
    `G.remove_nodes_from(n in G if n not in set(nbunch))`

    If you are going to compute subgraphs of your subgraphs you could
    end up with a chain of views that can be very slow once the chain
    has about 15 views in it. If they are all induced subgraphs, you
    can short-cut the chain by making them all subgraphs of the original
    graph. The graph class method `G.subgraph` does this when `G` is
    a subgraph. In contrast, this function allows you to choose to build
    chains or not, as you wish. The returned subgraph is a view on `G`.

    Examples
    --------
    >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
    >>> H = nx.induced_subgraph(G, [0, 1, 3])
    >>> list(H.edges)
    [(0, 1)]
    >>> list(H.nodes)
    [0, 1, 3]
networkx.information_centrality
Python Library Documentation: function current_flow_closeness_centrality in module networkx.algorithms.centrality.current_flow_closeness

current_flow_closeness_centrality(G, weight=None, dtype=<class 'float'>, solver='lu', *, backend=None, **backend_kwargs)
    Compute current-flow closeness centrality for nodes.

    Current-flow closeness centrality is variant of closeness
    centrality based on effective resistance between nodes in
    a network. This metric is also known as information centrality.

    Parameters
    ----------
    G : graph
      A NetworkX graph.

    weight : None or string, optional (default=None)
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.
      The weight reflects the capacity or the strength of the
      edge.

    dtype: data type (default=float)
      Default data type for internal matrices.
      Set to np.float32 for lower memory consumption.

    solver: string (default='lu')
       Type of linear solver to use for computing the flow matrix.
       Options are "full" (uses most memory), "lu" (recommended), and
       "cg" (uses least memory).

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with current flow closeness centrality as the value.

    See Also
    --------
    closeness_centrality

    Notes
    -----
    The algorithm is from Brandes [1]_.

    See also [2]_ for the original definition of information centrality.

    References
    ----------
    .. [1] Ulrik Brandes and Daniel Fleischer,
       Centrality Measures Based on Current Flow.
       Proc. 22nd Symp. Theoretical Aspects of Computer Science (STACS '05).
       LNCS 3404, pp. 533-544. Springer-Verlag, 2005.
       https://doi.org/10.1007/978-3-540-31856-9_44

    .. [2] Karen Stephenson and Marvin Zelen:
       Rethinking centrality: Methods and examples.
       Social Networks 11(1):1-37, 1989.
       https://doi.org/10.1016/0378-8733(89)90016-6
networkx.internet_as_graphs
Python Library Documentation: module networkx.generators.internet_as_graphs in networkx.generators

NAME
    networkx.generators.internet_as_graphs - Generates graphs resembling the Internet Autonomous System network

FUNCTIONS
    random_internet_as_graph(n, seed=None, *, backend=None, **backend_kwargs)
        Generates a random undirected graph resembling the Internet AS network

        Parameters
        ----------
        n: integer in [1000, 10000]
            Number of graph nodes
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        G: Networkx Graph object
            A randomly generated undirected graph

        Notes
        -----
        This algorithm returns an undirected graph resembling the Internet
        Autonomous System (AS) network, it uses the approach by Elmokashfi et al.
        [1]_ and it grants the properties described in the related paper [1]_.

        Each node models an autonomous system, with an attribute 'type' specifying
        its kind; tier-1 (T), mid-level (M), customer (C) or content-provider (CP).
        Each edge models an ADV communication link (hence, bidirectional) with
        attributes:

          - type: transit|peer, the kind of commercial agreement between nodes;
          - customer: <node id>, the identifier of the node acting as customer
            ('none' if type is peer).

        References
        ----------
        .. [1] A. Elmokashfi, A. Kvalbein and C. Dovrolis, "On the Scalability of
           BGP: The Role of Topology Growth," in IEEE Journal on Selected Areas
           in Communications, vol. 28, no. 8, pp. 1250-1261, October 2010.

DATA
    __all__ = ['random_internet_as_graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\internet_as_graphs.py

networkx.intersection
Python Library Documentation: function intersection in module networkx.algorithms.operators.binary

intersection(G, H, *, backend=None, **backend_kwargs)
    Returns a new graph that contains only the nodes and the edges that exist in
    both G and H.

    Parameters
    ----------
    G,H : graph
       A NetworkX graph. G and H can have different node sets but must be both graphs or both multigraphs.

    Raises
    ------
    NetworkXError
        If one is a MultiGraph and the other one is a graph.

    Returns
    -------
    GH : A new graph with the same type as G.

    Notes
    -----
    Attributes from the graph, nodes, and edges are not copied to the new
    graph.  If you want a new graph of the intersection of G and H
    with the attributes (including edge data) from G use remove_nodes_from()
    as follows

    >>> G = nx.path_graph(3)
    >>> H = nx.path_graph(5)
    >>> R = G.copy()
    >>> R.remove_nodes_from(n for n in G if n not in H)
    >>> R.remove_edges_from(e for e in G.edges if e not in H.edges)

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (1, 2)])
    >>> H = nx.Graph([(0, 3), (1, 2), (2, 3)])
    >>> R = nx.intersection(G, H)
    >>> R.nodes
    NodeView((0, 1, 2))
    >>> R.edges
    EdgeView([(1, 2)])
networkx.intersection_all
Python Library Documentation: function intersection_all in module networkx.algorithms.operators.all

intersection_all(graphs, *, backend=None, **backend_kwargs)
    Returns a new graph that contains only the nodes and the edges that exist in
    all graphs.

    Parameters
    ----------
    graphs : iterable
       Iterable of NetworkX graphs

    Returns
    -------
    R : A new graph with the same type as the first graph in list

    Raises
    ------
    ValueError
       If `graphs` is an empty list.

    NetworkXError
        In case of mixed type graphs, like MultiGraph and Graph, or directed and undirected graphs.

    Notes
    -----
    For operating on mixed type graphs, they should be converted to the same type.

    Attributes from the graph, nodes, and edges are not copied to the new
    graph.

    The resulting graph can be updated with attributes if desired. For example, code which adds the minimum attribute for each node across all graphs could work.
    >>> g = nx.Graph()
    >>> g.add_node(0, capacity=4)
    >>> g.add_node(1, capacity=3)
    >>> g.add_edge(0, 1)

    >>> h = g.copy()
    >>> h.nodes[0]["capacity"] = 2

    >>> gh = nx.intersection_all([g, h])

    >>> new_node_attr = {
    ...     n: min(*(anyG.nodes[n].get("capacity", float("inf")) for anyG in [g, h]))
    ...     for n in gh
    ... }
    >>> nx.set_node_attributes(gh, new_node_attr, "new_capacity")
    >>> gh.nodes(data=True)
    NodeDataView({0: {'new_capacity': 2}, 1: {'new_capacity': 3}})

    Examples
    --------
    >>> G1 = nx.Graph([(1, 2), (2, 3)])
    >>> G2 = nx.Graph([(2, 3), (3, 4)])
    >>> R = nx.intersection_all([G1, G2])
    >>> list(R.nodes())
    [2, 3]
    >>> list(R.edges())
    [(2, 3)]
networkx.intersection_array
Python Library Documentation: function intersection_array in module networkx.algorithms.distance_regular

intersection_array(G, *, backend=None, **backend_kwargs)
    Returns the intersection array of a distance-regular graph.

    Given a distance-regular graph G with integers b_i, c_i,i = 0,....,d
    such that for any 2 vertices x,y in G at a distance i=d(x,y), there
    are exactly c_i neighbors of y at a distance of i-1 from x and b_i
    neighbors of y at a distance of i+1 from x.

    A distance regular graph's intersection array is given by,
    [b_0,b_1,.....b_{d-1};c_1,c_2,.....c_d]

    Parameters
    ----------
    G: Networkx graph (undirected)

    Returns
    -------
    b,c: tuple of lists

    Examples
    --------
    >>> G = nx.icosahedral_graph()
    >>> nx.intersection_array(G)
    ([5, 2, 1], [1, 2, 5])

    References
    ----------
    .. [1] Weisstein, Eric W. "Intersection Array."
       From MathWorld--A Wolfram Web Resource.
       http://mathworld.wolfram.com/IntersectionArray.html

    See Also
    --------
    global_parameters
networkx.interval_graph
Python Library Documentation: function interval_graph in module networkx.generators.interval_graph

interval_graph(intervals, *, backend=None, **backend_kwargs)
    Generates an interval graph for a list of intervals given.

    In graph theory, an interval graph is an undirected graph formed from a set
    of closed intervals on the real line, with a vertex for each interval
    and an edge between vertices whose intervals intersect.
    It is the intersection graph of the intervals.

    More information can be found at:
    https://en.wikipedia.org/wiki/Interval_graph

    Parameters
    ----------
    intervals : a sequence of intervals, say (l, r) where l is the left end,
    and r is the right end of the closed interval.

    Returns
    -------
    G : networkx graph

    Examples
    --------
    >>> intervals = [(-2, 3), [1, 4], (2, 3), (4, 6)]
    >>> G = nx.interval_graph(intervals)
    >>> sorted(G.edges)
    [((-2, 3), (1, 4)), ((-2, 3), (2, 3)), ((1, 4), (2, 3)), ((1, 4), (4, 6))]

    Raises
    ------
    :exc:`TypeError`
        if `intervals` contains None or an element which is not
        collections.abc.Sequence or not a length of 2.
    :exc:`ValueError`
        if `intervals` contains an interval such that min1 > max1
        where min1,max1 = interval
networkx.inverse_line_graph
Python Library Documentation: function inverse_line_graph in module networkx.generators.line

inverse_line_graph(G, *, backend=None, **backend_kwargs)
    Returns the inverse line graph of graph G.

    If H is a graph, and G is the line graph of H, such that G = L(H).
    Then H is the inverse line graph of G.

    Not all graphs are line graphs and these do not have an inverse line graph.
    In these cases this function raises a NetworkXError.

    Parameters
    ----------
    G : graph
        A NetworkX Graph

    Returns
    -------
    H : graph
        The inverse line graph of G.

    Raises
    ------
    NetworkXNotImplemented
        If G is directed or a multigraph

    NetworkXError
        If G is not a line graph

    Notes
    -----
    This is an implementation of the Roussopoulos algorithm[1]_.

    If G consists of multiple components, then the algorithm doesn't work.
    You should invert every component separately:

    >>> K5 = nx.complete_graph(5)
    >>> P4 = nx.Graph([("a", "b"), ("b", "c"), ("c", "d")])
    >>> G = nx.union(K5, P4)
    >>> root_graphs = []
    >>> for comp in nx.connected_components(G):
    ...     root_graphs.append(nx.inverse_line_graph(G.subgraph(comp)))
    >>> len(root_graphs)
    2

    References
    ----------
    .. [1] Roussopoulos, N.D. , "A max {m, n} algorithm for determining the graph H from
       its line graph G", Information Processing Letters 2, (1973), 108--112, ISSN 0020-0190,
       `DOI link <https://doi.org/10.1016/0020-0190(73)90029-X>`_
networkx.is_aperiodic
Python Library Documentation: function is_aperiodic in module networkx.algorithms.dag

is_aperiodic(G, *, backend=None, **backend_kwargs)
    Returns True if `G` is aperiodic.

    A directed graph is aperiodic if there is no integer k > 1 that
    divides the length of every cycle in the graph.

    Parameters
    ----------
    G : NetworkX DiGraph
        A directed graph

    Returns
    -------
    bool
        True if the graph is aperiodic False otherwise

    Raises
    ------
    NetworkXError
        If `G` is not directed

    Examples
    --------
    A graph consisting of one cycle, the length of which is 2. Therefore ``k = 2``
    divides the length of every cycle in the graph and thus the graph
    is *not aperiodic*::

        >>> DG = nx.DiGraph([(1, 2), (2, 1)])
        >>> nx.is_aperiodic(DG)
        False

    A graph consisting of two cycles: one of length 2 and the other of length 3.
    The cycle lengths are coprime, so there is no single value of k where ``k > 1``
    that divides each cycle length and therefore the graph is *aperiodic*::

        >>> DG = nx.DiGraph([(1, 2), (2, 3), (3, 1), (1, 4), (4, 1)])
        >>> nx.is_aperiodic(DG)
        True

    A graph consisting of two cycles: one of length 2 and the other of length 4.
    The lengths of the cycles share a common factor ``k = 2``, and therefore
    the graph is *not aperiodic*::

        >>> DG = nx.DiGraph([(1, 2), (2, 1), (3, 4), (4, 5), (5, 6), (6, 3)])
        >>> nx.is_aperiodic(DG)
        False

    An acyclic graph, therefore the graph is *not aperiodic*::

        >>> DG = nx.DiGraph([(1, 2), (2, 3)])
        >>> nx.is_aperiodic(DG)
        False

    Notes
    -----
    This uses the method outlined in [1]_, which runs in $O(m)$ time
    given $m$ edges in `G`. Note that a graph is not aperiodic if it is
    acyclic as every integer trivial divides length 0 cycles.

    References
    ----------
    .. [1] Jarvis, J. P.; Shier, D. R. (1996),
       "Graph-theoretic analysis of finite Markov chains,"
       in Shier, D. R.; Wallenius, K. T., Applied Mathematical Modeling:
       A Multidisciplinary Approach, CRC Press.
networkx.is_arborescence
Python Library Documentation: function is_arborescence in module networkx.algorithms.tree.recognition

is_arborescence(G, *, backend=None, **backend_kwargs)
    Returns True if `G` is an arborescence.

    An arborescence is a directed tree with maximum in-degree equal to 1.

    Parameters
    ----------
    G : graph
        The graph to test.

    Returns
    -------
    b : bool
        A boolean that is True if `G` is an arborescence.

    Examples
    --------
    >>> G = nx.DiGraph([(0, 1), (0, 2), (2, 3), (3, 4)])
    >>> nx.is_arborescence(G)
    True
    >>> G.remove_edge(0, 1)
    >>> G.add_edge(1, 2)  # maximum in-degree is 2
    >>> nx.is_arborescence(G)
    False

    Notes
    -----
    In another convention, an arborescence is known as a *tree*.

    See Also
    --------
    is_tree
networkx.is_at_free
Python Library Documentation: function is_at_free in module networkx.algorithms.asteroidal

is_at_free(G, *, backend=None, **backend_kwargs)
    Check if a graph is AT-free.

    The method uses the `find_asteroidal_triple` method to recognize
    an AT-free graph. If no asteroidal triple is found the graph is
    AT-free and True is returned. If at least one asteroidal triple is
    found the graph is not AT-free and False is returned.

    Parameters
    ----------
    G : NetworkX Graph
        The graph to check whether is AT-free or not.

    Returns
    -------
    bool
        True if G is AT-free and False otherwise.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (1, 2), (1, 3), (1, 4), (4, 5)])
    >>> nx.is_at_free(G)
    True

    >>> G = nx.cycle_graph(6)
    >>> nx.is_at_free(G)
    False
networkx.is_attracting_component
Python Library Documentation: function is_attracting_component in module networkx.algorithms.components.attracting

is_attracting_component(G, *, backend=None, **backend_kwargs)
    Returns True if `G` consists of a single attracting component.

    Parameters
    ----------
    G : DiGraph, MultiDiGraph
        The graph to be analyzed.

    Returns
    -------
    attracting : bool
        True if `G` has a single attracting component. Otherwise, False.

    Raises
    ------
    NetworkXNotImplemented
        If the input graph is undirected.

    See Also
    --------
    attracting_components
    number_attracting_components
networkx.is_biconnected
Python Library Documentation: function is_biconnected in module networkx.algorithms.components.biconnected

is_biconnected(G, *, backend=None, **backend_kwargs)
    Returns True if the graph is biconnected, False otherwise.

    A graph is biconnected if, and only if, it cannot be disconnected by
    removing only one node (and all edges incident on that node).  If
    removing a node increases the number of disconnected components
    in the graph, that node is called an articulation point, or cut
    vertex.  A biconnected graph has no articulation points.

    Parameters
    ----------
    G : NetworkX Graph
        An undirected graph.

    Returns
    -------
    biconnected : bool
        True if the graph is biconnected, False otherwise.

    Raises
    ------
    NetworkXNotImplemented
        If the input graph is not undirected.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> print(nx.is_biconnected(G))
    False
    >>> G.add_edge(0, 3)
    >>> print(nx.is_biconnected(G))
    True

    See Also
    --------
    biconnected_components
    articulation_points
    biconnected_component_edges
    is_strongly_connected
    is_weakly_connected
    is_connected
    is_semiconnected

    Notes
    -----
    The algorithm to find articulation points and biconnected
    components is implemented using a non-recursive depth-first-search
    (DFS) that keeps track of the highest level that back edges reach
    in the DFS tree.  A node `n` is an articulation point if, and only
    if, there exists a subtree rooted at `n` such that there is no
    back edge from any successor of `n` that links to a predecessor of
    `n` in the DFS tree.  By keeping track of all the edges traversed
    by the DFS we can obtain the biconnected components because all
    edges of a bicomponent will be traversed consecutively between
    articulation points.

    References
    ----------
    .. [1] Hopcroft, J.; Tarjan, R. (1973).
       "Efficient algorithms for graph manipulation".
       Communications of the ACM 16: 372–378. doi:10.1145/362248.362272
networkx.is_bipartite
Python Library Documentation: function is_bipartite in module networkx.algorithms.bipartite.basic

is_bipartite(G, *, backend=None, **backend_kwargs)
    Returns True if graph G is bipartite, False if not.

    Parameters
    ----------
    G : NetworkX graph

    Examples
    --------
    >>> from networkx.algorithms import bipartite
    >>> G = nx.path_graph(4)
    >>> print(bipartite.is_bipartite(G))
    True

    See Also
    --------
    color, is_bipartite_node_set
networkx.is_branching
Python Library Documentation: function is_branching in module networkx.algorithms.tree.recognition

is_branching(G, *, backend=None, **backend_kwargs)
    Returns True if `G` is a branching.

    A branching is a directed forest with maximum in-degree equal to 1.

    Parameters
    ----------
    G : directed graph
        The directed graph to test.

    Returns
    -------
    b : bool
        A boolean that is True if `G` is a branching.

    Examples
    --------
    >>> G = nx.DiGraph([(0, 1), (1, 2), (2, 3), (3, 4)])
    >>> nx.is_branching(G)
    True
    >>> G.remove_edge(2, 3)
    >>> G.add_edge(3, 1)  # maximum in-degree is 2
    >>> nx.is_branching(G)
    False

    Notes
    -----
    In another convention, a branching is also known as a *forest*.

    See Also
    --------
    is_forest
networkx.is_chordal
Python Library Documentation: function is_chordal in module networkx.algorithms.chordal

is_chordal(G, *, backend=None, **backend_kwargs)
    Checks whether G is a chordal graph.

    A graph is chordal if every cycle of length at least 4 has a chord
    (an edge joining two nodes not adjacent in the cycle).

    Parameters
    ----------
    G : graph
      A NetworkX graph.

    Returns
    -------
    chordal : bool
      True if G is a chordal graph and False otherwise.

    Raises
    ------
    NetworkXNotImplemented
        The algorithm does not support DiGraph, MultiGraph and MultiDiGraph.

    Examples
    --------
    >>> e = [
    ...     (1, 2),
    ...     (1, 3),
    ...     (2, 3),
    ...     (2, 4),
    ...     (3, 4),
    ...     (3, 5),
    ...     (3, 6),
    ...     (4, 5),
    ...     (4, 6),
    ...     (5, 6),
    ... ]
    >>> G = nx.Graph(e)
    >>> nx.is_chordal(G)
    True

    Notes
    -----
    The routine tries to go through every node following maximum cardinality
    search. It returns False when it finds that the separator for any node
    is not a clique.  Based on the algorithms in [1]_.

    Self loops are ignored.

    References
    ----------
    .. [1] R. E. Tarjan and M. Yannakakis, Simple linear-time algorithms
       to test chordality of graphs, test acyclicity of hypergraphs, and
       selectively reduce acyclic hypergraphs, SIAM J. Comput., 13 (1984),
       pp. 566–579.
networkx.is_connected
Python Library Documentation: function is_connected in module networkx.algorithms.components.connected

is_connected(G, *, backend=None, **backend_kwargs)
    Returns True if the graph is connected, False otherwise.

    Parameters
    ----------
    G : NetworkX Graph
       An undirected graph.

    Returns
    -------
    connected : bool
      True if the graph is connected, false otherwise.

    Raises
    ------
    NetworkXNotImplemented
        If G is directed.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> print(nx.is_connected(G))
    True

    See Also
    --------
    is_strongly_connected
    is_weakly_connected
    is_semiconnected
    is_biconnected
    connected_components

    Notes
    -----
    For undirected graphs only.
networkx.is_d_separator
Python Library Documentation: function is_d_separator in module networkx.algorithms.d_separation

is_d_separator(G, x, y, z, *, backend=None, **backend_kwargs)
    Return whether node sets `x` and `y` are d-separated by `z`.

    Parameters
    ----------
    G : nx.DiGraph
        A NetworkX DAG.

    x : node or set of nodes
        First node or set of nodes in `G`.

    y : node or set of nodes
        Second node or set of nodes in `G`.

    z : node or set of nodes
        Potential separator (set of conditioning nodes in `G`). Can be empty set.

    Returns
    -------
    b : bool
        A boolean that is true if `x` is d-separated from `y` given `z` in `G`.

    Raises
    ------
    NetworkXError
        The *d-separation* test is commonly used on disjoint sets of
        nodes in acyclic directed graphs.  Accordingly, the algorithm
        raises a :exc:`NetworkXError` if the node sets are not
        disjoint or if the input graph is not a DAG.

    NodeNotFound
        If any of the input nodes are not found in the graph,
        a :exc:`NodeNotFound` exception is raised

    Notes
    -----
    A d-separating set in a DAG is a set of nodes that
    blocks all paths between the two sets. Nodes in `z`
    block a path if they are part of the path and are not a collider,
    or a descendant of a collider. Also colliders that are not in `z`
    block a path. A collider structure along a path
    is ``... -> c <- ...`` where ``c`` is the collider node.

    https://en.wikipedia.org/wiki/Bayesian_network#d-separation
networkx.is_digraphical
Python Library Documentation: function is_digraphical in module networkx.algorithms.graphical

is_digraphical(in_sequence, out_sequence, *, backend=None, **backend_kwargs)
    Returns True if some directed graph can realize the in- and out-degree
    sequences.

    Parameters
    ----------
    in_sequence : list or iterable container
        A sequence of integer node in-degrees

    out_sequence : list or iterable container
        A sequence of integer node out-degrees

    Returns
    -------
    valid : bool
      True if in and out-sequences are digraphic False if not.

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (1, 3), (2, 3), (3, 4), (4, 2), (5, 1), (5, 4)])
    >>> in_seq = (d for n, d in G.in_degree())
    >>> out_seq = (d for n, d in G.out_degree())
    >>> nx.is_digraphical(in_seq, out_seq)
    True

    To test a non-digraphical scenario:
    >>> in_seq_list = [d for n, d in G.in_degree()]
    >>> in_seq_list[-1] += 1
    >>> nx.is_digraphical(in_seq_list, out_seq)
    False

    Notes
    -----
    This algorithm is from Kleitman and Wang [1]_.
    The worst case runtime is $O(s \times \log n)$ where $s$ and $n$ are the
    sum and length of the sequences respectively.

    References
    ----------
    .. [1] D.J. Kleitman and D.L. Wang
       Algorithms for Constructing Graphs and Digraphs with Given Valences
       and Factors, Discrete Mathematics, 6(1), pp. 79-88 (1973)
networkx.is_directed
Python Library Documentation: function is_directed in module networkx.classes.function

is_directed(G)
    Return True if graph is directed.
networkx.is_directed_acyclic_graph
Python Library Documentation: function is_directed_acyclic_graph in module networkx.algorithms.dag

is_directed_acyclic_graph(G, *, backend=None, **backend_kwargs)
    Returns True if the graph `G` is a directed acyclic graph (DAG) or
    False if not.

    Parameters
    ----------
    G : NetworkX graph

    Returns
    -------
    bool
        True if `G` is a DAG, False otherwise

    Examples
    --------
    Undirected graph::

        >>> G = nx.Graph([(1, 2), (2, 3)])
        >>> nx.is_directed_acyclic_graph(G)
        False

    Directed graph with cycle::

        >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 1)])
        >>> nx.is_directed_acyclic_graph(G)
        False

    Directed acyclic graph::

        >>> G = nx.DiGraph([(1, 2), (2, 3)])
        >>> nx.is_directed_acyclic_graph(G)
        True

    See also
    --------
    topological_sort
networkx.is_distance_regular
Python Library Documentation: function is_distance_regular in module networkx.algorithms.distance_regular

is_distance_regular(G, *, backend=None, **backend_kwargs)
    Returns True if the graph is distance regular, False otherwise.

    A connected graph G is distance-regular if for any nodes x,y
    and any integers i,j=0,1,...,d (where d is the graph
    diameter), the number of vertices at distance i from x and
    distance j from y depends only on i,j and the graph distance
    between x and y, independently of the choice of x and y.

    Parameters
    ----------
    G: Networkx graph (undirected)

    Returns
    -------
    bool
      True if the graph is Distance Regular, False otherwise

    Examples
    --------
    >>> G = nx.hypercube_graph(6)
    >>> nx.is_distance_regular(G)
    True

    See Also
    --------
    intersection_array, global_parameters

    Notes
    -----
    For undirected and simple graphs only

    References
    ----------
    .. [1] Brouwer, A. E.; Cohen, A. M.; and Neumaier, A.
        Distance-Regular Graphs. New York: Springer-Verlag, 1989.
    .. [2] Weisstein, Eric W. "Distance-Regular Graph."
        http://mathworld.wolfram.com/Distance-RegularGraph.html
networkx.is_dominating_set
Python Library Documentation: function is_dominating_set in module networkx.algorithms.dominating

is_dominating_set(G, nbunch, *, backend=None, **backend_kwargs)
    Checks if `nbunch` is a dominating set for `G`.

    A *dominating set* for a graph with node set *V* is a subset *D* of
    *V* such that every node not in *D* is adjacent to at least one
    member of *D* [1]_.

    Parameters
    ----------
    G : NetworkX graph

    nbunch : iterable
        An iterable of nodes in the graph `G`.

    See also
    --------
    dominating_set

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Dominating_set
networkx.is_edge_cover
Python Library Documentation: function is_edge_cover in module networkx.algorithms.covering

is_edge_cover(G, cover, *, backend=None, **backend_kwargs)
    Decides whether a set of edges is a valid edge cover of the graph.

    Given a set of edges, whether it is an edge covering can
    be decided if we just check whether all nodes of the graph
    has an edge from the set, incident on it.

    Parameters
    ----------
    G : NetworkX graph
        An undirected bipartite graph.

    cover : set
        Set of edges to be checked.

    Returns
    -------
    bool
        Whether the set of edges is a valid edge cover of the graph.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
    >>> cover = {(2, 1), (3, 0)}
    >>> nx.is_edge_cover(G, cover)
    True

    Notes
    -----
    An edge cover of a graph is a set of edges such that every node of
    the graph is incident to at least one edge of the set.
networkx.is_empty
Python Library Documentation: function is_empty in module networkx.classes.function

is_empty(G)
    Returns True if `G` has no edges.

    Parameters
    ----------
    G : graph
        A NetworkX graph.

    Returns
    -------
    bool
        True if `G` has no edges, and False otherwise.

    Notes
    -----
    An empty graph can have nodes but not edges. The empty graph with zero
    nodes is known as the null graph. This is an $O(n)$ operation where n
    is the number of nodes in the graph.
networkx.is_eulerian
Python Library Documentation: function is_eulerian in module networkx.algorithms.euler

is_eulerian(G, *, backend=None, **backend_kwargs)
    Returns True if and only if `G` is Eulerian.

    A graph is *Eulerian* if it has an Eulerian circuit. An *Eulerian
    circuit* is a closed walk that includes each edge of a graph exactly
    once.

    Graphs with isolated vertices (i.e. vertices with zero degree) are not
    considered to have Eulerian circuits. Therefore, if the graph is not
    connected (or not strongly connected, for directed graphs), this function
    returns False.

    Parameters
    ----------
    G : NetworkX graph
       A graph, either directed or undirected.

    Examples
    --------
    >>> nx.is_eulerian(nx.DiGraph({0: [3], 1: [2], 2: [3], 3: [0, 1]}))
    True
    >>> nx.is_eulerian(nx.complete_graph(5))
    True
    >>> nx.is_eulerian(nx.petersen_graph())
    False

    If you prefer to allow graphs with isolated vertices to have Eulerian circuits,
    you can first remove such vertices and then call `is_eulerian` as below example shows.

    >>> G = nx.Graph([(0, 1), (1, 2), (0, 2)])
    >>> G.add_node(3)
    >>> nx.is_eulerian(G)
    False

    >>> G.remove_nodes_from(list(nx.isolates(G)))
    >>> nx.is_eulerian(G)
    True
networkx.is_forest
Python Library Documentation: function is_forest in module networkx.algorithms.tree.recognition

is_forest(G, *, backend=None, **backend_kwargs)
    Returns True if `G` is a forest.

    A forest is a graph with no undirected cycles.

    For directed graphs, `G` is a forest if the underlying graph is a forest.
    The underlying graph is obtained by treating each directed edge as a single
    undirected edge in a multigraph.

    Parameters
    ----------
    G : graph
        The graph to test.

    Returns
    -------
    b : bool
        A boolean that is True if `G` is a forest.

    Raises
    ------
    NetworkXPointlessConcept
        If `G` is empty.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_edges_from([(1, 2), (1, 3), (2, 4), (2, 5)])
    >>> nx.is_forest(G)
    True
    >>> G.add_edge(4, 1)
    >>> nx.is_forest(G)
    False

    Notes
    -----
    In another convention, a directed forest is known as a *polyforest* and
    then *forest* corresponds to a *branching*.

    See Also
    --------
    is_branching
networkx.is_frozen
Python Library Documentation: function is_frozen in module networkx.classes.function

is_frozen(G)
    Returns True if graph is frozen.

    Parameters
    ----------
    G : graph
      A NetworkX graph

    See Also
    --------
    freeze
networkx.is_graphical
Python Library Documentation: function is_graphical in module networkx.algorithms.graphical

is_graphical(sequence, method='eg', *, backend=None, **backend_kwargs)
    Returns True if sequence is a valid degree sequence.

    A degree sequence is valid if some graph can realize it.

    Parameters
    ----------
    sequence : list or iterable container
        A sequence of integer node degrees

    method : "eg" | "hh"  (default: 'eg')
        The method used to validate the degree sequence.
        "eg" corresponds to the Erdős-Gallai algorithm
        [EG1960]_, [choudum1986]_, and
        "hh" to the Havel-Hakimi algorithm
        [havel1955]_, [hakimi1962]_, [CL1996]_.

    Returns
    -------
    valid : bool
        True if the sequence is a valid degree sequence and False if not.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> sequence = (d for n, d in G.degree())
    >>> nx.is_graphical(sequence)
    True

    To test a non-graphical sequence:
    >>> sequence_list = [d for n, d in G.degree()]
    >>> sequence_list[-1] += 1
    >>> nx.is_graphical(sequence_list)
    False

    References
    ----------
    .. [EG1960] Erdős and Gallai, Mat. Lapok 11 264, 1960.
    .. [choudum1986] S.A. Choudum. "A simple proof of the Erdős-Gallai theorem on
       graph sequences." Bulletin of the Australian Mathematical Society, 33,
       pp 67-70, 1986. https://doi.org/10.1017/S0004972700002872
    .. [havel1955] Havel, V. "A Remark on the Existence of Finite Graphs"
       Casopis Pest. Mat. 80, 477-480, 1955.
    .. [hakimi1962] Hakimi, S. "On the Realizability of a Set of Integers as
       Degrees of the Vertices of a Graph." SIAM J. Appl. Math. 10, 496-506, 1962.
    .. [CL1996] G. Chartrand and L. Lesniak, "Graphs and Digraphs",
       Chapman and Hall/CRC, 1996.
networkx.is_isolate
Python Library Documentation: function is_isolate in module networkx.algorithms.isolate

is_isolate(G, n, *, backend=None, **backend_kwargs)
    Determines whether a node is an isolate.

    An *isolate* is a node with no neighbors (that is, with degree
    zero). For directed graphs, this means no in-neighbors and no
    out-neighbors.

    Parameters
    ----------
    G : NetworkX graph

    n : node
        A node in `G`.

    Returns
    -------
    is_isolate : bool
       True if and only if `n` has no neighbors.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_edge(1, 2)
    >>> G.add_node(3)
    >>> nx.is_isolate(G, 2)
    False
    >>> nx.is_isolate(G, 3)
    True
networkx.is_isomorphic
Python Library Documentation: function is_isomorphic in module networkx.algorithms.isomorphism.isomorph

is_isomorphic(G1, G2, node_match=None, edge_match=None, *, backend=None, **backend_kwargs)
    Returns True if the graphs G1 and G2 are isomorphic and False otherwise.

    Parameters
    ----------
    G1, G2: graphs
        The two graphs G1 and G2 must be the same type.

    node_match : callable
        A function that returns True if node n1 in G1 and n2 in G2 should
        be considered equal during the isomorphism test.
        If node_match is not specified then node attributes are not considered.

        The function will be called like

           node_match(G1.nodes[n1], G2.nodes[n2]).

        That is, the function will receive the node attribute dictionaries
        for n1 and n2 as inputs.

    edge_match : callable
        A function that returns True if the edge attribute dictionary
        for the pair of nodes (u1, v1) in G1 and (u2, v2) in G2 should
        be considered equal during the isomorphism test.  If edge_match is
        not specified then edge attributes are not considered.

        The function will be called like

           edge_match(G1[u1][v1], G2[u2][v2]).

        That is, the function will receive the edge attribute dictionaries
        of the edges under consideration.

    Notes
    -----
    Uses the vf2 algorithm [1]_.

    Examples
    --------
    >>> import networkx.algorithms.isomorphism as iso

    For digraphs G1 and G2, using 'weight' edge attribute (default: 1)

    >>> G1 = nx.DiGraph()
    >>> G2 = nx.DiGraph()
    >>> nx.add_path(G1, [1, 2, 3, 4], weight=1)
    >>> nx.add_path(G2, [10, 20, 30, 40], weight=2)
    >>> em = iso.numerical_edge_match("weight", 1)
    >>> nx.is_isomorphic(G1, G2)  # no weights considered
    True
    >>> nx.is_isomorphic(G1, G2, edge_match=em)  # match weights
    False

    For multidigraphs G1 and G2, using 'fill' node attribute (default: '')

    >>> G1 = nx.MultiDiGraph()
    >>> G2 = nx.MultiDiGraph()
    >>> G1.add_nodes_from([1, 2, 3], fill="red")
    >>> G2.add_nodes_from([10, 20, 30, 40], fill="red")
    >>> nx.add_path(G1, [1, 2, 3, 4], weight=3, linewidth=2.5)
    >>> nx.add_path(G2, [10, 20, 30, 40], weight=3)
    >>> nm = iso.categorical_node_match("fill", "red")
    >>> nx.is_isomorphic(G1, G2, node_match=nm)
    True

    For multidigraphs G1 and G2, using 'weight' edge attribute (default: 7)

    >>> G1.add_edge(1, 2, weight=7)
    1
    >>> G2.add_edge(10, 20)
    1
    >>> em = iso.numerical_multiedge_match("weight", 7, rtol=1e-6)
    >>> nx.is_isomorphic(G1, G2, edge_match=em)
    True

    For multigraphs G1 and G2, using 'weight' and 'linewidth' edge attributes
    with default values 7 and 2.5. Also using 'fill' node attribute with
    default value 'red'.

    >>> em = iso.numerical_multiedge_match(["weight", "linewidth"], [7, 2.5])
    >>> nm = iso.categorical_node_match("fill", "red")
    >>> nx.is_isomorphic(G1, G2, edge_match=em, node_match=nm)
    True

    See Also
    --------
    numerical_node_match, numerical_edge_match, numerical_multiedge_match
    categorical_node_match, categorical_edge_match, categorical_multiedge_match

    References
    ----------
    .. [1]  L. P. Cordella, P. Foggia, C. Sansone, M. Vento,
       "An Improved Algorithm for Matching Large Graphs",
       3rd IAPR-TC15 Workshop  on Graph-based Representations in
       Pattern Recognition, Cuen, pp. 149-159, 2001.
       https://www.researchgate.net/publication/200034365_An_Improved_Algorithm_for_Matching_Large_Graphs
networkx.is_k_edge_connected
Python Library Documentation: function is_k_edge_connected in module networkx.algorithms.connectivity.edge_augmentation

is_k_edge_connected(G, k, *, backend=None, **backend_kwargs)
    Tests to see if a graph is k-edge-connected.

    Is it impossible to disconnect the graph by removing fewer than k edges?
    If so, then G is k-edge-connected.

    Parameters
    ----------
    G : NetworkX graph
       An undirected graph.

    k : integer
        edge connectivity to test for

    Returns
    -------
    boolean
        True if G is k-edge-connected.

    See Also
    --------
    :func:`is_locally_k_edge_connected`

    Examples
    --------
    >>> G = nx.barbell_graph(10, 0)
    >>> nx.is_k_edge_connected(G, k=1)
    True
    >>> nx.is_k_edge_connected(G, k=2)
    False
networkx.is_k_regular
Python Library Documentation: function is_k_regular in module networkx.algorithms.regular

is_k_regular(G, k, *, backend=None, **backend_kwargs)
    Determines whether the graph ``G`` is a k-regular graph.

    A k-regular graph is a graph where each vertex has degree k.

    Parameters
    ----------
    G : NetworkX graph

    Returns
    -------
    bool
        Whether the given graph is k-regular.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (2, 3), (3, 4), (4, 1)])
    >>> nx.is_k_regular(G, k=3)
    False
networkx.is_kl_connected
Python Library Documentation: function is_kl_connected in module networkx.algorithms.hybrid

is_kl_connected(G, k, l, low_memory=False, *, backend=None, **backend_kwargs)
    Returns True if and only if `G` is locally `(k, l)`-connected.

    A graph is locally `(k, l)`-connected if for each edge `(u, v)` in the
    graph there are at least `l` edge-disjoint paths of length at most `k`
    joining `u` to `v`.

    Parameters
    ----------
    G : NetworkX graph
        The graph to test for local `(k, l)`-connectedness.

    k : integer
        The maximum length of paths to consider. A higher number means a looser
        connectivity requirement.

    l : integer
        The number of edge-disjoint paths. A higher number means a stricter
        connectivity requirement.

    low_memory : bool
        If this is True, this function uses an algorithm that uses slightly
        more time but less memory.

    Returns
    -------
    bool
        Whether the graph is locally `(k, l)`-connected subgraph.

    See also
    --------
    kl_connected_subgraph

    References
    ----------
    .. [1] Chung, Fan and Linyuan Lu. "The Small World Phenomenon in Hybrid
           Power Law Graphs." *Complex Networks*. Springer Berlin Heidelberg,
           2004. 89--104.
networkx.is_matching
Python Library Documentation: function is_matching in module networkx.algorithms.matching

is_matching(G, matching, *, backend=None, **backend_kwargs)
    Return True if ``matching`` is a valid matching of ``G``

    A *matching* in a graph is a set of edges in which no two distinct
    edges share a common endpoint. Each node is incident to at most one
    edge in the matching. The edges are said to be independent.

    Parameters
    ----------
    G : NetworkX graph

    matching : dict or set
        A dictionary or set representing a matching. If a dictionary, it
        must have ``matching[u] == v`` and ``matching[v] == u`` for each
        edge ``(u, v)`` in the matching. If a set, it must have elements
        of the form ``(u, v)``, where ``(u, v)`` is an edge in the
        matching.

    Returns
    -------
    bool
        Whether the given set or dictionary represents a valid matching
        in the graph.

    Raises
    ------
    NetworkXError
        If the proposed matching has an edge to a node not in G.
        Or if the matching is not a collection of 2-tuple edges.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (2, 4), (3, 5), (4, 5)])
    >>> nx.is_maximal_matching(G, {1: 3, 2: 4})  # using dict to represent matching
    True

    >>> nx.is_matching(G, {(1, 3), (2, 4)})  # using set to represent matching
    True
networkx.is_maximal_matching
Python Library Documentation: function is_maximal_matching in module networkx.algorithms.matching

is_maximal_matching(G, matching, *, backend=None, **backend_kwargs)
    Return True if ``matching`` is a maximal matching of ``G``

    A *maximal matching* in a graph is a matching in which adding any
    edge would cause the set to no longer be a valid matching.

    Parameters
    ----------
    G : NetworkX graph

    matching : dict or set
        A dictionary or set representing a matching. If a dictionary, it
        must have ``matching[u] == v`` and ``matching[v] == u`` for each
        edge ``(u, v)`` in the matching. If a set, it must have elements
        of the form ``(u, v)``, where ``(u, v)`` is an edge in the
        matching.

    Returns
    -------
    bool
        Whether the given set or dictionary represents a valid maximal
        matching in the graph.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (3, 4), (3, 5)])
    >>> nx.is_maximal_matching(G, {(1, 2), (3, 4)})
    True
networkx.is_minimal_d_separator
Python Library Documentation: function is_minimal_d_separator in module networkx.algorithms.d_separation

is_minimal_d_separator(G, x, y, z, *, included=None, restricted=None, backend=None, **backend_kwargs)
    Determine if `z` is a minimal d-separator for `x` and `y`.

    A d-separator, `z`, in a DAG is a set of nodes that blocks
    all paths from nodes in set `x` to nodes in set `y`.
    A minimal d-separator is a d-separator `z` such that removing
    any subset of nodes makes it no longer a d-separator.

    Note: This function checks whether `z` is a d-separator AND is
    minimal. One can use the function `is_d_separator` to only check if
    `z` is a d-separator. See examples below.

    Parameters
    ----------
    G : nx.DiGraph
        A NetworkX DAG.
    x : node | set
        A node or set of nodes in the graph.
    y : node | set
        A node or set of nodes in the graph.
    z : node | set
        The node or set of nodes to check if it is a minimal d-separating set.
        The function :func:`is_d_separator` is called inside this function
        to verify that `z` is in fact a d-separator.
    included : set | node | None
        A node or set of nodes which must be included in the found separating set,
        default is ``None``, which means the empty set.
    restricted : set | node | None
        Restricted node or set of nodes to consider. Only these nodes can be in
        the found separating set, default is ``None`` meaning all nodes in ``G``.

    Returns
    -------
    bool
        Whether or not the set `z` is a minimal d-separator subject to
        `restricted` nodes and `included` node constraints.

    Examples
    --------
    >>> G = nx.path_graph([0, 1, 2, 3], create_using=nx.DiGraph)
    >>> G.add_node(4)
    >>> nx.is_minimal_d_separator(G, 0, 2, {1})
    True
    >>> # since {1} is the minimal d-separator, {1, 3, 4} is not minimal
    >>> nx.is_minimal_d_separator(G, 0, 2, {1, 3, 4})
    False
    >>> # alternatively, if we only want to check that {1, 3, 4} is a d-separator
    >>> nx.is_d_separator(G, 0, 2, {1, 3, 4})
    True

    Raises
    ------
    NetworkXError
        Raises a :exc:`NetworkXError` if the input graph is not a DAG.

    NodeNotFound
        If any of the input nodes are not found in the graph,
        a :exc:`NodeNotFound` exception is raised.

    References
    ----------
    .. [1] van der Zander, Benito, and Maciej Liśkiewicz. "Finding
        minimal d-separators in linear time and applications." In
        Uncertainty in Artificial Intelligence, pp. 637-647. PMLR, 2020.

    Notes
    -----
    This function works on verifying that a set is minimal and
    d-separating between two nodes. Uses criterion (a), (b), (c) on
    page 4 of [1]_. a) closure(`x`) and `y` are disjoint. b) `z` contains
    all nodes from `included` and is contained in the `restricted`
    nodes and in the union of ancestors of `x`, `y`, and `included`.
    c) the nodes in `z` not in `included` are contained in both
    closure(x) and closure(y). The closure of a set is the set of nodes
    connected to the set by a directed path in G.

    The complexity is :math:`O(m)`, where :math:`m` stands for the
    number of edges in the subgraph of G consisting of only the
    ancestors of `x` and `y`.

    For full details, see [1]_.
networkx.is_multigraphical
Python Library Documentation: function is_multigraphical in module networkx.algorithms.graphical

is_multigraphical(sequence, *, backend=None, **backend_kwargs)
    Returns True if some multigraph can realize the sequence.

    Parameters
    ----------
    sequence : list
        A list of integers

    Returns
    -------
    valid : bool
        True if deg_sequence is a multigraphic degree sequence and False if not.

    Examples
    --------
    >>> G = nx.MultiGraph([(1, 2), (1, 3), (2, 3), (3, 4), (4, 2), (5, 1), (5, 4)])
    >>> sequence = (d for _, d in G.degree())
    >>> nx.is_multigraphical(sequence)
    True

    To test a non-multigraphical sequence:
    >>> sequence_list = [d for _, d in G.degree()]
    >>> sequence_list[-1] += 1
    >>> nx.is_multigraphical(sequence_list)
    False

    Notes
    -----
    The worst-case run time is $O(n)$ where $n$ is the length of the sequence.

    References
    ----------
    .. [1] S. L. Hakimi. "On the realizability of a set of integers as
       degrees of the vertices of a linear graph", J. SIAM, 10, pp. 496-506
       (1962).
networkx.is_negatively_weighted
Python Library Documentation: function is_negatively_weighted in module networkx.classes.function

is_negatively_weighted(G, edge=None, weight='weight', *, backend=None, **backend_kwargs)
    Returns True if `G` has negatively weighted edges.

    Parameters
    ----------
    G : graph
        A NetworkX graph.

    edge : tuple, optional
        A 2-tuple specifying the only edge in `G` that will be tested. If
        None, then every edge in `G` is tested.

    weight: string, optional
        The attribute name used to query for edge weights.

    Returns
    -------
    bool
        A boolean signifying if `G`, or the specified edge, is negatively
        weighted.

    Raises
    ------
    NetworkXError
        If the specified edge does not exist.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_edges_from([(1, 3), (2, 4), (2, 6)])
    >>> G.add_edge(1, 2, weight=4)
    >>> nx.is_negatively_weighted(G, (1, 2))
    False
    >>> G[2][4]["weight"] = -2
    >>> nx.is_negatively_weighted(G)
    True
    >>> G = nx.DiGraph()
    >>> edges = [("0", "3", 3), ("0", "1", -5), ("1", "0", -2)]
    >>> G.add_weighted_edges_from(edges)
    >>> nx.is_negatively_weighted(G)
    True
networkx.is_path
Python Library Documentation: function is_path in module networkx.classes.function

is_path(G, path)
    Returns whether or not the specified path exists.

    For it to return True, every node on the path must exist and
    each consecutive pair must be connected via one or more edges.

    Parameters
    ----------
    G : graph
        A NetworkX graph.

    path : list
        A list of nodes which defines the path to traverse

    Returns
    -------
    bool
        True if `path` is a valid path in `G`
networkx.is_perfect_matching
Python Library Documentation: function is_perfect_matching in module networkx.algorithms.matching

is_perfect_matching(G, matching, *, backend=None, **backend_kwargs)
    Return True if ``matching`` is a perfect matching for ``G``

    A *perfect matching* in a graph is a matching in which exactly one edge
    is incident upon each vertex.

    Parameters
    ----------
    G : NetworkX graph

    matching : dict or set
        A dictionary or set representing a matching. If a dictionary, it
        must have ``matching[u] == v`` and ``matching[v] == u`` for each
        edge ``(u, v)`` in the matching. If a set, it must have elements
        of the form ``(u, v)``, where ``(u, v)`` is an edge in the
        matching.

    Returns
    -------
    bool
        Whether the given set or dictionary represents a valid perfect
        matching in the graph.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (2, 4), (3, 5), (4, 5), (4, 6)])
    >>> my_match = {1: 2, 3: 5, 4: 6}
    >>> nx.is_perfect_matching(G, my_match)
    True
networkx.is_planar
Python Library Documentation: function is_planar in module networkx.algorithms.planarity

is_planar(G, *, backend=None, **backend_kwargs)
    Returns True if and only if `G` is planar.

    A graph is *planar* iff it can be drawn in a plane without
    any edge intersections.

    Parameters
    ----------
    G : NetworkX graph

    Returns
    -------
    bool
       Whether the graph is planar.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2)])
    >>> nx.is_planar(G)
    True
    >>> nx.is_planar(nx.complete_graph(5))
    False

    See Also
    --------
    check_planarity :
        Check if graph is planar *and* return a `PlanarEmbedding` instance if True.
networkx.is_pseudographical
Python Library Documentation: function is_pseudographical in module networkx.algorithms.graphical

is_pseudographical(sequence, *, backend=None, **backend_kwargs)
    Returns True if some pseudograph can realize the sequence.

    Every nonnegative integer sequence with an even sum is pseudographical
    (see [1]_).

    Parameters
    ----------
    sequence : list or iterable container
        A sequence of integer node degrees

    Returns
    -------
    valid : bool
      True if the sequence is a pseudographic degree sequence and False if not.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (3, 4), (4, 2), (5, 1), (5, 4)])
    >>> sequence = (d for _, d in G.degree())
    >>> nx.is_pseudographical(sequence)
    True

    To test a non-pseudographical sequence:
    >>> sequence_list = [d for _, d in G.degree()]
    >>> sequence_list[-1] += 1
    >>> nx.is_pseudographical(sequence_list)
    False

    Notes
    -----
    The worst-case run time is $O(n)$ where n is the length of the sequence.

    References
    ----------
    .. [1] F. Boesch and F. Harary. "Line removal algorithms for graphs
       and their degree lists", IEEE Trans. Circuits and Systems, CAS-23(12),
       pp. 778-782 (1976).
networkx.is_regular
Python Library Documentation: function is_regular in module networkx.algorithms.regular

is_regular(G, *, backend=None, **backend_kwargs)
    Determines whether the graph ``G`` is a regular graph.

    A regular graph is a graph where each vertex has the same degree. A
    regular digraph is a graph where the indegree and outdegree of each
    vertex are equal.

    Parameters
    ----------
    G : NetworkX graph

    Returns
    -------
    bool
        Whether the given graph or digraph is regular.

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 4), (4, 1)])
    >>> nx.is_regular(G)
    True
networkx.is_regular_expander
Python Library Documentation: function is_regular_expander in module networkx.generators.expanders

is_regular_expander(G, *, epsilon=0, backend=None, **backend_kwargs)
    Determines whether the graph G is a regular expander. [1]_

    An expander graph is a sparse graph with strong connectivity properties.

    More precisely, this helper checks whether the graph is a
    regular $(n, d, \lambda)$-expander with $\lambda$ close to
    the Alon-Boppana bound and given by
    $\lambda = 2 \sqrt{d - 1} + \epsilon$. [2]_

    In the case where $\epsilon = 0$ then if the graph successfully passes the test
    it is a Ramanujan graph. [3]_

    A Ramanujan graph has spectral gap almost as large as possible, which makes them
    excellent expanders.

    Parameters
    ----------
    G : NetworkX graph
    epsilon : int, float, default=0

    Returns
    -------
    bool
        Whether the given graph is a regular $(n, d, \lambda)$-expander
        where $\lambda = 2 \sqrt{d - 1} + \epsilon$.

    Examples
    --------
    >>> G = nx.random_regular_expander_graph(20, 4)
    >>> nx.is_regular_expander(G)
    True

    See Also
    --------
    maybe_regular_expander
    random_regular_expander_graph

    References
    ----------
    .. [1] Expander graph, https://en.wikipedia.org/wiki/Expander_graph
    .. [2] Alon-Boppana bound, https://en.wikipedia.org/wiki/Alon%E2%80%93Boppana_bound
    .. [3] Ramanujan graphs, https://en.wikipedia.org/wiki/Ramanujan_graph
networkx.is_semiconnected
Python Library Documentation: function is_semiconnected in module networkx.algorithms.components.semiconnected

is_semiconnected(G, *, backend=None, **backend_kwargs)
    Returns True if the graph is semiconnected, False otherwise.

    A graph is semiconnected if and only if for any pair of nodes, either one
    is reachable from the other, or they are mutually reachable.

    This function uses a theorem that states that a DAG is semiconnected
    if for any topological sort, for node $v_n$ in that sort, there is an
    edge $(v_i, v_{i+1})$. That allows us to check if a non-DAG `G` is
    semiconnected by condensing the graph: i.e. constructing a new graph `H`
    with nodes being the strongly connected components of `G`, and edges
    (scc_1, scc_2) if there is a edge $(v_1, v_2)$ in `G` for some
    $v_1 \in scc_1$ and $v_2 \in scc_2$. That results in a DAG, so we compute
    the topological sort of `H` and check if for every $n$ there is an edge
    $(scc_n, scc_{n+1})$.

    Parameters
    ----------
    G : NetworkX graph
        A directed graph.

    Returns
    -------
    semiconnected : bool
        True if the graph is semiconnected, False otherwise.

    Raises
    ------
    NetworkXNotImplemented
        If the input graph is undirected.

    NetworkXPointlessConcept
        If the graph is empty.

    Examples
    --------
    >>> G = nx.path_graph(4, create_using=nx.DiGraph())
    >>> print(nx.is_semiconnected(G))
    True
    >>> G = nx.DiGraph([(1, 2), (3, 2)])
    >>> print(nx.is_semiconnected(G))
    False

    See Also
    --------
    is_strongly_connected
    is_weakly_connected
    is_connected
    is_biconnected
networkx.is_semieulerian
Python Library Documentation: function is_semieulerian in module networkx.algorithms.euler

is_semieulerian(G, *, backend=None, **backend_kwargs)
    Return True iff `G` is semi-Eulerian.

    G is semi-Eulerian if it has an Eulerian path but no Eulerian circuit.

    See Also
    --------
    has_eulerian_path
    is_eulerian
networkx.is_simple_path
Python Library Documentation: function is_simple_path in module networkx.algorithms.simple_paths

is_simple_path(G, nodes, *, backend=None, **backend_kwargs)
    Returns True if and only if `nodes` form a simple path in `G`.

    A *simple path* in a graph is a nonempty sequence of nodes in which
    no node appears more than once in the sequence, and each adjacent
    pair of nodes in the sequence is adjacent in the graph.

    Parameters
    ----------
    G : graph
        A NetworkX graph.
    nodes : list
        A list of one or more nodes in the graph `G`.

    Returns
    -------
    bool
        Whether the given list of nodes represents a simple path in `G`.

    Notes
    -----
    An empty list of nodes is not a path but a list of one node is a
    path. Here's an explanation why.

    This function operates on *node paths*. One could also consider
    *edge paths*. There is a bijection between node paths and edge
    paths.

    The *length of a path* is the number of edges in the path, so a list
    of nodes of length *n* corresponds to a path of length *n* - 1.
    Thus the smallest edge path would be a list of zero edges, the empty
    path. This corresponds to a list of one node.

    To convert between a node path and an edge path, you can use code
    like the following::

        >>> from networkx.utils import pairwise
        >>> nodes = [0, 1, 2, 3]
        >>> edges = list(pairwise(nodes))
        >>> edges
        [(0, 1), (1, 2), (2, 3)]
        >>> nodes = [edges[0][0]] + [v for u, v in edges]
        >>> nodes
        [0, 1, 2, 3]

    Examples
    --------
    >>> G = nx.cycle_graph(4)
    >>> nx.is_simple_path(G, [2, 3, 0])
    True
    >>> nx.is_simple_path(G, [0, 2])
    False
networkx.is_strongly_connected
Python Library Documentation: function is_strongly_connected in module networkx.algorithms.components.strongly_connected

is_strongly_connected(G, *, backend=None, **backend_kwargs)
    Test directed graph for strong connectivity.

    A directed graph is strongly connected if and only if every vertex in
    the graph is reachable from every other vertex.

    Parameters
    ----------
    G : NetworkX Graph
       A directed graph.

    Returns
    -------
    connected : bool
      True if the graph is strongly connected, False otherwise.

    Examples
    --------
    >>> G = nx.DiGraph([(0, 1), (1, 2), (2, 3), (3, 0), (2, 4), (4, 2)])
    >>> nx.is_strongly_connected(G)
    True
    >>> G.remove_edge(2, 3)
    >>> nx.is_strongly_connected(G)
    False

    Raises
    ------
    NetworkXNotImplemented
        If G is undirected.

    See Also
    --------
    is_weakly_connected
    is_semiconnected
    is_connected
    is_biconnected
    strongly_connected_components

    Notes
    -----
    For directed graphs only.
networkx.is_strongly_regular
Python Library Documentation: function is_strongly_regular in module networkx.algorithms.distance_regular

is_strongly_regular(G, *, backend=None, **backend_kwargs)
    Returns True if and only if the given graph is strongly
    regular.

    An undirected graph is *strongly regular* if

    * it is regular,
    * each pair of adjacent vertices has the same number of neighbors in
      common,
    * each pair of nonadjacent vertices has the same number of neighbors
      in common.

    Each strongly regular graph is a distance-regular graph.
    Conversely, if a distance-regular graph has diameter two, then it is
    a strongly regular graph. For more information on distance-regular
    graphs, see :func:`is_distance_regular`.

    Parameters
    ----------
    G : NetworkX graph
        An undirected graph.

    Returns
    -------
    bool
        Whether `G` is strongly regular.

    Examples
    --------

    The cycle graph on five vertices is strongly regular. It is
    two-regular, each pair of adjacent vertices has no shared neighbors,
    and each pair of nonadjacent vertices has one shared neighbor::

        >>> G = nx.cycle_graph(5)
        >>> nx.is_strongly_regular(G)
        True
networkx.is_tournament
Python Library Documentation: function is_tournament in module networkx.algorithms.tournament

is_tournament(G, *, backend=None, **backend_kwargs)
    Returns True if and only if `G` is a tournament.

    A tournament is a directed graph, with neither self-loops nor
    multi-edges, in which there is exactly one directed edge joining
    each pair of distinct nodes.

    Parameters
    ----------
    G : NetworkX graph
        A directed graph representing a tournament.

    Returns
    -------
    bool
        Whether the given graph is a tournament graph.

    Examples
    --------
    >>> G = nx.DiGraph([(0, 1), (1, 2), (2, 0)])
    >>> nx.is_tournament(G)
    True

    Notes
    -----
    Some definitions require a self-loop on each node, but that is not
    the convention used here.
networkx.is_tree
Python Library Documentation: function is_tree in module networkx.algorithms.tree.recognition

is_tree(G, *, backend=None, **backend_kwargs)
    Returns True if `G` is a tree.

    A tree is a connected graph with no undirected cycles.

    For directed graphs, `G` is a tree if the underlying graph is a tree. The
    underlying graph is obtained by treating each directed edge as a single
    undirected edge in a multigraph.

    Parameters
    ----------
    G : graph
        The graph to test.

    Returns
    -------
    b : bool
        A boolean that is True if `G` is a tree.

    Raises
    ------
    NetworkXPointlessConcept
        If `G` is empty.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_edges_from([(1, 2), (1, 3), (2, 4), (2, 5)])
    >>> nx.is_tree(G)  # n-1 edges
    True
    >>> G.add_edge(3, 4)
    >>> nx.is_tree(G)  # n edges
    False

    Notes
    -----
    In another convention, a directed tree is known as a *polytree* and then
    *tree* corresponds to an *arborescence*.

    See Also
    --------
    is_arborescence
networkx.is_triad
Python Library Documentation: function is_triad in module networkx.algorithms.triads

is_triad(G, *, backend=None, **backend_kwargs)
    Returns True if the graph G is a triad, else False.

    Parameters
    ----------
    G : graph
       A NetworkX Graph

    Returns
    -------
    istriad : boolean
       Whether G is a valid triad

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 1)])
    >>> nx.is_triad(G)
    True
    >>> G.add_edge(0, 1)
    >>> nx.is_triad(G)
    False
networkx.is_valid_degree_sequence_erdos_gallai
Python Library Documentation: function is_valid_degree_sequence_erdos_gallai in module networkx.algorithms.graphical

is_valid_degree_sequence_erdos_gallai(deg_sequence, *, backend=None, **backend_kwargs)
    Returns True if deg_sequence can be realized by a simple graph.

    The validation is done using the Erdős-Gallai theorem [EG1960]_.

    Parameters
    ----------
    deg_sequence : list
        A list of integers

    Returns
    -------
    valid : bool
        True if deg_sequence is graphical and False if not.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (3, 4), (4, 2), (5, 1), (5, 4)])
    >>> sequence = (d for _, d in G.degree())
    >>> nx.is_valid_degree_sequence_erdos_gallai(sequence)
    True

    To test a non-valid sequence:
    >>> sequence_list = [d for _, d in G.degree()]
    >>> sequence_list[-1] += 1
    >>> nx.is_valid_degree_sequence_erdos_gallai(sequence_list)
    False

    Notes
    -----

    This implementation uses an equivalent form of the Erdős-Gallai criterion.
    Worst-case run time is $O(n)$ where $n$ is the length of the sequence.

    Specifically, a sequence d is graphical if and only if the
    sum of the sequence is even and for all strong indices k in the sequence,

     .. math::

       \sum_{i=1}^{k} d_i \leq k(k-1) + \sum_{j=k+1}^{n} \min(d_i,k)
             = k(n-1) - ( k \sum_{j=0}^{k-1} n_j - \sum_{j=0}^{k-1} j n_j )

    A strong index k is any index where d_k >= k and the value n_j is the
    number of occurrences of j in d.  The maximal strong index is called the
    Durfee index.

    This particular rearrangement comes from the proof of Theorem 3 in [2]_.

    The ZZ condition says that for the sequence d if

    .. math::
        |d| >= \frac{(\max(d) + \min(d) + 1)^2}{4*\min(d)}

    then d is graphical.  This was shown in Theorem 6 in [2]_.

    References
    ----------
    .. [1] A. Tripathi and S. Vijay. "A note on a theorem of Erdős & Gallai",
       Discrete Mathematics, 265, pp. 417-420 (2003).
    .. [2] I.E. Zverovich and V.E. Zverovich. "Contributions to the theory
       of graphic sequences", Discrete Mathematics, 105, pp. 292-303 (1992).
    .. [EG1960] Erdős and Gallai, Mat. Lapok 11 264, 1960.
networkx.is_valid_degree_sequence_havel_hakimi
Python Library Documentation: function is_valid_degree_sequence_havel_hakimi in module networkx.algorithms.graphical

is_valid_degree_sequence_havel_hakimi(deg_sequence, *, backend=None, **backend_kwargs)
    Returns True if deg_sequence can be realized by a simple graph.

    The validation proceeds using the Havel-Hakimi theorem
    [havel1955]_, [hakimi1962]_, [CL1996]_.
    Worst-case run time is $O(s)$ where $s$ is the sum of the sequence.

    Parameters
    ----------
    deg_sequence : list
        A list of integers where each element specifies the degree of a node
        in a graph.

    Returns
    -------
    valid : bool
        True if deg_sequence is graphical and False if not.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (3, 4), (4, 2), (5, 1), (5, 4)])
    >>> sequence = (d for _, d in G.degree())
    >>> nx.is_valid_degree_sequence_havel_hakimi(sequence)
    True

    To test a non-valid sequence:
    >>> sequence_list = [d for _, d in G.degree()]
    >>> sequence_list[-1] += 1
    >>> nx.is_valid_degree_sequence_havel_hakimi(sequence_list)
    False

    Notes
    -----
    The ZZ condition says that for the sequence d if

    .. math::
        |d| >= \frac{(\max(d) + \min(d) + 1)^2}{4*\min(d)}

    then d is graphical.  This was shown in Theorem 6 in [1]_.

    References
    ----------
    .. [1] I.E. Zverovich and V.E. Zverovich. "Contributions to the theory
       of graphic sequences", Discrete Mathematics, 105, pp. 292-303 (1992).
    .. [havel1955] Havel, V. "A Remark on the Existence of Finite Graphs"
       Casopis Pest. Mat. 80, 477-480, 1955.
    .. [hakimi1962] Hakimi, S. "On the Realizability of a Set of Integers as
       Degrees of the Vertices of a Graph." SIAM J. Appl. Math. 10, 496-506, 1962.
    .. [CL1996] G. Chartrand and L. Lesniak, "Graphs and Digraphs",
       Chapman and Hall/CRC, 1996.
networkx.is_valid_directed_joint_degree
Python Library Documentation: function is_valid_directed_joint_degree in module networkx.generators.joint_degree_seq

is_valid_directed_joint_degree(in_degrees, out_degrees, nkk, *, backend=None, **backend_kwargs)
    Checks whether the given directed joint degree input is realizable

    Parameters
    ----------
    in_degrees :  list of integers
        in degree sequence contains the in degrees of nodes.
    out_degrees : list of integers
        out degree sequence contains the out degrees of nodes.
    nkk  :  dictionary of dictionary of integers
        directed joint degree dictionary. for nodes of out degree k (first
        level of dict) and nodes of in degree l (second level of dict)
        describes the number of edges.

    Returns
    -------
    boolean
        returns true if given input is realizable, else returns false.

    Notes
    -----
    Here is the list of conditions that the inputs (in/out degree sequences,
    nkk) need to satisfy for simple directed graph realizability:

    - Condition 0: in_degrees and out_degrees have the same length
    - Condition 1: nkk[k][l]  is integer for all k,l
    - Condition 2: sum(nkk[k])/k = number of nodes with partition id k, is an
                   integer and matching degree sequence
    - Condition 3: number of edges and non-chords between k and l cannot exceed
                   maximum possible number of edges


    References
    ----------
    [1] B. Tillman, A. Markopoulou, C. T. Butts & M. Gjoka,
        "Construction of Directed 2K Graphs". In Proc. of KDD 2017.
networkx.is_valid_joint_degree
Python Library Documentation: function is_valid_joint_degree in module networkx.generators.joint_degree_seq

is_valid_joint_degree(joint_degrees, *, backend=None, **backend_kwargs)
    Checks whether the given joint degree dictionary is realizable.

    A *joint degree dictionary* is a dictionary of dictionaries, in
    which entry ``joint_degrees[k][l]`` is an integer representing the
    number of edges joining nodes of degree *k* with nodes of degree
    *l*. Such a dictionary is realizable as a simple graph if and only
    if the following conditions are satisfied.

    - each entry must be an integer,
    - the total number of nodes of degree *k*, computed by
      ``sum(joint_degrees[k].values()) / k``, must be an integer,
    - the total number of edges joining nodes of degree *k* with
      nodes of degree *l* cannot exceed the total number of possible edges,
    - each diagonal entry ``joint_degrees[k][k]`` must be even (this is
      a convention assumed by the :func:`joint_degree_graph` function).


    Parameters
    ----------
    joint_degrees :  dictionary of dictionary of integers
        A joint degree dictionary in which entry ``joint_degrees[k][l]``
        is the number of edges joining nodes of degree *k* with nodes of
        degree *l*.

    Returns
    -------
    bool
        Whether the given joint degree dictionary is realizable as a
        simple graph.

    References
    ----------
    .. [1] M. Gjoka, M. Kurant, A. Markopoulou, "2.5K Graphs: from Sampling
       to Generation", IEEE Infocom, 2013.
    .. [2] I. Stanton, A. Pinar, "Constructing and sampling graphs with a
       prescribed joint degree distribution", Journal of Experimental
       Algorithmics, 2012.
networkx.is_weakly_connected
Python Library Documentation: function is_weakly_connected in module networkx.algorithms.components.weakly_connected

is_weakly_connected(G, *, backend=None, **backend_kwargs)
    Test directed graph for weak connectivity.

    A directed graph is weakly connected if and only if the graph
    is connected when the direction of the edge between nodes is ignored.

    Note that if a graph is strongly connected (i.e. the graph is connected
    even when we account for directionality), it is by definition weakly
    connected as well.

    Parameters
    ----------
    G : NetworkX Graph
        A directed graph.

    Returns
    -------
    connected : bool
        True if the graph is weakly connected, False otherwise.

    Raises
    ------
    NetworkXNotImplemented
        If G is undirected.

    Examples
    --------
    >>> G = nx.DiGraph([(0, 1), (2, 1)])
    >>> G.add_node(3)
    >>> nx.is_weakly_connected(G)  # node 3 is not connected to the graph
    False
    >>> G.add_edge(2, 3)
    >>> nx.is_weakly_connected(G)
    True

    See Also
    --------
    is_strongly_connected
    is_semiconnected
    is_connected
    is_biconnected
    weakly_connected_components

    Notes
    -----
    For directed graphs only.
networkx.is_weighted
Python Library Documentation: function is_weighted in module networkx.classes.function

is_weighted(G, edge=None, weight='weight')
    Returns True if `G` has weighted edges.

    Parameters
    ----------
    G : graph
        A NetworkX graph.

    edge : tuple, optional
        A 2-tuple specifying the only edge in `G` that will be tested. If
        None, then every edge in `G` is tested.

    weight: string, optional
        The attribute name used to query for edge weights.

    Returns
    -------
    bool
        A boolean signifying if `G`, or the specified edge, is weighted.

    Raises
    ------
    NetworkXError
        If the specified edge does not exist.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.is_weighted(G)
    False
    >>> nx.is_weighted(G, (2, 3))
    False

    >>> G = nx.DiGraph()
    >>> G.add_edge(1, 2, weight=1)
    >>> nx.is_weighted(G)
    True
networkx.isolate
Python Library Documentation: module networkx.algorithms.isolate in networkx.algorithms

NAME
    networkx.algorithms.isolate - Functions for identifying isolate (degree zero) nodes.

FUNCTIONS
    is_isolate(G, n, *, backend=None, **backend_kwargs)
        Determines whether a node is an isolate.

        An *isolate* is a node with no neighbors (that is, with degree
        zero). For directed graphs, this means no in-neighbors and no
        out-neighbors.

        Parameters
        ----------
        G : NetworkX graph

        n : node
            A node in `G`.

        Returns
        -------
        is_isolate : bool
           True if and only if `n` has no neighbors.

        Examples
        --------
        >>> G = nx.Graph()
        >>> G.add_edge(1, 2)
        >>> G.add_node(3)
        >>> nx.is_isolate(G, 2)
        False
        >>> nx.is_isolate(G, 3)
        True

    isolates(G, *, backend=None, **backend_kwargs)
        Iterator over isolates in the graph.

        An *isolate* is a node with no neighbors (that is, with degree
        zero). For directed graphs, this means no in-neighbors and no
        out-neighbors.

        Parameters
        ----------
        G : NetworkX graph

        Returns
        -------
        iterator
            An iterator over the isolates of `G`.

        Examples
        --------
        To get a list of all isolates of a graph, use the :class:`list`
        constructor::

            >>> G = nx.Graph()
            >>> G.add_edge(1, 2)
            >>> G.add_node(3)
            >>> list(nx.isolates(G))
            [3]

        To remove all isolates in the graph, first create a list of the
        isolates, then use :meth:`Graph.remove_nodes_from`::

            >>> G.remove_nodes_from(list(nx.isolates(G)))
            >>> list(G)
            [1, 2]

        For digraphs, isolates have zero in-degree and zero out_degre::

            >>> G = nx.DiGraph([(0, 1), (1, 2)])
            >>> G.add_node(3)
            >>> list(nx.isolates(G))
            [3]

    number_of_isolates(G, *, backend=None, **backend_kwargs)
        Returns the number of isolates in the graph.

        An *isolate* is a node with no neighbors (that is, with degree
        zero). For directed graphs, this means no in-neighbors and no
        out-neighbors.

        Parameters
        ----------
        G : NetworkX graph

        Returns
        -------
        int
            The number of degree zero nodes in the graph `G`.

DATA
    __all__ = ['is_isolate', 'isolates', 'number_of_isolates']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\isolate.py

networkx.isolates
Python Library Documentation: function isolates in module networkx.algorithms.isolate

isolates(G, *, backend=None, **backend_kwargs)
    Iterator over isolates in the graph.

    An *isolate* is a node with no neighbors (that is, with degree
    zero). For directed graphs, this means no in-neighbors and no
    out-neighbors.

    Parameters
    ----------
    G : NetworkX graph

    Returns
    -------
    iterator
        An iterator over the isolates of `G`.

    Examples
    --------
    To get a list of all isolates of a graph, use the :class:`list`
    constructor::

        >>> G = nx.Graph()
        >>> G.add_edge(1, 2)
        >>> G.add_node(3)
        >>> list(nx.isolates(G))
        [3]

    To remove all isolates in the graph, first create a list of the
    isolates, then use :meth:`Graph.remove_nodes_from`::

        >>> G.remove_nodes_from(list(nx.isolates(G)))
        >>> list(G)
        [1, 2]

    For digraphs, isolates have zero in-degree and zero out_degre::

        >>> G = nx.DiGraph([(0, 1), (1, 2)])
        >>> G.add_node(3)
        >>> list(nx.isolates(G))
        [3]
networkx.isomorphism
Python Library Documentation: package networkx.algorithms.isomorphism in networkx.algorithms

NAME
    networkx.algorithms.isomorphism

PACKAGE CONTENTS
    ismags
    isomorph
    isomorphvf2
    matchhelpers
    temporalisomorphvf2
    tests (package)
    tree_isomorphism
    vf2pp
    vf2userfunc

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\isomorphism\__init__.py

networkx.jaccard_coefficient
Python Library Documentation: function jaccard_coefficient in module networkx.algorithms.link_prediction

jaccard_coefficient(G, ebunch=None, *, backend=None, **backend_kwargs)
    Compute the Jaccard coefficient of all node pairs in ebunch.

    Jaccard coefficient of nodes `u` and `v` is defined as

    .. math::

        \frac{|\Gamma(u) \cap \Gamma(v)|}{|\Gamma(u) \cup \Gamma(v)|}

    where $\Gamma(u)$ denotes the set of neighbors of $u$.

    Parameters
    ----------
    G : graph
        A NetworkX undirected graph.

    ebunch : iterable of node pairs, optional (default = None)
        Jaccard coefficient will be computed for each pair of nodes
        given in the iterable. The pairs must be given as 2-tuples
        (u, v) where u and v are nodes in the graph. If ebunch is None
        then all nonexistent edges in the graph will be used.
        Default value: None.

    Returns
    -------
    piter : iterator
        An iterator of 3-tuples in the form (u, v, p) where (u, v) is a
        pair of nodes and p is their Jaccard coefficient.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a `DiGraph`, a `Multigraph` or a `MultiDiGraph`.

    NodeNotFound
        If `ebunch` has a node that is not in `G`.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> preds = nx.jaccard_coefficient(G, [(0, 1), (2, 3)])
    >>> for u, v, p in preds:
    ...     print(f"({u}, {v}) -> {p:.8f}")
    (0, 1) -> 0.60000000
    (2, 3) -> 0.60000000

    References
    ----------
    .. [1] D. Liben-Nowell, J. Kleinberg.
           The Link Prediction Problem for Social Networks (2004).
           http://www.cs.cornell.edu/home/kleinber/link-pred.pdf
networkx.johnson
Python Library Documentation: function johnson in module networkx.algorithms.shortest_paths.weighted

johnson(G, weight='weight', *, backend=None, **backend_kwargs)
    Uses Johnson's Algorithm to compute shortest paths.

    Johnson's Algorithm finds a shortest path between each pair of
    nodes in a weighted graph even if negative weights are present.

    Parameters
    ----------
    G : NetworkX graph

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

    Returns
    -------
    distance : dictionary
        Dictionary, keyed by source and target, of shortest paths.

    Examples
    --------
    >>> graph = nx.DiGraph()
    >>> graph.add_weighted_edges_from(
    ...     [("0", "3", 3), ("0", "1", -5), ("0", "2", 2), ("1", "2", 4), ("2", "3", 1)]
    ... )
    >>> paths = nx.johnson(graph, weight="weight")
    >>> paths["0"]["2"]
    ['0', '1', '2']

    Notes
    -----
    Johnson's algorithm is suitable even for graphs with negative weights. It
    works by using the Bellman–Ford algorithm to compute a transformation of
    the input graph that removes all negative weights, allowing Dijkstra's
    algorithm to be used on the transformed graph.

    The time complexity of this algorithm is $O(n^2 \log n + n m)$,
    where $n$ is the number of nodes and $m$ the number of edges in the
    graph. For dense graphs, this may be faster than the Floyd–Warshall
    algorithm.

    See Also
    --------
    floyd_warshall_predecessor_and_distance
    floyd_warshall_numpy
    all_pairs_shortest_path
    all_pairs_shortest_path_length
    all_pairs_dijkstra_path
    bellman_ford_predecessor_and_distance
    all_pairs_bellman_ford_path
    all_pairs_bellman_ford_path_length
networkx.join_trees
Python Library Documentation: function join_trees in module networkx.algorithms.tree.operations

join_trees(rooted_trees, *, label_attribute=None, first_label=0, backend=None, **backend_kwargs)
    Returns a new rooted tree made by joining `rooted_trees`

    Constructs a new tree by joining each tree in `rooted_trees`.
    A new root node is added and connected to each of the roots
    of the input trees. While copying the nodes from the trees,
    relabeling to integers occurs. If the `label_attribute` is provided,
    the old node labels will be stored in the new tree under this attribute.

    Parameters
    ----------
    rooted_trees : list
        A list of pairs in which each left element is a NetworkX graph
        object representing a tree and each right element is the root
        node of that tree. The nodes of these trees will be relabeled to
        integers.

    label_attribute : str
        If provided, the old node labels will be stored in the new tree
        under this node attribute. If not provided, the original labels
        of the nodes in the input trees are not stored.

    first_label : int, optional (default=0)
        Specifies the label for the new root node. If provided, the root node of the joined tree
        will have this label. If not provided, the root node will default to a label of 0.

    Returns
    -------
    NetworkX graph
        The rooted tree resulting from joining the provided `rooted_trees`. The new tree has a root node
        labeled as specified by `first_label` (defaulting to 0 if not provided). Subtrees from the input
        `rooted_trees` are attached to this new root node. Each non-root node, if the `label_attribute`
        is provided, has an attribute that indicates the original label of the node in the input tree.

    Notes
    -----
    Trees are stored in NetworkX as NetworkX Graphs. There is no specific
    enforcement of the fact that these are trees. Testing for each tree
    can be done using :func:`networkx.is_tree`.

    Graph, edge, and node attributes are propagated from the given
    rooted trees to the created tree. If there are any overlapping graph
    attributes, those from later trees will overwrite those from earlier
    trees in the tuple of positional arguments.

    Examples
    --------
    Join two full balanced binary trees of height *h* to get a full
    balanced binary tree of depth *h* + 1::

        >>> h = 4
        >>> left = nx.balanced_tree(2, h)
        >>> right = nx.balanced_tree(2, h)
        >>> joined_tree = nx.join_trees([(left, 0), (right, 0)])
        >>> nx.is_isomorphic(joined_tree, nx.balanced_tree(2, h + 1))
        True
networkx.joint_degree_graph
Python Library Documentation: function joint_degree_graph in module networkx.generators.joint_degree_seq

joint_degree_graph(joint_degrees, seed=None, *, backend=None, **backend_kwargs)
    Generates a random simple graph with the given joint degree dictionary.

    Parameters
    ----------
    joint_degrees :  dictionary of dictionary of integers
        A joint degree dictionary in which entry ``joint_degrees[k][l]`` is the
        number of edges joining nodes of degree *k* with nodes of degree *l*.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : Graph
        A graph with the specified joint degree dictionary.

    Raises
    ------
    NetworkXError
        If *joint_degrees* dictionary is not realizable.

    Notes
    -----
    In each iteration of the "while loop" the algorithm picks two disconnected
    nodes *v* and *w*, of degree *k* and *l* correspondingly,  for which
    ``joint_degrees[k][l]`` has not reached its target yet. It then adds
    edge (*v*, *w*) and increases the number of edges in graph G by one.

    The intelligence of the algorithm lies in the fact that  it is always
    possible to add an edge between such disconnected nodes *v* and *w*,
    even if one or both nodes do not have free stubs. That is made possible by
    executing a "neighbor switch", an edge rewiring move that releases
    a free stub while keeping the joint degree of G the same.

    The algorithm continues for E (number of edges) iterations of
    the "while loop", at the which point all entries of the given
    ``joint_degrees[k][l]`` have reached their target values and the
    construction is complete.

    References
    ----------
    ..  [1] M. Gjoka, B. Tillman, A. Markopoulou, "Construction of Simple
        Graphs with a Target Joint Degree Matrix and Beyond", IEEE Infocom, '15

    Examples
    --------
    >>> joint_degrees = {
    ...     1: {4: 1},
    ...     2: {2: 2, 3: 2, 4: 2},
    ...     3: {2: 2, 4: 1},
    ...     4: {1: 1, 2: 2, 3: 1},
    ... }
    >>> G = nx.joint_degree_graph(joint_degrees)
    >>>
networkx.joint_degree_seq
Python Library Documentation: module networkx.generators.joint_degree_seq in networkx.generators

NAME
    networkx.generators.joint_degree_seq - Generate graphs with a given joint degree and directed joint degree

FUNCTIONS
    directed_joint_degree_graph(in_degrees, out_degrees, nkk, seed=None, *, backend=None, **backend_kwargs)
        Generates a random simple directed graph with the joint degree.

        Parameters
        ----------
        degree_seq :  list of tuples (of size 3)
            degree sequence contains tuples of nodes with node id, in degree and
            out degree.
        nkk  :  dictionary of dictionary of integers
            directed joint degree dictionary, for nodes of out degree k (first
            level of dict) and nodes of in degree l (second level of dict)
            describes the number of edges.
        seed : hashable object, optional
            Seed for random number generator.

        Returns
        -------
        G : Graph
            A directed graph with the specified inputs.

        Raises
        ------
        NetworkXError
            If degree_seq and nkk are not realizable as a simple directed graph.


        Notes
        -----
        Similarly to the undirected version:
        In each iteration of the "while loop" the algorithm picks two disconnected
        nodes v and w, of degree k and l correspondingly,  for which nkk[k][l] has
        not reached its target yet i.e. (for given k,l): n_edges_add < nkk[k][l].
        It then adds edge (v,w) and always increases the number of edges in graph G
        by one.

        The intelligence of the algorithm lies in the fact that  it is always
        possible to add an edge between disconnected nodes v and w, for which
        nkk[degree(v)][degree(w)] has not reached its target, even if one or both
        nodes do not have free stubs. If either node v or w does not have a free
        stub, we perform a "neighbor switch", an edge rewiring move that releases a
        free stub while keeping nkk the same.

        The difference for the directed version lies in the fact that neighbor
        switches might not be able to rewire, but in these cases unsaturated nodes
        can be reassigned to use instead, see [1] for detailed description and
        proofs.

        The algorithm continues for E (number of edges in the graph) iterations of
        the "while loop", at which point all entries of the given nkk[k][l] have
        reached their target values and the construction is complete.

        References
        ----------
        [1] B. Tillman, A. Markopoulou, C. T. Butts & M. Gjoka,
            "Construction of Directed 2K Graphs". In Proc. of KDD 2017.

        Examples
        --------
        >>> in_degrees = [0, 1, 1, 2]
        >>> out_degrees = [1, 1, 1, 1]
        >>> nkk = {1: {1: 2, 2: 2}}
        >>> G = nx.directed_joint_degree_graph(in_degrees, out_degrees, nkk)
        >>>

    is_valid_directed_joint_degree(in_degrees, out_degrees, nkk, *, backend=None, **backend_kwargs)
        Checks whether the given directed joint degree input is realizable

        Parameters
        ----------
        in_degrees :  list of integers
            in degree sequence contains the in degrees of nodes.
        out_degrees : list of integers
            out degree sequence contains the out degrees of nodes.
        nkk  :  dictionary of dictionary of integers
            directed joint degree dictionary. for nodes of out degree k (first
            level of dict) and nodes of in degree l (second level of dict)
            describes the number of edges.

        Returns
        -------
        boolean
            returns true if given input is realizable, else returns false.

        Notes
        -----
        Here is the list of conditions that the inputs (in/out degree sequences,
        nkk) need to satisfy for simple directed graph realizability:

        - Condition 0: in_degrees and out_degrees have the same length
        - Condition 1: nkk[k][l]  is integer for all k,l
        - Condition 2: sum(nkk[k])/k = number of nodes with partition id k, is an
                       integer and matching degree sequence
        - Condition 3: number of edges and non-chords between k and l cannot exceed
                       maximum possible number of edges


        References
        ----------
        [1] B. Tillman, A. Markopoulou, C. T. Butts & M. Gjoka,
            "Construction of Directed 2K Graphs". In Proc. of KDD 2017.

    is_valid_joint_degree(joint_degrees, *, backend=None, **backend_kwargs)
        Checks whether the given joint degree dictionary is realizable.

        A *joint degree dictionary* is a dictionary of dictionaries, in
        which entry ``joint_degrees[k][l]`` is an integer representing the
        number of edges joining nodes of degree *k* with nodes of degree
        *l*. Such a dictionary is realizable as a simple graph if and only
        if the following conditions are satisfied.

        - each entry must be an integer,
        - the total number of nodes of degree *k*, computed by
          ``sum(joint_degrees[k].values()) / k``, must be an integer,
        - the total number of edges joining nodes of degree *k* with
          nodes of degree *l* cannot exceed the total number of possible edges,
        - each diagonal entry ``joint_degrees[k][k]`` must be even (this is
          a convention assumed by the :func:`joint_degree_graph` function).


        Parameters
        ----------
        joint_degrees :  dictionary of dictionary of integers
            A joint degree dictionary in which entry ``joint_degrees[k][l]``
            is the number of edges joining nodes of degree *k* with nodes of
            degree *l*.

        Returns
        -------
        bool
            Whether the given joint degree dictionary is realizable as a
            simple graph.

        References
        ----------
        .. [1] M. Gjoka, M. Kurant, A. Markopoulou, "2.5K Graphs: from Sampling
           to Generation", IEEE Infocom, 2013.
        .. [2] I. Stanton, A. Pinar, "Constructing and sampling graphs with a
           prescribed joint degree distribution", Journal of Experimental
           Algorithmics, 2012.

    joint_degree_graph(joint_degrees, seed=None, *, backend=None, **backend_kwargs)
        Generates a random simple graph with the given joint degree dictionary.

        Parameters
        ----------
        joint_degrees :  dictionary of dictionary of integers
            A joint degree dictionary in which entry ``joint_degrees[k][l]`` is the
            number of edges joining nodes of degree *k* with nodes of degree *l*.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        G : Graph
            A graph with the specified joint degree dictionary.

        Raises
        ------
        NetworkXError
            If *joint_degrees* dictionary is not realizable.

        Notes
        -----
        In each iteration of the "while loop" the algorithm picks two disconnected
        nodes *v* and *w*, of degree *k* and *l* correspondingly,  for which
        ``joint_degrees[k][l]`` has not reached its target yet. It then adds
        edge (*v*, *w*) and increases the number of edges in graph G by one.

        The intelligence of the algorithm lies in the fact that  it is always
        possible to add an edge between such disconnected nodes *v* and *w*,
        even if one or both nodes do not have free stubs. That is made possible by
        executing a "neighbor switch", an edge rewiring move that releases
        a free stub while keeping the joint degree of G the same.

        The algorithm continues for E (number of edges) iterations of
        the "while loop", at the which point all entries of the given
        ``joint_degrees[k][l]`` have reached their target values and the
        construction is complete.

        References
        ----------
        ..  [1] M. Gjoka, B. Tillman, A. Markopoulou, "Construction of Simple
            Graphs with a Target Joint Degree Matrix and Beyond", IEEE Infocom, '15

        Examples
        --------
        >>> joint_degrees = {
        ...     1: {4: 1},
        ...     2: {2: 2, 3: 2, 4: 2},
        ...     3: {2: 2, 4: 1},
        ...     4: {1: 1, 2: 2, 3: 1},
        ... }
        >>> G = nx.joint_degree_graph(joint_degrees)
        >>>

DATA
    __all__ = ['is_valid_joint_degree', 'is_valid_directed_joint_degree', ...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\joint_degree_seq.py

networkx.json_graph
Python Library Documentation: package networkx.readwrite.json_graph in networkx.readwrite

NAME
    networkx.readwrite.json_graph

DESCRIPTION
    *********
    JSON data
    *********
    Generate and parse JSON serializable data for NetworkX graphs.

    These formats are suitable for use with the d3.js examples https://d3js.org/

    The three formats that you can generate with NetworkX are:

     - node-link like in the d3.js example https://bl.ocks.org/mbostock/4062045
     - tree like in the d3.js example https://bl.ocks.org/mbostock/4063550
     - adjacency like in the d3.js example https://bost.ocks.org/mike/miserables/

PACKAGE CONTENTS
    adjacency
    cytoscape
    node_link
    tests (package)
    tree

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\json_graph\__init__.py

networkx.junction_tree
Python Library Documentation: function junction_tree in module networkx.algorithms.tree.decomposition

junction_tree(G, *, backend=None, **backend_kwargs)
    Returns a junction tree of a given graph.

    A junction tree (or clique tree) is constructed from a (un)directed graph G.
    The tree is constructed based on a moralized and triangulated version of G.
    The tree's nodes consist of maximal cliques and sepsets of the revised graph.
    The sepset of two cliques is the intersection of the nodes of these cliques,
    e.g. the sepset of (A,B,C) and (A,C,E,F) is (A,C). These nodes are often called
    "variables" in this literature. The tree is bipartite with each sepset
    connected to its two cliques.

    Junction Trees are not unique as the order of clique consideration determines
    which sepsets are included.

    The junction tree algorithm consists of five steps [1]_:

    1. Moralize the graph
    2. Triangulate the graph
    3. Find maximal cliques
    4. Build the tree from cliques, connecting cliques with shared
       nodes, set edge-weight to number of shared variables
    5. Find maximum spanning tree


    Parameters
    ----------
    G : networkx.Graph
        Directed or undirected graph.

    Returns
    -------
    junction_tree : networkx.Graph
        The corresponding junction tree of `G`.

    Raises
    ------
    NetworkXNotImplemented
        Raised if `G` is an instance of `MultiGraph` or `MultiDiGraph`.

    References
    ----------
    .. [1] Junction tree algorithm:
       https://en.wikipedia.org/wiki/Junction_tree_algorithm

    .. [2] Finn V. Jensen and Frank Jensen. 1994. Optimal
       junction trees. In Proceedings of the Tenth international
       conference on Uncertainty in artificial intelligence (UAI’94).
       Morgan Kaufmann Publishers Inc., San Francisco, CA, USA, 360–366.
networkx.k_components
Python Library Documentation: function k_components in module networkx.algorithms.connectivity.kcomponents

k_components(G, flow_func=None, *, backend=None, **backend_kwargs)
    Returns the k-component structure of a graph G.

    A `k`-component is a maximal subgraph of a graph G that has, at least,
    node connectivity `k`: we need to remove at least `k` nodes to break it
    into more components. `k`-components have an inherent hierarchical
    structure because they are nested in terms of connectivity: a connected
    graph can contain several 2-components, each of which can contain
    one or more 3-components, and so forth.

    Parameters
    ----------
    G : NetworkX graph

    flow_func : function
        Function to perform the underlying flow computations. Default value
        :meth:`edmonds_karp`. This function performs better in sparse graphs with
        right tailed degree distributions. :meth:`shortest_augmenting_path` will
        perform better in denser graphs.

    Returns
    -------
    k_components : dict
        Dictionary with all connectivity levels `k` in the input Graph as keys
        and a list of sets of nodes that form a k-component of level `k` as
        values.

    Raises
    ------
    NetworkXNotImplemented
        If the input graph is directed.

    Examples
    --------
    >>> # Petersen graph has 10 nodes and it is triconnected, thus all
    >>> # nodes are in a single component on all three connectivity levels
    >>> G = nx.petersen_graph()
    >>> k_components = nx.k_components(G)

    Notes
    -----
    Moody and White [1]_ (appendix A) provide an algorithm for identifying
    k-components in a graph, which is based on Kanevsky's algorithm [2]_
    for finding all minimum-size node cut-sets of a graph (implemented in
    :meth:`all_node_cuts` function):

        1. Compute node connectivity, k, of the input graph G.

        2. Identify all k-cutsets at the current level of connectivity using
           Kanevsky's algorithm.

        3. Generate new graph components based on the removal of
           these cutsets. Nodes in a cutset belong to both sides
           of the induced cut.

        4. If the graph is neither complete nor trivial, return to 1;
           else end.

    This implementation also uses some heuristics (see [3]_ for details)
    to speed up the computation.

    See also
    --------
    node_connectivity
    all_node_cuts
    biconnected_components : special case of this function when k=2
    k_edge_components : similar to this function, but uses edge-connectivity
        instead of node-connectivity

    References
    ----------
    .. [1]  Moody, J. and D. White (2003). Social cohesion and embeddedness:
            A hierarchical conception of social groups.
            American Sociological Review 68(1), 103--28.
            http://www2.asanet.org/journals/ASRFeb03MoodyWhite.pdf

    .. [2]  Kanevsky, A. (1993). Finding all minimum-size separating vertex
            sets in a graph. Networks 23(6), 533--541.
            http://onlinelibrary.wiley.com/doi/10.1002/net.3230230604/abstract

    .. [3]  Torrents, J. and F. Ferraro (2015). Structural Cohesion:
            Visualization and Heuristics for Fast Computation.
            https://arxiv.org/pdf/1503.04476v1
networkx.k_core
Python Library Documentation: function k_core in module networkx.algorithms.core

k_core(G, k=None, core_number=None, *, backend=None, **backend_kwargs)
    Returns the k-core of G.

    A k-core is a maximal subgraph that contains nodes of degree `k` or more.

    .. deprecated:: 3.3
       `k_core` will not accept `MultiGraph` objects in version 3.5.

    Parameters
    ----------
    G : NetworkX graph
      A graph or directed graph
    k : int, optional
      The order of the core. If not specified return the main core.
    core_number : dictionary, optional
      Precomputed core numbers for the graph G.

    Returns
    -------
    G : NetworkX graph
      The k-core subgraph

    Raises
    ------
    NetworkXNotImplemented
      The k-core is not defined for multigraphs or graphs with self loops.

    Notes
    -----
    The main core is the core with `k` as the largest core_number.

    For directed graphs the node degree is defined to be the
    in-degree + out-degree.

    Graph, node, and edge attributes are copied to the subgraph.

    Examples
    --------
    >>> degrees = [0, 1, 2, 2, 2, 2, 3]
    >>> H = nx.havel_hakimi_graph(degrees)
    >>> H.degree
    DegreeView({0: 1, 1: 2, 2: 2, 3: 2, 4: 2, 5: 3, 6: 0})
    >>> nx.k_core(H).nodes
    NodeView((1, 2, 3, 5))

    See Also
    --------
    core_number

    References
    ----------
    .. [1] An O(m) Algorithm for Cores Decomposition of Networks
       Vladimir Batagelj and Matjaz Zaversnik,  2003.
       https://arxiv.org/abs/cs.DS/0310049
networkx.k_corona
Python Library Documentation: function k_corona in module networkx.algorithms.core

k_corona(G, k, core_number=None, *, backend=None, **backend_kwargs)
    Returns the k-corona of G.

    The k-corona is the subgraph of nodes in the k-core which have
    exactly k neighbors in the k-core.

    .. deprecated:: 3.3
       `k_corona` will not accept `MultiGraph` objects in version 3.5.

    Parameters
    ----------
    G : NetworkX graph
       A graph or directed graph
    k : int
       The order of the corona.
    core_number : dictionary, optional
       Precomputed core numbers for the graph G.

    Returns
    -------
    G : NetworkX graph
       The k-corona subgraph

    Raises
    ------
    NetworkXNotImplemented
        The k-corona is not defined for multigraphs or graphs with self loops.

    Notes
    -----
    For directed graphs the node degree is defined to be the
    in-degree + out-degree.

    Graph, node, and edge attributes are copied to the subgraph.

    Examples
    --------
    >>> degrees = [0, 1, 2, 2, 2, 2, 3]
    >>> H = nx.havel_hakimi_graph(degrees)
    >>> H.degree
    DegreeView({0: 1, 1: 2, 2: 2, 3: 2, 4: 2, 5: 3, 6: 0})
    >>> nx.k_corona(H, k=2).nodes
    NodeView((1, 2, 3, 5))

    See Also
    --------
    core_number

    References
    ----------
    .. [1]  k -core (bootstrap) percolation on complex networks:
       Critical phenomena and nonlocal effects,
       A. V. Goltsev, S. N. Dorogovtsev, and J. F. F. Mendes,
       Phys. Rev. E 73, 056101 (2006)
       http://link.aps.org/doi/10.1103/PhysRevE.73.056101
networkx.k_crust
Python Library Documentation: function k_crust in module networkx.algorithms.core

k_crust(G, k=None, core_number=None, *, backend=None, **backend_kwargs)
    Returns the k-crust of G.

    The k-crust is the graph G with the edges of the k-core removed
    and isolated nodes found after the removal of edges are also removed.

    .. deprecated:: 3.3
       `k_crust` will not accept `MultiGraph` objects in version 3.5.

    Parameters
    ----------
    G : NetworkX graph
       A graph or directed graph.
    k : int, optional
      The order of the shell. If not specified return the main crust.
    core_number : dictionary, optional
      Precomputed core numbers for the graph G.

    Returns
    -------
    G : NetworkX graph
       The k-crust subgraph

    Raises
    ------
    NetworkXNotImplemented
        The k-crust is not implemented for multigraphs or graphs with self loops.

    Notes
    -----
    This definition of k-crust is different than the definition in [1]_.
    The k-crust in [1]_ is equivalent to the k+1 crust of this algorithm.

    For directed graphs the node degree is defined to be the
    in-degree + out-degree.

    Graph, node, and edge attributes are copied to the subgraph.

    Examples
    --------
    >>> degrees = [0, 1, 2, 2, 2, 2, 3]
    >>> H = nx.havel_hakimi_graph(degrees)
    >>> H.degree
    DegreeView({0: 1, 1: 2, 2: 2, 3: 2, 4: 2, 5: 3, 6: 0})
    >>> nx.k_crust(H, k=1).nodes
    NodeView((0, 4, 6))

    See Also
    --------
    core_number

    References
    ----------
    .. [1] A model of Internet topology using k-shell decomposition
       Shai Carmi, Shlomo Havlin, Scott Kirkpatrick, Yuval Shavitt,
       and Eran Shir, PNAS  July 3, 2007   vol. 104  no. 27  11150-11154
       http://www.pnas.org/content/104/27/11150.full
networkx.k_edge_augmentation
Python Library Documentation: function k_edge_augmentation in module networkx.algorithms.connectivity.edge_augmentation

k_edge_augmentation(G, k, avail=None, weight=None, partial=False, *, backend=None, **backend_kwargs)
    Finds set of edges to k-edge-connect G.

    Adding edges from the augmentation to G make it impossible to disconnect G
    unless k or more edges are removed. This function uses the most efficient
    function available (depending on the value of k and if the problem is
    weighted or unweighted) to search for a minimum weight subset of available
    edges that k-edge-connects G. In general, finding a k-edge-augmentation is
    NP-hard, so solutions are not guaranteed to be minimal. Furthermore, a
    k-edge-augmentation may not exist.

    Parameters
    ----------
    G : NetworkX graph
       An undirected graph.

    k : integer
        Desired edge connectivity

    avail : dict or a set of 2 or 3 tuples
        The available edges that can be used in the augmentation.

        If unspecified, then all edges in the complement of G are available.
        Otherwise, each item is an available edge (with an optional weight).

        In the unweighted case, each item is an edge ``(u, v)``.

        In the weighted case, each item is a 3-tuple ``(u, v, d)`` or a dict
        with items ``(u, v): d``.  The third item, ``d``, can be a dictionary
        or a real number.  If ``d`` is a dictionary ``d[weight]``
        correspondings to the weight.

    weight : string
        key to use to find weights if ``avail`` is a set of 3-tuples where the
        third item in each tuple is a dictionary.

    partial : boolean
        If partial is True and no feasible k-edge-augmentation exists, then all
        a partial k-edge-augmentation is generated. Adding the edges in a
        partial augmentation to G, minimizes the number of k-edge-connected
        components and maximizes the edge connectivity between those
        components. For details, see :func:`partial_k_edge_augmentation`.

    Yields
    ------
    edge : tuple
        Edges that, once added to G, would cause G to become k-edge-connected.
        If partial is False, an error is raised if this is not possible.
        Otherwise, generated edges form a partial augmentation, which
        k-edge-connects any part of G where it is possible, and maximally
        connects the remaining parts.

    Raises
    ------
    NetworkXUnfeasible
        If partial is False and no k-edge-augmentation exists.

    NetworkXNotImplemented
        If the input graph is directed or a multigraph.

    ValueError:
        If k is less than 1

    Notes
    -----
    When k=1 this returns an optimal solution.

    When k=2 and ``avail`` is None, this returns an optimal solution.
    Otherwise when k=2, this returns a 2-approximation of the optimal solution.

    For k>3, this problem is NP-hard and this uses a randomized algorithm that
        produces a feasible solution, but provides no guarantees on the
        solution weight.

    Examples
    --------
    >>> # Unweighted cases
    >>> G = nx.path_graph((1, 2, 3, 4))
    >>> G.add_node(5)
    >>> sorted(nx.k_edge_augmentation(G, k=1))
    [(1, 5)]
    >>> sorted(nx.k_edge_augmentation(G, k=2))
    [(1, 5), (5, 4)]
    >>> sorted(nx.k_edge_augmentation(G, k=3))
    [(1, 4), (1, 5), (2, 5), (3, 5), (4, 5)]
    >>> complement = list(nx.k_edge_augmentation(G, k=5, partial=True))
    >>> G.add_edges_from(complement)
    >>> nx.edge_connectivity(G)
    4

    >>> # Weighted cases
    >>> G = nx.path_graph((1, 2, 3, 4))
    >>> G.add_node(5)
    >>> # avail can be a tuple with a dict
    >>> avail = [(1, 5, {"weight": 11}), (2, 5, {"weight": 10})]
    >>> sorted(nx.k_edge_augmentation(G, k=1, avail=avail, weight="weight"))
    [(2, 5)]
    >>> # or avail can be a 3-tuple with a real number
    >>> avail = [(1, 5, 11), (2, 5, 10), (4, 3, 1), (4, 5, 51)]
    >>> sorted(nx.k_edge_augmentation(G, k=2, avail=avail))
    [(1, 5), (2, 5), (4, 5)]
    >>> # or avail can be a dict
    >>> avail = {(1, 5): 11, (2, 5): 10, (4, 3): 1, (4, 5): 51}
    >>> sorted(nx.k_edge_augmentation(G, k=2, avail=avail))
    [(1, 5), (2, 5), (4, 5)]
    >>> # If augmentation is infeasible, then a partial solution can be found
    >>> avail = {(1, 5): 11}
    >>> sorted(nx.k_edge_augmentation(G, k=2, avail=avail, partial=True))
    [(1, 5)]
networkx.k_edge_components
Python Library Documentation: function k_edge_components in module networkx.algorithms.connectivity.edge_kcomponents

k_edge_components(G, k, *, backend=None, **backend_kwargs)
    Generates nodes in each maximal k-edge-connected component in G.

    Parameters
    ----------
    G : NetworkX graph

    k : Integer
        Desired edge connectivity

    Returns
    -------
    k_edge_components : a generator of k-edge-ccs. Each set of returned nodes
       will have k-edge-connectivity in the graph G.

    See Also
    --------
    :func:`local_edge_connectivity`
    :func:`k_edge_subgraphs` : similar to this function, but the subgraph
        defined by the nodes must also have k-edge-connectivity.
    :func:`k_components` : similar to this function, but uses node-connectivity
        instead of edge-connectivity

    Raises
    ------
    NetworkXNotImplemented
        If the input graph is a multigraph.

    ValueError:
        If k is less than 1

    Notes
    -----
    Attempts to use the most efficient implementation available based on k.
    If k=1, this is simply connected components for directed graphs and
    connected components for undirected graphs.
    If k=2 on an efficient bridge connected component algorithm from _[1] is
    run based on the chain decomposition.
    Otherwise, the algorithm from _[2] is used.

    Examples
    --------
    >>> import itertools as it
    >>> from networkx.utils import pairwise
    >>> paths = [
    ...     (1, 2, 4, 3, 1, 4),
    ...     (5, 6, 7, 8, 5, 7, 8, 6),
    ... ]
    >>> G = nx.Graph()
    >>> G.add_nodes_from(it.chain(*paths))
    >>> G.add_edges_from(it.chain(*[pairwise(path) for path in paths]))
    >>> # note this returns {1, 4} unlike k_edge_subgraphs
    >>> sorted(map(sorted, nx.k_edge_components(G, k=3)))
    [[1, 4], [2], [3], [5, 6, 7, 8]]

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Bridge_%28graph_theory%29
    .. [2] Wang, Tianhao, et al. (2015) A simple algorithm for finding all
        k-edge-connected components.
        http://journals.plos.org/plosone/article?id=10.1371/journal.pone.0136264
networkx.k_edge_subgraphs
Python Library Documentation: function k_edge_subgraphs in module networkx.algorithms.connectivity.edge_kcomponents

k_edge_subgraphs(G, k, *, backend=None, **backend_kwargs)
    Generates nodes in each maximal k-edge-connected subgraph in G.

    Parameters
    ----------
    G : NetworkX graph

    k : Integer
        Desired edge connectivity

    Returns
    -------
    k_edge_subgraphs : a generator of k-edge-subgraphs
        Each k-edge-subgraph is a maximal set of nodes that defines a subgraph
        of G that is k-edge-connected.

    See Also
    --------
    :func:`edge_connectivity`
    :func:`k_edge_components` : similar to this function, but nodes only
        need to have k-edge-connectivity within the graph G and the subgraphs
        might not be k-edge-connected.

    Raises
    ------
    NetworkXNotImplemented
        If the input graph is a multigraph.

    ValueError:
        If k is less than 1

    Notes
    -----
    Attempts to use the most efficient implementation available based on k.
    If k=1, or k=2 and the graph is undirected, then this simply calls
    `k_edge_components`.  Otherwise the algorithm from _[1] is used.

    Examples
    --------
    >>> import itertools as it
    >>> from networkx.utils import pairwise
    >>> paths = [
    ...     (1, 2, 4, 3, 1, 4),
    ...     (5, 6, 7, 8, 5, 7, 8, 6),
    ... ]
    >>> G = nx.Graph()
    >>> G.add_nodes_from(it.chain(*paths))
    >>> G.add_edges_from(it.chain(*[pairwise(path) for path in paths]))
    >>> # note this does not return {1, 4} unlike k_edge_components
    >>> sorted(map(sorted, nx.k_edge_subgraphs(G, k=3)))
    [[1], [2], [3], [4], [5, 6, 7, 8]]

    References
    ----------
    .. [1] Zhou, Liu, et al. (2012) Finding maximal k-edge-connected subgraphs
        from a large graph.  ACM International Conference on Extending Database
        Technology 2012 480-–491.
        https://openproceedings.org/2012/conf/edbt/ZhouLYLCL12.pdf
networkx.k_factor
Python Library Documentation: function k_factor in module networkx.algorithms.regular

k_factor(G, k, matching_weight='weight', *, backend=None, **backend_kwargs)
    Compute a k-factor of G

    A k-factor of a graph is a spanning k-regular subgraph.
    A spanning k-regular subgraph of G is a subgraph that contains
    each vertex of G and a subset of the edges of G such that each
    vertex has degree k.

    Parameters
    ----------
    G : NetworkX graph
      Undirected graph

    matching_weight: string, optional (default='weight')
       Edge data key corresponding to the edge weight.
       Used for finding the max-weighted perfect matching.
       If key not found, uses 1 as weight.

    Returns
    -------
    G2 : NetworkX graph
        A k-factor of G

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (2, 3), (3, 4), (4, 1)])
    >>> G2 = nx.k_factor(G, k=1)
    >>> G2.edges()
    EdgeView([(1, 2), (3, 4)])

    References
    ----------
    .. [1] "An algorithm for computing simple k-factors.",
       Meijer, Henk, Yurai Núñez-Rodríguez, and David Rappaport,
       Information processing letters, 2009.
networkx.k_random_intersection_graph
Python Library Documentation: function k_random_intersection_graph in module networkx.generators.intersection

k_random_intersection_graph(n, m, k, seed=None, *, backend=None, **backend_kwargs)
    Returns a intersection graph with randomly chosen attribute sets for
    each node that are of equal size (k).

    Parameters
    ----------
    n : int
        The number of nodes in the first bipartite set (nodes)
    m : int
        The number of nodes in the second bipartite set (attributes)
    k : float
        Size of attribute set to assign to each node.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    See Also
    --------
    gnp_random_graph, uniform_random_intersection_graph

    References
    ----------
    .. [1] Godehardt, E., and Jaworski, J.
       Two models of random intersection graphs and their applications.
       Electronic Notes in Discrete Mathematics 10 (2001), 129--132.
networkx.k_shell
Python Library Documentation: function k_shell in module networkx.algorithms.core

k_shell(G, k=None, core_number=None, *, backend=None, **backend_kwargs)
    Returns the k-shell of G.

    The k-shell is the subgraph induced by nodes with core number k.
    That is, nodes in the k-core that are not in the (k+1)-core.

    .. deprecated:: 3.3
       `k_shell` will not accept `MultiGraph` objects in version 3.5.

    Parameters
    ----------
    G : NetworkX graph
      A graph or directed graph.
    k : int, optional
      The order of the shell. If not specified return the outer shell.
    core_number : dictionary, optional
      Precomputed core numbers for the graph G.


    Returns
    -------
    G : NetworkX graph
       The k-shell subgraph

    Raises
    ------
    NetworkXNotImplemented
        The k-shell is not implemented for multigraphs or graphs with self loops.

    Notes
    -----
    This is similar to k_corona but in that case only neighbors in the
    k-core are considered.

    For directed graphs the node degree is defined to be the
    in-degree + out-degree.

    Graph, node, and edge attributes are copied to the subgraph.

    Examples
    --------
    >>> degrees = [0, 1, 2, 2, 2, 2, 3]
    >>> H = nx.havel_hakimi_graph(degrees)
    >>> H.degree
    DegreeView({0: 1, 1: 2, 2: 2, 3: 2, 4: 2, 5: 3, 6: 0})
    >>> nx.k_shell(H, k=1).nodes
    NodeView((0, 4))

    See Also
    --------
    core_number
    k_corona


    References
    ----------
    .. [1] A model of Internet topology using k-shell decomposition
       Shai Carmi, Shlomo Havlin, Scott Kirkpatrick, Yuval Shavitt,
       and Eran Shir, PNAS  July 3, 2007   vol. 104  no. 27  11150-11154
       http://www.pnas.org/content/104/27/11150.full
networkx.k_truss
Python Library Documentation: function k_truss in module networkx.algorithms.core

k_truss(G, k, *, backend=None, **backend_kwargs)
    Returns the k-truss of `G`.

    The k-truss is the maximal induced subgraph of `G` which contains at least
    three vertices where every edge is incident to at least `k-2` triangles.

    Parameters
    ----------
    G : NetworkX graph
      An undirected graph
    k : int
      The order of the truss

    Returns
    -------
    H : NetworkX graph
      The k-truss subgraph

    Raises
    ------
    NetworkXNotImplemented
      If `G` is a multigraph or directed graph or if it contains self loops.

    Notes
    -----
    A k-clique is a (k-2)-truss and a k-truss is a (k+1)-core.

    Graph, node, and edge attributes are copied to the subgraph.

    K-trusses were originally defined in [2] which states that the k-truss
    is the maximal induced subgraph where each edge belongs to at least
    `k-2` triangles. A more recent paper, [1], uses a slightly different
    definition requiring that each edge belong to at least `k` triangles.
    This implementation uses the original definition of `k-2` triangles.

    Examples
    --------
    >>> degrees = [0, 1, 2, 2, 2, 2, 3]
    >>> H = nx.havel_hakimi_graph(degrees)
    >>> H.degree
    DegreeView({0: 1, 1: 2, 2: 2, 3: 2, 4: 2, 5: 3, 6: 0})
    >>> nx.k_truss(H, k=2).nodes
    NodeView((0, 1, 2, 3, 4, 5))

    References
    ----------
    .. [1] Bounds and Algorithms for k-truss. Paul Burkhardt, Vance Faber,
       David G. Harris, 2018. https://arxiv.org/abs/1806.05523v2
    .. [2] Trusses: Cohesive Subgraphs for Social Network Analysis. Jonathan
       Cohen, 2005.
networkx.kamada_kawai_layout
Python Library Documentation: function kamada_kawai_layout in module networkx.drawing.layout

kamada_kawai_layout(G, dist=None, pos=None, weight='weight', scale=1, center=None, dim=2)
    Position nodes using Kamada-Kawai path-length cost-function.

    Parameters
    ----------
    G : NetworkX graph or list of nodes
        A position will be assigned to every node in G.

    dist : dict (default=None)
        A two-level dictionary of optimal distances between nodes,
        indexed by source and destination node.
        If None, the distance is computed using shortest_path_length().

    pos : dict or None  optional (default=None)
        Initial positions for nodes as a dictionary with node as keys
        and values as a coordinate list or tuple.  If None, then use
        circular_layout() for dim >= 2 and a linear layout for dim == 1.

    weight : string or None   optional (default='weight')
        The edge attribute that holds the numerical value used for
        the edge weight.  If None, then all edge weights are 1.

    scale : number (default: 1)
        Scale factor for positions.

    center : array-like or None
        Coordinate pair around which to center the layout.

    dim : int
        Dimension of layout.

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> pos = nx.kamada_kawai_layout(G)
networkx.karate_club_graph
Python Library Documentation: function karate_club_graph in module networkx.generators.social

karate_club_graph(*, backend=None, **backend_kwargs)
    Returns Zachary's Karate Club graph.

    Each node in the returned graph has a node attribute 'club' that
    indicates the name of the club to which the member represented by that node
    belongs, either 'Mr. Hi' or 'Officer'. Each edge has a weight based on the
    number of contexts in which that edge's incident node members interacted.

    The dataset is derived from the 'Club After Split From Data' column of Table 3 in [1]_.
    This was in turn derived from the 'Club After Fission' column of Table 1 in the
    same paper. Note that the nodes are 0-indexed in NetworkX, but 1-indexed in the
    paper (the 'Individual Number in Matrix C' column of Table 3 starts at 1). This
    means, for example, that ``G.nodes[9]["club"]`` returns 'Officer', which
    corresponds to row 10 of Table 3 in the paper.

    Examples
    --------
    To get the name of the club to which a node belongs::

        >>> G = nx.karate_club_graph()
        >>> G.nodes[5]["club"]
        'Mr. Hi'
        >>> G.nodes[9]["club"]
        'Officer'

    References
    ----------
    .. [1] Zachary, Wayne W.
       "An Information Flow Model for Conflict and Fission in Small Groups."
       *Journal of Anthropological Research*, 33, 452--473, (1977).
networkx.katz
Python Library Documentation: module networkx.algorithms.centrality.katz in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.katz - Katz centrality.

FUNCTIONS
    katz_centrality(G, alpha=0.1, beta=1.0, max_iter=1000, tol=1e-06, nstart=None, normalized=True, weight=None, *, backend=None, **backend_kwargs)
        Compute the Katz centrality for the nodes of the graph G.

        Katz centrality computes the centrality for a node based on the centrality
        of its neighbors. It is a generalization of the eigenvector centrality. The
        Katz centrality for node $i$ is

        .. math::

            x_i = \alpha \sum_{j} A_{ij} x_j + \beta,

        where $A$ is the adjacency matrix of graph G with eigenvalues $\lambda$.

        The parameter $\beta$ controls the initial centrality and

        .. math::

            \alpha < \frac{1}{\lambda_{\max}}.

        Katz centrality computes the relative influence of a node within a
        network by measuring the number of the immediate neighbors (first
        degree nodes) and also all other nodes in the network that connect
        to the node under consideration through these immediate neighbors.

        Extra weight can be provided to immediate neighbors through the
        parameter $\beta$.  Connections made with distant neighbors
        are, however, penalized by an attenuation factor $\alpha$ which
        should be strictly less than the inverse largest eigenvalue of the
        adjacency matrix in order for the Katz centrality to be computed
        correctly. More information is provided in [1]_.

        Parameters
        ----------
        G : graph
          A NetworkX graph.

        alpha : float, optional (default=0.1)
          Attenuation factor

        beta : scalar or dictionary, optional (default=1.0)
          Weight attributed to the immediate neighborhood. If not a scalar, the
          dictionary must have a value for every node.

        max_iter : integer, optional (default=1000)
          Maximum number of iterations in power method.

        tol : float, optional (default=1.0e-6)
          Error tolerance used to check convergence in power method iteration.

        nstart : dictionary, optional
          Starting value of Katz iteration for each node.

        normalized : bool, optional (default=True)
          If True normalize the resulting values.

        weight : None or string, optional (default=None)
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.
          In this measure the weight is interpreted as the connection strength.

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with Katz centrality as the value.

        Raises
        ------
        NetworkXError
           If the parameter `beta` is not a scalar but lacks a value for at least
           one node

        PowerIterationFailedConvergence
            If the algorithm fails to converge to the specified tolerance
            within the specified number of iterations of the power iteration
            method.

        Examples
        --------
        >>> import math
        >>> G = nx.path_graph(4)
        >>> phi = (1 + math.sqrt(5)) / 2.0  # largest eigenvalue of adj matrix
        >>> centrality = nx.katz_centrality(G, 1 / phi - 0.01)
        >>> for n, c in sorted(centrality.items()):
        ...     print(f"{n} {c:.2f}")
        0 0.37
        1 0.60
        2 0.60
        3 0.37

        See Also
        --------
        katz_centrality_numpy
        eigenvector_centrality
        eigenvector_centrality_numpy
        :func:`~networkx.algorithms.link_analysis.pagerank_alg.pagerank`
        :func:`~networkx.algorithms.link_analysis.hits_alg.hits`

        Notes
        -----
        Katz centrality was introduced by [2]_.

        This algorithm it uses the power method to find the eigenvector
        corresponding to the largest eigenvalue of the adjacency matrix of ``G``.
        The parameter ``alpha`` should be strictly less than the inverse of largest
        eigenvalue of the adjacency matrix for the algorithm to converge.
        You can use ``max(nx.adjacency_spectrum(G))`` to get $\lambda_{\max}$ the largest
        eigenvalue of the adjacency matrix.
        The iteration will stop after ``max_iter`` iterations or an error tolerance of
        ``number_of_nodes(G) * tol`` has been reached.

        For strongly connected graphs, as $\alpha \to 1/\lambda_{\max}$, and $\beta > 0$,
        Katz centrality approaches the results for eigenvector centrality.

        For directed graphs this finds "left" eigenvectors which corresponds
        to the in-edges in the graph. For out-edges Katz centrality,
        first reverse the graph with ``G.reverse()``.

        References
        ----------
        .. [1] Mark E. J. Newman:
           Networks: An Introduction.
           Oxford University Press, USA, 2010, p. 720.
        .. [2] Leo Katz:
           A New Status Index Derived from Sociometric Index.
           Psychometrika 18(1):39–43, 1953
           https://link.springer.com/content/pdf/10.1007/BF02289026.pdf

    katz_centrality_numpy(G, alpha=0.1, beta=1.0, normalized=True, weight=None, *, backend=None, **backend_kwargs)
        Compute the Katz centrality for the graph G.

        Katz centrality computes the centrality for a node based on the centrality
        of its neighbors. It is a generalization of the eigenvector centrality. The
        Katz centrality for node $i$ is

        .. math::

            x_i = \alpha \sum_{j} A_{ij} x_j + \beta,

        where $A$ is the adjacency matrix of graph G with eigenvalues $\lambda$.

        The parameter $\beta$ controls the initial centrality and

        .. math::

            \alpha < \frac{1}{\lambda_{\max}}.

        Katz centrality computes the relative influence of a node within a
        network by measuring the number of the immediate neighbors (first
        degree nodes) and also all other nodes in the network that connect
        to the node under consideration through these immediate neighbors.

        Extra weight can be provided to immediate neighbors through the
        parameter $\beta$.  Connections made with distant neighbors
        are, however, penalized by an attenuation factor $\alpha$ which
        should be strictly less than the inverse largest eigenvalue of the
        adjacency matrix in order for the Katz centrality to be computed
        correctly. More information is provided in [1]_.

        Parameters
        ----------
        G : graph
          A NetworkX graph

        alpha : float
          Attenuation factor

        beta : scalar or dictionary, optional (default=1.0)
          Weight attributed to the immediate neighborhood. If not a scalar the
          dictionary must have an value for every node.

        normalized : bool
          If True normalize the resulting values.

        weight : None or string, optional
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.
          In this measure the weight is interpreted as the connection strength.

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with Katz centrality as the value.

        Raises
        ------
        NetworkXError
           If the parameter `beta` is not a scalar but lacks a value for at least
           one node

        Examples
        --------
        >>> import math
        >>> G = nx.path_graph(4)
        >>> phi = (1 + math.sqrt(5)) / 2.0  # largest eigenvalue of adj matrix
        >>> centrality = nx.katz_centrality_numpy(G, 1 / phi)
        >>> for n, c in sorted(centrality.items()):
        ...     print(f"{n} {c:.2f}")
        0 0.37
        1 0.60
        2 0.60
        3 0.37

        See Also
        --------
        katz_centrality
        eigenvector_centrality_numpy
        eigenvector_centrality
        :func:`~networkx.algorithms.link_analysis.pagerank_alg.pagerank`
        :func:`~networkx.algorithms.link_analysis.hits_alg.hits`

        Notes
        -----
        Katz centrality was introduced by [2]_.

        This algorithm uses a direct linear solver to solve the above equation.
        The parameter ``alpha`` should be strictly less than the inverse of largest
        eigenvalue of the adjacency matrix for there to be a solution.
        You can use ``max(nx.adjacency_spectrum(G))`` to get $\lambda_{\max}$ the largest
        eigenvalue of the adjacency matrix.

        For strongly connected graphs, as $\alpha \to 1/\lambda_{\max}$, and $\beta > 0$,
        Katz centrality approaches the results for eigenvector centrality.

        For directed graphs this finds "left" eigenvectors which corresponds
        to the in-edges in the graph. For out-edges Katz centrality,
        first reverse the graph with ``G.reverse()``.

        References
        ----------
        .. [1] Mark E. J. Newman:
           Networks: An Introduction.
           Oxford University Press, USA, 2010, p. 173.
        .. [2] Leo Katz:
           A New Status Index Derived from Sociometric Index.
           Psychometrika 18(1):39–43, 1953
           https://link.springer.com/content/pdf/10.1007/BF02289026.pdf

DATA
    __all__ = ['katz_centrality', 'katz_centrality_numpy']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\katz.py

networkx.katz_centrality
Python Library Documentation: function katz_centrality in module networkx.algorithms.centrality.katz

katz_centrality(G, alpha=0.1, beta=1.0, max_iter=1000, tol=1e-06, nstart=None, normalized=True, weight=None, *, backend=None, **backend_kwargs)
    Compute the Katz centrality for the nodes of the graph G.

    Katz centrality computes the centrality for a node based on the centrality
    of its neighbors. It is a generalization of the eigenvector centrality. The
    Katz centrality for node $i$ is

    .. math::

        x_i = \alpha \sum_{j} A_{ij} x_j + \beta,

    where $A$ is the adjacency matrix of graph G with eigenvalues $\lambda$.

    The parameter $\beta$ controls the initial centrality and

    .. math::

        \alpha < \frac{1}{\lambda_{\max}}.

    Katz centrality computes the relative influence of a node within a
    network by measuring the number of the immediate neighbors (first
    degree nodes) and also all other nodes in the network that connect
    to the node under consideration through these immediate neighbors.

    Extra weight can be provided to immediate neighbors through the
    parameter $\beta$.  Connections made with distant neighbors
    are, however, penalized by an attenuation factor $\alpha$ which
    should be strictly less than the inverse largest eigenvalue of the
    adjacency matrix in order for the Katz centrality to be computed
    correctly. More information is provided in [1]_.

    Parameters
    ----------
    G : graph
      A NetworkX graph.

    alpha : float, optional (default=0.1)
      Attenuation factor

    beta : scalar or dictionary, optional (default=1.0)
      Weight attributed to the immediate neighborhood. If not a scalar, the
      dictionary must have a value for every node.

    max_iter : integer, optional (default=1000)
      Maximum number of iterations in power method.

    tol : float, optional (default=1.0e-6)
      Error tolerance used to check convergence in power method iteration.

    nstart : dictionary, optional
      Starting value of Katz iteration for each node.

    normalized : bool, optional (default=True)
      If True normalize the resulting values.

    weight : None or string, optional (default=None)
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.
      In this measure the weight is interpreted as the connection strength.

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with Katz centrality as the value.

    Raises
    ------
    NetworkXError
       If the parameter `beta` is not a scalar but lacks a value for at least
       one node

    PowerIterationFailedConvergence
        If the algorithm fails to converge to the specified tolerance
        within the specified number of iterations of the power iteration
        method.

    Examples
    --------
    >>> import math
    >>> G = nx.path_graph(4)
    >>> phi = (1 + math.sqrt(5)) / 2.0  # largest eigenvalue of adj matrix
    >>> centrality = nx.katz_centrality(G, 1 / phi - 0.01)
    >>> for n, c in sorted(centrality.items()):
    ...     print(f"{n} {c:.2f}")
    0 0.37
    1 0.60
    2 0.60
    3 0.37

    See Also
    --------
    katz_centrality_numpy
    eigenvector_centrality
    eigenvector_centrality_numpy
    :func:`~networkx.algorithms.link_analysis.pagerank_alg.pagerank`
    :func:`~networkx.algorithms.link_analysis.hits_alg.hits`

    Notes
    -----
    Katz centrality was introduced by [2]_.

    This algorithm it uses the power method to find the eigenvector
    corresponding to the largest eigenvalue of the adjacency matrix of ``G``.
    The parameter ``alpha`` should be strictly less than the inverse of largest
    eigenvalue of the adjacency matrix for the algorithm to converge.
    You can use ``max(nx.adjacency_spectrum(G))`` to get $\lambda_{\max}$ the largest
    eigenvalue of the adjacency matrix.
    The iteration will stop after ``max_iter`` iterations or an error tolerance of
    ``number_of_nodes(G) * tol`` has been reached.

    For strongly connected graphs, as $\alpha \to 1/\lambda_{\max}$, and $\beta > 0$,
    Katz centrality approaches the results for eigenvector centrality.

    For directed graphs this finds "left" eigenvectors which corresponds
    to the in-edges in the graph. For out-edges Katz centrality,
    first reverse the graph with ``G.reverse()``.

    References
    ----------
    .. [1] Mark E. J. Newman:
       Networks: An Introduction.
       Oxford University Press, USA, 2010, p. 720.
    .. [2] Leo Katz:
       A New Status Index Derived from Sociometric Index.
       Psychometrika 18(1):39–43, 1953
       https://link.springer.com/content/pdf/10.1007/BF02289026.pdf
networkx.katz_centrality_numpy
Python Library Documentation: function katz_centrality_numpy in module networkx.algorithms.centrality.katz

katz_centrality_numpy(G, alpha=0.1, beta=1.0, normalized=True, weight=None, *, backend=None, **backend_kwargs)
    Compute the Katz centrality for the graph G.

    Katz centrality computes the centrality for a node based on the centrality
    of its neighbors. It is a generalization of the eigenvector centrality. The
    Katz centrality for node $i$ is

    .. math::

        x_i = \alpha \sum_{j} A_{ij} x_j + \beta,

    where $A$ is the adjacency matrix of graph G with eigenvalues $\lambda$.

    The parameter $\beta$ controls the initial centrality and

    .. math::

        \alpha < \frac{1}{\lambda_{\max}}.

    Katz centrality computes the relative influence of a node within a
    network by measuring the number of the immediate neighbors (first
    degree nodes) and also all other nodes in the network that connect
    to the node under consideration through these immediate neighbors.

    Extra weight can be provided to immediate neighbors through the
    parameter $\beta$.  Connections made with distant neighbors
    are, however, penalized by an attenuation factor $\alpha$ which
    should be strictly less than the inverse largest eigenvalue of the
    adjacency matrix in order for the Katz centrality to be computed
    correctly. More information is provided in [1]_.

    Parameters
    ----------
    G : graph
      A NetworkX graph

    alpha : float
      Attenuation factor

    beta : scalar or dictionary, optional (default=1.0)
      Weight attributed to the immediate neighborhood. If not a scalar the
      dictionary must have an value for every node.

    normalized : bool
      If True normalize the resulting values.

    weight : None or string, optional
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.
      In this measure the weight is interpreted as the connection strength.

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with Katz centrality as the value.

    Raises
    ------
    NetworkXError
       If the parameter `beta` is not a scalar but lacks a value for at least
       one node

    Examples
    --------
    >>> import math
    >>> G = nx.path_graph(4)
    >>> phi = (1 + math.sqrt(5)) / 2.0  # largest eigenvalue of adj matrix
    >>> centrality = nx.katz_centrality_numpy(G, 1 / phi)
    >>> for n, c in sorted(centrality.items()):
    ...     print(f"{n} {c:.2f}")
    0 0.37
    1 0.60
    2 0.60
    3 0.37

    See Also
    --------
    katz_centrality
    eigenvector_centrality_numpy
    eigenvector_centrality
    :func:`~networkx.algorithms.link_analysis.pagerank_alg.pagerank`
    :func:`~networkx.algorithms.link_analysis.hits_alg.hits`

    Notes
    -----
    Katz centrality was introduced by [2]_.

    This algorithm uses a direct linear solver to solve the above equation.
    The parameter ``alpha`` should be strictly less than the inverse of largest
    eigenvalue of the adjacency matrix for there to be a solution.
    You can use ``max(nx.adjacency_spectrum(G))`` to get $\lambda_{\max}$ the largest
    eigenvalue of the adjacency matrix.

    For strongly connected graphs, as $\alpha \to 1/\lambda_{\max}$, and $\beta > 0$,
    Katz centrality approaches the results for eigenvector centrality.

    For directed graphs this finds "left" eigenvectors which corresponds
    to the in-edges in the graph. For out-edges Katz centrality,
    first reverse the graph with ``G.reverse()``.

    References
    ----------
    .. [1] Mark E. J. Newman:
       Networks: An Introduction.
       Oxford University Press, USA, 2010, p. 173.
    .. [2] Leo Katz:
       A New Status Index Derived from Sociometric Index.
       Psychometrika 18(1):39–43, 1953
       https://link.springer.com/content/pdf/10.1007/BF02289026.pdf
networkx.kemeny_constant
Python Library Documentation: function kemeny_constant in module networkx.algorithms.distance_measures

kemeny_constant(G, *, weight=None, backend=None, **backend_kwargs)
    Returns the Kemeny constant of the given graph.

    The *Kemeny constant* (or Kemeny's constant) of a graph `G`
    can be computed by regarding the graph as a Markov chain.
    The Kemeny constant is then the expected number of time steps
    to transition from a starting state i to a random destination state
    sampled from the Markov chain's stationary distribution.
    The Kemeny constant is independent of the chosen initial state [1]_.

    The Kemeny constant measures the time needed for spreading
    across a graph. Low values indicate a closely connected graph
    whereas high values indicate a spread-out graph.

    If weight is not provided, then a weight of 1 is used for all edges.

    Since `G` represents a Markov chain, the weights must be positive.

    Parameters
    ----------
    G : NetworkX graph

    weight : string or None, optional (default=None)
       The edge data key used to compute the Kemeny constant.
       If None, then each edge has weight 1.

    Returns
    -------
    float
        The Kemeny constant of the graph `G`.

    Raises
    ------
    NetworkXNotImplemented
        If the graph `G` is directed.

    NetworkXError
        If the graph `G` is not connected, or contains no nodes,
        or has edges with negative weights.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> round(nx.kemeny_constant(G), 10)
    3.2

    Notes
    -----
    The implementation is based on equation (3.3) in [2]_.
    Self-loops are allowed and indicate a Markov chain where
    the state can remain the same. Multi-edges are contracted
    in one edge with weight equal to the sum of the weights.

    References
    ----------
    .. [1] Wikipedia
       "Kemeny's constant."
       https://en.wikipedia.org/wiki/Kemeny%27s_constant
    .. [2] Lovász L.
        Random walks on graphs: A survey.
        Paul Erdös is Eighty, vol. 2, Bolyai Society,
        Mathematical Studies, Keszthely, Hungary (1993), pp. 1-46
networkx.kl_connected_subgraph
Python Library Documentation: function kl_connected_subgraph in module networkx.algorithms.hybrid

kl_connected_subgraph(G, k, l, low_memory=False, same_as_graph=False, *, backend=None, **backend_kwargs)
    Returns the maximum locally `(k, l)`-connected subgraph of `G`.

    A graph is locally `(k, l)`-connected if for each edge `(u, v)` in the
    graph there are at least `l` edge-disjoint paths of length at most `k`
    joining `u` to `v`.

    Parameters
    ----------
    G : NetworkX graph
        The graph in which to find a maximum locally `(k, l)`-connected
        subgraph.

    k : integer
        The maximum length of paths to consider. A higher number means a looser
        connectivity requirement.

    l : integer
        The number of edge-disjoint paths. A higher number means a stricter
        connectivity requirement.

    low_memory : bool
        If this is True, this function uses an algorithm that uses slightly
        more time but less memory.

    same_as_graph : bool
        If True then return a tuple of the form `(H, is_same)`,
        where `H` is the maximum locally `(k, l)`-connected subgraph and
        `is_same` is a Boolean representing whether `G` is locally `(k,
        l)`-connected (and hence, whether `H` is simply a copy of the input
        graph `G`).

    Returns
    -------
    NetworkX graph or two-tuple
        If `same_as_graph` is True, then this function returns a
        two-tuple as described above. Otherwise, it returns only the maximum
        locally `(k, l)`-connected subgraph.

    See also
    --------
    is_kl_connected

    References
    ----------
    .. [1] Chung, Fan and Linyuan Lu. "The Small World Phenomenon in Hybrid
           Power Law Graphs." *Complex Networks*. Springer Berlin Heidelberg,
           2004. 89--104.
networkx.kneser_graph
Python Library Documentation: function kneser_graph in module networkx.generators.classic

kneser_graph(n, k, *, backend=None, **backend_kwargs)
    Returns the Kneser Graph with parameters `n` and `k`.

    The Kneser Graph has nodes that are k-tuples (subsets) of the integers
    between 0 and ``n-1``. Nodes are adjacent if their corresponding sets are disjoint.

    Parameters
    ----------
    n: int
        Number of integers from which to make node subsets.
        Subsets are drawn from ``set(range(n))``.
    k: int
        Size of the subsets.

    Returns
    -------
    G : NetworkX Graph

    Examples
    --------
    >>> G = nx.kneser_graph(5, 2)
    >>> G.number_of_nodes()
    10
    >>> G.number_of_edges()
    15
    >>> nx.is_isomorphic(G, nx.petersen_graph())
    True
networkx.kosaraju_strongly_connected_components
Python Library Documentation: function kosaraju_strongly_connected_components in module networkx.algorithms.components.strongly_connected

kosaraju_strongly_connected_components(G, source=None, *, backend=None, **backend_kwargs)
    Generate nodes in strongly connected components of graph.

    Parameters
    ----------
    G : NetworkX Graph
        A directed graph.

    Returns
    -------
    comp : generator of sets
        A generator of sets of nodes, one for each strongly connected
        component of G.

    Raises
    ------
    NetworkXNotImplemented
        If G is undirected.

    Examples
    --------
    Generate a sorted list of strongly connected components, largest first.

    >>> G = nx.cycle_graph(4, create_using=nx.DiGraph())
    >>> nx.add_cycle(G, [10, 11, 12])
    >>> [
    ...     len(c)
    ...     for c in sorted(
    ...         nx.kosaraju_strongly_connected_components(G), key=len, reverse=True
    ...     )
    ... ]
    [4, 3]

    If you only want the largest component, it's more efficient to
    use max instead of sort.

    >>> largest = max(nx.kosaraju_strongly_connected_components(G), key=len)

    See Also
    --------
    strongly_connected_components

    Notes
    -----
    Uses Kosaraju's algorithm.
networkx.krackhardt_kite_graph
Python Library Documentation: function krackhardt_kite_graph in module networkx.generators.small

krackhardt_kite_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Krackhardt Kite Social Network.

    A 10 actor social network introduced by David Krackhardt
    to illustrate different centrality measures [1]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Krackhardt Kite graph with 10 nodes and 18 edges

    Notes
    -----
    The traditional labeling is:
    Andre=1, Beverley=2, Carol=3, Diane=4,
    Ed=5, Fernando=6, Garth=7, Heather=8, Ike=9, Jane=10.

    References
    ----------
    .. [1] Krackhardt, David. "Assessing the Political Landscape: Structure,
       Cognition, and Power in Organizations". Administrative Science Quarterly.
       35 (2): 342–369. doi:10.2307/2393394. JSTOR 2393394. June 1990.
networkx.ladder_graph
Python Library Documentation: function ladder_graph in module networkx.generators.classic

ladder_graph(n, create_using=None, *, backend=None, **backend_kwargs)
    Returns the Ladder graph of length n.

    This is two paths of n nodes, with
    each pair connected by a single edge.

    Node labels are the integers 0 to 2*n - 1.

    .. plot::

        >>> nx.draw(nx.ladder_graph(5))
networkx.laplacian
Python Library Documentation: module networkx.algorithms.centrality.laplacian in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.laplacian - Laplacian centrality measures.

FUNCTIONS
    laplacian_centrality(G, normalized=True, nodelist=None, weight='weight', walk_type=None, alpha=0.95, *, backend=None, **backend_kwargs)
        Compute the Laplacian centrality for nodes in the graph `G`.

        The Laplacian Centrality of a node ``i`` is measured by the drop in the
        Laplacian Energy after deleting node ``i`` from the graph. The Laplacian Energy
        is the sum of the squared eigenvalues of a graph's Laplacian matrix.

        .. math::

            C_L(u_i,G) = \frac{(\Delta E)_i}{E_L (G)} = \frac{E_L (G)-E_L (G_i)}{E_L (G)}

            E_L (G) = \sum_{i=0}^n \lambda_i^2

        Where $E_L (G)$ is the Laplacian energy of graph `G`,
        E_L (G_i) is the Laplacian energy of graph `G` after deleting node ``i``
        and $\lambda_i$ are the eigenvalues of `G`'s Laplacian matrix.
        This formula shows the normalized value. Without normalization,
        the numerator on the right side is returned.

        Parameters
        ----------
        G : graph
            A networkx graph

        normalized : bool (default = True)
            If True the centrality score is scaled so the sum over all nodes is 1.
            If False the centrality score for each node is the drop in Laplacian
            energy when that node is removed.

        nodelist : list, optional (default = None)
            The rows and columns are ordered according to the nodes in nodelist.
            If nodelist is None, then the ordering is produced by G.nodes().

        weight: string or None, optional (default=`weight`)
            Optional parameter `weight` to compute the Laplacian matrix.
            The edge data key used to compute each value in the matrix.
            If None, then each edge has weight 1.

        walk_type : string or None, optional (default=None)
            Optional parameter `walk_type` used when calling
            :func:`directed_laplacian_matrix <networkx.directed_laplacian_matrix>`.
            One of ``"random"``, ``"lazy"``, or ``"pagerank"``. If ``walk_type=None``
            (the default), then a value is selected according to the properties of `G`:
            - ``walk_type="random"`` if `G` is strongly connected and aperiodic
            - ``walk_type="lazy"`` if `G` is strongly connected but not aperiodic
            - ``walk_type="pagerank"`` for all other cases.

        alpha : real (default = 0.95)
            Optional parameter `alpha` used when calling
            :func:`directed_laplacian_matrix <networkx.directed_laplacian_matrix>`.
            (1 - alpha) is the teleportation probability used with pagerank.

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with Laplacian centrality as the value.

        Examples
        --------
        >>> G = nx.Graph()
        >>> edges = [(0, 1, 4), (0, 2, 2), (2, 1, 1), (1, 3, 2), (1, 4, 2), (4, 5, 1)]
        >>> G.add_weighted_edges_from(edges)
        >>> sorted((v, f"{c:0.2f}") for v, c in laplacian_centrality(G).items())
        [(0, '0.70'), (1, '0.90'), (2, '0.28'), (3, '0.22'), (4, '0.26'), (5, '0.04')]

        Notes
        -----
        The algorithm is implemented based on [1]_ with an extension to directed graphs
        using the ``directed_laplacian_matrix`` function.

        Raises
        ------
        NetworkXPointlessConcept
            If the graph `G` is the null graph.
        ZeroDivisionError
            If the graph `G` has no edges (is empty) and normalization is requested.

        References
        ----------
        .. [1] Qi, X., Fuller, E., Wu, Q., Wu, Y., and Zhang, C.-Q. (2012).
           Laplacian centrality: A new centrality measure for weighted networks.
           Information Sciences, 194:240-253.
           https://math.wvu.edu/~cqzhang/Publication-files/my-paper/INS-2012-Laplacian-W.pdf

        See Also
        --------
        :func:`~networkx.linalg.laplacianmatrix.directed_laplacian_matrix`
        :func:`~networkx.linalg.laplacianmatrix.laplacian_matrix`

DATA
    __all__ = ['laplacian_centrality']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\laplacian.py

networkx.laplacian_centrality
Python Library Documentation: function laplacian_centrality in module networkx.algorithms.centrality.laplacian

laplacian_centrality(G, normalized=True, nodelist=None, weight='weight', walk_type=None, alpha=0.95, *, backend=None, **backend_kwargs)
    Compute the Laplacian centrality for nodes in the graph `G`.

    The Laplacian Centrality of a node ``i`` is measured by the drop in the
    Laplacian Energy after deleting node ``i`` from the graph. The Laplacian Energy
    is the sum of the squared eigenvalues of a graph's Laplacian matrix.

    .. math::

        C_L(u_i,G) = \frac{(\Delta E)_i}{E_L (G)} = \frac{E_L (G)-E_L (G_i)}{E_L (G)}

        E_L (G) = \sum_{i=0}^n \lambda_i^2

    Where $E_L (G)$ is the Laplacian energy of graph `G`,
    E_L (G_i) is the Laplacian energy of graph `G` after deleting node ``i``
    and $\lambda_i$ are the eigenvalues of `G`'s Laplacian matrix.
    This formula shows the normalized value. Without normalization,
    the numerator on the right side is returned.

    Parameters
    ----------
    G : graph
        A networkx graph

    normalized : bool (default = True)
        If True the centrality score is scaled so the sum over all nodes is 1.
        If False the centrality score for each node is the drop in Laplacian
        energy when that node is removed.

    nodelist : list, optional (default = None)
        The rows and columns are ordered according to the nodes in nodelist.
        If nodelist is None, then the ordering is produced by G.nodes().

    weight: string or None, optional (default=`weight`)
        Optional parameter `weight` to compute the Laplacian matrix.
        The edge data key used to compute each value in the matrix.
        If None, then each edge has weight 1.

    walk_type : string or None, optional (default=None)
        Optional parameter `walk_type` used when calling
        :func:`directed_laplacian_matrix <networkx.directed_laplacian_matrix>`.
        One of ``"random"``, ``"lazy"``, or ``"pagerank"``. If ``walk_type=None``
        (the default), then a value is selected according to the properties of `G`:
        - ``walk_type="random"`` if `G` is strongly connected and aperiodic
        - ``walk_type="lazy"`` if `G` is strongly connected but not aperiodic
        - ``walk_type="pagerank"`` for all other cases.

    alpha : real (default = 0.95)
        Optional parameter `alpha` used when calling
        :func:`directed_laplacian_matrix <networkx.directed_laplacian_matrix>`.
        (1 - alpha) is the teleportation probability used with pagerank.

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with Laplacian centrality as the value.

    Examples
    --------
    >>> G = nx.Graph()
    >>> edges = [(0, 1, 4), (0, 2, 2), (2, 1, 1), (1, 3, 2), (1, 4, 2), (4, 5, 1)]
    >>> G.add_weighted_edges_from(edges)
    >>> sorted((v, f"{c:0.2f}") for v, c in laplacian_centrality(G).items())
    [(0, '0.70'), (1, '0.90'), (2, '0.28'), (3, '0.22'), (4, '0.26'), (5, '0.04')]

    Notes
    -----
    The algorithm is implemented based on [1]_ with an extension to directed graphs
    using the ``directed_laplacian_matrix`` function.

    Raises
    ------
    NetworkXPointlessConcept
        If the graph `G` is the null graph.
    ZeroDivisionError
        If the graph `G` has no edges (is empty) and normalization is requested.

    References
    ----------
    .. [1] Qi, X., Fuller, E., Wu, Q., Wu, Y., and Zhang, C.-Q. (2012).
       Laplacian centrality: A new centrality measure for weighted networks.
       Information Sciences, 194:240-253.
       https://math.wvu.edu/~cqzhang/Publication-files/my-paper/INS-2012-Laplacian-W.pdf

    See Also
    --------
    :func:`~networkx.linalg.laplacianmatrix.directed_laplacian_matrix`
    :func:`~networkx.linalg.laplacianmatrix.laplacian_matrix`
networkx.laplacian_matrix
Python Library Documentation: function laplacian_matrix in module networkx.linalg.laplacianmatrix

laplacian_matrix(G, nodelist=None, weight='weight', *, backend=None, **backend_kwargs)
    Returns the Laplacian matrix of G.

    The graph Laplacian is the matrix L = D - A, where
    A is the adjacency matrix and D is the diagonal matrix of node degrees.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    nodelist : list, optional
       The rows and columns are ordered according to the nodes in nodelist.
       If nodelist is None, then the ordering is produced by G.nodes().

    weight : string or None, optional (default='weight')
       The edge data key used to compute each value in the matrix.
       If None, then each edge has weight 1.

    Returns
    -------
    L : SciPy sparse array
      The Laplacian matrix of G.

    Notes
    -----
    For MultiGraph, the edges weights are summed.

    This returns an unnormalized matrix. For a normalized output,
    use `normalized_laplacian_matrix`, `directed_laplacian_matrix`,
    or `directed_combinatorial_laplacian_matrix`.

    This calculation uses the out-degree of the graph `G`. To use the
    in-degree for calculations instead, use `G.reverse(copy=False)` and
    take the transpose.

    See Also
    --------
    :func:`~networkx.convert_matrix.to_numpy_array`
    normalized_laplacian_matrix
    directed_laplacian_matrix
    directed_combinatorial_laplacian_matrix
    :func:`~networkx.linalg.spectrum.laplacian_spectrum`

    Examples
    --------
    For graphs with multiple connected components, L is permutation-similar
    to a block diagonal matrix where each block is the respective Laplacian
    matrix for each component.

    >>> G = nx.Graph([(1, 2), (2, 3), (4, 5)])
    >>> print(nx.laplacian_matrix(G).toarray())
    [[ 1 -1  0  0  0]
     [-1  2 -1  0  0]
     [ 0 -1  1  0  0]
     [ 0  0  0  1 -1]
     [ 0  0  0 -1  1]]

    >>> edges = [
    ...     (1, 2),
    ...     (2, 1),
    ...     (2, 4),
    ...     (4, 3),
    ...     (3, 4),
    ... ]
    >>> DiG = nx.DiGraph(edges)
    >>> print(nx.laplacian_matrix(DiG).toarray())
    [[ 1 -1  0  0]
     [-1  2 -1  0]
     [ 0  0  1 -1]
     [ 0  0 -1  1]]

    Notice that node 4 is represented by the third column and row. This is because
    by default the row/column order is the order of `G.nodes` (i.e. the node added
    order -- in the edgelist, 4 first appears in (2, 4), before node 3 in edge (4, 3).)
    To control the node order of the matrix, use the `nodelist` argument.

    >>> print(nx.laplacian_matrix(DiG, nodelist=[1, 2, 3, 4]).toarray())
    [[ 1 -1  0  0]
     [-1  2  0 -1]
     [ 0  0  1 -1]
     [ 0  0 -1  1]]

    This calculation uses the out-degree of the graph `G`. To use the
    in-degree for calculations instead, use `G.reverse(copy=False)` and
    take the transpose.

    >>> print(nx.laplacian_matrix(DiG.reverse(copy=False)).toarray().T)
    [[ 1 -1  0  0]
     [-1  1 -1  0]
     [ 0  0  2 -1]
     [ 0  0 -1  1]]

    References
    ----------
    .. [1] Langville, Amy N., and Carl D. Meyer. Google’s PageRank and Beyond:
       The Science of Search Engine Rankings. Princeton University Press, 2006.
networkx.laplacian_spectrum
Python Library Documentation: function laplacian_spectrum in module networkx.linalg.spectrum

laplacian_spectrum(G, weight='weight', *, backend=None, **backend_kwargs)
    Returns eigenvalues of the Laplacian of G

    Parameters
    ----------
    G : graph
       A NetworkX graph

    weight : string or None, optional (default='weight')
       The edge data key used to compute each value in the matrix.
       If None, then each edge has weight 1.

    Returns
    -------
    evals : NumPy array
      Eigenvalues

    Notes
    -----
    For MultiGraph/MultiDiGraph, the edges weights are summed.
    See :func:`~networkx.convert_matrix.to_numpy_array` for other options.

    See Also
    --------
    laplacian_matrix

    Examples
    --------
    The multiplicity of 0 as an eigenvalue of the laplacian matrix is equal
    to the number of connected components of G.

    >>> G = nx.Graph()  # Create a graph with 5 nodes and 3 connected components
    >>> G.add_nodes_from(range(5))
    >>> G.add_edges_from([(0, 2), (3, 4)])
    >>> nx.laplacian_spectrum(G)
    array([0., 0., 0., 2., 2.])
networkx.laplacianmatrix
Python Library Documentation: module networkx.linalg.laplacianmatrix in networkx.linalg

NAME
    networkx.linalg.laplacianmatrix - Laplacian matrix of graphs.

DESCRIPTION
    All calculations here are done using the out-degree. For Laplacians using
    in-degree, use `G.reverse(copy=False)` instead of `G` and take the transpose.

    The `laplacian_matrix` function provides an unnormalized matrix,
    while `normalized_laplacian_matrix`, `directed_laplacian_matrix`,
    and `directed_combinatorial_laplacian_matrix` are all normalized.

FUNCTIONS
    directed_combinatorial_laplacian_matrix(G, nodelist=None, weight='weight', walk_type=None, alpha=0.95, *, backend=None, **backend_kwargs)
        Return the directed combinatorial Laplacian matrix of G.

        The graph directed combinatorial Laplacian is the matrix

        .. math::

            L = \Phi - \frac{1}{2} \left (\Phi P + P^T \Phi \right)

        where `P` is the transition matrix of the graph and `\Phi` a matrix
        with the Perron vector of `P` in the diagonal and zeros elsewhere [1]_.

        Depending on the value of walk_type, `P` can be the transition matrix
        induced by a random walk, a lazy random walk, or a random walk with
        teleportation (PageRank).

        Parameters
        ----------
        G : DiGraph
           A NetworkX graph

        nodelist : list, optional
           The rows and columns are ordered according to the nodes in nodelist.
           If nodelist is None, then the ordering is produced by G.nodes().

        weight : string or None, optional (default='weight')
           The edge data key used to compute each value in the matrix.
           If None, then each edge has weight 1.

        walk_type : string or None, optional (default=None)
            One of ``"random"``, ``"lazy"``, or ``"pagerank"``. If ``walk_type=None``
            (the default), then a value is selected according to the properties of `G`:
            - ``walk_type="random"`` if `G` is strongly connected and aperiodic
            - ``walk_type="lazy"`` if `G` is strongly connected but not aperiodic
            - ``walk_type="pagerank"`` for all other cases.

        alpha : real
           (1 - alpha) is the teleportation probability used with pagerank

        Returns
        -------
        L : NumPy matrix
          Combinatorial Laplacian of G.

        Notes
        -----
        Only implemented for DiGraphs

        The result is always a symmetric matrix.

        This calculation uses the out-degree of the graph `G`. To use the
        in-degree for calculations instead, use `G.reverse(copy=False)` and
        take the transpose.

        See Also
        --------
        laplacian_matrix
        normalized_laplacian_matrix
        directed_laplacian_matrix

        References
        ----------
        .. [1] Fan Chung (2005).
           Laplacians and the Cheeger inequality for directed graphs.
           Annals of Combinatorics, 9(1), 2005

    directed_laplacian_matrix(G, nodelist=None, weight='weight', walk_type=None, alpha=0.95, *, backend=None, **backend_kwargs)
        Returns the directed Laplacian matrix of G.

        The graph directed Laplacian is the matrix

        .. math::

            L = I - \frac{1}{2} \left (\Phi^{1/2} P \Phi^{-1/2} + \Phi^{-1/2} P^T \Phi^{1/2} \right )

        where `I` is the identity matrix, `P` is the transition matrix of the
        graph, and `\Phi` a matrix with the Perron vector of `P` in the diagonal and
        zeros elsewhere [1]_.

        Depending on the value of walk_type, `P` can be the transition matrix
        induced by a random walk, a lazy random walk, or a random walk with
        teleportation (PageRank).

        Parameters
        ----------
        G : DiGraph
           A NetworkX graph

        nodelist : list, optional
           The rows and columns are ordered according to the nodes in nodelist.
           If nodelist is None, then the ordering is produced by G.nodes().

        weight : string or None, optional (default='weight')
           The edge data key used to compute each value in the matrix.
           If None, then each edge has weight 1.

        walk_type : string or None, optional (default=None)
           One of ``"random"``, ``"lazy"``, or ``"pagerank"``. If ``walk_type=None``
           (the default), then a value is selected according to the properties of `G`:
           - ``walk_type="random"`` if `G` is strongly connected and aperiodic
           - ``walk_type="lazy"`` if `G` is strongly connected but not aperiodic
           - ``walk_type="pagerank"`` for all other cases.

        alpha : real
           (1 - alpha) is the teleportation probability used with pagerank

        Returns
        -------
        L : NumPy matrix
          Normalized Laplacian of G.

        Notes
        -----
        Only implemented for DiGraphs

        The result is always a symmetric matrix.

        This calculation uses the out-degree of the graph `G`. To use the
        in-degree for calculations instead, use `G.reverse(copy=False)` and
        take the transpose.

        See Also
        --------
        laplacian_matrix
        normalized_laplacian_matrix
        directed_combinatorial_laplacian_matrix

        References
        ----------
        .. [1] Fan Chung (2005).
           Laplacians and the Cheeger inequality for directed graphs.
           Annals of Combinatorics, 9(1), 2005

    laplacian_matrix(G, nodelist=None, weight='weight', *, backend=None, **backend_kwargs)
        Returns the Laplacian matrix of G.

        The graph Laplacian is the matrix L = D - A, where
        A is the adjacency matrix and D is the diagonal matrix of node degrees.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        nodelist : list, optional
           The rows and columns are ordered according to the nodes in nodelist.
           If nodelist is None, then the ordering is produced by G.nodes().

        weight : string or None, optional (default='weight')
           The edge data key used to compute each value in the matrix.
           If None, then each edge has weight 1.

        Returns
        -------
        L : SciPy sparse array
          The Laplacian matrix of G.

        Notes
        -----
        For MultiGraph, the edges weights are summed.

        This returns an unnormalized matrix. For a normalized output,
        use `normalized_laplacian_matrix`, `directed_laplacian_matrix`,
        or `directed_combinatorial_laplacian_matrix`.

        This calculation uses the out-degree of the graph `G`. To use the
        in-degree for calculations instead, use `G.reverse(copy=False)` and
        take the transpose.

        See Also
        --------
        :func:`~networkx.convert_matrix.to_numpy_array`
        normalized_laplacian_matrix
        directed_laplacian_matrix
        directed_combinatorial_laplacian_matrix
        :func:`~networkx.linalg.spectrum.laplacian_spectrum`

        Examples
        --------
        For graphs with multiple connected components, L is permutation-similar
        to a block diagonal matrix where each block is the respective Laplacian
        matrix for each component.

        >>> G = nx.Graph([(1, 2), (2, 3), (4, 5)])
        >>> print(nx.laplacian_matrix(G).toarray())
        [[ 1 -1  0  0  0]
         [-1  2 -1  0  0]
         [ 0 -1  1  0  0]
         [ 0  0  0  1 -1]
         [ 0  0  0 -1  1]]

        >>> edges = [
        ...     (1, 2),
        ...     (2, 1),
        ...     (2, 4),
        ...     (4, 3),
        ...     (3, 4),
        ... ]
        >>> DiG = nx.DiGraph(edges)
        >>> print(nx.laplacian_matrix(DiG).toarray())
        [[ 1 -1  0  0]
         [-1  2 -1  0]
         [ 0  0  1 -1]
         [ 0  0 -1  1]]

        Notice that node 4 is represented by the third column and row. This is because
        by default the row/column order is the order of `G.nodes` (i.e. the node added
        order -- in the edgelist, 4 first appears in (2, 4), before node 3 in edge (4, 3).)
        To control the node order of the matrix, use the `nodelist` argument.

        >>> print(nx.laplacian_matrix(DiG, nodelist=[1, 2, 3, 4]).toarray())
        [[ 1 -1  0  0]
         [-1  2  0 -1]
         [ 0  0  1 -1]
         [ 0  0 -1  1]]

        This calculation uses the out-degree of the graph `G`. To use the
        in-degree for calculations instead, use `G.reverse(copy=False)` and
        take the transpose.

        >>> print(nx.laplacian_matrix(DiG.reverse(copy=False)).toarray().T)
        [[ 1 -1  0  0]
         [-1  1 -1  0]
         [ 0  0  2 -1]
         [ 0  0 -1  1]]

        References
        ----------
        .. [1] Langville, Amy N., and Carl D. Meyer. Google’s PageRank and Beyond:
           The Science of Search Engine Rankings. Princeton University Press, 2006.

    normalized_laplacian_matrix(G, nodelist=None, weight='weight', *, backend=None, **backend_kwargs)
        Returns the normalized Laplacian matrix of G.

        The normalized graph Laplacian is the matrix

        .. math::

            N = D^{-1/2} L D^{-1/2}

        where `L` is the graph Laplacian and `D` is the diagonal matrix of
        node degrees [1]_.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        nodelist : list, optional
           The rows and columns are ordered according to the nodes in nodelist.
           If nodelist is None, then the ordering is produced by G.nodes().

        weight : string or None, optional (default='weight')
           The edge data key used to compute each value in the matrix.
           If None, then each edge has weight 1.

        Returns
        -------
        N : SciPy sparse array
          The normalized Laplacian matrix of G.

        Notes
        -----
        For MultiGraph, the edges weights are summed.
        See :func:`to_numpy_array` for other options.

        If the Graph contains selfloops, D is defined as ``diag(sum(A, 1))``, where A is
        the adjacency matrix [2]_.

        This calculation uses the out-degree of the graph `G`. To use the
        in-degree for calculations instead, use `G.reverse(copy=False)` and
        take the transpose.

        For an unnormalized output, use `laplacian_matrix`.

        Examples
        --------

        >>> import numpy as np
        >>> edges = [
        ...     (1, 2),
        ...     (2, 1),
        ...     (2, 4),
        ...     (4, 3),
        ...     (3, 4),
        ... ]
        >>> DiG = nx.DiGraph(edges)
        >>> print(nx.normalized_laplacian_matrix(DiG).toarray())
        [[ 1.         -0.70710678  0.          0.        ]
         [-0.70710678  1.         -0.70710678  0.        ]
         [ 0.          0.          1.         -1.        ]
         [ 0.          0.         -1.          1.        ]]

        Notice that node 4 is represented by the third column and row. This is because
        by default the row/column order is the order of `G.nodes` (i.e. the node added
        order -- in the edgelist, 4 first appears in (2, 4), before node 3 in edge (4, 3).)
        To control the node order of the matrix, use the `nodelist` argument.

        >>> print(nx.normalized_laplacian_matrix(DiG, nodelist=[1, 2, 3, 4]).toarray())
        [[ 1.         -0.70710678  0.          0.        ]
         [-0.70710678  1.          0.         -0.70710678]
         [ 0.          0.          1.         -1.        ]
         [ 0.          0.         -1.          1.        ]]
        >>> G = nx.Graph(edges)
        >>> print(nx.normalized_laplacian_matrix(G).toarray())
        [[ 1.         -0.70710678  0.          0.        ]
         [-0.70710678  1.         -0.5         0.        ]
         [ 0.         -0.5         1.         -0.70710678]
         [ 0.          0.         -0.70710678  1.        ]]

        See Also
        --------
        laplacian_matrix
        normalized_laplacian_spectrum
        directed_laplacian_matrix
        directed_combinatorial_laplacian_matrix

        References
        ----------
        .. [1] Fan Chung-Graham, Spectral Graph Theory,
           CBMS Regional Conference Series in Mathematics, Number 92, 1997.
        .. [2] Steve Butler, Interlacing For Weighted Graphs Using The Normalized
           Laplacian, Electronic Journal of Linear Algebra, Volume 16, pp. 90-98,
           March 2007.
        .. [3] Langville, Amy N., and Carl D. Meyer. Google’s PageRank and Beyond:
           The Science of Search Engine Rankings. Princeton University Press, 2006.

    total_spanning_tree_weight(G, weight=None, root=None, *, backend=None, **backend_kwargs)
        Returns the total weight of all spanning trees of `G`.

        Kirchoff's Tree Matrix Theorem [1]_, [2]_ states that the determinant of any
        cofactor of the Laplacian matrix of a graph is the number of spanning trees
        in the graph. For a weighted Laplacian matrix, it is the sum across all
        spanning trees of the multiplicative weight of each tree. That is, the
        weight of each tree is the product of its edge weights.

        For unweighted graphs, the total weight equals the number of spanning trees in `G`.

        For directed graphs, the total weight follows by summing over all directed
        spanning trees in `G` that start in the `root` node [3]_.

        .. deprecated:: 3.3

           ``total_spanning_tree_weight`` is deprecated and will be removed in v3.5.
           Use ``nx.number_of_spanning_trees(G)`` instead.

        Parameters
        ----------
        G : NetworkX Graph

        weight : string or None, optional (default=None)
            The key for the edge attribute holding the edge weight.
            If None, then each edge has weight 1.

        root : node (only required for directed graphs)
           A node in the directed graph `G`.

        Returns
        -------
        total_weight : float
            Undirected graphs:
                The sum of the total multiplicative weights for all spanning trees in `G`.
            Directed graphs:
                The sum of the total multiplicative weights for all spanning trees of `G`,
                rooted at node `root`.

        Raises
        ------
        NetworkXPointlessConcept
            If `G` does not contain any nodes.

        NetworkXError
            If the graph `G` is not (weakly) connected,
            or if `G` is directed and the root node is not specified or not in G.

        Examples
        --------
        >>> G = nx.complete_graph(5)
        >>> round(nx.total_spanning_tree_weight(G))
        125

        >>> G = nx.Graph()
        >>> G.add_edge(1, 2, weight=2)
        >>> G.add_edge(1, 3, weight=1)
        >>> G.add_edge(2, 3, weight=1)
        >>> round(nx.total_spanning_tree_weight(G, "weight"))
        5

        Notes
        -----
        Self-loops are excluded. Multi-edges are contracted in one edge
        equal to the sum of the weights.

        References
        ----------
        .. [1] Wikipedia
           "Kirchhoff's theorem."
           https://en.wikipedia.org/wiki/Kirchhoff%27s_theorem
        .. [2] Kirchhoff, G. R.
            Über die Auflösung der Gleichungen, auf welche man
            bei der Untersuchung der linearen Vertheilung
            Galvanischer Ströme geführt wird
            Annalen der Physik und Chemie, vol. 72, pp. 497-508, 1847.
        .. [3] Margoliash, J.
            "Matrix-Tree Theorem for Directed Graphs"
            https://www.math.uchicago.edu/~may/VIGRE/VIGRE2010/REUPapers/Margoliash.pdf

DATA
    __all__ = ['laplacian_matrix', 'normalized_laplacian_matrix', 'total_s...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\linalg\laplacianmatrix.py

networkx.lattice
Python Library Documentation: module networkx.generators.lattice in networkx.generators

NAME
    networkx.generators.lattice - Functions for generating grid graphs and lattices

DESCRIPTION
    The :func:`grid_2d_graph`, :func:`triangular_lattice_graph`, and
    :func:`hexagonal_lattice_graph` functions correspond to the three
    `regular tilings of the plane`_, the square, triangular, and hexagonal
    tilings, respectively. :func:`grid_graph` and :func:`hypercube_graph`
    are similar for arbitrary dimensions. Useful relevant discussion can
    be found about `Triangular Tiling`_, and `Square, Hex and Triangle Grids`_

    .. _regular tilings of the plane: https://en.wikipedia.org/wiki/List_of_regular_polytopes_and_compounds#Euclidean_tilings
    .. _Square, Hex and Triangle Grids: http://www-cs-students.stanford.edu/~amitp/game-programming/grids/
    .. _Triangular Tiling: https://en.wikipedia.org/wiki/Triangular_tiling

FUNCTIONS
    grid_2d_graph(m, n, periodic=False, create_using=None, *, backend=None, **backend_kwargs)
        Returns the two-dimensional grid graph.

        The grid graph has each node connected to its four nearest neighbors.

        Parameters
        ----------
        m, n : int or iterable container of nodes
            If an integer, nodes are from `range(n)`.
            If a container, elements become the coordinate of the nodes.

        periodic : bool or iterable
            If `periodic` is True, both dimensions are periodic. If False, none
            are periodic.  If `periodic` is iterable, it should yield 2 bool
            values indicating whether the 1st and 2nd axes, respectively, are
            periodic.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        NetworkX graph
            The (possibly periodic) grid graph of the specified dimensions.

    grid_graph(dim, periodic=False, *, backend=None, **backend_kwargs)
        Returns the *n*-dimensional grid graph.

        The dimension *n* is the length of the list `dim` and the size in
        each dimension is the value of the corresponding list element.

        Parameters
        ----------
        dim : list or tuple of numbers or iterables of nodes
            'dim' is a tuple or list with, for each dimension, either a number
            that is the size of that dimension or an iterable of nodes for
            that dimension. The dimension of the grid_graph is the length
            of `dim`.

        periodic : bool or iterable
            If `periodic` is True, all dimensions are periodic. If False all
            dimensions are not periodic. If `periodic` is iterable, it should
            yield `dim` bool values each of which indicates whether the
            corresponding axis is periodic.

        Returns
        -------
        NetworkX graph
            The (possibly periodic) grid graph of the specified dimensions.

        Examples
        --------
        To produce a 2 by 3 by 4 grid graph, a graph on 24 nodes:

        >>> from networkx import grid_graph
        >>> G = grid_graph(dim=(2, 3, 4))
        >>> len(G)
        24
        >>> G = grid_graph(dim=(range(7, 9), range(3, 6)))
        >>> len(G)
        6

    hexagonal_lattice_graph(m, n, periodic=False, with_positions=True, create_using=None, *, backend=None, **backend_kwargs)
        Returns an `m` by `n` hexagonal lattice graph.

        The *hexagonal lattice graph* is a graph whose nodes and edges are
        the `hexagonal tiling`_ of the plane.

        The returned graph will have `m` rows and `n` columns of hexagons.
        `Odd numbered columns`_ are shifted up relative to even numbered columns.

        Positions of nodes are computed by default or `with_positions is True`.
        Node positions creating the standard embedding in the plane
        with sidelength 1 and are stored in the node attribute 'pos'.
        `pos = nx.get_node_attributes(G, 'pos')` creates a dict ready for drawing.

        .. _hexagonal tiling: https://en.wikipedia.org/wiki/Hexagonal_tiling
        .. _Odd numbered columns: http://www-cs-students.stanford.edu/~amitp/game-programming/grids/

        Parameters
        ----------
        m : int
            The number of rows of hexagons in the lattice.

        n : int
            The number of columns of hexagons in the lattice.

        periodic : bool
            Whether to make a periodic grid by joining the boundary vertices.
            For this to work `n` must be even and both `n > 1` and `m > 1`.
            The periodic connections create another row and column of hexagons
            so these graphs have fewer nodes as boundary nodes are identified.

        with_positions : bool (default: True)
            Store the coordinates of each node in the graph node attribute 'pos'.
            The coordinates provide a lattice with vertical columns of hexagons
            offset to interleave and cover the plane.
            Periodic positions shift the nodes vertically in a nonlinear way so
            the edges don't overlap so much.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            If graph is directed, edges will point up or right.

        Returns
        -------
        NetworkX graph
            The *m* by *n* hexagonal lattice graph.

    hypercube_graph(n, *, backend=None, **backend_kwargs)
        Returns the *n*-dimensional hypercube graph.

        The nodes are the integers between 0 and ``2 ** n - 1``, inclusive.

        For more information on the hypercube graph, see the Wikipedia
        article `Hypercube graph`_.

        .. _Hypercube graph: https://en.wikipedia.org/wiki/Hypercube_graph

        Parameters
        ----------
        n : int
            The dimension of the hypercube.
            The number of nodes in the graph will be ``2 ** n``.

        Returns
        -------
        NetworkX graph
            The hypercube graph of dimension *n*.

    triangular_lattice_graph(m, n, periodic=False, with_positions=True, create_using=None, *, backend=None, **backend_kwargs)
        Returns the $m$ by $n$ triangular lattice graph.

        The `triangular lattice graph`_ is a two-dimensional `grid graph`_ in
        which each square unit has a diagonal edge (each grid unit has a chord).

        The returned graph has $m$ rows and $n$ columns of triangles. Rows and
        columns include both triangles pointing up and down. Rows form a strip
        of constant height. Columns form a series of diamond shapes, staggered
        with the columns on either side. Another way to state the size is that
        the nodes form a grid of `m+1` rows and `(n + 1) // 2` columns.
        The odd row nodes are shifted horizontally relative to the even rows.

        Directed graph types have edges pointed up or right.

        Positions of nodes are computed by default or `with_positions is True`.
        The position of each node (embedded in a euclidean plane) is stored in
        the graph using equilateral triangles with sidelength 1.
        The height between rows of nodes is thus $\sqrt(3)/2$.
        Nodes lie in the first quadrant with the node $(0, 0)$ at the origin.

        .. _triangular lattice graph: http://mathworld.wolfram.com/TriangularGrid.html
        .. _grid graph: http://www-cs-students.stanford.edu/~amitp/game-programming/grids/
        .. _Triangular Tiling: https://en.wikipedia.org/wiki/Triangular_tiling

        Parameters
        ----------
        m : int
            The number of rows in the lattice.

        n : int
            The number of columns in the lattice.

        periodic : bool (default: False)
            If True, join the boundary vertices of the grid using periodic
            boundary conditions. The join between boundaries is the final row
            and column of triangles. This means there is one row and one column
            fewer nodes for the periodic lattice. Periodic lattices require
            `m >= 3`, `n >= 5` and are allowed but misaligned if `m` or `n` are odd

        with_positions : bool (default: True)
            Store the coordinates of each node in the graph node attribute 'pos'.
            The coordinates provide a lattice with equilateral triangles.
            Periodic positions shift the nodes vertically in a nonlinear way so
            the edges don't overlap so much.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        NetworkX graph
            The *m* by *n* triangular lattice graph.

DATA
    __all__ = ['grid_2d_graph', 'grid_graph', 'hypercube_graph', 'triangul...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\lattice.py

networkx.lattice_reference
Python Library Documentation: function lattice_reference in module networkx.algorithms.smallworld

lattice_reference(G, niter=5, D=None, connectivity=True, seed=None, *, backend=None, **backend_kwargs)
    Latticize the given graph by swapping edges.

    Parameters
    ----------
    G : graph
        An undirected graph.

    niter : integer (optional, default=1)
        An edge is rewired approximately niter times.

    D : numpy.array (optional, default=None)
        Distance to the diagonal matrix.

    connectivity : boolean (optional, default=True)
        Ensure connectivity for the latticized graph when set to True.

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : graph
        The latticized graph.

    Raises
    ------
    NetworkXError
        If there are fewer than 4 nodes or 2 edges in `G`

    Notes
    -----
    The implementation is adapted from the algorithm by Sporns et al. [1]_.
    which is inspired from the original work by Maslov and Sneppen(2002) [2]_.

    References
    ----------
    .. [1] Sporns, Olaf, and Jonathan D. Zwi.
       "The small world of the cerebral cortex."
       Neuroinformatics 2.2 (2004): 145-162.
    .. [2] Maslov, Sergei, and Kim Sneppen.
       "Specificity and stability in topology of protein networks."
       Science 296.5569 (2002): 910-913.
networkx.layout
Python Library Documentation: module networkx.drawing.layout in networkx.drawing

NAME
    networkx.drawing.layout

DESCRIPTION
    ******
    Layout
    ******

    Node positioning algorithms for graph drawing.

    For `random_layout()` the possible resulting shape
    is a square of side [0, scale] (default: [0, 1])
    Changing `center` shifts the layout by that amount.

    For the other layout routines, the extent is
    [center - scale, center + scale] (default: [-1, 1]).

    Warning: Most layout routines have only been tested in 2-dimensions.

FUNCTIONS
    arf_layout(G, pos=None, scaling=1, a=1.1, etol=1e-06, dt=0.001, max_iter=1000, *, seed=None)
        Arf layout for networkx

        The attractive and repulsive forces (arf) layout [1]
        improves the spring layout in three ways. First, it
        prevents congestion of highly connected nodes due to
        strong forcing between nodes. Second, it utilizes the
        layout space more effectively by preventing large gaps
        that spring layout tends to create. Lastly, the arf
        layout represents symmetries in the layout better than
        the default spring layout.

        Parameters
        ----------
        G : nx.Graph or nx.DiGraph
            Networkx graph.
        pos : dict
            Initial  position of  the nodes.  If set  to None  a
            random layout will be used.
        scaling : float
            Scales the radius of the circular layout space.
        a : float
            Strength of springs between connected nodes. Should be larger than 1. The greater a, the clearer the separation ofunconnected sub clusters.
        etol : float
            Gradient sum of spring forces must be larger than `etol` before successful termination.
        dt : float
            Time step for force differential equation simulations.
        max_iter : int
            Max iterations before termination of the algorithm.
        seed : int, RandomState instance or None  optional (default=None)
            Set the random state for deterministic node layouts.
            If int, `seed` is the seed used by the random number generator,
            if numpy.random.RandomState instance, `seed` is the random
            number generator,
            if None, the random number generator is the RandomState instance used
            by numpy.random.

        References
        .. [1] "Self-Organization Applied to Dynamic Network Layout", M. Geipel,
                International Journal of Modern Physics C, 2007, Vol 18, No 10, pp. 1537-1549.
                https://doi.org/10.1142/S0129183107011558 https://arxiv.org/abs/0704.1748

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node.

        Examples
        --------
        >>> G = nx.grid_graph((5, 5))
        >>> pos = nx.arf_layout(G)

    bfs_layout(G, start, *, align='vertical', scale=1, center=None)
        Position nodes according to breadth-first search algorithm.

        Parameters
        ----------
        G : NetworkX graph
            A position will be assigned to every node in G.

        start : node in `G`
            Starting node for bfs

        center : array-like or None
            Coordinate pair around which to center the layout.

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> pos = nx.bfs_layout(G, 0)

        Notes
        -----
        This algorithm currently only works in two dimensions and does not
        try to minimize edge crossings.

    bipartite_layout(G, nodes, align='vertical', scale=1, center=None, aspect_ratio=1.3333333333333333)
        Position nodes in two straight lines.

        Parameters
        ----------
        G : NetworkX graph or list of nodes
            A position will be assigned to every node in G.

        nodes : list or container
            Nodes in one node set of the bipartite graph.
            This set will be placed on left or top.

        align : string (default='vertical')
            The alignment of nodes. Vertical or horizontal.

        scale : number (default: 1)
            Scale factor for positions.

        center : array-like or None
            Coordinate pair around which to center the layout.

        aspect_ratio : number (default=4/3):
            The ratio of the width to the height of the layout.

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node.

        Examples
        --------
        >>> G = nx.bipartite.gnmk_random_graph(3, 5, 10, seed=123)
        >>> top = nx.bipartite.sets(G)[0]
        >>> pos = nx.bipartite_layout(G, top)

        Notes
        -----
        This algorithm currently only works in two dimensions and does not
        try to minimize edge crossings.

    circular_layout(G, scale=1, center=None, dim=2)
        Position nodes on a circle.

        Parameters
        ----------
        G : NetworkX graph or list of nodes
            A position will be assigned to every node in G.

        scale : number (default: 1)
            Scale factor for positions.

        center : array-like or None
            Coordinate pair around which to center the layout.

        dim : int
            Dimension of layout.
            If dim>2, the remaining dimensions are set to zero
            in the returned positions.
            If dim<2, a ValueError is raised.

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node

        Raises
        ------
        ValueError
            If dim < 2

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> pos = nx.circular_layout(G)

        Notes
        -----
        This algorithm currently only works in two dimensions and does not
        try to minimize edge crossings.

    forceatlas2_layout(G, pos=None, *, max_iter=100, jitter_tolerance=1.0, scaling_ratio=2.0, gravity=1.0, distributed_action=False, strong_gravity=False, node_mass=None, node_size=None, weight=None, dissuade_hubs=False, linlog=False, seed=None, dim=2)
        Position nodes using the ForceAtlas2 force-directed layout algorithm.

        This function applies the ForceAtlas2 layout algorithm [1]_ to a NetworkX graph,
        positioning the nodes in a way that visually represents the structure of the graph.
        The algorithm uses physical simulation to minimize the energy of the system,
        resulting in a more readable layout.

        Parameters
        ----------
        G : nx.Graph
            A NetworkX graph to be laid out.
        pos : dict or None, optional
            Initial positions of the nodes. If None, random initial positions are used.
        max_iter : int (default: 100)
            Number of iterations for the layout optimization.
        jitter_tolerance : float (default: 1.0)
            Controls the tolerance for adjusting the speed of layout generation.
        scaling_ratio : float (default: 2.0)
            Determines the scaling of attraction and repulsion forces.
        distributed_attraction : bool (default: False)
            Distributes the attraction force evenly among nodes.
        strong_gravity : bool (default: False)
            Applies a strong gravitational pull towards the center.
        node_mass : dict or None, optional
            Maps nodes to their masses, influencing the attraction to other nodes.
        node_size : dict or None, optional
            Maps nodes to their sizes, preventing crowding by creating a halo effect.
        dissuade_hubs : bool (default: False)
            Prevents the clustering of hub nodes.
        linlog : bool (default: False)
            Uses logarithmic attraction instead of linear.
        seed : int, RandomState instance or None  optional (default=None)
            Used only for the initial positions in the algorithm.
            Set the random state for deterministic node layouts.
            If int, `seed` is the seed used by the random number generator,
            if numpy.random.RandomState instance, `seed` is the random
            number generator,
            if None, the random number generator is the RandomState instance used
            by numpy.random.
        dim : int (default: 2)
            Sets the dimensions for the layout. Ignored if `pos` is provided.

        Examples
        --------
        >>> import networkx as nx
        >>> G = nx.florentine_families_graph()
        >>> pos = nx.forceatlas2_layout(G)
        >>> nx.draw(G, pos=pos)

        References
        ----------
        .. [1] Jacomy, M., Venturini, T., Heymann, S., & Bastian, M. (2014).
               ForceAtlas2, a continuous graph layout algorithm for handy network
               visualization designed for the Gephi software. PloS one, 9(6), e98679.
               https://doi.org/10.1371/journal.pone.0098679

    fruchterman_reingold_layout = spring_layout(G, k=None, pos=None, fixed=None, iterations=50, threshold=0.0001, weight='weight', scale=1, center=None, dim=2, seed=None)
        Position nodes using Fruchterman-Reingold force-directed algorithm.

        The algorithm simulates a force-directed representation of the network
        treating edges as springs holding nodes close, while treating nodes
        as repelling objects, sometimes called an anti-gravity force.
        Simulation continues until the positions are close to an equilibrium.

        There are some hard-coded values: minimal distance between
        nodes (0.01) and "temperature" of 0.1 to ensure nodes don't fly away.
        During the simulation, `k` helps determine the distance between nodes,
        though `scale` and `center` determine the size and place after
        rescaling occurs at the end of the simulation.

        Fixing some nodes doesn't allow them to move in the simulation.
        It also turns off the rescaling feature at the simulation's end.
        In addition, setting `scale` to `None` turns off rescaling.

        Parameters
        ----------
        G : NetworkX graph or list of nodes
            A position will be assigned to every node in G.

        k : float (default=None)
            Optimal distance between nodes.  If None the distance is set to
            1/sqrt(n) where n is the number of nodes.  Increase this value
            to move nodes farther apart.

        pos : dict or None  optional (default=None)
            Initial positions for nodes as a dictionary with node as keys
            and values as a coordinate list or tuple.  If None, then use
            random initial positions.

        fixed : list or None  optional (default=None)
            Nodes to keep fixed at initial position.
            Nodes not in ``G.nodes`` are ignored.
            ValueError raised if `fixed` specified and `pos` not.

        iterations : int  optional (default=50)
            Maximum number of iterations taken

        threshold: float optional (default = 1e-4)
            Threshold for relative error in node position changes.
            The iteration stops if the error is below this threshold.

        weight : string or None   optional (default='weight')
            The edge attribute that holds the numerical value used for
            the edge weight.  Larger means a stronger attractive force.
            If None, then all edge weights are 1.

        scale : number or None (default: 1)
            Scale factor for positions. Not used unless `fixed is None`.
            If scale is None, no rescaling is performed.

        center : array-like or None
            Coordinate pair around which to center the layout.
            Not used unless `fixed is None`.

        dim : int
            Dimension of layout.

        seed : int, RandomState instance or None  optional (default=None)
            Used only for the initial positions in the algorithm.
            Set the random state for deterministic node layouts.
            If int, `seed` is the seed used by the random number generator,
            if numpy.random.RandomState instance, `seed` is the random
            number generator,
            if None, the random number generator is the RandomState instance used
            by numpy.random.

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> pos = nx.spring_layout(G)

        # The same using longer but equivalent function name
        >>> pos = nx.fruchterman_reingold_layout(G)

    kamada_kawai_layout(G, dist=None, pos=None, weight='weight', scale=1, center=None, dim=2)
        Position nodes using Kamada-Kawai path-length cost-function.

        Parameters
        ----------
        G : NetworkX graph or list of nodes
            A position will be assigned to every node in G.

        dist : dict (default=None)
            A two-level dictionary of optimal distances between nodes,
            indexed by source and destination node.
            If None, the distance is computed using shortest_path_length().

        pos : dict or None  optional (default=None)
            Initial positions for nodes as a dictionary with node as keys
            and values as a coordinate list or tuple.  If None, then use
            circular_layout() for dim >= 2 and a linear layout for dim == 1.

        weight : string or None   optional (default='weight')
            The edge attribute that holds the numerical value used for
            the edge weight.  If None, then all edge weights are 1.

        scale : number (default: 1)
            Scale factor for positions.

        center : array-like or None
            Coordinate pair around which to center the layout.

        dim : int
            Dimension of layout.

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> pos = nx.kamada_kawai_layout(G)

    multipartite_layout(G, subset_key='subset', align='vertical', scale=1, center=None)
        Position nodes in layers of straight lines.

        Parameters
        ----------
        G : NetworkX graph or list of nodes
            A position will be assigned to every node in G.

        subset_key : string or dict (default='subset')
            If a string, the key of node data in G that holds the node subset.
            If a dict, keyed by layer number to the nodes in that layer/subset.

        align : string (default='vertical')
            The alignment of nodes. Vertical or horizontal.

        scale : number (default: 1)
            Scale factor for positions.

        center : array-like or None
            Coordinate pair around which to center the layout.

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node.

        Examples
        --------
        >>> G = nx.complete_multipartite_graph(28, 16, 10)
        >>> pos = nx.multipartite_layout(G)

        or use a dict to provide the layers of the layout

        >>> G = nx.Graph([(0, 1), (1, 2), (1, 3), (3, 4)])
        >>> layers = {"a": [0], "b": [1], "c": [2, 3], "d": [4]}
        >>> pos = nx.multipartite_layout(G, subset_key=layers)

        Notes
        -----
        This algorithm currently only works in two dimensions and does not
        try to minimize edge crossings.

        Network does not need to be a complete multipartite graph. As long as nodes
        have subset_key data, they will be placed in the corresponding layers.

    planar_layout(G, scale=1, center=None, dim=2)
        Position nodes without edge intersections.

        Parameters
        ----------
        G : NetworkX graph or list of nodes
            A position will be assigned to every node in G. If G is of type
            nx.PlanarEmbedding, the positions are selected accordingly.

        scale : number (default: 1)
            Scale factor for positions.

        center : array-like or None
            Coordinate pair around which to center the layout.

        dim : int
            Dimension of layout.

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node

        Raises
        ------
        NetworkXException
            If G is not planar

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> pos = nx.planar_layout(G)

    random_layout(G, center=None, dim=2, seed=None)
        Position nodes uniformly at random in the unit square.

        For every node, a position is generated by choosing each of dim
        coordinates uniformly at random on the interval [0.0, 1.0).

        NumPy (http://scipy.org) is required for this function.

        Parameters
        ----------
        G : NetworkX graph or list of nodes
            A position will be assigned to every node in G.

        center : array-like or None
            Coordinate pair around which to center the layout.

        dim : int
            Dimension of layout.

        seed : int, RandomState instance or None  optional (default=None)
            Set the random state for deterministic node layouts.
            If int, `seed` is the seed used by the random number generator,
            if numpy.random.RandomState instance, `seed` is the random
            number generator,
            if None, the random number generator is the RandomState instance used
            by numpy.random.

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node

        Examples
        --------
        >>> G = nx.lollipop_graph(4, 3)
        >>> pos = nx.random_layout(G)

    rescale_layout(pos, scale=1)
        Returns scaled position array to (-scale, scale) in all axes.

        The function acts on NumPy arrays which hold position information.
        Each position is one row of the array. The dimension of the space
        equals the number of columns. Each coordinate in one column.

        To rescale, the mean (center) is subtracted from each axis separately.
        Then all values are scaled so that the largest magnitude value
        from all axes equals `scale` (thus, the aspect ratio is preserved).
        The resulting NumPy Array is returned (order of rows unchanged).

        Parameters
        ----------
        pos : numpy array
            positions to be scaled. Each row is a position.

        scale : number (default: 1)
            The size of the resulting extent in all directions.

        Returns
        -------
        pos : numpy array
            scaled positions. Each row is a position.

        See Also
        --------
        rescale_layout_dict

    rescale_layout_dict(pos, scale=1)
        Return a dictionary of scaled positions keyed by node

        Parameters
        ----------
        pos : A dictionary of positions keyed by node

        scale : number (default: 1)
            The size of the resulting extent in all directions.

        Returns
        -------
        pos : A dictionary of positions keyed by node

        Examples
        --------
        >>> import numpy as np
        >>> pos = {0: np.array((0, 0)), 1: np.array((1, 1)), 2: np.array((0.5, 0.5))}
        >>> nx.rescale_layout_dict(pos)
        {0: array([-1., -1.]), 1: array([1., 1.]), 2: array([0., 0.])}

        >>> pos = {0: np.array((0, 0)), 1: np.array((-1, 1)), 2: np.array((-0.5, 0.5))}
        >>> nx.rescale_layout_dict(pos, scale=2)
        {0: array([ 2., -2.]), 1: array([-2.,  2.]), 2: array([0., 0.])}

        See Also
        --------
        rescale_layout

    shell_layout(G, nlist=None, rotate=None, scale=1, center=None, dim=2)
        Position nodes in concentric circles.

        Parameters
        ----------
        G : NetworkX graph or list of nodes
            A position will be assigned to every node in G.

        nlist : list of lists
           List of node lists for each shell.

        rotate : angle in radians (default=pi/len(nlist))
           Angle by which to rotate the starting position of each shell
           relative to the starting position of the previous shell.
           To recreate behavior before v2.5 use rotate=0.

        scale : number (default: 1)
            Scale factor for positions.

        center : array-like or None
            Coordinate pair around which to center the layout.

        dim : int
            Dimension of layout, currently only dim=2 is supported.
            Other dimension values result in a ValueError.

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node

        Raises
        ------
        ValueError
            If dim != 2

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> shells = [[0], [1, 2, 3]]
        >>> pos = nx.shell_layout(G, shells)

        Notes
        -----
        This algorithm currently only works in two dimensions and does not
        try to minimize edge crossings.

    spectral_layout(G, weight='weight', scale=1, center=None, dim=2)
        Position nodes using the eigenvectors of the graph Laplacian.

        Using the unnormalized Laplacian, the layout shows possible clusters of
        nodes which are an approximation of the ratio cut. If dim is the number of
        dimensions then the positions are the entries of the dim eigenvectors
        corresponding to the ascending eigenvalues starting from the second one.

        Parameters
        ----------
        G : NetworkX graph or list of nodes
            A position will be assigned to every node in G.

        weight : string or None   optional (default='weight')
            The edge attribute that holds the numerical value used for
            the edge weight.  If None, then all edge weights are 1.

        scale : number (default: 1)
            Scale factor for positions.

        center : array-like or None
            Coordinate pair around which to center the layout.

        dim : int
            Dimension of layout.

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> pos = nx.spectral_layout(G)

        Notes
        -----
        Directed graphs will be considered as undirected graphs when
        positioning the nodes.

        For larger graphs (>500 nodes) this will use the SciPy sparse
        eigenvalue solver (ARPACK).

    spiral_layout(G, scale=1, center=None, dim=2, resolution=0.35, equidistant=False)
        Position nodes in a spiral layout.

        Parameters
        ----------
        G : NetworkX graph or list of nodes
            A position will be assigned to every node in G.
        scale : number (default: 1)
            Scale factor for positions.
        center : array-like or None
            Coordinate pair around which to center the layout.
        dim : int, default=2
            Dimension of layout, currently only dim=2 is supported.
            Other dimension values result in a ValueError.
        resolution : float, default=0.35
            The compactness of the spiral layout returned.
            Lower values result in more compressed spiral layouts.
        equidistant : bool, default=False
            If True, nodes will be positioned equidistant from each other
            by decreasing angle further from center.
            If False, nodes will be positioned at equal angles
            from each other by increasing separation further from center.

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node

        Raises
        ------
        ValueError
            If dim != 2

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> pos = nx.spiral_layout(G)
        >>> nx.draw(G, pos=pos)

        Notes
        -----
        This algorithm currently only works in two dimensions.

    spring_layout(G, k=None, pos=None, fixed=None, iterations=50, threshold=0.0001, weight='weight', scale=1, center=None, dim=2, seed=None)
        Position nodes using Fruchterman-Reingold force-directed algorithm.

        The algorithm simulates a force-directed representation of the network
        treating edges as springs holding nodes close, while treating nodes
        as repelling objects, sometimes called an anti-gravity force.
        Simulation continues until the positions are close to an equilibrium.

        There are some hard-coded values: minimal distance between
        nodes (0.01) and "temperature" of 0.1 to ensure nodes don't fly away.
        During the simulation, `k` helps determine the distance between nodes,
        though `scale` and `center` determine the size and place after
        rescaling occurs at the end of the simulation.

        Fixing some nodes doesn't allow them to move in the simulation.
        It also turns off the rescaling feature at the simulation's end.
        In addition, setting `scale` to `None` turns off rescaling.

        Parameters
        ----------
        G : NetworkX graph or list of nodes
            A position will be assigned to every node in G.

        k : float (default=None)
            Optimal distance between nodes.  If None the distance is set to
            1/sqrt(n) where n is the number of nodes.  Increase this value
            to move nodes farther apart.

        pos : dict or None  optional (default=None)
            Initial positions for nodes as a dictionary with node as keys
            and values as a coordinate list or tuple.  If None, then use
            random initial positions.

        fixed : list or None  optional (default=None)
            Nodes to keep fixed at initial position.
            Nodes not in ``G.nodes`` are ignored.
            ValueError raised if `fixed` specified and `pos` not.

        iterations : int  optional (default=50)
            Maximum number of iterations taken

        threshold: float optional (default = 1e-4)
            Threshold for relative error in node position changes.
            The iteration stops if the error is below this threshold.

        weight : string or None   optional (default='weight')
            The edge attribute that holds the numerical value used for
            the edge weight.  Larger means a stronger attractive force.
            If None, then all edge weights are 1.

        scale : number or None (default: 1)
            Scale factor for positions. Not used unless `fixed is None`.
            If scale is None, no rescaling is performed.

        center : array-like or None
            Coordinate pair around which to center the layout.
            Not used unless `fixed is None`.

        dim : int
            Dimension of layout.

        seed : int, RandomState instance or None  optional (default=None)
            Used only for the initial positions in the algorithm.
            Set the random state for deterministic node layouts.
            If int, `seed` is the seed used by the random number generator,
            if numpy.random.RandomState instance, `seed` is the random
            number generator,
            if None, the random number generator is the RandomState instance used
            by numpy.random.

        Returns
        -------
        pos : dict
            A dictionary of positions keyed by node

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> pos = nx.spring_layout(G)

        # The same using longer but equivalent function name
        >>> pos = nx.fruchterman_reingold_layout(G)

DATA
    __all__ = ['bipartite_layout', 'circular_layout', 'forceatlas2_layout'...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\drawing\layout.py

networkx.lazy_imports
Python Library Documentation: module networkx.lazy_imports in networkx

NAME
    networkx.lazy_imports

FUNCTIONS
    _lazy_import(fullname)
        Return a lazily imported proxy for a module or library.

        Warning
        -------
        Importing using this function can currently cause trouble
        when the user tries to import from a subpackage of a module before
        the package is fully imported. In particular, this idiom may not work:

          np = lazy_import("numpy")
          from numpy.lib import recfunctions

        This is due to a difference in the way Python's LazyLoader handles
        subpackage imports compared to the normal import process. Hopefully
        we will get Python's LazyLoader to fix this, or find a workaround.
        In the meantime, this is a potential problem.

        The workaround is to import numpy before importing from the subpackage.

        Notes
        -----
        We often see the following pattern::

          def myfunc():
              import scipy as sp
              sp.argmin(...)
              ....

        This is to prevent a library, in this case `scipy`, from being
        imported at function definition time, since that can be slow.

        This function provides a proxy module that, upon access, imports
        the actual module.  So the idiom equivalent to the above example is::

          sp = lazy.load("scipy")

          def myfunc():
              sp.argmin(...)
              ....

        The initial import time is fast because the actual import is delayed
        until the first attribute is requested. The overall import time may
        decrease as well for users that don't make use of large portions
        of the library.

        Parameters
        ----------
        fullname : str
            The full name of the package or subpackage to import.  For example::

              sp = lazy.load("scipy")  # import scipy as sp
              spla = lazy.load("scipy.linalg")  # import scipy.linalg as spla

        Returns
        -------
        pm : importlib.util._LazyModule
            Proxy module. Can be used like any regularly imported module.
            Actual loading of the module occurs upon first attribute request.

    attach(module_name, submodules=None, submod_attrs=None)
        Attach lazily loaded submodules, and functions or other attributes.

        Typically, modules import submodules and attributes as follows::

          import mysubmodule
          import anothersubmodule

          from .foo import someattr

        The idea of  this function is to replace the `__init__.py`
        module's `__getattr__`, `__dir__`, and `__all__` attributes such that
        all imports work exactly the way they normally would, except that the
        actual import is delayed until the resulting module object is first used.

        The typical way to call this function, replacing the above imports, is::

          __getattr__, __lazy_dir__, __all__ = lazy.attach(
              __name__, ["mysubmodule", "anothersubmodule"], {"foo": "someattr"}
          )

        This functionality requires Python 3.7 or higher.

        Parameters
        ----------
        module_name : str
            Typically use __name__.
        submodules : set
            List of submodules to lazily import.
        submod_attrs : dict
            Dictionary of submodule -> list of attributes / functions.
            These attributes are imported as they are used.

        Returns
        -------
        __getattr__, __dir__, __all__

DATA
    __all__ = ['attach', '_lazy_import']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\lazy_imports.py

networkx.leda
Python Library Documentation: module networkx.readwrite.leda in networkx.readwrite

NAME
    networkx.readwrite.leda - Read graphs in LEDA format.

DESCRIPTION
    LEDA is a C++ class library for efficient data types and algorithms.

    Format
    ------
    See http://www.algorithmic-solutions.info/leda_guide/graphs/leda_native_graph_fileformat.html

FUNCTIONS
    parse_leda(lines, *, backend=None, **backend_kwargs)
        Read graph in LEDA format from string or iterable.

        Parameters
        ----------
        lines : string or iterable
           Data in LEDA format.

        Returns
        -------
        G : NetworkX graph

        Examples
        --------
        G=nx.parse_leda(string)

        References
        ----------
        .. [1] http://www.algorithmic-solutions.info/leda_guide/graphs/leda_native_graph_fileformat.html

    read_leda(path, encoding='UTF-8', *, backend=None, **backend_kwargs)
        Read graph in LEDA format from path.

        Parameters
        ----------
        path : file or string
           File or filename to read.  Filenames ending in .gz or .bz2  will be
           uncompressed.

        Returns
        -------
        G : NetworkX graph

        Examples
        --------
        G=nx.read_leda('file.leda')

        References
        ----------
        .. [1] http://www.algorithmic-solutions.info/leda_guide/graphs/leda_native_graph_fileformat.html

DATA
    __all__ = ['read_leda', 'parse_leda']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\leda.py

networkx.les_miserables_graph
Python Library Documentation: function les_miserables_graph in module networkx.generators.social

les_miserables_graph(*, backend=None, **backend_kwargs)
    Returns coappearance network of characters in the novel Les Miserables.

    References
    ----------
    .. [1] D. E. Knuth, 1993.
       The Stanford GraphBase: a platform for combinatorial computing,
       pp. 74-87. New York: AcM Press.
networkx.lexicographic_product
Python Library Documentation: function lexicographic_product in module networkx.algorithms.operators.product

lexicographic_product(G, H, *, backend=None, **backend_kwargs)
    Returns the lexicographic product of G and H.

    The lexicographical product $P$ of the graphs $G$ and $H$ has a node set
    that is the Cartesian product of the node sets, $V(P)=V(G) \times V(H)$.
    $P$ has an edge $((u,v), (x,y))$ if and only if $(u,v)$ is an edge in $G$
    or $u==v$ and $(x,y)$ is an edge in $H$.

    Parameters
    ----------
    G, H: graphs
     Networkx graphs.

    Returns
    -------
    P: NetworkX graph
     The Cartesian product of G and H. P will be a multi-graph if either G
     or H is a multi-graph. Will be a directed if G and H are directed,
     and undirected if G and H are undirected.

    Raises
    ------
    NetworkXError
     If G and H are not both directed or both undirected.

    Notes
    -----
    Node attributes in P are two-tuple of the G and H node attributes.
    Missing attributes are assigned None.

    Examples
    --------
    >>> G = nx.Graph()
    >>> H = nx.Graph()
    >>> G.add_node(0, a1=True)
    >>> H.add_node("a", a2="Spam")
    >>> P = nx.lexicographic_product(G, H)
    >>> list(P)
    [(0, 'a')]

    Edge attributes and edge keys (for multigraphs) are also copied to the
    new product graph
networkx.lexicographical_topological_sort
Python Library Documentation: function lexicographical_topological_sort in module networkx.algorithms.dag

lexicographical_topological_sort(G, key=None, *, backend=None, **backend_kwargs)
    Generate the nodes in the unique lexicographical topological sort order.

    Generates a unique ordering of nodes by first sorting topologically (for which there are often
    multiple valid orderings) and then additionally by sorting lexicographically.

    A topological sort arranges the nodes of a directed graph so that the
    upstream node of each directed edge precedes the downstream node.
    It is always possible to find a solution for directed graphs that have no cycles.
    There may be more than one valid solution.

    Lexicographical sorting is just sorting alphabetically. It is used here to break ties in the
    topological sort and to determine a single, unique ordering.  This can be useful in comparing
    sort results.

    The lexicographical order can be customized by providing a function to the `key=` parameter.
    The definition of the key function is the same as used in python's built-in `sort()`.
    The function takes a single argument and returns a key to use for sorting purposes.

    Lexicographical sorting can fail if the node names are un-sortable. See the example below.
    The solution is to provide a function to the `key=` argument that returns sortable keys.


    Parameters
    ----------
    G : NetworkX digraph
        A directed acyclic graph (DAG)

    key : function, optional
        A function of one argument that converts a node name to a comparison key.
        It defines and resolves ambiguities in the sort order.  Defaults to the identity function.

    Yields
    ------
    nodes
        Yields the nodes of G in lexicographical topological sort order.

    Raises
    ------
    NetworkXError
        Topological sort is defined for directed graphs only. If the graph `G`
        is undirected, a :exc:`NetworkXError` is raised.

    NetworkXUnfeasible
        If `G` is not a directed acyclic graph (DAG) no topological sort exists
        and a :exc:`NetworkXUnfeasible` exception is raised.  This can also be
        raised if `G` is changed while the returned iterator is being processed

    RuntimeError
        If `G` is changed while the returned iterator is being processed.

    TypeError
        Results from un-sortable node names.
        Consider using `key=` parameter to resolve ambiguities in the sort order.

    Examples
    --------
    >>> DG = nx.DiGraph([(2, 1), (2, 5), (1, 3), (1, 4), (5, 4)])
    >>> list(nx.lexicographical_topological_sort(DG))
    [2, 1, 3, 5, 4]
    >>> list(nx.lexicographical_topological_sort(DG, key=lambda x: -x))
    [2, 5, 1, 4, 3]

    The sort will fail for any graph with integer and string nodes. Comparison of integer to strings
    is not defined in python.  Is 3 greater or less than 'red'?

    >>> DG = nx.DiGraph([(1, "red"), (3, "red"), (1, "green"), (2, "blue")])
    >>> list(nx.lexicographical_topological_sort(DG))
    Traceback (most recent call last):
    ...
    TypeError: '<' not supported between instances of 'str' and 'int'
    ...

    Incomparable nodes can be resolved using a `key` function. This example function
    allows comparison of integers and strings by returning a tuple where the first
    element is True for `str`, False otherwise. The second element is the node name.
    This groups the strings and integers separately so they can be compared only among themselves.

    >>> key = lambda node: (isinstance(node, str), node)
    >>> list(nx.lexicographical_topological_sort(DG, key=key))
    [1, 2, 3, 'blue', 'green', 'red']

    Notes
    -----
    This algorithm is based on a description and proof in
    "Introduction to Algorithms: A Creative Approach" [1]_ .

    See also
    --------
    topological_sort

    References
    ----------
    .. [1] Manber, U. (1989).
       *Introduction to Algorithms - A Creative Approach.* Addison-Wesley.
networkx.linalg
Python Library Documentation: package networkx.linalg in networkx

NAME
    networkx.linalg

PACKAGE CONTENTS
    algebraicconnectivity
    attrmatrix
    bethehessianmatrix
    graphmatrix
    laplacianmatrix
    modularitymatrix
    spectrum
    tests (package)

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\linalg\__init__.py

networkx.line
Python Library Documentation: module networkx.generators.line in networkx.generators

NAME
    networkx.generators.line - Functions for generating line graphs.

FUNCTIONS
    inverse_line_graph(G, *, backend=None, **backend_kwargs)
        Returns the inverse line graph of graph G.

        If H is a graph, and G is the line graph of H, such that G = L(H).
        Then H is the inverse line graph of G.

        Not all graphs are line graphs and these do not have an inverse line graph.
        In these cases this function raises a NetworkXError.

        Parameters
        ----------
        G : graph
            A NetworkX Graph

        Returns
        -------
        H : graph
            The inverse line graph of G.

        Raises
        ------
        NetworkXNotImplemented
            If G is directed or a multigraph

        NetworkXError
            If G is not a line graph

        Notes
        -----
        This is an implementation of the Roussopoulos algorithm[1]_.

        If G consists of multiple components, then the algorithm doesn't work.
        You should invert every component separately:

        >>> K5 = nx.complete_graph(5)
        >>> P4 = nx.Graph([("a", "b"), ("b", "c"), ("c", "d")])
        >>> G = nx.union(K5, P4)
        >>> root_graphs = []
        >>> for comp in nx.connected_components(G):
        ...     root_graphs.append(nx.inverse_line_graph(G.subgraph(comp)))
        >>> len(root_graphs)
        2

        References
        ----------
        .. [1] Roussopoulos, N.D. , "A max {m, n} algorithm for determining the graph H from
           its line graph G", Information Processing Letters 2, (1973), 108--112, ISSN 0020-0190,
           `DOI link <https://doi.org/10.1016/0020-0190(73)90029-X>`_

    line_graph(G, create_using=None, *, backend=None, **backend_kwargs)
        Returns the line graph of the graph or digraph `G`.

        The line graph of a graph `G` has a node for each edge in `G` and an
        edge joining those nodes if the two edges in `G` share a common node. For
        directed graphs, nodes are adjacent exactly when the edges they represent
        form a directed path of length two.

        The nodes of the line graph are 2-tuples of nodes in the original graph (or
        3-tuples for multigraphs, with the key of the edge as the third element).

        For information about self-loops and more discussion, see the **Notes**
        section below.

        Parameters
        ----------
        G : graph
            A NetworkX Graph, DiGraph, MultiGraph, or MultiDigraph.
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        L : graph
            The line graph of G.

        Examples
        --------
        >>> G = nx.star_graph(3)
        >>> L = nx.line_graph(G)
        >>> print(sorted(map(sorted, L.edges())))  # makes a 3-clique, K3
        [[(0, 1), (0, 2)], [(0, 1), (0, 3)], [(0, 2), (0, 3)]]

        Edge attributes from `G` are not copied over as node attributes in `L`, but
        attributes can be copied manually:

        >>> G = nx.path_graph(4)
        >>> G.add_edges_from((u, v, {"tot": u + v}) for u, v in G.edges)
        >>> G.edges(data=True)
        EdgeDataView([(0, 1, {'tot': 1}), (1, 2, {'tot': 3}), (2, 3, {'tot': 5})])
        >>> H = nx.line_graph(G)
        >>> H.add_nodes_from((node, G.edges[node]) for node in H)
        >>> H.nodes(data=True)
        NodeDataView({(0, 1): {'tot': 1}, (2, 3): {'tot': 5}, (1, 2): {'tot': 3}})

        Notes
        -----
        Graph, node, and edge data are not propagated to the new graph. For
        undirected graphs, the nodes in G must be sortable, otherwise the
        constructed line graph may not be correct.

        *Self-loops in undirected graphs*

        For an undirected graph `G` without multiple edges, each edge can be
        written as a set `\{u, v\}`.  Its line graph `L` has the edges of `G` as
        its nodes. If `x` and `y` are two nodes in `L`, then `\{x, y\}` is an edge
        in `L` if and only if the intersection of `x` and `y` is nonempty. Thus,
        the set of all edges is determined by the set of all pairwise intersections
        of edges in `G`.

        Trivially, every edge in G would have a nonzero intersection with itself,
        and so every node in `L` should have a self-loop. This is not so
        interesting, and the original context of line graphs was with simple
        graphs, which had no self-loops or multiple edges. The line graph was also
        meant to be a simple graph and thus, self-loops in `L` are not part of the
        standard definition of a line graph. In a pairwise intersection matrix,
        this is analogous to excluding the diagonal entries from the line graph
        definition.

        Self-loops and multiple edges in `G` add nodes to `L` in a natural way, and
        do not require any fundamental changes to the definition. It might be
        argued that the self-loops we excluded before should now be included.
        However, the self-loops are still "trivial" in some sense and thus, are
        usually excluded.

        *Self-loops in directed graphs*

        For a directed graph `G` without multiple edges, each edge can be written
        as a tuple `(u, v)`. Its line graph `L` has the edges of `G` as its
        nodes. If `x` and `y` are two nodes in `L`, then `(x, y)` is an edge in `L`
        if and only if the tail of `x` matches the head of `y`, for example, if `x
        = (a, b)` and `y = (b, c)` for some vertices `a`, `b`, and `c` in `G`.

        Due to the directed nature of the edges, it is no longer the case that
        every edge in `G` should have a self-loop in `L`. Now, the only time
        self-loops arise is if a node in `G` itself has a self-loop.  So such
        self-loops are no longer "trivial" but instead, represent essential
        features of the topology of `G`. For this reason, the historical
        development of line digraphs is such that self-loops are included. When the
        graph `G` has multiple edges, once again only superficial changes are
        required to the definition.

        References
        ----------
        * Harary, Frank, and Norman, Robert Z., "Some properties of line digraphs",
          Rend. Circ. Mat. Palermo, II. Ser. 9 (1960), 161--168.
        * Hemminger, R. L.; Beineke, L. W. (1978), "Line graphs and line digraphs",
          in Beineke, L. W.; Wilson, R. J., Selected Topics in Graph Theory,
          Academic Press Inc., pp. 271--305.

DATA
    __all__ = ['line_graph', 'inverse_line_graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\line.py

networkx.line_graph
Python Library Documentation: function line_graph in module networkx.generators.line

line_graph(G, create_using=None, *, backend=None, **backend_kwargs)
    Returns the line graph of the graph or digraph `G`.

    The line graph of a graph `G` has a node for each edge in `G` and an
    edge joining those nodes if the two edges in `G` share a common node. For
    directed graphs, nodes are adjacent exactly when the edges they represent
    form a directed path of length two.

    The nodes of the line graph are 2-tuples of nodes in the original graph (or
    3-tuples for multigraphs, with the key of the edge as the third element).

    For information about self-loops and more discussion, see the **Notes**
    section below.

    Parameters
    ----------
    G : graph
        A NetworkX Graph, DiGraph, MultiGraph, or MultiDigraph.
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    L : graph
        The line graph of G.

    Examples
    --------
    >>> G = nx.star_graph(3)
    >>> L = nx.line_graph(G)
    >>> print(sorted(map(sorted, L.edges())))  # makes a 3-clique, K3
    [[(0, 1), (0, 2)], [(0, 1), (0, 3)], [(0, 2), (0, 3)]]

    Edge attributes from `G` are not copied over as node attributes in `L`, but
    attributes can be copied manually:

    >>> G = nx.path_graph(4)
    >>> G.add_edges_from((u, v, {"tot": u + v}) for u, v in G.edges)
    >>> G.edges(data=True)
    EdgeDataView([(0, 1, {'tot': 1}), (1, 2, {'tot': 3}), (2, 3, {'tot': 5})])
    >>> H = nx.line_graph(G)
    >>> H.add_nodes_from((node, G.edges[node]) for node in H)
    >>> H.nodes(data=True)
    NodeDataView({(0, 1): {'tot': 1}, (2, 3): {'tot': 5}, (1, 2): {'tot': 3}})

    Notes
    -----
    Graph, node, and edge data are not propagated to the new graph. For
    undirected graphs, the nodes in G must be sortable, otherwise the
    constructed line graph may not be correct.

    *Self-loops in undirected graphs*

    For an undirected graph `G` without multiple edges, each edge can be
    written as a set `\{u, v\}`.  Its line graph `L` has the edges of `G` as
    its nodes. If `x` and `y` are two nodes in `L`, then `\{x, y\}` is an edge
    in `L` if and only if the intersection of `x` and `y` is nonempty. Thus,
    the set of all edges is determined by the set of all pairwise intersections
    of edges in `G`.

    Trivially, every edge in G would have a nonzero intersection with itself,
    and so every node in `L` should have a self-loop. This is not so
    interesting, and the original context of line graphs was with simple
    graphs, which had no self-loops or multiple edges. The line graph was also
    meant to be a simple graph and thus, self-loops in `L` are not part of the
    standard definition of a line graph. In a pairwise intersection matrix,
    this is analogous to excluding the diagonal entries from the line graph
    definition.

    Self-loops and multiple edges in `G` add nodes to `L` in a natural way, and
    do not require any fundamental changes to the definition. It might be
    argued that the self-loops we excluded before should now be included.
    However, the self-loops are still "trivial" in some sense and thus, are
    usually excluded.

    *Self-loops in directed graphs*

    For a directed graph `G` without multiple edges, each edge can be written
    as a tuple `(u, v)`. Its line graph `L` has the edges of `G` as its
    nodes. If `x` and `y` are two nodes in `L`, then `(x, y)` is an edge in `L`
    if and only if the tail of `x` matches the head of `y`, for example, if `x
    = (a, b)` and `y = (b, c)` for some vertices `a`, `b`, and `c` in `G`.

    Due to the directed nature of the edges, it is no longer the case that
    every edge in `G` should have a self-loop in `L`. Now, the only time
    self-loops arise is if a node in `G` itself has a self-loop.  So such
    self-loops are no longer "trivial" but instead, represent essential
    features of the topology of `G`. For this reason, the historical
    development of line digraphs is such that self-loops are included. When the
    graph `G` has multiple edges, once again only superficial changes are
    required to the definition.

    References
    ----------
    * Harary, Frank, and Norman, Robert Z., "Some properties of line digraphs",
      Rend. Circ. Mat. Palermo, II. Ser. 9 (1960), 161--168.
    * Hemminger, R. L.; Beineke, L. W. (1978), "Line graphs and line digraphs",
      in Beineke, L. W.; Wilson, R. J., Selected Topics in Graph Theory,
      Academic Press Inc., pp. 271--305.
networkx.load
Python Library Documentation: module networkx.algorithms.centrality.load in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.load - Load centrality.

FUNCTIONS
    edge_load_centrality(G, cutoff=False, *, backend=None, **backend_kwargs)
        Compute edge load.

        WARNING: This concept of edge load has not been analysed
        or discussed outside of NetworkX that we know of.
        It is based loosely on load_centrality in the sense that
        it counts the number of shortest paths which cross each edge.
        This function is for demonstration and testing purposes.

        Parameters
        ----------
        G : graph
            A networkx graph

        cutoff : bool, optional (default=False)
            If specified, only consider paths of length <= cutoff.

        Returns
        -------
        A dict keyed by edge 2-tuple to the number of shortest paths
        which use that edge. Where more than one path is shortest
        the count is divided equally among paths.

    load_centrality = newman_betweenness_centrality(G, v=None, cutoff=None, normalized=True, weight=None, *, backend=None, **backend_kwargs)
        Compute load centrality for nodes.

        The load centrality of a node is the fraction of all shortest
        paths that pass through that node.

        Parameters
        ----------
        G : graph
          A networkx graph.

        normalized : bool, optional (default=True)
          If True the betweenness values are normalized by b=b/(n-1)(n-2) where
          n is the number of nodes in G.

        weight : None or string, optional (default=None)
          If None, edge weights are ignored.
          Otherwise holds the name of the edge attribute used as weight.
          The weight of an edge is treated as the length or distance between the two sides.

        cutoff : bool, optional (default=None)
          If specified, only consider paths of length <= cutoff.

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with centrality as the value.

        See Also
        --------
        betweenness_centrality

        Notes
        -----
        Load centrality is slightly different than betweenness. It was originally
        introduced by [2]_. For this load algorithm see [1]_.

        References
        ----------
        .. [1] Mark E. J. Newman:
           Scientific collaboration networks. II.
           Shortest paths, weighted networks, and centrality.
           Physical Review E 64, 016132, 2001.
           http://journals.aps.org/pre/abstract/10.1103/PhysRevE.64.016132
        .. [2] Kwang-Il Goh, Byungnam Kahng and Doochul Kim
           Universal behavior of Load Distribution in Scale-Free Networks.
           Physical Review Letters 87(27):1–4, 2001.
           https://doi.org/10.1103/PhysRevLett.87.278701

DATA
    __all__ = ['load_centrality', 'edge_load_centrality']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\load.py

networkx.load_centrality
Python Library Documentation: function newman_betweenness_centrality in module networkx.algorithms.centrality.load

newman_betweenness_centrality(G, v=None, cutoff=None, normalized=True, weight=None, *, backend=None, **backend_kwargs)
    Compute load centrality for nodes.

    The load centrality of a node is the fraction of all shortest
    paths that pass through that node.

    Parameters
    ----------
    G : graph
      A networkx graph.

    normalized : bool, optional (default=True)
      If True the betweenness values are normalized by b=b/(n-1)(n-2) where
      n is the number of nodes in G.

    weight : None or string, optional (default=None)
      If None, edge weights are ignored.
      Otherwise holds the name of the edge attribute used as weight.
      The weight of an edge is treated as the length or distance between the two sides.

    cutoff : bool, optional (default=None)
      If specified, only consider paths of length <= cutoff.

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with centrality as the value.

    See Also
    --------
    betweenness_centrality

    Notes
    -----
    Load centrality is slightly different than betweenness. It was originally
    introduced by [2]_. For this load algorithm see [1]_.

    References
    ----------
    .. [1] Mark E. J. Newman:
       Scientific collaboration networks. II.
       Shortest paths, weighted networks, and centrality.
       Physical Review E 64, 016132, 2001.
       http://journals.aps.org/pre/abstract/10.1103/PhysRevE.64.016132
    .. [2] Kwang-Il Goh, Byungnam Kahng and Doochul Kim
       Universal behavior of Load Distribution in Scale-Free Networks.
       Physical Review Letters 87(27):1–4, 2001.
       https://doi.org/10.1103/PhysRevLett.87.278701
networkx.local_bridges
Python Library Documentation: function local_bridges in module networkx.algorithms.bridges

local_bridges(G, with_span=True, weight=None, *, backend=None, **backend_kwargs)
    Iterate over local bridges of `G` optionally computing the span

    A *local bridge* is an edge whose endpoints have no common neighbors.
    That is, the edge is not part of a triangle in the graph.

    The *span* of a *local bridge* is the shortest path length between
    the endpoints if the local bridge is removed.

    Parameters
    ----------
    G : undirected graph

    with_span : bool
        If True, yield a 3-tuple `(u, v, span)`

    weight : function, string or None (default: None)
        If function, used to compute edge weights for the span.
        If string, the edge data attribute used in calculating span.
        If None, all edges have weight 1.

    Yields
    ------
    e : edge
        The local bridges as an edge 2-tuple of nodes `(u, v)` or
        as a 3-tuple `(u, v, span)` when `with_span is True`.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a directed graph or multigraph.

    Examples
    --------
    A cycle graph has every edge a local bridge with span N-1.

       >>> G = nx.cycle_graph(9)
       >>> (0, 8, 8) in set(nx.local_bridges(G))
       True
networkx.local_constraint
Python Library Documentation: function local_constraint in module networkx.algorithms.structuralholes

local_constraint(G, u, v, weight=None, *, backend=None, **backend_kwargs)
    Returns the local constraint on the node ``u`` with respect to
    the node ``v`` in the graph ``G``.

    Formally, the *local constraint on u with respect to v*, denoted
    $\ell(u, v)$, is defined by

    .. math::

       \ell(u, v) = \left(p_{uv} + \sum_{w \in N(v)} p_{uw} p_{wv}\right)^2,

    where $N(v)$ is the set of neighbors of $v$ and $p_{uv}$ is the
    normalized mutual weight of the (directed or undirected) edges
    joining $u$ and $v$, for each vertex $u$ and $v$ [1]_. The *mutual
    weight* of $u$ and $v$ is the sum of the weights of edges joining
    them (edge weights are assumed to be one if the graph is
    unweighted).

    Parameters
    ----------
    G : NetworkX graph
        The graph containing ``u`` and ``v``. This can be either
        directed or undirected.

    u : node
        A node in the graph ``G``.

    v : node
        A node in the graph ``G``.

    weight : None or string, optional
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.

    Returns
    -------
    float
        The constraint of the node ``v`` in the graph ``G``.

    See also
    --------
    constraint

    References
    ----------
    .. [1] Burt, Ronald S.
           "Structural holes and good ideas".
           American Journal of Sociology (110): 349–399.
networkx.local_efficiency
Python Library Documentation: function local_efficiency in module networkx.algorithms.efficiency_measures

local_efficiency(G, *, backend=None, **backend_kwargs)
    Returns the average local efficiency of the graph.

    The *efficiency* of a pair of nodes in a graph is the multiplicative
    inverse of the shortest path distance between the nodes. The *local
    efficiency* of a node in the graph is the average global efficiency of the
    subgraph induced by the neighbors of the node. The *average local
    efficiency* is the average of the local efficiencies of each node [1]_.

    Parameters
    ----------
    G : :class:`networkx.Graph`
        An undirected graph for which to compute the average local efficiency.

    Returns
    -------
    float
        The average local efficiency of the graph.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
    >>> nx.local_efficiency(G)
    0.9166666666666667

    Notes
    -----
    Edge weights are ignored when computing the shortest path distances.

    See also
    --------
    global_efficiency

    References
    ----------
    .. [1] Latora, Vito, and Massimo Marchiori.
           "Efficient behavior of small-world networks."
           *Physical Review Letters* 87.19 (2001): 198701.
           <https://doi.org/10.1103/PhysRevLett.87.198701>
networkx.local_reaching_centrality
Python Library Documentation: function local_reaching_centrality in module networkx.algorithms.centrality.reaching

local_reaching_centrality(G, v, paths=None, weight=None, normalized=True, *, backend=None, **backend_kwargs)
    Returns the local reaching centrality of a node in a directed
    graph.

    The *local reaching centrality* of a node in a directed graph is the
    proportion of other nodes reachable from that node [1]_.

    Parameters
    ----------
    G : DiGraph
        A NetworkX DiGraph.

    v : node
        A node in the directed graph `G`.

    paths : dictionary (default=None)
        If this is not `None` it must be a dictionary representation
        of single-source shortest paths, as computed by, for example,
        :func:`networkx.shortest_path` with source node `v`. Use this
        keyword argument if you intend to invoke this function many
        times but don't want the paths to be recomputed each time.

    weight : None or string, optional (default=None)
        Attribute to use for edge weights.  If `None`, each edge weight
        is assumed to be one. A higher weight implies a stronger
        connection between nodes and a *shorter* path length.

    normalized : bool, optional (default=True)
        Whether to normalize the edge weights by the total sum of edge
        weights.

    Returns
    -------
    h : float
        The local reaching centrality of the node ``v`` in the graph
        ``G``.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_edges_from([(1, 2), (1, 3)])
    >>> nx.local_reaching_centrality(G, 3)
    0.0
    >>> G.add_edge(3, 2)
    >>> nx.local_reaching_centrality(G, 3)
    0.5

    See also
    --------
    global_reaching_centrality

    References
    ----------
    .. [1] Mones, Enys, Lilla Vicsek, and Tamás Vicsek.
           "Hierarchy Measure for Complex Networks."
           *PLoS ONE* 7.3 (2012): e33799.
           https://doi.org/10.1371/journal.pone.0033799
networkx.lollipop_graph
Python Library Documentation: function lollipop_graph in module networkx.generators.classic

lollipop_graph(m, n, create_using=None, *, backend=None, **backend_kwargs)
    Returns the Lollipop Graph; ``K_m`` connected to ``P_n``.

    This is the Barbell Graph without the right barbell.

    .. plot::

        >>> nx.draw(nx.lollipop_graph(3, 4))

    Parameters
    ----------
    m, n : int or iterable container of nodes
        If an integer, nodes are from ``range(m)`` and ``range(m, m+n)``.
        If a container of nodes, those nodes appear in the graph.
        Warning: `m` and `n` are not checked for duplicates and if present the
        resulting graph may not be as desired. Make sure you have no duplicates.

        The nodes for `m` appear in the complete graph $K_m$ and the nodes
        for `n` appear in the path $P_n$
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    Networkx graph
       A complete graph with `m` nodes connected to a path of length `n`.

    Notes
    -----
    The 2 subgraphs are joined via an edge ``(m-1, m)``.
    If ``n=0``, this is merely a complete graph.

    (This graph is an extremal example in David Aldous and Jim
    Fill's etext on Random Walks on Graphs.)
networkx.lowest_common_ancestor
Python Library Documentation: function lowest_common_ancestor in module networkx.algorithms.lowest_common_ancestors

lowest_common_ancestor(G, node1, node2, default=None, *, backend=None, **backend_kwargs)
    Compute the lowest common ancestor of the given pair of nodes.

    Parameters
    ----------
    G : NetworkX directed graph

    node1, node2 : nodes in the graph.

    default : object
        Returned if no common ancestor between `node1` and `node2`

    Returns
    -------
    The lowest common ancestor of node1 and node2,
    or default if they have no common ancestors.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> nx.add_path(G, (0, 1, 2, 3))
    >>> nx.add_path(G, (0, 4, 3))
    >>> nx.lowest_common_ancestor(G, 2, 4)
    0

    See Also
    --------
    all_pairs_lowest_common_ancestor
networkx.lowest_common_ancestors
Python Library Documentation: module networkx.algorithms.lowest_common_ancestors in networkx.algorithms

NAME
    networkx.algorithms.lowest_common_ancestors - Algorithms for finding the lowest common ancestor of trees and DAGs.

FUNCTIONS
    all_pairs_lowest_common_ancestor(G, pairs=None, *, backend=None, **backend_kwargs)
        Return the lowest common ancestor of all pairs or the provided pairs

        Parameters
        ----------
        G : NetworkX directed graph

        pairs : iterable of pairs of nodes, optional (default: all pairs)
            The pairs of nodes of interest.
            If None, will find the LCA of all pairs of nodes.

        Yields
        ------
        ((node1, node2), lca) : 2-tuple
            Where lca is least common ancestor of node1 and node2.
            Note that for the default case, the order of the node pair is not considered,
            e.g. you will not get both ``(a, b)`` and ``(b, a)``

        Raises
        ------
        NetworkXPointlessConcept
            If `G` is null.
        NetworkXError
            If `G` is not a DAG.

        Examples
        --------
        The default behavior is to yield the lowest common ancestor for all
        possible combinations of nodes in `G`, including self-pairings:

        >>> G = nx.DiGraph([(0, 1), (0, 3), (1, 2)])
        >>> dict(nx.all_pairs_lowest_common_ancestor(G))
        {(0, 0): 0, (0, 1): 0, (0, 3): 0, (0, 2): 0, (1, 1): 1, (1, 3): 0, (1, 2): 1, (3, 3): 3, (3, 2): 0, (2, 2): 2}

        The pairs argument can be used to limit the output to only the
        specified node pairings:

        >>> dict(nx.all_pairs_lowest_common_ancestor(G, pairs=[(1, 2), (2, 3)]))
        {(1, 2): 1, (2, 3): 0}

        Notes
        -----
        Only defined on non-null directed acyclic graphs.

        See Also
        --------
        lowest_common_ancestor

    lowest_common_ancestor(G, node1, node2, default=None, *, backend=None, **backend_kwargs)
        Compute the lowest common ancestor of the given pair of nodes.

        Parameters
        ----------
        G : NetworkX directed graph

        node1, node2 : nodes in the graph.

        default : object
            Returned if no common ancestor between `node1` and `node2`

        Returns
        -------
        The lowest common ancestor of node1 and node2,
        or default if they have no common ancestors.

        Examples
        --------
        >>> G = nx.DiGraph()
        >>> nx.add_path(G, (0, 1, 2, 3))
        >>> nx.add_path(G, (0, 4, 3))
        >>> nx.lowest_common_ancestor(G, 2, 4)
        0

        See Also
        --------
        all_pairs_lowest_common_ancestor

    tree_all_pairs_lowest_common_ancestor(G, root=None, pairs=None, *, backend=None, **backend_kwargs)
        Yield the lowest common ancestor for sets of pairs in a tree.

        Parameters
        ----------
        G : NetworkX directed graph (must be a tree)

        root : node, optional (default: None)
            The root of the subtree to operate on.
            If None, assume the entire graph has exactly one source and use that.

        pairs : iterable or iterator of pairs of nodes, optional (default: None)
            The pairs of interest. If None, Defaults to all pairs of nodes
            under `root` that have a lowest common ancestor.

        Returns
        -------
        lcas : generator of tuples `((u, v), lca)` where `u` and `v` are nodes
            in `pairs` and `lca` is their lowest common ancestor.

        Examples
        --------
        >>> import pprint
        >>> G = nx.DiGraph([(1, 3), (2, 4), (1, 2)])
        >>> pprint.pprint(dict(nx.tree_all_pairs_lowest_common_ancestor(G)))
        {(1, 1): 1,
         (2, 1): 1,
         (2, 2): 2,
         (3, 1): 1,
         (3, 2): 1,
         (3, 3): 3,
         (3, 4): 1,
         (4, 1): 1,
         (4, 2): 2,
         (4, 4): 4}

        We can also use `pairs` argument to specify the pairs of nodes for which we
        want to compute lowest common ancestors. Here is an example:

        >>> dict(nx.tree_all_pairs_lowest_common_ancestor(G, pairs=[(1, 4), (2, 3)]))
        {(2, 3): 1, (1, 4): 1}

        Notes
        -----
        Only defined on non-null trees represented with directed edges from
        parents to children. Uses Tarjan's off-line lowest-common-ancestors
        algorithm. Runs in time $O(4 \times (V + E + P))$ time, where 4 is the largest
        value of the inverse Ackermann function likely to ever come up in actual
        use, and $P$ is the number of pairs requested (or $V^2$ if all are needed).

        Tarjan, R. E. (1979), "Applications of path compression on balanced trees",
        Journal of the ACM 26 (4): 690-715, doi:10.1145/322154.322161.

        See Also
        --------
        all_pairs_lowest_common_ancestor: similar routine for general DAGs
        lowest_common_ancestor: just a single pair for general DAGs

DATA
    __all__ = ['all_pairs_lowest_common_ancestor', 'tree_all_pairs_lowest_...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\lowest_common_ancestors.py

networkx.make_clique_bipartite
Python Library Documentation: function make_clique_bipartite in module networkx.algorithms.clique

make_clique_bipartite(G, fpos=None, create_using=None, name=None, *, backend=None, **backend_kwargs)
    Returns the bipartite clique graph corresponding to `G`.

    In the returned bipartite graph, the "bottom" nodes are the nodes of
    `G` and the "top" nodes represent the maximal cliques of `G`.
    There is an edge from node *v* to clique *C* in the returned graph
    if and only if *v* is an element of *C*.

    Parameters
    ----------
    G : NetworkX graph
        An undirected graph.

    fpos : bool
        If True or not None, the returned graph will have an
        additional attribute, `pos`, a dictionary mapping node to
        position in the Euclidean plane.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    NetworkX graph
        A bipartite graph whose "bottom" set is the nodes of the graph
        `G`, whose "top" set is the cliques of `G`, and whose edges
        join nodes of `G` to the cliques that contain them.

        The nodes of the graph `G` have the node attribute
        'bipartite' set to 1 and the nodes representing cliques
        have the node attribute 'bipartite' set to 0, as is the
        convention for bipartite graphs in NetworkX.
networkx.make_max_clique_graph
Python Library Documentation: function make_max_clique_graph in module networkx.algorithms.clique

make_max_clique_graph(G, create_using=None, *, backend=None, **backend_kwargs)
    Returns the maximal clique graph of the given graph.

    The nodes of the maximal clique graph of `G` are the cliques of
    `G` and an edge joins two cliques if the cliques are not disjoint.

    Parameters
    ----------
    G : NetworkX graph

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    NetworkX graph
        A graph whose nodes are the cliques of `G` and whose edges
        join two cliques if they are not disjoint.

    Notes
    -----
    This function behaves like the following code::

        import networkx as nx

        G = nx.make_clique_bipartite(G)
        cliques = [v for v in G.nodes() if G.nodes[v]["bipartite"] == 0]
        G = nx.bipartite.projected_graph(G, cliques)
        G = nx.relabel_nodes(G, {-v: v - 1 for v in G})

    It should be faster, though, since it skips all the intermediate
    steps.
networkx.margulis_gabber_galil_graph
Python Library Documentation: function margulis_gabber_galil_graph in module networkx.generators.expanders

margulis_gabber_galil_graph(n, create_using=None, *, backend=None, **backend_kwargs)
    Returns the Margulis-Gabber-Galil undirected MultiGraph on `n^2` nodes.

    The undirected MultiGraph is regular with degree `8`. Nodes are integer
    pairs. The second-largest eigenvalue of the adjacency matrix of the graph
    is at most `5 \sqrt{2}`, regardless of `n`.

    Parameters
    ----------
    n : int
        Determines the number of nodes in the graph: `n^2`.
    create_using : NetworkX graph constructor, optional (default MultiGraph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : graph
        The constructed undirected multigraph.

    Raises
    ------
    NetworkXError
        If the graph is directed or not a multigraph.
networkx.matching
Python Library Documentation: module networkx.algorithms.matching in networkx.algorithms

NAME
    networkx.algorithms.matching - Functions for computing and verifying matchings in a graph.

FUNCTIONS
    is_matching(G, matching, *, backend=None, **backend_kwargs)
        Return True if ``matching`` is a valid matching of ``G``

        A *matching* in a graph is a set of edges in which no two distinct
        edges share a common endpoint. Each node is incident to at most one
        edge in the matching. The edges are said to be independent.

        Parameters
        ----------
        G : NetworkX graph

        matching : dict or set
            A dictionary or set representing a matching. If a dictionary, it
            must have ``matching[u] == v`` and ``matching[v] == u`` for each
            edge ``(u, v)`` in the matching. If a set, it must have elements
            of the form ``(u, v)``, where ``(u, v)`` is an edge in the
            matching.

        Returns
        -------
        bool
            Whether the given set or dictionary represents a valid matching
            in the graph.

        Raises
        ------
        NetworkXError
            If the proposed matching has an edge to a node not in G.
            Or if the matching is not a collection of 2-tuple edges.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (2, 4), (3, 5), (4, 5)])
        >>> nx.is_maximal_matching(G, {1: 3, 2: 4})  # using dict to represent matching
        True

        >>> nx.is_matching(G, {(1, 3), (2, 4)})  # using set to represent matching
        True

    is_maximal_matching(G, matching, *, backend=None, **backend_kwargs)
        Return True if ``matching`` is a maximal matching of ``G``

        A *maximal matching* in a graph is a matching in which adding any
        edge would cause the set to no longer be a valid matching.

        Parameters
        ----------
        G : NetworkX graph

        matching : dict or set
            A dictionary or set representing a matching. If a dictionary, it
            must have ``matching[u] == v`` and ``matching[v] == u`` for each
            edge ``(u, v)`` in the matching. If a set, it must have elements
            of the form ``(u, v)``, where ``(u, v)`` is an edge in the
            matching.

        Returns
        -------
        bool
            Whether the given set or dictionary represents a valid maximal
            matching in the graph.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (3, 4), (3, 5)])
        >>> nx.is_maximal_matching(G, {(1, 2), (3, 4)})
        True

    is_perfect_matching(G, matching, *, backend=None, **backend_kwargs)
        Return True if ``matching`` is a perfect matching for ``G``

        A *perfect matching* in a graph is a matching in which exactly one edge
        is incident upon each vertex.

        Parameters
        ----------
        G : NetworkX graph

        matching : dict or set
            A dictionary or set representing a matching. If a dictionary, it
            must have ``matching[u] == v`` and ``matching[v] == u`` for each
            edge ``(u, v)`` in the matching. If a set, it must have elements
            of the form ``(u, v)``, where ``(u, v)`` is an edge in the
            matching.

        Returns
        -------
        bool
            Whether the given set or dictionary represents a valid perfect
            matching in the graph.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (2, 4), (3, 5), (4, 5), (4, 6)])
        >>> my_match = {1: 2, 3: 5, 4: 6}
        >>> nx.is_perfect_matching(G, my_match)
        True

    max_weight_matching(G, maxcardinality=False, weight='weight', *, backend=None, **backend_kwargs)
        Compute a maximum-weighted matching of G.

        A matching is a subset of edges in which no node occurs more than once.
        The weight of a matching is the sum of the weights of its edges.
        A maximal matching cannot add more edges and still be a matching.
        The cardinality of a matching is the number of matched edges.

        Parameters
        ----------
        G : NetworkX graph
          Undirected graph

        maxcardinality: bool, optional (default=False)
           If maxcardinality is True, compute the maximum-cardinality matching
           with maximum weight among all maximum-cardinality matchings.

        weight: string, optional (default='weight')
           Edge data key corresponding to the edge weight.
           If key not found, uses 1 as weight.


        Returns
        -------
        matching : set
            A maximal matching of the graph.

         Examples
        --------
        >>> G = nx.Graph()
        >>> edges = [(1, 2, 6), (1, 3, 2), (2, 3, 1), (2, 4, 7), (3, 5, 9), (4, 5, 3)]
        >>> G.add_weighted_edges_from(edges)
        >>> sorted(nx.max_weight_matching(G))
        [(2, 4), (5, 3)]

        Notes
        -----
        If G has edges with weight attributes the edge data are used as
        weight values else the weights are assumed to be 1.

        This function takes time O(number_of_nodes ** 3).

        If all edge weights are integers, the algorithm uses only integer
        computations.  If floating point weights are used, the algorithm
        could return a slightly suboptimal matching due to numeric
        precision errors.

        This method is based on the "blossom" method for finding augmenting
        paths and the "primal-dual" method for finding a matching of maximum
        weight, both methods invented by Jack Edmonds [1]_.

        Bipartite graphs can also be matched using the functions present in
        :mod:`networkx.algorithms.bipartite.matching`.

        References
        ----------
        .. [1] "Efficient Algorithms for Finding Maximum Matching in Graphs",
           Zvi Galil, ACM Computing Surveys, 1986.

    maximal_matching(G, *, backend=None, **backend_kwargs)
        Find a maximal matching in the graph.

        A matching is a subset of edges in which no node occurs more than once.
        A maximal matching cannot add more edges and still be a matching.

        Parameters
        ----------
        G : NetworkX graph
            Undirected graph

        Returns
        -------
        matching : set
            A maximal matching of the graph.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (2, 4), (3, 5), (4, 5)])
        >>> sorted(nx.maximal_matching(G))
        [(1, 2), (3, 5)]

        Notes
        -----
        The algorithm greedily selects a maximal matching M of the graph G
        (i.e. no superset of M exists). It runs in $O(|E|)$ time.

    min_weight_matching(G, weight='weight', *, backend=None, **backend_kwargs)
        Computing a minimum-weight maximal matching of G.

        Use the maximum-weight algorithm with edge weights subtracted
        from the maximum weight of all edges.

        A matching is a subset of edges in which no node occurs more than once.
        The weight of a matching is the sum of the weights of its edges.
        A maximal matching cannot add more edges and still be a matching.
        The cardinality of a matching is the number of matched edges.

        This method replaces the edge weights with 1 plus the maximum edge weight
        minus the original edge weight.

        new_weight = (max_weight + 1) - edge_weight

        then runs :func:`max_weight_matching` with the new weights.
        The max weight matching with these new weights corresponds
        to the min weight matching using the original weights.
        Adding 1 to the max edge weight keeps all edge weights positive
        and as integers if they started as integers.

        You might worry that adding 1 to each weight would make the algorithm
        favor matchings with more edges. But we use the parameter
        `maxcardinality=True` in `max_weight_matching` to ensure that the
        number of edges in the competing matchings are the same and thus
        the optimum does not change due to changes in the number of edges.

        Read the documentation of `max_weight_matching` for more information.

        Parameters
        ----------
        G : NetworkX graph
          Undirected graph

        weight: string, optional (default='weight')
           Edge data key corresponding to the edge weight.
           If key not found, uses 1 as weight.

        Returns
        -------
        matching : set
            A minimal weight matching of the graph.

        See Also
        --------
        max_weight_matching

DATA
    __all__ = ['is_matching', 'is_maximal_matching', 'is_perfect_matching'...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\matching.py

networkx.max_flow_min_cost
Python Library Documentation: function max_flow_min_cost in module networkx.algorithms.flow.mincost

max_flow_min_cost(G, s, t, capacity='capacity', weight='weight', *, backend=None, **backend_kwargs)
    Returns a maximum (s, t)-flow of minimum cost.

    G is a digraph with edge costs and capacities. There is a source
    node s and a sink node t. This function finds a maximum flow from
    s to t whose total cost is minimized.

    Parameters
    ----------
    G : NetworkX graph
        DiGraph on which a minimum cost flow satisfying all demands is
        to be found.

    s: node label
        Source of the flow.

    t: node label
        Destination of the flow.

    capacity: string
        Edges of the graph G are expected to have an attribute capacity
        that indicates how much flow the edge can support. If this
        attribute is not present, the edge is considered to have
        infinite capacity. Default value: 'capacity'.

    weight: string
        Edges of the graph G are expected to have an attribute weight
        that indicates the cost incurred by sending one unit of flow on
        that edge. If not present, the weight is considered to be 0.
        Default value: 'weight'.

    Returns
    -------
    flowDict: dictionary
        Dictionary of dictionaries keyed by nodes such that
        flowDict[u][v] is the flow edge (u, v).

    Raises
    ------
    NetworkXError
        This exception is raised if the input graph is not directed or
        not connected.

    NetworkXUnbounded
        This exception is raised if there is an infinite capacity path
        from s to t in G. In this case there is no maximum flow. This
        exception is also raised if the digraph G has a cycle of
        negative cost and infinite capacity. Then, the cost of a flow
        is unbounded below.

    See also
    --------
    cost_of_flow, min_cost_flow, min_cost_flow_cost, network_simplex

    Notes
    -----
    This algorithm is not guaranteed to work if edge weights or demands
    are floating point numbers (overflows and roundoff errors can
    cause problems). As a workaround you can use integer numbers by
    multiplying the relevant edge attributes by a convenient
    constant factor (eg 100).

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_edges_from(
    ...     [
    ...         (1, 2, {"capacity": 12, "weight": 4}),
    ...         (1, 3, {"capacity": 20, "weight": 6}),
    ...         (2, 3, {"capacity": 6, "weight": -3}),
    ...         (2, 6, {"capacity": 14, "weight": 1}),
    ...         (3, 4, {"weight": 9}),
    ...         (3, 5, {"capacity": 10, "weight": 5}),
    ...         (4, 2, {"capacity": 19, "weight": 13}),
    ...         (4, 5, {"capacity": 4, "weight": 0}),
    ...         (5, 7, {"capacity": 28, "weight": 2}),
    ...         (6, 5, {"capacity": 11, "weight": 1}),
    ...         (6, 7, {"weight": 8}),
    ...         (7, 4, {"capacity": 6, "weight": 6}),
    ...     ]
    ... )
    >>> mincostFlow = nx.max_flow_min_cost(G, 1, 7)
    >>> mincost = nx.cost_of_flow(G, mincostFlow)
    >>> mincost
    373
    >>> from networkx.algorithms.flow import maximum_flow
    >>> maxFlow = maximum_flow(G, 1, 7)[1]
    >>> nx.cost_of_flow(G, maxFlow) >= mincost
    True
    >>> mincostFlowValue = sum((mincostFlow[u][7] for u in G.predecessors(7))) - sum(
    ...     (mincostFlow[7][v] for v in G.successors(7))
    ... )
    >>> mincostFlowValue == nx.maximum_flow_value(G, 1, 7)
    True
networkx.max_weight_clique
Python Library Documentation: function max_weight_clique in module networkx.algorithms.clique

max_weight_clique(G, weight='weight', *, backend=None, **backend_kwargs)
    Find a maximum weight clique in G.

    A *clique* in a graph is a set of nodes such that every two distinct nodes
    are adjacent.  The *weight* of a clique is the sum of the weights of its
    nodes.  A *maximum weight clique* of graph G is a clique C in G such that
    no clique in G has weight greater than the weight of C.

    Parameters
    ----------
    G : NetworkX graph
        Undirected graph
    weight : string or None, optional (default='weight')
        The node attribute that holds the integer value used as a weight.
        If None, then each node has weight 1.

    Returns
    -------
    clique : list
        the nodes of a maximum weight clique
    weight : int
        the weight of a maximum weight clique

    Notes
    -----
    The implementation is recursive, and therefore it may run into recursion
    depth issues if G contains a clique whose number of nodes is close to the
    recursion depth limit.

    At each search node, the algorithm greedily constructs a weighted
    independent set cover of part of the graph in order to find a small set of
    nodes on which to branch.  The algorithm is very similar to the algorithm
    of Tavares et al. [1]_, other than the fact that the NetworkX version does
    not use bitsets.  This style of algorithm for maximum weight clique (and
    maximum weight independent set, which is the same problem but on the
    complement graph) has a decades-long history.  See Algorithm B of Warren
    and Hicks [2]_ and the references in that paper.

    References
    ----------
    .. [1] Tavares, W.A., Neto, M.B.C., Rodrigues, C.D., Michelon, P.: Um
           algoritmo de branch and bound para o problema da clique máxima
           ponderada.  Proceedings of XLVII SBPO 1 (2015).

    .. [2] Warren, Jeffrey S, Hicks, Illya V.: Combinatorial Branch-and-Bound
           for the Maximum Weight Independent Set Problem.  Technical Report,
           Texas A&M University (2016).
networkx.max_weight_matching
Python Library Documentation: function max_weight_matching in module networkx.algorithms.matching

max_weight_matching(G, maxcardinality=False, weight='weight', *, backend=None, **backend_kwargs)
    Compute a maximum-weighted matching of G.

    A matching is a subset of edges in which no node occurs more than once.
    The weight of a matching is the sum of the weights of its edges.
    A maximal matching cannot add more edges and still be a matching.
    The cardinality of a matching is the number of matched edges.

    Parameters
    ----------
    G : NetworkX graph
      Undirected graph

    maxcardinality: bool, optional (default=False)
       If maxcardinality is True, compute the maximum-cardinality matching
       with maximum weight among all maximum-cardinality matchings.

    weight: string, optional (default='weight')
       Edge data key corresponding to the edge weight.
       If key not found, uses 1 as weight.


    Returns
    -------
    matching : set
        A maximal matching of the graph.

     Examples
    --------
    >>> G = nx.Graph()
    >>> edges = [(1, 2, 6), (1, 3, 2), (2, 3, 1), (2, 4, 7), (3, 5, 9), (4, 5, 3)]
    >>> G.add_weighted_edges_from(edges)
    >>> sorted(nx.max_weight_matching(G))
    [(2, 4), (5, 3)]

    Notes
    -----
    If G has edges with weight attributes the edge data are used as
    weight values else the weights are assumed to be 1.

    This function takes time O(number_of_nodes ** 3).

    If all edge weights are integers, the algorithm uses only integer
    computations.  If floating point weights are used, the algorithm
    could return a slightly suboptimal matching due to numeric
    precision errors.

    This method is based on the "blossom" method for finding augmenting
    paths and the "primal-dual" method for finding a matching of maximum
    weight, both methods invented by Jack Edmonds [1]_.

    Bipartite graphs can also be matched using the functions present in
    :mod:`networkx.algorithms.bipartite.matching`.

    References
    ----------
    .. [1] "Efficient Algorithms for Finding Maximum Matching in Graphs",
       Zvi Galil, ACM Computing Surveys, 1986.
networkx.maximal_independent_set
Python Library Documentation: function maximal_independent_set in module networkx.algorithms.mis

maximal_independent_set(G, nodes=None, seed=None, *, backend=None, **backend_kwargs)
    Returns a random maximal independent set guaranteed to contain
    a given set of nodes.

    An independent set is a set of nodes such that the subgraph
    of G induced by these nodes contains no edges. A maximal
    independent set is an independent set such that it is not possible
    to add a new node and still get an independent set.

    Parameters
    ----------
    G : NetworkX graph

    nodes : list or iterable
       Nodes that must be part of the independent set. This set of nodes
       must be independent.

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    indep_nodes : list
       List of nodes that are part of a maximal independent set.

    Raises
    ------
    NetworkXUnfeasible
       If the nodes in the provided list are not part of the graph or
       do not form an independent set, an exception is raised.

    NetworkXNotImplemented
        If `G` is directed.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> nx.maximal_independent_set(G)  # doctest: +SKIP
    [4, 0, 2]
    >>> nx.maximal_independent_set(G, [1])  # doctest: +SKIP
    [1, 3]

    Notes
    -----
    This algorithm does not solve the maximum independent set problem.
networkx.maximal_matching
Python Library Documentation: function maximal_matching in module networkx.algorithms.matching

maximal_matching(G, *, backend=None, **backend_kwargs)
    Find a maximal matching in the graph.

    A matching is a subset of edges in which no node occurs more than once.
    A maximal matching cannot add more edges and still be a matching.

    Parameters
    ----------
    G : NetworkX graph
        Undirected graph

    Returns
    -------
    matching : set
        A maximal matching of the graph.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (2, 4), (3, 5), (4, 5)])
    >>> sorted(nx.maximal_matching(G))
    [(1, 2), (3, 5)]

    Notes
    -----
    The algorithm greedily selects a maximal matching M of the graph G
    (i.e. no superset of M exists). It runs in $O(|E|)$ time.
networkx.maximum_branching
Python Library Documentation: function maximum_branching in module networkx.algorithms.tree.branchings

maximum_branching(G, attr='weight', default=1, preserve_attrs=False, partition=None, *, backend=None, **backend_kwargs)
    Returns a maximum branching from G.

    Parameters
    ----------
    G : (multi)digraph-like
        The graph to be searched.
    attr : str
        The edge attribute used to in determining optimality.
    default : float
        The value of the edge attribute used if an edge does not have
        the attribute `attr`.
    preserve_attrs : bool
        If True, preserve the other attributes of the original graph (that are not
        passed to `attr`)
    partition : str
        The key for the edge attribute containing the partition
        data on the graph. Edges can be included, excluded or open using the
        `EdgePartition` enum.

    Returns
    -------
    B : (multi)digraph-like
        A maximum branching.
networkx.maximum_flow
Python Library Documentation: function maximum_flow in module networkx.algorithms.flow.maxflow

maximum_flow(flowG, _s, _t, capacity='capacity', flow_func=None, *, backend=None, **kwargs)
    Find a maximum single-commodity flow.

    Parameters
    ----------
    flowG : NetworkX graph
        Edges of the graph are expected to have an attribute called
        'capacity'. If this attribute is not present, the edge is
        considered to have infinite capacity.

    _s : node
        Source node for the flow.

    _t : node
        Sink node for the flow.

    capacity : string
        Edges of the graph G are expected to have an attribute capacity
        that indicates how much flow the edge can support. If this
        attribute is not present, the edge is considered to have
        infinite capacity. Default value: 'capacity'.

    flow_func : function
        A function for computing the maximum flow among a pair of nodes
        in a capacitated graph. The function has to accept at least three
        parameters: a Graph or Digraph, a source node, and a target node.
        And return a residual network that follows NetworkX conventions
        (see Notes). If flow_func is None, the default maximum
        flow function (:meth:`preflow_push`) is used. See below for
        alternative algorithms. The choice of the default function may change
        from version to version and should not be relied on. Default value:
        None.

    kwargs : Any other keyword parameter is passed to the function that
        computes the maximum flow.

    Returns
    -------
    flow_value : integer, float
        Value of the maximum flow, i.e., net outflow from the source.

    flow_dict : dict
        A dictionary containing the value of the flow that went through
        each edge.

    Raises
    ------
    NetworkXError
        The algorithm does not support MultiGraph and MultiDiGraph. If
        the input graph is an instance of one of these two classes, a
        NetworkXError is raised.

    NetworkXUnbounded
        If the graph has a path of infinite capacity, the value of a
        feasible flow on the graph is unbounded above and the function
        raises a NetworkXUnbounded.

    See also
    --------
    :meth:`maximum_flow_value`
    :meth:`minimum_cut`
    :meth:`minimum_cut_value`
    :meth:`edmonds_karp`
    :meth:`preflow_push`
    :meth:`shortest_augmenting_path`

    Notes
    -----
    The function used in the flow_func parameter has to return a residual
    network that follows NetworkX conventions:

    The residual network :samp:`R` from an input graph :samp:`G` has the
    same nodes as :samp:`G`. :samp:`R` is a DiGraph that contains a pair
    of edges :samp:`(u, v)` and :samp:`(v, u)` iff :samp:`(u, v)` is not a
    self-loop, and at least one of :samp:`(u, v)` and :samp:`(v, u)` exists
    in :samp:`G`.

    For each edge :samp:`(u, v)` in :samp:`R`, :samp:`R[u][v]['capacity']`
    is equal to the capacity of :samp:`(u, v)` in :samp:`G` if it exists
    in :samp:`G` or zero otherwise. If the capacity is infinite,
    :samp:`R[u][v]['capacity']` will have a high arbitrary finite value
    that does not affect the solution of the problem. This value is stored in
    :samp:`R.graph['inf']`. For each edge :samp:`(u, v)` in :samp:`R`,
    :samp:`R[u][v]['flow']` represents the flow function of :samp:`(u, v)` and
    satisfies :samp:`R[u][v]['flow'] == -R[v][u]['flow']`.

    The flow value, defined as the total flow into :samp:`t`, the sink, is
    stored in :samp:`R.graph['flow_value']`. Reachability to :samp:`t` using
    only edges :samp:`(u, v)` such that
    :samp:`R[u][v]['flow'] < R[u][v]['capacity']` induces a minimum
    :samp:`s`-:samp:`t` cut.

    Specific algorithms may store extra data in :samp:`R`.

    The function should supports an optional boolean parameter value_only. When
    True, it can optionally terminate the algorithm as soon as the maximum flow
    value and the minimum cut can be determined.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_edge("x", "a", capacity=3.0)
    >>> G.add_edge("x", "b", capacity=1.0)
    >>> G.add_edge("a", "c", capacity=3.0)
    >>> G.add_edge("b", "c", capacity=5.0)
    >>> G.add_edge("b", "d", capacity=4.0)
    >>> G.add_edge("d", "e", capacity=2.0)
    >>> G.add_edge("c", "y", capacity=2.0)
    >>> G.add_edge("e", "y", capacity=3.0)

    maximum_flow returns both the value of the maximum flow and a
    dictionary with all flows.

    >>> flow_value, flow_dict = nx.maximum_flow(G, "x", "y")
    >>> flow_value
    3.0
    >>> print(flow_dict["x"]["b"])
    1.0

    You can also use alternative algorithms for computing the
    maximum flow by using the flow_func parameter.

    >>> from networkx.algorithms.flow import shortest_augmenting_path
    >>> flow_value == nx.maximum_flow(G, "x", "y", flow_func=shortest_augmenting_path)[
    ...     0
    ... ]
    True
networkx.maximum_flow_value
Python Library Documentation: function maximum_flow_value in module networkx.algorithms.flow.maxflow

maximum_flow_value(flowG, _s, _t, capacity='capacity', flow_func=None, *, backend=None, **kwargs)
    Find the value of maximum single-commodity flow.

    Parameters
    ----------
    flowG : NetworkX graph
        Edges of the graph are expected to have an attribute called
        'capacity'. If this attribute is not present, the edge is
        considered to have infinite capacity.

    _s : node
        Source node for the flow.

    _t : node
        Sink node for the flow.

    capacity : string
        Edges of the graph G are expected to have an attribute capacity
        that indicates how much flow the edge can support. If this
        attribute is not present, the edge is considered to have
        infinite capacity. Default value: 'capacity'.

    flow_func : function
        A function for computing the maximum flow among a pair of nodes
        in a capacitated graph. The function has to accept at least three
        parameters: a Graph or Digraph, a source node, and a target node.
        And return a residual network that follows NetworkX conventions
        (see Notes). If flow_func is None, the default maximum
        flow function (:meth:`preflow_push`) is used. See below for
        alternative algorithms. The choice of the default function may change
        from version to version and should not be relied on. Default value:
        None.

    kwargs : Any other keyword parameter is passed to the function that
        computes the maximum flow.

    Returns
    -------
    flow_value : integer, float
        Value of the maximum flow, i.e., net outflow from the source.

    Raises
    ------
    NetworkXError
        The algorithm does not support MultiGraph and MultiDiGraph. If
        the input graph is an instance of one of these two classes, a
        NetworkXError is raised.

    NetworkXUnbounded
        If the graph has a path of infinite capacity, the value of a
        feasible flow on the graph is unbounded above and the function
        raises a NetworkXUnbounded.

    See also
    --------
    :meth:`maximum_flow`
    :meth:`minimum_cut`
    :meth:`minimum_cut_value`
    :meth:`edmonds_karp`
    :meth:`preflow_push`
    :meth:`shortest_augmenting_path`

    Notes
    -----
    The function used in the flow_func parameter has to return a residual
    network that follows NetworkX conventions:

    The residual network :samp:`R` from an input graph :samp:`G` has the
    same nodes as :samp:`G`. :samp:`R` is a DiGraph that contains a pair
    of edges :samp:`(u, v)` and :samp:`(v, u)` iff :samp:`(u, v)` is not a
    self-loop, and at least one of :samp:`(u, v)` and :samp:`(v, u)` exists
    in :samp:`G`.

    For each edge :samp:`(u, v)` in :samp:`R`, :samp:`R[u][v]['capacity']`
    is equal to the capacity of :samp:`(u, v)` in :samp:`G` if it exists
    in :samp:`G` or zero otherwise. If the capacity is infinite,
    :samp:`R[u][v]['capacity']` will have a high arbitrary finite value
    that does not affect the solution of the problem. This value is stored in
    :samp:`R.graph['inf']`. For each edge :samp:`(u, v)` in :samp:`R`,
    :samp:`R[u][v]['flow']` represents the flow function of :samp:`(u, v)` and
    satisfies :samp:`R[u][v]['flow'] == -R[v][u]['flow']`.

    The flow value, defined as the total flow into :samp:`t`, the sink, is
    stored in :samp:`R.graph['flow_value']`. Reachability to :samp:`t` using
    only edges :samp:`(u, v)` such that
    :samp:`R[u][v]['flow'] < R[u][v]['capacity']` induces a minimum
    :samp:`s`-:samp:`t` cut.

    Specific algorithms may store extra data in :samp:`R`.

    The function should supports an optional boolean parameter value_only. When
    True, it can optionally terminate the algorithm as soon as the maximum flow
    value and the minimum cut can be determined.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_edge("x", "a", capacity=3.0)
    >>> G.add_edge("x", "b", capacity=1.0)
    >>> G.add_edge("a", "c", capacity=3.0)
    >>> G.add_edge("b", "c", capacity=5.0)
    >>> G.add_edge("b", "d", capacity=4.0)
    >>> G.add_edge("d", "e", capacity=2.0)
    >>> G.add_edge("c", "y", capacity=2.0)
    >>> G.add_edge("e", "y", capacity=3.0)

    maximum_flow_value computes only the value of the
    maximum flow:

    >>> flow_value = nx.maximum_flow_value(G, "x", "y")
    >>> flow_value
    3.0

    You can also use alternative algorithms for computing the
    maximum flow by using the flow_func parameter.

    >>> from networkx.algorithms.flow import shortest_augmenting_path
    >>> flow_value == nx.maximum_flow_value(
    ...     G, "x", "y", flow_func=shortest_augmenting_path
    ... )
    True
networkx.maximum_spanning_arborescence
Python Library Documentation: function maximum_spanning_arborescence in module networkx.algorithms.tree.branchings

maximum_spanning_arborescence(G, attr='weight', default=1, preserve_attrs=False, partition=None, *, backend=None, **backend_kwargs)
    Returns a maximum spanning arborescence from G.

    Parameters
    ----------
    G : (multi)digraph-like
        The graph to be searched.
    attr : str
        The edge attribute used to in determining optimality.
    default : float
        The value of the edge attribute used if an edge does not have
        the attribute `attr`.
    preserve_attrs : bool
        If True, preserve the other attributes of the original graph (that are not
        passed to `attr`)
    partition : str
        The key for the edge attribute containing the partition
        data on the graph. Edges can be included, excluded or open using the
        `EdgePartition` enum.

    Returns
    -------
    B : (multi)digraph-like
        A maximum spanning arborescence.

    Raises
    ------
    NetworkXException
        If the graph does not contain a maximum spanning arborescence.
networkx.maximum_spanning_edges
Python Library Documentation: function maximum_spanning_edges in module networkx.algorithms.tree.mst

maximum_spanning_edges(G, algorithm='kruskal', weight='weight', keys=True, data=True, ignore_nan=False, *, backend=None, **backend_kwargs)
    Generate edges in a maximum spanning forest of an undirected
    weighted graph.

    A maximum spanning tree is a subgraph of the graph (a tree)
    with the maximum possible sum of edge weights.  A spanning forest is a
    union of the spanning trees for each connected component of the graph.

    Parameters
    ----------
    G : undirected Graph
       An undirected graph. If `G` is connected, then the algorithm finds a
       spanning tree. Otherwise, a spanning forest is found.

    algorithm : string
       The algorithm to use when finding a maximum spanning tree. Valid
       choices are 'kruskal', 'prim', or 'boruvka'. The default is 'kruskal'.

    weight : string
       Edge data key to use for weight (default 'weight').

    keys : bool
       Whether to yield edge key in multigraphs in addition to the edge.
       If `G` is not a multigraph, this is ignored.

    data : bool, optional
       If True yield the edge data along with the edge.

    ignore_nan : bool (default: False)
        If a NaN is found as an edge weight normally an exception is raised.
        If `ignore_nan is True` then that edge is ignored instead.

    Returns
    -------
    edges : iterator
       An iterator over edges in a maximum spanning tree of `G`.
       Edges connecting nodes `u` and `v` are represented as tuples:
       `(u, v, k, d)` or `(u, v, k)` or `(u, v, d)` or `(u, v)`

       If `G` is a multigraph, `keys` indicates whether the edge key `k` will
       be reported in the third position in the edge tuple. `data` indicates
       whether the edge datadict `d` will appear at the end of the edge tuple.

       If `G` is not a multigraph, the tuples are `(u, v, d)` if `data` is True
       or `(u, v)` if `data` is False.

    Examples
    --------
    >>> from networkx.algorithms import tree

    Find maximum spanning edges by Kruskal's algorithm

    >>> G = nx.cycle_graph(4)
    >>> G.add_edge(0, 3, weight=2)
    >>> mst = tree.maximum_spanning_edges(G, algorithm="kruskal", data=False)
    >>> edgelist = list(mst)
    >>> sorted(sorted(e) for e in edgelist)
    [[0, 1], [0, 3], [1, 2]]

    Find maximum spanning edges by Prim's algorithm

    >>> G = nx.cycle_graph(4)
    >>> G.add_edge(0, 3, weight=2)  # assign weight 2 to edge 0-3
    >>> mst = tree.maximum_spanning_edges(G, algorithm="prim", data=False)
    >>> edgelist = list(mst)
    >>> sorted(sorted(e) for e in edgelist)
    [[0, 1], [0, 3], [2, 3]]

    Notes
    -----
    For Borůvka's algorithm, each edge must have a weight attribute, and
    each edge weight must be distinct.

    For the other algorithms, if the graph edges do not have a weight
    attribute a default weight of 1 will be used.

    Modified code from David Eppstein, April 2006
    http://www.ics.uci.edu/~eppstein/PADS/
networkx.maximum_spanning_tree
Python Library Documentation: function maximum_spanning_tree in module networkx.algorithms.tree.mst

maximum_spanning_tree(G, weight='weight', algorithm='kruskal', ignore_nan=False, *, backend=None, **backend_kwargs)
    Returns a maximum spanning tree or forest on an undirected graph `G`.

    Parameters
    ----------
    G : undirected graph
        An undirected graph. If `G` is connected, then the algorithm finds a
        spanning tree. Otherwise, a spanning forest is found.

    weight : str
       Data key to use for edge weights.

    algorithm : string
       The algorithm to use when finding a maximum spanning tree. Valid
       choices are 'kruskal', 'prim', or 'boruvka'. The default is
       'kruskal'.

    ignore_nan : bool (default: False)
        If a NaN is found as an edge weight normally an exception is raised.
        If `ignore_nan is True` then that edge is ignored instead.


    Returns
    -------
    G : NetworkX Graph
       A maximum spanning tree or forest.


    Examples
    --------
    >>> G = nx.cycle_graph(4)
    >>> G.add_edge(0, 3, weight=2)
    >>> T = nx.maximum_spanning_tree(G)
    >>> sorted(T.edges(data=True))
    [(0, 1, {}), (0, 3, {'weight': 2}), (1, 2, {})]


    Notes
    -----
    For Borůvka's algorithm, each edge must have a weight attribute, and
    each edge weight must be distinct.

    For the other algorithms, if the graph edges do not have a weight
    attribute a default weight of 1 will be used.

    There may be more than one tree with the same minimum or maximum weight.
    See :mod:`networkx.tree.recognition` for more detailed definitions.

    Isolated nodes with self-loops are in the tree as edgeless isolated nodes.
networkx.maybe_regular_expander
Python Library Documentation: function maybe_regular_expander in module networkx.generators.expanders

maybe_regular_expander(n, d, *, create_using=None, max_tries=100, seed=None, backend=None, **backend_kwargs)
    Utility for creating a random regular expander.

    Returns a random $d$-regular graph on $n$ nodes which is an expander
    graph with very good probability.

    Parameters
    ----------
    n : int
      The number of nodes.
    d : int
      The degree of each node.
    create_using : Graph Instance or Constructor
      Indicator of type of graph to return.
      If a Graph-type instance, then clear and use it.
      If a constructor, call it to create an empty graph.
      Use the Graph constructor by default.
    max_tries : int. (default: 100)
      The number of allowed loops when generating each independent cycle
    seed : (default: None)
      Seed used to set random number generation state. See :ref`Randomness<randomness>`.

    Notes
    -----
    The nodes are numbered from $0$ to $n - 1$.

    The graph is generated by taking $d / 2$ random independent cycles.

    Joel Friedman proved that in this model the resulting
    graph is an expander with probability
    $1 - O(n^{-\tau})$ where $\tau = \lceil (\sqrt{d - 1}) / 2 \rceil - 1$. [1]_

    Examples
    --------
    >>> G = nx.maybe_regular_expander(n=200, d=6, seed=8020)

    Returns
    -------
    G : graph
        The constructed undirected graph.

    Raises
    ------
    NetworkXError
        If $d % 2 != 0$ as the degree must be even.
        If $n - 1$ is less than $ 2d $ as the graph is complete at most.
        If max_tries is reached

    See Also
    --------
    is_regular_expander
    random_regular_expander_graph

    References
    ----------
    .. [1] Joel Friedman,
       A Proof of Alon’s Second Eigenvalue Conjecture and Related Problems, 2004
       https://arxiv.org/abs/cs/0405020
networkx.min_cost_flow
Python Library Documentation: function min_cost_flow in module networkx.algorithms.flow.mincost

min_cost_flow(G, demand='demand', capacity='capacity', weight='weight', *, backend=None, **backend_kwargs)
    Returns a minimum cost flow satisfying all demands in digraph G.

    G is a digraph with edge costs and capacities and in which nodes
    have demand, i.e., they want to send or receive some amount of
    flow. A negative demand means that the node wants to send flow, a
    positive demand means that the node want to receive flow. A flow on
    the digraph G satisfies all demand if the net flow into each node
    is equal to the demand of that node.

    Parameters
    ----------
    G : NetworkX graph
        DiGraph on which a minimum cost flow satisfying all demands is
        to be found.

    demand : string
        Nodes of the graph G are expected to have an attribute demand
        that indicates how much flow a node wants to send (negative
        demand) or receive (positive demand). Note that the sum of the
        demands should be 0 otherwise the problem in not feasible. If
        this attribute is not present, a node is considered to have 0
        demand. Default value: 'demand'.

    capacity : string
        Edges of the graph G are expected to have an attribute capacity
        that indicates how much flow the edge can support. If this
        attribute is not present, the edge is considered to have
        infinite capacity. Default value: 'capacity'.

    weight : string
        Edges of the graph G are expected to have an attribute weight
        that indicates the cost incurred by sending one unit of flow on
        that edge. If not present, the weight is considered to be 0.
        Default value: 'weight'.

    Returns
    -------
    flowDict : dictionary
        Dictionary of dictionaries keyed by nodes such that
        flowDict[u][v] is the flow edge (u, v).

    Raises
    ------
    NetworkXError
        This exception is raised if the input graph is not directed or
        not connected.

    NetworkXUnfeasible
        This exception is raised in the following situations:

            * The sum of the demands is not zero. Then, there is no
              flow satisfying all demands.
            * There is no flow satisfying all demand.

    NetworkXUnbounded
        This exception is raised if the digraph G has a cycle of
        negative cost and infinite capacity. Then, the cost of a flow
        satisfying all demands is unbounded below.

    See also
    --------
    cost_of_flow, max_flow_min_cost, min_cost_flow_cost, network_simplex

    Notes
    -----
    This algorithm is not guaranteed to work if edge weights or demands
    are floating point numbers (overflows and roundoff errors can
    cause problems). As a workaround you can use integer numbers by
    multiplying the relevant edge attributes by a convenient
    constant factor (eg 100).

    Examples
    --------
    A simple example of a min cost flow problem.

    >>> G = nx.DiGraph()
    >>> G.add_node("a", demand=-5)
    >>> G.add_node("d", demand=5)
    >>> G.add_edge("a", "b", weight=3, capacity=4)
    >>> G.add_edge("a", "c", weight=6, capacity=10)
    >>> G.add_edge("b", "d", weight=1, capacity=9)
    >>> G.add_edge("c", "d", weight=2, capacity=5)
    >>> flowDict = nx.min_cost_flow(G)
    >>> flowDict
    {'a': {'b': 4, 'c': 1}, 'd': {}, 'b': {'d': 4}, 'c': {'d': 1}}
networkx.min_cost_flow_cost
Python Library Documentation: function min_cost_flow_cost in module networkx.algorithms.flow.mincost

min_cost_flow_cost(G, demand='demand', capacity='capacity', weight='weight', *, backend=None, **backend_kwargs)
    Find the cost of a minimum cost flow satisfying all demands in digraph G.

    G is a digraph with edge costs and capacities and in which nodes
    have demand, i.e., they want to send or receive some amount of
    flow. A negative demand means that the node wants to send flow, a
    positive demand means that the node want to receive flow. A flow on
    the digraph G satisfies all demand if the net flow into each node
    is equal to the demand of that node.

    Parameters
    ----------
    G : NetworkX graph
        DiGraph on which a minimum cost flow satisfying all demands is
        to be found.

    demand : string
        Nodes of the graph G are expected to have an attribute demand
        that indicates how much flow a node wants to send (negative
        demand) or receive (positive demand). Note that the sum of the
        demands should be 0 otherwise the problem in not feasible. If
        this attribute is not present, a node is considered to have 0
        demand. Default value: 'demand'.

    capacity : string
        Edges of the graph G are expected to have an attribute capacity
        that indicates how much flow the edge can support. If this
        attribute is not present, the edge is considered to have
        infinite capacity. Default value: 'capacity'.

    weight : string
        Edges of the graph G are expected to have an attribute weight
        that indicates the cost incurred by sending one unit of flow on
        that edge. If not present, the weight is considered to be 0.
        Default value: 'weight'.

    Returns
    -------
    flowCost : integer, float
        Cost of a minimum cost flow satisfying all demands.

    Raises
    ------
    NetworkXError
        This exception is raised if the input graph is not directed or
        not connected.

    NetworkXUnfeasible
        This exception is raised in the following situations:

            * The sum of the demands is not zero. Then, there is no
              flow satisfying all demands.
            * There is no flow satisfying all demand.

    NetworkXUnbounded
        This exception is raised if the digraph G has a cycle of
        negative cost and infinite capacity. Then, the cost of a flow
        satisfying all demands is unbounded below.

    See also
    --------
    cost_of_flow, max_flow_min_cost, min_cost_flow, network_simplex

    Notes
    -----
    This algorithm is not guaranteed to work if edge weights or demands
    are floating point numbers (overflows and roundoff errors can
    cause problems). As a workaround you can use integer numbers by
    multiplying the relevant edge attributes by a convenient
    constant factor (eg 100).

    Examples
    --------
    A simple example of a min cost flow problem.

    >>> G = nx.DiGraph()
    >>> G.add_node("a", demand=-5)
    >>> G.add_node("d", demand=5)
    >>> G.add_edge("a", "b", weight=3, capacity=4)
    >>> G.add_edge("a", "c", weight=6, capacity=10)
    >>> G.add_edge("b", "d", weight=1, capacity=9)
    >>> G.add_edge("c", "d", weight=2, capacity=5)
    >>> flowCost = nx.min_cost_flow_cost(G)
    >>> flowCost
    24
networkx.min_edge_cover
Python Library Documentation: function min_edge_cover in module networkx.algorithms.covering

min_edge_cover(G, matching_algorithm=None, *, backend=None, **backend_kwargs)
    Returns the min cardinality edge cover of the graph as a set of edges.

    A smallest edge cover can be found in polynomial time by finding
    a maximum matching and extending it greedily so that all nodes
    are covered. This function follows that process. A maximum matching
    algorithm can be specified for the first step of the algorithm.
    The resulting set may return a set with one 2-tuple for each edge,
    (the usual case) or with both 2-tuples `(u, v)` and `(v, u)` for
    each edge. The latter is only done when a bipartite matching algorithm
    is specified as `matching_algorithm`.

    Parameters
    ----------
    G : NetworkX graph
        An undirected graph.

    matching_algorithm : function
        A function that returns a maximum cardinality matching for `G`.
        The function must take one input, the graph `G`, and return
        either a set of edges (with only one direction for the pair of nodes)
        or a dictionary mapping each node to its mate. If not specified,
        :func:`~networkx.algorithms.matching.max_weight_matching` is used.
        Common bipartite matching functions include
        :func:`~networkx.algorithms.bipartite.matching.hopcroft_karp_matching`
        or
        :func:`~networkx.algorithms.bipartite.matching.eppstein_matching`.

    Returns
    -------
    min_cover : set

        A set of the edges in a minimum edge cover in the form of tuples.
        It contains only one of the equivalent 2-tuples `(u, v)` and `(v, u)`
        for each edge. If a bipartite method is used to compute the matching,
        the returned set contains both the 2-tuples `(u, v)` and `(v, u)`
        for each edge of a minimum edge cover.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
    >>> sorted(nx.min_edge_cover(G))
    [(2, 1), (3, 0)]

    Notes
    -----
    An edge cover of a graph is a set of edges such that every node of
    the graph is incident to at least one edge of the set.
    The minimum edge cover is an edge covering of smallest cardinality.

    Due to its implementation, the worst-case running time of this algorithm
    is bounded by the worst-case running time of the function
    ``matching_algorithm``.

    Minimum edge cover for `G` can also be found using the `min_edge_covering`
    function in :mod:`networkx.algorithms.bipartite.covering` which is
    simply this function with a default matching algorithm of
    :func:`~networkx.algorithms.bipartite.matching.hopcraft_karp_matching`
networkx.min_weight_matching
Python Library Documentation: function min_weight_matching in module networkx.algorithms.matching

min_weight_matching(G, weight='weight', *, backend=None, **backend_kwargs)
    Computing a minimum-weight maximal matching of G.

    Use the maximum-weight algorithm with edge weights subtracted
    from the maximum weight of all edges.

    A matching is a subset of edges in which no node occurs more than once.
    The weight of a matching is the sum of the weights of its edges.
    A maximal matching cannot add more edges and still be a matching.
    The cardinality of a matching is the number of matched edges.

    This method replaces the edge weights with 1 plus the maximum edge weight
    minus the original edge weight.

    new_weight = (max_weight + 1) - edge_weight

    then runs :func:`max_weight_matching` with the new weights.
    The max weight matching with these new weights corresponds
    to the min weight matching using the original weights.
    Adding 1 to the max edge weight keeps all edge weights positive
    and as integers if they started as integers.

    You might worry that adding 1 to each weight would make the algorithm
    favor matchings with more edges. But we use the parameter
    `maxcardinality=True` in `max_weight_matching` to ensure that the
    number of edges in the competing matchings are the same and thus
    the optimum does not change due to changes in the number of edges.

    Read the documentation of `max_weight_matching` for more information.

    Parameters
    ----------
    G : NetworkX graph
      Undirected graph

    weight: string, optional (default='weight')
       Edge data key corresponding to the edge weight.
       If key not found, uses 1 as weight.

    Returns
    -------
    matching : set
        A minimal weight matching of the graph.

    See Also
    --------
    max_weight_matching
networkx.minimal_d_separator
Python Library Documentation: function minimal_d_separator in module networkx.algorithms.d_separation

minimal_d_separator(G, u, v)
    Returns a minimal_d-separating set between `x` and `y` if possible

    .. deprecated:: 3.3

        minimal_d_separator is deprecated and will be removed in NetworkX v3.5.
        Please use `find_minimal_d_separator(G, x, y)`.
networkx.minimum_branching
Python Library Documentation: function minimum_branching in module networkx.algorithms.tree.branchings

minimum_branching(G, attr='weight', default=1, preserve_attrs=False, partition=None, *, backend=None, **backend_kwargs)
    Returns a minimum branching from G.

    Parameters
    ----------
    G : (multi)digraph-like
        The graph to be searched.
    attr : str
        The edge attribute used to in determining optimality.
    default : float
        The value of the edge attribute used if an edge does not have
        the attribute `attr`.
    preserve_attrs : bool
        If True, preserve the other attributes of the original graph (that are not
        passed to `attr`)
    partition : str
        The key for the edge attribute containing the partition
        data on the graph. Edges can be included, excluded or open using the
        `EdgePartition` enum.

    Returns
    -------
    B : (multi)digraph-like
        A minimum branching.

    See Also
    --------
        minimal_branching
networkx.minimum_cut
Python Library Documentation: function minimum_cut in module networkx.algorithms.flow.maxflow

minimum_cut(flowG, _s, _t, capacity='capacity', flow_func=None, *, backend=None, **kwargs)
    Compute the value and the node partition of a minimum (s, t)-cut.

    Use the max-flow min-cut theorem, i.e., the capacity of a minimum
    capacity cut is equal to the flow value of a maximum flow.

    Parameters
    ----------
    flowG : NetworkX graph
        Edges of the graph are expected to have an attribute called
        'capacity'. If this attribute is not present, the edge is
        considered to have infinite capacity.

    _s : node
        Source node for the flow.

    _t : node
        Sink node for the flow.

    capacity : string
        Edges of the graph G are expected to have an attribute capacity
        that indicates how much flow the edge can support. If this
        attribute is not present, the edge is considered to have
        infinite capacity. Default value: 'capacity'.

    flow_func : function
        A function for computing the maximum flow among a pair of nodes
        in a capacitated graph. The function has to accept at least three
        parameters: a Graph or Digraph, a source node, and a target node.
        And return a residual network that follows NetworkX conventions
        (see Notes). If flow_func is None, the default maximum
        flow function (:meth:`preflow_push`) is used. See below for
        alternative algorithms. The choice of the default function may change
        from version to version and should not be relied on. Default value:
        None.

    kwargs : Any other keyword parameter is passed to the function that
        computes the maximum flow.

    Returns
    -------
    cut_value : integer, float
        Value of the minimum cut.

    partition : pair of node sets
        A partitioning of the nodes that defines a minimum cut.

    Raises
    ------
    NetworkXUnbounded
        If the graph has a path of infinite capacity, all cuts have
        infinite capacity and the function raises a NetworkXError.

    See also
    --------
    :meth:`maximum_flow`
    :meth:`maximum_flow_value`
    :meth:`minimum_cut_value`
    :meth:`edmonds_karp`
    :meth:`preflow_push`
    :meth:`shortest_augmenting_path`

    Notes
    -----
    The function used in the flow_func parameter has to return a residual
    network that follows NetworkX conventions:

    The residual network :samp:`R` from an input graph :samp:`G` has the
    same nodes as :samp:`G`. :samp:`R` is a DiGraph that contains a pair
    of edges :samp:`(u, v)` and :samp:`(v, u)` iff :samp:`(u, v)` is not a
    self-loop, and at least one of :samp:`(u, v)` and :samp:`(v, u)` exists
    in :samp:`G`.

    For each edge :samp:`(u, v)` in :samp:`R`, :samp:`R[u][v]['capacity']`
    is equal to the capacity of :samp:`(u, v)` in :samp:`G` if it exists
    in :samp:`G` or zero otherwise. If the capacity is infinite,
    :samp:`R[u][v]['capacity']` will have a high arbitrary finite value
    that does not affect the solution of the problem. This value is stored in
    :samp:`R.graph['inf']`. For each edge :samp:`(u, v)` in :samp:`R`,
    :samp:`R[u][v]['flow']` represents the flow function of :samp:`(u, v)` and
    satisfies :samp:`R[u][v]['flow'] == -R[v][u]['flow']`.

    The flow value, defined as the total flow into :samp:`t`, the sink, is
    stored in :samp:`R.graph['flow_value']`. Reachability to :samp:`t` using
    only edges :samp:`(u, v)` such that
    :samp:`R[u][v]['flow'] < R[u][v]['capacity']` induces a minimum
    :samp:`s`-:samp:`t` cut.

    Specific algorithms may store extra data in :samp:`R`.

    The function should supports an optional boolean parameter value_only. When
    True, it can optionally terminate the algorithm as soon as the maximum flow
    value and the minimum cut can be determined.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_edge("x", "a", capacity=3.0)
    >>> G.add_edge("x", "b", capacity=1.0)
    >>> G.add_edge("a", "c", capacity=3.0)
    >>> G.add_edge("b", "c", capacity=5.0)
    >>> G.add_edge("b", "d", capacity=4.0)
    >>> G.add_edge("d", "e", capacity=2.0)
    >>> G.add_edge("c", "y", capacity=2.0)
    >>> G.add_edge("e", "y", capacity=3.0)

    minimum_cut computes both the value of the
    minimum cut and the node partition:

    >>> cut_value, partition = nx.minimum_cut(G, "x", "y")
    >>> reachable, non_reachable = partition

    'partition' here is a tuple with the two sets of nodes that define
    the minimum cut. You can compute the cut set of edges that induce
    the minimum cut as follows:

    >>> cutset = set()
    >>> for u, nbrs in ((n, G[n]) for n in reachable):
    ...     cutset.update((u, v) for v in nbrs if v in non_reachable)
    >>> print(sorted(cutset))
    [('c', 'y'), ('x', 'b')]
    >>> cut_value == sum(G.edges[u, v]["capacity"] for (u, v) in cutset)
    True

    You can also use alternative algorithms for computing the
    minimum cut by using the flow_func parameter.

    >>> from networkx.algorithms.flow import shortest_augmenting_path
    >>> cut_value == nx.minimum_cut(G, "x", "y", flow_func=shortest_augmenting_path)[0]
    True
networkx.minimum_cut_value
Python Library Documentation: function minimum_cut_value in module networkx.algorithms.flow.maxflow

minimum_cut_value(flowG, _s, _t, capacity='capacity', flow_func=None, *, backend=None, **kwargs)
    Compute the value of a minimum (s, t)-cut.

    Use the max-flow min-cut theorem, i.e., the capacity of a minimum
    capacity cut is equal to the flow value of a maximum flow.

    Parameters
    ----------
    flowG : NetworkX graph
        Edges of the graph are expected to have an attribute called
        'capacity'. If this attribute is not present, the edge is
        considered to have infinite capacity.

    _s : node
        Source node for the flow.

    _t : node
        Sink node for the flow.

    capacity : string
        Edges of the graph G are expected to have an attribute capacity
        that indicates how much flow the edge can support. If this
        attribute is not present, the edge is considered to have
        infinite capacity. Default value: 'capacity'.

    flow_func : function
        A function for computing the maximum flow among a pair of nodes
        in a capacitated graph. The function has to accept at least three
        parameters: a Graph or Digraph, a source node, and a target node.
        And return a residual network that follows NetworkX conventions
        (see Notes). If flow_func is None, the default maximum
        flow function (:meth:`preflow_push`) is used. See below for
        alternative algorithms. The choice of the default function may change
        from version to version and should not be relied on. Default value:
        None.

    kwargs : Any other keyword parameter is passed to the function that
        computes the maximum flow.

    Returns
    -------
    cut_value : integer, float
        Value of the minimum cut.

    Raises
    ------
    NetworkXUnbounded
        If the graph has a path of infinite capacity, all cuts have
        infinite capacity and the function raises a NetworkXError.

    See also
    --------
    :meth:`maximum_flow`
    :meth:`maximum_flow_value`
    :meth:`minimum_cut`
    :meth:`edmonds_karp`
    :meth:`preflow_push`
    :meth:`shortest_augmenting_path`

    Notes
    -----
    The function used in the flow_func parameter has to return a residual
    network that follows NetworkX conventions:

    The residual network :samp:`R` from an input graph :samp:`G` has the
    same nodes as :samp:`G`. :samp:`R` is a DiGraph that contains a pair
    of edges :samp:`(u, v)` and :samp:`(v, u)` iff :samp:`(u, v)` is not a
    self-loop, and at least one of :samp:`(u, v)` and :samp:`(v, u)` exists
    in :samp:`G`.

    For each edge :samp:`(u, v)` in :samp:`R`, :samp:`R[u][v]['capacity']`
    is equal to the capacity of :samp:`(u, v)` in :samp:`G` if it exists
    in :samp:`G` or zero otherwise. If the capacity is infinite,
    :samp:`R[u][v]['capacity']` will have a high arbitrary finite value
    that does not affect the solution of the problem. This value is stored in
    :samp:`R.graph['inf']`. For each edge :samp:`(u, v)` in :samp:`R`,
    :samp:`R[u][v]['flow']` represents the flow function of :samp:`(u, v)` and
    satisfies :samp:`R[u][v]['flow'] == -R[v][u]['flow']`.

    The flow value, defined as the total flow into :samp:`t`, the sink, is
    stored in :samp:`R.graph['flow_value']`. Reachability to :samp:`t` using
    only edges :samp:`(u, v)` such that
    :samp:`R[u][v]['flow'] < R[u][v]['capacity']` induces a minimum
    :samp:`s`-:samp:`t` cut.

    Specific algorithms may store extra data in :samp:`R`.

    The function should supports an optional boolean parameter value_only. When
    True, it can optionally terminate the algorithm as soon as the maximum flow
    value and the minimum cut can be determined.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_edge("x", "a", capacity=3.0)
    >>> G.add_edge("x", "b", capacity=1.0)
    >>> G.add_edge("a", "c", capacity=3.0)
    >>> G.add_edge("b", "c", capacity=5.0)
    >>> G.add_edge("b", "d", capacity=4.0)
    >>> G.add_edge("d", "e", capacity=2.0)
    >>> G.add_edge("c", "y", capacity=2.0)
    >>> G.add_edge("e", "y", capacity=3.0)

    minimum_cut_value computes only the value of the
    minimum cut:

    >>> cut_value = nx.minimum_cut_value(G, "x", "y")
    >>> cut_value
    3.0

    You can also use alternative algorithms for computing the
    minimum cut by using the flow_func parameter.

    >>> from networkx.algorithms.flow import shortest_augmenting_path
    >>> cut_value == nx.minimum_cut_value(
    ...     G, "x", "y", flow_func=shortest_augmenting_path
    ... )
    True
networkx.minimum_cycle_basis
Python Library Documentation: function minimum_cycle_basis in module networkx.algorithms.cycles

minimum_cycle_basis(G, weight=None, *, backend=None, **backend_kwargs)
    Returns a minimum weight cycle basis for G

    Minimum weight means a cycle basis for which the total weight
    (length for unweighted graphs) of all the cycles is minimum.

    Parameters
    ----------
    G : NetworkX Graph
    weight: string
        name of the edge attribute to use for edge weights

    Returns
    -------
    A list of cycle lists.  Each cycle list is a list of nodes
    which forms a cycle (loop) in G. Note that the nodes are not
    necessarily returned in a order by which they appear in the cycle

    Examples
    --------
    >>> G = nx.Graph()
    >>> nx.add_cycle(G, [0, 1, 2, 3])
    >>> nx.add_cycle(G, [0, 3, 4, 5])
    >>> nx.minimum_cycle_basis(G)
    [[5, 4, 3, 0], [3, 2, 1, 0]]

    References:
        [1] Kavitha, Telikepalli, et al. "An O(m^2n) Algorithm for
        Minimum Cycle Basis of Graphs."
        http://link.springer.com/article/10.1007/s00453-007-9064-z
        [2] de Pina, J. 1995. Applications of shortest path methods.
        Ph.D. thesis, University of Amsterdam, Netherlands

    See Also
    --------
    simple_cycles, cycle_basis
networkx.minimum_edge_cut
Python Library Documentation: function minimum_edge_cut in module networkx.algorithms.connectivity.cuts

minimum_edge_cut(G, s=None, t=None, flow_func=None, *, backend=None, **backend_kwargs)
    Returns a set of edges of minimum cardinality that disconnects G.

    If source and target nodes are provided, this function returns the
    set of edges of minimum cardinality that, if removed, would break
    all paths among source and target in G. If not, it returns a set of
    edges of minimum cardinality that disconnects G.

    Parameters
    ----------
    G : NetworkX graph

    s : node
        Source node. Optional. Default value: None.

    t : node
        Target node. Optional. Default value: None.

    flow_func : function
        A function for computing the maximum flow among a pair of nodes.
        The function has to accept at least three parameters: a Digraph,
        a source node, and a target node. And return a residual network
        that follows NetworkX conventions (see :meth:`maximum_flow` for
        details). If flow_func is None, the default maximum flow function
        (:meth:`edmonds_karp`) is used. See below for details. The
        choice of the default function may change from version
        to version and should not be relied on. Default value: None.

    Returns
    -------
    cutset : set
        Set of edges that, if removed, would disconnect G. If source
        and target nodes are provided, the set contains the edges that
        if removed, would destroy all paths between source and target.

    Examples
    --------
    >>> # Platonic icosahedral graph has edge connectivity 5
    >>> G = nx.icosahedral_graph()
    >>> len(nx.minimum_edge_cut(G))
    5

    You can use alternative flow algorithms for the underlying
    maximum flow computation. In dense networks the algorithm
    :meth:`shortest_augmenting_path` will usually perform better
    than the default :meth:`edmonds_karp`, which is faster for
    sparse networks with highly skewed degree distributions.
    Alternative flow functions have to be explicitly imported
    from the flow package.

    >>> from networkx.algorithms.flow import shortest_augmenting_path
    >>> len(nx.minimum_edge_cut(G, flow_func=shortest_augmenting_path))
    5

    If you specify a pair of nodes (source and target) as parameters,
    this function returns the value of local edge connectivity.

    >>> nx.edge_connectivity(G, 3, 7)
    5

    If you need to perform several local computations among different
    pairs of nodes on the same graph, it is recommended that you reuse
    the data structures used in the maximum flow computations. See
    :meth:`local_edge_connectivity` for details.

    Notes
    -----
    This is a flow based implementation of minimum edge cut. For
    undirected graphs the algorithm works by finding a 'small' dominating
    set of nodes of G (see algorithm 7 in [1]_) and computing the maximum
    flow between an arbitrary node in the dominating set and the rest of
    nodes in it. This is an implementation of algorithm 6 in [1]_. For
    directed graphs, the algorithm does n calls to the max flow function.
    The function raises an error if the directed graph is not weakly
    connected and returns an empty set if it is weakly connected.
    It is an implementation of algorithm 8 in [1]_.

    See also
    --------
    :meth:`minimum_st_edge_cut`
    :meth:`minimum_node_cut`
    :meth:`stoer_wagner`
    :meth:`node_connectivity`
    :meth:`edge_connectivity`
    :meth:`maximum_flow`
    :meth:`edmonds_karp`
    :meth:`preflow_push`
    :meth:`shortest_augmenting_path`

    References
    ----------
    .. [1] Abdol-Hossein Esfahanian. Connectivity Algorithms.
        http://www.cse.msu.edu/~cse835/Papers/Graph_connectivity_revised.pdf
networkx.minimum_node_cut
Python Library Documentation: function minimum_node_cut in module networkx.algorithms.connectivity.cuts

minimum_node_cut(G, s=None, t=None, flow_func=None, *, backend=None, **backend_kwargs)
    Returns a set of nodes of minimum cardinality that disconnects G.

    If source and target nodes are provided, this function returns the
    set of nodes of minimum cardinality that, if removed, would destroy
    all paths among source and target in G. If not, it returns a set
    of nodes of minimum cardinality that disconnects G.

    Parameters
    ----------
    G : NetworkX graph

    s : node
        Source node. Optional. Default value: None.

    t : node
        Target node. Optional. Default value: None.

    flow_func : function
        A function for computing the maximum flow among a pair of nodes.
        The function has to accept at least three parameters: a Digraph,
        a source node, and a target node. And return a residual network
        that follows NetworkX conventions (see :meth:`maximum_flow` for
        details). If flow_func is None, the default maximum flow function
        (:meth:`edmonds_karp`) is used. See below for details. The
        choice of the default function may change from version
        to version and should not be relied on. Default value: None.

    Returns
    -------
    cutset : set
        Set of nodes that, if removed, would disconnect G. If source
        and target nodes are provided, the set contains the nodes that
        if removed, would destroy all paths between source and target.

    Examples
    --------
    >>> # Platonic icosahedral graph has node connectivity 5
    >>> G = nx.icosahedral_graph()
    >>> node_cut = nx.minimum_node_cut(G)
    >>> len(node_cut)
    5

    You can use alternative flow algorithms for the underlying maximum
    flow computation. In dense networks the algorithm
    :meth:`shortest_augmenting_path` will usually perform better
    than the default :meth:`edmonds_karp`, which is faster for
    sparse networks with highly skewed degree distributions. Alternative
    flow functions have to be explicitly imported from the flow package.

    >>> from networkx.algorithms.flow import shortest_augmenting_path
    >>> node_cut == nx.minimum_node_cut(G, flow_func=shortest_augmenting_path)
    True

    If you specify a pair of nodes (source and target) as parameters,
    this function returns a local st node cut.

    >>> len(nx.minimum_node_cut(G, 3, 7))
    5

    If you need to perform several local st cuts among different
    pairs of nodes on the same graph, it is recommended that you reuse
    the data structures used in the maximum flow computations. See
    :meth:`minimum_st_node_cut` for details.

    Notes
    -----
    This is a flow based implementation of minimum node cut. The algorithm
    is based in solving a number of maximum flow computations to determine
    the capacity of the minimum cut on an auxiliary directed network that
    corresponds to the minimum node cut of G. It handles both directed
    and undirected graphs. This implementation is based on algorithm 11
    in [1]_.

    See also
    --------
    :meth:`minimum_st_node_cut`
    :meth:`minimum_cut`
    :meth:`minimum_edge_cut`
    :meth:`stoer_wagner`
    :meth:`node_connectivity`
    :meth:`edge_connectivity`
    :meth:`maximum_flow`
    :meth:`edmonds_karp`
    :meth:`preflow_push`
    :meth:`shortest_augmenting_path`

    References
    ----------
    .. [1] Abdol-Hossein Esfahanian. Connectivity Algorithms.
        http://www.cse.msu.edu/~cse835/Papers/Graph_connectivity_revised.pdf
networkx.minimum_spanning_arborescence
Python Library Documentation: function minimum_spanning_arborescence in module networkx.algorithms.tree.branchings

minimum_spanning_arborescence(G, attr='weight', default=1, preserve_attrs=False, partition=None, *, backend=None, **backend_kwargs)
    Returns a minimum spanning arborescence from G.

    Parameters
    ----------
    G : (multi)digraph-like
        The graph to be searched.
    attr : str
        The edge attribute used to in determining optimality.
    default : float
        The value of the edge attribute used if an edge does not have
        the attribute `attr`.
    preserve_attrs : bool
        If True, preserve the other attributes of the original graph (that are not
        passed to `attr`)
    partition : str
        The key for the edge attribute containing the partition
        data on the graph. Edges can be included, excluded or open using the
        `EdgePartition` enum.

    Returns
    -------
    B : (multi)digraph-like
        A minimum spanning arborescence.

    Raises
    ------
    NetworkXException
        If the graph does not contain a minimum spanning arborescence.
networkx.minimum_spanning_edges
Python Library Documentation: function minimum_spanning_edges in module networkx.algorithms.tree.mst

minimum_spanning_edges(G, algorithm='kruskal', weight='weight', keys=True, data=True, ignore_nan=False, *, backend=None, **backend_kwargs)
    Generate edges in a minimum spanning forest of an undirected
    weighted graph.

    A minimum spanning tree is a subgraph of the graph (a tree)
    with the minimum sum of edge weights.  A spanning forest is a
    union of the spanning trees for each connected component of the graph.

    Parameters
    ----------
    G : undirected Graph
       An undirected graph. If `G` is connected, then the algorithm finds a
       spanning tree. Otherwise, a spanning forest is found.

    algorithm : string
       The algorithm to use when finding a minimum spanning tree. Valid
       choices are 'kruskal', 'prim', or 'boruvka'. The default is 'kruskal'.

    weight : string
       Edge data key to use for weight (default 'weight').

    keys : bool
       Whether to yield edge key in multigraphs in addition to the edge.
       If `G` is not a multigraph, this is ignored.

    data : bool, optional
       If True yield the edge data along with the edge.

    ignore_nan : bool (default: False)
        If a NaN is found as an edge weight normally an exception is raised.
        If `ignore_nan is True` then that edge is ignored instead.

    Returns
    -------
    edges : iterator
       An iterator over edges in a maximum spanning tree of `G`.
       Edges connecting nodes `u` and `v` are represented as tuples:
       `(u, v, k, d)` or `(u, v, k)` or `(u, v, d)` or `(u, v)`

       If `G` is a multigraph, `keys` indicates whether the edge key `k` will
       be reported in the third position in the edge tuple. `data` indicates
       whether the edge datadict `d` will appear at the end of the edge tuple.

       If `G` is not a multigraph, the tuples are `(u, v, d)` if `data` is True
       or `(u, v)` if `data` is False.

    Examples
    --------
    >>> from networkx.algorithms import tree

    Find minimum spanning edges by Kruskal's algorithm

    >>> G = nx.cycle_graph(4)
    >>> G.add_edge(0, 3, weight=2)
    >>> mst = tree.minimum_spanning_edges(G, algorithm="kruskal", data=False)
    >>> edgelist = list(mst)
    >>> sorted(sorted(e) for e in edgelist)
    [[0, 1], [1, 2], [2, 3]]

    Find minimum spanning edges by Prim's algorithm

    >>> G = nx.cycle_graph(4)
    >>> G.add_edge(0, 3, weight=2)
    >>> mst = tree.minimum_spanning_edges(G, algorithm="prim", data=False)
    >>> edgelist = list(mst)
    >>> sorted(sorted(e) for e in edgelist)
    [[0, 1], [1, 2], [2, 3]]

    Notes
    -----
    For Borůvka's algorithm, each edge must have a weight attribute, and
    each edge weight must be distinct.

    For the other algorithms, if the graph edges do not have a weight
    attribute a default weight of 1 will be used.

    Modified code from David Eppstein, April 2006
    http://www.ics.uci.edu/~eppstein/PADS/
networkx.minimum_spanning_tree
Python Library Documentation: function minimum_spanning_tree in module networkx.algorithms.tree.mst

minimum_spanning_tree(G, weight='weight', algorithm='kruskal', ignore_nan=False, *, backend=None, **backend_kwargs)
    Returns a minimum spanning tree or forest on an undirected graph `G`.

    Parameters
    ----------
    G : undirected graph
        An undirected graph. If `G` is connected, then the algorithm finds a
        spanning tree. Otherwise, a spanning forest is found.

    weight : str
       Data key to use for edge weights.

    algorithm : string
       The algorithm to use when finding a minimum spanning tree. Valid
       choices are 'kruskal', 'prim', or 'boruvka'. The default is
       'kruskal'.

    ignore_nan : bool (default: False)
        If a NaN is found as an edge weight normally an exception is raised.
        If `ignore_nan is True` then that edge is ignored instead.

    Returns
    -------
    G : NetworkX Graph
       A minimum spanning tree or forest.

    Examples
    --------
    >>> G = nx.cycle_graph(4)
    >>> G.add_edge(0, 3, weight=2)
    >>> T = nx.minimum_spanning_tree(G)
    >>> sorted(T.edges(data=True))
    [(0, 1, {}), (1, 2, {}), (2, 3, {})]


    Notes
    -----
    For Borůvka's algorithm, each edge must have a weight attribute, and
    each edge weight must be distinct.

    For the other algorithms, if the graph edges do not have a weight
    attribute a default weight of 1 will be used.

    There may be more than one tree with the same minimum or maximum weight.
    See :mod:`networkx.tree.recognition` for more detailed definitions.

    Isolated nodes with self-loops are in the tree as edgeless isolated nodes.
networkx.minors
Python Library Documentation: package networkx.algorithms.minors in networkx.algorithms

NAME
    networkx.algorithms.minors - Subpackages related to graph-minor problems.

DESCRIPTION
    In graph theory, an undirected graph H is called a minor of the graph G if H
    can be formed from G by deleting edges and vertices and by contracting edges
    [1]_.

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Graph_minor

PACKAGE CONTENTS
    contraction

FUNCTIONS
    contracted_edge(G, edge, self_loops=True, copy=True, *, backend=None, **backend_kwargs)
        Returns the graph that results from contracting the specified edge.

        Edge contraction identifies the two endpoints of the edge as a single node
        incident to any edge that was incident to the original two nodes. A graph
        that results from edge contraction is called a *minor* of the original
        graph.

        Parameters
        ----------
        G : NetworkX graph
           The graph whose edge will be contracted.

        edge : tuple
           Must be a pair of nodes in `G`.

        self_loops : Boolean
           If this is True, any edges (including `edge`) joining the
           endpoints of `edge` in `G` become self-loops on the new node in the
           returned graph.

        copy : Boolean (default True)
            If this is True, a the contraction will be performed on a copy of `G`,
            otherwise the contraction will happen in place.

        Returns
        -------
        Networkx graph
           A new graph object of the same type as `G` (leaving `G` unmodified)
           with endpoints of `edge` identified in a single node. The right node
           of `edge` will be merged into the left one, so only the left one will
           appear in the returned graph.

        Raises
        ------
        ValueError
           If `edge` is not an edge in `G`.

        Examples
        --------
        Attempting to contract two nonadjacent nodes yields an error:

        >>> G = nx.cycle_graph(4)
        >>> nx.contracted_edge(G, (1, 3))
        Traceback (most recent call last):
          ...
        ValueError: Edge (1, 3) does not exist in graph G; cannot contract it

        Contracting two adjacent nodes in the cycle graph on *n* nodes yields the
        cycle graph on *n - 1* nodes:

        >>> C5 = nx.cycle_graph(5)
        >>> C4 = nx.cycle_graph(4)
        >>> M = nx.contracted_edge(C5, (0, 1), self_loops=False)
        >>> nx.is_isomorphic(M, C4)
        True

        See also
        --------
        contracted_nodes
        quotient_graph

    contracted_nodes(G, u, v, self_loops=True, copy=True, *, backend=None, **backend_kwargs)
        Returns the graph that results from contracting `u` and `v`.

        Node contraction identifies the two nodes as a single node incident to any
        edge that was incident to the original two nodes.

        Parameters
        ----------
        G : NetworkX graph
            The graph whose nodes will be contracted.

        u, v : nodes
            Must be nodes in `G`.

        self_loops : Boolean
            If this is True, any edges joining `u` and `v` in `G` become
            self-loops on the new node in the returned graph.

        copy : Boolean
            If this is True (default True), make a copy of
            `G` and return that instead of directly changing `G`.


        Returns
        -------
        Networkx graph
            If Copy is True,
            A new graph object of the same type as `G` (leaving `G` unmodified)
            with `u` and `v` identified in a single node. The right node `v`
            will be merged into the node `u`, so only `u` will appear in the
            returned graph.
            If copy is False,
            Modifies `G` with `u` and `v` identified in a single node.
            The right node `v` will be merged into the node `u`, so
            only `u` will appear in the returned graph.

        Notes
        -----
        For multigraphs, the edge keys for the realigned edges may
        not be the same as the edge keys for the old edges. This is
        natural because edge keys are unique only within each pair of nodes.

        For non-multigraphs where `u` and `v` are adjacent to a third node
        `w`, the edge (`v`, `w`) will be contracted into the edge (`u`,
        `w`) with its attributes stored into a "contraction" attribute.

        This function is also available as `identified_nodes`.

        Examples
        --------
        Contracting two nonadjacent nodes of the cycle graph on four nodes `C_4`
        yields the path graph (ignoring parallel edges):

        >>> G = nx.cycle_graph(4)
        >>> M = nx.contracted_nodes(G, 1, 3)
        >>> P3 = nx.path_graph(3)
        >>> nx.is_isomorphic(M, P3)
        True

        >>> G = nx.MultiGraph(P3)
        >>> M = nx.contracted_nodes(G, 0, 2)
        >>> M.edges
        MultiEdgeView([(0, 1, 0), (0, 1, 1)])

        >>> G = nx.Graph([(1, 2), (2, 2)])
        >>> H = nx.contracted_nodes(G, 1, 2, self_loops=False)
        >>> list(H.nodes())
        [1]
        >>> list(H.edges())
        [(1, 1)]

        In a ``MultiDiGraph`` with a self loop, the in and out edges will
        be treated separately as edges, so while contracting a node which
        has a self loop the contraction will add multiple edges:

        >>> G = nx.MultiDiGraph([(1, 2), (2, 2)])
        >>> H = nx.contracted_nodes(G, 1, 2)
        >>> list(H.edges())  # edge 1->2, 2->2, 2<-2 from the original Graph G
        [(1, 1), (1, 1), (1, 1)]
        >>> H = nx.contracted_nodes(G, 1, 2, self_loops=False)
        >>> list(H.edges())  # edge 2->2, 2<-2 from the original Graph G
        [(1, 1), (1, 1)]

        See Also
        --------
        contracted_edge
        quotient_graph

    equivalence_classes(iterable, relation)
        Returns equivalence classes of `relation` when applied to `iterable`.

        The equivalence classes, or blocks, consist of objects from `iterable`
        which are all equivalent. They are defined to be equivalent if the
        `relation` function returns `True` when passed any two objects from that
        class, and `False` otherwise. To define an equivalence relation the
        function must be reflexive, symmetric and transitive.

        Parameters
        ----------
        iterable : list, tuple, or set
            An iterable of elements/nodes.

        relation : function
            A Boolean-valued function that implements an equivalence relation
            (reflexive, symmetric, transitive binary relation) on the elements
            of `iterable` - it must take two elements and return `True` if
            they are related, or `False` if not.

        Returns
        -------
        set of frozensets
            A set of frozensets representing the partition induced by the equivalence
            relation function `relation` on the elements of `iterable`. Each
            member set in the return set represents an equivalence class, or
            block, of the partition.

            Duplicate elements will be ignored so it makes the most sense for
            `iterable` to be a :class:`set`.

        Notes
        -----
        This function does not check that `relation` represents an equivalence
        relation. You can check that your equivalence classes provide a partition
        using `is_partition`.

        Examples
        --------
        Let `X` be the set of integers from `0` to `9`, and consider an equivalence
        relation `R` on `X` of congruence modulo `3`: this means that two integers
        `x` and `y` in `X` are equivalent under `R` if they leave the same
        remainder when divided by `3`, i.e. `(x - y) mod 3 = 0`.

        The equivalence classes of this relation are `{0, 3, 6, 9}`, `{1, 4, 7}`,
        `{2, 5, 8}`: `0`, `3`, `6`, `9` are all divisible by `3` and leave zero
        remainder; `1`, `4`, `7` leave remainder `1`; while `2`, `5` and `8` leave
        remainder `2`. We can see this by calling `equivalence_classes` with
        `X` and a function implementation of `R`.

        >>> X = set(range(10))
        >>> def mod3(x, y):
        ...     return (x - y) % 3 == 0
        >>> equivalence_classes(X, mod3)  # doctest: +SKIP
        {frozenset({1, 4, 7}), frozenset({8, 2, 5}), frozenset({0, 9, 3, 6})}

    identified_nodes = contracted_nodes(G, u, v, self_loops=True, copy=True, *, backend=None, **backend_kwargs)
        Returns the graph that results from contracting `u` and `v`.

        Node contraction identifies the two nodes as a single node incident to any
        edge that was incident to the original two nodes.

        Parameters
        ----------
        G : NetworkX graph
            The graph whose nodes will be contracted.

        u, v : nodes
            Must be nodes in `G`.

        self_loops : Boolean
            If this is True, any edges joining `u` and `v` in `G` become
            self-loops on the new node in the returned graph.

        copy : Boolean
            If this is True (default True), make a copy of
            `G` and return that instead of directly changing `G`.


        Returns
        -------
        Networkx graph
            If Copy is True,
            A new graph object of the same type as `G` (leaving `G` unmodified)
            with `u` and `v` identified in a single node. The right node `v`
            will be merged into the node `u`, so only `u` will appear in the
            returned graph.
            If copy is False,
            Modifies `G` with `u` and `v` identified in a single node.
            The right node `v` will be merged into the node `u`, so
            only `u` will appear in the returned graph.

        Notes
        -----
        For multigraphs, the edge keys for the realigned edges may
        not be the same as the edge keys for the old edges. This is
        natural because edge keys are unique only within each pair of nodes.

        For non-multigraphs where `u` and `v` are adjacent to a third node
        `w`, the edge (`v`, `w`) will be contracted into the edge (`u`,
        `w`) with its attributes stored into a "contraction" attribute.

        This function is also available as `identified_nodes`.

        Examples
        --------
        Contracting two nonadjacent nodes of the cycle graph on four nodes `C_4`
        yields the path graph (ignoring parallel edges):

        >>> G = nx.cycle_graph(4)
        >>> M = nx.contracted_nodes(G, 1, 3)
        >>> P3 = nx.path_graph(3)
        >>> nx.is_isomorphic(M, P3)
        True

        >>> G = nx.MultiGraph(P3)
        >>> M = nx.contracted_nodes(G, 0, 2)
        >>> M.edges
        MultiEdgeView([(0, 1, 0), (0, 1, 1)])

        >>> G = nx.Graph([(1, 2), (2, 2)])
        >>> H = nx.contracted_nodes(G, 1, 2, self_loops=False)
        >>> list(H.nodes())
        [1]
        >>> list(H.edges())
        [(1, 1)]

        In a ``MultiDiGraph`` with a self loop, the in and out edges will
        be treated separately as edges, so while contracting a node which
        has a self loop the contraction will add multiple edges:

        >>> G = nx.MultiDiGraph([(1, 2), (2, 2)])
        >>> H = nx.contracted_nodes(G, 1, 2)
        >>> list(H.edges())  # edge 1->2, 2->2, 2<-2 from the original Graph G
        [(1, 1), (1, 1), (1, 1)]
        >>> H = nx.contracted_nodes(G, 1, 2, self_loops=False)
        >>> list(H.edges())  # edge 2->2, 2<-2 from the original Graph G
        [(1, 1), (1, 1)]

        See Also
        --------
        contracted_edge
        quotient_graph

    quotient_graph(G, partition, edge_relation=None, node_data=None, edge_data=None, weight='weight', relabel=False, create_using=None, *, backend=None, **backend_kwargs)
        Returns the quotient graph of `G` under the specified equivalence
        relation on nodes.

        Parameters
        ----------
        G : NetworkX graph
            The graph for which to return the quotient graph with the
            specified node relation.

        partition : function, or dict or list of lists, tuples or sets
            If a function, this function must represent an equivalence
            relation on the nodes of `G`. It must take two arguments *u*
            and *v* and return True exactly when *u* and *v* are in the
            same equivalence class. The equivalence classes form the nodes
            in the returned graph.

            If a dict of lists/tuples/sets, the keys can be any meaningful
            block labels, but the values must be the block lists/tuples/sets
            (one list/tuple/set per block), and the blocks must form a valid
            partition of the nodes of the graph. That is, each node must be
            in exactly one block of the partition.

            If a list of sets, the list must form a valid partition of
            the nodes of the graph. That is, each node must be in exactly
            one block of the partition.

        edge_relation : Boolean function with two arguments
            This function must represent an edge relation on the *blocks* of
            the `partition` of `G`. It must take two arguments, *B* and *C*,
            each one a set of nodes, and return True exactly when there should be
            an edge joining block *B* to block *C* in the returned graph.

            If `edge_relation` is not specified, it is assumed to be the
            following relation. Block *B* is related to block *C* if and
            only if some node in *B* is adjacent to some node in *C*,
            according to the edge set of `G`.

        node_data : function
            This function takes one argument, *B*, a set of nodes in `G`,
            and must return a dictionary representing the node data
            attributes to set on the node representing *B* in the quotient graph.
            If None, the following node attributes will be set:

            * 'graph', the subgraph of the graph `G` that this block
              represents,
            * 'nnodes', the number of nodes in this block,
            * 'nedges', the number of edges within this block,
            * 'density', the density of the subgraph of `G` that this
              block represents.

        edge_data : function
            This function takes two arguments, *B* and *C*, each one a set
            of nodes, and must return a dictionary representing the edge
            data attributes to set on the edge joining *B* and *C*, should
            there be an edge joining *B* and *C* in the quotient graph (if
            no such edge occurs in the quotient graph as determined by
            `edge_relation`, then the output of this function is ignored).

            If the quotient graph would be a multigraph, this function is
            not applied, since the edge data from each edge in the graph
            `G` appears in the edges of the quotient graph.

        weight : string or None, optional (default="weight")
            The name of an edge attribute that holds the numerical value
            used as a weight. If None then each edge has weight 1.

        relabel : bool
            If True, relabel the nodes of the quotient graph to be
            nonnegative integers. Otherwise, the nodes are identified with
            :class:`frozenset` instances representing the blocks given in
            `partition`.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        NetworkX graph
            The quotient graph of `G` under the equivalence relation
            specified by `partition`. If the partition were given as a
            list of :class:`set` instances and `relabel` is False,
            each node will be a :class:`frozenset` corresponding to the same
            :class:`set`.

        Raises
        ------
        NetworkXException
            If the given partition is not a valid partition of the nodes of
            `G`.

        Examples
        --------
        The quotient graph of the complete bipartite graph under the "same
        neighbors" equivalence relation is `K_2`. Under this relation, two nodes
        are equivalent if they are not adjacent but have the same neighbor set.

        >>> G = nx.complete_bipartite_graph(2, 3)
        >>> same_neighbors = lambda u, v: (u not in G[v] and v not in G[u] and G[u] == G[v])
        >>> Q = nx.quotient_graph(G, same_neighbors)
        >>> K2 = nx.complete_graph(2)
        >>> nx.is_isomorphic(Q, K2)
        True

        The quotient graph of a directed graph under the "same strongly connected
        component" equivalence relation is the condensation of the graph (see
        :func:`condensation`). This example comes from the Wikipedia article
        *`Strongly connected component`_*.

        >>> G = nx.DiGraph()
        >>> edges = [
        ...     "ab",
        ...     "be",
        ...     "bf",
        ...     "bc",
        ...     "cg",
        ...     "cd",
        ...     "dc",
        ...     "dh",
        ...     "ea",
        ...     "ef",
        ...     "fg",
        ...     "gf",
        ...     "hd",
        ...     "hf",
        ... ]
        >>> G.add_edges_from(tuple(x) for x in edges)
        >>> components = list(nx.strongly_connected_components(G))
        >>> sorted(sorted(component) for component in components)
        [['a', 'b', 'e'], ['c', 'd', 'h'], ['f', 'g']]
        >>>
        >>> C = nx.condensation(G, components)
        >>> component_of = C.graph["mapping"]
        >>> same_component = lambda u, v: component_of[u] == component_of[v]
        >>> Q = nx.quotient_graph(G, same_component)
        >>> nx.is_isomorphic(C, Q)
        True

        Node identification can be represented as the quotient of a graph under the
        equivalence relation that places the two nodes in one block and each other
        node in its own singleton block.

        >>> K24 = nx.complete_bipartite_graph(2, 4)
        >>> K34 = nx.complete_bipartite_graph(3, 4)
        >>> C = nx.contracted_nodes(K34, 1, 2)
        >>> nodes = {1, 2}
        >>> is_contracted = lambda u, v: u in nodes and v in nodes
        >>> Q = nx.quotient_graph(K34, is_contracted)
        >>> nx.is_isomorphic(Q, C)
        True
        >>> nx.is_isomorphic(Q, K24)
        True

        The blockmodeling technique described in [1]_ can be implemented as a
        quotient graph.

        >>> G = nx.path_graph(6)
        >>> partition = [{0, 1}, {2, 3}, {4, 5}]
        >>> M = nx.quotient_graph(G, partition, relabel=True)
        >>> list(M.edges())
        [(0, 1), (1, 2)]

        Here is the sample example but using partition as a dict of block sets.

        >>> G = nx.path_graph(6)
        >>> partition = {0: {0, 1}, 2: {2, 3}, 4: {4, 5}}
        >>> M = nx.quotient_graph(G, partition, relabel=True)
        >>> list(M.edges())
        [(0, 1), (1, 2)]

        Partitions can be represented in various ways:

        0. a list/tuple/set of block lists/tuples/sets
        1. a dict with block labels as keys and blocks lists/tuples/sets as values
        2. a dict with block lists/tuples/sets as keys and block labels as values
        3. a function from nodes in the original iterable to block labels
        4. an equivalence relation function on the target iterable

        As `quotient_graph` is designed to accept partitions represented as (0), (1) or
        (4) only, the `equivalence_classes` function can be used to get the partitions
        in the right form, in order to call `quotient_graph`.

        .. _Strongly connected component: https://en.wikipedia.org/wiki/Strongly_connected_component

        References
        ----------
        .. [1] Patrick Doreian, Vladimir Batagelj, and Anuska Ferligoj.
               *Generalized Blockmodeling*.
               Cambridge University Press, 2004.

DATA
    __all__ = ['contracted_edge', 'contracted_nodes', 'equivalence_classes...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\minors\__init__.py

networkx.mis
Python Library Documentation: module networkx.algorithms.mis in networkx.algorithms

NAME
    networkx.algorithms.mis - Algorithm to find a maximal (not maximum) independent set.

FUNCTIONS
    maximal_independent_set(G, nodes=None, seed=None, *, backend=None, **backend_kwargs)
        Returns a random maximal independent set guaranteed to contain
        a given set of nodes.

        An independent set is a set of nodes such that the subgraph
        of G induced by these nodes contains no edges. A maximal
        independent set is an independent set such that it is not possible
        to add a new node and still get an independent set.

        Parameters
        ----------
        G : NetworkX graph

        nodes : list or iterable
           Nodes that must be part of the independent set. This set of nodes
           must be independent.

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        indep_nodes : list
           List of nodes that are part of a maximal independent set.

        Raises
        ------
        NetworkXUnfeasible
           If the nodes in the provided list are not part of the graph or
           do not form an independent set, an exception is raised.

        NetworkXNotImplemented
            If `G` is directed.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> nx.maximal_independent_set(G)  # doctest: +SKIP
        [4, 0, 2]
        >>> nx.maximal_independent_set(G, [1])  # doctest: +SKIP
        [1, 3]

        Notes
        -----
        This algorithm does not solve the maximum independent set problem.

DATA
    __all__ = ['maximal_independent_set']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\mis.py

networkx.mixing
Python Library Documentation: module networkx.algorithms.assortativity.mixing in networkx.algorithms.assortativity

NAME
    networkx.algorithms.assortativity.mixing - Mixing matrices for node attributes and degree.

FUNCTIONS
    attribute_mixing_dict(G, attribute, nodes=None, normalized=False, *, backend=None, **backend_kwargs)
        Returns dictionary representation of mixing matrix for attribute.

        Parameters
        ----------
        G : graph
           NetworkX graph object.

        attribute : string
           Node attribute key.

        nodes: list or iterable (optional)
            Unse nodes in container to build the dict. The default is all nodes.

        normalized : bool (default=False)
           Return counts if False or probabilities if True.

        Examples
        --------
        >>> G = nx.Graph()
        >>> G.add_nodes_from([0, 1], color="red")
        >>> G.add_nodes_from([2, 3], color="blue")
        >>> G.add_edge(1, 3)
        >>> d = nx.attribute_mixing_dict(G, "color")
        >>> print(d["red"]["blue"])
        1
        >>> print(d["blue"]["red"])  # d symmetric for undirected graphs
        1

        Returns
        -------
        d : dictionary
           Counts or joint probability of occurrence of attribute pairs.

    attribute_mixing_matrix(G, attribute, nodes=None, mapping=None, normalized=True, *, backend=None, **backend_kwargs)
        Returns mixing matrix for attribute.

        Parameters
        ----------
        G : graph
           NetworkX graph object.

        attribute : string
           Node attribute key.

        nodes: list or iterable (optional)
            Use only nodes in container to build the matrix. The default is
            all nodes.

        mapping : dictionary, optional
           Mapping from node attribute to integer index in matrix.
           If not specified, an arbitrary ordering will be used.

        normalized : bool (default=True)
           Return counts if False or probabilities if True.

        Returns
        -------
        m: numpy array
           Counts or joint probability of occurrence of attribute pairs.

        Notes
        -----
        If each node has a unique attribute value, the unnormalized mixing matrix
        will be equal to the adjacency matrix. To get a denser mixing matrix,
        the rounding can be performed to form groups of nodes with equal values.
        For example, the exact height of persons in cm (180.79155222, 163.9080892,
        163.30095355, 167.99016217, 168.21590163, ...) can be rounded to (180, 163,
        163, 168, 168, ...).

        Definitions of attribute mixing matrix vary on whether the matrix
        should include rows for attribute values that don't arise. Here we
        do not include such empty-rows. But you can force them to appear
        by inputting a `mapping` that includes those values.

        Examples
        --------
        >>> G = nx.path_graph(3)
        >>> gender = {0: "male", 1: "female", 2: "female"}
        >>> nx.set_node_attributes(G, gender, "gender")
        >>> mapping = {"male": 0, "female": 1}
        >>> mix_mat = nx.attribute_mixing_matrix(G, "gender", mapping=mapping)
        >>> mix_mat
        array([[0.  , 0.25],
               [0.25, 0.5 ]])

    degree_mixing_dict(G, x='out', y='in', weight=None, nodes=None, normalized=False, *, backend=None, **backend_kwargs)
        Returns dictionary representation of mixing matrix for degree.

        Parameters
        ----------
        G : graph
            NetworkX graph object.

        x: string ('in','out')
           The degree type for source node (directed graphs only).

        y: string ('in','out')
           The degree type for target node (directed graphs only).

        weight: string or None, optional (default=None)
           The edge attribute that holds the numerical value used
           as a weight.  If None, then each edge has weight 1.
           The degree is the sum of the edge weights adjacent to the node.

        normalized : bool (default=False)
            Return counts if False or probabilities if True.

        Returns
        -------
        d: dictionary
           Counts or joint probability of occurrence of degree pairs.

    degree_mixing_matrix(G, x='out', y='in', weight=None, nodes=None, normalized=True, mapping=None, *, backend=None, **backend_kwargs)
        Returns mixing matrix for attribute.

        Parameters
        ----------
        G : graph
           NetworkX graph object.

        x: string ('in','out')
           The degree type for source node (directed graphs only).

        y: string ('in','out')
           The degree type for target node (directed graphs only).

        nodes: list or iterable (optional)
            Build the matrix using only nodes in container.
            The default is all nodes.

        weight: string or None, optional (default=None)
           The edge attribute that holds the numerical value used
           as a weight.  If None, then each edge has weight 1.
           The degree is the sum of the edge weights adjacent to the node.

        normalized : bool (default=True)
           Return counts if False or probabilities if True.

        mapping : dictionary, optional
           Mapping from node degree to integer index in matrix.
           If not specified, an arbitrary ordering will be used.

        Returns
        -------
        m: numpy array
           Counts, or joint probability, of occurrence of node degree.

        Notes
        -----
        Definitions of degree mixing matrix vary on whether the matrix
        should include rows for degree values that don't arise. Here we
        do not include such empty-rows. But you can force them to appear
        by inputting a `mapping` that includes those values. See examples.

        Examples
        --------
        >>> G = nx.star_graph(3)
        >>> mix_mat = nx.degree_mixing_matrix(G)
        >>> mix_mat
        array([[0. , 0.5],
               [0.5, 0. ]])

        If you want every possible degree to appear as a row, even if no nodes
        have that degree, use `mapping` as follows,

        >>> max_degree = max(deg for n, deg in G.degree)
        >>> mapping = {x: x for x in range(max_degree + 1)}  # identity mapping
        >>> mix_mat = nx.degree_mixing_matrix(G, mapping=mapping)
        >>> mix_mat
        array([[0. , 0. , 0. , 0. ],
               [0. , 0. , 0. , 0.5],
               [0. , 0. , 0. , 0. ],
               [0. , 0.5, 0. , 0. ]])

    mixing_dict(xy, normalized=False)
        Returns a dictionary representation of mixing matrix.

        Parameters
        ----------
        xy : list or container of two-tuples
           Pairs of (x,y) items.

        attribute : string
           Node attribute key

        normalized : bool (default=False)
           Return counts if False or probabilities if True.

        Returns
        -------
        d: dictionary
           Counts or Joint probability of occurrence of values in xy.

DATA
    __all__ = ['attribute_mixing_matrix', 'attribute_mixing_dict', 'degree...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\assortativity\mixing.py

networkx.mixing_dict
Python Library Documentation: function mixing_dict in module networkx.algorithms.assortativity.mixing

mixing_dict(xy, normalized=False)
    Returns a dictionary representation of mixing matrix.

    Parameters
    ----------
    xy : list or container of two-tuples
       Pairs of (x,y) items.

    attribute : string
       Node attribute key

    normalized : bool (default=False)
       Return counts if False or probabilities if True.

    Returns
    -------
    d: dictionary
       Counts or Joint probability of occurrence of values in xy.
networkx.mixing_expansion
Python Library Documentation: function mixing_expansion in module networkx.algorithms.cuts

mixing_expansion(G, S, T=None, weight=None, *, backend=None, **backend_kwargs)
    Returns the mixing expansion between two node sets.

    The *mixing expansion* is the quotient of the cut size and twice the
    number of edges in the graph. [1]

    Parameters
    ----------
    G : NetworkX graph

    S : collection
        A collection of nodes in `G`.

    T : collection
        A collection of nodes in `G`.

    weight : object
        Edge attribute key to use as weight. If not specified, edges
        have weight one.

    Returns
    -------
    number
        The mixing expansion between the two sets `S` and `T`.

    See also
    --------
    boundary_expansion
    edge_expansion
    node_expansion

    References
    ----------
    .. [1] Vadhan, Salil P.
           "Pseudorandomness."
           *Foundations and Trends
           in Theoretical Computer Science* 7.1–3 (2011): 1–336.
           <https://doi.org/10.1561/0400000010>
networkx.modular_product
Python Library Documentation: function modular_product in module networkx.algorithms.operators.product

modular_product(G, H, *, backend=None, **backend_kwargs)
    Returns the Modular product of G and H.

    The modular product of `G` and `H` is the graph $M = G \nabla H$,
    consisting of the node set $V(M) = V(G) \times V(H)$ that is the Cartesian
    product of the node sets of `G` and `H`. Further, M contains an edge ((u, v), (x, y)):

    - if u is adjacent to x in `G` and v is adjacent to y in `H`, or
    - if u is not adjacent to x in `G` and v is not adjacent to y in `H`.

    More formally::

        E(M) = {((u, v), (x, y)) | ((u, x) in E(G) and (v, y) in E(H)) or
                                   ((u, x) not in E(G) and (v, y) not in E(H))}

    Parameters
    ----------
    G, H: NetworkX graphs
        The graphs to take the modular product of.

    Returns
    -------
    M: NetworkX graph
        The Modular product of `G` and `H`.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is not a simple graph.

    Examples
    --------
    >>> G = nx.cycle_graph(4)
    >>> H = nx.path_graph(2)
    >>> M = nx.modular_product(G, H)
    >>> list(M)
    [(0, 0), (0, 1), (1, 0), (1, 1), (2, 0), (2, 1), (3, 0), (3, 1)]
    >>> print(M)
    Graph with 8 nodes and 8 edges

    Notes
    -----
    The *modular product* is defined in [1]_ and was first
    introduced as the *weak modular product*.

    The modular product reduces the problem of counting isomorphic subgraphs
    in `G` and `H` to the problem of counting cliques in M. The subgraphs of
    `G` and `H` that are induced by the nodes of a clique in M are
    isomorphic [2]_ [3]_.

    References
    ----------
    .. [1] R. Hammack, W. Imrich, and S. Klavžar,
        "Handbook of Product Graphs", CRC Press, 2011.

    .. [2] H. G. Barrow and R. M. Burstall,
        "Subgraph isomorphism, matching relational structures and maximal
        cliques", Information Processing Letters, vol. 4, issue 4, pp. 83-84,
        1976, https://doi.org/10.1016/0020-0190(76)90049-1.

    .. [3] V. G. Vizing, "Reduction of the problem of isomorphism and isomorphic
        entrance to the task of finding the nondensity of a graph." Proc. Third
        All-Union Conference on Problems of Theoretical Cybernetics. 1974.
networkx.modularity_matrix
Python Library Documentation: function modularity_matrix in module networkx.linalg.modularitymatrix

modularity_matrix(G, nodelist=None, weight=None, *, backend=None, **backend_kwargs)
    Returns the modularity matrix of G.

    The modularity matrix is the matrix B = A - <A>, where A is the adjacency
    matrix and <A> is the average adjacency matrix, assuming that the graph
    is described by the configuration model.

    More specifically, the element B_ij of B is defined as

    .. math::
        A_{ij} - {k_i k_j \over 2 m}

    where k_i is the degree of node i, and where m is the number of edges
    in the graph. When weight is set to a name of an attribute edge, Aij, k_i,
    k_j and m are computed using its value.

    Parameters
    ----------
    G : Graph
       A NetworkX graph

    nodelist : list, optional
       The rows and columns are ordered according to the nodes in nodelist.
       If nodelist is None, then the ordering is produced by G.nodes().

    weight : string or None, optional (default=None)
       The edge attribute that holds the numerical value used for
       the edge weight.  If None then all edge weights are 1.

    Returns
    -------
    B : Numpy array
      The modularity matrix of G.

    Examples
    --------
    >>> k = [3, 2, 2, 1, 0]
    >>> G = nx.havel_hakimi_graph(k)
    >>> B = nx.modularity_matrix(G)


    See Also
    --------
    to_numpy_array
    modularity_spectrum
    adjacency_matrix
    directed_modularity_matrix

    References
    ----------
    .. [1] M. E. J. Newman, "Modularity and community structure in networks",
           Proc. Natl. Acad. Sci. USA, vol. 103, pp. 8577-8582, 2006.
networkx.modularity_spectrum
Python Library Documentation: function modularity_spectrum in module networkx.linalg.spectrum

modularity_spectrum(G, *, backend=None, **backend_kwargs)
    Returns eigenvalues of the modularity matrix of G.

    Parameters
    ----------
    G : Graph
       A NetworkX Graph or DiGraph

    Returns
    -------
    evals : NumPy array
      Eigenvalues

    See Also
    --------
    modularity_matrix

    References
    ----------
    .. [1] M. E. J. Newman, "Modularity and community structure in networks",
       Proc. Natl. Acad. Sci. USA, vol. 103, pp. 8577-8582, 2006.
networkx.modularitymatrix
Python Library Documentation: module networkx.linalg.modularitymatrix in networkx.linalg

NAME
    networkx.linalg.modularitymatrix - Modularity matrix of graphs.

FUNCTIONS
    directed_modularity_matrix(G, nodelist=None, weight=None, *, backend=None, **backend_kwargs)
        Returns the directed modularity matrix of G.

        The modularity matrix is the matrix B = A - <A>, where A is the adjacency
        matrix and <A> is the expected adjacency matrix, assuming that the graph
        is described by the configuration model.

        More specifically, the element B_ij of B is defined as

        .. math::
            B_{ij} = A_{ij} - k_i^{out} k_j^{in} / m

        where :math:`k_i^{in}` is the in degree of node i, and :math:`k_j^{out}` is the out degree
        of node j, with m the number of edges in the graph. When weight is set
        to a name of an attribute edge, Aij, k_i, k_j and m are computed using
        its value.

        Parameters
        ----------
        G : DiGraph
           A NetworkX DiGraph

        nodelist : list, optional
           The rows and columns are ordered according to the nodes in nodelist.
           If nodelist is None, then the ordering is produced by G.nodes().

        weight : string or None, optional (default=None)
           The edge attribute that holds the numerical value used for
           the edge weight.  If None then all edge weights are 1.

        Returns
        -------
        B : Numpy array
          The modularity matrix of G.

        Examples
        --------
        >>> G = nx.DiGraph()
        >>> G.add_edges_from(
        ...     (
        ...         (1, 2),
        ...         (1, 3),
        ...         (3, 1),
        ...         (3, 2),
        ...         (3, 5),
        ...         (4, 5),
        ...         (4, 6),
        ...         (5, 4),
        ...         (5, 6),
        ...         (6, 4),
        ...     )
        ... )
        >>> B = nx.directed_modularity_matrix(G)


        Notes
        -----
        NetworkX defines the element A_ij of the adjacency matrix as 1 if there
        is a link going from node i to node j. Leicht and Newman use the opposite
        definition. This explains the different expression for B_ij.

        See Also
        --------
        to_numpy_array
        modularity_spectrum
        adjacency_matrix
        modularity_matrix

        References
        ----------
        .. [1] E. A. Leicht, M. E. J. Newman,
            "Community structure in directed networks",
            Phys. Rev Lett., vol. 100, no. 11, p. 118703, 2008.

    modularity_matrix(G, nodelist=None, weight=None, *, backend=None, **backend_kwargs)
        Returns the modularity matrix of G.

        The modularity matrix is the matrix B = A - <A>, where A is the adjacency
        matrix and <A> is the average adjacency matrix, assuming that the graph
        is described by the configuration model.

        More specifically, the element B_ij of B is defined as

        .. math::
            A_{ij} - {k_i k_j \over 2 m}

        where k_i is the degree of node i, and where m is the number of edges
        in the graph. When weight is set to a name of an attribute edge, Aij, k_i,
        k_j and m are computed using its value.

        Parameters
        ----------
        G : Graph
           A NetworkX graph

        nodelist : list, optional
           The rows and columns are ordered according to the nodes in nodelist.
           If nodelist is None, then the ordering is produced by G.nodes().

        weight : string or None, optional (default=None)
           The edge attribute that holds the numerical value used for
           the edge weight.  If None then all edge weights are 1.

        Returns
        -------
        B : Numpy array
          The modularity matrix of G.

        Examples
        --------
        >>> k = [3, 2, 2, 1, 0]
        >>> G = nx.havel_hakimi_graph(k)
        >>> B = nx.modularity_matrix(G)


        See Also
        --------
        to_numpy_array
        modularity_spectrum
        adjacency_matrix
        directed_modularity_matrix

        References
        ----------
        .. [1] M. E. J. Newman, "Modularity and community structure in networks",
               Proc. Natl. Acad. Sci. USA, vol. 103, pp. 8577-8582, 2006.

DATA
    __all__ = ['modularity_matrix', 'directed_modularity_matrix']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\linalg\modularitymatrix.py

networkx.moebius_kantor_graph
Python Library Documentation: function moebius_kantor_graph in module networkx.generators.small

moebius_kantor_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Moebius-Kantor graph.

    The Möbius-Kantor graph is the cubic symmetric graph on 16 nodes.
    Its LCF notation is [5,-5]^8, and it is isomorphic to the generalized
    Petersen graph [1]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Moebius-Kantor graph

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/M%C3%B6bius%E2%80%93Kantor_graph
networkx.moral
Python Library Documentation: module networkx.algorithms.moral in networkx.algorithms

NAME
    networkx.algorithms.moral - Function for computing the moral graph of a directed graph.

FUNCTIONS
    moral_graph(G, *, backend=None, **backend_kwargs)
        Return the Moral Graph

        Returns the moralized graph of a given directed graph.

        Parameters
        ----------
        G : NetworkX graph
            Directed graph

        Returns
        -------
        H : NetworkX graph
            The undirected moralized graph of G

        Raises
        ------
        NetworkXNotImplemented
            If `G` is undirected.

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (2, 3), (2, 5), (3, 4), (4, 3)])
        >>> G_moral = nx.moral_graph(G)
        >>> G_moral.edges()
        EdgeView([(1, 2), (2, 3), (2, 5), (2, 4), (3, 4)])

        Notes
        -----
        A moral graph is an undirected graph H = (V, E) generated from a
        directed Graph, where if a node has more than one parent node, edges
        between these parent nodes are inserted and all directed edges become
        undirected.

        https://en.wikipedia.org/wiki/Moral_graph

        References
        ----------
        .. [1] Wray L. Buntine. 1995. Chain graphs for learning.
               In Proceedings of the Eleventh conference on Uncertainty
               in artificial intelligence (UAI'95)

DATA
    __all__ = ['moral_graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\moral.py

networkx.moral_graph
Python Library Documentation: function moral_graph in module networkx.algorithms.moral

moral_graph(G, *, backend=None, **backend_kwargs)
    Return the Moral Graph

    Returns the moralized graph of a given directed graph.

    Parameters
    ----------
    G : NetworkX graph
        Directed graph

    Returns
    -------
    H : NetworkX graph
        The undirected moralized graph of G

    Raises
    ------
    NetworkXNotImplemented
        If `G` is undirected.

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (2, 3), (2, 5), (3, 4), (4, 3)])
    >>> G_moral = nx.moral_graph(G)
    >>> G_moral.edges()
    EdgeView([(1, 2), (2, 3), (2, 5), (2, 4), (3, 4)])

    Notes
    -----
    A moral graph is an undirected graph H = (V, E) generated from a
    directed Graph, where if a node has more than one parent node, edges
    between these parent nodes are inserted and all directed edges become
    undirected.

    https://en.wikipedia.org/wiki/Moral_graph

    References
    ----------
    .. [1] Wray L. Buntine. 1995. Chain graphs for learning.
           In Proceedings of the Eleventh conference on Uncertainty
           in artificial intelligence (UAI'95)
networkx.multi_source_dijkstra
Python Library Documentation: function multi_source_dijkstra in module networkx.algorithms.shortest_paths.weighted

multi_source_dijkstra(G, sources, target=None, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
    Find shortest weighted paths and lengths from a given set of
    source nodes.

    Uses Dijkstra's algorithm to compute the shortest paths and lengths
    between one of the source nodes and the given `target`, or all other
    reachable nodes if not specified, for a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    sources : non-empty set of nodes
        Starting nodes for paths. If this is just a set containing a
        single node, then all paths computed by this function will start
        from that node. If there are two or more nodes in the set, the
        computed paths may begin from any one of the start nodes.

    target : node label, optional
        Ending node for path

    cutoff : integer or float, optional
        Length (sum of edge weights) at which the search is stopped.
        If cutoff is provided, only return paths with summed weight <= cutoff.

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Returns
    -------
    distance, path : pair of dictionaries, or numeric and list
        If target is None, returns a tuple of two dictionaries keyed by node.
        The first dictionary stores distance from one of the source nodes.
        The second stores the path from one of the sources to that node.
        If target is not None, returns a tuple of (distance, path) where
        distance is the distance from source to target and path is a list
        representing the path from source to target.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> length, path = nx.multi_source_dijkstra(G, {0, 4})
    >>> for node in [0, 1, 2, 3, 4]:
    ...     print(f"{node}: {length[node]}")
    0: 0
    1: 1
    2: 2
    3: 1
    4: 0
    >>> path[1]
    [0, 1]
    >>> path[3]
    [4, 3]

    >>> length, path = nx.multi_source_dijkstra(G, {0, 4}, 1)
    >>> length
    1
    >>> path
    [0, 1]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The weight function can be used to hide edges by returning None.
    So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
    will find the shortest red path.

    Based on the Python cookbook recipe (119466) at
    https://code.activestate.com/recipes/119466/

    This algorithm is not guaranteed to work if edge weights
    are negative or are floating point numbers
    (overflows and roundoff errors can cause problems).

    Raises
    ------
    ValueError
        If `sources` is empty.
    NodeNotFound
        If any of `sources` is not in `G`.

    See Also
    --------
    multi_source_dijkstra_path
    multi_source_dijkstra_path_length
networkx.multi_source_dijkstra_path
Python Library Documentation: function multi_source_dijkstra_path in module networkx.algorithms.shortest_paths.weighted

multi_source_dijkstra_path(G, sources, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
    Find shortest weighted paths in G from a given set of source
    nodes.

    Compute shortest path between any of the source nodes and all other
    reachable nodes for a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    sources : non-empty set of nodes
        Starting nodes for paths. If this is just a set containing a
        single node, then all paths computed by this function will start
        from that node. If there are two or more nodes in the set, the
        computed paths may begin from any one of the start nodes.

    cutoff : integer or float, optional
        Length (sum of edge weights) at which the search is stopped.
        If cutoff is provided, only return paths with summed weight <= cutoff.

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Returns
    -------
    paths : dictionary
        Dictionary of shortest paths keyed by target.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> path = nx.multi_source_dijkstra_path(G, {0, 4})
    >>> path[1]
    [0, 1]
    >>> path[3]
    [4, 3]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The weight function can be used to hide edges by returning None.
    So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
    will find the shortest red path.

    Raises
    ------
    ValueError
        If `sources` is empty.
    NodeNotFound
        If any of `sources` is not in `G`.

    See Also
    --------
    multi_source_dijkstra, multi_source_bellman_ford
networkx.multi_source_dijkstra_path_length
Python Library Documentation: function multi_source_dijkstra_path_length in module networkx.algorithms.shortest_paths.weighted

multi_source_dijkstra_path_length(G, sources, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
    Find shortest weighted path lengths in G from a given set of
    source nodes.

    Compute the shortest path length between any of the source nodes and
    all other reachable nodes for a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    sources : non-empty set of nodes
        Starting nodes for paths. If this is just a set containing a
        single node, then all paths computed by this function will start
        from that node. If there are two or more nodes in the set, the
        computed paths may begin from any one of the start nodes.

    cutoff : integer or float, optional
        Length (sum of edge weights) at which the search is stopped.
        If cutoff is provided, only return paths with summed weight <= cutoff.

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Returns
    -------
    length : dict
        Dict keyed by node to shortest path length to nearest source.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> length = nx.multi_source_dijkstra_path_length(G, {0, 4})
    >>> for node in [0, 1, 2, 3, 4]:
    ...     print(f"{node}: {length[node]}")
    0: 0
    1: 1
    2: 2
    3: 1
    4: 0

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The weight function can be used to hide edges by returning None.
    So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
    will find the shortest red path.

    Raises
    ------
    ValueError
        If `sources` is empty.
    NodeNotFound
        If any of `sources` is not in `G`.

    See Also
    --------
    multi_source_dijkstra
networkx.multidigraph
Python Library Documentation: module networkx.classes.multidigraph in networkx.classes

NAME
    networkx.classes.multidigraph - Base class for MultiDiGraph.

CLASSES
    networkx.classes.digraph.DiGraph(networkx.classes.graph.Graph)
        MultiDiGraph(networkx.classes.multigraph.MultiGraph, networkx.classes.digraph.DiGraph)
    networkx.classes.multigraph.MultiGraph(networkx.classes.graph.Graph)
        MultiDiGraph(networkx.classes.multigraph.MultiGraph, networkx.classes.digraph.DiGraph)

    class MultiDiGraph(networkx.classes.multigraph.MultiGraph, networkx.classes.digraph.DiGraph)
     |  MultiDiGraph(incoming_graph_data=None, multigraph_input=None, **attr)
     |
     |  A directed graph class that can store multiedges.
     |
     |  Multiedges are multiple edges between two nodes.  Each edge
     |  can hold optional data or attributes.
     |
     |  A MultiDiGraph holds directed edges.  Self loops are allowed.
     |
     |  Nodes can be arbitrary (hashable) Python objects with optional
     |  key/value attributes. By convention `None` is not used as a node.
     |
     |  Edges are represented as links between nodes with optional
     |  key/value attributes.
     |
     |  Parameters
     |  ----------
     |  incoming_graph_data : input graph (optional, default: None)
     |      Data to initialize graph. If None (default) an empty
     |      graph is created.  The data can be any format that is supported
     |      by the to_networkx_graph() function, currently including edge list,
     |      dict of dicts, dict of lists, NetworkX graph, 2D NumPy array, SciPy
     |      sparse matrix, or PyGraphviz graph.
     |
     |  multigraph_input : bool or None (default None)
     |      Note: Only used when `incoming_graph_data` is a dict.
     |      If True, `incoming_graph_data` is assumed to be a
     |      dict-of-dict-of-dict-of-dict structure keyed by
     |      node to neighbor to edge keys to edge data for multi-edges.
     |      A NetworkXError is raised if this is not the case.
     |      If False, :func:`to_networkx_graph` is used to try to determine
     |      the dict's graph data structure as either a dict-of-dict-of-dict
     |      keyed by node to neighbor to edge data, or a dict-of-iterable
     |      keyed by node to neighbors.
     |      If None, the treatment for True is tried, but if it fails,
     |      the treatment for False is tried.
     |
     |  attr : keyword arguments, optional (default= no attributes)
     |      Attributes to add to graph as key=value pairs.
     |
     |  See Also
     |  --------
     |  Graph
     |  DiGraph
     |  MultiGraph
     |
     |  Examples
     |  --------
     |  Create an empty graph structure (a "null graph") with no nodes and
     |  no edges.
     |
     |  >>> G = nx.MultiDiGraph()
     |
     |  G can be grown in several ways.
     |
     |  **Nodes:**
     |
     |  Add one node at a time:
     |
     |  >>> G.add_node(1)
     |
     |  Add the nodes from any container (a list, dict, set or
     |  even the lines from a file or the nodes from another graph).
     |
     |  >>> G.add_nodes_from([2, 3])
     |  >>> G.add_nodes_from(range(100, 110))
     |  >>> H = nx.path_graph(10)
     |  >>> G.add_nodes_from(H)
     |
     |  In addition to strings and integers any hashable Python object
     |  (except None) can represent a node, e.g. a customized node object,
     |  or even another Graph.
     |
     |  >>> G.add_node(H)
     |
     |  **Edges:**
     |
     |  G can also be grown by adding edges.
     |
     |  Add one edge,
     |
     |  >>> key = G.add_edge(1, 2)
     |
     |  a list of edges,
     |
     |  >>> keys = G.add_edges_from([(1, 2), (1, 3)])
     |
     |  or a collection of edges,
     |
     |  >>> keys = G.add_edges_from(H.edges)
     |
     |  If some edges connect nodes not yet in the graph, the nodes
     |  are added automatically.  If an edge already exists, an additional
     |  edge is created and stored using a key to identify the edge.
     |  By default the key is the lowest unused integer.
     |
     |  >>> keys = G.add_edges_from([(4, 5, dict(route=282)), (4, 5, dict(route=37))])
     |  >>> G[4]
     |  AdjacencyView({5: {0: {}, 1: {'route': 282}, 2: {'route': 37}}})
     |
     |  **Attributes:**
     |
     |  Each graph, node, and edge can hold key/value attribute pairs
     |  in an associated attribute dictionary (the keys must be hashable).
     |  By default these are empty, but can be added or changed using
     |  add_edge, add_node or direct manipulation of the attribute
     |  dictionaries named graph, node and edge respectively.
     |
     |  >>> G = nx.MultiDiGraph(day="Friday")
     |  >>> G.graph
     |  {'day': 'Friday'}
     |
     |  Add node attributes using add_node(), add_nodes_from() or G.nodes
     |
     |  >>> G.add_node(1, time="5pm")
     |  >>> G.add_nodes_from([3], time="2pm")
     |  >>> G.nodes[1]
     |  {'time': '5pm'}
     |  >>> G.nodes[1]["room"] = 714
     |  >>> del G.nodes[1]["room"]  # remove attribute
     |  >>> list(G.nodes(data=True))
     |  [(1, {'time': '5pm'}), (3, {'time': '2pm'})]
     |
     |  Add edge attributes using add_edge(), add_edges_from(), subscript
     |  notation, or G.edges.
     |
     |  >>> key = G.add_edge(1, 2, weight=4.7)
     |  >>> keys = G.add_edges_from([(3, 4), (4, 5)], color="red")
     |  >>> keys = G.add_edges_from([(1, 2, {"color": "blue"}), (2, 3, {"weight": 8})])
     |  >>> G[1][2][0]["weight"] = 4.7
     |  >>> G.edges[1, 2, 0]["weight"] = 4
     |
     |  Warning: we protect the graph data structure by making `G.edges[1,
     |  2, 0]` a read-only dict-like structure. However, you can assign to
     |  attributes in e.g. `G.edges[1, 2, 0]`. Thus, use 2 sets of brackets
     |  to add/change data attributes: `G.edges[1, 2, 0]['weight'] = 4`
     |  (for multigraphs the edge key is required: `MG.edges[u, v,
     |  key][name] = value`).
     |
     |  **Shortcuts:**
     |
     |  Many common graph features allow python syntax to speed reporting.
     |
     |  >>> 1 in G  # check if node in graph
     |  True
     |  >>> [n for n in G if n < 3]  # iterate through nodes
     |  [1, 2]
     |  >>> len(G)  # number of nodes in graph
     |  5
     |  >>> G[1]  # adjacency dict-like view mapping neighbor -> edge key -> edge attributes
     |  AdjacencyView({2: {0: {'weight': 4}, 1: {'color': 'blue'}}})
     |
     |  Often the best way to traverse all edges of a graph is via the neighbors.
     |  The neighbors are available as an adjacency-view `G.adj` object or via
     |  the method `G.adjacency()`.
     |
     |  >>> for n, nbrsdict in G.adjacency():
     |  ...     for nbr, keydict in nbrsdict.items():
     |  ...         for key, eattr in keydict.items():
     |  ...             if "weight" in eattr:
     |  ...                 # Do something useful with the edges
     |  ...                 pass
     |
     |  But the edges() method is often more convenient:
     |
     |  >>> for u, v, keys, weight in G.edges(data="weight", keys=True):
     |  ...     if weight is not None:
     |  ...         # Do something useful with the edges
     |  ...         pass
     |
     |  **Reporting:**
     |
     |  Simple graph information is obtained using methods and object-attributes.
     |  Reporting usually provides views instead of containers to reduce memory
     |  usage. The views update as the graph is updated similarly to dict-views.
     |  The objects `nodes`, `edges` and `adj` provide access to data attributes
     |  via lookup (e.g. `nodes[n]`, `edges[u, v, k]`, `adj[u][v]`) and iteration
     |  (e.g. `nodes.items()`, `nodes.data('color')`,
     |  `nodes.data('color', default='blue')` and similarly for `edges`)
     |  Views exist for `nodes`, `edges`, `neighbors()`/`adj` and `degree`.
     |
     |  For details on these and other miscellaneous methods, see below.
     |
     |  **Subclasses (Advanced):**
     |
     |  The MultiDiGraph class uses a dict-of-dict-of-dict-of-dict structure.
     |  The outer dict (node_dict) holds adjacency information keyed by node.
     |  The next dict (adjlist_dict) represents the adjacency information
     |  and holds edge_key dicts keyed by neighbor. The edge_key dict holds
     |  each edge_attr dict keyed by edge key. The inner dict
     |  (edge_attr_dict) represents the edge data and holds edge attribute
     |  values keyed by attribute names.
     |
     |  Each of these four dicts in the dict-of-dict-of-dict-of-dict
     |  structure can be replaced by a user defined dict-like object.
     |  In general, the dict-like features should be maintained but
     |  extra features can be added. To replace one of the dicts create
     |  a new graph class by changing the class(!) variable holding the
     |  factory for that dict-like structure. The variable names are
     |  node_dict_factory, node_attr_dict_factory, adjlist_inner_dict_factory,
     |  adjlist_outer_dict_factory, edge_key_dict_factory, edge_attr_dict_factory
     |  and graph_attr_dict_factory.
     |
     |  node_dict_factory : function, (default: dict)
     |      Factory function to be used to create the dict containing node
     |      attributes, keyed by node id.
     |      It should require no arguments and return a dict-like object
     |
     |  node_attr_dict_factory: function, (default: dict)
     |      Factory function to be used to create the node attribute
     |      dict which holds attribute values keyed by attribute name.
     |      It should require no arguments and return a dict-like object
     |
     |  adjlist_outer_dict_factory : function, (default: dict)
     |      Factory function to be used to create the outer-most dict
     |      in the data structure that holds adjacency info keyed by node.
     |      It should require no arguments and return a dict-like object.
     |
     |  adjlist_inner_dict_factory : function, (default: dict)
     |      Factory function to be used to create the adjacency list
     |      dict which holds multiedge key dicts keyed by neighbor.
     |      It should require no arguments and return a dict-like object.
     |
     |  edge_key_dict_factory : function, (default: dict)
     |      Factory function to be used to create the edge key dict
     |      which holds edge data keyed by edge key.
     |      It should require no arguments and return a dict-like object.
     |
     |  edge_attr_dict_factory : function, (default: dict)
     |      Factory function to be used to create the edge attribute
     |      dict which holds attribute values keyed by attribute name.
     |      It should require no arguments and return a dict-like object.
     |
     |  graph_attr_dict_factory : function, (default: dict)
     |      Factory function to be used to create the graph attribute
     |      dict which holds attribute values keyed by attribute name.
     |      It should require no arguments and return a dict-like object.
     |
     |  Typically, if your extension doesn't impact the data structure all
     |  methods will inherited without issue except: `to_directed/to_undirected`.
     |  By default these methods create a DiGraph/Graph class and you probably
     |  want them to create your extension of a DiGraph/Graph. To facilitate
     |  this we define two class variables that you can set in your subclass.
     |
     |  to_directed_class : callable, (default: DiGraph or MultiDiGraph)
     |      Class to create a new graph structure in the `to_directed` method.
     |      If `None`, a NetworkX class (DiGraph or MultiDiGraph) is used.
     |
     |  to_undirected_class : callable, (default: Graph or MultiGraph)
     |      Class to create a new graph structure in the `to_undirected` method.
     |      If `None`, a NetworkX class (Graph or MultiGraph) is used.
     |
     |  **Subclassing Example**
     |
     |  Create a low memory graph class that effectively disallows edge
     |  attributes by using a single attribute dict for all edges.
     |  This reduces the memory used, but you lose edge attributes.
     |
     |  >>> class ThinGraph(nx.Graph):
     |  ...     all_edge_dict = {"weight": 1}
     |  ...
     |  ...     def single_edge_dict(self):
     |  ...         return self.all_edge_dict
     |  ...
     |  ...     edge_attr_dict_factory = single_edge_dict
     |  >>> G = ThinGraph()
     |  >>> G.add_edge(2, 1)
     |  >>> G[2][1]
     |  {'weight': 1}
     |  >>> G.add_edge(2, 2)
     |  >>> G[2][1] is G[2][2]
     |  True
     |
     |  Method resolution order:
     |      MultiDiGraph
     |      networkx.classes.multigraph.MultiGraph
     |      networkx.classes.digraph.DiGraph
     |      networkx.classes.graph.Graph
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __init__(self, incoming_graph_data=None, multigraph_input=None, **attr)
     |      Initialize a graph with edges, name, or graph attributes.
     |
     |      Parameters
     |      ----------
     |      incoming_graph_data : input graph
     |          Data to initialize graph.  If incoming_graph_data=None (default)
     |          an empty graph is created.  The data can be an edge list, or any
     |          NetworkX graph object.  If the corresponding optional Python
     |          packages are installed the data can also be a 2D NumPy array, a
     |          SciPy sparse array, or a PyGraphviz graph.
     |
     |      multigraph_input : bool or None (default None)
     |          Note: Only used when `incoming_graph_data` is a dict.
     |          If True, `incoming_graph_data` is assumed to be a
     |          dict-of-dict-of-dict-of-dict structure keyed by
     |          node to neighbor to edge keys to edge data for multi-edges.
     |          A NetworkXError is raised if this is not the case.
     |          If False, :func:`to_networkx_graph` is used to try to determine
     |          the dict's graph data structure as either a dict-of-dict-of-dict
     |          keyed by node to neighbor to edge data, or a dict-of-iterable
     |          keyed by node to neighbors.
     |          If None, the treatment for True is tried, but if it fails,
     |          the treatment for False is tried.
     |
     |      attr : keyword arguments, optional (default= no attributes)
     |          Attributes to add to graph as key=value pairs.
     |
     |      See Also
     |      --------
     |      convert
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G = nx.Graph(name="my graph")
     |      >>> e = [(1, 2), (2, 3), (3, 4)]  # list of edges
     |      >>> G = nx.Graph(e)
     |
     |      Arbitrary graph attribute pairs (key=value) may be assigned
     |
     |      >>> G = nx.Graph(e, day="Friday")
     |      >>> G.graph
     |      {'day': 'Friday'}
     |
     |  add_edge(self, u_for_edge, v_for_edge, key=None, **attr)
     |      Add an edge between u and v.
     |
     |      The nodes u and v will be automatically added if they are
     |      not already in the graph.
     |
     |      Edge attributes can be specified with keywords or by directly
     |      accessing the edge's attribute dictionary. See examples below.
     |
     |      Parameters
     |      ----------
     |      u_for_edge, v_for_edge : nodes
     |          Nodes can be, for example, strings or numbers.
     |          Nodes must be hashable (and not None) Python objects.
     |      key : hashable identifier, optional (default=lowest unused integer)
     |          Used to distinguish multiedges between a pair of nodes.
     |      attr : keyword arguments, optional
     |          Edge data (or labels or objects) can be assigned using
     |          keyword arguments.
     |
     |      Returns
     |      -------
     |      The edge key assigned to the edge.
     |
     |      See Also
     |      --------
     |      add_edges_from : add a collection of edges
     |
     |      Notes
     |      -----
     |      To replace/update edge data, use the optional key argument
     |      to identify a unique edge.  Otherwise a new edge will be created.
     |
     |      NetworkX algorithms designed for weighted graphs cannot use
     |      multigraphs directly because it is not clear how to handle
     |      multiedge weights.  Convert to Graph using edge attribute
     |      'weight' to enable weighted graph algorithms.
     |
     |      Default keys are generated using the method `new_edge_key()`.
     |      This method can be overridden by subclassing the base class and
     |      providing a custom `new_edge_key()` method.
     |
     |      Examples
     |      --------
     |      The following all add the edge e=(1, 2) to graph G:
     |
     |      >>> G = nx.MultiDiGraph()
     |      >>> e = (1, 2)
     |      >>> key = G.add_edge(1, 2)  # explicit two-node form
     |      >>> G.add_edge(*e)  # single edge as tuple of two nodes
     |      1
     |      >>> G.add_edges_from([(1, 2)])  # add edges from iterable container
     |      [2]
     |
     |      Associate data to edges using keywords:
     |
     |      >>> key = G.add_edge(1, 2, weight=3)
     |      >>> key = G.add_edge(1, 2, key=0, weight=4)  # update data for key=0
     |      >>> key = G.add_edge(1, 3, weight=7, capacity=15, length=342.7)
     |
     |      For non-string attribute keys, use subscript notation.
     |
     |      >>> ekey = G.add_edge(1, 2)
     |      >>> G[1][2][0].update({0: 5})
     |      >>> G.edges[1, 2, 0].update({0: 5})
     |
     |  adj = <functools.cached_property object>
     |      Graph adjacency object holding the neighbors of each node.
     |
     |      This object is a read-only dict-like structure with node keys
     |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
     |      to the edgekey-dict.  So `G.adj[3][2][0]['color'] = 'blue'` sets
     |      the color of the edge `(3, 2, 0)` to `"blue"`.
     |
     |      Iterating over G.adj behaves like a dict. Useful idioms include
     |      `for nbr, datadict in G.adj[n].items():`.
     |
     |      The neighbor information is also provided by subscripting the graph.
     |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
     |
     |      For directed graphs, `G.adj` holds outgoing (successor) info.
     |
     |  degree = <functools.cached_property object>
     |      A DegreeView for the Graph as G.degree or G.degree().
     |
     |      The node degree is the number of edges adjacent to the node.
     |      The weighted node degree is the sum of the edge weights for
     |      edges incident to that node.
     |
     |      This object provides an iterator for (node, degree) as well as
     |      lookup for the degree for a single node.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      weight : string or None, optional (default=None)
     |         The name of an edge attribute that holds the numerical value used
     |         as a weight.  If None, then each edge has weight 1.
     |         The degree is the sum of the edge weights adjacent to the node.
     |
     |      Returns
     |      -------
     |      DiMultiDegreeView or int
     |          If multiple nodes are requested (the default), returns a `DiMultiDegreeView`
     |          mapping nodes to their degree.
     |          If a single node is requested, returns the degree of the node as an integer.
     |
     |      See Also
     |      --------
     |      out_degree, in_degree
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiDiGraph()
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.degree(0)  # node 0 with degree 1
     |      1
     |      >>> list(G.degree([0, 1, 2]))
     |      [(0, 1), (1, 2), (2, 2)]
     |      >>> G.add_edge(0, 1)  # parallel edge
     |      1
     |      >>> list(G.degree([0, 1, 2]))  # parallel edges are counted
     |      [(0, 2), (1, 3), (2, 2)]
     |
     |  edges = <functools.cached_property object>
     |      An OutMultiEdgeView of the Graph as G.edges or G.edges().
     |
     |      edges(self, nbunch=None, data=False, keys=False, default=None)
     |
     |      The OutMultiEdgeView provides set-like operations on the edge-tuples
     |      as well as edge attribute lookup. When called, it also provides
     |      an EdgeDataView object which allows control of access to edge
     |      attributes (but does not provide set-like operations).
     |      Hence, ``G.edges[u, v, k]['color']`` provides the value of the color
     |      attribute for the edge from ``u`` to ``v`` with key ``k`` while
     |      ``for (u, v, k, c) in G.edges(data='color', default='red', keys=True):``
     |      iterates through all the edges yielding the color attribute with
     |      default `'red'` if no color attribute exists.
     |
     |      Edges are returned as tuples with optional data and keys
     |      in the order (node, neighbor, key, data). If ``keys=True`` is not
     |      provided, the tuples will just be (node, neighbor, data), but
     |      multiple tuples with the same node and neighbor will be
     |      generated when multiple edges between two nodes exist.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges from these nodes.
     |      data : string or bool, optional (default=False)
     |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
     |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
     |          If False, return 2-tuple (u, v).
     |      keys : bool, optional (default=False)
     |          If True, return edge keys with each edge, creating (u, v, k,
     |          d) tuples when data is also requested (the default) and (u,
     |          v, k) tuples when data is not requested.
     |      default : value, optional (default=None)
     |          Value used for edges that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      edges : OutMultiEdgeView
     |          A view of edge attributes, usually it iterates over (u, v)
     |          (u, v, k) or (u, v, k, d) tuples of edges, but can also be
     |          used for attribute lookup as ``edges[u, v, k]['foo']``.
     |
     |      Notes
     |      -----
     |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
     |      For directed graphs this returns the out-edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiDiGraph()
     |      >>> nx.add_path(G, [0, 1, 2])
     |      >>> key = G.add_edge(2, 3, weight=5)
     |      >>> key2 = G.add_edge(1, 2)  # second edge between these nodes
     |      >>> [e for e in G.edges()]
     |      [(0, 1), (1, 2), (1, 2), (2, 3)]
     |      >>> list(G.edges(data=True))  # default data is {} (empty dict)
     |      [(0, 1, {}), (1, 2, {}), (1, 2, {}), (2, 3, {'weight': 5})]
     |      >>> list(G.edges(data="weight", default=1))
     |      [(0, 1, 1), (1, 2, 1), (1, 2, 1), (2, 3, 5)]
     |      >>> list(G.edges(keys=True))  # default keys are integers
     |      [(0, 1, 0), (1, 2, 0), (1, 2, 1), (2, 3, 0)]
     |      >>> list(G.edges(data=True, keys=True))
     |      [(0, 1, 0, {}), (1, 2, 0, {}), (1, 2, 1, {}), (2, 3, 0, {'weight': 5})]
     |      >>> list(G.edges(data="weight", default=1, keys=True))
     |      [(0, 1, 0, 1), (1, 2, 0, 1), (1, 2, 1, 1), (2, 3, 0, 5)]
     |      >>> list(G.edges([0, 2]))
     |      [(0, 1), (2, 3)]
     |      >>> list(G.edges(0))
     |      [(0, 1)]
     |      >>> list(G.edges(1))
     |      [(1, 2), (1, 2)]
     |
     |      See Also
     |      --------
     |      in_edges, out_edges
     |
     |  in_degree = <functools.cached_property object>
     |      A DegreeView for (node, in_degree) or in_degree for single node.
     |
     |      The node in-degree is the number of edges pointing into the node.
     |      The weighted node degree is the sum of the edge weights for
     |      edges incident to that node.
     |
     |      This object provides an iterator for (node, degree) as well as
     |      lookup for the degree for a single node.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      weight : string or None, optional (default=None)
     |         The edge attribute that holds the numerical value used
     |         as a weight.  If None, then each edge has weight 1.
     |         The degree is the sum of the edge weights adjacent to the node.
     |
     |      Returns
     |      -------
     |      If a single node is requested
     |      deg : int
     |          Degree of the node
     |
     |      OR if multiple nodes are requested
     |      nd_iter : iterator
     |          The iterator returns two-tuples of (node, in-degree).
     |
     |      See Also
     |      --------
     |      degree, out_degree
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiDiGraph()
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.in_degree(0)  # node 0 with degree 0
     |      0
     |      >>> list(G.in_degree([0, 1, 2]))
     |      [(0, 0), (1, 1), (2, 1)]
     |      >>> G.add_edge(0, 1)  # parallel edge
     |      1
     |      >>> list(G.in_degree([0, 1, 2]))  # parallel edges counted
     |      [(0, 0), (1, 2), (2, 1)]
     |
     |  in_edges = <functools.cached_property object>
     |      A view of the in edges of the graph as G.in_edges or G.in_edges().
     |
     |      in_edges(self, nbunch=None, data=False, keys=False, default=None)
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |      data : string or bool, optional (default=False)
     |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
     |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
     |          If False, return 2-tuple (u, v).
     |      keys : bool, optional (default=False)
     |          If True, return edge keys with each edge, creating 3-tuples
     |          (u, v, k) or with data, 4-tuples (u, v, k, d).
     |      default : value, optional (default=None)
     |          Value used for edges that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      in_edges : InMultiEdgeView or InMultiEdgeDataView
     |          A view of edge attributes, usually it iterates over (u, v)
     |          or (u, v, k) or (u, v, k, d) tuples of edges, but can also be
     |          used for attribute lookup as `edges[u, v, k]['foo']`.
     |
     |      See Also
     |      --------
     |      edges
     |
     |  is_directed(self)
     |      Returns True if graph is directed, False otherwise.
     |
     |  is_multigraph(self)
     |      Returns True if graph is a multigraph, False otherwise.
     |
     |  out_degree = <functools.cached_property object>
     |      Returns an iterator for (node, out-degree) or out-degree for single node.
     |
     |      out_degree(self, nbunch=None, weight=None)
     |
     |      The node out-degree is the number of edges pointing out of the node.
     |      This function returns the out-degree for a single node or an iterator
     |      for a bunch of nodes or if nothing is passed as argument.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      weight : string or None, optional (default=None)
     |         The edge attribute that holds the numerical value used
     |         as a weight.  If None, then each edge has weight 1.
     |         The degree is the sum of the edge weights.
     |
     |      Returns
     |      -------
     |      If a single node is requested
     |      deg : int
     |          Degree of the node
     |
     |      OR if multiple nodes are requested
     |      nd_iter : iterator
     |          The iterator returns two-tuples of (node, out-degree).
     |
     |      See Also
     |      --------
     |      degree, in_degree
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiDiGraph()
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.out_degree(0)  # node 0 with degree 1
     |      1
     |      >>> list(G.out_degree([0, 1, 2]))
     |      [(0, 1), (1, 1), (2, 1)]
     |      >>> G.add_edge(0, 1)  # parallel edge
     |      1
     |      >>> list(G.out_degree([0, 1, 2]))  # counts parallel edges
     |      [(0, 2), (1, 1), (2, 1)]
     |
     |  out_edges = <functools.cached_property object>
     |      An OutMultiEdgeView of the Graph as G.edges or G.edges().
     |
     |      edges(self, nbunch=None, data=False, keys=False, default=None)
     |
     |      The OutMultiEdgeView provides set-like operations on the edge-tuples
     |      as well as edge attribute lookup. When called, it also provides
     |      an EdgeDataView object which allows control of access to edge
     |      attributes (but does not provide set-like operations).
     |      Hence, ``G.edges[u, v, k]['color']`` provides the value of the color
     |      attribute for the edge from ``u`` to ``v`` with key ``k`` while
     |      ``for (u, v, k, c) in G.edges(data='color', default='red', keys=True):``
     |      iterates through all the edges yielding the color attribute with
     |      default `'red'` if no color attribute exists.
     |
     |      Edges are returned as tuples with optional data and keys
     |      in the order (node, neighbor, key, data). If ``keys=True`` is not
     |      provided, the tuples will just be (node, neighbor, data), but
     |      multiple tuples with the same node and neighbor will be
     |      generated when multiple edges between two nodes exist.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges from these nodes.
     |      data : string or bool, optional (default=False)
     |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
     |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
     |          If False, return 2-tuple (u, v).
     |      keys : bool, optional (default=False)
     |          If True, return edge keys with each edge, creating (u, v, k,
     |          d) tuples when data is also requested (the default) and (u,
     |          v, k) tuples when data is not requested.
     |      default : value, optional (default=None)
     |          Value used for edges that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      edges : OutMultiEdgeView
     |          A view of edge attributes, usually it iterates over (u, v)
     |          (u, v, k) or (u, v, k, d) tuples of edges, but can also be
     |          used for attribute lookup as ``edges[u, v, k]['foo']``.
     |
     |      Notes
     |      -----
     |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
     |      For directed graphs this returns the out-edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiDiGraph()
     |      >>> nx.add_path(G, [0, 1, 2])
     |      >>> key = G.add_edge(2, 3, weight=5)
     |      >>> key2 = G.add_edge(1, 2)  # second edge between these nodes
     |      >>> [e for e in G.edges()]
     |      [(0, 1), (1, 2), (1, 2), (2, 3)]
     |      >>> list(G.edges(data=True))  # default data is {} (empty dict)
     |      [(0, 1, {}), (1, 2, {}), (1, 2, {}), (2, 3, {'weight': 5})]
     |      >>> list(G.edges(data="weight", default=1))
     |      [(0, 1, 1), (1, 2, 1), (1, 2, 1), (2, 3, 5)]
     |      >>> list(G.edges(keys=True))  # default keys are integers
     |      [(0, 1, 0), (1, 2, 0), (1, 2, 1), (2, 3, 0)]
     |      >>> list(G.edges(data=True, keys=True))
     |      [(0, 1, 0, {}), (1, 2, 0, {}), (1, 2, 1, {}), (2, 3, 0, {'weight': 5})]
     |      >>> list(G.edges(data="weight", default=1, keys=True))
     |      [(0, 1, 0, 1), (1, 2, 0, 1), (1, 2, 1, 1), (2, 3, 0, 5)]
     |      >>> list(G.edges([0, 2]))
     |      [(0, 1), (2, 3)]
     |      >>> list(G.edges(0))
     |      [(0, 1)]
     |      >>> list(G.edges(1))
     |      [(1, 2), (1, 2)]
     |
     |      See Also
     |      --------
     |      in_edges, out_edges
     |
     |  pred = <functools.cached_property object>
     |      Graph adjacency object holding the predecessors of each node.
     |
     |      This object is a read-only dict-like structure with node keys
     |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
     |      to the edgekey-dict.  So `G.adj[3][2][0]['color'] = 'blue'` sets
     |      the color of the edge `(3, 2, 0)` to `"blue"`.
     |
     |      Iterating over G.adj behaves like a dict. Useful idioms include
     |      `for nbr, datadict in G.adj[n].items():`.
     |
     |  remove_edge(self, u, v, key=None)
     |      Remove an edge between u and v.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |          Remove an edge between nodes u and v.
     |      key : hashable identifier, optional (default=None)
     |          Used to distinguish multiple edges between a pair of nodes.
     |          If None, remove a single edge between u and v. If there are
     |          multiple edges, removes the last edge added in terms of
     |          insertion order.
     |
     |      Raises
     |      ------
     |      NetworkXError
     |          If there is not an edge between u and v, or
     |          if there is no edge with the specified key.
     |
     |      See Also
     |      --------
     |      remove_edges_from : remove a collection of edges
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiDiGraph()
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.remove_edge(0, 1)
     |      >>> e = (1, 2)
     |      >>> G.remove_edge(*e)  # unpacks e from an edge tuple
     |
     |      For multiple edges
     |
     |      >>> G = nx.MultiDiGraph()
     |      >>> G.add_edges_from([(1, 2), (1, 2), (1, 2)])  # key_list returned
     |      [0, 1, 2]
     |
     |      When ``key=None`` (the default), edges are removed in the opposite
     |      order that they were added:
     |
     |      >>> G.remove_edge(1, 2)
     |      >>> G.edges(keys=True)
     |      OutMultiEdgeView([(1, 2, 0), (1, 2, 1)])
     |
     |      For edges with keys
     |
     |      >>> G = nx.MultiDiGraph()
     |      >>> G.add_edge(1, 2, key="first")
     |      'first'
     |      >>> G.add_edge(1, 2, key="second")
     |      'second'
     |      >>> G.remove_edge(1, 2, key="first")
     |      >>> G.edges(keys=True)
     |      OutMultiEdgeView([(1, 2, 'second')])
     |
     |  reverse(self, copy=True)
     |      Returns the reverse of the graph.
     |
     |      The reverse is a graph with the same nodes and edges
     |      but with the directions of the edges reversed.
     |
     |      Parameters
     |      ----------
     |      copy : bool optional (default=True)
     |          If True, return a new DiGraph holding the reversed edges.
     |          If False, the reverse graph is created using a view of
     |          the original graph.
     |
     |  succ = <functools.cached_property object>
     |      Graph adjacency object holding the successors of each node.
     |
     |      This object is a read-only dict-like structure with node keys
     |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
     |      to the edgekey-dict.  So `G.adj[3][2][0]['color'] = 'blue'` sets
     |      the color of the edge `(3, 2, 0)` to `"blue"`.
     |
     |      Iterating over G.adj behaves like a dict. Useful idioms include
     |      `for nbr, datadict in G.adj[n].items():`.
     |
     |      The neighbor information is also provided by subscripting the graph.
     |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
     |
     |      For directed graphs, `G.succ` is identical to `G.adj`.
     |
     |  to_undirected(self, reciprocal=False, as_view=False)
     |      Returns an undirected representation of the digraph.
     |
     |      Parameters
     |      ----------
     |      reciprocal : bool (optional)
     |        If True only keep edges that appear in both directions
     |        in the original digraph.
     |      as_view : bool (optional, default=False)
     |        If True return an undirected view of the original directed graph.
     |
     |      Returns
     |      -------
     |      G : MultiGraph
     |          An undirected graph with the same name and nodes and
     |          with edge (u, v, data) if either (u, v, data) or (v, u, data)
     |          is in the digraph.  If both edges exist in digraph and
     |          their edge data is different, only one edge is created
     |          with an arbitrary choice of which edge data to use.
     |          You must check and correct for this manually if desired.
     |
     |      See Also
     |      --------
     |      MultiGraph, copy, add_edge, add_edges_from
     |
     |      Notes
     |      -----
     |      This returns a "deepcopy" of the edge, node, and
     |      graph attributes which attempts to completely copy
     |      all of the data and references.
     |
     |      This is in contrast to the similar D=MultiDiGraph(G) which
     |      returns a shallow copy of the data.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Warning: If you have subclassed MultiDiGraph to use dict-like
     |      objects in the data structure, those changes do not transfer
     |      to the MultiGraph created by this method.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(2)  # or MultiGraph, etc
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1), (1, 0)]
     |      >>> G2 = H.to_undirected()
     |      >>> list(G2.edges)
     |      [(0, 1)]
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  edge_key_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from networkx.classes.multigraph.MultiGraph:
     |
     |  add_edges_from(self, ebunch_to_add, **attr)
     |      Add all the edges in ebunch_to_add.
     |
     |      Parameters
     |      ----------
     |      ebunch_to_add : container of edges
     |          Each edge given in the container will be added to the
     |          graph. The edges can be:
     |
     |              - 2-tuples (u, v) or
     |              - 3-tuples (u, v, d) for an edge data dict d, or
     |              - 3-tuples (u, v, k) for not iterable key k, or
     |              - 4-tuples (u, v, k, d) for an edge with data and key k
     |
     |      attr : keyword arguments, optional
     |          Edge data (or labels or objects) can be assigned using
     |          keyword arguments.
     |
     |      Returns
     |      -------
     |      A list of edge keys assigned to the edges in `ebunch`.
     |
     |      See Also
     |      --------
     |      add_edge : add a single edge
     |      add_weighted_edges_from : convenient way to add weighted edges
     |
     |      Notes
     |      -----
     |      Adding the same edge twice has no effect but any edge data
     |      will be updated when each duplicate edge is added.
     |
     |      Edge attributes specified in an ebunch take precedence over
     |      attributes specified via keyword arguments.
     |
     |      Default keys are generated using the method ``new_edge_key()``.
     |      This method can be overridden by subclassing the base class and
     |      providing a custom ``new_edge_key()`` method.
     |
     |      When adding edges from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_edges)`, and pass this
     |      object to `G.add_edges_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_edges_from([(0, 1), (1, 2)])  # using a list of edge tuples
     |      >>> e = zip(range(0, 3), range(1, 4))
     |      >>> G.add_edges_from(e)  # Add the path graph 0-1-2-3
     |
     |      Associate data to edges
     |
     |      >>> G.add_edges_from([(1, 2), (2, 3)], weight=3)
     |      >>> G.add_edges_from([(3, 4), (1, 4)], label="WN2898")
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.MultiGraph([(1, 2), (2, 3), (3, 4)])
     |      >>> # Grow graph by one new node, adding edges to all existing nodes.
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_edges_from(((5, n) for n in G.nodes))
     |      >>> # right way - note that there will be no self-edge for node 5
     |      >>> assigned_keys = G.add_edges_from(list((5, n) for n in G.nodes))
     |
     |  copy(self, as_view=False)
     |      Returns a copy of the graph.
     |
     |      The copy method by default returns an independent shallow copy
     |      of the graph and attributes. That is, if an attribute is a
     |      container, that container is shared by the original an the copy.
     |      Use Python's `copy.deepcopy` for new containers.
     |
     |      If `as_view` is True then a view is returned instead of a copy.
     |
     |      Notes
     |      -----
     |      All copies reproduce the graph structure, but data attributes
     |      may be handled in different ways. There are four types of copies
     |      of a graph that people might want.
     |
     |      Deepcopy -- A "deepcopy" copies the graph structure as well as
     |      all data attributes and any objects they might contain.
     |      The entire graph object is new so that changes in the copy
     |      do not affect the original object. (see Python's copy.deepcopy)
     |
     |      Data Reference (Shallow) -- For a shallow copy the graph structure
     |      is copied but the edge, node and graph attribute dicts are
     |      references to those in the original graph. This saves
     |      time and memory but could cause confusion if you change an attribute
     |      in one graph and it changes the attribute in the other.
     |      NetworkX does not provide this level of shallow copy.
     |
     |      Independent Shallow -- This copy creates new independent attribute
     |      dicts and then does a shallow copy of the attributes. That is, any
     |      attributes that are containers are shared between the new graph
     |      and the original. This is exactly what `dict.copy()` provides.
     |      You can obtain this style copy using:
     |
     |          >>> G = nx.path_graph(5)
     |          >>> H = G.copy()
     |          >>> H = G.copy(as_view=False)
     |          >>> H = nx.Graph(G)
     |          >>> H = G.__class__(G)
     |
     |      Fresh Data -- For fresh data, the graph structure is copied while
     |      new empty data attribute dicts are created. The resulting graph
     |      is independent of the original and it has no edge, node or graph
     |      attributes. Fresh copies are not enabled. Instead use:
     |
     |          >>> H = G.__class__()
     |          >>> H.add_nodes_from(G)
     |          >>> H.add_edges_from(G.edges)
     |
     |      View -- Inspired by dict-views, graph-views act like read-only
     |      versions of the original graph, providing a copy of the original
     |      structure without requiring any memory for copying the information.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Parameters
     |      ----------
     |      as_view : bool, optional (default=False)
     |          If True, the returned graph-view provides a read-only view
     |          of the original graph without actually copying any data.
     |
     |      Returns
     |      -------
     |      G : Graph
     |          A copy of the graph.
     |
     |      See Also
     |      --------
     |      to_directed: return a directed copy of the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> H = G.copy()
     |
     |  get_edge_data(self, u, v, key=None, default=None)
     |      Returns the attribute dictionary associated with edge (u, v,
     |      key).
     |
     |      If a key is not provided, returns a dictionary mapping edge keys
     |      to attribute dictionaries for each edge between u and v.
     |
     |      This is identical to `G[u][v][key]` except the default is returned
     |      instead of an exception is the edge doesn't exist.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |
     |      default :  any Python object (default=None)
     |          Value to return if the specific edge (u, v, key) is not
     |          found, OR if there are no edges between u and v and no key
     |          is specified.
     |
     |      key : hashable identifier, optional (default=None)
     |          Return data only for the edge with specified key, as an
     |          attribute dictionary (rather than a dictionary mapping keys
     |          to attribute dictionaries).
     |
     |      Returns
     |      -------
     |      edge_dict : dictionary
     |          The edge attribute dictionary, OR a dictionary mapping edge
     |          keys to attribute dictionaries for each of those edges if no
     |          specific key is provided (even if there's only one edge
     |          between u and v).
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiGraph()  # or MultiDiGraph
     |      >>> key = G.add_edge(0, 1, key="a", weight=7)
     |      >>> G[0][1]["a"]  # key='a'
     |      {'weight': 7}
     |      >>> G.edges[0, 1, "a"]  # key='a'
     |      {'weight': 7}
     |
     |      Warning: we protect the graph data structure by making
     |      `G.edges` and `G[1][2]` read-only dict-like structures.
     |      However, you can assign values to attributes in e.g.
     |      `G.edges[1, 2, 'a']` or `G[1][2]['a']` using an additional
     |      bracket as shown next. You need to specify all edge info
     |      to assign to the edge data associated with an edge.
     |
     |      >>> G[0][1]["a"]["weight"] = 10
     |      >>> G.edges[0, 1, "a"]["weight"] = 10
     |      >>> G[0][1]["a"]["weight"]
     |      10
     |      >>> G.edges[1, 0, "a"]["weight"]
     |      10
     |
     |      >>> G = nx.MultiGraph()  # or MultiDiGraph
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.edges[0, 1, 0]["weight"] = 5
     |      >>> G.get_edge_data(0, 1)
     |      {0: {'weight': 5}}
     |      >>> e = (0, 1)
     |      >>> G.get_edge_data(*e)  # tuple form
     |      {0: {'weight': 5}}
     |      >>> G.get_edge_data(3, 0)  # edge not in graph, returns None
     |      >>> G.get_edge_data(3, 0, default=0)  # edge not in graph, return default
     |      0
     |      >>> G.get_edge_data(1, 0, 0)  # specific key gives back
     |      {'weight': 5}
     |
     |  has_edge(self, u, v, key=None)
     |      Returns True if the graph has an edge between nodes u and v.
     |
     |      This is the same as `v in G[u] or key in G[u][v]`
     |      without KeyError exceptions.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |          Nodes can be, for example, strings or numbers.
     |
     |      key : hashable identifier, optional (default=None)
     |          If specified return True only if the edge with
     |          key is found.
     |
     |      Returns
     |      -------
     |      edge_ind : bool
     |          True if edge is in the graph, False otherwise.
     |
     |      Examples
     |      --------
     |      Can be called either using two nodes u, v, an edge tuple (u, v),
     |      or an edge tuple (u, v, key).
     |
     |      >>> G = nx.MultiGraph()  # or MultiDiGraph
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.has_edge(0, 1)  # using two nodes
     |      True
     |      >>> e = (0, 1)
     |      >>> G.has_edge(*e)  #  e is a 2-tuple (u, v)
     |      True
     |      >>> G.add_edge(0, 1, key="a")
     |      'a'
     |      >>> G.has_edge(0, 1, key="a")  # specify key
     |      True
     |      >>> G.has_edge(1, 0, key="a")  # edges aren't directed
     |      True
     |      >>> e = (0, 1, "a")
     |      >>> G.has_edge(*e)  # e is a 3-tuple (u, v, 'a')
     |      True
     |
     |      The following syntax are equivalent:
     |
     |      >>> G.has_edge(0, 1)
     |      True
     |      >>> 1 in G[0]  # though this gives :exc:`KeyError` if 0 not in G
     |      True
     |      >>> 0 in G[1]  # other order; also gives :exc:`KeyError` if 0 not in G
     |      True
     |
     |  new_edge_key(self, u, v)
     |      Returns an unused key for edges between nodes `u` and `v`.
     |
     |      The nodes `u` and `v` do not need to be already in the graph.
     |
     |      Notes
     |      -----
     |      In the standard MultiGraph class the new key is the number of existing
     |      edges between `u` and `v` (increased if necessary to ensure unused).
     |      The first edge will have key 0, then 1, etc. If an edge is removed
     |      further new_edge_keys may not be in this order.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |
     |      Returns
     |      -------
     |      key : int
     |
     |  number_of_edges(self, u=None, v=None)
     |      Returns the number of edges between two nodes.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes, optional (Default=all edges)
     |          If u and v are specified, return the number of edges between
     |          u and v. Otherwise return the total number of all edges.
     |
     |      Returns
     |      -------
     |      nedges : int
     |          The number of edges in the graph.  If nodes `u` and `v` are
     |          specified return the number of edges between those nodes. If
     |          the graph is directed, this only returns the number of edges
     |          from `u` to `v`.
     |
     |      See Also
     |      --------
     |      size
     |
     |      Examples
     |      --------
     |      For undirected multigraphs, this method counts the total number
     |      of edges in the graph::
     |
     |          >>> G = nx.MultiGraph()
     |          >>> G.add_edges_from([(0, 1), (0, 1), (1, 2)])
     |          [0, 1, 0]
     |          >>> G.number_of_edges()
     |          3
     |
     |      If you specify two nodes, this counts the total number of edges
     |      joining the two nodes::
     |
     |          >>> G.number_of_edges(0, 1)
     |          2
     |
     |      For directed multigraphs, this method can count the total number
     |      of directed edges from `u` to `v`::
     |
     |          >>> G = nx.MultiDiGraph()
     |          >>> G.add_edges_from([(0, 1), (0, 1), (1, 0)])
     |          [0, 1, 0]
     |          >>> G.number_of_edges(0, 1)
     |          2
     |          >>> G.number_of_edges(1, 0)
     |          1
     |
     |  remove_edges_from(self, ebunch)
     |      Remove all edges specified in ebunch.
     |
     |      Parameters
     |      ----------
     |      ebunch: list or container of edge tuples
     |          Each edge given in the list or container will be removed
     |          from the graph. The edges can be:
     |
     |              - 2-tuples (u, v) A single edge between u and v is removed.
     |              - 3-tuples (u, v, key) The edge identified by key is removed.
     |              - 4-tuples (u, v, key, data) where data is ignored.
     |
     |      See Also
     |      --------
     |      remove_edge : remove a single edge
     |
     |      Notes
     |      -----
     |      Will fail silently if an edge in ebunch is not in the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> ebunch = [(1, 2), (2, 3)]
     |      >>> G.remove_edges_from(ebunch)
     |
     |      Removing multiple copies of edges
     |
     |      >>> G = nx.MultiGraph()
     |      >>> keys = G.add_edges_from([(1, 2), (1, 2), (1, 2)])
     |      >>> G.remove_edges_from([(1, 2), (2, 1)])  # edges aren't directed
     |      >>> list(G.edges())
     |      [(1, 2)]
     |      >>> G.remove_edges_from([(1, 2), (1, 2)])  # silently ignore extra copy
     |      >>> list(G.edges)  # now empty graph
     |      []
     |
     |      When the edge is a 2-tuple ``(u, v)`` but there are multiple edges between
     |      u and v in the graph, the most recent edge (in terms of insertion
     |      order) is removed.
     |
     |      >>> G = nx.MultiGraph()
     |      >>> for key in ("x", "y", "a"):
     |      ...     k = G.add_edge(0, 1, key=key)
     |      >>> G.edges(keys=True)
     |      MultiEdgeView([(0, 1, 'x'), (0, 1, 'y'), (0, 1, 'a')])
     |      >>> G.remove_edges_from([(0, 1)])
     |      >>> G.edges(keys=True)
     |      MultiEdgeView([(0, 1, 'x'), (0, 1, 'y')])
     |
     |  to_directed(self, as_view=False)
     |      Returns a directed representation of the graph.
     |
     |      Returns
     |      -------
     |      G : MultiDiGraph
     |          A directed graph with the same name, same nodes, and with
     |          each edge (u, v, k, data) replaced by two directed edges
     |          (u, v, k, data) and (v, u, k, data).
     |
     |      Notes
     |      -----
     |      This returns a "deepcopy" of the edge, node, and
     |      graph attributes which attempts to completely copy
     |      all of the data and references.
     |
     |      This is in contrast to the similar D=MultiDiGraph(G) which
     |      returns a shallow copy of the data.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Warning: If you have subclassed MultiGraph to use dict-like objects
     |      in the data structure, those changes do not transfer to the
     |      MultiDiGraph created by this method.
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiGraph()
     |      >>> G.add_edge(0, 1)
     |      0
     |      >>> G.add_edge(0, 1)
     |      1
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1, 0), (0, 1, 1), (1, 0, 0), (1, 0, 1)]
     |
     |      If already directed, return a (deep) copy
     |
     |      >>> G = nx.MultiDiGraph()
     |      >>> G.add_edge(0, 1)
     |      0
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1, 0)]
     |
     |  to_directed_class(self)
     |      Returns the class to use for empty directed copies.
     |
     |      If you subclass the base classes, use this to designate
     |      what directed class to use for `to_directed()` copies.
     |
     |  to_undirected_class(self)
     |      Returns the class to use for empty undirected copies.
     |
     |      If you subclass the base classes, use this to designate
     |      what directed class to use for `to_directed()` copies.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from networkx.classes.digraph.DiGraph:
     |
     |  add_node(self, node_for_adding, **attr)
     |      Add a single node `node_for_adding` and update node attributes.
     |
     |      Parameters
     |      ----------
     |      node_for_adding : node
     |          A node can be any hashable Python object except None.
     |      attr : keyword arguments, optional
     |          Set or change node attributes using key=value.
     |
     |      See Also
     |      --------
     |      add_nodes_from
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_node(1)
     |      >>> G.add_node("Hello")
     |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
     |      >>> G.add_node(K3)
     |      >>> G.number_of_nodes()
     |      3
     |
     |      Use keywords set/change node attributes:
     |
     |      >>> G.add_node(1, size=10)
     |      >>> G.add_node(3, weight=0.4, UTM=("13S", 382871, 3972649))
     |
     |      Notes
     |      -----
     |      A hashable object is one that can be used as a key in a Python
     |      dictionary. This includes strings, numbers, tuples of strings
     |      and numbers, etc.
     |
     |      On many platforms hashable items also include mutables such as
     |      NetworkX Graphs, though one should be careful that the hash
     |      doesn't change on mutables.
     |
     |  add_nodes_from(self, nodes_for_adding, **attr)
     |      Add multiple nodes.
     |
     |      Parameters
     |      ----------
     |      nodes_for_adding : iterable container
     |          A container of nodes (list, dict, set, etc.).
     |          OR
     |          A container of (node, attribute dict) tuples.
     |          Node attributes are updated using the attribute dict.
     |      attr : keyword arguments, optional (default= no attributes)
     |          Update attributes for all nodes in nodes.
     |          Node attributes specified in nodes as a tuple take
     |          precedence over attributes specified via keyword arguments.
     |
     |      See Also
     |      --------
     |      add_node
     |
     |      Notes
     |      -----
     |      When adding nodes from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
     |      object to `G.add_nodes_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_nodes_from("Hello")
     |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
     |      >>> G.add_nodes_from(K3)
     |      >>> sorted(G.nodes(), key=str)
     |      [0, 1, 2, 'H', 'e', 'l', 'o']
     |
     |      Use keywords to update specific node attributes for every node.
     |
     |      >>> G.add_nodes_from([1, 2], size=10)
     |      >>> G.add_nodes_from([3, 4], weight=0.4)
     |
     |      Use (node, attrdict) tuples to update attributes for specific nodes.
     |
     |      >>> G.add_nodes_from([(1, dict(size=11)), (2, {"color": "blue"})])
     |      >>> G.nodes[1]["size"]
     |      11
     |      >>> H = nx.Graph()
     |      >>> H.add_nodes_from(G.nodes(data=True))
     |      >>> H.nodes[1]["size"]
     |      11
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.DiGraph([(0, 1), (1, 2), (3, 4)])
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_nodes_from(n + 1 for n in G.nodes)
     |      >>> # correct way
     |      >>> G.add_nodes_from(list(n + 1 for n in G.nodes))
     |
     |  clear(self)
     |      Remove all nodes and edges from the graph.
     |
     |      This also removes the name, and all graph, node, and edge attributes.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.clear()
     |      >>> list(G.nodes)
     |      []
     |      >>> list(G.edges)
     |      []
     |
     |  clear_edges(self)
     |      Remove all edges from the graph without altering nodes.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.clear_edges()
     |      >>> list(G.nodes)
     |      [0, 1, 2, 3]
     |      >>> list(G.edges)
     |      []
     |
     |  has_predecessor(self, u, v)
     |      Returns True if node u has predecessor v.
     |
     |      This is true if graph has the edge u<-v.
     |
     |  has_successor(self, u, v)
     |      Returns True if node u has successor v.
     |
     |      This is true if graph has the edge u->v.
     |
     |  neighbors = successors(self, n)
     |
     |  predecessors(self, n)
     |      Returns an iterator over predecessor nodes of n.
     |
     |      A predecessor of n is a node m such that there exists a directed
     |      edge from m to n.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Raises
     |      ------
     |      NetworkXError
     |         If n is not in the graph.
     |
     |      See Also
     |      --------
     |      successors
     |
     |  remove_node(self, n)
     |      Remove node n.
     |
     |      Removes the node n and all adjacent edges.
     |      Attempting to remove a nonexistent node will raise an exception.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Raises
     |      ------
     |      NetworkXError
     |         If n is not in the graph.
     |
     |      See Also
     |      --------
     |      remove_nodes_from
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> list(G.edges)
     |      [(0, 1), (1, 2)]
     |      >>> G.remove_node(1)
     |      >>> list(G.edges)
     |      []
     |
     |  remove_nodes_from(self, nodes)
     |      Remove multiple nodes.
     |
     |      Parameters
     |      ----------
     |      nodes : iterable container
     |          A container of nodes (list, dict, set, etc.).  If a node
     |          in the container is not in the graph it is silently ignored.
     |
     |      See Also
     |      --------
     |      remove_node
     |
     |      Notes
     |      -----
     |      When removing nodes from an iterator over the graph you are changing,
     |      a `RuntimeError` will be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
     |      object to `G.remove_nodes_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> e = list(G.nodes)
     |      >>> e
     |      [0, 1, 2]
     |      >>> G.remove_nodes_from(e)
     |      >>> list(G.nodes)
     |      []
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.DiGraph([(0, 1), (1, 2), (3, 4)])
     |      >>> # this command will fail, as the graph's dict is modified during iteration
     |      >>> # G.remove_nodes_from(n for n in G.nodes if n < 2)
     |      >>> # this command will work, since the dictionary underlying graph is not modified
     |      >>> G.remove_nodes_from(list(n for n in G.nodes if n < 2))
     |
     |  successors(self, n)
     |      Returns an iterator over successor nodes of n.
     |
     |      A successor of n is a node m such that there exists a directed
     |      edge from n to m.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Raises
     |      ------
     |      NetworkXError
     |         If n is not in the graph.
     |
     |      See Also
     |      --------
     |      predecessors
     |
     |      Notes
     |      -----
     |      neighbors() and successors() are the same.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from networkx.classes.graph.Graph:
     |
     |  __contains__(self, n)
     |      Returns True if n is a node, False otherwise. Use: 'n in G'.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> 1 in G
     |      True
     |
     |  __getitem__(self, n)
     |      Returns a dict of neighbors of node n.  Use: 'G[n]'.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph.
     |
     |      Returns
     |      -------
     |      adj_dict : dictionary
     |         The adjacency dictionary for nodes connected to n.
     |
     |      Notes
     |      -----
     |      G[n] is the same as G.adj[n] and similar to G.neighbors(n)
     |      (which is an iterator over G.adj[n])
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G[0]
     |      AtlasView({1: {}})
     |
     |  __iter__(self)
     |      Iterate over the nodes. Use: 'for n in G'.
     |
     |      Returns
     |      -------
     |      niter : iterator
     |          An iterator over all nodes in the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> [n for n in G]
     |      [0, 1, 2, 3]
     |      >>> list(G)
     |      [0, 1, 2, 3]
     |
     |  __len__(self)
     |      Returns the number of nodes in the graph. Use: 'len(G)'.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      number_of_nodes: identical method
     |      order: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> len(G)
     |      4
     |
     |  __str__(self)
     |      Returns a short summary of the graph.
     |
     |      Returns
     |      -------
     |      info : string
     |          Graph information including the graph name (if any), graph type, and the
     |          number of nodes and edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph(name="foo")
     |      >>> str(G)
     |      "Graph named 'foo' with 0 nodes and 0 edges"
     |
     |      >>> G = nx.path_graph(3)
     |      >>> str(G)
     |      'Graph with 3 nodes and 2 edges'
     |
     |  add_weighted_edges_from(self, ebunch_to_add, weight='weight', **attr)
     |      Add weighted edges in `ebunch_to_add` with specified weight attr
     |
     |      Parameters
     |      ----------
     |      ebunch_to_add : container of edges
     |          Each edge given in the list or container will be added
     |          to the graph. The edges must be given as 3-tuples (u, v, w)
     |          where w is a number.
     |      weight : string, optional (default= 'weight')
     |          The attribute name for the edge weights to be added.
     |      attr : keyword arguments, optional (default= no attributes)
     |          Edge attributes to add/update for all edges.
     |
     |      See Also
     |      --------
     |      add_edge : add a single edge
     |      add_edges_from : add multiple edges
     |
     |      Notes
     |      -----
     |      Adding the same edge twice for Graph/DiGraph simply updates
     |      the edge data. For MultiGraph/MultiDiGraph, duplicate edges
     |      are stored.
     |
     |      When adding edges from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_edges)`, and pass this
     |      object to `G.add_weighted_edges_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_weighted_edges_from([(0, 1, 3.0), (1, 2, 7.5)])
     |
     |      Evaluate an iterator over edges before passing it
     |
     |      >>> G = nx.Graph([(1, 2), (2, 3), (3, 4)])
     |      >>> weight = 0.1
     |      >>> # Grow graph by one new node, adding edges to all existing nodes.
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_weighted_edges_from(((5, n, weight) for n in G.nodes))
     |      >>> # correct way - note that there will be no self-edge for node 5
     |      >>> G.add_weighted_edges_from(list((5, n, weight) for n in G.nodes))
     |
     |  adjacency(self)
     |      Returns an iterator over (node, adjacency dict) tuples for all nodes.
     |
     |      For directed graphs, only outgoing neighbors/adjacencies are included.
     |
     |      Returns
     |      -------
     |      adj_iter : iterator
     |         An iterator over (node, adjacency dictionary) for all nodes in
     |         the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> [(n, nbrdict) for n, nbrdict in G.adjacency()]
     |      [(0, {1: {}}), (1, {0: {}, 2: {}}), (2, {1: {}, 3: {}}), (3, {2: {}})]
     |
     |  edge_subgraph(self, edges)
     |      Returns the subgraph induced by the specified edges.
     |
     |      The induced subgraph contains each edge in `edges` and each
     |      node incident to any one of those edges.
     |
     |      Parameters
     |      ----------
     |      edges : iterable
     |          An iterable of edges in this graph.
     |
     |      Returns
     |      -------
     |      G : Graph
     |          An edge-induced subgraph of this graph with the same edge
     |          attributes.
     |
     |      Notes
     |      -----
     |      The graph, edge, and node attributes in the returned subgraph
     |      view are references to the corresponding attributes in the original
     |      graph. The view is read-only.
     |
     |      To create a full graph version of the subgraph with its own copy
     |      of the edge or node attributes, use::
     |
     |          G.edge_subgraph(edges).copy()
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(5)
     |      >>> H = G.edge_subgraph([(0, 1), (3, 4)])
     |      >>> list(H.nodes)
     |      [0, 1, 3, 4]
     |      >>> list(H.edges)
     |      [(0, 1), (3, 4)]
     |
     |  has_node(self, n)
     |      Returns True if the graph contains the node n.
     |
     |      Identical to `n in G`
     |
     |      Parameters
     |      ----------
     |      n : node
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.has_node(0)
     |      True
     |
     |      It is more readable and simpler to use
     |
     |      >>> 0 in G
     |      True
     |
     |  nbunch_iter(self, nbunch=None)
     |      Returns an iterator over nodes contained in nbunch that are
     |      also in the graph.
     |
     |      The nodes in nbunch are checked for membership in the graph
     |      and if not are silently ignored.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      Returns
     |      -------
     |      niter : iterator
     |          An iterator over nodes in nbunch that are also in the graph.
     |          If nbunch is None, iterate over all nodes in the graph.
     |
     |      Raises
     |      ------
     |      NetworkXError
     |          If nbunch is not a node or sequence of nodes.
     |          If a node in nbunch is not hashable.
     |
     |      See Also
     |      --------
     |      Graph.__iter__
     |
     |      Notes
     |      -----
     |      When nbunch is an iterator, the returned iterator yields values
     |      directly from nbunch, becoming exhausted when nbunch is exhausted.
     |
     |      To test whether nbunch is a single node, one can use
     |      "if nbunch in self:", even after processing with this routine.
     |
     |      If nbunch is not a node or a (possibly empty) sequence/iterator
     |      or None, a :exc:`NetworkXError` is raised.  Also, if any object in
     |      nbunch is not hashable, a :exc:`NetworkXError` is raised.
     |
     |  nodes = <functools.cached_property object>
     |      A NodeView of the Graph as G.nodes or G.nodes().
     |
     |      Can be used as `G.nodes` for data lookup and for set-like operations.
     |      Can also be used as `G.nodes(data='color', default=None)` to return a
     |      NodeDataView which reports specific node data but no set operations.
     |      It presents a dict-like interface as well with `G.nodes.items()`
     |      iterating over `(node, nodedata)` 2-tuples and `G.nodes[3]['foo']`
     |      providing the value of the `foo` attribute for node `3`. In addition,
     |      a view `G.nodes.data('foo')` provides a dict-like interface to the
     |      `foo` attribute of each node. `G.nodes.data('foo', default=1)`
     |      provides a default for nodes that do not have attribute `foo`.
     |
     |      Parameters
     |      ----------
     |      data : string or bool, optional (default=False)
     |          The node attribute returned in 2-tuple (n, ddict[data]).
     |          If True, return entire node attribute dict as (n, ddict).
     |          If False, return just the nodes n.
     |
     |      default : value, optional (default=None)
     |          Value used for nodes that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      NodeView
     |          Allows set-like operations over the nodes as well as node
     |          attribute dict lookup and calling to get a NodeDataView.
     |          A NodeDataView iterates over `(n, data)` and has no set operations.
     |          A NodeView iterates over `n` and includes set operations.
     |
     |          When called, if data is False, an iterator over nodes.
     |          Otherwise an iterator of 2-tuples (node, attribute value)
     |          where the attribute is specified in `data`.
     |          If data is True then the attribute becomes the
     |          entire data dictionary.
     |
     |      Notes
     |      -----
     |      If your node data is not needed, it is simpler and equivalent
     |      to use the expression ``for n in G``, or ``list(G)``.
     |
     |      Examples
     |      --------
     |      There are two simple ways of getting a list of all nodes in the graph:
     |
     |      >>> G = nx.path_graph(3)
     |      >>> list(G.nodes)
     |      [0, 1, 2]
     |      >>> list(G)
     |      [0, 1, 2]
     |
     |      To get the node data along with the nodes:
     |
     |      >>> G.add_node(1, time="5pm")
     |      >>> G.nodes[0]["foo"] = "bar"
     |      >>> list(G.nodes(data=True))
     |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
     |      >>> list(G.nodes.data())
     |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
     |
     |      >>> list(G.nodes(data="foo"))
     |      [(0, 'bar'), (1, None), (2, None)]
     |      >>> list(G.nodes.data("foo"))
     |      [(0, 'bar'), (1, None), (2, None)]
     |
     |      >>> list(G.nodes(data="time"))
     |      [(0, None), (1, '5pm'), (2, None)]
     |      >>> list(G.nodes.data("time"))
     |      [(0, None), (1, '5pm'), (2, None)]
     |
     |      >>> list(G.nodes(data="time", default="Not Available"))
     |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
     |      >>> list(G.nodes.data("time", default="Not Available"))
     |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
     |
     |      If some of your nodes have an attribute and the rest are assumed
     |      to have a default attribute value you can create a dictionary
     |      from node/attribute pairs using the `default` keyword argument
     |      to guarantee the value is never None::
     |
     |          >>> G = nx.Graph()
     |          >>> G.add_node(0)
     |          >>> G.add_node(1, weight=2)
     |          >>> G.add_node(2, weight=3)
     |          >>> dict(G.nodes(data="weight", default=1))
     |          {0: 1, 1: 2, 2: 3}
     |
     |  number_of_nodes(self)
     |      Returns the number of nodes in the graph.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      order: identical method
     |      __len__: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.number_of_nodes()
     |      3
     |
     |  order(self)
     |      Returns the number of nodes in the graph.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      number_of_nodes: identical method
     |      __len__: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.order()
     |      3
     |
     |  size(self, weight=None)
     |      Returns the number of edges or total of all edge weights.
     |
     |      Parameters
     |      ----------
     |      weight : string or None, optional (default=None)
     |          The edge attribute that holds the numerical value used
     |          as a weight. If None, then each edge has weight 1.
     |
     |      Returns
     |      -------
     |      size : numeric
     |          The number of edges or
     |          (if weight keyword is provided) the total weight sum.
     |
     |          If weight is None, returns an int. Otherwise a float
     |          (or more general numeric if the weights are more general).
     |
     |      See Also
     |      --------
     |      number_of_edges
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.size()
     |      3
     |
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_edge("a", "b", weight=2)
     |      >>> G.add_edge("b", "c", weight=4)
     |      >>> G.size()
     |      2
     |      >>> G.size(weight="weight")
     |      6.0
     |
     |  subgraph(self, nodes)
     |      Returns a SubGraph view of the subgraph induced on `nodes`.
     |
     |      The induced subgraph of the graph contains the nodes in `nodes`
     |      and the edges between those nodes.
     |
     |      Parameters
     |      ----------
     |      nodes : list, iterable
     |          A container of nodes which will be iterated through once.
     |
     |      Returns
     |      -------
     |      G : SubGraph View
     |          A subgraph view of the graph. The graph structure cannot be
     |          changed but node/edge attributes can and are shared with the
     |          original graph.
     |
     |      Notes
     |      -----
     |      The graph, edge and node attributes are shared with the original graph.
     |      Changes to the graph structure is ruled out by the view, but changes
     |      to attributes are reflected in the original graph.
     |
     |      To create a subgraph with its own copy of the edge/node attributes use:
     |      G.subgraph(nodes).copy()
     |
     |      For an inplace reduction of a graph to a subgraph you can remove nodes:
     |      G.remove_nodes_from([n for n in G if n not in set(nodes)])
     |
     |      Subgraph views are sometimes NOT what you want. In most cases where
     |      you want to do more than simply look at the induced edges, it makes
     |      more sense to just create the subgraph as its own graph with code like:
     |
     |      ::
     |
     |          # Create a subgraph SG based on a (possibly multigraph) G
     |          SG = G.__class__()
     |          SG.add_nodes_from((n, G.nodes[n]) for n in largest_wcc)
     |          if SG.is_multigraph():
     |              SG.add_edges_from(
     |                  (n, nbr, key, d)
     |                  for n, nbrs in G.adj.items()
     |                  if n in largest_wcc
     |                  for nbr, keydict in nbrs.items()
     |                  if nbr in largest_wcc
     |                  for key, d in keydict.items()
     |              )
     |          else:
     |              SG.add_edges_from(
     |                  (n, nbr, d)
     |                  for n, nbrs in G.adj.items()
     |                  if n in largest_wcc
     |                  for nbr, d in nbrs.items()
     |                  if nbr in largest_wcc
     |              )
     |          SG.graph.update(G.graph)
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> H = G.subgraph([0, 1, 2])
     |      >>> list(H.edges)
     |      [(0, 1), (1, 2)]
     |
     |  update(self, edges=None, nodes=None)
     |      Update the graph using nodes/edges/graphs as input.
     |
     |      Like dict.update, this method takes a graph as input, adding the
     |      graph's nodes and edges to this graph. It can also take two inputs:
     |      edges and nodes. Finally it can take either edges or nodes.
     |      To specify only nodes the keyword `nodes` must be used.
     |
     |      The collections of edges and nodes are treated similarly to
     |      the add_edges_from/add_nodes_from methods. When iterated, they
     |      should yield 2-tuples (u, v) or 3-tuples (u, v, datadict).
     |
     |      Parameters
     |      ----------
     |      edges : Graph object, collection of edges, or None
     |          The first parameter can be a graph or some edges. If it has
     |          attributes `nodes` and `edges`, then it is taken to be a
     |          Graph-like object and those attributes are used as collections
     |          of nodes and edges to be added to the graph.
     |          If the first parameter does not have those attributes, it is
     |          treated as a collection of edges and added to the graph.
     |          If the first argument is None, no edges are added.
     |      nodes : collection of nodes, or None
     |          The second parameter is treated as a collection of nodes
     |          to be added to the graph unless it is None.
     |          If `edges is None` and `nodes is None` an exception is raised.
     |          If the first parameter is a Graph, then `nodes` is ignored.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(5)
     |      >>> G.update(nx.complete_graph(range(4, 10)))
     |      >>> from itertools import combinations
     |      >>> edges = (
     |      ...     (u, v, {"power": u * v})
     |      ...     for u, v in combinations(range(10, 20), 2)
     |      ...     if u * v < 225
     |      ... )
     |      >>> nodes = [1000]  # for singleton, use a container
     |      >>> G.update(edges, nodes)
     |
     |      Notes
     |      -----
     |      It you want to update the graph using an adjacency structure
     |      it is straightforward to obtain the edges/nodes from adjacency.
     |      The following examples provide common cases, your adjacency may
     |      be slightly different and require tweaks of these examples::
     |
     |      >>> # dict-of-set/list/tuple
     |      >>> adj = {1: {2, 3}, 2: {1, 3}, 3: {1, 2}}
     |      >>> e = [(u, v) for u, nbrs in adj.items() for v in nbrs]
     |      >>> G.update(edges=e, nodes=adj)
     |
     |      >>> DG = nx.DiGraph()
     |      >>> # dict-of-dict-of-attribute
     |      >>> adj = {1: {2: 1.3, 3: 0.7}, 2: {1: 1.4}, 3: {1: 0.7}}
     |      >>> e = [
     |      ...     (u, v, {"weight": d})
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, d in nbrs.items()
     |      ... ]
     |      >>> DG.update(edges=e, nodes=adj)
     |
     |      >>> # dict-of-dict-of-dict
     |      >>> adj = {1: {2: {"weight": 1.3}, 3: {"color": 0.7, "weight": 1.2}}}
     |      >>> e = [
     |      ...     (u, v, {"weight": d})
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, d in nbrs.items()
     |      ... ]
     |      >>> DG.update(edges=e, nodes=adj)
     |
     |      >>> # predecessor adjacency (dict-of-set)
     |      >>> pred = {1: {2, 3}, 2: {3}, 3: {3}}
     |      >>> e = [(v, u) for u, nbrs in pred.items() for v in nbrs]
     |
     |      >>> # MultiGraph dict-of-dict-of-dict-of-attribute
     |      >>> MDG = nx.MultiDiGraph()
     |      >>> adj = {
     |      ...     1: {2: {0: {"weight": 1.3}, 1: {"weight": 1.2}}},
     |      ...     3: {2: {0: {"weight": 0.7}}},
     |      ... }
     |      >>> e = [
     |      ...     (u, v, ekey, d)
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, keydict in nbrs.items()
     |      ...     for ekey, d in keydict.items()
     |      ... ]
     |      >>> MDG.update(edges=e)
     |
     |      See Also
     |      --------
     |      add_edges_from: add multiple edges to a graph
     |      add_nodes_from: add multiple nodes to a graph
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from networkx.classes.graph.Graph:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  name
     |      String identifier of the graph.
     |
     |      This graph attribute appears in the attribute dict G.graph
     |      keyed by the string `"name"`. as well as an attribute (technically
     |      a property) `G.name`. This is entirely user controlled.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from networkx.classes.graph.Graph:
     |
     |  __networkx_backend__ = 'networkx'
     |
     |  adjlist_inner_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  adjlist_outer_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  edge_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  graph_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  node_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  node_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)

DATA
    __all__ = ['MultiDiGraph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\classes\multidigraph.py

networkx.multigraph
Python Library Documentation: module networkx.classes.multigraph in networkx.classes

NAME
    networkx.classes.multigraph - Base class for MultiGraph.

CLASSES
    networkx.classes.graph.Graph(builtins.object)
        MultiGraph

    class MultiGraph(networkx.classes.graph.Graph)
     |  MultiGraph(incoming_graph_data=None, multigraph_input=None, **attr)
     |
     |  An undirected graph class that can store multiedges.
     |
     |  Multiedges are multiple edges between two nodes.  Each edge
     |  can hold optional data or attributes.
     |
     |  A MultiGraph holds undirected edges.  Self loops are allowed.
     |
     |  Nodes can be arbitrary (hashable) Python objects with optional
     |  key/value attributes. By convention `None` is not used as a node.
     |
     |  Edges are represented as links between nodes with optional
     |  key/value attributes, in a MultiGraph each edge has a key to
     |  distinguish between multiple edges that have the same source and
     |  destination nodes.
     |
     |  Parameters
     |  ----------
     |  incoming_graph_data : input graph (optional, default: None)
     |      Data to initialize graph. If None (default) an empty
     |      graph is created.  The data can be any format that is supported
     |      by the to_networkx_graph() function, currently including edge list,
     |      dict of dicts, dict of lists, NetworkX graph, 2D NumPy array,
     |      SciPy sparse array, or PyGraphviz graph.
     |
     |  multigraph_input : bool or None (default None)
     |      Note: Only used when `incoming_graph_data` is a dict.
     |      If True, `incoming_graph_data` is assumed to be a
     |      dict-of-dict-of-dict-of-dict structure keyed by
     |      node to neighbor to edge keys to edge data for multi-edges.
     |      A NetworkXError is raised if this is not the case.
     |      If False, :func:`to_networkx_graph` is used to try to determine
     |      the dict's graph data structure as either a dict-of-dict-of-dict
     |      keyed by node to neighbor to edge data, or a dict-of-iterable
     |      keyed by node to neighbors.
     |      If None, the treatment for True is tried, but if it fails,
     |      the treatment for False is tried.
     |
     |  attr : keyword arguments, optional (default= no attributes)
     |      Attributes to add to graph as key=value pairs.
     |
     |  See Also
     |  --------
     |  Graph
     |  DiGraph
     |  MultiDiGraph
     |
     |  Examples
     |  --------
     |  Create an empty graph structure (a "null graph") with no nodes and
     |  no edges.
     |
     |  >>> G = nx.MultiGraph()
     |
     |  G can be grown in several ways.
     |
     |  **Nodes:**
     |
     |  Add one node at a time:
     |
     |  >>> G.add_node(1)
     |
     |  Add the nodes from any container (a list, dict, set or
     |  even the lines from a file or the nodes from another graph).
     |
     |  >>> G.add_nodes_from([2, 3])
     |  >>> G.add_nodes_from(range(100, 110))
     |  >>> H = nx.path_graph(10)
     |  >>> G.add_nodes_from(H)
     |
     |  In addition to strings and integers any hashable Python object
     |  (except None) can represent a node, e.g. a customized node object,
     |  or even another Graph.
     |
     |  >>> G.add_node(H)
     |
     |  **Edges:**
     |
     |  G can also be grown by adding edges.
     |
     |  Add one edge,
     |
     |  >>> key = G.add_edge(1, 2)
     |
     |  a list of edges,
     |
     |  >>> keys = G.add_edges_from([(1, 2), (1, 3)])
     |
     |  or a collection of edges,
     |
     |  >>> keys = G.add_edges_from(H.edges)
     |
     |  If some edges connect nodes not yet in the graph, the nodes
     |  are added automatically.  If an edge already exists, an additional
     |  edge is created and stored using a key to identify the edge.
     |  By default the key is the lowest unused integer.
     |
     |  >>> keys = G.add_edges_from([(4, 5, {"route": 28}), (4, 5, {"route": 37})])
     |  >>> G[4]
     |  AdjacencyView({3: {0: {}}, 5: {0: {}, 1: {'route': 28}, 2: {'route': 37}}})
     |
     |  **Attributes:**
     |
     |  Each graph, node, and edge can hold key/value attribute pairs
     |  in an associated attribute dictionary (the keys must be hashable).
     |  By default these are empty, but can be added or changed using
     |  add_edge, add_node or direct manipulation of the attribute
     |  dictionaries named graph, node and edge respectively.
     |
     |  >>> G = nx.MultiGraph(day="Friday")
     |  >>> G.graph
     |  {'day': 'Friday'}
     |
     |  Add node attributes using add_node(), add_nodes_from() or G.nodes
     |
     |  >>> G.add_node(1, time="5pm")
     |  >>> G.add_nodes_from([3], time="2pm")
     |  >>> G.nodes[1]
     |  {'time': '5pm'}
     |  >>> G.nodes[1]["room"] = 714
     |  >>> del G.nodes[1]["room"]  # remove attribute
     |  >>> list(G.nodes(data=True))
     |  [(1, {'time': '5pm'}), (3, {'time': '2pm'})]
     |
     |  Add edge attributes using add_edge(), add_edges_from(), subscript
     |  notation, or G.edges.
     |
     |  >>> key = G.add_edge(1, 2, weight=4.7)
     |  >>> keys = G.add_edges_from([(3, 4), (4, 5)], color="red")
     |  >>> keys = G.add_edges_from([(1, 2, {"color": "blue"}), (2, 3, {"weight": 8})])
     |  >>> G[1][2][0]["weight"] = 4.7
     |  >>> G.edges[1, 2, 0]["weight"] = 4
     |
     |  Warning: we protect the graph data structure by making `G.edges[1,
     |  2, 0]` a read-only dict-like structure. However, you can assign to
     |  attributes in e.g. `G.edges[1, 2, 0]`. Thus, use 2 sets of brackets
     |  to add/change data attributes: `G.edges[1, 2, 0]['weight'] = 4`.
     |
     |  **Shortcuts:**
     |
     |  Many common graph features allow python syntax to speed reporting.
     |
     |  >>> 1 in G  # check if node in graph
     |  True
     |  >>> [n for n in G if n < 3]  # iterate through nodes
     |  [1, 2]
     |  >>> len(G)  # number of nodes in graph
     |  5
     |  >>> G[1]  # adjacency dict-like view mapping neighbor -> edge key -> edge attributes
     |  AdjacencyView({2: {0: {'weight': 4}, 1: {'color': 'blue'}}})
     |
     |  Often the best way to traverse all edges of a graph is via the neighbors.
     |  The neighbors are reported as an adjacency-dict `G.adj` or `G.adjacency()`.
     |
     |  >>> for n, nbrsdict in G.adjacency():
     |  ...     for nbr, keydict in nbrsdict.items():
     |  ...         for key, eattr in keydict.items():
     |  ...             if "weight" in eattr:
     |  ...                 # Do something useful with the edges
     |  ...                 pass
     |
     |  But the edges() method is often more convenient:
     |
     |  >>> for u, v, keys, weight in G.edges(data="weight", keys=True):
     |  ...     if weight is not None:
     |  ...         # Do something useful with the edges
     |  ...         pass
     |
     |  **Reporting:**
     |
     |  Simple graph information is obtained using methods and object-attributes.
     |  Reporting usually provides views instead of containers to reduce memory
     |  usage. The views update as the graph is updated similarly to dict-views.
     |  The objects `nodes`, `edges` and `adj` provide access to data attributes
     |  via lookup (e.g. `nodes[n]`, `edges[u, v, k]`, `adj[u][v]`) and iteration
     |  (e.g. `nodes.items()`, `nodes.data('color')`,
     |  `nodes.data('color', default='blue')` and similarly for `edges`)
     |  Views exist for `nodes`, `edges`, `neighbors()`/`adj` and `degree`.
     |
     |  For details on these and other miscellaneous methods, see below.
     |
     |  **Subclasses (Advanced):**
     |
     |  The MultiGraph class uses a dict-of-dict-of-dict-of-dict data structure.
     |  The outer dict (node_dict) holds adjacency information keyed by node.
     |  The next dict (adjlist_dict) represents the adjacency information
     |  and holds edge_key dicts keyed by neighbor. The edge_key dict holds
     |  each edge_attr dict keyed by edge key. The inner dict
     |  (edge_attr_dict) represents the edge data and holds edge attribute
     |  values keyed by attribute names.
     |
     |  Each of these four dicts in the dict-of-dict-of-dict-of-dict
     |  structure can be replaced by a user defined dict-like object.
     |  In general, the dict-like features should be maintained but
     |  extra features can be added. To replace one of the dicts create
     |  a new graph class by changing the class(!) variable holding the
     |  factory for that dict-like structure. The variable names are
     |  node_dict_factory, node_attr_dict_factory, adjlist_inner_dict_factory,
     |  adjlist_outer_dict_factory, edge_key_dict_factory, edge_attr_dict_factory
     |  and graph_attr_dict_factory.
     |
     |  node_dict_factory : function, (default: dict)
     |      Factory function to be used to create the dict containing node
     |      attributes, keyed by node id.
     |      It should require no arguments and return a dict-like object
     |
     |  node_attr_dict_factory: function, (default: dict)
     |      Factory function to be used to create the node attribute
     |      dict which holds attribute values keyed by attribute name.
     |      It should require no arguments and return a dict-like object
     |
     |  adjlist_outer_dict_factory : function, (default: dict)
     |      Factory function to be used to create the outer-most dict
     |      in the data structure that holds adjacency info keyed by node.
     |      It should require no arguments and return a dict-like object.
     |
     |  adjlist_inner_dict_factory : function, (default: dict)
     |      Factory function to be used to create the adjacency list
     |      dict which holds multiedge key dicts keyed by neighbor.
     |      It should require no arguments and return a dict-like object.
     |
     |  edge_key_dict_factory : function, (default: dict)
     |      Factory function to be used to create the edge key dict
     |      which holds edge data keyed by edge key.
     |      It should require no arguments and return a dict-like object.
     |
     |  edge_attr_dict_factory : function, (default: dict)
     |      Factory function to be used to create the edge attribute
     |      dict which holds attribute values keyed by attribute name.
     |      It should require no arguments and return a dict-like object.
     |
     |  graph_attr_dict_factory : function, (default: dict)
     |      Factory function to be used to create the graph attribute
     |      dict which holds attribute values keyed by attribute name.
     |      It should require no arguments and return a dict-like object.
     |
     |  Typically, if your extension doesn't impact the data structure all
     |  methods will inherited without issue except: `to_directed/to_undirected`.
     |  By default these methods create a DiGraph/Graph class and you probably
     |  want them to create your extension of a DiGraph/Graph. To facilitate
     |  this we define two class variables that you can set in your subclass.
     |
     |  to_directed_class : callable, (default: DiGraph or MultiDiGraph)
     |      Class to create a new graph structure in the `to_directed` method.
     |      If `None`, a NetworkX class (DiGraph or MultiDiGraph) is used.
     |
     |  to_undirected_class : callable, (default: Graph or MultiGraph)
     |      Class to create a new graph structure in the `to_undirected` method.
     |      If `None`, a NetworkX class (Graph or MultiGraph) is used.
     |
     |  **Subclassing Example**
     |
     |  Create a low memory graph class that effectively disallows edge
     |  attributes by using a single attribute dict for all edges.
     |  This reduces the memory used, but you lose edge attributes.
     |
     |  >>> class ThinGraph(nx.Graph):
     |  ...     all_edge_dict = {"weight": 1}
     |  ...
     |  ...     def single_edge_dict(self):
     |  ...         return self.all_edge_dict
     |  ...
     |  ...     edge_attr_dict_factory = single_edge_dict
     |  >>> G = ThinGraph()
     |  >>> G.add_edge(2, 1)
     |  >>> G[2][1]
     |  {'weight': 1}
     |  >>> G.add_edge(2, 2)
     |  >>> G[2][1] is G[2][2]
     |  True
     |
     |  Method resolution order:
     |      MultiGraph
     |      networkx.classes.graph.Graph
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __init__(self, incoming_graph_data=None, multigraph_input=None, **attr)
     |      Initialize a graph with edges, name, or graph attributes.
     |
     |      Parameters
     |      ----------
     |      incoming_graph_data : input graph
     |          Data to initialize graph.  If incoming_graph_data=None (default)
     |          an empty graph is created.  The data can be an edge list, or any
     |          NetworkX graph object.  If the corresponding optional Python
     |          packages are installed the data can also be a 2D NumPy array, a
     |          SciPy sparse array, or a PyGraphviz graph.
     |
     |      multigraph_input : bool or None (default None)
     |          Note: Only used when `incoming_graph_data` is a dict.
     |          If True, `incoming_graph_data` is assumed to be a
     |          dict-of-dict-of-dict-of-dict structure keyed by
     |          node to neighbor to edge keys to edge data for multi-edges.
     |          A NetworkXError is raised if this is not the case.
     |          If False, :func:`to_networkx_graph` is used to try to determine
     |          the dict's graph data structure as either a dict-of-dict-of-dict
     |          keyed by node to neighbor to edge data, or a dict-of-iterable
     |          keyed by node to neighbors.
     |          If None, the treatment for True is tried, but if it fails,
     |          the treatment for False is tried.
     |
     |      attr : keyword arguments, optional (default= no attributes)
     |          Attributes to add to graph as key=value pairs.
     |
     |      See Also
     |      --------
     |      convert
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiGraph()
     |      >>> G = nx.MultiGraph(name="my graph")
     |      >>> e = [(1, 2), (1, 2), (2, 3), (3, 4)]  # list of edges
     |      >>> G = nx.MultiGraph(e)
     |
     |      Arbitrary graph attribute pairs (key=value) may be assigned
     |
     |      >>> G = nx.MultiGraph(e, day="Friday")
     |      >>> G.graph
     |      {'day': 'Friday'}
     |
     |  add_edge(self, u_for_edge, v_for_edge, key=None, **attr)
     |      Add an edge between u and v.
     |
     |      The nodes u and v will be automatically added if they are
     |      not already in the graph.
     |
     |      Edge attributes can be specified with keywords or by directly
     |      accessing the edge's attribute dictionary. See examples below.
     |
     |      Parameters
     |      ----------
     |      u_for_edge, v_for_edge : nodes
     |          Nodes can be, for example, strings or numbers.
     |          Nodes must be hashable (and not None) Python objects.
     |      key : hashable identifier, optional (default=lowest unused integer)
     |          Used to distinguish multiedges between a pair of nodes.
     |      attr : keyword arguments, optional
     |          Edge data (or labels or objects) can be assigned using
     |          keyword arguments.
     |
     |      Returns
     |      -------
     |      The edge key assigned to the edge.
     |
     |      See Also
     |      --------
     |      add_edges_from : add a collection of edges
     |
     |      Notes
     |      -----
     |      To replace/update edge data, use the optional key argument
     |      to identify a unique edge.  Otherwise a new edge will be created.
     |
     |      NetworkX algorithms designed for weighted graphs cannot use
     |      multigraphs directly because it is not clear how to handle
     |      multiedge weights.  Convert to Graph using edge attribute
     |      'weight' to enable weighted graph algorithms.
     |
     |      Default keys are generated using the method `new_edge_key()`.
     |      This method can be overridden by subclassing the base class and
     |      providing a custom `new_edge_key()` method.
     |
     |      Examples
     |      --------
     |      The following each add an additional edge e=(1, 2) to graph G:
     |
     |      >>> G = nx.MultiGraph()
     |      >>> e = (1, 2)
     |      >>> ekey = G.add_edge(1, 2)  # explicit two-node form
     |      >>> G.add_edge(*e)  # single edge as tuple of two nodes
     |      1
     |      >>> G.add_edges_from([(1, 2)])  # add edges from iterable container
     |      [2]
     |
     |      Associate data to edges using keywords:
     |
     |      >>> ekey = G.add_edge(1, 2, weight=3)
     |      >>> ekey = G.add_edge(1, 2, key=0, weight=4)  # update data for key=0
     |      >>> ekey = G.add_edge(1, 3, weight=7, capacity=15, length=342.7)
     |
     |      For non-string attribute keys, use subscript notation.
     |
     |      >>> ekey = G.add_edge(1, 2)
     |      >>> G[1][2][0].update({0: 5})
     |      >>> G.edges[1, 2, 0].update({0: 5})
     |
     |  add_edges_from(self, ebunch_to_add, **attr)
     |      Add all the edges in ebunch_to_add.
     |
     |      Parameters
     |      ----------
     |      ebunch_to_add : container of edges
     |          Each edge given in the container will be added to the
     |          graph. The edges can be:
     |
     |              - 2-tuples (u, v) or
     |              - 3-tuples (u, v, d) for an edge data dict d, or
     |              - 3-tuples (u, v, k) for not iterable key k, or
     |              - 4-tuples (u, v, k, d) for an edge with data and key k
     |
     |      attr : keyword arguments, optional
     |          Edge data (or labels or objects) can be assigned using
     |          keyword arguments.
     |
     |      Returns
     |      -------
     |      A list of edge keys assigned to the edges in `ebunch`.
     |
     |      See Also
     |      --------
     |      add_edge : add a single edge
     |      add_weighted_edges_from : convenient way to add weighted edges
     |
     |      Notes
     |      -----
     |      Adding the same edge twice has no effect but any edge data
     |      will be updated when each duplicate edge is added.
     |
     |      Edge attributes specified in an ebunch take precedence over
     |      attributes specified via keyword arguments.
     |
     |      Default keys are generated using the method ``new_edge_key()``.
     |      This method can be overridden by subclassing the base class and
     |      providing a custom ``new_edge_key()`` method.
     |
     |      When adding edges from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_edges)`, and pass this
     |      object to `G.add_edges_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_edges_from([(0, 1), (1, 2)])  # using a list of edge tuples
     |      >>> e = zip(range(0, 3), range(1, 4))
     |      >>> G.add_edges_from(e)  # Add the path graph 0-1-2-3
     |
     |      Associate data to edges
     |
     |      >>> G.add_edges_from([(1, 2), (2, 3)], weight=3)
     |      >>> G.add_edges_from([(3, 4), (1, 4)], label="WN2898")
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.MultiGraph([(1, 2), (2, 3), (3, 4)])
     |      >>> # Grow graph by one new node, adding edges to all existing nodes.
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_edges_from(((5, n) for n in G.nodes))
     |      >>> # right way - note that there will be no self-edge for node 5
     |      >>> assigned_keys = G.add_edges_from(list((5, n) for n in G.nodes))
     |
     |  adj = <functools.cached_property object>
     |      Graph adjacency object holding the neighbors of each node.
     |
     |      This object is a read-only dict-like structure with node keys
     |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
     |      to the edgekey-data-dict.  So `G.adj[3][2][0]['color'] = 'blue'` sets
     |      the color of the edge `(3, 2, 0)` to `"blue"`.
     |
     |      Iterating over G.adj behaves like a dict. Useful idioms include
     |      `for nbr, edgesdict in G.adj[n].items():`.
     |
     |      The neighbor information is also provided by subscripting the graph.
     |
     |      Examples
     |      --------
     |      >>> e = [(1, 2), (1, 2), (1, 3), (3, 4)]  # list of edges
     |      >>> G = nx.MultiGraph(e)
     |      >>> G.edges[1, 2, 0]["weight"] = 3
     |      >>> result = set()
     |      >>> for edgekey, data in G[1][2].items():
     |      ...     result.add(data.get("weight", 1))
     |      >>> result
     |      {1, 3}
     |
     |      For directed graphs, `G.adj` holds outgoing (successor) info.
     |
     |  copy(self, as_view=False)
     |      Returns a copy of the graph.
     |
     |      The copy method by default returns an independent shallow copy
     |      of the graph and attributes. That is, if an attribute is a
     |      container, that container is shared by the original an the copy.
     |      Use Python's `copy.deepcopy` for new containers.
     |
     |      If `as_view` is True then a view is returned instead of a copy.
     |
     |      Notes
     |      -----
     |      All copies reproduce the graph structure, but data attributes
     |      may be handled in different ways. There are four types of copies
     |      of a graph that people might want.
     |
     |      Deepcopy -- A "deepcopy" copies the graph structure as well as
     |      all data attributes and any objects they might contain.
     |      The entire graph object is new so that changes in the copy
     |      do not affect the original object. (see Python's copy.deepcopy)
     |
     |      Data Reference (Shallow) -- For a shallow copy the graph structure
     |      is copied but the edge, node and graph attribute dicts are
     |      references to those in the original graph. This saves
     |      time and memory but could cause confusion if you change an attribute
     |      in one graph and it changes the attribute in the other.
     |      NetworkX does not provide this level of shallow copy.
     |
     |      Independent Shallow -- This copy creates new independent attribute
     |      dicts and then does a shallow copy of the attributes. That is, any
     |      attributes that are containers are shared between the new graph
     |      and the original. This is exactly what `dict.copy()` provides.
     |      You can obtain this style copy using:
     |
     |          >>> G = nx.path_graph(5)
     |          >>> H = G.copy()
     |          >>> H = G.copy(as_view=False)
     |          >>> H = nx.Graph(G)
     |          >>> H = G.__class__(G)
     |
     |      Fresh Data -- For fresh data, the graph structure is copied while
     |      new empty data attribute dicts are created. The resulting graph
     |      is independent of the original and it has no edge, node or graph
     |      attributes. Fresh copies are not enabled. Instead use:
     |
     |          >>> H = G.__class__()
     |          >>> H.add_nodes_from(G)
     |          >>> H.add_edges_from(G.edges)
     |
     |      View -- Inspired by dict-views, graph-views act like read-only
     |      versions of the original graph, providing a copy of the original
     |      structure without requiring any memory for copying the information.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Parameters
     |      ----------
     |      as_view : bool, optional (default=False)
     |          If True, the returned graph-view provides a read-only view
     |          of the original graph without actually copying any data.
     |
     |      Returns
     |      -------
     |      G : Graph
     |          A copy of the graph.
     |
     |      See Also
     |      --------
     |      to_directed: return a directed copy of the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> H = G.copy()
     |
     |  degree = <functools.cached_property object>
     |      A DegreeView for the Graph as G.degree or G.degree().
     |
     |      The node degree is the number of edges adjacent to the node.
     |      The weighted node degree is the sum of the edge weights for
     |      edges incident to that node.
     |
     |      This object provides an iterator for (node, degree) as well as
     |      lookup for the degree for a single node.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      weight : string or None, optional (default=None)
     |         The name of an edge attribute that holds the numerical value used
     |         as a weight.  If None, then each edge has weight 1.
     |         The degree is the sum of the edge weights adjacent to the node.
     |
     |      Returns
     |      -------
     |      MultiDegreeView or int
     |          If multiple nodes are requested (the default), returns a `MultiDegreeView`
     |          mapping nodes to their degree.
     |          If a single node is requested, returns the degree of the node as an integer.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.degree(0)  # node 0 with degree 1
     |      1
     |      >>> list(G.degree([0, 1]))
     |      [(0, 1), (1, 2)]
     |
     |  edges = <functools.cached_property object>
     |      Returns an iterator over the edges.
     |
     |      edges(self, nbunch=None, data=False, keys=False, default=None)
     |
     |      The MultiEdgeView provides set-like operations on the edge-tuples
     |      as well as edge attribute lookup. When called, it also provides
     |      an EdgeDataView object which allows control of access to edge
     |      attributes (but does not provide set-like operations).
     |      Hence, ``G.edges[u, v, k]['color']`` provides the value of the color
     |      attribute for the edge from ``u`` to ``v`` with key ``k`` while
     |      ``for (u, v, k, c) in G.edges(data='color', keys=True, default="red"):``
     |      iterates through all the edges yielding the color attribute with
     |      default `'red'` if no color attribute exists.
     |
     |      Edges are returned as tuples with optional data and keys
     |      in the order (node, neighbor, key, data). If ``keys=True`` is not
     |      provided, the tuples will just be (node, neighbor, data), but
     |      multiple tuples with the same node and neighbor will be generated
     |      when multiple edges exist between two nodes.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges from these nodes.
     |      data : string or bool, optional (default=False)
     |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
     |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
     |          If False, return 2-tuple (u, v).
     |      keys : bool, optional (default=False)
     |          If True, return edge keys with each edge, creating (u, v, k)
     |          tuples or (u, v, k, d) tuples if data is also requested.
     |      default : value, optional (default=None)
     |          Value used for edges that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      edges : MultiEdgeView
     |          A view of edge attributes, usually it iterates over (u, v)
     |          (u, v, k) or (u, v, k, d) tuples of edges, but can also be
     |          used for attribute lookup as ``edges[u, v, k]['foo']``.
     |
     |      Notes
     |      -----
     |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
     |      For directed graphs this returns the out-edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiGraph()
     |      >>> nx.add_path(G, [0, 1, 2])
     |      >>> key = G.add_edge(2, 3, weight=5)
     |      >>> key2 = G.add_edge(2, 1, weight=2)  # multi-edge
     |      >>> [e for e in G.edges()]
     |      [(0, 1), (1, 2), (1, 2), (2, 3)]
     |      >>> G.edges.data()  # default data is {} (empty dict)
     |      MultiEdgeDataView([(0, 1, {}), (1, 2, {}), (1, 2, {'weight': 2}), (2, 3, {'weight': 5})])
     |      >>> G.edges.data("weight", default=1)
     |      MultiEdgeDataView([(0, 1, 1), (1, 2, 1), (1, 2, 2), (2, 3, 5)])
     |      >>> G.edges(keys=True)  # default keys are integers
     |      MultiEdgeView([(0, 1, 0), (1, 2, 0), (1, 2, 1), (2, 3, 0)])
     |      >>> G.edges.data(keys=True)
     |      MultiEdgeDataView([(0, 1, 0, {}), (1, 2, 0, {}), (1, 2, 1, {'weight': 2}), (2, 3, 0, {'weight': 5})])
     |      >>> G.edges.data("weight", default=1, keys=True)
     |      MultiEdgeDataView([(0, 1, 0, 1), (1, 2, 0, 1), (1, 2, 1, 2), (2, 3, 0, 5)])
     |      >>> G.edges([0, 3])  # Note ordering of tuples from listed sources
     |      MultiEdgeDataView([(0, 1), (3, 2)])
     |      >>> G.edges([0, 3, 2, 1])  # Note ordering of tuples
     |      MultiEdgeDataView([(0, 1), (3, 2), (2, 1), (2, 1)])
     |      >>> G.edges(0)
     |      MultiEdgeDataView([(0, 1)])
     |
     |  get_edge_data(self, u, v, key=None, default=None)
     |      Returns the attribute dictionary associated with edge (u, v,
     |      key).
     |
     |      If a key is not provided, returns a dictionary mapping edge keys
     |      to attribute dictionaries for each edge between u and v.
     |
     |      This is identical to `G[u][v][key]` except the default is returned
     |      instead of an exception is the edge doesn't exist.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |
     |      default :  any Python object (default=None)
     |          Value to return if the specific edge (u, v, key) is not
     |          found, OR if there are no edges between u and v and no key
     |          is specified.
     |
     |      key : hashable identifier, optional (default=None)
     |          Return data only for the edge with specified key, as an
     |          attribute dictionary (rather than a dictionary mapping keys
     |          to attribute dictionaries).
     |
     |      Returns
     |      -------
     |      edge_dict : dictionary
     |          The edge attribute dictionary, OR a dictionary mapping edge
     |          keys to attribute dictionaries for each of those edges if no
     |          specific key is provided (even if there's only one edge
     |          between u and v).
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiGraph()  # or MultiDiGraph
     |      >>> key = G.add_edge(0, 1, key="a", weight=7)
     |      >>> G[0][1]["a"]  # key='a'
     |      {'weight': 7}
     |      >>> G.edges[0, 1, "a"]  # key='a'
     |      {'weight': 7}
     |
     |      Warning: we protect the graph data structure by making
     |      `G.edges` and `G[1][2]` read-only dict-like structures.
     |      However, you can assign values to attributes in e.g.
     |      `G.edges[1, 2, 'a']` or `G[1][2]['a']` using an additional
     |      bracket as shown next. You need to specify all edge info
     |      to assign to the edge data associated with an edge.
     |
     |      >>> G[0][1]["a"]["weight"] = 10
     |      >>> G.edges[0, 1, "a"]["weight"] = 10
     |      >>> G[0][1]["a"]["weight"]
     |      10
     |      >>> G.edges[1, 0, "a"]["weight"]
     |      10
     |
     |      >>> G = nx.MultiGraph()  # or MultiDiGraph
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.edges[0, 1, 0]["weight"] = 5
     |      >>> G.get_edge_data(0, 1)
     |      {0: {'weight': 5}}
     |      >>> e = (0, 1)
     |      >>> G.get_edge_data(*e)  # tuple form
     |      {0: {'weight': 5}}
     |      >>> G.get_edge_data(3, 0)  # edge not in graph, returns None
     |      >>> G.get_edge_data(3, 0, default=0)  # edge not in graph, return default
     |      0
     |      >>> G.get_edge_data(1, 0, 0)  # specific key gives back
     |      {'weight': 5}
     |
     |  has_edge(self, u, v, key=None)
     |      Returns True if the graph has an edge between nodes u and v.
     |
     |      This is the same as `v in G[u] or key in G[u][v]`
     |      without KeyError exceptions.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |          Nodes can be, for example, strings or numbers.
     |
     |      key : hashable identifier, optional (default=None)
     |          If specified return True only if the edge with
     |          key is found.
     |
     |      Returns
     |      -------
     |      edge_ind : bool
     |          True if edge is in the graph, False otherwise.
     |
     |      Examples
     |      --------
     |      Can be called either using two nodes u, v, an edge tuple (u, v),
     |      or an edge tuple (u, v, key).
     |
     |      >>> G = nx.MultiGraph()  # or MultiDiGraph
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.has_edge(0, 1)  # using two nodes
     |      True
     |      >>> e = (0, 1)
     |      >>> G.has_edge(*e)  #  e is a 2-tuple (u, v)
     |      True
     |      >>> G.add_edge(0, 1, key="a")
     |      'a'
     |      >>> G.has_edge(0, 1, key="a")  # specify key
     |      True
     |      >>> G.has_edge(1, 0, key="a")  # edges aren't directed
     |      True
     |      >>> e = (0, 1, "a")
     |      >>> G.has_edge(*e)  # e is a 3-tuple (u, v, 'a')
     |      True
     |
     |      The following syntax are equivalent:
     |
     |      >>> G.has_edge(0, 1)
     |      True
     |      >>> 1 in G[0]  # though this gives :exc:`KeyError` if 0 not in G
     |      True
     |      >>> 0 in G[1]  # other order; also gives :exc:`KeyError` if 0 not in G
     |      True
     |
     |  is_directed(self)
     |      Returns True if graph is directed, False otherwise.
     |
     |  is_multigraph(self)
     |      Returns True if graph is a multigraph, False otherwise.
     |
     |  new_edge_key(self, u, v)
     |      Returns an unused key for edges between nodes `u` and `v`.
     |
     |      The nodes `u` and `v` do not need to be already in the graph.
     |
     |      Notes
     |      -----
     |      In the standard MultiGraph class the new key is the number of existing
     |      edges between `u` and `v` (increased if necessary to ensure unused).
     |      The first edge will have key 0, then 1, etc. If an edge is removed
     |      further new_edge_keys may not be in this order.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |
     |      Returns
     |      -------
     |      key : int
     |
     |  number_of_edges(self, u=None, v=None)
     |      Returns the number of edges between two nodes.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes, optional (Default=all edges)
     |          If u and v are specified, return the number of edges between
     |          u and v. Otherwise return the total number of all edges.
     |
     |      Returns
     |      -------
     |      nedges : int
     |          The number of edges in the graph.  If nodes `u` and `v` are
     |          specified return the number of edges between those nodes. If
     |          the graph is directed, this only returns the number of edges
     |          from `u` to `v`.
     |
     |      See Also
     |      --------
     |      size
     |
     |      Examples
     |      --------
     |      For undirected multigraphs, this method counts the total number
     |      of edges in the graph::
     |
     |          >>> G = nx.MultiGraph()
     |          >>> G.add_edges_from([(0, 1), (0, 1), (1, 2)])
     |          [0, 1, 0]
     |          >>> G.number_of_edges()
     |          3
     |
     |      If you specify two nodes, this counts the total number of edges
     |      joining the two nodes::
     |
     |          >>> G.number_of_edges(0, 1)
     |          2
     |
     |      For directed multigraphs, this method can count the total number
     |      of directed edges from `u` to `v`::
     |
     |          >>> G = nx.MultiDiGraph()
     |          >>> G.add_edges_from([(0, 1), (0, 1), (1, 0)])
     |          [0, 1, 0]
     |          >>> G.number_of_edges(0, 1)
     |          2
     |          >>> G.number_of_edges(1, 0)
     |          1
     |
     |  remove_edge(self, u, v, key=None)
     |      Remove an edge between u and v.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |          Remove an edge between nodes u and v.
     |      key : hashable identifier, optional (default=None)
     |          Used to distinguish multiple edges between a pair of nodes.
     |          If None, remove a single edge between u and v. If there are
     |          multiple edges, removes the last edge added in terms of
     |          insertion order.
     |
     |      Raises
     |      ------
     |      NetworkXError
     |          If there is not an edge between u and v, or
     |          if there is no edge with the specified key.
     |
     |      See Also
     |      --------
     |      remove_edges_from : remove a collection of edges
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiGraph()
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.remove_edge(0, 1)
     |      >>> e = (1, 2)
     |      >>> G.remove_edge(*e)  # unpacks e from an edge tuple
     |
     |      For multiple edges
     |
     |      >>> G = nx.MultiGraph()  # or MultiDiGraph, etc
     |      >>> G.add_edges_from([(1, 2), (1, 2), (1, 2)])  # key_list returned
     |      [0, 1, 2]
     |
     |      When ``key=None`` (the default), edges are removed in the opposite
     |      order that they were added:
     |
     |      >>> G.remove_edge(1, 2)
     |      >>> G.edges(keys=True)
     |      MultiEdgeView([(1, 2, 0), (1, 2, 1)])
     |      >>> G.remove_edge(2, 1)  # edges are not directed
     |      >>> G.edges(keys=True)
     |      MultiEdgeView([(1, 2, 0)])
     |
     |      For edges with keys
     |
     |      >>> G = nx.MultiGraph()
     |      >>> G.add_edge(1, 2, key="first")
     |      'first'
     |      >>> G.add_edge(1, 2, key="second")
     |      'second'
     |      >>> G.remove_edge(1, 2, key="first")
     |      >>> G.edges(keys=True)
     |      MultiEdgeView([(1, 2, 'second')])
     |
     |  remove_edges_from(self, ebunch)
     |      Remove all edges specified in ebunch.
     |
     |      Parameters
     |      ----------
     |      ebunch: list or container of edge tuples
     |          Each edge given in the list or container will be removed
     |          from the graph. The edges can be:
     |
     |              - 2-tuples (u, v) A single edge between u and v is removed.
     |              - 3-tuples (u, v, key) The edge identified by key is removed.
     |              - 4-tuples (u, v, key, data) where data is ignored.
     |
     |      See Also
     |      --------
     |      remove_edge : remove a single edge
     |
     |      Notes
     |      -----
     |      Will fail silently if an edge in ebunch is not in the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> ebunch = [(1, 2), (2, 3)]
     |      >>> G.remove_edges_from(ebunch)
     |
     |      Removing multiple copies of edges
     |
     |      >>> G = nx.MultiGraph()
     |      >>> keys = G.add_edges_from([(1, 2), (1, 2), (1, 2)])
     |      >>> G.remove_edges_from([(1, 2), (2, 1)])  # edges aren't directed
     |      >>> list(G.edges())
     |      [(1, 2)]
     |      >>> G.remove_edges_from([(1, 2), (1, 2)])  # silently ignore extra copy
     |      >>> list(G.edges)  # now empty graph
     |      []
     |
     |      When the edge is a 2-tuple ``(u, v)`` but there are multiple edges between
     |      u and v in the graph, the most recent edge (in terms of insertion
     |      order) is removed.
     |
     |      >>> G = nx.MultiGraph()
     |      >>> for key in ("x", "y", "a"):
     |      ...     k = G.add_edge(0, 1, key=key)
     |      >>> G.edges(keys=True)
     |      MultiEdgeView([(0, 1, 'x'), (0, 1, 'y'), (0, 1, 'a')])
     |      >>> G.remove_edges_from([(0, 1)])
     |      >>> G.edges(keys=True)
     |      MultiEdgeView([(0, 1, 'x'), (0, 1, 'y')])
     |
     |  to_directed(self, as_view=False)
     |      Returns a directed representation of the graph.
     |
     |      Returns
     |      -------
     |      G : MultiDiGraph
     |          A directed graph with the same name, same nodes, and with
     |          each edge (u, v, k, data) replaced by two directed edges
     |          (u, v, k, data) and (v, u, k, data).
     |
     |      Notes
     |      -----
     |      This returns a "deepcopy" of the edge, node, and
     |      graph attributes which attempts to completely copy
     |      all of the data and references.
     |
     |      This is in contrast to the similar D=MultiDiGraph(G) which
     |      returns a shallow copy of the data.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Warning: If you have subclassed MultiGraph to use dict-like objects
     |      in the data structure, those changes do not transfer to the
     |      MultiDiGraph created by this method.
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiGraph()
     |      >>> G.add_edge(0, 1)
     |      0
     |      >>> G.add_edge(0, 1)
     |      1
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1, 0), (0, 1, 1), (1, 0, 0), (1, 0, 1)]
     |
     |      If already directed, return a (deep) copy
     |
     |      >>> G = nx.MultiDiGraph()
     |      >>> G.add_edge(0, 1)
     |      0
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1, 0)]
     |
     |  to_directed_class(self)
     |      Returns the class to use for empty directed copies.
     |
     |      If you subclass the base classes, use this to designate
     |      what directed class to use for `to_directed()` copies.
     |
     |  to_undirected(self, as_view=False)
     |      Returns an undirected copy of the graph.
     |
     |      Returns
     |      -------
     |      G : Graph/MultiGraph
     |          A deepcopy of the graph.
     |
     |      See Also
     |      --------
     |      copy, add_edge, add_edges_from
     |
     |      Notes
     |      -----
     |      This returns a "deepcopy" of the edge, node, and
     |      graph attributes which attempts to completely copy
     |      all of the data and references.
     |
     |      This is in contrast to the similar `G = nx.MultiGraph(D)`
     |      which returns a shallow copy of the data.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Warning: If you have subclassed MultiGraph to use dict-like
     |      objects in the data structure, those changes do not transfer
     |      to the MultiGraph created by this method.
     |
     |      Examples
     |      --------
     |      >>> G = nx.MultiGraph([(0, 1), (0, 1), (1, 2)])
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1, 0), (0, 1, 1), (1, 0, 0), (1, 0, 1), (1, 2, 0), (2, 1, 0)]
     |      >>> G2 = H.to_undirected()
     |      >>> list(G2.edges)
     |      [(0, 1, 0), (0, 1, 1), (1, 2, 0)]
     |
     |  to_undirected_class(self)
     |      Returns the class to use for empty undirected copies.
     |
     |      If you subclass the base classes, use this to designate
     |      what directed class to use for `to_directed()` copies.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  edge_key_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from networkx.classes.graph.Graph:
     |
     |  __contains__(self, n)
     |      Returns True if n is a node, False otherwise. Use: 'n in G'.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> 1 in G
     |      True
     |
     |  __getitem__(self, n)
     |      Returns a dict of neighbors of node n.  Use: 'G[n]'.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph.
     |
     |      Returns
     |      -------
     |      adj_dict : dictionary
     |         The adjacency dictionary for nodes connected to n.
     |
     |      Notes
     |      -----
     |      G[n] is the same as G.adj[n] and similar to G.neighbors(n)
     |      (which is an iterator over G.adj[n])
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G[0]
     |      AtlasView({1: {}})
     |
     |  __iter__(self)
     |      Iterate over the nodes. Use: 'for n in G'.
     |
     |      Returns
     |      -------
     |      niter : iterator
     |          An iterator over all nodes in the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> [n for n in G]
     |      [0, 1, 2, 3]
     |      >>> list(G)
     |      [0, 1, 2, 3]
     |
     |  __len__(self)
     |      Returns the number of nodes in the graph. Use: 'len(G)'.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      number_of_nodes: identical method
     |      order: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> len(G)
     |      4
     |
     |  __str__(self)
     |      Returns a short summary of the graph.
     |
     |      Returns
     |      -------
     |      info : string
     |          Graph information including the graph name (if any), graph type, and the
     |          number of nodes and edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph(name="foo")
     |      >>> str(G)
     |      "Graph named 'foo' with 0 nodes and 0 edges"
     |
     |      >>> G = nx.path_graph(3)
     |      >>> str(G)
     |      'Graph with 3 nodes and 2 edges'
     |
     |  add_node(self, node_for_adding, **attr)
     |      Add a single node `node_for_adding` and update node attributes.
     |
     |      Parameters
     |      ----------
     |      node_for_adding : node
     |          A node can be any hashable Python object except None.
     |      attr : keyword arguments, optional
     |          Set or change node attributes using key=value.
     |
     |      See Also
     |      --------
     |      add_nodes_from
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_node(1)
     |      >>> G.add_node("Hello")
     |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
     |      >>> G.add_node(K3)
     |      >>> G.number_of_nodes()
     |      3
     |
     |      Use keywords set/change node attributes:
     |
     |      >>> G.add_node(1, size=10)
     |      >>> G.add_node(3, weight=0.4, UTM=("13S", 382871, 3972649))
     |
     |      Notes
     |      -----
     |      A hashable object is one that can be used as a key in a Python
     |      dictionary. This includes strings, numbers, tuples of strings
     |      and numbers, etc.
     |
     |      On many platforms hashable items also include mutables such as
     |      NetworkX Graphs, though one should be careful that the hash
     |      doesn't change on mutables.
     |
     |  add_nodes_from(self, nodes_for_adding, **attr)
     |      Add multiple nodes.
     |
     |      Parameters
     |      ----------
     |      nodes_for_adding : iterable container
     |          A container of nodes (list, dict, set, etc.).
     |          OR
     |          A container of (node, attribute dict) tuples.
     |          Node attributes are updated using the attribute dict.
     |      attr : keyword arguments, optional (default= no attributes)
     |          Update attributes for all nodes in nodes.
     |          Node attributes specified in nodes as a tuple take
     |          precedence over attributes specified via keyword arguments.
     |
     |      See Also
     |      --------
     |      add_node
     |
     |      Notes
     |      -----
     |      When adding nodes from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
     |      object to `G.add_nodes_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_nodes_from("Hello")
     |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
     |      >>> G.add_nodes_from(K3)
     |      >>> sorted(G.nodes(), key=str)
     |      [0, 1, 2, 'H', 'e', 'l', 'o']
     |
     |      Use keywords to update specific node attributes for every node.
     |
     |      >>> G.add_nodes_from([1, 2], size=10)
     |      >>> G.add_nodes_from([3, 4], weight=0.4)
     |
     |      Use (node, attrdict) tuples to update attributes for specific nodes.
     |
     |      >>> G.add_nodes_from([(1, dict(size=11)), (2, {"color": "blue"})])
     |      >>> G.nodes[1]["size"]
     |      11
     |      >>> H = nx.Graph()
     |      >>> H.add_nodes_from(G.nodes(data=True))
     |      >>> H.nodes[1]["size"]
     |      11
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.Graph([(0, 1), (1, 2), (3, 4)])
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_nodes_from(n + 1 for n in G.nodes)
     |      >>> # correct way
     |      >>> G.add_nodes_from(list(n + 1 for n in G.nodes))
     |
     |  add_weighted_edges_from(self, ebunch_to_add, weight='weight', **attr)
     |      Add weighted edges in `ebunch_to_add` with specified weight attr
     |
     |      Parameters
     |      ----------
     |      ebunch_to_add : container of edges
     |          Each edge given in the list or container will be added
     |          to the graph. The edges must be given as 3-tuples (u, v, w)
     |          where w is a number.
     |      weight : string, optional (default= 'weight')
     |          The attribute name for the edge weights to be added.
     |      attr : keyword arguments, optional (default= no attributes)
     |          Edge attributes to add/update for all edges.
     |
     |      See Also
     |      --------
     |      add_edge : add a single edge
     |      add_edges_from : add multiple edges
     |
     |      Notes
     |      -----
     |      Adding the same edge twice for Graph/DiGraph simply updates
     |      the edge data. For MultiGraph/MultiDiGraph, duplicate edges
     |      are stored.
     |
     |      When adding edges from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_edges)`, and pass this
     |      object to `G.add_weighted_edges_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_weighted_edges_from([(0, 1, 3.0), (1, 2, 7.5)])
     |
     |      Evaluate an iterator over edges before passing it
     |
     |      >>> G = nx.Graph([(1, 2), (2, 3), (3, 4)])
     |      >>> weight = 0.1
     |      >>> # Grow graph by one new node, adding edges to all existing nodes.
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_weighted_edges_from(((5, n, weight) for n in G.nodes))
     |      >>> # correct way - note that there will be no self-edge for node 5
     |      >>> G.add_weighted_edges_from(list((5, n, weight) for n in G.nodes))
     |
     |  adjacency(self)
     |      Returns an iterator over (node, adjacency dict) tuples for all nodes.
     |
     |      For directed graphs, only outgoing neighbors/adjacencies are included.
     |
     |      Returns
     |      -------
     |      adj_iter : iterator
     |         An iterator over (node, adjacency dictionary) for all nodes in
     |         the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> [(n, nbrdict) for n, nbrdict in G.adjacency()]
     |      [(0, {1: {}}), (1, {0: {}, 2: {}}), (2, {1: {}, 3: {}}), (3, {2: {}})]
     |
     |  clear(self)
     |      Remove all nodes and edges from the graph.
     |
     |      This also removes the name, and all graph, node, and edge attributes.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.clear()
     |      >>> list(G.nodes)
     |      []
     |      >>> list(G.edges)
     |      []
     |
     |  clear_edges(self)
     |      Remove all edges from the graph without altering nodes.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.clear_edges()
     |      >>> list(G.nodes)
     |      [0, 1, 2, 3]
     |      >>> list(G.edges)
     |      []
     |
     |  edge_subgraph(self, edges)
     |      Returns the subgraph induced by the specified edges.
     |
     |      The induced subgraph contains each edge in `edges` and each
     |      node incident to any one of those edges.
     |
     |      Parameters
     |      ----------
     |      edges : iterable
     |          An iterable of edges in this graph.
     |
     |      Returns
     |      -------
     |      G : Graph
     |          An edge-induced subgraph of this graph with the same edge
     |          attributes.
     |
     |      Notes
     |      -----
     |      The graph, edge, and node attributes in the returned subgraph
     |      view are references to the corresponding attributes in the original
     |      graph. The view is read-only.
     |
     |      To create a full graph version of the subgraph with its own copy
     |      of the edge or node attributes, use::
     |
     |          G.edge_subgraph(edges).copy()
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(5)
     |      >>> H = G.edge_subgraph([(0, 1), (3, 4)])
     |      >>> list(H.nodes)
     |      [0, 1, 3, 4]
     |      >>> list(H.edges)
     |      [(0, 1), (3, 4)]
     |
     |  has_node(self, n)
     |      Returns True if the graph contains the node n.
     |
     |      Identical to `n in G`
     |
     |      Parameters
     |      ----------
     |      n : node
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.has_node(0)
     |      True
     |
     |      It is more readable and simpler to use
     |
     |      >>> 0 in G
     |      True
     |
     |  nbunch_iter(self, nbunch=None)
     |      Returns an iterator over nodes contained in nbunch that are
     |      also in the graph.
     |
     |      The nodes in nbunch are checked for membership in the graph
     |      and if not are silently ignored.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      Returns
     |      -------
     |      niter : iterator
     |          An iterator over nodes in nbunch that are also in the graph.
     |          If nbunch is None, iterate over all nodes in the graph.
     |
     |      Raises
     |      ------
     |      NetworkXError
     |          If nbunch is not a node or sequence of nodes.
     |          If a node in nbunch is not hashable.
     |
     |      See Also
     |      --------
     |      Graph.__iter__
     |
     |      Notes
     |      -----
     |      When nbunch is an iterator, the returned iterator yields values
     |      directly from nbunch, becoming exhausted when nbunch is exhausted.
     |
     |      To test whether nbunch is a single node, one can use
     |      "if nbunch in self:", even after processing with this routine.
     |
     |      If nbunch is not a node or a (possibly empty) sequence/iterator
     |      or None, a :exc:`NetworkXError` is raised.  Also, if any object in
     |      nbunch is not hashable, a :exc:`NetworkXError` is raised.
     |
     |  neighbors(self, n)
     |      Returns an iterator over all neighbors of node n.
     |
     |      This is identical to `iter(G[n])`
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Returns
     |      -------
     |      neighbors : iterator
     |          An iterator over all neighbors of node n
     |
     |      Raises
     |      ------
     |      NetworkXError
     |          If the node n is not in the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> [n for n in G.neighbors(0)]
     |      [1]
     |
     |      Notes
     |      -----
     |      Alternate ways to access the neighbors are ``G.adj[n]`` or ``G[n]``:
     |
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_edge("a", "b", weight=7)
     |      >>> G["a"]
     |      AtlasView({'b': {'weight': 7}})
     |      >>> G = nx.path_graph(4)
     |      >>> [n for n in G[0]]
     |      [1]
     |
     |  nodes = <functools.cached_property object>
     |      A NodeView of the Graph as G.nodes or G.nodes().
     |
     |      Can be used as `G.nodes` for data lookup and for set-like operations.
     |      Can also be used as `G.nodes(data='color', default=None)` to return a
     |      NodeDataView which reports specific node data but no set operations.
     |      It presents a dict-like interface as well with `G.nodes.items()`
     |      iterating over `(node, nodedata)` 2-tuples and `G.nodes[3]['foo']`
     |      providing the value of the `foo` attribute for node `3`. In addition,
     |      a view `G.nodes.data('foo')` provides a dict-like interface to the
     |      `foo` attribute of each node. `G.nodes.data('foo', default=1)`
     |      provides a default for nodes that do not have attribute `foo`.
     |
     |      Parameters
     |      ----------
     |      data : string or bool, optional (default=False)
     |          The node attribute returned in 2-tuple (n, ddict[data]).
     |          If True, return entire node attribute dict as (n, ddict).
     |          If False, return just the nodes n.
     |
     |      default : value, optional (default=None)
     |          Value used for nodes that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      NodeView
     |          Allows set-like operations over the nodes as well as node
     |          attribute dict lookup and calling to get a NodeDataView.
     |          A NodeDataView iterates over `(n, data)` and has no set operations.
     |          A NodeView iterates over `n` and includes set operations.
     |
     |          When called, if data is False, an iterator over nodes.
     |          Otherwise an iterator of 2-tuples (node, attribute value)
     |          where the attribute is specified in `data`.
     |          If data is True then the attribute becomes the
     |          entire data dictionary.
     |
     |      Notes
     |      -----
     |      If your node data is not needed, it is simpler and equivalent
     |      to use the expression ``for n in G``, or ``list(G)``.
     |
     |      Examples
     |      --------
     |      There are two simple ways of getting a list of all nodes in the graph:
     |
     |      >>> G = nx.path_graph(3)
     |      >>> list(G.nodes)
     |      [0, 1, 2]
     |      >>> list(G)
     |      [0, 1, 2]
     |
     |      To get the node data along with the nodes:
     |
     |      >>> G.add_node(1, time="5pm")
     |      >>> G.nodes[0]["foo"] = "bar"
     |      >>> list(G.nodes(data=True))
     |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
     |      >>> list(G.nodes.data())
     |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
     |
     |      >>> list(G.nodes(data="foo"))
     |      [(0, 'bar'), (1, None), (2, None)]
     |      >>> list(G.nodes.data("foo"))
     |      [(0, 'bar'), (1, None), (2, None)]
     |
     |      >>> list(G.nodes(data="time"))
     |      [(0, None), (1, '5pm'), (2, None)]
     |      >>> list(G.nodes.data("time"))
     |      [(0, None), (1, '5pm'), (2, None)]
     |
     |      >>> list(G.nodes(data="time", default="Not Available"))
     |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
     |      >>> list(G.nodes.data("time", default="Not Available"))
     |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
     |
     |      If some of your nodes have an attribute and the rest are assumed
     |      to have a default attribute value you can create a dictionary
     |      from node/attribute pairs using the `default` keyword argument
     |      to guarantee the value is never None::
     |
     |          >>> G = nx.Graph()
     |          >>> G.add_node(0)
     |          >>> G.add_node(1, weight=2)
     |          >>> G.add_node(2, weight=3)
     |          >>> dict(G.nodes(data="weight", default=1))
     |          {0: 1, 1: 2, 2: 3}
     |
     |  number_of_nodes(self)
     |      Returns the number of nodes in the graph.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      order: identical method
     |      __len__: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.number_of_nodes()
     |      3
     |
     |  order(self)
     |      Returns the number of nodes in the graph.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      number_of_nodes: identical method
     |      __len__: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.order()
     |      3
     |
     |  remove_node(self, n)
     |      Remove node n.
     |
     |      Removes the node n and all adjacent edges.
     |      Attempting to remove a nonexistent node will raise an exception.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Raises
     |      ------
     |      NetworkXError
     |         If n is not in the graph.
     |
     |      See Also
     |      --------
     |      remove_nodes_from
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> list(G.edges)
     |      [(0, 1), (1, 2)]
     |      >>> G.remove_node(1)
     |      >>> list(G.edges)
     |      []
     |
     |  remove_nodes_from(self, nodes)
     |      Remove multiple nodes.
     |
     |      Parameters
     |      ----------
     |      nodes : iterable container
     |          A container of nodes (list, dict, set, etc.).  If a node
     |          in the container is not in the graph it is silently
     |          ignored.
     |
     |      See Also
     |      --------
     |      remove_node
     |
     |      Notes
     |      -----
     |      When removing nodes from an iterator over the graph you are changing,
     |      a `RuntimeError` will be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
     |      object to `G.remove_nodes_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> e = list(G.nodes)
     |      >>> e
     |      [0, 1, 2]
     |      >>> G.remove_nodes_from(e)
     |      >>> list(G.nodes)
     |      []
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.Graph([(0, 1), (1, 2), (3, 4)])
     |      >>> # this command will fail, as the graph's dict is modified during iteration
     |      >>> # G.remove_nodes_from(n for n in G.nodes if n < 2)
     |      >>> # this command will work, since the dictionary underlying graph is not modified
     |      >>> G.remove_nodes_from(list(n for n in G.nodes if n < 2))
     |
     |  size(self, weight=None)
     |      Returns the number of edges or total of all edge weights.
     |
     |      Parameters
     |      ----------
     |      weight : string or None, optional (default=None)
     |          The edge attribute that holds the numerical value used
     |          as a weight. If None, then each edge has weight 1.
     |
     |      Returns
     |      -------
     |      size : numeric
     |          The number of edges or
     |          (if weight keyword is provided) the total weight sum.
     |
     |          If weight is None, returns an int. Otherwise a float
     |          (or more general numeric if the weights are more general).
     |
     |      See Also
     |      --------
     |      number_of_edges
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.size()
     |      3
     |
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_edge("a", "b", weight=2)
     |      >>> G.add_edge("b", "c", weight=4)
     |      >>> G.size()
     |      2
     |      >>> G.size(weight="weight")
     |      6.0
     |
     |  subgraph(self, nodes)
     |      Returns a SubGraph view of the subgraph induced on `nodes`.
     |
     |      The induced subgraph of the graph contains the nodes in `nodes`
     |      and the edges between those nodes.
     |
     |      Parameters
     |      ----------
     |      nodes : list, iterable
     |          A container of nodes which will be iterated through once.
     |
     |      Returns
     |      -------
     |      G : SubGraph View
     |          A subgraph view of the graph. The graph structure cannot be
     |          changed but node/edge attributes can and are shared with the
     |          original graph.
     |
     |      Notes
     |      -----
     |      The graph, edge and node attributes are shared with the original graph.
     |      Changes to the graph structure is ruled out by the view, but changes
     |      to attributes are reflected in the original graph.
     |
     |      To create a subgraph with its own copy of the edge/node attributes use:
     |      G.subgraph(nodes).copy()
     |
     |      For an inplace reduction of a graph to a subgraph you can remove nodes:
     |      G.remove_nodes_from([n for n in G if n not in set(nodes)])
     |
     |      Subgraph views are sometimes NOT what you want. In most cases where
     |      you want to do more than simply look at the induced edges, it makes
     |      more sense to just create the subgraph as its own graph with code like:
     |
     |      ::
     |
     |          # Create a subgraph SG based on a (possibly multigraph) G
     |          SG = G.__class__()
     |          SG.add_nodes_from((n, G.nodes[n]) for n in largest_wcc)
     |          if SG.is_multigraph():
     |              SG.add_edges_from(
     |                  (n, nbr, key, d)
     |                  for n, nbrs in G.adj.items()
     |                  if n in largest_wcc
     |                  for nbr, keydict in nbrs.items()
     |                  if nbr in largest_wcc
     |                  for key, d in keydict.items()
     |              )
     |          else:
     |              SG.add_edges_from(
     |                  (n, nbr, d)
     |                  for n, nbrs in G.adj.items()
     |                  if n in largest_wcc
     |                  for nbr, d in nbrs.items()
     |                  if nbr in largest_wcc
     |              )
     |          SG.graph.update(G.graph)
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> H = G.subgraph([0, 1, 2])
     |      >>> list(H.edges)
     |      [(0, 1), (1, 2)]
     |
     |  update(self, edges=None, nodes=None)
     |      Update the graph using nodes/edges/graphs as input.
     |
     |      Like dict.update, this method takes a graph as input, adding the
     |      graph's nodes and edges to this graph. It can also take two inputs:
     |      edges and nodes. Finally it can take either edges or nodes.
     |      To specify only nodes the keyword `nodes` must be used.
     |
     |      The collections of edges and nodes are treated similarly to
     |      the add_edges_from/add_nodes_from methods. When iterated, they
     |      should yield 2-tuples (u, v) or 3-tuples (u, v, datadict).
     |
     |      Parameters
     |      ----------
     |      edges : Graph object, collection of edges, or None
     |          The first parameter can be a graph or some edges. If it has
     |          attributes `nodes` and `edges`, then it is taken to be a
     |          Graph-like object and those attributes are used as collections
     |          of nodes and edges to be added to the graph.
     |          If the first parameter does not have those attributes, it is
     |          treated as a collection of edges and added to the graph.
     |          If the first argument is None, no edges are added.
     |      nodes : collection of nodes, or None
     |          The second parameter is treated as a collection of nodes
     |          to be added to the graph unless it is None.
     |          If `edges is None` and `nodes is None` an exception is raised.
     |          If the first parameter is a Graph, then `nodes` is ignored.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(5)
     |      >>> G.update(nx.complete_graph(range(4, 10)))
     |      >>> from itertools import combinations
     |      >>> edges = (
     |      ...     (u, v, {"power": u * v})
     |      ...     for u, v in combinations(range(10, 20), 2)
     |      ...     if u * v < 225
     |      ... )
     |      >>> nodes = [1000]  # for singleton, use a container
     |      >>> G.update(edges, nodes)
     |
     |      Notes
     |      -----
     |      It you want to update the graph using an adjacency structure
     |      it is straightforward to obtain the edges/nodes from adjacency.
     |      The following examples provide common cases, your adjacency may
     |      be slightly different and require tweaks of these examples::
     |
     |      >>> # dict-of-set/list/tuple
     |      >>> adj = {1: {2, 3}, 2: {1, 3}, 3: {1, 2}}
     |      >>> e = [(u, v) for u, nbrs in adj.items() for v in nbrs]
     |      >>> G.update(edges=e, nodes=adj)
     |
     |      >>> DG = nx.DiGraph()
     |      >>> # dict-of-dict-of-attribute
     |      >>> adj = {1: {2: 1.3, 3: 0.7}, 2: {1: 1.4}, 3: {1: 0.7}}
     |      >>> e = [
     |      ...     (u, v, {"weight": d})
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, d in nbrs.items()
     |      ... ]
     |      >>> DG.update(edges=e, nodes=adj)
     |
     |      >>> # dict-of-dict-of-dict
     |      >>> adj = {1: {2: {"weight": 1.3}, 3: {"color": 0.7, "weight": 1.2}}}
     |      >>> e = [
     |      ...     (u, v, {"weight": d})
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, d in nbrs.items()
     |      ... ]
     |      >>> DG.update(edges=e, nodes=adj)
     |
     |      >>> # predecessor adjacency (dict-of-set)
     |      >>> pred = {1: {2, 3}, 2: {3}, 3: {3}}
     |      >>> e = [(v, u) for u, nbrs in pred.items() for v in nbrs]
     |
     |      >>> # MultiGraph dict-of-dict-of-dict-of-attribute
     |      >>> MDG = nx.MultiDiGraph()
     |      >>> adj = {
     |      ...     1: {2: {0: {"weight": 1.3}, 1: {"weight": 1.2}}},
     |      ...     3: {2: {0: {"weight": 0.7}}},
     |      ... }
     |      >>> e = [
     |      ...     (u, v, ekey, d)
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, keydict in nbrs.items()
     |      ...     for ekey, d in keydict.items()
     |      ... ]
     |      >>> MDG.update(edges=e)
     |
     |      See Also
     |      --------
     |      add_edges_from: add multiple edges to a graph
     |      add_nodes_from: add multiple nodes to a graph
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from networkx.classes.graph.Graph:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  name
     |      String identifier of the graph.
     |
     |      This graph attribute appears in the attribute dict G.graph
     |      keyed by the string `"name"`. as well as an attribute (technically
     |      a property) `G.name`. This is entirely user controlled.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from networkx.classes.graph.Graph:
     |
     |  __networkx_backend__ = 'networkx'
     |
     |  adjlist_inner_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  adjlist_outer_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  edge_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  graph_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  node_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  node_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)

DATA
    __all__ = ['MultiGraph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\classes\multigraph.py

networkx.multiline_adjlist
Python Library Documentation: module networkx.readwrite.multiline_adjlist in networkx.readwrite

NAME
    networkx.readwrite.multiline_adjlist

DESCRIPTION
    *************************
    Multi-line Adjacency List
    *************************
    Read and write NetworkX graphs as multi-line adjacency lists.

    The multi-line adjacency list format is useful for graphs with
    nodes that can be meaningfully represented as strings.  With this format
    simple edge data can be stored but node or graph data is not.

    Format
    ------
    The first label in a line is the source node label followed by the node degree
    d.  The next d lines are target node labels and optional edge data.
    That pattern repeats for all nodes in the graph.

    The graph with edges a-b, a-c, d-e can be represented as the following
    adjacency list (anything following the # in a line is a comment)::

         # example.multiline-adjlist
         a 2
         b
         c
         d 1
         e

FUNCTIONS
    generate_multiline_adjlist(G, delimiter=' ')
        Generate a single line of the graph G in multiline adjacency list format.

        Parameters
        ----------
        G : NetworkX graph

        delimiter : string, optional
           Separator for node labels

        Returns
        -------
        lines : string
            Lines of data in multiline adjlist format.

        Examples
        --------
        >>> G = nx.lollipop_graph(4, 3)
        >>> for line in nx.generate_multiline_adjlist(G):
        ...     print(line)
        0 3
        1 {}
        2 {}
        3 {}
        1 2
        2 {}
        3 {}
        2 1
        3 {}
        3 1
        4 {}
        4 1
        5 {}
        5 1
        6 {}
        6 0

        See Also
        --------
        write_multiline_adjlist, read_multiline_adjlist

    parse_multiline_adjlist(lines, comments='#', delimiter=None, create_using=None, nodetype=None, edgetype=None, *, backend=None, **backend_kwargs)
        Parse lines of a multiline adjacency list representation of a graph.

        Parameters
        ----------
        lines : list or iterator of strings
            Input data in multiline adjlist format

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        nodetype : Python type, optional
           Convert nodes to this type.

        edgetype : Python type, optional
           Convert edges to this type.

        comments : string, optional
           Marker for comment lines

        delimiter : string, optional
           Separator for node labels.  The default is whitespace.

        Returns
        -------
        G: NetworkX graph
            The graph corresponding to the lines in multiline adjacency list format.

        Examples
        --------
        >>> lines = [
        ...     "1 2",
        ...     "2 {'weight':3, 'name': 'Frodo'}",
        ...     "3 {}",
        ...     "2 1",
        ...     "5 {'weight':6, 'name': 'Saruman'}",
        ... ]
        >>> G = nx.parse_multiline_adjlist(iter(lines), nodetype=int)
        >>> list(G)
        [1, 2, 3, 5]

    read_multiline_adjlist(path, comments='#', delimiter=None, create_using=None, nodetype=None, edgetype=None, encoding='utf-8', *, backend=None, **backend_kwargs)
        Read graph in multi-line adjacency list format from path.

        Parameters
        ----------
        path : string or file
           Filename or file handle to read.
           Filenames ending in .gz or .bz2 will be uncompressed.

        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        nodetype : Python type, optional
           Convert nodes to this type.

        edgetype : Python type, optional
           Convert edge data to this type.

        comments : string, optional
           Marker for comment lines

        delimiter : string, optional
           Separator for node labels.  The default is whitespace.

        Returns
        -------
        G: NetworkX graph

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_multiline_adjlist(G, "test.adjlist")
        >>> G = nx.read_multiline_adjlist("test.adjlist")

        The path can be a file or a string with the name of the file. If a
        file s provided, it has to be opened in 'rb' mode.

        >>> fh = open("test.adjlist", "rb")
        >>> G = nx.read_multiline_adjlist(fh)

        Filenames ending in .gz or .bz2 will be compressed.

        >>> nx.write_multiline_adjlist(G, "test.adjlist.gz")
        >>> G = nx.read_multiline_adjlist("test.adjlist.gz")

        The optional nodetype is a function to convert node strings to nodetype.

        For example

        >>> G = nx.read_multiline_adjlist("test.adjlist", nodetype=int)

        will attempt to convert all nodes to integer type.

        The optional edgetype is a function to convert edge data strings to
        edgetype.

        >>> G = nx.read_multiline_adjlist("test.adjlist")

        The optional create_using parameter is a NetworkX graph container.
        The default is Graph(), an undirected graph.  To read the data as
        a directed graph use

        >>> G = nx.read_multiline_adjlist("test.adjlist", create_using=nx.DiGraph)

        Notes
        -----
        This format does not store graph, node, or edge data.

        See Also
        --------
        write_multiline_adjlist

    write_multiline_adjlist(G, path, delimiter=' ', comments='#', encoding='utf-8')
        Write the graph G in multiline adjacency list format to path

        Parameters
        ----------
        G : NetworkX graph

        path : string or file
           Filename or file handle to write to.
           Filenames ending in .gz or .bz2 will be compressed.

        comments : string, optional
           Marker for comment lines

        delimiter : string, optional
           Separator for node labels

        encoding : string, optional
           Text encoding.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_multiline_adjlist(G, "test.adjlist")

        The path can be a file handle or a string with the name of the file. If a
        file handle is provided, it has to be opened in 'wb' mode.

        >>> fh = open("test.adjlist", "wb")
        >>> nx.write_multiline_adjlist(G, fh)

        Filenames ending in .gz or .bz2 will be compressed.

        >>> nx.write_multiline_adjlist(G, "test.adjlist.gz")

        See Also
        --------
        read_multiline_adjlist

DATA
    __all__ = ['generate_multiline_adjlist', 'write_multiline_adjlist', 'p...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\multiline_adjlist.py

networkx.multipartite_layout
Python Library Documentation: function multipartite_layout in module networkx.drawing.layout

multipartite_layout(G, subset_key='subset', align='vertical', scale=1, center=None)
    Position nodes in layers of straight lines.

    Parameters
    ----------
    G : NetworkX graph or list of nodes
        A position will be assigned to every node in G.

    subset_key : string or dict (default='subset')
        If a string, the key of node data in G that holds the node subset.
        If a dict, keyed by layer number to the nodes in that layer/subset.

    align : string (default='vertical')
        The alignment of nodes. Vertical or horizontal.

    scale : number (default: 1)
        Scale factor for positions.

    center : array-like or None
        Coordinate pair around which to center the layout.

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node.

    Examples
    --------
    >>> G = nx.complete_multipartite_graph(28, 16, 10)
    >>> pos = nx.multipartite_layout(G)

    or use a dict to provide the layers of the layout

    >>> G = nx.Graph([(0, 1), (1, 2), (1, 3), (3, 4)])
    >>> layers = {"a": [0], "b": [1], "c": [2, 3], "d": [4]}
    >>> pos = nx.multipartite_layout(G, subset_key=layers)

    Notes
    -----
    This algorithm currently only works in two dimensions and does not
    try to minimize edge crossings.

    Network does not need to be a complete multipartite graph. As long as nodes
    have subset_key data, they will be placed in the corresponding layers.
networkx.mycielski
Python Library Documentation: module networkx.generators.mycielski in networkx.generators

NAME
    networkx.generators.mycielski

DESCRIPTION
    Functions related to the Mycielski Operation and the Mycielskian family
    of graphs.

FUNCTIONS
    mycielski_graph(n, *, backend=None, **backend_kwargs)
        Generator for the n_th Mycielski Graph.

        The Mycielski family of graphs is an infinite set of graphs.
        :math:`M_1` is the singleton graph, :math:`M_2` is two vertices with an
        edge, and, for :math:`i > 2`, :math:`M_i` is the Mycielskian of
        :math:`M_{i-1}`.

        More information can be found at
        http://mathworld.wolfram.com/MycielskiGraph.html

        Parameters
        ----------
        n : int
            The desired Mycielski Graph.

        Returns
        -------
        M : graph
            The n_th Mycielski Graph

        Notes
        -----
        The first graph in the Mycielski sequence is the singleton graph.
        The Mycielskian of this graph is not the :math:`P_2` graph, but rather the
        :math:`P_2` graph with an extra, isolated vertex. The second Mycielski
        graph is the :math:`P_2` graph, so the first two are hard coded.
        The remaining graphs are generated using the Mycielski operation.

    mycielskian(G, iterations=1, *, backend=None, **backend_kwargs)
        Returns the Mycielskian of a simple, undirected graph G

        The Mycielskian of graph preserves a graph's triangle free
        property while increasing the chromatic number by 1.

        The Mycielski Operation on a graph, :math:`G=(V, E)`, constructs a new
        graph with :math:`2|V| + 1` nodes and :math:`3|E| + |V|` edges.

        The construction is as follows:

        Let :math:`V = {0, ..., n-1}`. Construct another vertex set
        :math:`U = {n, ..., 2n}` and a vertex, `w`.
        Construct a new graph, `M`, with vertices :math:`U \bigcup V \bigcup w`.
        For edges, :math:`(u, v) \in E` add edges :math:`(u, v), (u, v + n)`, and
        :math:`(u + n, v)` to M. Finally, for all vertices :math:`u \in U`, add
        edge :math:`(u, w)` to M.

        The Mycielski Operation can be done multiple times by repeating the above
        process iteratively.

        More information can be found at https://en.wikipedia.org/wiki/Mycielskian

        Parameters
        ----------
        G : graph
            A simple, undirected NetworkX graph
        iterations : int
            The number of iterations of the Mycielski operation to
            perform on G. Defaults to 1. Must be a non-negative integer.

        Returns
        -------
        M : graph
            The Mycielskian of G after the specified number of iterations.

        Notes
        -----
        Graph, node, and edge data are not necessarily propagated to the new graph.

DATA
    __all__ = ['mycielskian', 'mycielski_graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\mycielski.py

networkx.mycielski_graph
Python Library Documentation: function mycielski_graph in module networkx.generators.mycielski

mycielski_graph(n, *, backend=None, **backend_kwargs)
    Generator for the n_th Mycielski Graph.

    The Mycielski family of graphs is an infinite set of graphs.
    :math:`M_1` is the singleton graph, :math:`M_2` is two vertices with an
    edge, and, for :math:`i > 2`, :math:`M_i` is the Mycielskian of
    :math:`M_{i-1}`.

    More information can be found at
    http://mathworld.wolfram.com/MycielskiGraph.html

    Parameters
    ----------
    n : int
        The desired Mycielski Graph.

    Returns
    -------
    M : graph
        The n_th Mycielski Graph

    Notes
    -----
    The first graph in the Mycielski sequence is the singleton graph.
    The Mycielskian of this graph is not the :math:`P_2` graph, but rather the
    :math:`P_2` graph with an extra, isolated vertex. The second Mycielski
    graph is the :math:`P_2` graph, so the first two are hard coded.
    The remaining graphs are generated using the Mycielski operation.
networkx.mycielskian
Python Library Documentation: function mycielskian in module networkx.generators.mycielski

mycielskian(G, iterations=1, *, backend=None, **backend_kwargs)
    Returns the Mycielskian of a simple, undirected graph G

    The Mycielskian of graph preserves a graph's triangle free
    property while increasing the chromatic number by 1.

    The Mycielski Operation on a graph, :math:`G=(V, E)`, constructs a new
    graph with :math:`2|V| + 1` nodes and :math:`3|E| + |V|` edges.

    The construction is as follows:

    Let :math:`V = {0, ..., n-1}`. Construct another vertex set
    :math:`U = {n, ..., 2n}` and a vertex, `w`.
    Construct a new graph, `M`, with vertices :math:`U \bigcup V \bigcup w`.
    For edges, :math:`(u, v) \in E` add edges :math:`(u, v), (u, v + n)`, and
    :math:`(u + n, v)` to M. Finally, for all vertices :math:`u \in U`, add
    edge :math:`(u, w)` to M.

    The Mycielski Operation can be done multiple times by repeating the above
    process iteratively.

    More information can be found at https://en.wikipedia.org/wiki/Mycielskian

    Parameters
    ----------
    G : graph
        A simple, undirected NetworkX graph
    iterations : int
        The number of iterations of the Mycielski operation to
        perform on G. Defaults to 1. Must be a non-negative integer.

    Returns
    -------
    M : graph
        The Mycielskian of G after the specified number of iterations.

    Notes
    -----
    Graph, node, and edge data are not necessarily propagated to the new graph.
networkx.navigable_small_world_graph
Python Library Documentation: function navigable_small_world_graph in module networkx.generators.geometric

navigable_small_world_graph(n, p=1, q=1, r=2, dim=2, seed=None, *, backend=None, **backend_kwargs)
    Returns a navigable small-world graph.

    A navigable small-world graph is a directed grid with additional long-range
    connections that are chosen randomly.

      [...] we begin with a set of nodes [...] that are identified with the set
      of lattice points in an $n \times n$ square,
      $\{(i, j): i \in \{1, 2, \ldots, n\}, j \in \{1, 2, \ldots, n\}\}$,
      and we define the *lattice distance* between two nodes $(i, j)$ and
      $(k, l)$ to be the number of "lattice steps" separating them:
      $d((i, j), (k, l)) = |k - i| + |l - j|$.

      For a universal constant $p >= 1$, the node $u$ has a directed edge to
      every other node within lattice distance $p$---these are its *local
      contacts*. For universal constants $q >= 0$ and $r >= 0$ we also
      construct directed edges from $u$ to $q$ other nodes (the *long-range
      contacts*) using independent random trials; the $i$th directed edge from
      $u$ has endpoint $v$ with probability proportional to $[d(u,v)]^{-r}$.

      -- [1]_

    Parameters
    ----------
    n : int
        The length of one side of the lattice; the number of nodes in
        the graph is therefore $n^2$.
    p : int
        The diameter of short range connections. Each node is joined with every
        other node within this lattice distance.
    q : int
        The number of long-range connections for each node.
    r : float
        Exponent for decaying probability of connections.  The probability of
        connecting to a node at lattice distance $d$ is $1/d^r$.
    dim : int
        Dimension of grid
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    References
    ----------
    .. [1] J. Kleinberg. The small-world phenomenon: An algorithmic
       perspective. Proc. 32nd ACM Symposium on Theory of Computing, 2000.
networkx.negative_edge_cycle
Python Library Documentation: function negative_edge_cycle in module networkx.algorithms.shortest_paths.weighted

negative_edge_cycle(G, weight='weight', heuristic=True, *, backend=None, **backend_kwargs)
    Returns True if there exists a negative edge cycle anywhere in G.

    Parameters
    ----------
    G : NetworkX graph

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

    heuristic : bool
        Determines whether to use a heuristic to early detect negative
        cycles at a negligible cost. In case of graphs with a negative cycle,
        the performance of detection increases by at least an order of magnitude.

    Returns
    -------
    negative_cycle : bool
        True if a negative edge cycle exists, otherwise False.

    Examples
    --------
    >>> G = nx.cycle_graph(5, create_using=nx.DiGraph())
    >>> print(nx.negative_edge_cycle(G))
    False
    >>> G[1][2]["weight"] = -7
    >>> print(nx.negative_edge_cycle(G))
    True

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    This algorithm uses bellman_ford_predecessor_and_distance() but finds
    negative cycles on any component by first adding a new node connected to
    every node, and starting bellman_ford_predecessor_and_distance on that
    node.  It then removes that extra node.
networkx.neighbor_degree
Python Library Documentation: module networkx.algorithms.assortativity.neighbor_degree in networkx.algorithms.assortativity

NAME
    networkx.algorithms.assortativity.neighbor_degree

FUNCTIONS
    average_neighbor_degree(G, source='out', target='out', nodes=None, weight=None, *, backend=None, **backend_kwargs)
        Returns the average degree of the neighborhood of each node.

        In an undirected graph, the neighborhood `N(i)` of node `i` contains the
        nodes that are connected to `i` by an edge.

        For directed graphs, `N(i)` is defined according to the parameter `source`:

            - if source is 'in', then `N(i)` consists of predecessors of node `i`.
            - if source is 'out', then `N(i)` consists of successors of node `i`.
            - if source is 'in+out', then `N(i)` is both predecessors and successors.

        The average neighborhood degree of a node `i` is

        .. math::

            k_{nn,i} = \frac{1}{|N(i)|} \sum_{j \in N(i)} k_j

        where `N(i)` are the neighbors of node `i` and `k_j` is
        the degree of node `j` which belongs to `N(i)`. For weighted
        graphs, an analogous measure can be defined [1]_,

        .. math::

            k_{nn,i}^{w} = \frac{1}{s_i} \sum_{j \in N(i)} w_{ij} k_j

        where `s_i` is the weighted degree of node `i`, `w_{ij}`
        is the weight of the edge that links `i` and `j` and
        `N(i)` are the neighbors of node `i`.


        Parameters
        ----------
        G : NetworkX graph

        source : string ("in"|"out"|"in+out"), optional (default="out")
           Directed graphs only.
           Use "in"- or "out"-neighbors of source node.

        target : string ("in"|"out"|"in+out"), optional (default="out")
           Directed graphs only.
           Use "in"- or "out"-degree for target node.

        nodes : list or iterable, optional (default=G.nodes)
            Compute neighbor degree only for specified nodes.

        weight : string or None, optional (default=None)
           The edge attribute that holds the numerical value used as a weight.
           If None, then each edge has weight 1.

        Returns
        -------
        d: dict
           A dictionary keyed by node to the average degree of its neighbors.

        Raises
        ------
        NetworkXError
            If either `source` or `target` are not one of 'in', 'out', or 'in+out'.
            If either `source` or `target` is passed for an undirected graph.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> G.edges[0, 1]["weight"] = 5
        >>> G.edges[2, 3]["weight"] = 3

        >>> nx.average_neighbor_degree(G)
        {0: 2.0, 1: 1.5, 2: 1.5, 3: 2.0}
        >>> nx.average_neighbor_degree(G, weight="weight")
        {0: 2.0, 1: 1.1666666666666667, 2: 1.25, 3: 2.0}

        >>> G = nx.DiGraph()
        >>> nx.add_path(G, [0, 1, 2, 3])
        >>> nx.average_neighbor_degree(G, source="in", target="in")
        {0: 0.0, 1: 0.0, 2: 1.0, 3: 1.0}

        >>> nx.average_neighbor_degree(G, source="out", target="out")
        {0: 1.0, 1: 1.0, 2: 0.0, 3: 0.0}

        See Also
        --------
        average_degree_connectivity

        References
        ----------
        .. [1] A. Barrat, M. Barthélemy, R. Pastor-Satorras, and A. Vespignani,
           "The architecture of complex weighted networks".
           PNAS 101 (11): 3747–3752 (2004).

DATA
    __all__ = ['average_neighbor_degree']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\assortativity\neighbor_degree.py

networkx.neighbors
Python Library Documentation: function neighbors in module networkx.classes.function

neighbors(G, n)
    Returns an iterator over all neighbors of node n.

    This function wraps the :func:`G.neighbors <networkx.Graph.neighbors>` function.
networkx.network_simplex
Python Library Documentation: function network_simplex in module networkx.algorithms.flow.networksimplex

network_simplex(G, demand='demand', capacity='capacity', weight='weight', *, backend=None, **backend_kwargs)
    Find a minimum cost flow satisfying all demands in digraph G.

    This is a primal network simplex algorithm that uses the leaving
    arc rule to prevent cycling.

    G is a digraph with edge costs and capacities and in which nodes
    have demand, i.e., they want to send or receive some amount of
    flow. A negative demand means that the node wants to send flow, a
    positive demand means that the node want to receive flow. A flow on
    the digraph G satisfies all demand if the net flow into each node
    is equal to the demand of that node.

    Parameters
    ----------
    G : NetworkX graph
        DiGraph on which a minimum cost flow satisfying all demands is
        to be found.

    demand : string
        Nodes of the graph G are expected to have an attribute demand
        that indicates how much flow a node wants to send (negative
        demand) or receive (positive demand). Note that the sum of the
        demands should be 0 otherwise the problem in not feasible. If
        this attribute is not present, a node is considered to have 0
        demand. Default value: 'demand'.

    capacity : string
        Edges of the graph G are expected to have an attribute capacity
        that indicates how much flow the edge can support. If this
        attribute is not present, the edge is considered to have
        infinite capacity. Default value: 'capacity'.

    weight : string
        Edges of the graph G are expected to have an attribute weight
        that indicates the cost incurred by sending one unit of flow on
        that edge. If not present, the weight is considered to be 0.
        Default value: 'weight'.

    Returns
    -------
    flowCost : integer, float
        Cost of a minimum cost flow satisfying all demands.

    flowDict : dictionary
        Dictionary of dictionaries keyed by nodes such that
        flowDict[u][v] is the flow edge (u, v).

    Raises
    ------
    NetworkXError
        This exception is raised if the input graph is not directed or
        not connected.

    NetworkXUnfeasible
        This exception is raised in the following situations:

            * The sum of the demands is not zero. Then, there is no
              flow satisfying all demands.
            * There is no flow satisfying all demand.

    NetworkXUnbounded
        This exception is raised if the digraph G has a cycle of
        negative cost and infinite capacity. Then, the cost of a flow
        satisfying all demands is unbounded below.

    Notes
    -----
    This algorithm is not guaranteed to work if edge weights or demands
    are floating point numbers (overflows and roundoff errors can
    cause problems). As a workaround you can use integer numbers by
    multiplying the relevant edge attributes by a convenient
    constant factor (eg 100).

    See also
    --------
    cost_of_flow, max_flow_min_cost, min_cost_flow, min_cost_flow_cost

    Examples
    --------
    A simple example of a min cost flow problem.

    >>> G = nx.DiGraph()
    >>> G.add_node("a", demand=-5)
    >>> G.add_node("d", demand=5)
    >>> G.add_edge("a", "b", weight=3, capacity=4)
    >>> G.add_edge("a", "c", weight=6, capacity=10)
    >>> G.add_edge("b", "d", weight=1, capacity=9)
    >>> G.add_edge("c", "d", weight=2, capacity=5)
    >>> flowCost, flowDict = nx.network_simplex(G)
    >>> flowCost
    24
    >>> flowDict
    {'a': {'b': 4, 'c': 1}, 'd': {}, 'b': {'d': 4}, 'c': {'d': 1}}

    The mincost flow algorithm can also be used to solve shortest path
    problems. To find the shortest path between two nodes u and v,
    give all edges an infinite capacity, give node u a demand of -1 and
    node v a demand a 1. Then run the network simplex. The value of a
    min cost flow will be the distance between u and v and edges
    carrying positive flow will indicate the path.

    >>> G = nx.DiGraph()
    >>> G.add_weighted_edges_from(
    ...     [
    ...         ("s", "u", 10),
    ...         ("s", "x", 5),
    ...         ("u", "v", 1),
    ...         ("u", "x", 2),
    ...         ("v", "y", 1),
    ...         ("x", "u", 3),
    ...         ("x", "v", 5),
    ...         ("x", "y", 2),
    ...         ("y", "s", 7),
    ...         ("y", "v", 6),
    ...     ]
    ... )
    >>> G.add_node("s", demand=-1)
    >>> G.add_node("v", demand=1)
    >>> flowCost, flowDict = nx.network_simplex(G)
    >>> flowCost == nx.shortest_path_length(G, "s", "v", weight="weight")
    True
    >>> sorted([(u, v) for u in flowDict for v in flowDict[u] if flowDict[u][v] > 0])
    [('s', 'x'), ('u', 'v'), ('x', 'u')]
    >>> nx.shortest_path(G, "s", "v", weight="weight")
    ['s', 'x', 'u', 'v']

    It is possible to change the name of the attributes used for the
    algorithm.

    >>> G = nx.DiGraph()
    >>> G.add_node("p", spam=-4)
    >>> G.add_node("q", spam=2)
    >>> G.add_node("a", spam=-2)
    >>> G.add_node("d", spam=-1)
    >>> G.add_node("t", spam=2)
    >>> G.add_node("w", spam=3)
    >>> G.add_edge("p", "q", cost=7, vacancies=5)
    >>> G.add_edge("p", "a", cost=1, vacancies=4)
    >>> G.add_edge("q", "d", cost=2, vacancies=3)
    >>> G.add_edge("t", "q", cost=1, vacancies=2)
    >>> G.add_edge("a", "t", cost=2, vacancies=4)
    >>> G.add_edge("d", "w", cost=3, vacancies=4)
    >>> G.add_edge("t", "w", cost=4, vacancies=1)
    >>> flowCost, flowDict = nx.network_simplex(
    ...     G, demand="spam", capacity="vacancies", weight="cost"
    ... )
    >>> flowCost
    37
    >>> flowDict
    {'p': {'q': 2, 'a': 2}, 'q': {'d': 1}, 'a': {'t': 4}, 'd': {'w': 2}, 't': {'q': 1, 'w': 1}, 'w': {}}

    References
    ----------
    .. [1] Z. Kiraly, P. Kovacs.
           Efficient implementation of minimum-cost flow algorithms.
           Acta Universitatis Sapientiae, Informatica 4(1):67--118. 2012.
    .. [2] R. Barr, F. Glover, D. Klingman.
           Enhancement of spanning tree labeling procedures for network
           optimization.
           INFOR 17(1):16--34. 1979.
networkx.newman_watts_strogatz_graph
Python Library Documentation: function newman_watts_strogatz_graph in module networkx.generators.random_graphs

newman_watts_strogatz_graph(n, k, p, seed=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns a Newman–Watts–Strogatz small-world graph.

    Parameters
    ----------
    n : int
        The number of nodes.
    k : int
        Each node is joined with its `k` nearest neighbors in a ring
        topology.
    p : float
        The probability of adding a new edge for each edge.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Notes
    -----
    First create a ring over $n$ nodes [1]_.  Then each node in the ring is
    connected with its $k$ nearest neighbors (or $k - 1$ neighbors if $k$
    is odd).  Then shortcuts are created by adding new edges as follows: for
    each edge $(u, v)$ in the underlying "$n$-ring with $k$ nearest
    neighbors" with probability $p$ add a new edge $(u, w)$ with
    randomly-chosen existing node $w$.  In contrast with
    :func:`watts_strogatz_graph`, no edges are removed.

    See Also
    --------
    watts_strogatz_graph

    References
    ----------
    .. [1] M. E. J. Newman and D. J. Watts,
       Renormalization group analysis of the small-world network model,
       Physics Letters A, 263, 341, 1999.
       https://doi.org/10.1016/S0375-9601(99)00757-4
networkx.node_attribute_xy
Python Library Documentation: function node_attribute_xy in module networkx.algorithms.assortativity.pairs

node_attribute_xy(G, attribute, nodes=None, *, backend=None, **backend_kwargs)
    Yields 2-tuples of node attribute values for all edges in `G`.

    This generator yields, for each edge in `G` incident to a node in `nodes`,
    a 2-tuple of form ``(attribute value,  attribute value)`` for the parameter
    specified node-attribute.

    Parameters
    ----------
    G: NetworkX graph

    attribute: key
        The node attribute key.

    nodes: list or iterable (optional)
        Use only edges that are incident to specified nodes.
        The default is all nodes.

    Yields
    ------
    (x, y): 2-tuple
        Generates 2-tuple of (attribute, attribute) values.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_node(1, color="red")
    >>> G.add_node(2, color="blue")
    >>> G.add_node(3, color="green")
    >>> G.add_edge(1, 2)
    >>> list(nx.node_attribute_xy(G, "color"))
    [('red', 'blue')]

    Notes
    -----
    For undirected graphs, each edge is produced twice, once for each edge
    representation (u, v) and (v, u), with the exception of self-loop edges
    which only appear once.
networkx.node_boundary
Python Library Documentation: function node_boundary in module networkx.algorithms.boundary

node_boundary(G, nbunch1, nbunch2=None, *, backend=None, **backend_kwargs)
    Returns the node boundary of `nbunch1`.

    The *node boundary* of a set *S* with respect to a set *T* is the
    set of nodes *v* in *T* such that for some *u* in *S*, there is an
    edge joining *u* to *v*. If *T* is not specified, it is assumed to
    be the set of all nodes not in *S*.

    Parameters
    ----------
    G : NetworkX graph

    nbunch1 : iterable
        Iterable of nodes in the graph representing the set of nodes
        whose node boundary will be returned. (This is the set *S* from
        the definition above.)

    nbunch2 : iterable
        Iterable of nodes representing the target (or "exterior") set of
        nodes. (This is the set *T* from the definition above.) If not
        specified, this is assumed to be the set of all nodes in `G`
        not in `nbunch1`.

    Returns
    -------
    set
        The node boundary of `nbunch1` with respect to `nbunch2`.

    Examples
    --------
    >>> G = nx.wheel_graph(6)

    When nbunch2=None:

    >>> list(nx.node_boundary(G, (3, 4)))
    [0, 2, 5]

    When nbunch2 is given:

    >>> list(nx.node_boundary(G, (3, 4), (0, 1, 5)))
    [0, 5]

    Notes
    -----
    Any element of `nbunch` that is not in the graph `G` will be
    ignored.

    `nbunch1` and `nbunch2` are usually meant to be disjoint, but in
    the interest of speed and generality, that is not required here.
networkx.node_classification
Python Library Documentation: module networkx.algorithms.node_classification in networkx.algorithms

NAME
    networkx.algorithms.node_classification - This module provides the functions for node classification problem.

DESCRIPTION
    The functions in this module are not imported
    into the top level `networkx` namespace.
    You can access these functions by importing
    the `networkx.algorithms.node_classification` modules,
    then accessing the functions as attributes of `node_classification`.
    For example:

      >>> from networkx.algorithms import node_classification
      >>> G = nx.path_graph(4)
      >>> G.edges()
      EdgeView([(0, 1), (1, 2), (2, 3)])
      >>> G.nodes[0]["label"] = "A"
      >>> G.nodes[3]["label"] = "B"
      >>> node_classification.harmonic_function(G)
      ['A', 'A', 'B', 'B']

    References
    ----------
    Zhu, X., Ghahramani, Z., & Lafferty, J. (2003, August).
    Semi-supervised learning using gaussian fields and harmonic functions.
    In ICML (Vol. 3, pp. 912-919).

FUNCTIONS
    harmonic_function(G, max_iter=30, label_name='label', *, backend=None, **backend_kwargs)
        Node classification by Harmonic function

        Function for computing Harmonic function algorithm by Zhu et al.

        Parameters
        ----------
        G : NetworkX Graph
        max_iter : int
            maximum number of iterations allowed
        label_name : string
            name of target labels to predict

        Returns
        -------
        predicted : list
            List of length ``len(G)`` with the predicted labels for each node.

        Raises
        ------
        NetworkXError
            If no nodes in `G` have attribute `label_name`.

        Examples
        --------
        >>> from networkx.algorithms import node_classification
        >>> G = nx.path_graph(4)
        >>> G.nodes[0]["label"] = "A"
        >>> G.nodes[3]["label"] = "B"
        >>> G.nodes(data=True)
        NodeDataView({0: {'label': 'A'}, 1: {}, 2: {}, 3: {'label': 'B'}})
        >>> G.edges()
        EdgeView([(0, 1), (1, 2), (2, 3)])
        >>> predicted = node_classification.harmonic_function(G)
        >>> predicted
        ['A', 'A', 'B', 'B']

        References
        ----------
        Zhu, X., Ghahramani, Z., & Lafferty, J. (2003, August).
        Semi-supervised learning using gaussian fields and harmonic functions.
        In ICML (Vol. 3, pp. 912-919).

    local_and_global_consistency(G, alpha=0.99, max_iter=30, label_name='label', *, backend=None, **backend_kwargs)
        Node classification by Local and Global Consistency

        Function for computing Local and global consistency algorithm by Zhou et al.

        Parameters
        ----------
        G : NetworkX Graph
        alpha : float
            Clamping factor
        max_iter : int
            Maximum number of iterations allowed
        label_name : string
            Name of target labels to predict

        Returns
        -------
        predicted : list
            List of length ``len(G)`` with the predicted labels for each node.

        Raises
        ------
        NetworkXError
            If no nodes in `G` have attribute `label_name`.

        Examples
        --------
        >>> from networkx.algorithms import node_classification
        >>> G = nx.path_graph(4)
        >>> G.nodes[0]["label"] = "A"
        >>> G.nodes[3]["label"] = "B"
        >>> G.nodes(data=True)
        NodeDataView({0: {'label': 'A'}, 1: {}, 2: {}, 3: {'label': 'B'}})
        >>> G.edges()
        EdgeView([(0, 1), (1, 2), (2, 3)])
        >>> predicted = node_classification.local_and_global_consistency(G)
        >>> predicted
        ['A', 'A', 'B', 'B']

        References
        ----------
        Zhou, D., Bousquet, O., Lal, T. N., Weston, J., & Schölkopf, B. (2004).
        Learning with local and global consistency.
        Advances in neural information processing systems, 16(16), 321-328.

DATA
    __all__ = ['harmonic_function', 'local_and_global_consistency']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\node_classification.py

networkx.node_clique_number
Python Library Documentation: function node_clique_number in module networkx.algorithms.clique

node_clique_number(G, nodes=None, cliques=None, separate_nodes=False, *, backend=None, **backend_kwargs)
    Returns the size of the largest maximal clique containing each given node.

    Returns a single or list depending on input nodes.
    An optional list of cliques can be input if already computed.

    Parameters
    ----------
    G : NetworkX graph
        An undirected graph.

    cliques : list, optional (default=None)
        A list of cliques, each of which is itself a list of nodes.
        If not specified, the list of all cliques will be computed
        using :func:`find_cliques`.

    Returns
    -------
    int or dict
        If `nodes` is a single node, returns the size of the
        largest maximal clique in `G` containing that node.
        Otherwise return a dict keyed by node to the size
        of the largest maximal clique containing that node.

    See Also
    --------
    find_cliques
        find_cliques yields the maximal cliques of G.
        It accepts a `nodes` argument which restricts consideration to
        maximal cliques containing all the given `nodes`.
        The search for the cliques is optimized for `nodes`.
networkx.node_connected_component
Python Library Documentation: function node_connected_component in module networkx.algorithms.components.connected

node_connected_component(G, n, *, backend=None, **backend_kwargs)
    Returns the set of nodes in the component of graph containing node n.

    Parameters
    ----------
    G : NetworkX Graph
       An undirected graph.

    n : node label
       A node in G

    Returns
    -------
    comp : set
       A set of nodes in the component of G containing node n.

    Raises
    ------
    NetworkXNotImplemented
        If G is directed.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (1, 2), (5, 6), (3, 4)])
    >>> nx.node_connected_component(G, 0)  # nodes of component that contains node 0
    {0, 1, 2}

    See Also
    --------
    connected_components

    Notes
    -----
    For undirected graphs only.
networkx.node_connectivity
Python Library Documentation: function node_connectivity in module networkx.algorithms.connectivity.connectivity

node_connectivity(G, s=None, t=None, flow_func=None, *, backend=None, **backend_kwargs)
    Returns node connectivity for a graph or digraph G.

    Node connectivity is equal to the minimum number of nodes that
    must be removed to disconnect G or render it trivial. If source
    and target nodes are provided, this function returns the local node
    connectivity: the minimum number of nodes that must be removed to break
    all paths from source to target in G.

    Parameters
    ----------
    G : NetworkX graph
        Undirected graph

    s : node
        Source node. Optional. Default value: None.

    t : node
        Target node. Optional. Default value: None.

    flow_func : function
        A function for computing the maximum flow among a pair of nodes.
        The function has to accept at least three parameters: a Digraph,
        a source node, and a target node. And return a residual network
        that follows NetworkX conventions (see :meth:`maximum_flow` for
        details). If flow_func is None, the default maximum flow function
        (:meth:`edmonds_karp`) is used. See below for details. The
        choice of the default function may change from version
        to version and should not be relied on. Default value: None.

    Returns
    -------
    K : integer
        Node connectivity of G, or local node connectivity if source
        and target are provided.

    Examples
    --------
    >>> # Platonic icosahedral graph is 5-node-connected
    >>> G = nx.icosahedral_graph()
    >>> nx.node_connectivity(G)
    5

    You can use alternative flow algorithms for the underlying maximum
    flow computation. In dense networks the algorithm
    :meth:`shortest_augmenting_path` will usually perform better
    than the default :meth:`edmonds_karp`, which is faster for
    sparse networks with highly skewed degree distributions. Alternative
    flow functions have to be explicitly imported from the flow package.

    >>> from networkx.algorithms.flow import shortest_augmenting_path
    >>> nx.node_connectivity(G, flow_func=shortest_augmenting_path)
    5

    If you specify a pair of nodes (source and target) as parameters,
    this function returns the value of local node connectivity.

    >>> nx.node_connectivity(G, 3, 7)
    5

    If you need to perform several local computations among different
    pairs of nodes on the same graph, it is recommended that you reuse
    the data structures used in the maximum flow computations. See
    :meth:`local_node_connectivity` for details.

    Notes
    -----
    This is a flow based implementation of node connectivity. The
    algorithm works by solving $O((n-\delta-1+\delta(\delta-1)/2))$
    maximum flow problems on an auxiliary digraph. Where $\delta$
    is the minimum degree of G. For details about the auxiliary
    digraph and the computation of local node connectivity see
    :meth:`local_node_connectivity`. This implementation is based
    on algorithm 11 in [1]_.

    See also
    --------
    :meth:`local_node_connectivity`
    :meth:`edge_connectivity`
    :meth:`maximum_flow`
    :meth:`edmonds_karp`
    :meth:`preflow_push`
    :meth:`shortest_augmenting_path`

    References
    ----------
    .. [1] Abdol-Hossein Esfahanian. Connectivity Algorithms.
        http://www.cse.msu.edu/~cse835/Papers/Graph_connectivity_revised.pdf
networkx.node_degree_xy
Python Library Documentation: function node_degree_xy in module networkx.algorithms.assortativity.pairs

node_degree_xy(G, x='out', y='in', weight=None, nodes=None, *, backend=None, **backend_kwargs)
    Yields 2-tuples of ``(degree, degree)`` values for edges in `G`.

    This generator yields, for each edge in `G` incident to a node in `nodes`,
    a 2-tuple of form ``(degree, degree)``. The node degrees are weighted
    when a `weight` attribute is specified.

    Parameters
    ----------
    G: NetworkX graph

    x: string ('in','out')
       The degree type for source node (directed graphs only).

    y: string ('in','out')
       The degree type for target node (directed graphs only).

    weight: string or None, optional (default=None)
       The edge attribute that holds the numerical value used
       as a weight.  If None, then each edge has weight 1.
       The degree is the sum of the edge weights adjacent to the node.

    nodes: list or iterable (optional)
        Use only edges that are adjacency to specified nodes.
        The default is all nodes.

    Yields
    ------
    (x, y): 2-tuple
        Generates 2-tuple of (degree, degree) values.

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_edge(1, 2)
    >>> list(nx.node_degree_xy(G, x="out", y="in"))
    [(1, 1)]
    >>> list(nx.node_degree_xy(G, x="in", y="out"))
    [(0, 0)]

    Notes
    -----
    For undirected graphs, each edge is produced twice, once for each edge
    representation (u, v) and (v, u), with the exception of self-loop edges
    which only appear once.
networkx.node_disjoint_paths
Python Library Documentation: function node_disjoint_paths in module networkx.algorithms.connectivity.disjoint_paths

node_disjoint_paths(G, s, t, flow_func=None, cutoff=None, auxiliary=None, residual=None, *, backend=None, **backend_kwargs)
    Computes node disjoint paths between source and target.

    Node disjoint paths are paths that only share their first and last
    nodes. The number of node independent paths between two nodes is
    equal to their local node connectivity.

    Parameters
    ----------
    G : NetworkX graph

    s : node
        Source node.

    t : node
        Target node.

    flow_func : function
        A function for computing the maximum flow among a pair of nodes.
        The function has to accept at least three parameters: a Digraph,
        a source node, and a target node. And return a residual network
        that follows NetworkX conventions (see :meth:`maximum_flow` for
        details). If flow_func is None, the default maximum flow function
        (:meth:`edmonds_karp`) is used. See below for details. The choice
        of the default function may change from version to version and
        should not be relied on. Default value: None.

    cutoff : integer or None (default: None)
        Maximum number of paths to yield. If specified, the maximum flow
        algorithm will terminate when the flow value reaches or exceeds the
        cutoff. This only works for flows that support the cutoff parameter
        (most do) and is ignored otherwise.

    auxiliary : NetworkX DiGraph
        Auxiliary digraph to compute flow based node connectivity. It has
        to have a graph attribute called mapping with a dictionary mapping
        node names in G and in the auxiliary digraph. If provided
        it will be reused instead of recreated. Default value: None.

    residual : NetworkX DiGraph
        Residual network to compute maximum flow. If provided it will be
        reused instead of recreated. Default value: None.

    Returns
    -------
    paths : generator
        Generator of node disjoint paths.

    Raises
    ------
    NetworkXNoPath
        If there is no path between source and target.

    NetworkXError
        If source or target are not in the graph G.

    Examples
    --------
    We use in this example the platonic icosahedral graph, which has node
    connectivity 5, thus there are 5 node disjoint paths between any pair
    of non neighbor nodes.

    >>> G = nx.icosahedral_graph()
    >>> len(list(nx.node_disjoint_paths(G, 0, 6)))
    5

    If you need to compute node disjoint paths between several pairs of
    nodes in the same graph, it is recommended that you reuse the
    data structures that NetworkX uses in the computation: the
    auxiliary digraph for node connectivity and node cuts, and the
    residual network for the underlying maximum flow computation.

    Example of how to compute node disjoint paths reusing the data
    structures:

    >>> # You also have to explicitly import the function for
    >>> # building the auxiliary digraph from the connectivity package
    >>> from networkx.algorithms.connectivity import build_auxiliary_node_connectivity
    >>> H = build_auxiliary_node_connectivity(G)
    >>> # And the function for building the residual network from the
    >>> # flow package
    >>> from networkx.algorithms.flow import build_residual_network
    >>> # Note that the auxiliary digraph has an edge attribute named capacity
    >>> R = build_residual_network(H, "capacity")
    >>> # Reuse the auxiliary digraph and the residual network by passing them
    >>> # as arguments
    >>> len(list(nx.node_disjoint_paths(G, 0, 6, auxiliary=H, residual=R)))
    5

    You can also use alternative flow algorithms for computing node disjoint
    paths. For instance, in dense networks the algorithm
    :meth:`shortest_augmenting_path` will usually perform better than
    the default :meth:`edmonds_karp` which is faster for sparse
    networks with highly skewed degree distributions. Alternative flow
    functions have to be explicitly imported from the flow package.

    >>> from networkx.algorithms.flow import shortest_augmenting_path
    >>> len(list(nx.node_disjoint_paths(G, 0, 6, flow_func=shortest_augmenting_path)))
    5

    Notes
    -----
    This is a flow based implementation of node disjoint paths. We compute
    the maximum flow between source and target on an auxiliary directed
    network. The saturated edges in the residual network after running the
    maximum flow algorithm correspond to node disjoint paths between source
    and target in the original network. This function handles both directed
    and undirected graphs, and can use all flow algorithms from NetworkX flow
    package.

    See also
    --------
    :meth:`edge_disjoint_paths`
    :meth:`node_connectivity`
    :meth:`maximum_flow`
    :meth:`edmonds_karp`
    :meth:`preflow_push`
    :meth:`shortest_augmenting_path`
networkx.node_expansion
Python Library Documentation: function node_expansion in module networkx.algorithms.cuts

node_expansion(G, S, *, backend=None, **backend_kwargs)
    Returns the node expansion of the set `S`.

    The *node expansion* is the quotient of the size of the node
    boundary of *S* and the cardinality of *S*. [1]

    Parameters
    ----------
    G : NetworkX graph

    S : collection
        A collection of nodes in `G`.

    Returns
    -------
    number
        The node expansion of the set `S`.

    See also
    --------
    boundary_expansion
    edge_expansion
    mixing_expansion

    References
    ----------
    .. [1] Vadhan, Salil P.
           "Pseudorandomness."
           *Foundations and Trends
           in Theoretical Computer Science* 7.1–3 (2011): 1–336.
           <https://doi.org/10.1561/0400000010>
networkx.nodes
Python Library Documentation: function nodes in module networkx.classes.function

nodes(G)
    Returns a NodeView over the graph nodes.

    This function wraps the :func:`G.nodes <networkx.Graph.nodes>` property.
networkx.nodes_with_selfloops
Python Library Documentation: function nodes_with_selfloops in module networkx.classes.function

nodes_with_selfloops(G)
    Returns an iterator over nodes with self loops.

    A node with a self loop has an edge with both ends adjacent
    to that node.

    Returns
    -------
    nodelist : iterator
        A iterator over nodes with self loops.

    See Also
    --------
    selfloop_edges, number_of_selfloops

    Examples
    --------
    >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
    >>> G.add_edge(1, 1)
    >>> G.add_edge(1, 2)
    >>> list(nx.nodes_with_selfloops(G))
    [1]
networkx.non_edges
Python Library Documentation: function non_edges in module networkx.classes.function

non_edges(graph)
    Returns the nonexistent edges in the graph.

    Parameters
    ----------
    graph : NetworkX graph.
        Graph to find nonexistent edges.

    Returns
    -------
    non_edges : iterator
        Iterator of edges that are not in the graph.
networkx.non_neighbors
Python Library Documentation: function non_neighbors in module networkx.classes.function

non_neighbors(graph, node)
    Returns the non-neighbors of the node in the graph.

    Parameters
    ----------
    graph : NetworkX graph
        Graph to find neighbors.

    node : node
        The node whose neighbors will be returned.

    Returns
    -------
    non_neighbors : set
        Set of nodes in the graph that are not neighbors of the node.
networkx.non_randomness
Python Library Documentation: function non_randomness in module networkx.algorithms.non_randomness

non_randomness(G, k=None, weight='weight', *, backend=None, **backend_kwargs)
    Compute the non-randomness of graph G.

    The first returned value nr is the sum of non-randomness values of all
    edges within the graph (where the non-randomness of an edge tends to be
    small when the two nodes linked by that edge are from two different
    communities).

    The second computed value nr_rd is a relative measure that indicates
    to what extent graph G is different from random graphs in terms
    of probability. When it is close to 0, the graph tends to be more
    likely generated by an Erdos Renyi model.

    Parameters
    ----------
    G : NetworkX graph
        Graph must be symmetric, connected, and without self-loops.

    k : int
        The number of communities in G.
        If k is not set, the function will use a default community
        detection algorithm to set it.

    weight : string or None, optional (default=None)
        The name of an edge attribute that holds the numerical value used
        as a weight. If None, then each edge has weight 1, i.e., the graph is
        binary.

    Returns
    -------
    non-randomness : (float, float) tuple
        Non-randomness, Relative non-randomness w.r.t.
        Erdos Renyi random graphs.

    Raises
    ------
    NetworkXException
        if the input graph is not connected.
    NetworkXError
        if the input graph contains self-loops or if graph has no edges.

    Examples
    --------
    >>> G = nx.karate_club_graph()
    >>> nr, nr_rd = nx.non_randomness(G, 2)
    >>> nr, nr_rd = nx.non_randomness(G, 2, "weight")

    Notes
    -----
    This computes Eq. (4.4) and (4.5) in Ref. [1]_.

    If a weight field is passed, this algorithm will use the eigenvalues
    of the weighted adjacency matrix to compute Eq. (4.4) and (4.5).

    References
    ----------
    .. [1] Xiaowei Ying and Xintao Wu,
           On Randomness Measures for Social Networks,
           SIAM International Conference on Data Mining. 2009
networkx.nonisomorphic_trees
Python Library Documentation: function nonisomorphic_trees in module networkx.generators.nonisomorphic_trees

nonisomorphic_trees(order, create='graph', *, backend=None, **backend_kwargs)
    Generates lists of nonisomorphic trees

    Parameters
    ----------
    order : int
       order of the desired tree(s)

    create : one of {"graph", "matrix"} (default="graph")
       If ``"graph"`` is selected a list of ``Graph`` instances will be returned,
       if matrix is selected a list of adjacency matrices will be returned.

       .. deprecated:: 3.3

          The `create` argument is deprecated and will be removed in NetworkX
          version 3.5. In the future, `nonisomorphic_trees` will yield graph
          instances by default. To generate adjacency matrices, call
          ``nx.to_numpy_array`` on the output, e.g.::

             [nx.to_numpy_array(G) for G in nx.nonisomorphic_trees(N)]

    Yields
    ------
    list
       A list of nonisomorphic trees, in one of two formats depending on the
       value of the `create` parameter:
       - ``create="graph"``: yields a list of `networkx.Graph` instances
       - ``create="matrix"``: yields a list of list-of-lists representing adjacency matrices
networkx.normalized_cut_size
Python Library Documentation: function normalized_cut_size in module networkx.algorithms.cuts

normalized_cut_size(G, S, T=None, weight=None, *, backend=None, **backend_kwargs)
    Returns the normalized size of the cut between two sets of nodes.

    The *normalized cut size* is the cut size times the sum of the
    reciprocal sizes of the volumes of the two sets. [1]

    Parameters
    ----------
    G : NetworkX graph

    S : collection
        A collection of nodes in `G`.

    T : collection
        A collection of nodes in `G`.

    weight : object
        Edge attribute key to use as weight. If not specified, edges
        have weight one.

    Returns
    -------
    number
        The normalized cut size between the two sets `S` and `T`.

    Notes
    -----
    In a multigraph, the cut size is the total weight of edges including
    multiplicity.

    See also
    --------
    conductance
    cut_size
    edge_expansion
    volume

    References
    ----------
    .. [1] David Gleich.
           *Hierarchical Directed Spectral Graph Partitioning*.
           <https://www.cs.purdue.edu/homes/dgleich/publications/Gleich%202005%20-%20hierarchical%20directed%20spectral.pdf>
networkx.normalized_laplacian_matrix
Python Library Documentation: function normalized_laplacian_matrix in module networkx.linalg.laplacianmatrix

normalized_laplacian_matrix(G, nodelist=None, weight='weight', *, backend=None, **backend_kwargs)
    Returns the normalized Laplacian matrix of G.

    The normalized graph Laplacian is the matrix

    .. math::

        N = D^{-1/2} L D^{-1/2}

    where `L` is the graph Laplacian and `D` is the diagonal matrix of
    node degrees [1]_.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    nodelist : list, optional
       The rows and columns are ordered according to the nodes in nodelist.
       If nodelist is None, then the ordering is produced by G.nodes().

    weight : string or None, optional (default='weight')
       The edge data key used to compute each value in the matrix.
       If None, then each edge has weight 1.

    Returns
    -------
    N : SciPy sparse array
      The normalized Laplacian matrix of G.

    Notes
    -----
    For MultiGraph, the edges weights are summed.
    See :func:`to_numpy_array` for other options.

    If the Graph contains selfloops, D is defined as ``diag(sum(A, 1))``, where A is
    the adjacency matrix [2]_.

    This calculation uses the out-degree of the graph `G`. To use the
    in-degree for calculations instead, use `G.reverse(copy=False)` and
    take the transpose.

    For an unnormalized output, use `laplacian_matrix`.

    Examples
    --------

    >>> import numpy as np
    >>> edges = [
    ...     (1, 2),
    ...     (2, 1),
    ...     (2, 4),
    ...     (4, 3),
    ...     (3, 4),
    ... ]
    >>> DiG = nx.DiGraph(edges)
    >>> print(nx.normalized_laplacian_matrix(DiG).toarray())
    [[ 1.         -0.70710678  0.          0.        ]
     [-0.70710678  1.         -0.70710678  0.        ]
     [ 0.          0.          1.         -1.        ]
     [ 0.          0.         -1.          1.        ]]

    Notice that node 4 is represented by the third column and row. This is because
    by default the row/column order is the order of `G.nodes` (i.e. the node added
    order -- in the edgelist, 4 first appears in (2, 4), before node 3 in edge (4, 3).)
    To control the node order of the matrix, use the `nodelist` argument.

    >>> print(nx.normalized_laplacian_matrix(DiG, nodelist=[1, 2, 3, 4]).toarray())
    [[ 1.         -0.70710678  0.          0.        ]
     [-0.70710678  1.          0.         -0.70710678]
     [ 0.          0.          1.         -1.        ]
     [ 0.          0.         -1.          1.        ]]
    >>> G = nx.Graph(edges)
    >>> print(nx.normalized_laplacian_matrix(G).toarray())
    [[ 1.         -0.70710678  0.          0.        ]
     [-0.70710678  1.         -0.5         0.        ]
     [ 0.         -0.5         1.         -0.70710678]
     [ 0.          0.         -0.70710678  1.        ]]

    See Also
    --------
    laplacian_matrix
    normalized_laplacian_spectrum
    directed_laplacian_matrix
    directed_combinatorial_laplacian_matrix

    References
    ----------
    .. [1] Fan Chung-Graham, Spectral Graph Theory,
       CBMS Regional Conference Series in Mathematics, Number 92, 1997.
    .. [2] Steve Butler, Interlacing For Weighted Graphs Using The Normalized
       Laplacian, Electronic Journal of Linear Algebra, Volume 16, pp. 90-98,
       March 2007.
    .. [3] Langville, Amy N., and Carl D. Meyer. Google’s PageRank and Beyond:
       The Science of Search Engine Rankings. Princeton University Press, 2006.
networkx.normalized_laplacian_spectrum
Python Library Documentation: function normalized_laplacian_spectrum in module networkx.linalg.spectrum

normalized_laplacian_spectrum(G, weight='weight', *, backend=None, **backend_kwargs)
    Return eigenvalues of the normalized Laplacian of G

    Parameters
    ----------
    G : graph
       A NetworkX graph

    weight : string or None, optional (default='weight')
       The edge data key used to compute each value in the matrix.
       If None, then each edge has weight 1.

    Returns
    -------
    evals : NumPy array
      Eigenvalues

    Notes
    -----
    For MultiGraph/MultiDiGraph, the edges weights are summed.
    See to_numpy_array for other options.

    See Also
    --------
    normalized_laplacian_matrix
networkx.null_graph
Python Library Documentation: function null_graph in module networkx.generators.classic

null_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Null graph with no nodes or edges.

    See empty_graph for the use of create_using.
networkx.number_attracting_components
Python Library Documentation: function number_attracting_components in module networkx.algorithms.components.attracting

number_attracting_components(G, *, backend=None, **backend_kwargs)
    Returns the number of attracting components in `G`.

    Parameters
    ----------
    G : DiGraph, MultiDiGraph
        The graph to be analyzed.

    Returns
    -------
    n : int
        The number of attracting components in G.

    Raises
    ------
    NetworkXNotImplemented
        If the input graph is undirected.

    See Also
    --------
    attracting_components
    is_attracting_component
networkx.number_connected_components
Python Library Documentation: function number_connected_components in module networkx.algorithms.components.connected

number_connected_components(G, *, backend=None, **backend_kwargs)
    Returns the number of connected components.

    Parameters
    ----------
    G : NetworkX graph
       An undirected graph.

    Returns
    -------
    n : integer
       Number of connected components

    Raises
    ------
    NetworkXNotImplemented
        If G is directed.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (1, 2), (5, 6), (3, 4)])
    >>> nx.number_connected_components(G)
    3

    See Also
    --------
    connected_components
    number_weakly_connected_components
    number_strongly_connected_components

    Notes
    -----
    For undirected graphs only.
networkx.number_of_cliques
Python Library Documentation: function number_of_cliques in module networkx.algorithms.clique

number_of_cliques(G, nodes=None, cliques=None)
    Returns the number of maximal cliques for each node.

    Returns a single or list depending on input nodes.
    Optional list of cliques can be input if already computed.
networkx.number_of_edges
Python Library Documentation: function number_of_edges in module networkx.classes.function

number_of_edges(G)
    Returns the number of edges in the graph.

    This function wraps the :func:`G.number_of_edges <networkx.Graph.number_of_edges>` function.
networkx.number_of_isolates
Python Library Documentation: function number_of_isolates in module networkx.algorithms.isolate

number_of_isolates(G, *, backend=None, **backend_kwargs)
    Returns the number of isolates in the graph.

    An *isolate* is a node with no neighbors (that is, with degree
    zero). For directed graphs, this means no in-neighbors and no
    out-neighbors.

    Parameters
    ----------
    G : NetworkX graph

    Returns
    -------
    int
        The number of degree zero nodes in the graph `G`.
networkx.number_of_nodes
Python Library Documentation: function number_of_nodes in module networkx.classes.function

number_of_nodes(G)
    Returns the number of nodes in the graph.

    This function wraps the :func:`G.number_of_nodes <networkx.Graph.number_of_nodes>` function.
networkx.number_of_nonisomorphic_trees
Python Library Documentation: function number_of_nonisomorphic_trees in module networkx.generators.nonisomorphic_trees

number_of_nonisomorphic_trees(order, *, backend=None, **backend_kwargs)
    Returns the number of nonisomorphic trees

    Parameters
    ----------
    order : int
      order of the desired tree(s)

    Returns
    -------
    length : Number of nonisomorphic graphs for the given order

    References
    ----------
networkx.number_of_selfloops
Python Library Documentation: function number_of_selfloops in module networkx.classes.function

number_of_selfloops(G)
    Returns the number of selfloop edges.

    A selfloop edge has the same node at both ends.

    Returns
    -------
    nloops : int
        The number of selfloops.

    See Also
    --------
    nodes_with_selfloops, selfloop_edges

    Examples
    --------
    >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
    >>> G.add_edge(1, 1)
    >>> G.add_edge(1, 2)
    >>> nx.number_of_selfloops(G)
    1
networkx.number_of_spanning_trees
Python Library Documentation: function number_of_spanning_trees in module networkx.algorithms.tree.mst

number_of_spanning_trees(G, *, root=None, weight=None, backend=None, **backend_kwargs)
    Returns the number of spanning trees in `G`.

    A spanning tree for an undirected graph is a tree that connects
    all nodes in the graph. For a directed graph, the analog of a
    spanning tree is called a (spanning) arborescence. The arborescence
    includes a unique directed path from the `root` node to each other node.
    The graph must be weakly connected, and the root must be a node
    that includes all nodes as successors [3]_. Note that to avoid
    discussing sink-roots and reverse-arborescences, we have reversed
    the edge orientation from [3]_ and use the in-degree laplacian.

    This function (when `weight` is `None`) returns the number of
    spanning trees for an undirected graph and the number of
    arborescences from a single root node for a directed graph.
    When `weight` is the name of an edge attribute which holds the
    weight value of each edge, the function returns the sum over
    all trees of the multiplicative weight of each tree. That is,
    the weight of the tree is the product of its edge weights.

    Kirchoff's Tree Matrix Theorem states that any cofactor of the
    Laplacian matrix of a graph is the number of spanning trees in the
    graph. (Here we use cofactors for a diagonal entry so that the
    cofactor becomes the determinant of the matrix with one row
    and its matching column removed.) For a weighted Laplacian matrix,
    the cofactor is the sum across all spanning trees of the
    multiplicative weight of each tree. That is, the weight of each
    tree is the product of its edge weights. The theorem is also
    known as Kirchhoff's theorem [1]_ and the Matrix-Tree theorem [2]_.

    For directed graphs, a similar theorem (Tutte's Theorem) holds with
    the cofactor chosen to be the one with row and column removed that
    correspond to the root. The cofactor is the number of arborescences
    with the specified node as root. And the weighted version gives the
    sum of the arborescence weights with root `root`. The arborescence
    weight is the product of its edge weights.

    Parameters
    ----------
    G : NetworkX graph

    root : node
       A node in the directed graph `G` that has all nodes as descendants.
       (This is ignored for undirected graphs.)

    weight : string or None, optional (default=None)
        The name of the edge attribute holding the edge weight.
        If `None`, then each edge is assumed to have a weight of 1.

    Returns
    -------
    Number
        Undirected graphs:
            The number of spanning trees of the graph `G`.
            Or the sum of all spanning tree weights of the graph `G`
            where the weight of a tree is the product of its edge weights.
        Directed graphs:
            The number of arborescences of `G` rooted at node `root`.
            Or the sum of all arborescence weights of the graph `G` with
            specified root where the weight of an arborescence is the product
            of its edge weights.

    Raises
    ------
    NetworkXPointlessConcept
        If `G` does not contain any nodes.

    NetworkXError
        If the graph `G` is directed and the root node
        is not specified or is not in G.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> round(nx.number_of_spanning_trees(G))
    125

    >>> G = nx.Graph()
    >>> G.add_edge(1, 2, weight=2)
    >>> G.add_edge(1, 3, weight=1)
    >>> G.add_edge(2, 3, weight=1)
    >>> round(nx.number_of_spanning_trees(G, weight="weight"))
    5

    Notes
    -----
    Self-loops are excluded. Multi-edges are contracted in one edge
    equal to the sum of the weights.

    References
    ----------
    .. [1] Wikipedia
       "Kirchhoff's theorem."
       https://en.wikipedia.org/wiki/Kirchhoff%27s_theorem
    .. [2] Kirchhoff, G. R.
        Über die Auflösung der Gleichungen, auf welche man
        bei der Untersuchung der linearen Vertheilung
        Galvanischer Ströme geführt wird
        Annalen der Physik und Chemie, vol. 72, pp. 497-508, 1847.
    .. [3] Margoliash, J.
        "Matrix-Tree Theorem for Directed Graphs"
        https://www.math.uchicago.edu/~may/VIGRE/VIGRE2010/REUPapers/Margoliash.pdf
networkx.number_of_walks
Python Library Documentation: function number_of_walks in module networkx.algorithms.walks

number_of_walks(G, walk_length, *, backend=None, **backend_kwargs)
    Returns the number of walks connecting each pair of nodes in `G`

    A *walk* is a sequence of nodes in which each adjacent pair of nodes
    in the sequence is adjacent in the graph. A walk can repeat the same
    edge and go in the opposite direction just as people can walk on a
    set of paths, but standing still is not counted as part of the walk.

    This function only counts the walks with `walk_length` edges. Note that
    the number of nodes in the walk sequence is one more than `walk_length`.
    The number of walks can grow very quickly on a larger graph
    and with a larger walk length.

    Parameters
    ----------
    G : NetworkX graph

    walk_length : int
        A nonnegative integer representing the length of a walk.

    Returns
    -------
    dict
        A dictionary of dictionaries in which outer keys are source
        nodes, inner keys are target nodes, and inner values are the
        number of walks of length `walk_length` connecting those nodes.

    Raises
    ------
    ValueError
        If `walk_length` is negative

    Examples
    --------

    >>> G = nx.Graph([(0, 1), (1, 2)])
    >>> walks = nx.number_of_walks(G, 2)
    >>> walks
    {0: {0: 1, 1: 0, 2: 1}, 1: {0: 0, 1: 2, 2: 0}, 2: {0: 1, 1: 0, 2: 1}}
    >>> total_walks = sum(sum(tgts.values()) for _, tgts in walks.items())

    You can also get the number of walks from a specific source node using the
    returned dictionary. For example, number of walks of length 1 from node 0
    can be found as follows:

    >>> walks = nx.number_of_walks(G, 1)
    >>> walks[0]
    {0: 0, 1: 1, 2: 0}
    >>> sum(walks[0].values())  # walks from 0 of length 1
    1

    Similarly, a target node can also be specified:

    >>> walks[0][1]
    1
networkx.number_strongly_connected_components
Python Library Documentation: function number_strongly_connected_components in module networkx.algorithms.components.strongly_connected

number_strongly_connected_components(G, *, backend=None, **backend_kwargs)
    Returns number of strongly connected components in graph.

    Parameters
    ----------
    G : NetworkX graph
       A directed graph.

    Returns
    -------
    n : integer
       Number of strongly connected components

    Raises
    ------
    NetworkXNotImplemented
        If G is undirected.

    Examples
    --------
    >>> G = nx.DiGraph(
    ...     [(0, 1), (1, 2), (2, 0), (2, 3), (4, 5), (3, 4), (5, 6), (6, 3), (6, 7)]
    ... )
    >>> nx.number_strongly_connected_components(G)
    3

    See Also
    --------
    strongly_connected_components
    number_connected_components
    number_weakly_connected_components

    Notes
    -----
    For directed graphs only.
networkx.number_weakly_connected_components
Python Library Documentation: function number_weakly_connected_components in module networkx.algorithms.components.weakly_connected

number_weakly_connected_components(G, *, backend=None, **backend_kwargs)
    Returns the number of weakly connected components in G.

    Parameters
    ----------
    G : NetworkX graph
        A directed graph.

    Returns
    -------
    n : integer
        Number of weakly connected components

    Raises
    ------
    NetworkXNotImplemented
        If G is undirected.

    Examples
    --------
    >>> G = nx.DiGraph([(0, 1), (2, 1), (3, 4)])
    >>> nx.number_weakly_connected_components(G)
    2

    See Also
    --------
    weakly_connected_components
    number_connected_components
    number_strongly_connected_components

    Notes
    -----
    For directed graphs only.
networkx.numeric_assortativity_coefficient
Python Library Documentation: function numeric_assortativity_coefficient in module networkx.algorithms.assortativity.correlation

numeric_assortativity_coefficient(G, attribute, nodes=None, *, backend=None, **backend_kwargs)
    Compute assortativity for numerical node attributes.

    Assortativity measures the similarity of connections
    in the graph with respect to the given numeric attribute.

    Parameters
    ----------
    G : NetworkX graph

    attribute : string
        Node attribute key.

    nodes: list or iterable (optional)
        Compute numeric assortativity only for attributes of nodes in
        container. The default is all nodes.

    Returns
    -------
    r: float
       Assortativity of graph for given attribute

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_nodes_from([0, 1], size=2)
    >>> G.add_nodes_from([2, 3], size=3)
    >>> G.add_edges_from([(0, 1), (2, 3)])
    >>> print(nx.numeric_assortativity_coefficient(G, "size"))
    1.0

    Notes
    -----
    This computes Eq. (21) in Ref. [1]_ , which is the Pearson correlation
    coefficient of the specified (scalar valued) attribute across edges.

    References
    ----------
    .. [1] M. E. J. Newman, Mixing patterns in networks
           Physical Review E, 67 026126, 2003
networkx.nx_agraph
Python Library Documentation: module networkx.drawing.nx_agraph in networkx.drawing

NAME
    networkx.drawing.nx_agraph

DESCRIPTION
    ***************
    Graphviz AGraph
    ***************

    Interface to pygraphviz AGraph class.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> A = nx.nx_agraph.to_agraph(G)
    >>> H = nx.nx_agraph.from_agraph(A)

    See Also
    --------
     - Pygraphviz: http://pygraphviz.github.io/
     - Graphviz:      https://www.graphviz.org
     - DOT Language:  http://www.graphviz.org/doc/info/lang.html

FUNCTIONS
    from_agraph(A, create_using=None, *, backend=None, **backend_kwargs)
        Returns a NetworkX Graph or DiGraph from a PyGraphviz graph.

        Parameters
        ----------
        A : PyGraphviz AGraph
          A graph created with PyGraphviz

        create_using : NetworkX graph constructor, optional (default=None)
           Graph type to create. If graph instance, then cleared before populated.
           If `None`, then the appropriate Graph type is inferred from `A`.

        Examples
        --------
        >>> K5 = nx.complete_graph(5)
        >>> A = nx.nx_agraph.to_agraph(K5)
        >>> G = nx.nx_agraph.from_agraph(A)

        Notes
        -----
        The Graph G will have a dictionary G.graph_attr containing
        the default graphviz attributes for graphs, nodes and edges.

        Default node attributes will be in the dictionary G.node_attr
        which is keyed by node.

        Edge attributes will be returned as edge data in G.  With
        edge_attr=False the edge data will be the Graphviz edge weight
        attribute or the value 1 if no edge weight attribute is found.

    graphviz_layout(G, prog='neato', root=None, args='')
        Create node positions for G using Graphviz.

        Parameters
        ----------
        G : NetworkX graph
          A graph created with NetworkX
        prog : string
          Name of Graphviz layout program
        root : string, optional
          Root node for twopi layout
        args : string, optional
          Extra arguments to Graphviz layout program

        Returns
        -------
        Dictionary of x, y, positions keyed by node.

        Examples
        --------
        >>> G = nx.petersen_graph()
        >>> pos = nx.nx_agraph.graphviz_layout(G)
        >>> pos = nx.nx_agraph.graphviz_layout(G, prog="dot")

        Notes
        -----
        This is a wrapper for pygraphviz_layout.

        Note that some graphviz layouts are not guaranteed to be deterministic,
        see https://gitlab.com/graphviz/graphviz/-/issues/1767 for more info.

    pygraphviz_layout(G, prog='neato', root=None, args='')
        Create node positions for G using Graphviz.

        Parameters
        ----------
        G : NetworkX graph
          A graph created with NetworkX
        prog : string
          Name of Graphviz layout program
        root : string, optional
          Root node for twopi layout
        args : string, optional
          Extra arguments to Graphviz layout program

        Returns
        -------
        node_pos : dict
          Dictionary of x, y, positions keyed by node.

        Examples
        --------
        >>> G = nx.petersen_graph()
        >>> pos = nx.nx_agraph.graphviz_layout(G)
        >>> pos = nx.nx_agraph.graphviz_layout(G, prog="dot")

        Notes
        -----
        If you use complex node objects, they may have the same string
        representation and GraphViz could treat them as the same node.
        The layout may assign both nodes a single location. See Issue #1568
        If this occurs in your case, consider relabeling the nodes just
        for the layout computation using something similar to::

            >>> H = nx.convert_node_labels_to_integers(G, label_attribute="node_label")
            >>> H_layout = nx.nx_agraph.pygraphviz_layout(G, prog="dot")
            >>> G_layout = {H.nodes[n]["node_label"]: p for n, p in H_layout.items()}

        Note that some graphviz layouts are not guaranteed to be deterministic,
        see https://gitlab.com/graphviz/graphviz/-/issues/1767 for more info.

    read_dot(path, *, backend=None, **backend_kwargs)
        Returns a NetworkX graph from a dot file on path.

        Parameters
        ----------
        path : file or string
           File name or file handle to read.

    to_agraph(N)
        Returns a pygraphviz graph from a NetworkX graph N.

        Parameters
        ----------
        N : NetworkX graph
          A graph created with NetworkX

        Examples
        --------
        >>> K5 = nx.complete_graph(5)
        >>> A = nx.nx_agraph.to_agraph(K5)

        Notes
        -----
        If N has an dict N.graph_attr an attempt will be made first
        to copy properties attached to the graph (see from_agraph)
        and then updated with the calling arguments if any.

    view_pygraphviz(G, edgelabel=None, prog='dot', args='', suffix='', path=None, show=True)
        Views the graph G using the specified layout algorithm.

        Parameters
        ----------
        G : NetworkX graph
            The machine to draw.
        edgelabel : str, callable, None
            If a string, then it specifies the edge attribute to be displayed
            on the edge labels. If a callable, then it is called for each
            edge and it should return the string to be displayed on the edges.
            The function signature of `edgelabel` should be edgelabel(data),
            where `data` is the edge attribute dictionary.
        prog : string
            Name of Graphviz layout program.
        args : str
            Additional arguments to pass to the Graphviz layout program.
        suffix : str
            If `filename` is None, we save to a temporary file.  The value of
            `suffix` will appear at the tail end of the temporary filename.
        path : str, None
            The filename used to save the image.  If None, save to a temporary
            file.  File formats are the same as those from pygraphviz.agraph.draw.
        show : bool, default = True
            Whether to display the graph with :mod:`PIL.Image.show`,
            default is `True`. If `False`, the rendered graph is still available
            at `path`.

        Returns
        -------
        path : str
            The filename of the generated image.
        A : PyGraphviz graph
            The PyGraphviz graph instance used to generate the image.

        Notes
        -----
        If this function is called in succession too quickly, sometimes the
        image is not displayed. So you might consider time.sleep(.5) between
        calls if you experience problems.

        Note that some graphviz layouts are not guaranteed to be deterministic,
        see https://gitlab.com/graphviz/graphviz/-/issues/1767 for more info.

    write_dot(G, path)
        Write NetworkX graph G to Graphviz dot format on path.

        Parameters
        ----------
        G : graph
           A networkx graph
        path : filename
           Filename or file handle to write

        Notes
        -----
        To use a specific graph layout, call ``A.layout`` prior to `write_dot`.
        Note that some graphviz layouts are not guaranteed to be deterministic,
        see https://gitlab.com/graphviz/graphviz/-/issues/1767 for more info.

DATA
    __all__ = ['from_agraph', 'to_agraph', 'write_dot', 'read_dot', 'graph...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\drawing\nx_agraph.py

networkx.nx_latex
Python Library Documentation: module networkx.drawing.nx_latex in networkx.drawing

NAME
    networkx.drawing.nx_latex

DESCRIPTION
    *****
    LaTeX
    *****

    Export NetworkX graphs in LaTeX format using the TikZ library within TeX/LaTeX.
    Usually, you will want the drawing to appear in a figure environment so
    you use ``to_latex(G, caption="A caption")``. If you want the raw
    drawing commands without a figure environment use :func:`to_latex_raw`.
    And if you want to write to a file instead of just returning the latex
    code as a string, use ``write_latex(G, "filename.tex", caption="A caption")``.

    To construct a figure with subfigures for each graph to be shown, provide
    ``to_latex`` or ``write_latex`` a list of graphs, a list of subcaptions,
    and a number of rows of subfigures inside the figure.

    To be able to refer to the figures or subfigures in latex using ``\\ref``,
    the keyword ``latex_label`` is available for figures and `sub_labels` for
    a list of labels, one for each subfigure.

    We intend to eventually provide an interface to the TikZ Graph
    features which include e.g. layout algorithms.

    Let us know via github what you'd like to see available, or better yet
    give us some code to do it, or even better make a github pull request
    to add the feature.

    The TikZ approach
    =================
    Drawing options can be stored on the graph as node/edge attributes, or
    can be provided as dicts keyed by node/edge to a string of the options
    for that node/edge. Similarly a label can be shown for each node/edge
    by specifying the labels as graph node/edge attributes or by providing
    a dict keyed by node/edge to the text to be written for that node/edge.

    Options for the tikzpicture environment (e.g. "[scale=2]") can be provided
    via a keyword argument. Similarly default node and edge options can be
    provided through keywords arguments. The default node options are applied
    to the single TikZ "path" that draws all nodes (and no edges). The default edge
    options are applied to a TikZ "scope" which contains a path for each edge.

    Examples
    ========
    >>> G = nx.path_graph(3)
    >>> nx.write_latex(G, "just_my_figure.tex", as_document=True)
    >>> nx.write_latex(G, "my_figure.tex", caption="A path graph", latex_label="fig1")
    >>> latex_code = nx.to_latex(G)  # a string rather than a file

    You can change many features of the nodes and edges.

    >>> G = nx.path_graph(4, create_using=nx.DiGraph)
    >>> pos = {n: (n, n) for n in G}  # nodes set on a line

    >>> G.nodes[0]["style"] = "blue"
    >>> G.nodes[2]["style"] = "line width=3,draw"
    >>> G.nodes[3]["label"] = "Stop"
    >>> G.edges[(0, 1)]["label"] = "1st Step"
    >>> G.edges[(0, 1)]["label_opts"] = "near start"
    >>> G.edges[(1, 2)]["style"] = "line width=3"
    >>> G.edges[(1, 2)]["label"] = "2nd Step"
    >>> G.edges[(2, 3)]["style"] = "green"
    >>> G.edges[(2, 3)]["label"] = "3rd Step"
    >>> G.edges[(2, 3)]["label_opts"] = "near end"

    >>> nx.write_latex(G, "latex_graph.tex", pos=pos, as_document=True)

    Then compile the LaTeX using something like ``pdflatex latex_graph.tex``
    and view the pdf file created: ``latex_graph.pdf``.

    If you want **subfigures** each containing one graph, you can input a list of graphs.

    >>> H1 = nx.path_graph(4)
    >>> H2 = nx.complete_graph(4)
    >>> H3 = nx.path_graph(8)
    >>> H4 = nx.complete_graph(8)
    >>> graphs = [H1, H2, H3, H4]
    >>> caps = ["Path 4", "Complete graph 4", "Path 8", "Complete graph 8"]
    >>> lbls = ["fig2a", "fig2b", "fig2c", "fig2d"]
    >>> nx.write_latex(graphs, "subfigs.tex", n_rows=2, sub_captions=caps, sub_labels=lbls)
    >>> latex_code = nx.to_latex(graphs, n_rows=2, sub_captions=caps, sub_labels=lbls)

    >>> node_color = {0: "red", 1: "orange", 2: "blue", 3: "gray!90"}
    >>> edge_width = {e: "line width=1.5" for e in H3.edges}
    >>> pos = nx.circular_layout(H3)
    >>> latex_code = nx.to_latex(H3, pos, node_options=node_color, edge_options=edge_width)
    >>> print(latex_code)
    \documentclass{report}
    \usepackage{tikz}
    \usepackage{subcaption}
    <BLANKLINE>
    \begin{document}
    \begin{figure}
      \begin{tikzpicture}
          \draw
            (1.0, 0.0) node[red] (0){0}
            (0.707, 0.707) node[orange] (1){1}
            (-0.0, 1.0) node[blue] (2){2}
            (-0.707, 0.707) node[gray!90] (3){3}
            (-1.0, -0.0) node (4){4}
            (-0.707, -0.707) node (5){5}
            (0.0, -1.0) node (6){6}
            (0.707, -0.707) node (7){7};
          \begin{scope}[-]
            \draw[line width=1.5] (0) to (1);
            \draw[line width=1.5] (1) to (2);
            \draw[line width=1.5] (2) to (3);
            \draw[line width=1.5] (3) to (4);
            \draw[line width=1.5] (4) to (5);
            \draw[line width=1.5] (5) to (6);
            \draw[line width=1.5] (6) to (7);
          \end{scope}
        \end{tikzpicture}
    \end{figure}
    \end{document}

    Notes
    -----
    If you want to change the preamble/postamble of the figure/document/subfigure
    environment, use the keyword arguments: `figure_wrapper`, `document_wrapper`,
    `subfigure_wrapper`. The default values are stored in private variables
    e.g. ``nx.nx_layout._DOCUMENT_WRAPPER``

    References
    ----------
    TikZ:          https://tikz.dev/

    TikZ options details:   https://tikz.dev/tikz-actions

FUNCTIONS
    to_latex(Gbunch, pos='pos', tikz_options='', default_node_options='', node_options='node_options', node_label='node_label', default_edge_options='', edge_options='edge_options', edge_label='edge_label', edge_label_options='edge_label_options', caption='', latex_label='', sub_captions=None, sub_labels=None, n_rows=1, as_document=True, document_wrapper='\\documentclass{{report}}\n\\usepackage{{tikz}}\n\\usepackage{{subcaption}}\n\n\\begin{{document}}\n{content}\n\\end{{document}}', figure_wrapper='\\begin{{figure}}\n{content}{caption}{label}\n\\end{{figure}}', subfigure_wrapper='  \\begin{{subfigure}}{{{size}\\textwidth}}\n{content}{caption}{label}\n  \\end{{subfigure}}')
        Return latex code to draw the graph(s) in `Gbunch`

        The TikZ drawing utility in LaTeX is used to draw the graph(s).
        If `Gbunch` is a graph, it is drawn in a figure environment.
        If `Gbunch` is an iterable of graphs, each is drawn in a subfigure environment
        within a single figure environment.

        If `as_document` is True, the figure is wrapped inside a document environment
        so that the resulting string is ready to be compiled by LaTeX. Otherwise,
        the string is ready for inclusion in a larger tex document using ``\include``
        or ``\input`` statements.

        Parameters
        ==========
        Gbunch : NetworkX graph or iterable of NetworkX graphs
            The NetworkX graph to be drawn or an iterable of graphs
            to be drawn inside subfigures of a single figure.
        pos : string or list of strings
            The name of the node attribute on `G` that holds the position of each node.
            Positions can be sequences of length 2 with numbers for (x,y) coordinates.
            They can also be strings to denote positions in TikZ style, such as (x, y)
            or (angle:radius).
            If a dict, it should be keyed by node to a position.
            If an empty dict, a circular layout is computed by TikZ.
            If you are drawing many graphs in subfigures, use a list of position dicts.
        tikz_options : string
            The tikzpicture options description defining the options for the picture.
            Often large scale options like `[scale=2]`.
        default_node_options : string
            The draw options for a path of nodes. Individual node options override these.
        node_options : string or dict
            The name of the node attribute on `G` that holds the options for each node.
            Or a dict keyed by node to a string holding the options for that node.
        node_label : string or dict
            The name of the node attribute on `G` that holds the node label (text)
            displayed for each node. If the attribute is "" or not present, the node
            itself is drawn as a string. LaTeX processing such as ``"$A_1$"`` is allowed.
            Or a dict keyed by node to a string holding the label for that node.
        default_edge_options : string
            The options for the scope drawing all edges. The default is "[-]" for
            undirected graphs and "[->]" for directed graphs.
        edge_options : string or dict
            The name of the edge attribute on `G` that holds the options for each edge.
            If the edge is a self-loop and ``"loop" not in edge_options`` the option
            "loop," is added to the options for the self-loop edge. Hence you can
            use "[loop above]" explicitly, but the default is "[loop]".
            Or a dict keyed by edge to a string holding the options for that edge.
        edge_label : string or dict
            The name of the edge attribute on `G` that holds the edge label (text)
            displayed for each edge. If the attribute is "" or not present, no edge
            label is drawn.
            Or a dict keyed by edge to a string holding the label for that edge.
        edge_label_options : string or dict
            The name of the edge attribute on `G` that holds the label options for
            each edge. For example, "[sloped,above,blue]". The default is no options.
            Or a dict keyed by edge to a string holding the label options for that edge.
        caption : string
            The caption string for the figure environment
        latex_label : string
            The latex label used for the figure for easy referral from the main text
        sub_captions : list of strings
            The sub_caption string for each subfigure in the figure
        sub_latex_labels : list of strings
            The latex label for each subfigure in the figure
        n_rows : int
            The number of rows of subfigures to arrange for multiple graphs
        as_document : bool
            Whether to wrap the latex code in a document environment for compiling
        document_wrapper : formatted text string with variable ``content``.
            This text is called to evaluate the content embedded in a document
            environment with a preamble setting up TikZ.
        figure_wrapper : formatted text string
            This text is evaluated with variables ``content``, ``caption`` and ``label``.
            It wraps the content and if a caption is provided, adds the latex code for
            that caption, and if a label is provided, adds the latex code for a label.
        subfigure_wrapper : formatted text string
            This text evaluate variables ``size``, ``content``, ``caption`` and ``label``.
            It wraps the content and if a caption is provided, adds the latex code for
            that caption, and if a label is provided, adds the latex code for a label.
            The size is the vertical size of each row of subfigures as a fraction.

        Returns
        =======
        latex_code : string
            The text string which draws the desired graph(s) when compiled by LaTeX.

        See Also
        ========
        write_latex
        to_latex_raw

    to_latex_raw(G, pos='pos', tikz_options='', default_node_options='', node_options='node_options', node_label='label', default_edge_options='', edge_options='edge_options', edge_label='label', edge_label_options='edge_label_options')
        Return a string of the LaTeX/TikZ code to draw `G`

        This function produces just the code for the tikzpicture
        without any enclosing environment.

        Parameters
        ==========
        G : NetworkX graph
            The NetworkX graph to be drawn
        pos : string or dict (default "pos")
            The name of the node attribute on `G` that holds the position of each node.
            Positions can be sequences of length 2 with numbers for (x,y) coordinates.
            They can also be strings to denote positions in TikZ style, such as (x, y)
            or (angle:radius).
            If a dict, it should be keyed by node to a position.
            If an empty dict, a circular layout is computed by TikZ.
        tikz_options : string
            The tikzpicture options description defining the options for the picture.
            Often large scale options like `[scale=2]`.
        default_node_options : string
            The draw options for a path of nodes. Individual node options override these.
        node_options : string or dict
            The name of the node attribute on `G` that holds the options for each node.
            Or a dict keyed by node to a string holding the options for that node.
        node_label : string or dict
            The name of the node attribute on `G` that holds the node label (text)
            displayed for each node. If the attribute is "" or not present, the node
            itself is drawn as a string. LaTeX processing such as ``"$A_1$"`` is allowed.
            Or a dict keyed by node to a string holding the label for that node.
        default_edge_options : string
            The options for the scope drawing all edges. The default is "[-]" for
            undirected graphs and "[->]" for directed graphs.
        edge_options : string or dict
            The name of the edge attribute on `G` that holds the options for each edge.
            If the edge is a self-loop and ``"loop" not in edge_options`` the option
            "loop," is added to the options for the self-loop edge. Hence you can
            use "[loop above]" explicitly, but the default is "[loop]".
            Or a dict keyed by edge to a string holding the options for that edge.
        edge_label : string or dict
            The name of the edge attribute on `G` that holds the edge label (text)
            displayed for each edge. If the attribute is "" or not present, no edge
            label is drawn.
            Or a dict keyed by edge to a string holding the label for that edge.
        edge_label_options : string or dict
            The name of the edge attribute on `G` that holds the label options for
            each edge. For example, "[sloped,above,blue]". The default is no options.
            Or a dict keyed by edge to a string holding the label options for that edge.

        Returns
        =======
        latex_code : string
           The text string which draws the desired graph(s) when compiled by LaTeX.

        See Also
        ========
        to_latex
        write_latex

    write_latex(Gbunch, path, **options)
        Write the latex code to draw the graph(s) onto `path`.

        This convenience function creates the latex drawing code as a string
        and writes that to a file ready to be compiled when `as_document` is True
        or ready to be ``import`` ed or ``include`` ed into your main LaTeX document.

        The `path` argument can be a string filename or a file handle to write to.

        Parameters
        ----------
        Gbunch : NetworkX graph or iterable of NetworkX graphs
            If Gbunch is a graph, it is drawn in a figure environment.
            If Gbunch is an iterable of graphs, each is drawn in a subfigure
            environment within a single figure environment.
        path : filename
            Filename or file handle to write to
        options : dict
            By default, TikZ is used with options: (others are ignored)::

                pos : string or dict or list
                    The name of the node attribute on `G` that holds the position of each node.
                    Positions can be sequences of length 2 with numbers for (x,y) coordinates.
                    They can also be strings to denote positions in TikZ style, such as (x, y)
                    or (angle:radius).
                    If a dict, it should be keyed by node to a position.
                    If an empty dict, a circular layout is computed by TikZ.
                    If you are drawing many graphs in subfigures, use a list of position dicts.
                tikz_options : string
                    The tikzpicture options description defining the options for the picture.
                    Often large scale options like `[scale=2]`.
                default_node_options : string
                    The draw options for a path of nodes. Individual node options override these.
                node_options : string or dict
                    The name of the node attribute on `G` that holds the options for each node.
                    Or a dict keyed by node to a string holding the options for that node.
                node_label : string or dict
                    The name of the node attribute on `G` that holds the node label (text)
                    displayed for each node. If the attribute is "" or not present, the node
                    itself is drawn as a string. LaTeX processing such as ``"$A_1$"`` is allowed.
                    Or a dict keyed by node to a string holding the label for that node.
                default_edge_options : string
                    The options for the scope drawing all edges. The default is "[-]" for
                    undirected graphs and "[->]" for directed graphs.
                edge_options : string or dict
                    The name of the edge attribute on `G` that holds the options for each edge.
                    If the edge is a self-loop and ``"loop" not in edge_options`` the option
                    "loop," is added to the options for the self-loop edge. Hence you can
                    use "[loop above]" explicitly, but the default is "[loop]".
                    Or a dict keyed by edge to a string holding the options for that edge.
                edge_label : string or dict
                    The name of the edge attribute on `G` that holds the edge label (text)
                    displayed for each edge. If the attribute is "" or not present, no edge
                    label is drawn.
                    Or a dict keyed by edge to a string holding the label for that edge.
                edge_label_options : string or dict
                    The name of the edge attribute on `G` that holds the label options for
                    each edge. For example, "[sloped,above,blue]". The default is no options.
                    Or a dict keyed by edge to a string holding the label options for that edge.
                caption : string
                    The caption string for the figure environment
                latex_label : string
                    The latex label used for the figure for easy referral from the main text
                sub_captions : list of strings
                    The sub_caption string for each subfigure in the figure
                sub_latex_labels : list of strings
                    The latex label for each subfigure in the figure
                n_rows : int
                    The number of rows of subfigures to arrange for multiple graphs
                as_document : bool
                    Whether to wrap the latex code in a document environment for compiling
                document_wrapper : formatted text string with variable ``content``.
                    This text is called to evaluate the content embedded in a document
                    environment with a preamble setting up the TikZ syntax.
                figure_wrapper : formatted text string
                    This text is evaluated with variables ``content``, ``caption`` and ``label``.
                    It wraps the content and if a caption is provided, adds the latex code for
                    that caption, and if a label is provided, adds the latex code for a label.
                subfigure_wrapper : formatted text string
                    This text evaluate variables ``size``, ``content``, ``caption`` and ``label``.
                    It wraps the content and if a caption is provided, adds the latex code for
                    that caption, and if a label is provided, adds the latex code for a label.
                    The size is the vertical size of each row of subfigures as a fraction.

        See Also
        ========
        to_latex

DATA
    __all__ = ['to_latex_raw', 'to_latex', 'write_latex']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\drawing\nx_latex.py

networkx.nx_pydot
Python Library Documentation: module networkx.drawing.nx_pydot in networkx.drawing

NAME
    networkx.drawing.nx_pydot

DESCRIPTION
    *****
    Pydot
    *****

    Import and export NetworkX graphs in Graphviz dot format using pydot.

    Either this module or nx_agraph can be used to interface with graphviz.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> PG = nx.nx_pydot.to_pydot(G)
    >>> H = nx.nx_pydot.from_pydot(PG)

    See Also
    --------
     - pydot:         https://github.com/erocarrera/pydot
     - Graphviz:      https://www.graphviz.org
     - DOT Language:  http://www.graphviz.org/doc/info/lang.html

FUNCTIONS
    from_pydot(P, *, backend=None, **backend_kwargs)
        Returns a NetworkX graph from a Pydot graph.

        Parameters
        ----------
        P : Pydot graph
          A graph created with Pydot

        Returns
        -------
        G : NetworkX multigraph
            A MultiGraph or MultiDiGraph.

        Examples
        --------
        >>> K5 = nx.complete_graph(5)
        >>> A = nx.nx_pydot.to_pydot(K5)
        >>> G = nx.nx_pydot.from_pydot(A)  # return MultiGraph

        # make a Graph instead of MultiGraph
        >>> G = nx.Graph(nx.nx_pydot.from_pydot(A))

    graphviz_layout(G, prog='neato', root=None)
        Create node positions using Pydot and Graphviz.

        Returns a dictionary of positions keyed by node.

        Parameters
        ----------
        G : NetworkX Graph
            The graph for which the layout is computed.
        prog : string (default: 'neato')
            The name of the GraphViz program to use for layout.
            Options depend on GraphViz version but may include:
            'dot', 'twopi', 'fdp', 'sfdp', 'circo'
        root : Node from G or None (default: None)
            The node of G from which to start some layout algorithms.

        Returns
        -------
          Dictionary of (x, y) positions keyed by node.

        Examples
        --------
        >>> G = nx.complete_graph(4)
        >>> pos = nx.nx_pydot.graphviz_layout(G)
        >>> pos = nx.nx_pydot.graphviz_layout(G, prog="dot")

        Notes
        -----
        This is a wrapper for pydot_layout.

    pydot_layout(G, prog='neato', root=None)
        Create node positions using :mod:`pydot` and Graphviz.

        Parameters
        ----------
        G : Graph
            NetworkX graph to be laid out.
        prog : string  (default: 'neato')
            Name of the GraphViz command to use for layout.
            Options depend on GraphViz version but may include:
            'dot', 'twopi', 'fdp', 'sfdp', 'circo'
        root : Node from G or None (default: None)
            The node of G from which to start some layout algorithms.

        Returns
        -------
        dict
            Dictionary of positions keyed by node.

        Examples
        --------
        >>> G = nx.complete_graph(4)
        >>> pos = nx.nx_pydot.pydot_layout(G)
        >>> pos = nx.nx_pydot.pydot_layout(G, prog="dot")

        Notes
        -----
        If you use complex node objects, they may have the same string
        representation and GraphViz could treat them as the same node.
        The layout may assign both nodes a single location. See Issue #1568
        If this occurs in your case, consider relabeling the nodes just
        for the layout computation using something similar to::

            H = nx.convert_node_labels_to_integers(G, label_attribute="node_label")
            H_layout = nx.nx_pydot.pydot_layout(H, prog="dot")
            G_layout = {H.nodes[n]["node_label"]: p for n, p in H_layout.items()}

    read_dot(path, *, backend=None, **backend_kwargs)
        Returns a NetworkX :class:`MultiGraph` or :class:`MultiDiGraph` from the
        dot file with the passed path.

        If this file contains multiple graphs, only the first such graph is
        returned. All graphs _except_ the first are silently ignored.

        Parameters
        ----------
        path : str or file
            Filename or file handle.

        Returns
        -------
        G : MultiGraph or MultiDiGraph
            A :class:`MultiGraph` or :class:`MultiDiGraph`.

        Notes
        -----
        Use `G = nx.Graph(nx.nx_pydot.read_dot(path))` to return a :class:`Graph` instead of a
        :class:`MultiGraph`.

    to_pydot(N)
        Returns a pydot graph from a NetworkX graph N.

        Parameters
        ----------
        N : NetworkX graph
          A graph created with NetworkX

        Examples
        --------
        >>> K5 = nx.complete_graph(5)
        >>> P = nx.nx_pydot.to_pydot(K5)

        Notes
        -----

    write_dot(G, path)
        Write NetworkX graph G to Graphviz dot format on path.

        Path can be a string or a file handle.

DATA
    __all__ = ['write_dot', 'read_dot', 'graphviz_layout', 'pydot_layout',...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\drawing\nx_pydot.py

networkx.nx_pylab
Python Library Documentation: module networkx.drawing.nx_pylab in networkx.drawing

NAME
    networkx.drawing.nx_pylab

DESCRIPTION
    **********
    Matplotlib
    **********

    Draw networks with matplotlib.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> nx.draw(G)

    See Also
    --------
     - :doc:`matplotlib <matplotlib:index>`
     - :func:`matplotlib.pyplot.scatter`
     - :obj:`matplotlib.patches.FancyArrowPatch`

FUNCTIONS
    draw(G, pos=None, ax=None, **kwds)
        Draw the graph G with Matplotlib.

        Draw the graph as a simple representation with no node
        labels or edge labels and using the full Matplotlib figure area
        and no axis labels by default.  See draw_networkx() for more
        full-featured drawing that allows title, axis labels etc.

        Parameters
        ----------
        G : graph
            A networkx graph

        pos : dictionary, optional
            A dictionary with nodes as keys and positions as values.
            If not specified a spring layout positioning will be computed.
            See :py:mod:`networkx.drawing.layout` for functions that
            compute node positions.

        ax : Matplotlib Axes object, optional
            Draw the graph in specified Matplotlib axes.

        kwds : optional keywords
            See networkx.draw_networkx() for a description of optional keywords.

        Examples
        --------
        >>> G = nx.dodecahedral_graph()
        >>> nx.draw(G)
        >>> nx.draw(G, pos=nx.spring_layout(G))  # use spring layout

        See Also
        --------
        draw_networkx
        draw_networkx_nodes
        draw_networkx_edges
        draw_networkx_labels
        draw_networkx_edge_labels

        Notes
        -----
        This function has the same name as pylab.draw and pyplot.draw
        so beware when using `from networkx import *`

        since you might overwrite the pylab.draw function.

        With pyplot use

        >>> import matplotlib.pyplot as plt
        >>> G = nx.dodecahedral_graph()
        >>> nx.draw(G)  # networkx draw()
        >>> plt.draw()  # pyplot draw()

        Also see the NetworkX drawing examples at
        https://networkx.org/documentation/latest/auto_examples/index.html

    draw_circular(G, **kwargs)
        Draw the graph `G` with a circular layout.

        This is a convenience function equivalent to::

            nx.draw(G, pos=nx.circular_layout(G), **kwargs)

        Parameters
        ----------
        G : graph
            A networkx graph

        kwargs : optional keywords
            See `draw_networkx` for a description of optional keywords.

        Notes
        -----
        The layout is computed each time this function is called. For
        repeated drawing it is much more efficient to call
        `~networkx.drawing.layout.circular_layout` directly and reuse the result::

            >>> G = nx.complete_graph(5)
            >>> pos = nx.circular_layout(G)
            >>> nx.draw(G, pos=pos)  # Draw the original graph
            >>> # Draw a subgraph, reusing the same node positions
            >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> nx.draw_circular(G)

        See Also
        --------
        :func:`~networkx.drawing.layout.circular_layout`

    draw_forceatlas2(G, **kwargs)
        Draw a networkx graph with forceatlas2 layout.

        This is a convenience function equivalent to::

           nx.draw(G, pos=nx.forceatlas2_layout(G), **kwargs)

        Parameters
        ----------
        G : graph
           A networkx graph

        kwargs : optional keywords
           See networkx.draw_networkx() for a description of optional keywords,
           with the exception of the pos parameter which is not used by this
           function.

    draw_kamada_kawai(G, **kwargs)
        Draw the graph `G` with a Kamada-Kawai force-directed layout.

        This is a convenience function equivalent to::

            nx.draw(G, pos=nx.kamada_kawai_layout(G), **kwargs)

        Parameters
        ----------
        G : graph
            A networkx graph

        kwargs : optional keywords
            See `draw_networkx` for a description of optional keywords.

        Notes
        -----
        The layout is computed each time this function is called.
        For repeated drawing it is much more efficient to call
        `~networkx.drawing.layout.kamada_kawai_layout` directly and reuse the
        result::

            >>> G = nx.complete_graph(5)
            >>> pos = nx.kamada_kawai_layout(G)
            >>> nx.draw(G, pos=pos)  # Draw the original graph
            >>> # Draw a subgraph, reusing the same node positions
            >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> nx.draw_kamada_kawai(G)

        See Also
        --------
        :func:`~networkx.drawing.layout.kamada_kawai_layout`

    draw_networkx(G, pos=None, arrows=None, with_labels=True, **kwds)
        Draw the graph G using Matplotlib.

        Draw the graph with Matplotlib with options for node positions,
        labeling, titles, and many other drawing features.
        See draw() for simple drawing without labels or axes.

        Parameters
        ----------
        G : graph
            A networkx graph

        pos : dictionary, optional
            A dictionary with nodes as keys and positions as values.
            If not specified a spring layout positioning will be computed.
            See :py:mod:`networkx.drawing.layout` for functions that
            compute node positions.

        arrows : bool or None, optional (default=None)
            If `None`, directed graphs draw arrowheads with
            `~matplotlib.patches.FancyArrowPatch`, while undirected graphs draw edges
            via `~matplotlib.collections.LineCollection` for speed.
            If `True`, draw arrowheads with FancyArrowPatches (bendable and stylish).
            If `False`, draw edges using LineCollection (linear and fast).
            For directed graphs, if True draw arrowheads.
            Note: Arrows will be the same color as edges.

        arrowstyle : str (default='-\|>' for directed graphs)
            For directed graphs, choose the style of the arrowsheads.
            For undirected graphs default to '-'

            See `matplotlib.patches.ArrowStyle` for more options.

        arrowsize : int or list (default=10)
            For directed graphs, choose the size of the arrow head's length and
            width. A list of values can be passed in to assign a different size for arrow head's length and width.
            See `matplotlib.patches.FancyArrowPatch` for attribute `mutation_scale`
            for more info.

        with_labels :  bool (default=True)
            Set to True to draw labels on the nodes.

        ax : Matplotlib Axes object, optional
            Draw the graph in the specified Matplotlib axes.

        nodelist : list (default=list(G))
            Draw only specified nodes

        edgelist : list (default=list(G.edges()))
            Draw only specified edges

        node_size : scalar or array (default=300)
            Size of nodes.  If an array is specified it must be the
            same length as nodelist.

        node_color : color or array of colors (default='#1f78b4')
            Node color. Can be a single color or a sequence of colors with the same
            length as nodelist. Color can be string or rgb (or rgba) tuple of
            floats from 0-1. If numeric values are specified they will be
            mapped to colors using the cmap and vmin,vmax parameters. See
            matplotlib.scatter for more details.

        node_shape :  string (default='o')
            The shape of the node.  Specification is as matplotlib.scatter
            marker, one of 'so^>v<dph8'.

        alpha : float or None (default=None)
            The node and edge transparency

        cmap : Matplotlib colormap, optional
            Colormap for mapping intensities of nodes

        vmin,vmax : float, optional
            Minimum and maximum for node colormap scaling

        linewidths : scalar or sequence (default=1.0)
            Line width of symbol border

        width : float or array of floats (default=1.0)
            Line width of edges

        edge_color : color or array of colors (default='k')
            Edge color. Can be a single color or a sequence of colors with the same
            length as edgelist. Color can be string or rgb (or rgba) tuple of
            floats from 0-1. If numeric values are specified they will be
            mapped to colors using the edge_cmap and edge_vmin,edge_vmax parameters.

        edge_cmap : Matplotlib colormap, optional
            Colormap for mapping intensities of edges

        edge_vmin,edge_vmax : floats, optional
            Minimum and maximum for edge colormap scaling

        style : string (default=solid line)
            Edge line style e.g.: '-', '--', '-.', ':'
            or words like 'solid' or 'dashed'.
            (See `matplotlib.patches.FancyArrowPatch`: `linestyle`)

        labels : dictionary (default=None)
            Node labels in a dictionary of text labels keyed by node

        font_size : int (default=12 for nodes, 10 for edges)
            Font size for text labels

        font_color : color (default='k' black)
            Font color string. Color can be string or rgb (or rgba) tuple of
            floats from 0-1.

        font_weight : string (default='normal')
            Font weight

        font_family : string (default='sans-serif')
            Font family

        label : string, optional
            Label for graph legend

        hide_ticks : bool, optional
            Hide ticks of axes. When `True` (the default), ticks and ticklabels
            are removed from the axes. To set ticks and tick labels to the pyplot default,
            use ``hide_ticks=False``.

        kwds : optional keywords
            See networkx.draw_networkx_nodes(), networkx.draw_networkx_edges(), and
            networkx.draw_networkx_labels() for a description of optional keywords.

        Notes
        -----
        For directed graphs, arrows  are drawn at the head end.  Arrows can be
        turned off with keyword arrows=False.

        Examples
        --------
        >>> G = nx.dodecahedral_graph()
        >>> nx.draw(G)
        >>> nx.draw(G, pos=nx.spring_layout(G))  # use spring layout

        >>> import matplotlib.pyplot as plt
        >>> limits = plt.axis("off")  # turn off axis

        Also see the NetworkX drawing examples at
        https://networkx.org/documentation/latest/auto_examples/index.html

        See Also
        --------
        draw
        draw_networkx_nodes
        draw_networkx_edges
        draw_networkx_labels
        draw_networkx_edge_labels

    draw_networkx_edge_labels(G, pos, edge_labels=None, label_pos=0.5, font_size=10, font_color='k', font_family='sans-serif', font_weight='normal', alpha=None, bbox=None, horizontalalignment='center', verticalalignment='center', ax=None, rotate=True, clip_on=True, node_size=300, nodelist=None, connectionstyle='arc3', hide_ticks=True)
        Draw edge labels.

        Parameters
        ----------
        G : graph
            A networkx graph

        pos : dictionary
            A dictionary with nodes as keys and positions as values.
            Positions should be sequences of length 2.

        edge_labels : dictionary (default=None)
            Edge labels in a dictionary of labels keyed by edge two-tuple.
            Only labels for the keys in the dictionary are drawn.

        label_pos : float (default=0.5)
            Position of edge label along edge (0=head, 0.5=center, 1=tail)

        font_size : int (default=10)
            Font size for text labels

        font_color : color (default='k' black)
            Font color string. Color can be string or rgb (or rgba) tuple of
            floats from 0-1.

        font_weight : string (default='normal')
            Font weight

        font_family : string (default='sans-serif')
            Font family

        alpha : float or None (default=None)
            The text transparency

        bbox : Matplotlib bbox, optional
            Specify text box properties (e.g. shape, color etc.) for edge labels.
            Default is {boxstyle='round', ec=(1.0, 1.0, 1.0), fc=(1.0, 1.0, 1.0)}.

        horizontalalignment : string (default='center')
            Horizontal alignment {'center', 'right', 'left'}

        verticalalignment : string (default='center')
            Vertical alignment {'center', 'top', 'bottom', 'baseline', 'center_baseline'}

        ax : Matplotlib Axes object, optional
            Draw the graph in the specified Matplotlib axes.

        rotate : bool (default=True)
            Rotate edge labels to lie parallel to edges

        clip_on : bool (default=True)
            Turn on clipping of edge labels at axis boundaries

        node_size : scalar or array (default=300)
            Size of nodes.  If an array it must be the same length as nodelist.

        nodelist : list, optional (default=G.nodes())
           This provides the node order for the `node_size` array (if it is an array).

        connectionstyle : string or iterable of strings (default="arc3")
            Pass the connectionstyle parameter to create curved arc of rounding
            radius rad. For example, connectionstyle='arc3,rad=0.2'.
            See `matplotlib.patches.ConnectionStyle` and
            `matplotlib.patches.FancyArrowPatch` for more info.
            If Iterable, index indicates i'th edge key of MultiGraph

        hide_ticks : bool, optional
            Hide ticks of axes. When `True` (the default), ticks and ticklabels
            are removed from the axes. To set ticks and tick labels to the pyplot default,
            use ``hide_ticks=False``.

        Returns
        -------
        dict
            `dict` of labels keyed by edge

        Examples
        --------
        >>> G = nx.dodecahedral_graph()
        >>> edge_labels = nx.draw_networkx_edge_labels(G, pos=nx.spring_layout(G))

        Also see the NetworkX drawing examples at
        https://networkx.org/documentation/latest/auto_examples/index.html

        See Also
        --------
        draw
        draw_networkx
        draw_networkx_nodes
        draw_networkx_edges
        draw_networkx_labels

    draw_networkx_edges(G, pos, edgelist=None, width=1.0, edge_color='k', style='solid', alpha=None, arrowstyle=None, arrowsize=10, edge_cmap=None, edge_vmin=None, edge_vmax=None, ax=None, arrows=None, label=None, node_size=300, nodelist=None, node_shape='o', connectionstyle='arc3', min_source_margin=0, min_target_margin=0, hide_ticks=True)
        Draw the edges of the graph G.

        This draws only the edges of the graph G.

        Parameters
        ----------
        G : graph
            A networkx graph

        pos : dictionary
            A dictionary with nodes as keys and positions as values.
            Positions should be sequences of length 2.

        edgelist : collection of edge tuples (default=G.edges())
            Draw only specified edges

        width : float or array of floats (default=1.0)
            Line width of edges

        edge_color : color or array of colors (default='k')
            Edge color. Can be a single color or a sequence of colors with the same
            length as edgelist. Color can be string or rgb (or rgba) tuple of
            floats from 0-1. If numeric values are specified they will be
            mapped to colors using the edge_cmap and edge_vmin,edge_vmax parameters.

        style : string or array of strings (default='solid')
            Edge line style e.g.: '-', '--', '-.', ':'
            or words like 'solid' or 'dashed'.
            Can be a single style or a sequence of styles with the same
            length as the edge list.
            If less styles than edges are given the styles will cycle.
            If more styles than edges are given the styles will be used sequentially
            and not be exhausted.
            Also, `(offset, onoffseq)` tuples can be used as style instead of a strings.
            (See `matplotlib.patches.FancyArrowPatch`: `linestyle`)

        alpha : float or array of floats (default=None)
            The edge transparency.  This can be a single alpha value,
            in which case it will be applied to all specified edges. Otherwise,
            if it is an array, the elements of alpha will be applied to the colors
            in order (cycling through alpha multiple times if necessary).

        edge_cmap : Matplotlib colormap, optional
            Colormap for mapping intensities of edges

        edge_vmin,edge_vmax : floats, optional
            Minimum and maximum for edge colormap scaling

        ax : Matplotlib Axes object, optional
            Draw the graph in the specified Matplotlib axes.

        arrows : bool or None, optional (default=None)
            If `None`, directed graphs draw arrowheads with
            `~matplotlib.patches.FancyArrowPatch`, while undirected graphs draw edges
            via `~matplotlib.collections.LineCollection` for speed.
            If `True`, draw arrowheads with FancyArrowPatches (bendable and stylish).
            If `False`, draw edges using LineCollection (linear and fast).

            Note: Arrowheads will be the same color as edges.

        arrowstyle : str or list of strs (default='-\|>' for directed graphs)
            For directed graphs and `arrows==True` defaults to '-\|>',
            For undirected graphs default to '-'.

            See `matplotlib.patches.ArrowStyle` for more options.

        arrowsize : int or list of ints(default=10)
            For directed graphs, choose the size of the arrow head's length and
            width. See `matplotlib.patches.FancyArrowPatch` for attribute
            `mutation_scale` for more info.

        connectionstyle : string or iterable of strings (default="arc3")
            Pass the connectionstyle parameter to create curved arc of rounding
            radius rad. For example, connectionstyle='arc3,rad=0.2'.
            See `matplotlib.patches.ConnectionStyle` and
            `matplotlib.patches.FancyArrowPatch` for more info.
            If Iterable, index indicates i'th edge key of MultiGraph

        node_size : scalar or array (default=300)
            Size of nodes. Though the nodes are not drawn with this function, the
            node size is used in determining edge positioning.

        nodelist : list, optional (default=G.nodes())
           This provides the node order for the `node_size` array (if it is an array).

        node_shape :  string (default='o')
            The marker used for nodes, used in determining edge positioning.
            Specification is as a `matplotlib.markers` marker, e.g. one of 'so^>v<dph8'.

        label : None or string
            Label for legend

        min_source_margin : int or list of ints (default=0)
            The minimum margin (gap) at the beginning of the edge at the source.

        min_target_margin : int or list of ints (default=0)
            The minimum margin (gap) at the end of the edge at the target.

        hide_ticks : bool, optional
            Hide ticks of axes. When `True` (the default), ticks and ticklabels
            are removed from the axes. To set ticks and tick labels to the pyplot default,
            use ``hide_ticks=False``.

        Returns
        -------
         matplotlib.collections.LineCollection or a list of matplotlib.patches.FancyArrowPatch
            If ``arrows=True``, a list of FancyArrowPatches is returned.
            If ``arrows=False``, a LineCollection is returned.
            If ``arrows=None`` (the default), then a LineCollection is returned if
            `G` is undirected, otherwise returns a list of FancyArrowPatches.

        Notes
        -----
        For directed graphs, arrows are drawn at the head end.  Arrows can be
        turned off with keyword arrows=False or by passing an arrowstyle without
        an arrow on the end.

        Be sure to include `node_size` as a keyword argument; arrows are
        drawn considering the size of nodes.

        Self-loops are always drawn with `~matplotlib.patches.FancyArrowPatch`
        regardless of the value of `arrows` or whether `G` is directed.
        When ``arrows=False`` or ``arrows=None`` and `G` is undirected, the
        FancyArrowPatches corresponding to the self-loops are not explicitly
        returned. They should instead be accessed via the ``Axes.patches``
        attribute (see examples).

        Examples
        --------
        >>> G = nx.dodecahedral_graph()
        >>> edges = nx.draw_networkx_edges(G, pos=nx.spring_layout(G))

        >>> G = nx.DiGraph()
        >>> G.add_edges_from([(1, 2), (1, 3), (2, 3)])
        >>> arcs = nx.draw_networkx_edges(G, pos=nx.spring_layout(G))
        >>> alphas = [0.3, 0.4, 0.5]
        >>> for i, arc in enumerate(arcs):  # change alpha values of arcs
        ...     arc.set_alpha(alphas[i])

        The FancyArrowPatches corresponding to self-loops are not always
        returned, but can always be accessed via the ``patches`` attribute of the
        `matplotlib.Axes` object.

        >>> import matplotlib.pyplot as plt
        >>> fig, ax = plt.subplots()
        >>> G = nx.Graph([(0, 1), (0, 0)])  # Self-loop at node 0
        >>> edge_collection = nx.draw_networkx_edges(G, pos=nx.circular_layout(G), ax=ax)
        >>> self_loop_fap = ax.patches[0]

        Also see the NetworkX drawing examples at
        https://networkx.org/documentation/latest/auto_examples/index.html

        See Also
        --------
        draw
        draw_networkx
        draw_networkx_nodes
        draw_networkx_labels
        draw_networkx_edge_labels

    draw_networkx_labels(G, pos, labels=None, font_size=12, font_color='k', font_family='sans-serif', font_weight='normal', alpha=None, bbox=None, horizontalalignment='center', verticalalignment='center', ax=None, clip_on=True, hide_ticks=True)
        Draw node labels on the graph G.

        Parameters
        ----------
        G : graph
            A networkx graph

        pos : dictionary
            A dictionary with nodes as keys and positions as values.
            Positions should be sequences of length 2.

        labels : dictionary (default={n: n for n in G})
            Node labels in a dictionary of text labels keyed by node.
            Node-keys in labels should appear as keys in `pos`.
            If needed use: `{n:lab for n,lab in labels.items() if n in pos}`

        font_size : int or dictionary of nodes to ints (default=12)
            Font size for text labels.

        font_color : color or dictionary of nodes to colors (default='k' black)
            Font color string. Color can be string or rgb (or rgba) tuple of
            floats from 0-1.

        font_weight : string or dictionary of nodes to strings (default='normal')
            Font weight.

        font_family : string or dictionary of nodes to strings (default='sans-serif')
            Font family.

        alpha : float or None or dictionary of nodes to floats (default=None)
            The text transparency.

        bbox : Matplotlib bbox, (default is Matplotlib's ax.text default)
            Specify text box properties (e.g. shape, color etc.) for node labels.

        horizontalalignment : string or array of strings (default='center')
            Horizontal alignment {'center', 'right', 'left'}. If an array is
            specified it must be the same length as `nodelist`.

        verticalalignment : string (default='center')
            Vertical alignment {'center', 'top', 'bottom', 'baseline', 'center_baseline'}.
            If an array is specified it must be the same length as `nodelist`.

        ax : Matplotlib Axes object, optional
            Draw the graph in the specified Matplotlib axes.

        clip_on : bool (default=True)
            Turn on clipping of node labels at axis boundaries

        hide_ticks : bool, optional
            Hide ticks of axes. When `True` (the default), ticks and ticklabels
            are removed from the axes. To set ticks and tick labels to the pyplot default,
            use ``hide_ticks=False``.

        Returns
        -------
        dict
            `dict` of labels keyed on the nodes

        Examples
        --------
        >>> G = nx.dodecahedral_graph()
        >>> labels = nx.draw_networkx_labels(G, pos=nx.spring_layout(G))

        Also see the NetworkX drawing examples at
        https://networkx.org/documentation/latest/auto_examples/index.html

        See Also
        --------
        draw
        draw_networkx
        draw_networkx_nodes
        draw_networkx_edges
        draw_networkx_edge_labels

    draw_networkx_nodes(G, pos, nodelist=None, node_size=300, node_color='#1f78b4', node_shape='o', alpha=None, cmap=None, vmin=None, vmax=None, ax=None, linewidths=None, edgecolors=None, label=None, margins=None, hide_ticks=True)
        Draw the nodes of the graph G.

        This draws only the nodes of the graph G.

        Parameters
        ----------
        G : graph
            A networkx graph

        pos : dictionary
            A dictionary with nodes as keys and positions as values.
            Positions should be sequences of length 2.

        ax : Matplotlib Axes object, optional
            Draw the graph in the specified Matplotlib axes.

        nodelist : list (default list(G))
            Draw only specified nodes

        node_size : scalar or array (default=300)
            Size of nodes.  If an array it must be the same length as nodelist.

        node_color : color or array of colors (default='#1f78b4')
            Node color. Can be a single color or a sequence of colors with the same
            length as nodelist. Color can be string or rgb (or rgba) tuple of
            floats from 0-1. If numeric values are specified they will be
            mapped to colors using the cmap and vmin,vmax parameters. See
            matplotlib.scatter for more details.

        node_shape :  string (default='o')
            The shape of the node.  Specification is as matplotlib.scatter
            marker, one of 'so^>v<dph8'.

        alpha : float or array of floats (default=None)
            The node transparency.  This can be a single alpha value,
            in which case it will be applied to all the nodes of color. Otherwise,
            if it is an array, the elements of alpha will be applied to the colors
            in order (cycling through alpha multiple times if necessary).

        cmap : Matplotlib colormap (default=None)
            Colormap for mapping intensities of nodes

        vmin,vmax : floats or None (default=None)
            Minimum and maximum for node colormap scaling

        linewidths : [None | scalar | sequence] (default=1.0)
            Line width of symbol border

        edgecolors : [None | scalar | sequence] (default = node_color)
            Colors of node borders. Can be a single color or a sequence of colors with the
            same length as nodelist. Color can be string or rgb (or rgba) tuple of floats
            from 0-1. If numeric values are specified they will be mapped to colors
            using the cmap and vmin,vmax parameters. See `~matplotlib.pyplot.scatter` for more details.

        label : [None | string]
            Label for legend

        margins : float or 2-tuple, optional
            Sets the padding for axis autoscaling. Increase margin to prevent
            clipping for nodes that are near the edges of an image. Values should
            be in the range ``[0, 1]``. See :meth:`matplotlib.axes.Axes.margins`
            for details. The default is `None`, which uses the Matplotlib default.

        hide_ticks : bool, optional
            Hide ticks of axes. When `True` (the default), ticks and ticklabels
            are removed from the axes. To set ticks and tick labels to the pyplot default,
            use ``hide_ticks=False``.

        Returns
        -------
        matplotlib.collections.PathCollection
            `PathCollection` of the nodes.

        Examples
        --------
        >>> G = nx.dodecahedral_graph()
        >>> nodes = nx.draw_networkx_nodes(G, pos=nx.spring_layout(G))

        Also see the NetworkX drawing examples at
        https://networkx.org/documentation/latest/auto_examples/index.html

        See Also
        --------
        draw
        draw_networkx
        draw_networkx_edges
        draw_networkx_labels
        draw_networkx_edge_labels

    draw_planar(G, **kwargs)
        Draw a planar networkx graph `G` with planar layout.

        This is a convenience function equivalent to::

            nx.draw(G, pos=nx.planar_layout(G), **kwargs)

        Parameters
        ----------
        G : graph
            A planar networkx graph

        kwargs : optional keywords
            See `draw_networkx` for a description of optional keywords.

        Raises
        ------
        NetworkXException
            When `G` is not planar

        Notes
        -----
        The layout is computed each time this function is called.
        For repeated drawing it is much more efficient to call
        `~networkx.drawing.layout.planar_layout` directly and reuse the result::

            >>> G = nx.path_graph(5)
            >>> pos = nx.planar_layout(G)
            >>> nx.draw(G, pos=pos)  # Draw the original graph
            >>> # Draw a subgraph, reusing the same node positions
            >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.draw_planar(G)

        See Also
        --------
        :func:`~networkx.drawing.layout.planar_layout`

    draw_random(G, **kwargs)
        Draw the graph `G` with a random layout.

        This is a convenience function equivalent to::

            nx.draw(G, pos=nx.random_layout(G), **kwargs)

        Parameters
        ----------
        G : graph
            A networkx graph

        kwargs : optional keywords
            See `draw_networkx` for a description of optional keywords.

        Notes
        -----
        The layout is computed each time this function is called.
        For repeated drawing it is much more efficient to call
        `~networkx.drawing.layout.random_layout` directly and reuse the result::

            >>> G = nx.complete_graph(5)
            >>> pos = nx.random_layout(G)
            >>> nx.draw(G, pos=pos)  # Draw the original graph
            >>> # Draw a subgraph, reusing the same node positions
            >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

        Examples
        --------
        >>> G = nx.lollipop_graph(4, 3)
        >>> nx.draw_random(G)

        See Also
        --------
        :func:`~networkx.drawing.layout.random_layout`

    draw_shell(G, nlist=None, **kwargs)
        Draw networkx graph `G` with shell layout.

        This is a convenience function equivalent to::

            nx.draw(G, pos=nx.shell_layout(G, nlist=nlist), **kwargs)

        Parameters
        ----------
        G : graph
            A networkx graph

        nlist : list of list of nodes, optional
            A list containing lists of nodes representing the shells.
            Default is `None`, meaning all nodes are in a single shell.
            See `~networkx.drawing.layout.shell_layout` for details.

        kwargs : optional keywords
            See `draw_networkx` for a description of optional keywords.

        Notes
        -----
        The layout is computed each time this function is called.
        For repeated drawing it is much more efficient to call
        `~networkx.drawing.layout.shell_layout` directly and reuse the result::

            >>> G = nx.complete_graph(5)
            >>> pos = nx.shell_layout(G)
            >>> nx.draw(G, pos=pos)  # Draw the original graph
            >>> # Draw a subgraph, reusing the same node positions
            >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> shells = [[0], [1, 2, 3]]
        >>> nx.draw_shell(G, nlist=shells)

        See Also
        --------
        :func:`~networkx.drawing.layout.shell_layout`

    draw_spectral(G, **kwargs)
        Draw the graph `G` with a spectral 2D layout.

        This is a convenience function equivalent to::

            nx.draw(G, pos=nx.spectral_layout(G), **kwargs)

        For more information about how node positions are determined, see
        `~networkx.drawing.layout.spectral_layout`.

        Parameters
        ----------
        G : graph
            A networkx graph

        kwargs : optional keywords
            See `draw_networkx` for a description of optional keywords.

        Notes
        -----
        The layout is computed each time this function is called.
        For repeated drawing it is much more efficient to call
        `~networkx.drawing.layout.spectral_layout` directly and reuse the result::

            >>> G = nx.complete_graph(5)
            >>> pos = nx.spectral_layout(G)
            >>> nx.draw(G, pos=pos)  # Draw the original graph
            >>> # Draw a subgraph, reusing the same node positions
            >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> nx.draw_spectral(G)

        See Also
        --------
        :func:`~networkx.drawing.layout.spectral_layout`

    draw_spring(G, **kwargs)
        Draw the graph `G` with a spring layout.

        This is a convenience function equivalent to::

            nx.draw(G, pos=nx.spring_layout(G), **kwargs)

        Parameters
        ----------
        G : graph
            A networkx graph

        kwargs : optional keywords
            See `draw_networkx` for a description of optional keywords.

        Notes
        -----
        `~networkx.drawing.layout.spring_layout` is also the default layout for
        `draw`, so this function is equivalent to `draw`.

        The layout is computed each time this function is called.
        For repeated drawing it is much more efficient to call
        `~networkx.drawing.layout.spring_layout` directly and reuse the result::

            >>> G = nx.complete_graph(5)
            >>> pos = nx.spring_layout(G)
            >>> nx.draw(G, pos=pos)  # Draw the original graph
            >>> # Draw a subgraph, reusing the same node positions
            >>> nx.draw(G.subgraph([0, 1, 2]), pos=pos, node_color="red")

        Examples
        --------
        >>> G = nx.path_graph(20)
        >>> nx.draw_spring(G)

        See Also
        --------
        draw
        :func:`~networkx.drawing.layout.spring_layout`

DATA
    __all__ = ['draw', 'draw_networkx', 'draw_networkx_nodes', 'draw_netwo...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\drawing\nx_pylab.py

networkx.octahedral_graph
Python Library Documentation: function octahedral_graph in module networkx.generators.small

octahedral_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Platonic Octahedral graph.

    The octahedral graph is the 6-node 12-edge Platonic graph having the
    connectivity of the octahedron [1]_. If 6 couples go to a party,
    and each person shakes hands with every person except his or her partner,
    then this graph describes the set of handshakes that take place;
    for this reason it is also called the cocktail party graph [2]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Octahedral graph

    References
    ----------
    .. [1] https://mathworld.wolfram.com/OctahedralGraph.html
    .. [2] https://en.wikipedia.org/wiki/Tur%C3%A1n_graph#Special_cases
networkx.omega
Python Library Documentation: function omega in module networkx.algorithms.smallworld

omega(G, niter=5, nrand=10, seed=None, *, backend=None, **backend_kwargs)
    Returns the small-world coefficient (omega) of a graph

    The small-world coefficient of a graph G is:

    omega = Lr/L - C/Cl

    where C and L are respectively the average clustering coefficient and
    average shortest path length of G. Lr is the average shortest path length
    of an equivalent random graph and Cl is the average clustering coefficient
    of an equivalent lattice graph.

    The small-world coefficient (omega) measures how much G is like a lattice
    or a random graph. Negative values mean G is similar to a lattice whereas
    positive values mean G is a random graph.
    Values close to 0 mean that G has small-world characteristics.

    Parameters
    ----------
    G : NetworkX graph
        An undirected graph.

    niter: integer (optional, default=5)
        Approximate number of rewiring per edge to compute the equivalent
        random graph.

    nrand: integer (optional, default=10)
        Number of random graphs generated to compute the maximal clustering
        coefficient (Cr) and average shortest path length (Lr).

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.


    Returns
    -------
    omega : float
        The small-world coefficient (omega)

    Notes
    -----
    The implementation is adapted from the algorithm by Telesford et al. [1]_.

    References
    ----------
    .. [1] Telesford, Joyce, Hayasaka, Burdette, and Laurienti (2011).
           "The Ubiquity of Small-World Networks".
           Brain Connectivity. 1 (0038): 367-75.  PMC 3604768. PMID 22432451.
           doi:10.1089/brain.2011.0038.
networkx.onion_layers
Python Library Documentation: function onion_layers in module networkx.algorithms.core

onion_layers(G, *, backend=None, **backend_kwargs)
    Returns the layer of each vertex in an onion decomposition of the graph.

    The onion decomposition refines the k-core decomposition by providing
    information on the internal organization of each k-shell. It is usually
    used alongside the `core numbers`.

    Parameters
    ----------
    G : NetworkX graph
        An undirected graph without self loops.

    Returns
    -------
    od_layers : dictionary
        A dictionary keyed by node to the onion layer. The layers are
        contiguous integers starting at 1.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a multigraph or directed graph or if it contains self loops.

    Examples
    --------
    >>> degrees = [0, 1, 2, 2, 2, 2, 3]
    >>> H = nx.havel_hakimi_graph(degrees)
    >>> H.degree
    DegreeView({0: 1, 1: 2, 2: 2, 3: 2, 4: 2, 5: 3, 6: 0})
    >>> nx.onion_layers(H)
    {6: 1, 0: 2, 4: 3, 1: 4, 2: 4, 3: 4, 5: 4}

    See Also
    --------
    core_number

    References
    ----------
    .. [1] Multi-scale structure and topological anomaly detection via a new
       network statistic: The onion decomposition
       L. Hébert-Dufresne, J. A. Grochow, and A. Allard
       Scientific Reports 6, 31708 (2016)
       http://doi.org/10.1038/srep31708
    .. [2] Percolation and the effective structure of complex networks
       A. Allard and L. Hébert-Dufresne
       Physical Review X 9, 011023 (2019)
       http://doi.org/10.1103/PhysRevX.9.011023
networkx.operators
Python Library Documentation: package networkx.algorithms.operators in networkx.algorithms

NAME
    networkx.algorithms.operators

PACKAGE CONTENTS
    all
    binary
    product
    tests (package)
    unary

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\operators\__init__.py

networkx.optimal_edit_paths
Python Library Documentation: function optimal_edit_paths in module networkx.algorithms.similarity

optimal_edit_paths(G1, G2, node_match=None, edge_match=None, node_subst_cost=None, node_del_cost=None, node_ins_cost=None, edge_subst_cost=None, edge_del_cost=None, edge_ins_cost=None, upper_bound=None, *, backend=None, **backend_kwargs)
    Returns all minimum-cost edit paths transforming G1 to G2.

    Graph edit path is a sequence of node and edge edit operations
    transforming graph G1 to graph isomorphic to G2.  Edit operations
    include substitutions, deletions, and insertions.

    Parameters
    ----------
    G1, G2: graphs
        The two graphs G1 and G2 must be of the same type.

    node_match : callable
        A function that returns True if node n1 in G1 and n2 in G2
        should be considered equal during matching.

        The function will be called like

           node_match(G1.nodes[n1], G2.nodes[n2]).

        That is, the function will receive the node attribute
        dictionaries for n1 and n2 as inputs.

        Ignored if node_subst_cost is specified.  If neither
        node_match nor node_subst_cost are specified then node
        attributes are not considered.

    edge_match : callable
        A function that returns True if the edge attribute dictionaries
        for the pair of nodes (u1, v1) in G1 and (u2, v2) in G2 should
        be considered equal during matching.

        The function will be called like

           edge_match(G1[u1][v1], G2[u2][v2]).

        That is, the function will receive the edge attribute
        dictionaries of the edges under consideration.

        Ignored if edge_subst_cost is specified.  If neither
        edge_match nor edge_subst_cost are specified then edge
        attributes are not considered.

    node_subst_cost, node_del_cost, node_ins_cost : callable
        Functions that return the costs of node substitution, node
        deletion, and node insertion, respectively.

        The functions will be called like

           node_subst_cost(G1.nodes[n1], G2.nodes[n2]),
           node_del_cost(G1.nodes[n1]),
           node_ins_cost(G2.nodes[n2]).

        That is, the functions will receive the node attribute
        dictionaries as inputs.  The functions are expected to return
        positive numeric values.

        Function node_subst_cost overrides node_match if specified.
        If neither node_match nor node_subst_cost are specified then
        default node substitution cost of 0 is used (node attributes
        are not considered during matching).

        If node_del_cost is not specified then default node deletion
        cost of 1 is used.  If node_ins_cost is not specified then
        default node insertion cost of 1 is used.

    edge_subst_cost, edge_del_cost, edge_ins_cost : callable
        Functions that return the costs of edge substitution, edge
        deletion, and edge insertion, respectively.

        The functions will be called like

           edge_subst_cost(G1[u1][v1], G2[u2][v2]),
           edge_del_cost(G1[u1][v1]),
           edge_ins_cost(G2[u2][v2]).

        That is, the functions will receive the edge attribute
        dictionaries as inputs.  The functions are expected to return
        positive numeric values.

        Function edge_subst_cost overrides edge_match if specified.
        If neither edge_match nor edge_subst_cost are specified then
        default edge substitution cost of 0 is used (edge attributes
        are not considered during matching).

        If edge_del_cost is not specified then default edge deletion
        cost of 1 is used.  If edge_ins_cost is not specified then
        default edge insertion cost of 1 is used.

    upper_bound : numeric
        Maximum edit distance to consider.

    Returns
    -------
    edit_paths : list of tuples (node_edit_path, edge_edit_path)
       - node_edit_path : list of tuples ``(u, v)`` indicating node transformations
         between `G1` and `G2`. ``u`` is `None` for insertion, ``v`` is `None`
         for deletion.
       - edge_edit_path : list of tuples ``((u1, v1), (u2, v2))`` indicating edge
         transformations between `G1` and `G2`. ``(None, (u2,v2))`` for insertion
         and ``((u1,v1), None)`` for deletion.

    cost : numeric
        Optimal edit path cost (graph edit distance). When the cost
        is zero, it indicates that `G1` and `G2` are isomorphic.

    Examples
    --------
    >>> G1 = nx.cycle_graph(4)
    >>> G2 = nx.wheel_graph(5)
    >>> paths, cost = nx.optimal_edit_paths(G1, G2)
    >>> len(paths)
    40
    >>> cost
    5.0

    Notes
    -----
    To transform `G1` into a graph isomorphic to `G2`, apply the node
    and edge edits in the returned ``edit_paths``.
    In the case of isomorphic graphs, the cost is zero, and the paths
    represent different isomorphic mappings (isomorphisms). That is, the
    edits involve renaming nodes and edges to match the structure of `G2`.

    See Also
    --------
    graph_edit_distance, optimize_edit_paths

    References
    ----------
    .. [1] Zeina Abu-Aisheh, Romain Raveaux, Jean-Yves Ramel, Patrick
       Martineau. An Exact Graph Edit Distance Algorithm for Solving
       Pattern Recognition Problems. 4th International Conference on
       Pattern Recognition Applications and Methods 2015, Jan 2015,
       Lisbon, Portugal. 2015,
       <10.5220/0005209202710278>. <hal-01168816>
       https://hal.archives-ouvertes.fr/hal-01168816
networkx.optimize_edit_paths
Python Library Documentation: function optimize_edit_paths in module networkx.algorithms.similarity

optimize_edit_paths(G1, G2, node_match=None, edge_match=None, node_subst_cost=None, node_del_cost=None, node_ins_cost=None, edge_subst_cost=None, edge_del_cost=None, edge_ins_cost=None, upper_bound=None, strictly_decreasing=True, roots=None, timeout=None, *, backend=None, **backend_kwargs)
    GED (graph edit distance) calculation: advanced interface.

    Graph edit path is a sequence of node and edge edit operations
    transforming graph G1 to graph isomorphic to G2.  Edit operations
    include substitutions, deletions, and insertions.

    Graph edit distance is defined as minimum cost of edit path.

    Parameters
    ----------
    G1, G2: graphs
        The two graphs G1 and G2 must be of the same type.

    node_match : callable
        A function that returns True if node n1 in G1 and n2 in G2
        should be considered equal during matching.

        The function will be called like

           node_match(G1.nodes[n1], G2.nodes[n2]).

        That is, the function will receive the node attribute
        dictionaries for n1 and n2 as inputs.

        Ignored if node_subst_cost is specified.  If neither
        node_match nor node_subst_cost are specified then node
        attributes are not considered.

    edge_match : callable
        A function that returns True if the edge attribute dictionaries
        for the pair of nodes (u1, v1) in G1 and (u2, v2) in G2 should
        be considered equal during matching.

        The function will be called like

           edge_match(G1[u1][v1], G2[u2][v2]).

        That is, the function will receive the edge attribute
        dictionaries of the edges under consideration.

        Ignored if edge_subst_cost is specified.  If neither
        edge_match nor edge_subst_cost are specified then edge
        attributes are not considered.

    node_subst_cost, node_del_cost, node_ins_cost : callable
        Functions that return the costs of node substitution, node
        deletion, and node insertion, respectively.

        The functions will be called like

           node_subst_cost(G1.nodes[n1], G2.nodes[n2]),
           node_del_cost(G1.nodes[n1]),
           node_ins_cost(G2.nodes[n2]).

        That is, the functions will receive the node attribute
        dictionaries as inputs.  The functions are expected to return
        positive numeric values.

        Function node_subst_cost overrides node_match if specified.
        If neither node_match nor node_subst_cost are specified then
        default node substitution cost of 0 is used (node attributes
        are not considered during matching).

        If node_del_cost is not specified then default node deletion
        cost of 1 is used.  If node_ins_cost is not specified then
        default node insertion cost of 1 is used.

    edge_subst_cost, edge_del_cost, edge_ins_cost : callable
        Functions that return the costs of edge substitution, edge
        deletion, and edge insertion, respectively.

        The functions will be called like

           edge_subst_cost(G1[u1][v1], G2[u2][v2]),
           edge_del_cost(G1[u1][v1]),
           edge_ins_cost(G2[u2][v2]).

        That is, the functions will receive the edge attribute
        dictionaries as inputs.  The functions are expected to return
        positive numeric values.

        Function edge_subst_cost overrides edge_match if specified.
        If neither edge_match nor edge_subst_cost are specified then
        default edge substitution cost of 0 is used (edge attributes
        are not considered during matching).

        If edge_del_cost is not specified then default edge deletion
        cost of 1 is used.  If edge_ins_cost is not specified then
        default edge insertion cost of 1 is used.

    upper_bound : numeric
        Maximum edit distance to consider.

    strictly_decreasing : bool
        If True, return consecutive approximations of strictly
        decreasing cost.  Otherwise, return all edit paths of cost
        less than or equal to the previous minimum cost.

    roots : 2-tuple
        Tuple where first element is a node in G1 and the second
        is a node in G2.
        These nodes are forced to be matched in the comparison to
        allow comparison between rooted graphs.

    timeout : numeric
        Maximum number of seconds to execute.
        After timeout is met, the current best GED is returned.

    Returns
    -------
    Generator of tuples (node_edit_path, edge_edit_path, cost)
        node_edit_path : list of tuples (u, v)
        edge_edit_path : list of tuples ((u1, v1), (u2, v2))
        cost : numeric

    See Also
    --------
    graph_edit_distance, optimize_graph_edit_distance, optimal_edit_paths

    References
    ----------
    .. [1] Zeina Abu-Aisheh, Romain Raveaux, Jean-Yves Ramel, Patrick
       Martineau. An Exact Graph Edit Distance Algorithm for Solving
       Pattern Recognition Problems. 4th International Conference on
       Pattern Recognition Applications and Methods 2015, Jan 2015,
       Lisbon, Portugal. 2015,
       <10.5220/0005209202710278>. <hal-01168816>
       https://hal.archives-ouvertes.fr/hal-01168816
networkx.optimize_graph_edit_distance
Python Library Documentation: function optimize_graph_edit_distance in module networkx.algorithms.similarity

optimize_graph_edit_distance(G1, G2, node_match=None, edge_match=None, node_subst_cost=None, node_del_cost=None, node_ins_cost=None, edge_subst_cost=None, edge_del_cost=None, edge_ins_cost=None, upper_bound=None, *, backend=None, **backend_kwargs)
    Returns consecutive approximations of GED (graph edit distance)
    between graphs G1 and G2.

    Graph edit distance is a graph similarity measure analogous to
    Levenshtein distance for strings.  It is defined as minimum cost
    of edit path (sequence of node and edge edit operations)
    transforming graph G1 to graph isomorphic to G2.

    Parameters
    ----------
    G1, G2: graphs
        The two graphs G1 and G2 must be of the same type.

    node_match : callable
        A function that returns True if node n1 in G1 and n2 in G2
        should be considered equal during matching.

        The function will be called like

           node_match(G1.nodes[n1], G2.nodes[n2]).

        That is, the function will receive the node attribute
        dictionaries for n1 and n2 as inputs.

        Ignored if node_subst_cost is specified.  If neither
        node_match nor node_subst_cost are specified then node
        attributes are not considered.

    edge_match : callable
        A function that returns True if the edge attribute dictionaries
        for the pair of nodes (u1, v1) in G1 and (u2, v2) in G2 should
        be considered equal during matching.

        The function will be called like

           edge_match(G1[u1][v1], G2[u2][v2]).

        That is, the function will receive the edge attribute
        dictionaries of the edges under consideration.

        Ignored if edge_subst_cost is specified.  If neither
        edge_match nor edge_subst_cost are specified then edge
        attributes are not considered.

    node_subst_cost, node_del_cost, node_ins_cost : callable
        Functions that return the costs of node substitution, node
        deletion, and node insertion, respectively.

        The functions will be called like

           node_subst_cost(G1.nodes[n1], G2.nodes[n2]),
           node_del_cost(G1.nodes[n1]),
           node_ins_cost(G2.nodes[n2]).

        That is, the functions will receive the node attribute
        dictionaries as inputs.  The functions are expected to return
        positive numeric values.

        Function node_subst_cost overrides node_match if specified.
        If neither node_match nor node_subst_cost are specified then
        default node substitution cost of 0 is used (node attributes
        are not considered during matching).

        If node_del_cost is not specified then default node deletion
        cost of 1 is used.  If node_ins_cost is not specified then
        default node insertion cost of 1 is used.

    edge_subst_cost, edge_del_cost, edge_ins_cost : callable
        Functions that return the costs of edge substitution, edge
        deletion, and edge insertion, respectively.

        The functions will be called like

           edge_subst_cost(G1[u1][v1], G2[u2][v2]),
           edge_del_cost(G1[u1][v1]),
           edge_ins_cost(G2[u2][v2]).

        That is, the functions will receive the edge attribute
        dictionaries as inputs.  The functions are expected to return
        positive numeric values.

        Function edge_subst_cost overrides edge_match if specified.
        If neither edge_match nor edge_subst_cost are specified then
        default edge substitution cost of 0 is used (edge attributes
        are not considered during matching).

        If edge_del_cost is not specified then default edge deletion
        cost of 1 is used.  If edge_ins_cost is not specified then
        default edge insertion cost of 1 is used.

    upper_bound : numeric
        Maximum edit distance to consider.

    Returns
    -------
    Generator of consecutive approximations of graph edit distance.

    Examples
    --------
    >>> G1 = nx.cycle_graph(6)
    >>> G2 = nx.wheel_graph(7)
    >>> for v in nx.optimize_graph_edit_distance(G1, G2):
    ...     minv = v
    >>> minv
    7.0

    See Also
    --------
    graph_edit_distance, optimize_edit_paths

    References
    ----------
    .. [1] Zeina Abu-Aisheh, Romain Raveaux, Jean-Yves Ramel, Patrick
       Martineau. An Exact Graph Edit Distance Algorithm for Solving
       Pattern Recognition Problems. 4th International Conference on
       Pattern Recognition Applications and Methods 2015, Jan 2015,
       Lisbon, Portugal. 2015,
       <10.5220/0005209202710278>. <hal-01168816>
       https://hal.archives-ouvertes.fr/hal-01168816
networkx.out_degree_centrality
Python Library Documentation: function out_degree_centrality in module networkx.algorithms.centrality.degree_alg

out_degree_centrality(G, *, backend=None, **backend_kwargs)
    Compute the out-degree centrality for nodes.

    The out-degree centrality for a node v is the fraction of nodes its
    outgoing edges are connected to.

    Parameters
    ----------
    G : graph
        A NetworkX graph

    Returns
    -------
    nodes : dictionary
        Dictionary of nodes with out-degree centrality as values.

    Raises
    ------
    NetworkXNotImplemented
        If G is undirected.

    Examples
    --------
    >>> G = nx.DiGraph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3)])
    >>> nx.out_degree_centrality(G)
    {0: 1.0, 1: 0.6666666666666666, 2: 0.0, 3: 0.0}

    See Also
    --------
    degree_centrality, in_degree_centrality

    Notes
    -----
    The degree centrality values are normalized by dividing by the maximum
    possible degree in a simple graph n-1 where n is the number of nodes in G.

    For multigraphs or graphs with self loops the maximum degree might
    be higher than n-1 and values of degree centrality greater than 1
    are possible.
networkx.overall_reciprocity
Python Library Documentation: function overall_reciprocity in module networkx.algorithms.reciprocity

overall_reciprocity(G, *, backend=None, **backend_kwargs)
    Compute the reciprocity for the whole graph.

    See the doc of reciprocity for the definition.

    Parameters
    ----------
    G : graph
       A networkx graph
networkx.pagerank
Python Library Documentation: function pagerank in module networkx.algorithms.link_analysis.pagerank_alg

pagerank(G, alpha=0.85, personalization=None, max_iter=100, tol=1e-06, nstart=None, weight='weight', dangling=None, *, backend=None, **backend_kwargs)
    Returns the PageRank of the nodes in the graph.

    PageRank computes a ranking of the nodes in the graph G based on
    the structure of the incoming links. It was originally designed as
    an algorithm to rank web pages.

    Parameters
    ----------
    G : graph
      A NetworkX graph.  Undirected graphs will be converted to a directed
      graph with two directed edges for each undirected edge.

    alpha : float, optional
      Damping parameter for PageRank, default=0.85.

    personalization: dict, optional
      The "personalization vector" consisting of a dictionary with a
      key some subset of graph nodes and personalization value each of those.
      At least one personalization value must be non-zero.
      If not specified, a nodes personalization value will be zero.
      By default, a uniform distribution is used.

    max_iter : integer, optional
      Maximum number of iterations in power method eigenvalue solver.

    tol : float, optional
      Error tolerance used to check convergence in power method solver.
      The iteration will stop after a tolerance of ``len(G) * tol`` is reached.

    nstart : dictionary, optional
      Starting value of PageRank iteration for each node.

    weight : key, optional
      Edge data key to use as weight.  If None weights are set to 1.

    dangling: dict, optional
      The outedges to be assigned to any "dangling" nodes, i.e., nodes without
      any outedges. The dict key is the node the outedge points to and the dict
      value is the weight of that outedge. By default, dangling nodes are given
      outedges according to the personalization vector (uniform if not
      specified). This must be selected to result in an irreducible transition
      matrix (see notes under google_matrix). It may be common to have the
      dangling dict to be the same as the personalization dict.


    Returns
    -------
    pagerank : dictionary
       Dictionary of nodes with PageRank as value

    Examples
    --------
    >>> G = nx.DiGraph(nx.path_graph(4))
    >>> pr = nx.pagerank(G, alpha=0.9)

    Notes
    -----
    The eigenvector calculation is done by the power iteration method
    and has no guarantee of convergence.  The iteration will stop after
    an error tolerance of ``len(G) * tol`` has been reached. If the
    number of iterations exceed `max_iter`, a
    :exc:`networkx.exception.PowerIterationFailedConvergence` exception
    is raised.

    The PageRank algorithm was designed for directed graphs but this
    algorithm does not check if the input graph is directed and will
    execute on undirected graphs by converting each edge in the
    directed graph to two edges.

    See Also
    --------
    google_matrix

    Raises
    ------
    PowerIterationFailedConvergence
        If the algorithm fails to converge to the specified tolerance
        within the specified number of iterations of the power iteration
        method.

    References
    ----------
    .. [1] A. Langville and C. Meyer,
       "A survey of eigenvector methods of web information retrieval."
       http://citeseer.ist.psu.edu/713792.html
    .. [2] Page, Lawrence; Brin, Sergey; Motwani, Rajeev and Winograd, Terry,
       The PageRank citation ranking: Bringing order to the Web. 1999
       http://dbpubs.stanford.edu:8090/pub/showDoc.Fulltext?lang=en&doc=1999-66&format=pdf
networkx.pagerank_alg
Python Library Documentation: module networkx.algorithms.link_analysis.pagerank_alg in networkx.algorithms.link_analysis

NAME
    networkx.algorithms.link_analysis.pagerank_alg - PageRank analysis of graph structure.

FUNCTIONS
    google_matrix(G, alpha=0.85, personalization=None, nodelist=None, weight='weight', dangling=None, *, backend=None, **backend_kwargs)
        Returns the Google matrix of the graph.

        Parameters
        ----------
        G : graph
          A NetworkX graph.  Undirected graphs will be converted to a directed
          graph with two directed edges for each undirected edge.

        alpha : float
          The damping factor.

        personalization: dict, optional
          The "personalization vector" consisting of a dictionary with a
          key some subset of graph nodes and personalization value each of those.
          At least one personalization value must be non-zero.
          If not specified, a nodes personalization value will be zero.
          By default, a uniform distribution is used.

        nodelist : list, optional
          The rows and columns are ordered according to the nodes in nodelist.
          If nodelist is None, then the ordering is produced by G.nodes().

        weight : key, optional
          Edge data key to use as weight.  If None weights are set to 1.

        dangling: dict, optional
          The outedges to be assigned to any "dangling" nodes, i.e., nodes without
          any outedges. The dict key is the node the outedge points to and the dict
          value is the weight of that outedge. By default, dangling nodes are given
          outedges according to the personalization vector (uniform if not
          specified) This must be selected to result in an irreducible transition
          matrix (see notes below). It may be common to have the dangling dict to
          be the same as the personalization dict.

        Returns
        -------
        A : 2D NumPy ndarray
           Google matrix of the graph

        Notes
        -----
        The array returned represents the transition matrix that describes the
        Markov chain used in PageRank. For PageRank to converge to a unique
        solution (i.e., a unique stationary distribution in a Markov chain), the
        transition matrix must be irreducible. In other words, it must be that
        there exists a path between every pair of nodes in the graph, or else there
        is the potential of "rank sinks."

        This implementation works with Multi(Di)Graphs. For multigraphs the
        weight between two nodes is set to be the sum of all edge weights
        between those nodes.

        See Also
        --------
        pagerank

    pagerank(G, alpha=0.85, personalization=None, max_iter=100, tol=1e-06, nstart=None, weight='weight', dangling=None, *, backend=None, **backend_kwargs)
        Returns the PageRank of the nodes in the graph.

        PageRank computes a ranking of the nodes in the graph G based on
        the structure of the incoming links. It was originally designed as
        an algorithm to rank web pages.

        Parameters
        ----------
        G : graph
          A NetworkX graph.  Undirected graphs will be converted to a directed
          graph with two directed edges for each undirected edge.

        alpha : float, optional
          Damping parameter for PageRank, default=0.85.

        personalization: dict, optional
          The "personalization vector" consisting of a dictionary with a
          key some subset of graph nodes and personalization value each of those.
          At least one personalization value must be non-zero.
          If not specified, a nodes personalization value will be zero.
          By default, a uniform distribution is used.

        max_iter : integer, optional
          Maximum number of iterations in power method eigenvalue solver.

        tol : float, optional
          Error tolerance used to check convergence in power method solver.
          The iteration will stop after a tolerance of ``len(G) * tol`` is reached.

        nstart : dictionary, optional
          Starting value of PageRank iteration for each node.

        weight : key, optional
          Edge data key to use as weight.  If None weights are set to 1.

        dangling: dict, optional
          The outedges to be assigned to any "dangling" nodes, i.e., nodes without
          any outedges. The dict key is the node the outedge points to and the dict
          value is the weight of that outedge. By default, dangling nodes are given
          outedges according to the personalization vector (uniform if not
          specified). This must be selected to result in an irreducible transition
          matrix (see notes under google_matrix). It may be common to have the
          dangling dict to be the same as the personalization dict.


        Returns
        -------
        pagerank : dictionary
           Dictionary of nodes with PageRank as value

        Examples
        --------
        >>> G = nx.DiGraph(nx.path_graph(4))
        >>> pr = nx.pagerank(G, alpha=0.9)

        Notes
        -----
        The eigenvector calculation is done by the power iteration method
        and has no guarantee of convergence.  The iteration will stop after
        an error tolerance of ``len(G) * tol`` has been reached. If the
        number of iterations exceed `max_iter`, a
        :exc:`networkx.exception.PowerIterationFailedConvergence` exception
        is raised.

        The PageRank algorithm was designed for directed graphs but this
        algorithm does not check if the input graph is directed and will
        execute on undirected graphs by converting each edge in the
        directed graph to two edges.

        See Also
        --------
        google_matrix

        Raises
        ------
        PowerIterationFailedConvergence
            If the algorithm fails to converge to the specified tolerance
            within the specified number of iterations of the power iteration
            method.

        References
        ----------
        .. [1] A. Langville and C. Meyer,
           "A survey of eigenvector methods of web information retrieval."
           http://citeseer.ist.psu.edu/713792.html
        .. [2] Page, Lawrence; Brin, Sergey; Motwani, Rajeev and Winograd, Terry,
           The PageRank citation ranking: Bringing order to the Web. 1999
           http://dbpubs.stanford.edu:8090/pub/showDoc.Fulltext?lang=en&doc=1999-66&format=pdf

DATA
    __all__ = ['pagerank', 'google_matrix']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\link_analysis\pagerank_alg.py

networkx.pairs
Python Library Documentation: module networkx.algorithms.assortativity.pairs in networkx.algorithms.assortativity

NAME
    networkx.algorithms.assortativity.pairs - Generators of x-y pairs of node data.

FUNCTIONS
    node_attribute_xy(G, attribute, nodes=None, *, backend=None, **backend_kwargs)
        Yields 2-tuples of node attribute values for all edges in `G`.

        This generator yields, for each edge in `G` incident to a node in `nodes`,
        a 2-tuple of form ``(attribute value,  attribute value)`` for the parameter
        specified node-attribute.

        Parameters
        ----------
        G: NetworkX graph

        attribute: key
            The node attribute key.

        nodes: list or iterable (optional)
            Use only edges that are incident to specified nodes.
            The default is all nodes.

        Yields
        ------
        (x, y): 2-tuple
            Generates 2-tuple of (attribute, attribute) values.

        Examples
        --------
        >>> G = nx.DiGraph()
        >>> G.add_node(1, color="red")
        >>> G.add_node(2, color="blue")
        >>> G.add_node(3, color="green")
        >>> G.add_edge(1, 2)
        >>> list(nx.node_attribute_xy(G, "color"))
        [('red', 'blue')]

        Notes
        -----
        For undirected graphs, each edge is produced twice, once for each edge
        representation (u, v) and (v, u), with the exception of self-loop edges
        which only appear once.

    node_degree_xy(G, x='out', y='in', weight=None, nodes=None, *, backend=None, **backend_kwargs)
        Yields 2-tuples of ``(degree, degree)`` values for edges in `G`.

        This generator yields, for each edge in `G` incident to a node in `nodes`,
        a 2-tuple of form ``(degree, degree)``. The node degrees are weighted
        when a `weight` attribute is specified.

        Parameters
        ----------
        G: NetworkX graph

        x: string ('in','out')
           The degree type for source node (directed graphs only).

        y: string ('in','out')
           The degree type for target node (directed graphs only).

        weight: string or None, optional (default=None)
           The edge attribute that holds the numerical value used
           as a weight.  If None, then each edge has weight 1.
           The degree is the sum of the edge weights adjacent to the node.

        nodes: list or iterable (optional)
            Use only edges that are adjacency to specified nodes.
            The default is all nodes.

        Yields
        ------
        (x, y): 2-tuple
            Generates 2-tuple of (degree, degree) values.

        Examples
        --------
        >>> G = nx.DiGraph()
        >>> G.add_edge(1, 2)
        >>> list(nx.node_degree_xy(G, x="out", y="in"))
        [(1, 1)]
        >>> list(nx.node_degree_xy(G, x="in", y="out"))
        [(0, 0)]

        Notes
        -----
        For undirected graphs, each edge is produced twice, once for each edge
        representation (u, v) and (v, u), with the exception of self-loop edges
        which only appear once.

DATA
    __all__ = ['node_attribute_xy', 'node_degree_xy']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\assortativity\pairs.py

networkx.pajek
Python Library Documentation: module networkx.readwrite.pajek in networkx.readwrite

NAME
    networkx.readwrite.pajek

DESCRIPTION
    *****
    Pajek
    *****
    Read graphs in Pajek format.

    This implementation handles directed and undirected graphs including
    those with self loops and parallel edges.

    Format
    ------
    See http://vlado.fmf.uni-lj.si/pub/networks/pajek/doc/draweps.htm
    for format information.

FUNCTIONS
    generate_pajek(G)
        Generate lines in Pajek graph format.

        Parameters
        ----------
        G : graph
           A Networkx graph

        References
        ----------
        See http://vlado.fmf.uni-lj.si/pub/networks/pajek/doc/draweps.htm
        for format information.

    parse_pajek(lines, *, backend=None, **backend_kwargs)
        Parse Pajek format graph from string or iterable.

        Parameters
        ----------
        lines : string or iterable
           Data in Pajek format.

        Returns
        -------
        G : NetworkX graph

        See Also
        --------
        read_pajek

    read_pajek(path, encoding='UTF-8', *, backend=None, **backend_kwargs)
        Read graph in Pajek format from path.

        Parameters
        ----------
        path : file or string
           File or filename to write.
           Filenames ending in .gz or .bz2 will be uncompressed.

        Returns
        -------
        G : NetworkX MultiGraph or MultiDiGraph.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_pajek(G, "test.net")
        >>> G = nx.read_pajek("test.net")

        To create a Graph instead of a MultiGraph use

        >>> G1 = nx.Graph(G)

        References
        ----------
        See http://vlado.fmf.uni-lj.si/pub/networks/pajek/doc/draweps.htm
        for format information.

    write_pajek(G, path, encoding='UTF-8')
        Write graph in Pajek format to path.

        Parameters
        ----------
        G : graph
           A Networkx graph
        path : file or string
           File or filename to write.
           Filenames ending in .gz or .bz2 will be compressed.

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> nx.write_pajek(G, "test.net")

        Warnings
        --------
        Optional node attributes and edge attributes must be non-empty strings.
        Otherwise it will not be written into the file. You will need to
        convert those attributes to strings if you want to keep them.

        References
        ----------
        See http://vlado.fmf.uni-lj.si/pub/networks/pajek/doc/draweps.htm
        for format information.

DATA
    __all__ = ['read_pajek', 'parse_pajek', 'generate_pajek', 'write_pajek...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\pajek.py

networkx.paley_graph
Python Library Documentation: function paley_graph in module networkx.generators.expanders

paley_graph(p, create_using=None, *, backend=None, **backend_kwargs)
    Returns the Paley $\frac{(p-1)}{2}$ -regular graph on $p$ nodes.

    The returned graph is a graph on $\mathbb{Z}/p\mathbb{Z}$ with edges between $x$ and $y$
    if and only if $x-y$ is a nonzero square in $\mathbb{Z}/p\mathbb{Z}$.

    If $p \equiv 1  \pmod 4$, $-1$ is a square in $\mathbb{Z}/p\mathbb{Z}$ and therefore $x-y$ is a square if and
    only if $y-x$ is also a square, i.e the edges in the Paley graph are symmetric.

    If $p \equiv 3 \pmod 4$, $-1$ is not a square in $\mathbb{Z}/p\mathbb{Z}$ and therefore either $x-y$ or $y-x$
    is a square in $\mathbb{Z}/p\mathbb{Z}$ but not both.

    Note that a more general definition of Paley graphs extends this construction
    to graphs over $q=p^n$ vertices, by using the finite field $F_q$ instead of $\mathbb{Z}/p\mathbb{Z}$.
    This construction requires to compute squares in general finite fields and is
    not what is implemented here (i.e `paley_graph(25)` does not return the true
    Paley graph associated with $5^2$).

    Parameters
    ----------
    p : int, an odd prime number.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : graph
        The constructed directed graph.

    Raises
    ------
    NetworkXError
        If the graph is a multigraph.

    References
    ----------
    Chapter 13 in B. Bollobas, Random Graphs. Second edition.
    Cambridge Studies in Advanced Mathematics, 73.
    Cambridge University Press, Cambridge (2001).
networkx.panther_similarity
Python Library Documentation: function panther_similarity in module networkx.algorithms.similarity

panther_similarity(G, source, k=5, path_length=5, c=0.5, delta=0.1, eps=None, weight='weight', *, backend=None, **backend_kwargs)
    Returns the Panther similarity of nodes in the graph `G` to node ``v``.

    Panther is a similarity metric that says "two objects are considered
    to be similar if they frequently appear on the same paths." [1]_.

    Parameters
    ----------
    G : NetworkX graph
        A NetworkX graph
    source : node
        Source node for which to find the top `k` similar other nodes
    k : int (default = 5)
        The number of most similar nodes to return.
    path_length : int (default = 5)
        How long the randomly generated paths should be (``T`` in [1]_)
    c : float (default = 0.5)
        A universal positive constant used to scale the number
        of sample random paths to generate.
    delta : float (default = 0.1)
        The probability that the similarity $S$ is not an epsilon-approximation to (R, phi),
        where $R$ is the number of random paths and $\phi$ is the probability
        that an element sampled from a set $A \subseteq D$, where $D$ is the domain.
    eps : float or None (default = None)
        The error bound. Per [1]_, a good value is ``sqrt(1/|E|)``. Therefore,
        if no value is provided, the recommended computed value will be used.
    weight : string or None, optional (default="weight")
        The name of an edge attribute that holds the numerical value
        used as a weight. If None then each edge has weight 1.

    Returns
    -------
    similarity : dictionary
        Dictionary of nodes to similarity scores (as floats). Note:
        the self-similarity (i.e., ``v``) will not be included in
        the returned dictionary. So, for ``k = 5``, a dictionary of
        top 4 nodes and their similarity scores will be returned.

    Raises
    ------
    NetworkXUnfeasible
        If `source` is an isolated node.

    NodeNotFound
        If `source` is not in `G`.

    Notes
    -----
        The isolated nodes in `G` are ignored.

    Examples
    --------
    >>> G = nx.star_graph(10)
    >>> sim = nx.panther_similarity(G, 0)

    References
    ----------
    .. [1] Zhang, J., Tang, J., Ma, C., Tong, H., Jing, Y., & Li, J.
           Panther: Fast top-k similarity search on large networks.
           In Proceedings of the ACM SIGKDD International Conference
           on Knowledge Discovery and Data Mining (Vol. 2015-August, pp. 1445–1454).
           Association for Computing Machinery. https://doi.org/10.1145/2783258.2783267.
networkx.pappus_graph
Python Library Documentation: function pappus_graph in module networkx.generators.small

pappus_graph(*, backend=None, **backend_kwargs)
    Returns the Pappus graph.

    The Pappus graph is a cubic symmetric distance-regular graph with 18 nodes
    and 27 edges. It is Hamiltonian and can be represented in LCF notation as
    [5,7,-7,7,-7,-5]^3 [1]_.

    Returns
    -------
    G : networkx Graph
        Pappus graph

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Pappus_graph
networkx.parse_adjlist
Python Library Documentation: function parse_adjlist in module networkx.readwrite.adjlist

parse_adjlist(lines, comments='#', delimiter=None, create_using=None, nodetype=None, *, backend=None, **backend_kwargs)
    Parse lines of a graph adjacency list representation.

    Parameters
    ----------
    lines : list or iterator of strings
        Input data in adjlist format

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    nodetype : Python type, optional
       Convert nodes to this type.

    comments : string, optional
       Marker for comment lines

    delimiter : string, optional
       Separator for node labels.  The default is whitespace.

    Returns
    -------
    G: NetworkX graph
        The graph corresponding to the lines in adjacency list format.

    Examples
    --------
    >>> lines = ["1 2 5", "2 3 4", "3 5", "4", "5"]
    >>> G = nx.parse_adjlist(lines, nodetype=int)
    >>> nodes = [1, 2, 3, 4, 5]
    >>> all(node in G for node in nodes)
    True
    >>> edges = [(1, 2), (1, 5), (2, 3), (2, 4), (3, 5)]
    >>> all((u, v) in G.edges() or (v, u) in G.edges() for (u, v) in edges)
    True

    See Also
    --------
    read_adjlist
networkx.parse_edgelist
Python Library Documentation: function parse_edgelist in module networkx.readwrite.edgelist

parse_edgelist(lines, comments='#', delimiter=None, create_using=None, nodetype=None, data=True, *, backend=None, **backend_kwargs)
    Parse lines of an edge list representation of a graph.

    Parameters
    ----------
    lines : list or iterator of strings
        Input data in edgelist format
    comments : string, optional
       Marker for comment lines. Default is `'#'`. To specify that no character
       should be treated as a comment, use ``comments=None``.
    delimiter : string, optional
       Separator for node labels. Default is `None`, meaning any whitespace.
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.
    nodetype : Python type, optional
       Convert nodes to this type. Default is `None`, meaning no conversion is
       performed.
    data : bool or list of (label,type) tuples
       If `False` generate no edge data or if `True` use a dictionary
       representation of edge data or a list tuples specifying dictionary
       key names and types for edge data.

    Returns
    -------
    G: NetworkX Graph
        The graph corresponding to lines

    Examples
    --------
    Edgelist with no data:

    >>> lines = ["1 2", "2 3", "3 4"]
    >>> G = nx.parse_edgelist(lines, nodetype=int)
    >>> list(G)
    [1, 2, 3, 4]
    >>> list(G.edges())
    [(1, 2), (2, 3), (3, 4)]

    Edgelist with data in Python dictionary representation:

    >>> lines = ["1 2 {'weight': 3}", "2 3 {'weight': 27}", "3 4 {'weight': 3.0}"]
    >>> G = nx.parse_edgelist(lines, nodetype=int)
    >>> list(G)
    [1, 2, 3, 4]
    >>> list(G.edges(data=True))
    [(1, 2, {'weight': 3}), (2, 3, {'weight': 27}), (3, 4, {'weight': 3.0})]

    Edgelist with data in a list:

    >>> lines = ["1 2 3", "2 3 27", "3 4 3.0"]
    >>> G = nx.parse_edgelist(lines, nodetype=int, data=(("weight", float),))
    >>> list(G)
    [1, 2, 3, 4]
    >>> list(G.edges(data=True))
    [(1, 2, {'weight': 3.0}), (2, 3, {'weight': 27.0}), (3, 4, {'weight': 3.0})]

    See Also
    --------
    read_weighted_edgelist
networkx.parse_gml
Python Library Documentation: function parse_gml in module networkx.readwrite.gml

parse_gml(lines, label='label', destringizer=None, *, backend=None, **backend_kwargs)
    Parse GML graph from a string or iterable.

    Parameters
    ----------
    lines : string or iterable of strings
       Data in GML format.

    label : string, optional
        If not None, the parsed nodes will be renamed according to node
        attributes indicated by `label`. Default value: 'label'.

    destringizer : callable, optional
        A `destringizer` that recovers values stored as strings in GML. If it
        cannot convert a string to a value, a `ValueError` is raised. Default
        value : None.

    Returns
    -------
    G : NetworkX graph
        The parsed graph.

    Raises
    ------
    NetworkXError
        If the input cannot be parsed.

    See Also
    --------
    write_gml, read_gml

    Notes
    -----
    This stores nested GML attributes as dictionaries in the NetworkX graph,
    node, and edge attribute structures.

    GML files are stored using a 7-bit ASCII encoding with any extended
    ASCII characters (iso8859-1) appearing as HTML character entities.
    Without specifying a `stringizer`/`destringizer`, the code is capable of
    writing `int`/`float`/`str`/`dict`/`list` data as required by the GML
    specification.  For writing other data types, and for reading data other
    than `str` you need to explicitly supply a `stringizer`/`destringizer`.

    For additional documentation on the GML file format, please see the
    `GML url <https://web.archive.org/web/20190207140002/http://www.fim.uni-passau.de/index.php?id=17297&L=1>`_.

    See the module docstring :mod:`networkx.readwrite.gml` for more details.
networkx.parse_graphml
Python Library Documentation: function parse_graphml in module networkx.readwrite.graphml

parse_graphml(graphml_string, node_type=<class 'str'>, edge_key_type=<class 'int'>, force_multigraph=False, *, backend=None, **backend_kwargs)
    Read graph in GraphML format from string.

    Parameters
    ----------
    graphml_string : string
       String containing graphml information
       (e.g., contents of a graphml file).

    node_type: Python type (default: str)
       Convert node ids to this type

    edge_key_type: Python type (default: int)
       Convert graphml edge ids to this type. Multigraphs use id as edge key.
       Non-multigraphs add to edge attribute dict with name "id".

    force_multigraph : bool (default: False)
       If True, return a multigraph with edge keys. If False (the default)
       return a multigraph when multiedges are in the graph.


    Returns
    -------
    graph: NetworkX graph
        If no parallel edges are found a Graph or DiGraph is returned.
        Otherwise a MultiGraph or MultiDiGraph is returned.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> linefeed = chr(10)  # linefeed =

    >>> s = linefeed.join(nx.generate_graphml(G))
    >>> H = nx.parse_graphml(s)

    Notes
    -----
    Default node and edge attributes are not propagated to each node and edge.
    They can be obtained from `G.graph` and applied to node and edge attributes
    if desired using something like this:

    >>> default_color = G.graph["node_default"]["color"]  # doctest: +SKIP
    >>> for node, data in G.nodes(data=True):  # doctest: +SKIP
    ...     if "color" not in data:
    ...         data["color"] = default_color
    >>> default_color = G.graph["edge_default"]["color"]  # doctest: +SKIP
    >>> for u, v, data in G.edges(data=True):  # doctest: +SKIP
    ...     if "color" not in data:
    ...         data["color"] = default_color

    This implementation does not support mixed graphs (directed and unidirected
    edges together), hypergraphs, nested graphs, or ports.

    For multigraphs the GraphML edge "id" will be used as the edge
    key.  If not specified then they "key" attribute will be used.  If
    there is no "key" attribute a default NetworkX multigraph edge key
    will be provided.
networkx.parse_leda
Python Library Documentation: function parse_leda in module networkx.readwrite.leda

parse_leda(lines, *, backend=None, **backend_kwargs)
    Read graph in LEDA format from string or iterable.

    Parameters
    ----------
    lines : string or iterable
       Data in LEDA format.

    Returns
    -------
    G : NetworkX graph

    Examples
    --------
    G=nx.parse_leda(string)

    References
    ----------
    .. [1] http://www.algorithmic-solutions.info/leda_guide/graphs/leda_native_graph_fileformat.html
networkx.parse_multiline_adjlist
Python Library Documentation: function parse_multiline_adjlist in module networkx.readwrite.multiline_adjlist

parse_multiline_adjlist(lines, comments='#', delimiter=None, create_using=None, nodetype=None, edgetype=None, *, backend=None, **backend_kwargs)
    Parse lines of a multiline adjacency list representation of a graph.

    Parameters
    ----------
    lines : list or iterator of strings
        Input data in multiline adjlist format

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    nodetype : Python type, optional
       Convert nodes to this type.

    edgetype : Python type, optional
       Convert edges to this type.

    comments : string, optional
       Marker for comment lines

    delimiter : string, optional
       Separator for node labels.  The default is whitespace.

    Returns
    -------
    G: NetworkX graph
        The graph corresponding to the lines in multiline adjacency list format.

    Examples
    --------
    >>> lines = [
    ...     "1 2",
    ...     "2 {'weight':3, 'name': 'Frodo'}",
    ...     "3 {}",
    ...     "2 1",
    ...     "5 {'weight':6, 'name': 'Saruman'}",
    ... ]
    >>> G = nx.parse_multiline_adjlist(iter(lines), nodetype=int)
    >>> list(G)
    [1, 2, 3, 5]
networkx.parse_pajek
Python Library Documentation: function parse_pajek in module networkx.readwrite.pajek

parse_pajek(lines, *, backend=None, **backend_kwargs)
    Parse Pajek format graph from string or iterable.

    Parameters
    ----------
    lines : string or iterable
       Data in Pajek format.

    Returns
    -------
    G : NetworkX graph

    See Also
    --------
    read_pajek
networkx.partial_duplication_graph
Python Library Documentation: function partial_duplication_graph in module networkx.generators.duplication

partial_duplication_graph(N, n, p, q, seed=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns a random graph using the partial duplication model.

    Parameters
    ----------
    N : int
        The total number of nodes in the final graph.

    n : int
        The number of nodes in the initial clique.

    p : float
        The probability of joining each neighbor of a node to the
        duplicate node. Must be a number in the between zero and one,
        inclusive.

    q : float
        The probability of joining the source node to the duplicate
        node. Must be a number in the between zero and one, inclusive.

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Notes
    -----
    A graph of nodes is grown by creating a fully connected graph
    of size `n`. The following procedure is then repeated until
    a total of `N` nodes have been reached.

    1. A random node, *u*, is picked and a new node, *v*, is created.
    2. For each neighbor of *u* an edge from the neighbor to *v* is created
       with probability `p`.
    3. An edge from *u* to *v* is created with probability `q`.

    This algorithm appears in [1].

    This implementation allows the possibility of generating
    disconnected graphs.

    References
    ----------
    .. [1] Knudsen Michael, and Carsten Wiuf. "A Markov chain approach to
           randomly grown graphs." Journal of Applied Mathematics 2008.
           <https://doi.org/10.1155/2008/190836>
networkx.partition_spanning_tree
Python Library Documentation: function partition_spanning_tree in module networkx.algorithms.tree.mst

partition_spanning_tree(G, minimum=True, weight='weight', partition='partition', ignore_nan=False, *, backend=None, **backend_kwargs)
    Find a spanning tree while respecting a partition of edges.

    Edges can be flagged as either `INCLUDED` which are required to be in the
    returned tree, `EXCLUDED`, which cannot be in the returned tree and `OPEN`.

    This is used in the SpanningTreeIterator to create new partitions following
    the algorithm of Sörensen and Janssens [1]_.

    Parameters
    ----------
    G : undirected graph
        An undirected graph.

    minimum : bool (default: True)
        Determines whether the returned tree is the minimum spanning tree of
        the partition of the maximum one.

    weight : str
        Data key to use for edge weights.

    partition : str
        The key for the edge attribute containing the partition
        data on the graph. Edges can be included, excluded or open using the
        `EdgePartition` enum.

    ignore_nan : bool (default: False)
        If a NaN is found as an edge weight normally an exception is raised.
        If `ignore_nan is True` then that edge is ignored instead.


    Returns
    -------
    G : NetworkX Graph
        A minimum spanning tree using all of the included edges in the graph and
        none of the excluded edges.

    References
    ----------
    .. [1] G.K. Janssens, K. Sörensen, An algorithm to generate all spanning
           trees in order of increasing cost, Pesquisa Operacional, 2005-08,
           Vol. 25 (2), p. 219-229,
           https://www.scielo.br/j/pope/a/XHswBwRwJyrfL88dmMwYNWp/?lang=en
networkx.path_graph
Python Library Documentation: function path_graph in module networkx.generators.classic

path_graph(n, create_using=None, *, backend=None, **backend_kwargs)
    Returns the Path graph `P_n` of linearly connected nodes.

    .. plot::

        >>> nx.draw(nx.path_graph(5))

    Parameters
    ----------
    n : int or iterable
        If an integer, nodes are 0 to n - 1.
        If an iterable of nodes, in the order they appear in the path.
        Warning: n is not checked for duplicates and if present the
        resulting graph may not be as desired. Make sure you have no duplicates.
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.
networkx.path_weight
Python Library Documentation: function path_weight in module networkx.classes.function

path_weight(G, path, weight)
    Returns total cost associated with specified path and weight

    Parameters
    ----------
    G : graph
        A NetworkX graph.

    path: list
        A list of node labels which defines the path to traverse

    weight: string
        A string indicating which edge attribute to use for path cost

    Returns
    -------
    cost: int or float
        An integer or a float representing the total cost with respect to the
        specified weight of the specified path

    Raises
    ------
    NetworkXNoPath
        If the specified edge does not exist.
networkx.percolation
Python Library Documentation: module networkx.algorithms.centrality.percolation in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.percolation - Percolation centrality measures.

FUNCTIONS
    percolation_centrality(G, attribute='percolation', states=None, weight=None, *, backend=None, **backend_kwargs)
        Compute the percolation centrality for nodes.

        Percolation centrality of a node $v$, at a given time, is defined
        as the proportion of ‘percolated paths’ that go through that node.

        This measure quantifies relative impact of nodes based on their
        topological connectivity, as well as their percolation states.

        Percolation states of nodes are used to depict network percolation
        scenarios (such as during infection transmission in a social network
        of individuals, spreading of computer viruses on computer networks, or
        transmission of disease over a network of towns) over time. In this
        measure usually the percolation state is expressed as a decimal
        between 0.0 and 1.0.

        When all nodes are in the same percolated state this measure is
        equivalent to betweenness centrality.

        Parameters
        ----------
        G : graph
          A NetworkX graph.

        attribute : None or string, optional (default='percolation')
          Name of the node attribute to use for percolation state, used
          if `states` is None. If a node does not set the attribute the
          state of that node will be set to the default value of 1.
          If all nodes do not have the attribute all nodes will be set to
          1 and the centrality measure will be equivalent to betweenness centrality.

        states : None or dict, optional (default=None)
          Specify percolation states for the nodes, nodes as keys states
          as values.

        weight : None or string, optional (default=None)
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.
          The weight of an edge is treated as the length or distance between the two sides.


        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with percolation centrality as the value.

        See Also
        --------
        betweenness_centrality

        Notes
        -----
        The algorithm is from Mahendra Piraveenan, Mikhail Prokopenko, and
        Liaquat Hossain [1]_
        Pair dependencies are calculated and accumulated using [2]_

        For weighted graphs the edge weights must be greater than zero.
        Zero edge weights can produce an infinite number of equal length
        paths between pairs of nodes.

        References
        ----------
        .. [1] Mahendra Piraveenan, Mikhail Prokopenko, Liaquat Hossain
           Percolation Centrality: Quantifying Graph-Theoretic Impact of Nodes
           during Percolation in Networks
           http://journals.plos.org/plosone/article?id=10.1371/journal.pone.0053095
        .. [2] Ulrik Brandes:
           A Faster Algorithm for Betweenness Centrality.
           Journal of Mathematical Sociology 25(2):163-177, 2001.
           https://doi.org/10.1080/0022250X.2001.9990249

DATA
    __all__ = ['percolation_centrality']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\percolation.py

networkx.percolation_centrality
Python Library Documentation: function percolation_centrality in module networkx.algorithms.centrality.percolation

percolation_centrality(G, attribute='percolation', states=None, weight=None, *, backend=None, **backend_kwargs)
    Compute the percolation centrality for nodes.

    Percolation centrality of a node $v$, at a given time, is defined
    as the proportion of ‘percolated paths’ that go through that node.

    This measure quantifies relative impact of nodes based on their
    topological connectivity, as well as their percolation states.

    Percolation states of nodes are used to depict network percolation
    scenarios (such as during infection transmission in a social network
    of individuals, spreading of computer viruses on computer networks, or
    transmission of disease over a network of towns) over time. In this
    measure usually the percolation state is expressed as a decimal
    between 0.0 and 1.0.

    When all nodes are in the same percolated state this measure is
    equivalent to betweenness centrality.

    Parameters
    ----------
    G : graph
      A NetworkX graph.

    attribute : None or string, optional (default='percolation')
      Name of the node attribute to use for percolation state, used
      if `states` is None. If a node does not set the attribute the
      state of that node will be set to the default value of 1.
      If all nodes do not have the attribute all nodes will be set to
      1 and the centrality measure will be equivalent to betweenness centrality.

    states : None or dict, optional (default=None)
      Specify percolation states for the nodes, nodes as keys states
      as values.

    weight : None or string, optional (default=None)
      If None, all edge weights are considered equal.
      Otherwise holds the name of the edge attribute used as weight.
      The weight of an edge is treated as the length or distance between the two sides.


    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with percolation centrality as the value.

    See Also
    --------
    betweenness_centrality

    Notes
    -----
    The algorithm is from Mahendra Piraveenan, Mikhail Prokopenko, and
    Liaquat Hossain [1]_
    Pair dependencies are calculated and accumulated using [2]_

    For weighted graphs the edge weights must be greater than zero.
    Zero edge weights can produce an infinite number of equal length
    paths between pairs of nodes.

    References
    ----------
    .. [1] Mahendra Piraveenan, Mikhail Prokopenko, Liaquat Hossain
       Percolation Centrality: Quantifying Graph-Theoretic Impact of Nodes
       during Percolation in Networks
       http://journals.plos.org/plosone/article?id=10.1371/journal.pone.0053095
    .. [2] Ulrik Brandes:
       A Faster Algorithm for Betweenness Centrality.
       Journal of Mathematical Sociology 25(2):163-177, 2001.
       https://doi.org/10.1080/0022250X.2001.9990249
networkx.periphery
Python Library Documentation: function periphery in module networkx.algorithms.distance_measures

periphery(G, e=None, usebounds=False, weight=None, *, backend=None, **backend_kwargs)
    Returns the periphery of the graph G.

    The periphery is the set of nodes with eccentricity equal to the diameter.

    Parameters
    ----------
    G : NetworkX graph
       A graph

    e : eccentricity dictionary, optional
      A precomputed dictionary of eccentricities.

    weight : string, function, or None
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

        If this is None, every edge has weight/distance/cost 1.

        Weights stored as floating point values can lead to small round-off
        errors in distances. Use integer weights to avoid this.

        Weights should be positive, since they are distances.

    Returns
    -------
    p : list
       List of nodes in periphery

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
    >>> nx.periphery(G)
    [2, 5]

    See Also
    --------
    barycenter
    center
networkx.petersen_graph
Python Library Documentation: function petersen_graph in module networkx.generators.small

petersen_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Petersen graph.

    The Peterson graph is a cubic, undirected graph with 10 nodes and 15 edges [1]_.
    Julius Petersen constructed the graph as the smallest counterexample
    against the claim that a connected bridgeless cubic graph
    has an edge colouring with three colours [2]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Petersen graph

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Petersen_graph
    .. [2] https://www.win.tue.nl/~aeb/drg/graphs/Petersen.html
networkx.planar_drawing
Python Library Documentation: module networkx.algorithms.planar_drawing in networkx.algorithms

NAME
    networkx.algorithms.planar_drawing

FUNCTIONS
    combinatorial_embedding_to_pos(embedding, fully_triangulate=False)
        Assigns every node a (x, y) position based on the given embedding

        The algorithm iteratively inserts nodes of the input graph in a certain
        order and rearranges previously inserted nodes so that the planar drawing
        stays valid. This is done efficiently by only maintaining relative
        positions during the node placements and calculating the absolute positions
        at the end. For more information see [1]_.

        Parameters
        ----------
        embedding : nx.PlanarEmbedding
            This defines the order of the edges

        fully_triangulate : bool
            If set to True the algorithm adds edges to a copy of the input
            embedding and makes it chordal.

        Returns
        -------
        pos : dict
            Maps each node to a tuple that defines the (x, y) position

        References
        ----------
        .. [1] M. Chrobak and T.H. Payne:
            A Linear-time Algorithm for Drawing a Planar Graph on a Grid 1989
            http://citeseerx.ist.psu.edu/viewdoc/summary?doi=10.1.1.51.6677

DATA
    __all__ = ['combinatorial_embedding_to_pos']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\planar_drawing.py

networkx.planar_layout
Python Library Documentation: function planar_layout in module networkx.drawing.layout

planar_layout(G, scale=1, center=None, dim=2)
    Position nodes without edge intersections.

    Parameters
    ----------
    G : NetworkX graph or list of nodes
        A position will be assigned to every node in G. If G is of type
        nx.PlanarEmbedding, the positions are selected accordingly.

    scale : number (default: 1)
        Scale factor for positions.

    center : array-like or None
        Coordinate pair around which to center the layout.

    dim : int
        Dimension of layout.

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node

    Raises
    ------
    NetworkXException
        If G is not planar

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> pos = nx.planar_layout(G)
networkx.planarity
Python Library Documentation: module networkx.algorithms.planarity in networkx.algorithms

NAME
    networkx.algorithms.planarity

CLASSES
    networkx.classes.digraph.DiGraph(networkx.classes.graph.Graph)
        PlanarEmbedding

    class PlanarEmbedding(networkx.classes.digraph.DiGraph)
     |  PlanarEmbedding(incoming_graph_data=None, **attr)
     |
     |  Represents a planar graph with its planar embedding.
     |
     |  The planar embedding is given by a `combinatorial embedding
     |  <https://en.wikipedia.org/wiki/Graph_embedding#Combinatorial_embedding>`_.
     |
     |  .. note:: `check_planarity` is the preferred way to check if a graph is planar.
     |
     |  **Neighbor ordering:**
     |
     |  In comparison to a usual graph structure, the embedding also stores the
     |  order of all neighbors for every vertex.
     |  The order of the neighbors can be given in clockwise (cw) direction or
     |  counterclockwise (ccw) direction. This order is stored as edge attributes
     |  in the underlying directed graph. For the edge (u, v) the edge attribute
     |  'cw' is set to the neighbor of u that follows immediately after v in
     |  clockwise direction.
     |
     |  In order for a PlanarEmbedding to be valid it must fulfill multiple
     |  conditions. It is possible to check if these conditions are fulfilled with
     |  the method :meth:`check_structure`.
     |  The conditions are:
     |
     |  * Edges must go in both directions (because the edge attributes differ)
     |  * Every edge must have a 'cw' and 'ccw' attribute which corresponds to a
     |    correct planar embedding.
     |
     |  As long as a PlanarEmbedding is invalid only the following methods should
     |  be called:
     |
     |  * :meth:`add_half_edge`
     |  * :meth:`connect_components`
     |
     |  Even though the graph is a subclass of nx.DiGraph, it can still be used
     |  for algorithms that require undirected graphs, because the method
     |  :meth:`is_directed` is overridden. This is possible, because a valid
     |  PlanarGraph must have edges in both directions.
     |
     |  **Half edges:**
     |
     |  In methods like `add_half_edge` the term "half-edge" is used, which is
     |  a term that is used in `doubly connected edge lists
     |  <https://en.wikipedia.org/wiki/Doubly_connected_edge_list>`_. It is used
     |  to emphasize that the edge is only in one direction and there exists
     |  another half-edge in the opposite direction.
     |  While conventional edges always have two faces (including outer face) next
     |  to them, it is possible to assign each half-edge *exactly one* face.
     |  For a half-edge (u, v) that is oriented such that u is below v then the
     |  face that belongs to (u, v) is to the right of this half-edge.
     |
     |  See Also
     |  --------
     |  is_planar :
     |      Preferred way to check if an existing graph is planar.
     |
     |  check_planarity :
     |      A convenient way to create a `PlanarEmbedding`. If not planar,
     |      it returns a subgraph that shows this.
     |
     |  Examples
     |  --------
     |
     |  Create an embedding of a star graph (compare `nx.star_graph(3)`):
     |
     |  >>> G = nx.PlanarEmbedding()
     |  >>> G.add_half_edge(0, 1)
     |  >>> G.add_half_edge(0, 2, ccw=1)
     |  >>> G.add_half_edge(0, 3, ccw=2)
     |  >>> G.add_half_edge(1, 0)
     |  >>> G.add_half_edge(2, 0)
     |  >>> G.add_half_edge(3, 0)
     |
     |  Alternatively the same embedding can also be defined in counterclockwise
     |  orientation. The following results in exactly the same PlanarEmbedding:
     |
     |  >>> G = nx.PlanarEmbedding()
     |  >>> G.add_half_edge(0, 1)
     |  >>> G.add_half_edge(0, 3, cw=1)
     |  >>> G.add_half_edge(0, 2, cw=3)
     |  >>> G.add_half_edge(1, 0)
     |  >>> G.add_half_edge(2, 0)
     |  >>> G.add_half_edge(3, 0)
     |
     |  After creating a graph, it is possible to validate that the PlanarEmbedding
     |  object is correct:
     |
     |  >>> G.check_structure()
     |
     |  Method resolution order:
     |      PlanarEmbedding
     |      networkx.classes.digraph.DiGraph
     |      networkx.classes.graph.Graph
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __init__(self, incoming_graph_data=None, **attr)
     |      Initialize a graph with edges, name, or graph attributes.
     |
     |      Parameters
     |      ----------
     |      incoming_graph_data : input graph (optional, default: None)
     |          Data to initialize graph.  If None (default) an empty
     |          graph is created.  The data can be an edge list, or any
     |          NetworkX graph object.  If the corresponding optional Python
     |          packages are installed the data can also be a 2D NumPy array, a
     |          SciPy sparse array, or a PyGraphviz graph.
     |
     |      attr : keyword arguments, optional (default= no attributes)
     |          Attributes to add to graph as key=value pairs.
     |
     |      See Also
     |      --------
     |      convert
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G = nx.Graph(name="my graph")
     |      >>> e = [(1, 2), (2, 3), (3, 4)]  # list of edges
     |      >>> G = nx.Graph(e)
     |
     |      Arbitrary graph attribute pairs (key=value) may be assigned
     |
     |      >>> G = nx.Graph(e, day="Friday")
     |      >>> G.graph
     |      {'day': 'Friday'}
     |
     |  add_half_edge(self, start_node, end_node, *, cw=None, ccw=None)
     |      Adds a half-edge from `start_node` to `end_node`.
     |
     |      If the half-edge is not the first one out of `start_node`, a reference
     |      node must be provided either in the clockwise (parameter `cw`) or in
     |      the counterclockwise (parameter `ccw`) direction. Only one of `cw`/`ccw`
     |      can be specified (or neither in the case of the first edge).
     |      Note that specifying a reference in the clockwise (`cw`) direction means
     |      inserting the new edge in the first counterclockwise position with
     |      respect to the reference (and vice-versa).
     |
     |      Parameters
     |      ----------
     |      start_node : node
     |          Start node of inserted edge.
     |      end_node : node
     |          End node of inserted edge.
     |      cw, ccw: node
     |          End node of reference edge.
     |          Omit or pass `None` if adding the first out-half-edge of `start_node`.
     |
     |
     |      Raises
     |      ------
     |      NetworkXException
     |          If the `cw` or `ccw` node is not a successor of `start_node`.
     |          If `start_node` has successors, but neither `cw` or `ccw` is provided.
     |          If both `cw` and `ccw` are specified.
     |
     |      See Also
     |      --------
     |      connect_components
     |
     |  add_half_edge_ccw(self, start_node, end_node, reference_neighbor)
     |      Adds a half-edge from start_node to end_node.
     |
     |      The half-edge is added counter clockwise next to the existing half-edge
     |      (start_node, reference_neighbor).
     |
     |      Parameters
     |      ----------
     |      start_node : node
     |          Start node of inserted edge.
     |      end_node : node
     |          End node of inserted edge.
     |      reference_neighbor: node
     |          End node of reference edge.
     |
     |      Raises
     |      ------
     |      NetworkXException
     |          If the reference_neighbor does not exist.
     |
     |      See Also
     |      --------
     |      add_half_edge
     |      add_half_edge_cw
     |      connect_components
     |
     |  add_half_edge_cw(self, start_node, end_node, reference_neighbor)
     |      Adds a half-edge from start_node to end_node.
     |
     |      The half-edge is added clockwise next to the existing half-edge
     |      (start_node, reference_neighbor).
     |
     |      Parameters
     |      ----------
     |      start_node : node
     |          Start node of inserted edge.
     |      end_node : node
     |          End node of inserted edge.
     |      reference_neighbor: node
     |          End node of reference edge.
     |
     |      Raises
     |      ------
     |      NetworkXException
     |          If the reference_neighbor does not exist.
     |
     |      See Also
     |      --------
     |      add_half_edge
     |      add_half_edge_ccw
     |      connect_components
     |
     |  add_half_edge_first(self, start_node, end_node)
     |      Add a half-edge and set end_node as start_node's leftmost neighbor.
     |
     |      The new edge is inserted counterclockwise with respect to the current
     |      leftmost neighbor, if there is one.
     |
     |      Parameters
     |      ----------
     |      start_node : node
     |      end_node : node
     |
     |      See Also
     |      --------
     |      add_half_edge
     |      connect_components
     |
     |  check_structure(self)
     |      Runs without exceptions if this object is valid.
     |
     |      Checks that the following properties are fulfilled:
     |
     |      * Edges go in both directions (because the edge attributes differ).
     |      * Every edge has a 'cw' and 'ccw' attribute which corresponds to a
     |        correct planar embedding.
     |
     |      Running this method verifies that the underlying Graph must be planar.
     |
     |      Raises
     |      ------
     |      NetworkXException
     |          This exception is raised with a short explanation if the
     |          PlanarEmbedding is invalid.
     |
     |  connect_components(self, v, w)
     |      Adds half-edges for (v, w) and (w, v) at some position.
     |
     |      This method should only be called if v and w are in different
     |      components, or it might break the embedding.
     |      This especially means that if `connect_components(v, w)`
     |      is called it is not allowed to call `connect_components(w, v)`
     |      afterwards. The neighbor orientations in both directions are
     |      all set correctly after the first call.
     |
     |      Parameters
     |      ----------
     |      v : node
     |      w : node
     |
     |      See Also
     |      --------
     |      add_half_edge
     |
     |  copy(self, as_view=False)
     |      Returns a copy of the graph.
     |
     |      The copy method by default returns an independent shallow copy
     |      of the graph and attributes. That is, if an attribute is a
     |      container, that container is shared by the original an the copy.
     |      Use Python's `copy.deepcopy` for new containers.
     |
     |      If `as_view` is True then a view is returned instead of a copy.
     |
     |      Notes
     |      -----
     |      All copies reproduce the graph structure, but data attributes
     |      may be handled in different ways. There are four types of copies
     |      of a graph that people might want.
     |
     |      Deepcopy -- A "deepcopy" copies the graph structure as well as
     |      all data attributes and any objects they might contain.
     |      The entire graph object is new so that changes in the copy
     |      do not affect the original object. (see Python's copy.deepcopy)
     |
     |      Data Reference (Shallow) -- For a shallow copy the graph structure
     |      is copied but the edge, node and graph attribute dicts are
     |      references to those in the original graph. This saves
     |      time and memory but could cause confusion if you change an attribute
     |      in one graph and it changes the attribute in the other.
     |      NetworkX does not provide this level of shallow copy.
     |
     |      Independent Shallow -- This copy creates new independent attribute
     |      dicts and then does a shallow copy of the attributes. That is, any
     |      attributes that are containers are shared between the new graph
     |      and the original. This is exactly what `dict.copy()` provides.
     |      You can obtain this style copy using:
     |
     |          >>> G = nx.path_graph(5)
     |          >>> H = G.copy()
     |          >>> H = G.copy(as_view=False)
     |          >>> H = nx.Graph(G)
     |          >>> H = G.__class__(G)
     |
     |      Fresh Data -- For fresh data, the graph structure is copied while
     |      new empty data attribute dicts are created. The resulting graph
     |      is independent of the original and it has no edge, node or graph
     |      attributes. Fresh copies are not enabled. Instead use:
     |
     |          >>> H = G.__class__()
     |          >>> H.add_nodes_from(G)
     |          >>> H.add_edges_from(G.edges)
     |
     |      View -- Inspired by dict-views, graph-views act like read-only
     |      versions of the original graph, providing a copy of the original
     |      structure without requiring any memory for copying the information.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Parameters
     |      ----------
     |      as_view : bool, optional (default=False)
     |          If True, the returned graph-view provides a read-only view
     |          of the original graph without actually copying any data.
     |
     |      Returns
     |      -------
     |      G : Graph
     |          A copy of the graph.
     |
     |      See Also
     |      --------
     |      to_directed: return a directed copy of the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> H = G.copy()
     |
     |  get_data(self)
     |      Converts the adjacency structure into a better readable structure.
     |
     |      Returns
     |      -------
     |      embedding : dict
     |          A dict mapping all nodes to a list of neighbors sorted in
     |          clockwise order.
     |
     |      See Also
     |      --------
     |      set_data
     |
     |  is_directed(self)
     |      A valid PlanarEmbedding is undirected.
     |
     |      All reverse edges are contained, i.e. for every existing
     |      half-edge (v, w) the half-edge in the opposite direction (w, v) is also
     |      contained.
     |
     |  neighbors_cw_order(self, v)
     |      Generator for the neighbors of v in clockwise order.
     |
     |      Parameters
     |      ----------
     |      v : node
     |
     |      Yields
     |      ------
     |      node
     |
     |  next_face_half_edge(self, v, w)
     |      Returns the following half-edge left of a face.
     |
     |      Parameters
     |      ----------
     |      v : node
     |      w : node
     |
     |      Returns
     |      -------
     |      half-edge : tuple
     |
     |  remove_edge(self, u, v)
     |      Remove the edge between u and v.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |      Remove the half-edges (u, v) and (v, u) and update the
     |      edge ordering around the removed edge.
     |
     |      Raises
     |      ------
     |      NetworkXError
     |      If there is not an edge between u and v.
     |
     |      See Also
     |      --------
     |      remove_edges_from : remove a collection of edges
     |
     |  remove_edges_from(self, ebunch)
     |      Remove all edges specified in ebunch.
     |
     |      Parameters
     |      ----------
     |      ebunch: list or container of edge tuples
     |          Each pair of half-edges between the nodes given in the tuples
     |          will be removed from the graph. The nodes can be passed as:
     |
     |              - 2-tuples (u, v) half-edges (u, v) and (v, u).
     |              - 3-tuples (u, v, k) where k is ignored.
     |
     |      See Also
     |      --------
     |      remove_edge : remove a single edge
     |
     |      Notes
     |      -----
     |      Will fail silently if an edge in ebunch is not in the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> ebunch = [(1, 2), (2, 3)]
     |      >>> G.remove_edges_from(ebunch)
     |
     |  remove_node(self, n)
     |      Remove node n.
     |
     |      Removes the node n and all adjacent edges, updating the
     |      PlanarEmbedding to account for any resulting edge removal.
     |      Attempting to remove a non-existent node will raise an exception.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Raises
     |      ------
     |      NetworkXError
     |         If n is not in the graph.
     |
     |      See Also
     |      --------
     |      remove_nodes_from
     |
     |  remove_nodes_from(self, nodes)
     |      Remove multiple nodes.
     |
     |      Parameters
     |      ----------
     |      nodes : iterable container
     |          A container of nodes (list, dict, set, etc.).  If a node
     |          in the container is not in the graph it is silently ignored.
     |
     |      See Also
     |      --------
     |      remove_node
     |
     |      Notes
     |      -----
     |      When removing nodes from an iterator over the graph you are changing,
     |      a `RuntimeError` will be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
     |      object to `G.remove_nodes_from`.
     |
     |  set_data(self, data)
     |      Inserts edges according to given sorted neighbor list.
     |
     |      The input format is the same as the output format of get_data().
     |
     |      Parameters
     |      ----------
     |      data : dict
     |          A dict mapping all nodes to a list of neighbors sorted in
     |          clockwise order.
     |
     |      See Also
     |      --------
     |      get_data
     |
     |  traverse_face(self, v, w, mark_half_edges=None)
     |      Returns nodes on the face that belong to the half-edge (v, w).
     |
     |      The face that is traversed lies to the right of the half-edge (in an
     |      orientation where v is below w).
     |
     |      Optionally it is possible to pass a set to which all encountered half
     |      edges are added. Before calling this method, this set must not include
     |      any half-edges that belong to the face.
     |
     |      Parameters
     |      ----------
     |      v : node
     |          Start node of half-edge.
     |      w : node
     |          End node of half-edge.
     |      mark_half_edges: set, optional
     |          Set to which all encountered half-edges are added.
     |
     |      Returns
     |      -------
     |      face : list
     |          A list of nodes that lie on this face.
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from networkx.classes.digraph.DiGraph:
     |
     |  add_edge(self, u_of_edge, v_of_edge, **attr)
     |      Add an edge between u and v.
     |
     |      The nodes u and v will be automatically added if they are
     |      not already in the graph.
     |
     |      Edge attributes can be specified with keywords or by directly
     |      accessing the edge's attribute dictionary. See examples below.
     |
     |      Parameters
     |      ----------
     |      u_of_edge, v_of_edge : nodes
     |          Nodes can be, for example, strings or numbers.
     |          Nodes must be hashable (and not None) Python objects.
     |      attr : keyword arguments, optional
     |          Edge data (or labels or objects) can be assigned using
     |          keyword arguments.
     |
     |      See Also
     |      --------
     |      add_edges_from : add a collection of edges
     |
     |      Notes
     |      -----
     |      Adding an edge that already exists updates the edge data.
     |
     |      Many NetworkX algorithms designed for weighted graphs use
     |      an edge attribute (by default `weight`) to hold a numerical value.
     |
     |      Examples
     |      --------
     |      The following all add the edge e=(1, 2) to graph G:
     |
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> e = (1, 2)
     |      >>> G.add_edge(1, 2)  # explicit two-node form
     |      >>> G.add_edge(*e)  # single edge as tuple of two nodes
     |      >>> G.add_edges_from([(1, 2)])  # add edges from iterable container
     |
     |      Associate data to edges using keywords:
     |
     |      >>> G.add_edge(1, 2, weight=3)
     |      >>> G.add_edge(1, 3, weight=7, capacity=15, length=342.7)
     |
     |      For non-string attribute keys, use subscript notation.
     |
     |      >>> G.add_edge(1, 2)
     |      >>> G[1][2].update({0: 5})
     |      >>> G.edges[1, 2].update({0: 5})
     |
     |  add_edges_from(self, ebunch_to_add, **attr)
     |      Add all the edges in ebunch_to_add.
     |
     |      Parameters
     |      ----------
     |      ebunch_to_add : container of edges
     |          Each edge given in the container will be added to the
     |          graph. The edges must be given as 2-tuples (u, v) or
     |          3-tuples (u, v, d) where d is a dictionary containing edge data.
     |      attr : keyword arguments, optional
     |          Edge data (or labels or objects) can be assigned using
     |          keyword arguments.
     |
     |      See Also
     |      --------
     |      add_edge : add a single edge
     |      add_weighted_edges_from : convenient way to add weighted edges
     |
     |      Notes
     |      -----
     |      Adding the same edge twice has no effect but any edge data
     |      will be updated when each duplicate edge is added.
     |
     |      Edge attributes specified in an ebunch take precedence over
     |      attributes specified via keyword arguments.
     |
     |      When adding edges from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_edges)`, and pass this
     |      object to `G.add_edges_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_edges_from([(0, 1), (1, 2)])  # using a list of edge tuples
     |      >>> e = zip(range(0, 3), range(1, 4))
     |      >>> G.add_edges_from(e)  # Add the path graph 0-1-2-3
     |
     |      Associate data to edges
     |
     |      >>> G.add_edges_from([(1, 2), (2, 3)], weight=3)
     |      >>> G.add_edges_from([(3, 4), (1, 4)], label="WN2898")
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 4)])
     |      >>> # Grow graph by one new node, adding edges to all existing nodes.
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_edges_from(((5, n) for n in G.nodes))
     |      >>> # right way - note that there will be no self-edge for node 5
     |      >>> G.add_edges_from(list((5, n) for n in G.nodes))
     |
     |  add_node(self, node_for_adding, **attr)
     |      Add a single node `node_for_adding` and update node attributes.
     |
     |      Parameters
     |      ----------
     |      node_for_adding : node
     |          A node can be any hashable Python object except None.
     |      attr : keyword arguments, optional
     |          Set or change node attributes using key=value.
     |
     |      See Also
     |      --------
     |      add_nodes_from
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_node(1)
     |      >>> G.add_node("Hello")
     |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
     |      >>> G.add_node(K3)
     |      >>> G.number_of_nodes()
     |      3
     |
     |      Use keywords set/change node attributes:
     |
     |      >>> G.add_node(1, size=10)
     |      >>> G.add_node(3, weight=0.4, UTM=("13S", 382871, 3972649))
     |
     |      Notes
     |      -----
     |      A hashable object is one that can be used as a key in a Python
     |      dictionary. This includes strings, numbers, tuples of strings
     |      and numbers, etc.
     |
     |      On many platforms hashable items also include mutables such as
     |      NetworkX Graphs, though one should be careful that the hash
     |      doesn't change on mutables.
     |
     |  add_nodes_from(self, nodes_for_adding, **attr)
     |      Add multiple nodes.
     |
     |      Parameters
     |      ----------
     |      nodes_for_adding : iterable container
     |          A container of nodes (list, dict, set, etc.).
     |          OR
     |          A container of (node, attribute dict) tuples.
     |          Node attributes are updated using the attribute dict.
     |      attr : keyword arguments, optional (default= no attributes)
     |          Update attributes for all nodes in nodes.
     |          Node attributes specified in nodes as a tuple take
     |          precedence over attributes specified via keyword arguments.
     |
     |      See Also
     |      --------
     |      add_node
     |
     |      Notes
     |      -----
     |      When adding nodes from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_nodes)`, and pass this
     |      object to `G.add_nodes_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_nodes_from("Hello")
     |      >>> K3 = nx.Graph([(0, 1), (1, 2), (2, 0)])
     |      >>> G.add_nodes_from(K3)
     |      >>> sorted(G.nodes(), key=str)
     |      [0, 1, 2, 'H', 'e', 'l', 'o']
     |
     |      Use keywords to update specific node attributes for every node.
     |
     |      >>> G.add_nodes_from([1, 2], size=10)
     |      >>> G.add_nodes_from([3, 4], weight=0.4)
     |
     |      Use (node, attrdict) tuples to update attributes for specific nodes.
     |
     |      >>> G.add_nodes_from([(1, dict(size=11)), (2, {"color": "blue"})])
     |      >>> G.nodes[1]["size"]
     |      11
     |      >>> H = nx.Graph()
     |      >>> H.add_nodes_from(G.nodes(data=True))
     |      >>> H.nodes[1]["size"]
     |      11
     |
     |      Evaluate an iterator over a graph if using it to modify the same graph
     |
     |      >>> G = nx.DiGraph([(0, 1), (1, 2), (3, 4)])
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_nodes_from(n + 1 for n in G.nodes)
     |      >>> # correct way
     |      >>> G.add_nodes_from(list(n + 1 for n in G.nodes))
     |
     |  adj = <functools.cached_property object>
     |      Graph adjacency object holding the neighbors of each node.
     |
     |      This object is a read-only dict-like structure with node keys
     |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
     |      to the edge-data-dict.  So `G.adj[3][2]['color'] = 'blue'` sets
     |      the color of the edge `(3, 2)` to `"blue"`.
     |
     |      Iterating over G.adj behaves like a dict. Useful idioms include
     |      `for nbr, datadict in G.adj[n].items():`.
     |
     |      The neighbor information is also provided by subscripting the graph.
     |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
     |
     |      For directed graphs, `G.adj` holds outgoing (successor) info.
     |
     |  clear(self)
     |      Remove all nodes and edges from the graph.
     |
     |      This also removes the name, and all graph, node, and edge attributes.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.clear()
     |      >>> list(G.nodes)
     |      []
     |      >>> list(G.edges)
     |      []
     |
     |  clear_edges(self)
     |      Remove all edges from the graph without altering nodes.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.clear_edges()
     |      >>> list(G.nodes)
     |      [0, 1, 2, 3]
     |      >>> list(G.edges)
     |      []
     |
     |  degree = <functools.cached_property object>
     |      A DegreeView for the Graph as G.degree or G.degree().
     |
     |      The node degree is the number of edges adjacent to the node.
     |      The weighted node degree is the sum of the edge weights for
     |      edges incident to that node.
     |
     |      This object provides an iterator for (node, degree) as well as
     |      lookup for the degree for a single node.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      weight : string or None, optional (default=None)
     |         The name of an edge attribute that holds the numerical value used
     |         as a weight.  If None, then each edge has weight 1.
     |         The degree is the sum of the edge weights adjacent to the node.
     |
     |      Returns
     |      -------
     |      DiDegreeView or int
     |          If multiple nodes are requested (the default), returns a `DiDegreeView`
     |          mapping nodes to their degree.
     |          If a single node is requested, returns the degree of the node as an integer.
     |
     |      See Also
     |      --------
     |      in_degree, out_degree
     |
     |      Examples
     |      --------
     |      >>> G = nx.DiGraph()  # or MultiDiGraph
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.degree(0)  # node 0 with degree 1
     |      1
     |      >>> list(G.degree([0, 1, 2]))
     |      [(0, 1), (1, 2), (2, 2)]
     |
     |  edges = <functools.cached_property object>
     |      An OutEdgeView of the DiGraph as G.edges or G.edges().
     |
     |      edges(self, nbunch=None, data=False, default=None)
     |
     |      The OutEdgeView provides set-like operations on the edge-tuples
     |      as well as edge attribute lookup. When called, it also provides
     |      an EdgeDataView object which allows control of access to edge
     |      attributes (but does not provide set-like operations).
     |      Hence, `G.edges[u, v]['color']` provides the value of the color
     |      attribute for edge `(u, v)` while
     |      `for (u, v, c) in G.edges.data('color', default='red'):`
     |      iterates through all the edges yielding the color attribute
     |      with default `'red'` if no color attribute exists.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges from these nodes.
     |      data : string or bool, optional (default=False)
     |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
     |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
     |          If False, return 2-tuple (u, v).
     |      default : value, optional (default=None)
     |          Value used for edges that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      edges : OutEdgeView
     |          A view of edge attributes, usually it iterates over (u, v)
     |          or (u, v, d) tuples of edges, but can also be used for
     |          attribute lookup as `edges[u, v]['foo']`.
     |
     |      See Also
     |      --------
     |      in_edges, out_edges
     |
     |      Notes
     |      -----
     |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
     |      For directed graphs this returns the out-edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
     |      >>> nx.add_path(G, [0, 1, 2])
     |      >>> G.add_edge(2, 3, weight=5)
     |      >>> [e for e in G.edges]
     |      [(0, 1), (1, 2), (2, 3)]
     |      >>> G.edges.data()  # default data is {} (empty dict)
     |      OutEdgeDataView([(0, 1, {}), (1, 2, {}), (2, 3, {'weight': 5})])
     |      >>> G.edges.data("weight", default=1)
     |      OutEdgeDataView([(0, 1, 1), (1, 2, 1), (2, 3, 5)])
     |      >>> G.edges([0, 2])  # only edges originating from these nodes
     |      OutEdgeDataView([(0, 1), (2, 3)])
     |      >>> G.edges(0)  # only edges from node 0
     |      OutEdgeDataView([(0, 1)])
     |
     |  has_predecessor(self, u, v)
     |      Returns True if node u has predecessor v.
     |
     |      This is true if graph has the edge u<-v.
     |
     |  has_successor(self, u, v)
     |      Returns True if node u has successor v.
     |
     |      This is true if graph has the edge u->v.
     |
     |  in_degree = <functools.cached_property object>
     |      An InDegreeView for (node, in_degree) or in_degree for single node.
     |
     |      The node in_degree is the number of edges pointing to the node.
     |      The weighted node degree is the sum of the edge weights for
     |      edges incident to that node.
     |
     |      This object provides an iteration over (node, in_degree) as well as
     |      lookup for the degree for a single node.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      weight : string or None, optional (default=None)
     |         The name of an edge attribute that holds the numerical value used
     |         as a weight.  If None, then each edge has weight 1.
     |         The degree is the sum of the edge weights adjacent to the node.
     |
     |      Returns
     |      -------
     |      If a single node is requested
     |      deg : int
     |          In-degree of the node
     |
     |      OR if multiple nodes are requested
     |      nd_iter : iterator
     |          The iterator returns two-tuples of (node, in-degree).
     |
     |      See Also
     |      --------
     |      degree, out_degree
     |
     |      Examples
     |      --------
     |      >>> G = nx.DiGraph()
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.in_degree(0)  # node 0 with degree 0
     |      0
     |      >>> list(G.in_degree([0, 1, 2]))
     |      [(0, 0), (1, 1), (2, 1)]
     |
     |  in_edges = <functools.cached_property object>
     |      A view of the in edges of the graph as G.in_edges or G.in_edges().
     |
     |      in_edges(self, nbunch=None, data=False, default=None):
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |      data : string or bool, optional (default=False)
     |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
     |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
     |          If False, return 2-tuple (u, v).
     |      default : value, optional (default=None)
     |          Value used for edges that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      in_edges : InEdgeView or InEdgeDataView
     |          A view of edge attributes, usually it iterates over (u, v)
     |          or (u, v, d) tuples of edges, but can also be used for
     |          attribute lookup as `edges[u, v]['foo']`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.DiGraph()
     |      >>> G.add_edge(1, 2, color="blue")
     |      >>> G.in_edges()
     |      InEdgeView([(1, 2)])
     |      >>> G.in_edges(nbunch=2)
     |      InEdgeDataView([(1, 2)])
     |
     |      See Also
     |      --------
     |      edges
     |
     |  is_multigraph(self)
     |      Returns True if graph is a multigraph, False otherwise.
     |
     |  neighbors = successors(self, n)
     |
     |  out_degree = <functools.cached_property object>
     |      An OutDegreeView for (node, out_degree)
     |
     |      The node out_degree is the number of edges pointing out of the node.
     |      The weighted node degree is the sum of the edge weights for
     |      edges incident to that node.
     |
     |      This object provides an iterator over (node, out_degree) as well as
     |      lookup for the degree for a single node.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      weight : string or None, optional (default=None)
     |         The name of an edge attribute that holds the numerical value used
     |         as a weight.  If None, then each edge has weight 1.
     |         The degree is the sum of the edge weights adjacent to the node.
     |
     |      Returns
     |      -------
     |      If a single node is requested
     |      deg : int
     |          Out-degree of the node
     |
     |      OR if multiple nodes are requested
     |      nd_iter : iterator
     |          The iterator returns two-tuples of (node, out-degree).
     |
     |      See Also
     |      --------
     |      degree, in_degree
     |
     |      Examples
     |      --------
     |      >>> G = nx.DiGraph()
     |      >>> nx.add_path(G, [0, 1, 2, 3])
     |      >>> G.out_degree(0)  # node 0 with degree 1
     |      1
     |      >>> list(G.out_degree([0, 1, 2]))
     |      [(0, 1), (1, 1), (2, 1)]
     |
     |  out_edges = <functools.cached_property object>
     |      An OutEdgeView of the DiGraph as G.edges or G.edges().
     |
     |      edges(self, nbunch=None, data=False, default=None)
     |
     |      The OutEdgeView provides set-like operations on the edge-tuples
     |      as well as edge attribute lookup. When called, it also provides
     |      an EdgeDataView object which allows control of access to edge
     |      attributes (but does not provide set-like operations).
     |      Hence, `G.edges[u, v]['color']` provides the value of the color
     |      attribute for edge `(u, v)` while
     |      `for (u, v, c) in G.edges.data('color', default='red'):`
     |      iterates through all the edges yielding the color attribute
     |      with default `'red'` if no color attribute exists.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges from these nodes.
     |      data : string or bool, optional (default=False)
     |          The edge attribute returned in 3-tuple (u, v, ddict[data]).
     |          If True, return edge attribute dict in 3-tuple (u, v, ddict).
     |          If False, return 2-tuple (u, v).
     |      default : value, optional (default=None)
     |          Value used for edges that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      edges : OutEdgeView
     |          A view of edge attributes, usually it iterates over (u, v)
     |          or (u, v, d) tuples of edges, but can also be used for
     |          attribute lookup as `edges[u, v]['foo']`.
     |
     |      See Also
     |      --------
     |      in_edges, out_edges
     |
     |      Notes
     |      -----
     |      Nodes in nbunch that are not in the graph will be (quietly) ignored.
     |      For directed graphs this returns the out-edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
     |      >>> nx.add_path(G, [0, 1, 2])
     |      >>> G.add_edge(2, 3, weight=5)
     |      >>> [e for e in G.edges]
     |      [(0, 1), (1, 2), (2, 3)]
     |      >>> G.edges.data()  # default data is {} (empty dict)
     |      OutEdgeDataView([(0, 1, {}), (1, 2, {}), (2, 3, {'weight': 5})])
     |      >>> G.edges.data("weight", default=1)
     |      OutEdgeDataView([(0, 1, 1), (1, 2, 1), (2, 3, 5)])
     |      >>> G.edges([0, 2])  # only edges originating from these nodes
     |      OutEdgeDataView([(0, 1), (2, 3)])
     |      >>> G.edges(0)  # only edges from node 0
     |      OutEdgeDataView([(0, 1)])
     |
     |  pred = <functools.cached_property object>
     |      Graph adjacency object holding the predecessors of each node.
     |
     |      This object is a read-only dict-like structure with node keys
     |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
     |      to the edge-data-dict.  So `G.pred[2][3]['color'] = 'blue'` sets
     |      the color of the edge `(3, 2)` to `"blue"`.
     |
     |      Iterating over G.pred behaves like a dict. Useful idioms include
     |      `for nbr, datadict in G.pred[n].items():`.  A data-view not provided
     |      by dicts also exists: `for nbr, foovalue in G.pred[node].data('foo'):`
     |      A default can be set via a `default` argument to the `data` method.
     |
     |  predecessors(self, n)
     |      Returns an iterator over predecessor nodes of n.
     |
     |      A predecessor of n is a node m such that there exists a directed
     |      edge from m to n.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Raises
     |      ------
     |      NetworkXError
     |         If n is not in the graph.
     |
     |      See Also
     |      --------
     |      successors
     |
     |  reverse(self, copy=True)
     |      Returns the reverse of the graph.
     |
     |      The reverse is a graph with the same nodes and edges
     |      but with the directions of the edges reversed.
     |
     |      Parameters
     |      ----------
     |      copy : bool optional (default=True)
     |          If True, return a new DiGraph holding the reversed edges.
     |          If False, the reverse graph is created using a view of
     |          the original graph.
     |
     |  succ = <functools.cached_property object>
     |      Graph adjacency object holding the successors of each node.
     |
     |      This object is a read-only dict-like structure with node keys
     |      and neighbor-dict values.  The neighbor-dict is keyed by neighbor
     |      to the edge-data-dict.  So `G.succ[3][2]['color'] = 'blue'` sets
     |      the color of the edge `(3, 2)` to `"blue"`.
     |
     |      Iterating over G.succ behaves like a dict. Useful idioms include
     |      `for nbr, datadict in G.succ[n].items():`.  A data-view not provided
     |      by dicts also exists: `for nbr, foovalue in G.succ[node].data('foo'):`
     |      and a default can be set via a `default` argument to the `data` method.
     |
     |      The neighbor information is also provided by subscripting the graph.
     |      So `for nbr, foovalue in G[node].data('foo', default=1):` works.
     |
     |      For directed graphs, `G.adj` is identical to `G.succ`.
     |
     |  successors(self, n)
     |      Returns an iterator over successor nodes of n.
     |
     |      A successor of n is a node m such that there exists a directed
     |      edge from n to m.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph
     |
     |      Raises
     |      ------
     |      NetworkXError
     |         If n is not in the graph.
     |
     |      See Also
     |      --------
     |      predecessors
     |
     |      Notes
     |      -----
     |      neighbors() and successors() are the same.
     |
     |  to_undirected(self, reciprocal=False, as_view=False)
     |      Returns an undirected representation of the digraph.
     |
     |      Parameters
     |      ----------
     |      reciprocal : bool (optional)
     |        If True only keep edges that appear in both directions
     |        in the original digraph.
     |      as_view : bool (optional, default=False)
     |        If True return an undirected view of the original directed graph.
     |
     |      Returns
     |      -------
     |      G : Graph
     |          An undirected graph with the same name and nodes and
     |          with edge (u, v, data) if either (u, v, data) or (v, u, data)
     |          is in the digraph.  If both edges exist in digraph and
     |          their edge data is different, only one edge is created
     |          with an arbitrary choice of which edge data to use.
     |          You must check and correct for this manually if desired.
     |
     |      See Also
     |      --------
     |      Graph, copy, add_edge, add_edges_from
     |
     |      Notes
     |      -----
     |      If edges in both directions (u, v) and (v, u) exist in the
     |      graph, attributes for the new undirected edge will be a combination of
     |      the attributes of the directed edges.  The edge data is updated
     |      in the (arbitrary) order that the edges are encountered.  For
     |      more customized control of the edge attributes use add_edge().
     |
     |      This returns a "deepcopy" of the edge, node, and
     |      graph attributes which attempts to completely copy
     |      all of the data and references.
     |
     |      This is in contrast to the similar G=DiGraph(D) which returns a
     |      shallow copy of the data.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Warning: If you have subclassed DiGraph to use dict-like objects
     |      in the data structure, those changes do not transfer to the
     |      Graph created by this method.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(2)  # or MultiGraph, etc
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1), (1, 0)]
     |      >>> G2 = H.to_undirected()
     |      >>> list(G2.edges)
     |      [(0, 1)]
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from networkx.classes.graph.Graph:
     |
     |  __contains__(self, n)
     |      Returns True if n is a node, False otherwise. Use: 'n in G'.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> 1 in G
     |      True
     |
     |  __getitem__(self, n)
     |      Returns a dict of neighbors of node n.  Use: 'G[n]'.
     |
     |      Parameters
     |      ----------
     |      n : node
     |         A node in the graph.
     |
     |      Returns
     |      -------
     |      adj_dict : dictionary
     |         The adjacency dictionary for nodes connected to n.
     |
     |      Notes
     |      -----
     |      G[n] is the same as G.adj[n] and similar to G.neighbors(n)
     |      (which is an iterator over G.adj[n])
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G[0]
     |      AtlasView({1: {}})
     |
     |  __iter__(self)
     |      Iterate over the nodes. Use: 'for n in G'.
     |
     |      Returns
     |      -------
     |      niter : iterator
     |          An iterator over all nodes in the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> [n for n in G]
     |      [0, 1, 2, 3]
     |      >>> list(G)
     |      [0, 1, 2, 3]
     |
     |  __len__(self)
     |      Returns the number of nodes in the graph. Use: 'len(G)'.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      number_of_nodes: identical method
     |      order: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> len(G)
     |      4
     |
     |  __str__(self)
     |      Returns a short summary of the graph.
     |
     |      Returns
     |      -------
     |      info : string
     |          Graph information including the graph name (if any), graph type, and the
     |          number of nodes and edges.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph(name="foo")
     |      >>> str(G)
     |      "Graph named 'foo' with 0 nodes and 0 edges"
     |
     |      >>> G = nx.path_graph(3)
     |      >>> str(G)
     |      'Graph with 3 nodes and 2 edges'
     |
     |  add_weighted_edges_from(self, ebunch_to_add, weight='weight', **attr)
     |      Add weighted edges in `ebunch_to_add` with specified weight attr
     |
     |      Parameters
     |      ----------
     |      ebunch_to_add : container of edges
     |          Each edge given in the list or container will be added
     |          to the graph. The edges must be given as 3-tuples (u, v, w)
     |          where w is a number.
     |      weight : string, optional (default= 'weight')
     |          The attribute name for the edge weights to be added.
     |      attr : keyword arguments, optional (default= no attributes)
     |          Edge attributes to add/update for all edges.
     |
     |      See Also
     |      --------
     |      add_edge : add a single edge
     |      add_edges_from : add multiple edges
     |
     |      Notes
     |      -----
     |      Adding the same edge twice for Graph/DiGraph simply updates
     |      the edge data. For MultiGraph/MultiDiGraph, duplicate edges
     |      are stored.
     |
     |      When adding edges from an iterator over the graph you are changing,
     |      a `RuntimeError` can be raised with message:
     |      `RuntimeError: dictionary changed size during iteration`. This
     |      happens when the graph's underlying dictionary is modified during
     |      iteration. To avoid this error, evaluate the iterator into a separate
     |      object, e.g. by using `list(iterator_of_edges)`, and pass this
     |      object to `G.add_weighted_edges_from`.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_weighted_edges_from([(0, 1, 3.0), (1, 2, 7.5)])
     |
     |      Evaluate an iterator over edges before passing it
     |
     |      >>> G = nx.Graph([(1, 2), (2, 3), (3, 4)])
     |      >>> weight = 0.1
     |      >>> # Grow graph by one new node, adding edges to all existing nodes.
     |      >>> # wrong way - will raise RuntimeError
     |      >>> # G.add_weighted_edges_from(((5, n, weight) for n in G.nodes))
     |      >>> # correct way - note that there will be no self-edge for node 5
     |      >>> G.add_weighted_edges_from(list((5, n, weight) for n in G.nodes))
     |
     |  adjacency(self)
     |      Returns an iterator over (node, adjacency dict) tuples for all nodes.
     |
     |      For directed graphs, only outgoing neighbors/adjacencies are included.
     |
     |      Returns
     |      -------
     |      adj_iter : iterator
     |         An iterator over (node, adjacency dictionary) for all nodes in
     |         the graph.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> [(n, nbrdict) for n, nbrdict in G.adjacency()]
     |      [(0, {1: {}}), (1, {0: {}, 2: {}}), (2, {1: {}, 3: {}}), (3, {2: {}})]
     |
     |  edge_subgraph(self, edges)
     |      Returns the subgraph induced by the specified edges.
     |
     |      The induced subgraph contains each edge in `edges` and each
     |      node incident to any one of those edges.
     |
     |      Parameters
     |      ----------
     |      edges : iterable
     |          An iterable of edges in this graph.
     |
     |      Returns
     |      -------
     |      G : Graph
     |          An edge-induced subgraph of this graph with the same edge
     |          attributes.
     |
     |      Notes
     |      -----
     |      The graph, edge, and node attributes in the returned subgraph
     |      view are references to the corresponding attributes in the original
     |      graph. The view is read-only.
     |
     |      To create a full graph version of the subgraph with its own copy
     |      of the edge or node attributes, use::
     |
     |          G.edge_subgraph(edges).copy()
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(5)
     |      >>> H = G.edge_subgraph([(0, 1), (3, 4)])
     |      >>> list(H.nodes)
     |      [0, 1, 3, 4]
     |      >>> list(H.edges)
     |      [(0, 1), (3, 4)]
     |
     |  get_edge_data(self, u, v, default=None)
     |      Returns the attribute dictionary associated with edge (u, v).
     |
     |      This is identical to `G[u][v]` except the default is returned
     |      instead of an exception if the edge doesn't exist.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |      default:  any Python object (default=None)
     |          Value to return if the edge (u, v) is not found.
     |
     |      Returns
     |      -------
     |      edge_dict : dictionary
     |          The edge attribute dictionary.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G[0][1]
     |      {}
     |
     |      Warning: Assigning to `G[u][v]` is not permitted.
     |      But it is safe to assign attributes `G[u][v]['foo']`
     |
     |      >>> G[0][1]["weight"] = 7
     |      >>> G[0][1]["weight"]
     |      7
     |      >>> G[1][0]["weight"]
     |      7
     |
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.get_edge_data(0, 1)  # default edge data is {}
     |      {}
     |      >>> e = (0, 1)
     |      >>> G.get_edge_data(*e)  # tuple form
     |      {}
     |      >>> G.get_edge_data("a", "b", default=0)  # edge not in graph, return 0
     |      0
     |
     |  has_edge(self, u, v)
     |      Returns True if the edge (u, v) is in the graph.
     |
     |      This is the same as `v in G[u]` without KeyError exceptions.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes
     |          Nodes can be, for example, strings or numbers.
     |          Nodes must be hashable (and not None) Python objects.
     |
     |      Returns
     |      -------
     |      edge_ind : bool
     |          True if edge is in the graph, False otherwise.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.has_edge(0, 1)  # using two nodes
     |      True
     |      >>> e = (0, 1)
     |      >>> G.has_edge(*e)  #  e is a 2-tuple (u, v)
     |      True
     |      >>> e = (0, 1, {"weight": 7})
     |      >>> G.has_edge(*e[:2])  # e is a 3-tuple (u, v, data_dictionary)
     |      True
     |
     |      The following syntax are equivalent:
     |
     |      >>> G.has_edge(0, 1)
     |      True
     |      >>> 1 in G[0]  # though this gives KeyError if 0 not in G
     |      True
     |
     |  has_node(self, n)
     |      Returns True if the graph contains the node n.
     |
     |      Identical to `n in G`
     |
     |      Parameters
     |      ----------
     |      n : node
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.has_node(0)
     |      True
     |
     |      It is more readable and simpler to use
     |
     |      >>> 0 in G
     |      True
     |
     |  nbunch_iter(self, nbunch=None)
     |      Returns an iterator over nodes contained in nbunch that are
     |      also in the graph.
     |
     |      The nodes in nbunch are checked for membership in the graph
     |      and if not are silently ignored.
     |
     |      Parameters
     |      ----------
     |      nbunch : single node, container, or all nodes (default= all nodes)
     |          The view will only report edges incident to these nodes.
     |
     |      Returns
     |      -------
     |      niter : iterator
     |          An iterator over nodes in nbunch that are also in the graph.
     |          If nbunch is None, iterate over all nodes in the graph.
     |
     |      Raises
     |      ------
     |      NetworkXError
     |          If nbunch is not a node or sequence of nodes.
     |          If a node in nbunch is not hashable.
     |
     |      See Also
     |      --------
     |      Graph.__iter__
     |
     |      Notes
     |      -----
     |      When nbunch is an iterator, the returned iterator yields values
     |      directly from nbunch, becoming exhausted when nbunch is exhausted.
     |
     |      To test whether nbunch is a single node, one can use
     |      "if nbunch in self:", even after processing with this routine.
     |
     |      If nbunch is not a node or a (possibly empty) sequence/iterator
     |      or None, a :exc:`NetworkXError` is raised.  Also, if any object in
     |      nbunch is not hashable, a :exc:`NetworkXError` is raised.
     |
     |  nodes = <functools.cached_property object>
     |      A NodeView of the Graph as G.nodes or G.nodes().
     |
     |      Can be used as `G.nodes` for data lookup and for set-like operations.
     |      Can also be used as `G.nodes(data='color', default=None)` to return a
     |      NodeDataView which reports specific node data but no set operations.
     |      It presents a dict-like interface as well with `G.nodes.items()`
     |      iterating over `(node, nodedata)` 2-tuples and `G.nodes[3]['foo']`
     |      providing the value of the `foo` attribute for node `3`. In addition,
     |      a view `G.nodes.data('foo')` provides a dict-like interface to the
     |      `foo` attribute of each node. `G.nodes.data('foo', default=1)`
     |      provides a default for nodes that do not have attribute `foo`.
     |
     |      Parameters
     |      ----------
     |      data : string or bool, optional (default=False)
     |          The node attribute returned in 2-tuple (n, ddict[data]).
     |          If True, return entire node attribute dict as (n, ddict).
     |          If False, return just the nodes n.
     |
     |      default : value, optional (default=None)
     |          Value used for nodes that don't have the requested attribute.
     |          Only relevant if data is not True or False.
     |
     |      Returns
     |      -------
     |      NodeView
     |          Allows set-like operations over the nodes as well as node
     |          attribute dict lookup and calling to get a NodeDataView.
     |          A NodeDataView iterates over `(n, data)` and has no set operations.
     |          A NodeView iterates over `n` and includes set operations.
     |
     |          When called, if data is False, an iterator over nodes.
     |          Otherwise an iterator of 2-tuples (node, attribute value)
     |          where the attribute is specified in `data`.
     |          If data is True then the attribute becomes the
     |          entire data dictionary.
     |
     |      Notes
     |      -----
     |      If your node data is not needed, it is simpler and equivalent
     |      to use the expression ``for n in G``, or ``list(G)``.
     |
     |      Examples
     |      --------
     |      There are two simple ways of getting a list of all nodes in the graph:
     |
     |      >>> G = nx.path_graph(3)
     |      >>> list(G.nodes)
     |      [0, 1, 2]
     |      >>> list(G)
     |      [0, 1, 2]
     |
     |      To get the node data along with the nodes:
     |
     |      >>> G.add_node(1, time="5pm")
     |      >>> G.nodes[0]["foo"] = "bar"
     |      >>> list(G.nodes(data=True))
     |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
     |      >>> list(G.nodes.data())
     |      [(0, {'foo': 'bar'}), (1, {'time': '5pm'}), (2, {})]
     |
     |      >>> list(G.nodes(data="foo"))
     |      [(0, 'bar'), (1, None), (2, None)]
     |      >>> list(G.nodes.data("foo"))
     |      [(0, 'bar'), (1, None), (2, None)]
     |
     |      >>> list(G.nodes(data="time"))
     |      [(0, None), (1, '5pm'), (2, None)]
     |      >>> list(G.nodes.data("time"))
     |      [(0, None), (1, '5pm'), (2, None)]
     |
     |      >>> list(G.nodes(data="time", default="Not Available"))
     |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
     |      >>> list(G.nodes.data("time", default="Not Available"))
     |      [(0, 'Not Available'), (1, '5pm'), (2, 'Not Available')]
     |
     |      If some of your nodes have an attribute and the rest are assumed
     |      to have a default attribute value you can create a dictionary
     |      from node/attribute pairs using the `default` keyword argument
     |      to guarantee the value is never None::
     |
     |          >>> G = nx.Graph()
     |          >>> G.add_node(0)
     |          >>> G.add_node(1, weight=2)
     |          >>> G.add_node(2, weight=3)
     |          >>> dict(G.nodes(data="weight", default=1))
     |          {0: 1, 1: 2, 2: 3}
     |
     |  number_of_edges(self, u=None, v=None)
     |      Returns the number of edges between two nodes.
     |
     |      Parameters
     |      ----------
     |      u, v : nodes, optional (default=all edges)
     |          If u and v are specified, return the number of edges between
     |          u and v. Otherwise return the total number of all edges.
     |
     |      Returns
     |      -------
     |      nedges : int
     |          The number of edges in the graph.  If nodes `u` and `v` are
     |          specified return the number of edges between those nodes. If
     |          the graph is directed, this only returns the number of edges
     |          from `u` to `v`.
     |
     |      See Also
     |      --------
     |      size
     |
     |      Examples
     |      --------
     |      For undirected graphs, this method counts the total number of
     |      edges in the graph:
     |
     |      >>> G = nx.path_graph(4)
     |      >>> G.number_of_edges()
     |      3
     |
     |      If you specify two nodes, this counts the total number of edges
     |      joining the two nodes:
     |
     |      >>> G.number_of_edges(0, 1)
     |      1
     |
     |      For directed graphs, this method can count the total number of
     |      directed edges from `u` to `v`:
     |
     |      >>> G = nx.DiGraph()
     |      >>> G.add_edge(0, 1)
     |      >>> G.add_edge(1, 0)
     |      >>> G.number_of_edges(0, 1)
     |      1
     |
     |  number_of_nodes(self)
     |      Returns the number of nodes in the graph.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      order: identical method
     |      __len__: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.number_of_nodes()
     |      3
     |
     |  order(self)
     |      Returns the number of nodes in the graph.
     |
     |      Returns
     |      -------
     |      nnodes : int
     |          The number of nodes in the graph.
     |
     |      See Also
     |      --------
     |      number_of_nodes: identical method
     |      __len__: identical method
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.order()
     |      3
     |
     |  size(self, weight=None)
     |      Returns the number of edges or total of all edge weights.
     |
     |      Parameters
     |      ----------
     |      weight : string or None, optional (default=None)
     |          The edge attribute that holds the numerical value used
     |          as a weight. If None, then each edge has weight 1.
     |
     |      Returns
     |      -------
     |      size : numeric
     |          The number of edges or
     |          (if weight keyword is provided) the total weight sum.
     |
     |          If weight is None, returns an int. Otherwise a float
     |          (or more general numeric if the weights are more general).
     |
     |      See Also
     |      --------
     |      number_of_edges
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.size()
     |      3
     |
     |      >>> G = nx.Graph()  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> G.add_edge("a", "b", weight=2)
     |      >>> G.add_edge("b", "c", weight=4)
     |      >>> G.size()
     |      2
     |      >>> G.size(weight="weight")
     |      6.0
     |
     |  subgraph(self, nodes)
     |      Returns a SubGraph view of the subgraph induced on `nodes`.
     |
     |      The induced subgraph of the graph contains the nodes in `nodes`
     |      and the edges between those nodes.
     |
     |      Parameters
     |      ----------
     |      nodes : list, iterable
     |          A container of nodes which will be iterated through once.
     |
     |      Returns
     |      -------
     |      G : SubGraph View
     |          A subgraph view of the graph. The graph structure cannot be
     |          changed but node/edge attributes can and are shared with the
     |          original graph.
     |
     |      Notes
     |      -----
     |      The graph, edge and node attributes are shared with the original graph.
     |      Changes to the graph structure is ruled out by the view, but changes
     |      to attributes are reflected in the original graph.
     |
     |      To create a subgraph with its own copy of the edge/node attributes use:
     |      G.subgraph(nodes).copy()
     |
     |      For an inplace reduction of a graph to a subgraph you can remove nodes:
     |      G.remove_nodes_from([n for n in G if n not in set(nodes)])
     |
     |      Subgraph views are sometimes NOT what you want. In most cases where
     |      you want to do more than simply look at the induced edges, it makes
     |      more sense to just create the subgraph as its own graph with code like:
     |
     |      ::
     |
     |          # Create a subgraph SG based on a (possibly multigraph) G
     |          SG = G.__class__()
     |          SG.add_nodes_from((n, G.nodes[n]) for n in largest_wcc)
     |          if SG.is_multigraph():
     |              SG.add_edges_from(
     |                  (n, nbr, key, d)
     |                  for n, nbrs in G.adj.items()
     |                  if n in largest_wcc
     |                  for nbr, keydict in nbrs.items()
     |                  if nbr in largest_wcc
     |                  for key, d in keydict.items()
     |              )
     |          else:
     |              SG.add_edges_from(
     |                  (n, nbr, d)
     |                  for n, nbrs in G.adj.items()
     |                  if n in largest_wcc
     |                  for nbr, d in nbrs.items()
     |                  if nbr in largest_wcc
     |              )
     |          SG.graph.update(G.graph)
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(4)  # or DiGraph, MultiGraph, MultiDiGraph, etc
     |      >>> H = G.subgraph([0, 1, 2])
     |      >>> list(H.edges)
     |      [(0, 1), (1, 2)]
     |
     |  to_directed(self, as_view=False)
     |      Returns a directed representation of the graph.
     |
     |      Returns
     |      -------
     |      G : DiGraph
     |          A directed graph with the same name, same nodes, and with
     |          each edge (u, v, data) replaced by two directed edges
     |          (u, v, data) and (v, u, data).
     |
     |      Notes
     |      -----
     |      This returns a "deepcopy" of the edge, node, and
     |      graph attributes which attempts to completely copy
     |      all of the data and references.
     |
     |      This is in contrast to the similar D=DiGraph(G) which returns a
     |      shallow copy of the data.
     |
     |      See the Python copy module for more information on shallow
     |      and deep copies, https://docs.python.org/3/library/copy.html.
     |
     |      Warning: If you have subclassed Graph to use dict-like objects
     |      in the data structure, those changes do not transfer to the
     |      DiGraph created by this method.
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()  # or MultiGraph, etc
     |      >>> G.add_edge(0, 1)
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1), (1, 0)]
     |
     |      If already directed, return a (deep) copy
     |
     |      >>> G = nx.DiGraph()  # or MultiDiGraph, etc
     |      >>> G.add_edge(0, 1)
     |      >>> H = G.to_directed()
     |      >>> list(H.edges)
     |      [(0, 1)]
     |
     |  to_directed_class(self)
     |      Returns the class to use for empty directed copies.
     |
     |      If you subclass the base classes, use this to designate
     |      what directed class to use for `to_directed()` copies.
     |
     |  to_undirected_class(self)
     |      Returns the class to use for empty undirected copies.
     |
     |      If you subclass the base classes, use this to designate
     |      what directed class to use for `to_directed()` copies.
     |
     |  update(self, edges=None, nodes=None)
     |      Update the graph using nodes/edges/graphs as input.
     |
     |      Like dict.update, this method takes a graph as input, adding the
     |      graph's nodes and edges to this graph. It can also take two inputs:
     |      edges and nodes. Finally it can take either edges or nodes.
     |      To specify only nodes the keyword `nodes` must be used.
     |
     |      The collections of edges and nodes are treated similarly to
     |      the add_edges_from/add_nodes_from methods. When iterated, they
     |      should yield 2-tuples (u, v) or 3-tuples (u, v, datadict).
     |
     |      Parameters
     |      ----------
     |      edges : Graph object, collection of edges, or None
     |          The first parameter can be a graph or some edges. If it has
     |          attributes `nodes` and `edges`, then it is taken to be a
     |          Graph-like object and those attributes are used as collections
     |          of nodes and edges to be added to the graph.
     |          If the first parameter does not have those attributes, it is
     |          treated as a collection of edges and added to the graph.
     |          If the first argument is None, no edges are added.
     |      nodes : collection of nodes, or None
     |          The second parameter is treated as a collection of nodes
     |          to be added to the graph unless it is None.
     |          If `edges is None` and `nodes is None` an exception is raised.
     |          If the first parameter is a Graph, then `nodes` is ignored.
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(5)
     |      >>> G.update(nx.complete_graph(range(4, 10)))
     |      >>> from itertools import combinations
     |      >>> edges = (
     |      ...     (u, v, {"power": u * v})
     |      ...     for u, v in combinations(range(10, 20), 2)
     |      ...     if u * v < 225
     |      ... )
     |      >>> nodes = [1000]  # for singleton, use a container
     |      >>> G.update(edges, nodes)
     |
     |      Notes
     |      -----
     |      It you want to update the graph using an adjacency structure
     |      it is straightforward to obtain the edges/nodes from adjacency.
     |      The following examples provide common cases, your adjacency may
     |      be slightly different and require tweaks of these examples::
     |
     |      >>> # dict-of-set/list/tuple
     |      >>> adj = {1: {2, 3}, 2: {1, 3}, 3: {1, 2}}
     |      >>> e = [(u, v) for u, nbrs in adj.items() for v in nbrs]
     |      >>> G.update(edges=e, nodes=adj)
     |
     |      >>> DG = nx.DiGraph()
     |      >>> # dict-of-dict-of-attribute
     |      >>> adj = {1: {2: 1.3, 3: 0.7}, 2: {1: 1.4}, 3: {1: 0.7}}
     |      >>> e = [
     |      ...     (u, v, {"weight": d})
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, d in nbrs.items()
     |      ... ]
     |      >>> DG.update(edges=e, nodes=adj)
     |
     |      >>> # dict-of-dict-of-dict
     |      >>> adj = {1: {2: {"weight": 1.3}, 3: {"color": 0.7, "weight": 1.2}}}
     |      >>> e = [
     |      ...     (u, v, {"weight": d})
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, d in nbrs.items()
     |      ... ]
     |      >>> DG.update(edges=e, nodes=adj)
     |
     |      >>> # predecessor adjacency (dict-of-set)
     |      >>> pred = {1: {2, 3}, 2: {3}, 3: {3}}
     |      >>> e = [(v, u) for u, nbrs in pred.items() for v in nbrs]
     |
     |      >>> # MultiGraph dict-of-dict-of-dict-of-attribute
     |      >>> MDG = nx.MultiDiGraph()
     |      >>> adj = {
     |      ...     1: {2: {0: {"weight": 1.3}, 1: {"weight": 1.2}}},
     |      ...     3: {2: {0: {"weight": 0.7}}},
     |      ... }
     |      >>> e = [
     |      ...     (u, v, ekey, d)
     |      ...     for u, nbrs in adj.items()
     |      ...     for v, keydict in nbrs.items()
     |      ...     for ekey, d in keydict.items()
     |      ... ]
     |      >>> MDG.update(edges=e)
     |
     |      See Also
     |      --------
     |      add_edges_from: add multiple edges to a graph
     |      add_nodes_from: add multiple nodes to a graph
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from networkx.classes.graph.Graph:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  name
     |      String identifier of the graph.
     |
     |      This graph attribute appears in the attribute dict G.graph
     |      keyed by the string `"name"`. as well as an attribute (technically
     |      a property) `G.name`. This is entirely user controlled.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from networkx.classes.graph.Graph:
     |
     |  __networkx_backend__ = 'networkx'
     |
     |  adjlist_inner_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  adjlist_outer_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  edge_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  graph_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  node_attr_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)
     |
     |
     |  node_dict_factory = <class 'dict'>
     |      dict() -> new empty dictionary
     |      dict(mapping) -> new dictionary initialized from a mapping object's
     |          (key, value) pairs
     |      dict(iterable) -> new dictionary initialized as if via:
     |          d = {}
     |          for k, v in iterable:
     |              d[k] = v
     |      dict(**kwargs) -> new dictionary initialized with the name=value pairs
     |          in the keyword argument list.  For example:  dict(one=1, two=2)

FUNCTIONS
    check_planarity(G, counterexample=False, *, backend=None, **backend_kwargs)
        Check if a graph is planar and return a counterexample or an embedding.

        A graph is planar iff it can be drawn in a plane without
        any edge intersections.

        Parameters
        ----------
        G : NetworkX graph
        counterexample : bool
            A Kuratowski subgraph (to proof non planarity) is only returned if set
            to true.

        Returns
        -------
        (is_planar, certificate) : (bool, NetworkX graph) tuple
            is_planar is true if the graph is planar.
            If the graph is planar `certificate` is a PlanarEmbedding
            otherwise it is a Kuratowski subgraph.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2)])
        >>> is_planar, P = nx.check_planarity(G)
        >>> print(is_planar)
        True

        When `G` is planar, a `PlanarEmbedding` instance is returned:

        >>> P.get_data()
        {0: [1, 2], 1: [0], 2: [0]}

        Notes
        -----
        A (combinatorial) embedding consists of cyclic orderings of the incident
        edges at each vertex. Given such an embedding there are multiple approaches
        discussed in literature to drawing the graph (subject to various
        constraints, e.g. integer coordinates), see e.g. [2].

        The planarity check algorithm and extraction of the combinatorial embedding
        is based on the Left-Right Planarity Test [1].

        A counterexample is only generated if the corresponding parameter is set,
        because the complexity of the counterexample generation is higher.

        See also
        --------
        is_planar :
            Check for planarity without creating a `PlanarEmbedding` or counterexample.

        References
        ----------
        .. [1] Ulrik Brandes:
            The Left-Right Planarity Test
            2009
            http://citeseerx.ist.psu.edu/viewdoc/summary?doi=10.1.1.217.9208
        .. [2] Takao Nishizeki, Md Saidur Rahman:
            Planar graph drawing
            Lecture Notes Series on Computing: Volume 12
            2004

    is_planar(G, *, backend=None, **backend_kwargs)
        Returns True if and only if `G` is planar.

        A graph is *planar* iff it can be drawn in a plane without
        any edge intersections.

        Parameters
        ----------
        G : NetworkX graph

        Returns
        -------
        bool
           Whether the graph is planar.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2)])
        >>> nx.is_planar(G)
        True
        >>> nx.is_planar(nx.complete_graph(5))
        False

        See Also
        --------
        check_planarity :
            Check if graph is planar *and* return a `PlanarEmbedding` instance if True.

DATA
    __all__ = ['check_planarity', 'is_planar', 'PlanarEmbedding']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\planarity.py

networkx.planted_partition_graph
Python Library Documentation: function planted_partition_graph in module networkx.generators.community

planted_partition_graph(l, k, p_in, p_out, seed=None, directed=False, *, backend=None, **backend_kwargs)
    Returns the planted l-partition graph.

    This model partitions a graph with n=l*k vertices in
    l groups with k vertices each. Vertices of the same
    group are linked with a probability p_in, and vertices
    of different groups are linked with probability p_out.

    Parameters
    ----------
    l : int
      Number of groups
    k : int
      Number of vertices in each group
    p_in : float
      probability of connecting vertices within a group
    p_out : float
      probability of connected vertices between groups
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    directed : bool,optional (default=False)
      If True return a directed graph

    Returns
    -------
    G : NetworkX Graph or DiGraph
      planted l-partition graph

    Raises
    ------
    NetworkXError
      If `p_in`, `p_out` are not in `[0, 1]`

    Examples
    --------
    >>> G = nx.planted_partition_graph(4, 3, 0.5, 0.1, seed=42)

    See Also
    --------
    random_partition_model

    References
    ----------
    .. [1] A. Condon, R.M. Karp, Algorithms for graph partitioning
        on the planted partition model,
        Random Struct. Algor. 18 (2001) 116-140.

    .. [2] Santo Fortunato 'Community Detection in Graphs' Physical Reports
       Volume 486, Issue 3-5 p. 75-174. https://arxiv.org/abs/0906.0612
networkx.polynomials
Python Library Documentation: module networkx.algorithms.polynomials in networkx.algorithms

NAME
    networkx.algorithms.polynomials - Provides algorithms supporting the computation of graph polynomials.

DESCRIPTION
    Graph polynomials are polynomial-valued graph invariants that encode a wide
    variety of structural information. Examples include the Tutte polynomial,
    chromatic polynomial, characteristic polynomial, and matching polynomial. An
    extensive treatment is provided in [1]_.

    For a simple example, the `~sympy.matrices.matrices.MatrixDeterminant.charpoly`
    method can be used to compute the characteristic polynomial from the adjacency
    matrix of a graph. Consider the complete graph ``K_4``:

    >>> import sympy
    >>> x = sympy.Symbol("x")
    >>> G = nx.complete_graph(4)
    >>> A = nx.to_numpy_array(G, dtype=int)
    >>> M = sympy.SparseMatrix(A)
    >>> M.charpoly(x).as_expr()
    x**4 - 6*x**2 - 8*x - 3


    .. [1] Y. Shi, M. Dehmer, X. Li, I. Gutman,
       "Graph Polynomials"

FUNCTIONS
    chromatic_polynomial(G, *, backend=None, **backend_kwargs)
        Returns the chromatic polynomial of `G`

        This function computes the chromatic polynomial via an iterative version of
        the deletion-contraction algorithm.

        The chromatic polynomial `X_G(x)` is a fundamental graph polynomial
        invariant in one variable. Evaluating `X_G(k)` for an natural number `k`
        enumerates the proper k-colorings of `G`.

        There are several equivalent definitions; here are three:

        Def 1 (explicit formula):
        For `G` an undirected graph, `c(G)` the number of connected components of
        `G`, `E` the edge set of `G`, and `G(S)` the spanning subgraph of `G` with
        edge set `S` [1]_:

        .. math::

            X_G(x) = \sum_{S \subseteq E} (-1)^{|S|} x^{c(G(S))}


        Def 2 (interpolating polynomial):
        For `G` an undirected graph, `n(G)` the number of vertices of `G`, `k_0 = 0`,
        and `k_i` the number of distinct ways to color the vertices of `G` with `i`
        unique colors (for `i` a natural number at most `n(G)`), `X_G(x)` is the
        unique Lagrange interpolating polynomial of degree `n(G)` through the points
        `(0, k_0), (1, k_1), \dots, (n(G), k_{n(G)})` [2]_.


        Def 3 (chromatic recurrence):
        For `G` an undirected graph, `G-e` the graph obtained from `G` by deleting
        edge `e`, `G/e` the graph obtained from `G` by contracting edge `e`, `n(G)`
        the number of vertices of `G`, and `e(G)` the number of edges of `G` [3]_:

        .. math::
            X_G(x) = \begin{cases}
               x^{n(G)}, & \text{if $e(G)=0$} \\
               X_{G-e}(x) - X_{G/e}(x), & \text{otherwise, for an arbitrary edge $e$}
            \end{cases}

        This formulation is also known as the Fundamental Reduction Theorem [4]_.


        Parameters
        ----------
        G : NetworkX graph

        Returns
        -------
        instance of `sympy.core.add.Add`
            A Sympy expression representing the chromatic polynomial for `G`.

        Examples
        --------
        >>> C = nx.cycle_graph(5)
        >>> nx.chromatic_polynomial(C)
        x**5 - 5*x**4 + 10*x**3 - 10*x**2 + 4*x

        >>> G = nx.complete_graph(4)
        >>> nx.chromatic_polynomial(G)
        x**4 - 6*x**3 + 11*x**2 - 6*x

        Notes
        -----
        Interpretation of the coefficients is discussed in [5]_. Several special
        cases are listed in [2]_.

        The chromatic polynomial is a specialization of the Tutte polynomial; in
        particular, ``X_G(x) = T_G(x, 0)`` [6]_.

        The chromatic polynomial may take negative arguments, though evaluations
        may not have chromatic interpretations. For instance, ``X_G(-1)`` enumerates
        the acyclic orientations of `G` [7]_.

        References
        ----------
        .. [1] D. B. West,
           "Introduction to Graph Theory," p. 222
        .. [2] E. W. Weisstein
           "Chromatic Polynomial"
           MathWorld--A Wolfram Web Resource
           https://mathworld.wolfram.com/ChromaticPolynomial.html
        .. [3] D. B. West,
           "Introduction to Graph Theory," p. 221
        .. [4] J. Zhang, J. Goodall,
           "An Introduction to Chromatic Polynomials"
           https://math.mit.edu/~apost/courses/18.204_2018/Julie_Zhang_paper.pdf
        .. [5] R. C. Read,
           "An Introduction to Chromatic Polynomials"
           Journal of Combinatorial Theory, 1968
           https://math.berkeley.edu/~mrklug/ReadChromatic.pdf
        .. [6] W. T. Tutte,
           "Graph-polynomials"
           Advances in Applied Mathematics, 2004
           https://www.sciencedirect.com/science/article/pii/S0196885803000411
        .. [7] R. P. Stanley,
           "Acyclic orientations of graphs"
           Discrete Mathematics, 2006
           https://math.mit.edu/~rstan/pubs/pubfiles/18.pdf

    tutte_polynomial(G, *, backend=None, **backend_kwargs)
        Returns the Tutte polynomial of `G`

        This function computes the Tutte polynomial via an iterative version of
        the deletion-contraction algorithm.

        The Tutte polynomial `T_G(x, y)` is a fundamental graph polynomial invariant in
        two variables. It encodes a wide array of information related to the
        edge-connectivity of a graph; "Many problems about graphs can be reduced to
        problems of finding and evaluating the Tutte polynomial at certain values" [1]_.
        In fact, every deletion-contraction-expressible feature of a graph is a
        specialization of the Tutte polynomial [2]_ (see Notes for examples).

        There are several equivalent definitions; here are three:

        Def 1 (rank-nullity expansion): For `G` an undirected graph, `n(G)` the
        number of vertices of `G`, `E` the edge set of `G`, `V` the vertex set of
        `G`, and `c(A)` the number of connected components of the graph with vertex
        set `V` and edge set `A` [3]_:

        .. math::

            T_G(x, y) = \sum_{A \in E} (x-1)^{c(A) - c(E)} (y-1)^{c(A) + |A| - n(G)}

        Def 2 (spanning tree expansion): Let `G` be an undirected graph, `T` a spanning
        tree of `G`, and `E` the edge set of `G`. Let `E` have an arbitrary strict
        linear order `L`. Let `B_e` be the unique minimal nonempty edge cut of
        $E \setminus T \cup {e}$. An edge `e` is internally active with respect to
        `T` and `L` if `e` is the least edge in `B_e` according to the linear order
        `L`. The internal activity of `T` (denoted `i(T)`) is the number of edges
        in $E \setminus T$ that are internally active with respect to `T` and `L`.
        Let `P_e` be the unique path in $T \cup {e}$ whose source and target vertex
        are the same. An edge `e` is externally active with respect to `T` and `L`
        if `e` is the least edge in `P_e` according to the linear order `L`. The
        external activity of `T` (denoted `e(T)`) is the number of edges in
        $E \setminus T$ that are externally active with respect to `T` and `L`.
        Then [4]_ [5]_:

        .. math::

            T_G(x, y) = \sum_{T \text{ a spanning tree of } G} x^{i(T)} y^{e(T)}

        Def 3 (deletion-contraction recurrence): For `G` an undirected graph, `G-e`
        the graph obtained from `G` by deleting edge `e`, `G/e` the graph obtained
        from `G` by contracting edge `e`, `k(G)` the number of cut-edges of `G`,
        and `l(G)` the number of self-loops of `G`:

        .. math::
            T_G(x, y) = \begin{cases}
               x^{k(G)} y^{l(G)}, & \text{if all edges are cut-edges or self-loops} \\
               T_{G-e}(x, y) + T_{G/e}(x, y), & \text{otherwise, for an arbitrary edge $e$ not a cut-edge or loop}
            \end{cases}

        Parameters
        ----------
        G : NetworkX graph

        Returns
        -------
        instance of `sympy.core.add.Add`
            A Sympy expression representing the Tutte polynomial for `G`.

        Examples
        --------
        >>> C = nx.cycle_graph(5)
        >>> nx.tutte_polynomial(C)
        x**4 + x**3 + x**2 + x + y

        >>> D = nx.diamond_graph()
        >>> nx.tutte_polynomial(D)
        x**3 + 2*x**2 + 2*x*y + x + y**2 + y

        Notes
        -----
        Some specializations of the Tutte polynomial:

        - `T_G(1, 1)` counts the number of spanning trees of `G`
        - `T_G(1, 2)` counts the number of connected spanning subgraphs of `G`
        - `T_G(2, 1)` counts the number of spanning forests in `G`
        - `T_G(0, 2)` counts the number of strong orientations of `G`
        - `T_G(2, 0)` counts the number of acyclic orientations of `G`

        Edge contraction is defined and deletion-contraction is introduced in [6]_.
        Combinatorial meaning of the coefficients is introduced in [7]_.
        Universality, properties, and applications are discussed in [8]_.

        Practically, up-front computation of the Tutte polynomial may be useful when
        users wish to repeatedly calculate edge-connectivity-related information
        about one or more graphs.

        References
        ----------
        .. [1] M. Brandt,
           "The Tutte Polynomial."
           Talking About Combinatorial Objects Seminar, 2015
           https://math.berkeley.edu/~brandtm/talks/tutte.pdf
        .. [2] A. Björklund, T. Husfeldt, P. Kaski, M. Koivisto,
           "Computing the Tutte polynomial in vertex-exponential time"
           49th Annual IEEE Symposium on Foundations of Computer Science, 2008
           https://ieeexplore.ieee.org/abstract/document/4691000
        .. [3] Y. Shi, M. Dehmer, X. Li, I. Gutman,
           "Graph Polynomials," p. 14
        .. [4] Y. Shi, M. Dehmer, X. Li, I. Gutman,
           "Graph Polynomials," p. 46
        .. [5] A. Nešetril, J. Goodall,
           "Graph invariants, homomorphisms, and the Tutte polynomial"
           https://iuuk.mff.cuni.cz/~andrew/Tutte.pdf
        .. [6] D. B. West,
           "Introduction to Graph Theory," p. 84
        .. [7] G. Coutinho,
           "A brief introduction to the Tutte polynomial"
           Structural Analysis of Complex Networks, 2011
           https://homepages.dcc.ufmg.br/~gabriel/seminars/coutinho_tuttepolynomial_seminar.pdf
        .. [8] J. A. Ellis-Monaghan, C. Merino,
           "Graph polynomials and their applications I: The Tutte polynomial"
           Structural Analysis of Complex Networks, 2011
           https://arxiv.org/pdf/0803.3079.pdf

DATA
    __all__ = ['tutte_polynomial', 'chromatic_polynomial']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\polynomials.py

networkx.power
Python Library Documentation: function power in module networkx.algorithms.operators.product

power(G, k, *, backend=None, **backend_kwargs)
    Returns the specified power of a graph.

    The $k$th power of a simple graph $G$, denoted $G^k$, is a
    graph on the same set of nodes in which two distinct nodes $u$ and
    $v$ are adjacent in $G^k$ if and only if the shortest path
    distance between $u$ and $v$ in $G$ is at most $k$.

    Parameters
    ----------
    G : graph
        A NetworkX simple graph object.

    k : positive integer
        The power to which to raise the graph `G`.

    Returns
    -------
    NetworkX simple graph
        `G` to the power `k`.

    Raises
    ------
    ValueError
        If the exponent `k` is not positive.

    NetworkXNotImplemented
        If `G` is not a simple graph.

    Examples
    --------
    The number of edges will never decrease when taking successive
    powers:

    >>> G = nx.path_graph(4)
    >>> list(nx.power(G, 2).edges)
    [(0, 1), (0, 2), (1, 2), (1, 3), (2, 3)]
    >>> list(nx.power(G, 3).edges)
    [(0, 1), (0, 2), (0, 3), (1, 2), (1, 3), (2, 3)]

    The `k` th power of a cycle graph on *n* nodes is the complete graph
    on *n* nodes, if `k` is at least ``n // 2``:

    >>> G = nx.cycle_graph(5)
    >>> H = nx.complete_graph(5)
    >>> nx.is_isomorphic(nx.power(G, 2), H)
    True
    >>> G = nx.cycle_graph(8)
    >>> H = nx.complete_graph(8)
    >>> nx.is_isomorphic(nx.power(G, 4), H)
    True

    References
    ----------
    .. [1] J. A. Bondy, U. S. R. Murty, *Graph Theory*. Springer, 2008.

    Notes
    -----
    This definition of "power graph" comes from Exercise 3.1.6 of
    *Graph Theory* by Bondy and Murty [1]_.
networkx.powerlaw_cluster_graph
Python Library Documentation: function powerlaw_cluster_graph in module networkx.generators.random_graphs

powerlaw_cluster_graph(n, m, p, seed=None, *, create_using=None, backend=None, **backend_kwargs)
    Holme and Kim algorithm for growing graphs with powerlaw
    degree distribution and approximate average clustering.

    Parameters
    ----------
    n : int
        the number of nodes
    m : int
        the number of random edges to add for each new node
    p : float,
        Probability of adding a triangle after adding a random edge
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Notes
    -----
    The average clustering has a hard time getting above a certain
    cutoff that depends on `m`.  This cutoff is often quite low.  The
    transitivity (fraction of triangles to possible triangles) seems to
    decrease with network size.

    It is essentially the Barabási–Albert (BA) growth model with an
    extra step that each random edge is followed by a chance of
    making an edge to one of its neighbors too (and thus a triangle).

    This algorithm improves on BA in the sense that it enables a
    higher average clustering to be attained if desired.

    It seems possible to have a disconnected graph with this algorithm
    since the initial `m` nodes may not be all linked to a new node
    on the first iteration like the BA model.

    Raises
    ------
    NetworkXError
        If `m` does not satisfy ``1 <= m <= n`` or `p` does not
        satisfy ``0 <= p <= 1``.

    References
    ----------
    .. [1] P. Holme and B. J. Kim,
       "Growing scale-free networks with tunable clustering",
       Phys. Rev. E, 65, 026107, 2002.
networkx.predecessor
Python Library Documentation: function predecessor in module networkx.algorithms.shortest_paths.unweighted

predecessor(G, source, target=None, cutoff=None, return_seen=None, *, backend=None, **backend_kwargs)
    Returns dict of predecessors for the path from source to all nodes in G.

    Parameters
    ----------
    G : NetworkX graph

    source : node label
       Starting node for path

    target : node label, optional
       Ending node for path. If provided only predecessors between
       source and target are returned

    cutoff : integer, optional
        Depth to stop the search. Only paths of length <= cutoff are returned.

    return_seen : bool, optional (default=None)
        Whether to return a dictionary, keyed by node, of the level (number of
        hops) to reach the node (as seen during breadth-first-search).

    Returns
    -------
    pred : dictionary
        Dictionary, keyed by node, of predecessors in the shortest path.


    (pred, seen): tuple of dictionaries
        If `return_seen` argument is set to `True`, then a tuple of dictionaries
        is returned. The first element is the dictionary, keyed by node, of
        predecessors in the shortest path. The second element is the dictionary,
        keyed by node, of the level (number of hops) to reach the node (as seen
        during breadth-first-search).

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> list(G)
    [0, 1, 2, 3]
    >>> nx.predecessor(G, 0)
    {0: [], 1: [0], 2: [1], 3: [2]}
    >>> nx.predecessor(G, 0, return_seen=True)
    ({0: [], 1: [0], 2: [1], 3: [2]}, {0: 0, 1: 1, 2: 2, 3: 3})
networkx.preferential_attachment
Python Library Documentation: function preferential_attachment in module networkx.algorithms.link_prediction

preferential_attachment(G, ebunch=None, *, backend=None, **backend_kwargs)
    Compute the preferential attachment score of all node pairs in ebunch.

    Preferential attachment score of `u` and `v` is defined as

    .. math::

        |\Gamma(u)| |\Gamma(v)|

    where $\Gamma(u)$ denotes the set of neighbors of $u$.

    Parameters
    ----------
    G : graph
        NetworkX undirected graph.

    ebunch : iterable of node pairs, optional (default = None)
        Preferential attachment score will be computed for each pair of
        nodes given in the iterable. The pairs must be given as
        2-tuples (u, v) where u and v are nodes in the graph. If ebunch
        is None then all nonexistent edges in the graph will be used.
        Default value: None.

    Returns
    -------
    piter : iterator
        An iterator of 3-tuples in the form (u, v, p) where (u, v) is a
        pair of nodes and p is their preferential attachment score.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a `DiGraph`, a `Multigraph` or a `MultiDiGraph`.

    NodeNotFound
        If `ebunch` has a node that is not in `G`.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> preds = nx.preferential_attachment(G, [(0, 1), (2, 3)])
    >>> for u, v, p in preds:
    ...     print(f"({u}, {v}) -> {p}")
    (0, 1) -> 16
    (2, 3) -> 16

    References
    ----------
    .. [1] D. Liben-Nowell, J. Kleinberg.
           The Link Prediction Problem for Social Networks (2004).
           http://www.cs.cornell.edu/home/kleinber/link-pred.pdf
networkx.prefix_tree
Python Library Documentation: function prefix_tree in module networkx.generators.trees

prefix_tree(paths, *, backend=None, **backend_kwargs)
    Creates a directed prefix tree from a list of paths.

    Usually the paths are described as strings or lists of integers.

    A "prefix tree" represents the prefix structure of the strings.
    Each node represents a prefix of some string. The root represents
    the empty prefix with children for the single letter prefixes which
    in turn have children for each double letter prefix starting with
    the single letter corresponding to the parent node, and so on.

    More generally the prefixes do not need to be strings. A prefix refers
    to the start of a sequence. The root has children for each one element
    prefix and they have children for each two element prefix that starts
    with the one element sequence of the parent, and so on.

    Note that this implementation uses integer nodes with an attribute.
    Each node has an attribute "source" whose value is the original element
    of the path to which this node corresponds. For example, suppose `paths`
    consists of one path: "can". Then the nodes `[1, 2, 3]` which represent
    this path have "source" values "c", "a" and "n".

    All the descendants of a node have a common prefix in the sequence/path
    associated with that node. From the returned tree, the prefix for each
    node can be constructed by traversing the tree up to the root and
    accumulating the "source" values along the way.

    The root node is always `0` and has "source" attribute `None`.
    The root is the only node with in-degree zero.
    The nil node is always `-1` and has "source" attribute `"NIL"`.
    The nil node is the only node with out-degree zero.


    Parameters
    ----------
    paths: iterable of paths
        An iterable of paths which are themselves sequences.
        Matching prefixes among these sequences are identified with
        nodes of the prefix tree. One leaf of the tree is associated
        with each path. (Identical paths are associated with the same
        leaf of the tree.)


    Returns
    -------
    tree: DiGraph
        A directed graph representing an arborescence consisting of the
        prefix tree generated by `paths`. Nodes are directed "downward",
        from parent to child. A special "synthetic" root node is added
        to be the parent of the first node in each path. A special
        "synthetic" leaf node, the "nil" node `-1`, is added to be the child
        of all nodes representing the last element in a path. (The
        addition of this nil node technically makes this not an
        arborescence but a directed acyclic graph; removing the nil node
        makes it an arborescence.)


    Notes
    -----
    The prefix tree is also known as a *trie*.


    Examples
    --------
    Create a prefix tree from a list of strings with common prefixes::

        >>> paths = ["ab", "abs", "ad"]
        >>> T = nx.prefix_tree(paths)
        >>> list(T.edges)
        [(0, 1), (1, 2), (1, 4), (2, -1), (2, 3), (3, -1), (4, -1)]

    The leaf nodes can be obtained as predecessors of the nil node::

        >>> root, NIL = 0, -1
        >>> list(T.predecessors(NIL))
        [2, 3, 4]

    To recover the original paths that generated the prefix tree,
    traverse up the tree from the node `-1` to the node `0`::

        >>> recovered = []
        >>> for v in T.predecessors(NIL):
        ...     prefix = ""
        ...     while v != root:
        ...         prefix = str(T.nodes[v]["source"]) + prefix
        ...         v = next(T.predecessors(v))  # only one predecessor
        ...     recovered.append(prefix)
        >>> sorted(recovered)
        ['ab', 'abs', 'ad']
networkx.prefix_tree_recursive
Python Library Documentation: function prefix_tree_recursive in module networkx.generators.trees

prefix_tree_recursive(paths, *, backend=None, **backend_kwargs)
    Recursively creates a directed prefix tree from a list of paths.

    The original recursive version of prefix_tree for comparison. It is
    the same algorithm but the recursion is unrolled onto a stack.

    Usually the paths are described as strings or lists of integers.

    A "prefix tree" represents the prefix structure of the strings.
    Each node represents a prefix of some string. The root represents
    the empty prefix with children for the single letter prefixes which
    in turn have children for each double letter prefix starting with
    the single letter corresponding to the parent node, and so on.

    More generally the prefixes do not need to be strings. A prefix refers
    to the start of a sequence. The root has children for each one element
    prefix and they have children for each two element prefix that starts
    with the one element sequence of the parent, and so on.

    Note that this implementation uses integer nodes with an attribute.
    Each node has an attribute "source" whose value is the original element
    of the path to which this node corresponds. For example, suppose `paths`
    consists of one path: "can". Then the nodes `[1, 2, 3]` which represent
    this path have "source" values "c", "a" and "n".

    All the descendants of a node have a common prefix in the sequence/path
    associated with that node. From the returned tree, ehe prefix for each
    node can be constructed by traversing the tree up to the root and
    accumulating the "source" values along the way.

    The root node is always `0` and has "source" attribute `None`.
    The root is the only node with in-degree zero.
    The nil node is always `-1` and has "source" attribute `"NIL"`.
    The nil node is the only node with out-degree zero.


    Parameters
    ----------
    paths: iterable of paths
        An iterable of paths which are themselves sequences.
        Matching prefixes among these sequences are identified with
        nodes of the prefix tree. One leaf of the tree is associated
        with each path. (Identical paths are associated with the same
        leaf of the tree.)


    Returns
    -------
    tree: DiGraph
        A directed graph representing an arborescence consisting of the
        prefix tree generated by `paths`. Nodes are directed "downward",
        from parent to child. A special "synthetic" root node is added
        to be the parent of the first node in each path. A special
        "synthetic" leaf node, the "nil" node `-1`, is added to be the child
        of all nodes representing the last element in a path. (The
        addition of this nil node technically makes this not an
        arborescence but a directed acyclic graph; removing the nil node
        makes it an arborescence.)


    Notes
    -----
    The prefix tree is also known as a *trie*.


    Examples
    --------
    Create a prefix tree from a list of strings with common prefixes::

        >>> paths = ["ab", "abs", "ad"]
        >>> T = nx.prefix_tree(paths)
        >>> list(T.edges)
        [(0, 1), (1, 2), (1, 4), (2, -1), (2, 3), (3, -1), (4, -1)]

    The leaf nodes can be obtained as predecessors of the nil node.

        >>> root, NIL = 0, -1
        >>> list(T.predecessors(NIL))
        [2, 3, 4]

    To recover the original paths that generated the prefix tree,
    traverse up the tree from the node `-1` to the node `0`::

        >>> recovered = []
        >>> for v in T.predecessors(NIL):
        ...     prefix = ""
        ...     while v != root:
        ...         prefix = str(T.nodes[v]["source"]) + prefix
        ...         v = next(T.predecessors(v))  # only one predecessor
        ...     recovered.append(prefix)
        >>> sorted(recovered)
        ['ab', 'abs', 'ad']
networkx.product
Python Library Documentation: module networkx.algorithms.operators.product in networkx.algorithms.operators

NAME
    networkx.algorithms.operators.product - Graph products.

FUNCTIONS
    cartesian_product(G, H, *, backend=None, **backend_kwargs)
        Returns the Cartesian product of G and H.

        The Cartesian product $P$ of the graphs $G$ and $H$ has a node set that
        is the Cartesian product of the node sets, $V(P)=V(G) \times V(H)$.
        $P$ has an edge $((u,v),(x,y))$ if and only if either $u$ is equal to $x$
        and both $v$ and $y$ are adjacent in $H$ or if $v$ is equal to $y$ and
        both $u$ and $x$ are adjacent in $G$.

        Parameters
        ----------
        G, H: graphs
         Networkx graphs.

        Returns
        -------
        P: NetworkX graph
         The Cartesian product of G and H. P will be a multi-graph if either G
         or H is a multi-graph. Will be a directed if G and H are directed,
         and undirected if G and H are undirected.

        Raises
        ------
        NetworkXError
         If G and H are not both directed or both undirected.

        Notes
        -----
        Node attributes in P are two-tuple of the G and H node attributes.
        Missing attributes are assigned None.

        Examples
        --------
        >>> G = nx.Graph()
        >>> H = nx.Graph()
        >>> G.add_node(0, a1=True)
        >>> H.add_node("a", a2="Spam")
        >>> P = nx.cartesian_product(G, H)
        >>> list(P)
        [(0, 'a')]

        Edge attributes and edge keys (for multigraphs) are also copied to the
        new product graph

    corona_product(G, H, *, backend=None, **backend_kwargs)
        Returns the Corona product of G and H.

        The corona product of $G$ and $H$ is the graph $C = G \circ H$ obtained by
        taking one copy of $G$, called the center graph, $|V(G)|$ copies of $H$,
        called the outer graph, and making the $i$-th vertex of $G$ adjacent to
        every vertex of the $i$-th copy of $H$, where $1 ≤ i ≤ |V(G)|$.

        Parameters
        ----------
        G, H: NetworkX graphs
            The graphs to take the carona product of.
            `G` is the center graph and `H` is the outer graph

        Returns
        -------
        C: NetworkX graph
            The Corona product of G and H.

        Raises
        ------
        NetworkXError
            If G and H are not both directed or both undirected.

        Examples
        --------
        >>> G = nx.cycle_graph(4)
        >>> H = nx.path_graph(2)
        >>> C = nx.corona_product(G, H)
        >>> list(C)
        [0, 1, 2, 3, (0, 0), (0, 1), (1, 0), (1, 1), (2, 0), (2, 1), (3, 0), (3, 1)]
        >>> print(C)
        Graph with 12 nodes and 16 edges

        References
        ----------
        [1] M. Tavakoli, F. Rahbarnia, and A. R. Ashrafi,
            "Studying the corona product of graphs under some graph invariants,"
            Transactions on Combinatorics, vol. 3, no. 3, pp. 43–49, Sep. 2014,
            doi: 10.22108/toc.2014.5542.
        [2] A. Faraji, "Corona Product in Graph Theory," Ali Faraji, May 11, 2021.
            https://blog.alifaraji.ir/math/graph-theory/corona-product.html (accessed Dec. 07, 2021).

    lexicographic_product(G, H, *, backend=None, **backend_kwargs)
        Returns the lexicographic product of G and H.

        The lexicographical product $P$ of the graphs $G$ and $H$ has a node set
        that is the Cartesian product of the node sets, $V(P)=V(G) \times V(H)$.
        $P$ has an edge $((u,v), (x,y))$ if and only if $(u,v)$ is an edge in $G$
        or $u==v$ and $(x,y)$ is an edge in $H$.

        Parameters
        ----------
        G, H: graphs
         Networkx graphs.

        Returns
        -------
        P: NetworkX graph
         The Cartesian product of G and H. P will be a multi-graph if either G
         or H is a multi-graph. Will be a directed if G and H are directed,
         and undirected if G and H are undirected.

        Raises
        ------
        NetworkXError
         If G and H are not both directed or both undirected.

        Notes
        -----
        Node attributes in P are two-tuple of the G and H node attributes.
        Missing attributes are assigned None.

        Examples
        --------
        >>> G = nx.Graph()
        >>> H = nx.Graph()
        >>> G.add_node(0, a1=True)
        >>> H.add_node("a", a2="Spam")
        >>> P = nx.lexicographic_product(G, H)
        >>> list(P)
        [(0, 'a')]

        Edge attributes and edge keys (for multigraphs) are also copied to the
        new product graph

    modular_product(G, H, *, backend=None, **backend_kwargs)
        Returns the Modular product of G and H.

        The modular product of `G` and `H` is the graph $M = G \nabla H$,
        consisting of the node set $V(M) = V(G) \times V(H)$ that is the Cartesian
        product of the node sets of `G` and `H`. Further, M contains an edge ((u, v), (x, y)):

        - if u is adjacent to x in `G` and v is adjacent to y in `H`, or
        - if u is not adjacent to x in `G` and v is not adjacent to y in `H`.

        More formally::

            E(M) = {((u, v), (x, y)) | ((u, x) in E(G) and (v, y) in E(H)) or
                                       ((u, x) not in E(G) and (v, y) not in E(H))}

        Parameters
        ----------
        G, H: NetworkX graphs
            The graphs to take the modular product of.

        Returns
        -------
        M: NetworkX graph
            The Modular product of `G` and `H`.

        Raises
        ------
        NetworkXNotImplemented
            If `G` is not a simple graph.

        Examples
        --------
        >>> G = nx.cycle_graph(4)
        >>> H = nx.path_graph(2)
        >>> M = nx.modular_product(G, H)
        >>> list(M)
        [(0, 0), (0, 1), (1, 0), (1, 1), (2, 0), (2, 1), (3, 0), (3, 1)]
        >>> print(M)
        Graph with 8 nodes and 8 edges

        Notes
        -----
        The *modular product* is defined in [1]_ and was first
        introduced as the *weak modular product*.

        The modular product reduces the problem of counting isomorphic subgraphs
        in `G` and `H` to the problem of counting cliques in M. The subgraphs of
        `G` and `H` that are induced by the nodes of a clique in M are
        isomorphic [2]_ [3]_.

        References
        ----------
        .. [1] R. Hammack, W. Imrich, and S. Klavžar,
            "Handbook of Product Graphs", CRC Press, 2011.

        .. [2] H. G. Barrow and R. M. Burstall,
            "Subgraph isomorphism, matching relational structures and maximal
            cliques", Information Processing Letters, vol. 4, issue 4, pp. 83-84,
            1976, https://doi.org/10.1016/0020-0190(76)90049-1.

        .. [3] V. G. Vizing, "Reduction of the problem of isomorphism and isomorphic
            entrance to the task of finding the nondensity of a graph." Proc. Third
            All-Union Conference on Problems of Theoretical Cybernetics. 1974.

    power(G, k, *, backend=None, **backend_kwargs)
        Returns the specified power of a graph.

        The $k$th power of a simple graph $G$, denoted $G^k$, is a
        graph on the same set of nodes in which two distinct nodes $u$ and
        $v$ are adjacent in $G^k$ if and only if the shortest path
        distance between $u$ and $v$ in $G$ is at most $k$.

        Parameters
        ----------
        G : graph
            A NetworkX simple graph object.

        k : positive integer
            The power to which to raise the graph `G`.

        Returns
        -------
        NetworkX simple graph
            `G` to the power `k`.

        Raises
        ------
        ValueError
            If the exponent `k` is not positive.

        NetworkXNotImplemented
            If `G` is not a simple graph.

        Examples
        --------
        The number of edges will never decrease when taking successive
        powers:

        >>> G = nx.path_graph(4)
        >>> list(nx.power(G, 2).edges)
        [(0, 1), (0, 2), (1, 2), (1, 3), (2, 3)]
        >>> list(nx.power(G, 3).edges)
        [(0, 1), (0, 2), (0, 3), (1, 2), (1, 3), (2, 3)]

        The `k` th power of a cycle graph on *n* nodes is the complete graph
        on *n* nodes, if `k` is at least ``n // 2``:

        >>> G = nx.cycle_graph(5)
        >>> H = nx.complete_graph(5)
        >>> nx.is_isomorphic(nx.power(G, 2), H)
        True
        >>> G = nx.cycle_graph(8)
        >>> H = nx.complete_graph(8)
        >>> nx.is_isomorphic(nx.power(G, 4), H)
        True

        References
        ----------
        .. [1] J. A. Bondy, U. S. R. Murty, *Graph Theory*. Springer, 2008.

        Notes
        -----
        This definition of "power graph" comes from Exercise 3.1.6 of
        *Graph Theory* by Bondy and Murty [1]_.

    rooted_product(G, H, root, *, backend=None, **backend_kwargs)
        Return the rooted product of graphs G and H rooted at root in H.

        A new graph is constructed representing the rooted product of
        the inputted graphs, G and H, with a root in H.
        A rooted product duplicates H for each nodes in G with the root
        of H corresponding to the node in G. Nodes are renamed as the direct
        product of G and H. The result is a subgraph of the cartesian product.

        Parameters
        ----------
        G,H : graph
           A NetworkX graph
        root : node
           A node in H

        Returns
        -------
        R : The rooted product of G and H with a specified root in H

        Notes
        -----
        The nodes of R are the Cartesian Product of the nodes of G and H.
        The nodes of G and H are not relabeled.

    strong_product(G, H, *, backend=None, **backend_kwargs)
        Returns the strong product of G and H.

        The strong product $P$ of the graphs $G$ and $H$ has a node set that
        is the Cartesian product of the node sets, $V(P)=V(G) \times V(H)$.
        $P$ has an edge $((u,x), (v,y))$ if any of the following conditions
        are met:

        - $u=v$ and $(x,y)$ is an edge in $H$
        - $x=y$ and $(u,v)$ is an edge in $G$
        - $(u,v)$ is an edge in $G$ and $(x,y)$ is an edge in $H$

        Parameters
        ----------
        G, H: graphs
         Networkx graphs.

        Returns
        -------
        P: NetworkX graph
         The Cartesian product of G and H. P will be a multi-graph if either G
         or H is a multi-graph. Will be a directed if G and H are directed,
         and undirected if G and H are undirected.

        Raises
        ------
        NetworkXError
         If G and H are not both directed or both undirected.

        Notes
        -----
        Node attributes in P are two-tuple of the G and H node attributes.
        Missing attributes are assigned None.

        Examples
        --------
        >>> G = nx.Graph()
        >>> H = nx.Graph()
        >>> G.add_node(0, a1=True)
        >>> H.add_node("a", a2="Spam")
        >>> P = nx.strong_product(G, H)
        >>> list(P)
        [(0, 'a')]

        Edge attributes and edge keys (for multigraphs) are also copied to the
        new product graph

    tensor_product(G, H, *, backend=None, **backend_kwargs)
        Returns the tensor product of G and H.

        The tensor product $P$ of the graphs $G$ and $H$ has a node set that
        is the Cartesian product of the node sets, $V(P)=V(G) \times V(H)$.
        $P$ has an edge $((u,v), (x,y))$ if and only if $(u,x)$ is an edge in $G$
        and $(v,y)$ is an edge in $H$.

        Tensor product is sometimes also referred to as the categorical product,
        direct product, cardinal product or conjunction.


        Parameters
        ----------
        G, H: graphs
         Networkx graphs.

        Returns
        -------
        P: NetworkX graph
         The tensor product of G and H. P will be a multi-graph if either G
         or H is a multi-graph, will be a directed if G and H are directed,
         and undirected if G and H are undirected.

        Raises
        ------
        NetworkXError
         If G and H are not both directed or both undirected.

        Notes
        -----
        Node attributes in P are two-tuple of the G and H node attributes.
        Missing attributes are assigned None.

        Examples
        --------
        >>> G = nx.Graph()
        >>> H = nx.Graph()
        >>> G.add_node(0, a1=True)
        >>> H.add_node("a", a2="Spam")
        >>> P = nx.tensor_product(G, H)
        >>> list(P)
        [(0, 'a')]

        Edge attributes and edge keys (for multigraphs) are also copied to the
        new product graph

DATA
    __all__ = ['tensor_product', 'cartesian_product', 'lexicographic_produ...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\operators\product.py

networkx.projected_graph
Python Library Documentation: function projected_graph in module networkx.algorithms.bipartite.projection

projected_graph(B, nodes, multigraph=False, *, backend=None, **backend_kwargs)
    Returns the projection of B onto one of its node sets.

    Returns the graph G that is the projection of the bipartite graph B
    onto the specified nodes. They retain their attributes and are connected
    in G if they have a common neighbor in B.

    Parameters
    ----------
    B : NetworkX graph
      The input graph should be bipartite.

    nodes : list or iterable
      Nodes to project onto (the "bottom" nodes).

    multigraph: bool (default=False)
       If True return a multigraph where the multiple edges represent multiple
       shared neighbors.  They edge key in the multigraph is assigned to the
       label of the neighbor.

    Returns
    -------
    Graph : NetworkX graph or multigraph
       A graph that is the projection onto the given nodes.

    Examples
    --------
    >>> from networkx.algorithms import bipartite
    >>> B = nx.path_graph(4)
    >>> G = bipartite.projected_graph(B, [1, 3])
    >>> list(G)
    [1, 3]
    >>> list(G.edges())
    [(1, 3)]

    If nodes `a`, and `b` are connected through both nodes 1 and 2 then
    building a multigraph results in two edges in the projection onto
    [`a`, `b`]:

    >>> B = nx.Graph()
    >>> B.add_edges_from([("a", 1), ("b", 1), ("a", 2), ("b", 2)])
    >>> G = bipartite.projected_graph(B, ["a", "b"], multigraph=True)
    >>> print([sorted((u, v)) for u, v in G.edges()])
    [['a', 'b'], ['a', 'b']]

    Notes
    -----
    No attempt is made to verify that the input graph B is bipartite.
    Returns a simple graph that is the projection of the bipartite graph B
    onto the set of nodes given in list nodes.  If multigraph=True then
    a multigraph is returned with an edge for every shared neighbor.

    Directed graphs are allowed as input.  The output will also then
    be a directed graph with edges if there is a directed path between
    the nodes.

    The graph and node properties are (shallow) copied to the projected graph.

    See :mod:`bipartite documentation <networkx.algorithms.bipartite>`
    for further details on how bipartite graphs are handled in NetworkX.

    See Also
    --------
    is_bipartite,
    is_bipartite_node_set,
    sets,
    weighted_projected_graph,
    collaboration_weighted_projected_graph,
    overlap_weighted_projected_graph,
    generic_weighted_projected_graph
networkx.prominent_group
Python Library Documentation: function prominent_group in module networkx.algorithms.centrality.group

prominent_group(G, k, weight=None, C=None, endpoints=False, normalized=True, greedy=False, *, backend=None, **backend_kwargs)
    Find the prominent group of size $k$ in graph $G$. The prominence of the
    group is evaluated by the group betweenness centrality.

    Group betweenness centrality of a group of nodes $C$ is the sum of the
    fraction of all-pairs shortest paths that pass through any vertex in $C$

    .. math::

       c_B(v) =\sum_{s,t \in V} \frac{\sigma(s, t|v)}{\sigma(s, t)}

    where $V$ is the set of nodes, $\sigma(s, t)$ is the number of
    shortest $(s, t)$-paths, and $\sigma(s, t|C)$ is the number of
    those paths passing through some node in group $C$. Note that
    $(s, t)$ are not members of the group ($V-C$ is the set of nodes
    in $V$ that are not in $C$).

    Parameters
    ----------
    G : graph
       A NetworkX graph.

    k : int
       The number of nodes in the group.

    normalized : bool, optional (default=True)
       If True, group betweenness is normalized by ``1/((|V|-|C|)(|V|-|C|-1))``
       where ``|V|`` is the number of nodes in G and ``|C|`` is the number of
       nodes in C.

    weight : None or string, optional (default=None)
       If None, all edge weights are considered equal.
       Otherwise holds the name of the edge attribute used as weight.
       The weight of an edge is treated as the length or distance between the two sides.

    endpoints : bool, optional (default=False)
       If True include the endpoints in the shortest path counts.

    C : list or set, optional (default=None)
       list of nodes which won't be candidates of the prominent group.

    greedy : bool, optional (default=False)
       Using a naive greedy algorithm in order to find non-optimal prominent
       group. For scale free networks the results are negligibly below the optimal
       results.

    Raises
    ------
    NodeNotFound
       If node(s) in C are not present in G.

    Returns
    -------
    max_GBC : float
       The group betweenness centrality of the prominent group.

    max_group : list
        The list of nodes in the prominent group.

    See Also
    --------
    betweenness_centrality, group_betweenness_centrality

    Notes
    -----
    Group betweenness centrality is described in [1]_ and its importance discussed in [3]_.
    The algorithm is described in [2]_ and is based on techniques mentioned in [4]_.

    The number of nodes in the group must be a maximum of ``n - 2`` where ``n``
    is the total number of nodes in the graph.

    For weighted graphs the edge weights must be greater than zero.
    Zero edge weights can produce an infinite number of equal length
    paths between pairs of nodes.

    The total number of paths between source and target is counted
    differently for directed and undirected graphs. Directed paths
    between "u" and "v" are counted as two possible paths (one each
    direction) while undirected paths between "u" and "v" are counted
    as one path. Said another way, the sum in the expression above is
    over all ``s != t`` for directed graphs and for ``s < t`` for undirected graphs.

    References
    ----------
    .. [1] M G Everett and S P Borgatti:
       The Centrality of Groups and Classes.
       Journal of Mathematical Sociology. 23(3): 181-201. 1999.
       http://www.analytictech.com/borgatti/group_centrality.htm
    .. [2] Rami Puzis, Yuval Elovici, and Shlomi Dolev:
       "Finding the Most Prominent Group in Complex Networks"
       AI communications 20(4): 287-296, 2007.
       https://www.researchgate.net/profile/Rami_Puzis2/publication/220308855
    .. [3] Sourav Medya et. al.:
       Group Centrality Maximization via Network Design.
       SIAM International Conference on Data Mining, SDM 2018, 126–134.
       https://sites.cs.ucsb.edu/~arlei/pubs/sdm18.pdf
    .. [4] Rami Puzis, Yuval Elovici, and Shlomi Dolev.
       "Fast algorithm for successive computation of group betweenness centrality."
       https://journals.aps.org/pre/pdf/10.1103/PhysRevE.76.056709
networkx.quotient_graph
Python Library Documentation: function quotient_graph in module networkx.algorithms.minors.contraction

quotient_graph(G, partition, edge_relation=None, node_data=None, edge_data=None, weight='weight', relabel=False, create_using=None, *, backend=None, **backend_kwargs)
    Returns the quotient graph of `G` under the specified equivalence
    relation on nodes.

    Parameters
    ----------
    G : NetworkX graph
        The graph for which to return the quotient graph with the
        specified node relation.

    partition : function, or dict or list of lists, tuples or sets
        If a function, this function must represent an equivalence
        relation on the nodes of `G`. It must take two arguments *u*
        and *v* and return True exactly when *u* and *v* are in the
        same equivalence class. The equivalence classes form the nodes
        in the returned graph.

        If a dict of lists/tuples/sets, the keys can be any meaningful
        block labels, but the values must be the block lists/tuples/sets
        (one list/tuple/set per block), and the blocks must form a valid
        partition of the nodes of the graph. That is, each node must be
        in exactly one block of the partition.

        If a list of sets, the list must form a valid partition of
        the nodes of the graph. That is, each node must be in exactly
        one block of the partition.

    edge_relation : Boolean function with two arguments
        This function must represent an edge relation on the *blocks* of
        the `partition` of `G`. It must take two arguments, *B* and *C*,
        each one a set of nodes, and return True exactly when there should be
        an edge joining block *B* to block *C* in the returned graph.

        If `edge_relation` is not specified, it is assumed to be the
        following relation. Block *B* is related to block *C* if and
        only if some node in *B* is adjacent to some node in *C*,
        according to the edge set of `G`.

    node_data : function
        This function takes one argument, *B*, a set of nodes in `G`,
        and must return a dictionary representing the node data
        attributes to set on the node representing *B* in the quotient graph.
        If None, the following node attributes will be set:

        * 'graph', the subgraph of the graph `G` that this block
          represents,
        * 'nnodes', the number of nodes in this block,
        * 'nedges', the number of edges within this block,
        * 'density', the density of the subgraph of `G` that this
          block represents.

    edge_data : function
        This function takes two arguments, *B* and *C*, each one a set
        of nodes, and must return a dictionary representing the edge
        data attributes to set on the edge joining *B* and *C*, should
        there be an edge joining *B* and *C* in the quotient graph (if
        no such edge occurs in the quotient graph as determined by
        `edge_relation`, then the output of this function is ignored).

        If the quotient graph would be a multigraph, this function is
        not applied, since the edge data from each edge in the graph
        `G` appears in the edges of the quotient graph.

    weight : string or None, optional (default="weight")
        The name of an edge attribute that holds the numerical value
        used as a weight. If None then each edge has weight 1.

    relabel : bool
        If True, relabel the nodes of the quotient graph to be
        nonnegative integers. Otherwise, the nodes are identified with
        :class:`frozenset` instances representing the blocks given in
        `partition`.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    NetworkX graph
        The quotient graph of `G` under the equivalence relation
        specified by `partition`. If the partition were given as a
        list of :class:`set` instances and `relabel` is False,
        each node will be a :class:`frozenset` corresponding to the same
        :class:`set`.

    Raises
    ------
    NetworkXException
        If the given partition is not a valid partition of the nodes of
        `G`.

    Examples
    --------
    The quotient graph of the complete bipartite graph under the "same
    neighbors" equivalence relation is `K_2`. Under this relation, two nodes
    are equivalent if they are not adjacent but have the same neighbor set.

    >>> G = nx.complete_bipartite_graph(2, 3)
    >>> same_neighbors = lambda u, v: (u not in G[v] and v not in G[u] and G[u] == G[v])
    >>> Q = nx.quotient_graph(G, same_neighbors)
    >>> K2 = nx.complete_graph(2)
    >>> nx.is_isomorphic(Q, K2)
    True

    The quotient graph of a directed graph under the "same strongly connected
    component" equivalence relation is the condensation of the graph (see
    :func:`condensation`). This example comes from the Wikipedia article
    *`Strongly connected component`_*.

    >>> G = nx.DiGraph()
    >>> edges = [
    ...     "ab",
    ...     "be",
    ...     "bf",
    ...     "bc",
    ...     "cg",
    ...     "cd",
    ...     "dc",
    ...     "dh",
    ...     "ea",
    ...     "ef",
    ...     "fg",
    ...     "gf",
    ...     "hd",
    ...     "hf",
    ... ]
    >>> G.add_edges_from(tuple(x) for x in edges)
    >>> components = list(nx.strongly_connected_components(G))
    >>> sorted(sorted(component) for component in components)
    [['a', 'b', 'e'], ['c', 'd', 'h'], ['f', 'g']]
    >>>
    >>> C = nx.condensation(G, components)
    >>> component_of = C.graph["mapping"]
    >>> same_component = lambda u, v: component_of[u] == component_of[v]
    >>> Q = nx.quotient_graph(G, same_component)
    >>> nx.is_isomorphic(C, Q)
    True

    Node identification can be represented as the quotient of a graph under the
    equivalence relation that places the two nodes in one block and each other
    node in its own singleton block.

    >>> K24 = nx.complete_bipartite_graph(2, 4)
    >>> K34 = nx.complete_bipartite_graph(3, 4)
    >>> C = nx.contracted_nodes(K34, 1, 2)
    >>> nodes = {1, 2}
    >>> is_contracted = lambda u, v: u in nodes and v in nodes
    >>> Q = nx.quotient_graph(K34, is_contracted)
    >>> nx.is_isomorphic(Q, C)
    True
    >>> nx.is_isomorphic(Q, K24)
    True

    The blockmodeling technique described in [1]_ can be implemented as a
    quotient graph.

    >>> G = nx.path_graph(6)
    >>> partition = [{0, 1}, {2, 3}, {4, 5}]
    >>> M = nx.quotient_graph(G, partition, relabel=True)
    >>> list(M.edges())
    [(0, 1), (1, 2)]

    Here is the sample example but using partition as a dict of block sets.

    >>> G = nx.path_graph(6)
    >>> partition = {0: {0, 1}, 2: {2, 3}, 4: {4, 5}}
    >>> M = nx.quotient_graph(G, partition, relabel=True)
    >>> list(M.edges())
    [(0, 1), (1, 2)]

    Partitions can be represented in various ways:

    0. a list/tuple/set of block lists/tuples/sets
    1. a dict with block labels as keys and blocks lists/tuples/sets as values
    2. a dict with block lists/tuples/sets as keys and block labels as values
    3. a function from nodes in the original iterable to block labels
    4. an equivalence relation function on the target iterable

    As `quotient_graph` is designed to accept partitions represented as (0), (1) or
    (4) only, the `equivalence_classes` function can be used to get the partitions
    in the right form, in order to call `quotient_graph`.

    .. _Strongly connected component: https://en.wikipedia.org/wiki/Strongly_connected_component

    References
    ----------
    .. [1] Patrick Doreian, Vladimir Batagelj, and Anuska Ferligoj.
           *Generalized Blockmodeling*.
           Cambridge University Press, 2004.
networkx.ra_index_soundarajan_hopcroft
Python Library Documentation: function ra_index_soundarajan_hopcroft in module networkx.algorithms.link_prediction

ra_index_soundarajan_hopcroft(G, ebunch=None, community='community', *, backend=None, **backend_kwargs)
    Compute the resource allocation index of all node pairs in
    ebunch using community information.

    For two nodes $u$ and $v$, this function computes the resource
    allocation index considering only common neighbors belonging to the
    same community as $u$ and $v$. Mathematically,

    .. math::

        \sum_{w \in \Gamma(u) \cap \Gamma(v)} \frac{f(w)}{|\Gamma(w)|}

    where $f(w)$ equals 1 if $w$ belongs to the same community as $u$
    and $v$ or 0 otherwise and $\Gamma(u)$ denotes the set of
    neighbors of $u$.

    Parameters
    ----------
    G : graph
        A NetworkX undirected graph.

    ebunch : iterable of node pairs, optional (default = None)
        The score will be computed for each pair of nodes given in the
        iterable. The pairs must be given as 2-tuples (u, v) where u
        and v are nodes in the graph. If ebunch is None then all
        nonexistent edges in the graph will be used.
        Default value: None.

    community : string, optional (default = 'community')
        Nodes attribute name containing the community information.
        G[u][community] identifies which community u belongs to. Each
        node belongs to at most one community. Default value: 'community'.

    Returns
    -------
    piter : iterator
        An iterator of 3-tuples in the form (u, v, p) where (u, v) is a
        pair of nodes and p is their score.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a `DiGraph`, a `Multigraph` or a `MultiDiGraph`.

    NetworkXAlgorithmError
        If no community information is available for a node in `ebunch` or in `G` (if `ebunch` is `None`).

    NodeNotFound
        If `ebunch` has a node that is not in `G`.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_edges_from([(0, 1), (0, 2), (1, 3), (2, 3)])
    >>> G.nodes[0]["community"] = 0
    >>> G.nodes[1]["community"] = 0
    >>> G.nodes[2]["community"] = 1
    >>> G.nodes[3]["community"] = 0
    >>> preds = nx.ra_index_soundarajan_hopcroft(G, [(0, 3)])
    >>> for u, v, p in preds:
    ...     print(f"({u}, {v}) -> {p:.8f}")
    (0, 3) -> 0.50000000

    References
    ----------
    .. [1] Sucheta Soundarajan and John Hopcroft.
       Using community information to improve the precision of link
       prediction methods.
       In Proceedings of the 21st international conference companion on
       World Wide Web (WWW '12 Companion). ACM, New York, NY, USA, 607-608.
       http://doi.acm.org/10.1145/2187980.2188150
networkx.radius
Python Library Documentation: function radius in module networkx.algorithms.distance_measures

radius(G, e=None, usebounds=False, weight=None, *, backend=None, **backend_kwargs)
    Returns the radius of the graph G.

    The radius is the minimum eccentricity.

    Parameters
    ----------
    G : NetworkX graph
       A graph

    e : eccentricity dictionary, optional
      A precomputed dictionary of eccentricities.

    weight : string, function, or None
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

        If this is None, every edge has weight/distance/cost 1.

        Weights stored as floating point values can lead to small round-off
        errors in distances. Use integer weights to avoid this.

        Weights should be positive, since they are distances.

    Returns
    -------
    r : integer
       Radius of graph

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
    >>> nx.radius(G)
    2
networkx.random_clustered
Python Library Documentation: module networkx.generators.random_clustered in networkx.generators

NAME
    networkx.generators.random_clustered - Generate graphs with given degree and triangle sequence.

FUNCTIONS
    random_clustered_graph(joint_degree_sequence, create_using=None, seed=None, *, backend=None, **backend_kwargs)
        Generate a random graph with the given joint independent edge degree and
        triangle degree sequence.

        This uses a configuration model-like approach to generate a random graph
        (with parallel edges and self-loops) by randomly assigning edges to match
        the given joint degree sequence.

        The joint degree sequence is a list of pairs of integers of the form
        $[(d_{1,i}, d_{1,t}), \dotsc, (d_{n,i}, d_{n,t})]$. According to this list,
        vertex $u$ is a member of $d_{u,t}$ triangles and has $d_{u, i}$ other
        edges. The number $d_{u,t}$ is the *triangle degree* of $u$ and the number
        $d_{u,i}$ is the *independent edge degree*.

        Parameters
        ----------
        joint_degree_sequence : list of integer pairs
            Each list entry corresponds to the independent edge degree and
            triangle degree of a node.
        create_using : NetworkX graph constructor, optional (default MultiGraph)
           Graph type to create. If graph instance, then cleared before populated.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        G : MultiGraph
            A graph with the specified degree sequence. Nodes are labeled
            starting at 0 with an index corresponding to the position in
            deg_sequence.

        Raises
        ------
        NetworkXError
            If the independent edge degree sequence sum is not even
            or the triangle degree sequence sum is not divisible by 3.

        Notes
        -----
        As described by Miller [1]_ (see also Newman [2]_ for an equivalent
        description).

        A non-graphical degree sequence (not realizable by some simple
        graph) is allowed since this function returns graphs with self
        loops and parallel edges.  An exception is raised if the
        independent degree sequence does not have an even sum or the
        triangle degree sequence sum is not divisible by 3.

        This configuration model-like construction process can lead to
        duplicate edges and loops.  You can remove the self-loops and
        parallel edges (see below) which will likely result in a graph
        that doesn't have the exact degree sequence specified.  This
        "finite-size effect" decreases as the size of the graph increases.

        References
        ----------
        .. [1] Joel C. Miller. "Percolation and epidemics in random clustered
               networks". In: Physical review. E, Statistical, nonlinear, and soft
               matter physics 80 (2 Part 1 August 2009).
        .. [2] M. E. J. Newman. "Random Graphs with Clustering".
               In: Physical Review Letters 103 (5 July 2009)

        Examples
        --------
        >>> deg = [(1, 0), (1, 0), (1, 0), (2, 0), (1, 0), (2, 1), (0, 1), (0, 1)]
        >>> G = nx.random_clustered_graph(deg)

        To remove parallel edges:

        >>> G = nx.Graph(G)

        To remove self loops:

        >>> G.remove_edges_from(nx.selfloop_edges(G))

DATA
    __all__ = ['random_clustered_graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\random_clustered.py

networkx.random_clustered_graph
Python Library Documentation: function random_clustered_graph in module networkx.generators.random_clustered

random_clustered_graph(joint_degree_sequence, create_using=None, seed=None, *, backend=None, **backend_kwargs)
    Generate a random graph with the given joint independent edge degree and
    triangle degree sequence.

    This uses a configuration model-like approach to generate a random graph
    (with parallel edges and self-loops) by randomly assigning edges to match
    the given joint degree sequence.

    The joint degree sequence is a list of pairs of integers of the form
    $[(d_{1,i}, d_{1,t}), \dotsc, (d_{n,i}, d_{n,t})]$. According to this list,
    vertex $u$ is a member of $d_{u,t}$ triangles and has $d_{u, i}$ other
    edges. The number $d_{u,t}$ is the *triangle degree* of $u$ and the number
    $d_{u,i}$ is the *independent edge degree*.

    Parameters
    ----------
    joint_degree_sequence : list of integer pairs
        Each list entry corresponds to the independent edge degree and
        triangle degree of a node.
    create_using : NetworkX graph constructor, optional (default MultiGraph)
       Graph type to create. If graph instance, then cleared before populated.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : MultiGraph
        A graph with the specified degree sequence. Nodes are labeled
        starting at 0 with an index corresponding to the position in
        deg_sequence.

    Raises
    ------
    NetworkXError
        If the independent edge degree sequence sum is not even
        or the triangle degree sequence sum is not divisible by 3.

    Notes
    -----
    As described by Miller [1]_ (see also Newman [2]_ for an equivalent
    description).

    A non-graphical degree sequence (not realizable by some simple
    graph) is allowed since this function returns graphs with self
    loops and parallel edges.  An exception is raised if the
    independent degree sequence does not have an even sum or the
    triangle degree sequence sum is not divisible by 3.

    This configuration model-like construction process can lead to
    duplicate edges and loops.  You can remove the self-loops and
    parallel edges (see below) which will likely result in a graph
    that doesn't have the exact degree sequence specified.  This
    "finite-size effect" decreases as the size of the graph increases.

    References
    ----------
    .. [1] Joel C. Miller. "Percolation and epidemics in random clustered
           networks". In: Physical review. E, Statistical, nonlinear, and soft
           matter physics 80 (2 Part 1 August 2009).
    .. [2] M. E. J. Newman. "Random Graphs with Clustering".
           In: Physical Review Letters 103 (5 July 2009)

    Examples
    --------
    >>> deg = [(1, 0), (1, 0), (1, 0), (2, 0), (1, 0), (2, 1), (0, 1), (0, 1)]
    >>> G = nx.random_clustered_graph(deg)

    To remove parallel edges:

    >>> G = nx.Graph(G)

    To remove self loops:

    >>> G.remove_edges_from(nx.selfloop_edges(G))
networkx.random_cograph
Python Library Documentation: function random_cograph in module networkx.generators.cographs

random_cograph(n, seed=None, *, backend=None, **backend_kwargs)
    Returns a random cograph with $2 ^ n$ nodes.

    A cograph is a graph containing no path on four vertices.
    Cographs or $P_4$-free graphs can be obtained from a single vertex
    by disjoint union and complementation operations.

    This generator starts off from a single vertex and performs disjoint
    union and full join operations on itself.
    The decision on which operation will take place is random.

    Parameters
    ----------
    n : int
        The order of the cograph.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : A random graph containing no path on four vertices.

    See Also
    --------
    full_join
    union

    References
    ----------
    .. [1] D.G. Corneil, H. Lerchs, L.Stewart Burlingham,
       "Complement reducible graphs",
       Discrete Applied Mathematics, Volume 3, Issue 3, 1981, Pages 163-174,
       ISSN 0166-218X.
networkx.random_degree_sequence_graph
Python Library Documentation: function random_degree_sequence_graph in module networkx.generators.degree_seq

random_degree_sequence_graph(sequence, seed=None, tries=10, *, backend=None, **backend_kwargs)
    Returns a simple random graph with the given degree sequence.

    If the maximum degree $d_m$ in the sequence is $O(m^{1/4})$ then the
    algorithm produces almost uniform random graphs in $O(m d_m)$ time
    where $m$ is the number of edges.

    Parameters
    ----------
    sequence :  list of integers
        Sequence of degrees
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    tries : int, optional
        Maximum number of tries to create a graph

    Returns
    -------
    G : Graph
        A graph with the specified degree sequence.
        Nodes are labeled starting at 0 with an index
        corresponding to the position in the sequence.

    Raises
    ------
    NetworkXUnfeasible
        If the degree sequence is not graphical.
    NetworkXError
        If a graph is not produced in specified number of tries

    See Also
    --------
    is_graphical, configuration_model

    Notes
    -----
    The generator algorithm [1]_ is not guaranteed to produce a graph.

    References
    ----------
    .. [1] Moshen Bayati, Jeong Han Kim, and Amin Saberi,
       A sequential algorithm for generating random graphs.
       Algorithmica, Volume 58, Number 4, 860-910,
       DOI: 10.1007/s00453-009-9340-1

    Examples
    --------
    >>> sequence = [1, 2, 2, 3]
    >>> G = nx.random_degree_sequence_graph(sequence, seed=42)
    >>> sorted(d for n, d in G.degree())
    [1, 2, 2, 3]
networkx.random_geometric_graph
Python Library Documentation: function random_geometric_graph in module networkx.generators.geometric

random_geometric_graph(n, radius, dim=2, pos=None, p=2, seed=None, *, pos_name='pos', backend=None, **backend_kwargs)
    Returns a random geometric graph in the unit cube of dimensions `dim`.

    The random geometric graph model places `n` nodes uniformly at
    random in the unit cube. Two nodes are joined by an edge if the
    distance between the nodes is at most `radius`.

    Edges are determined using a KDTree when SciPy is available.
    This reduces the time complexity from $O(n^2)$ to $O(n)$.

    Parameters
    ----------
    n : int or iterable
        Number of nodes or iterable of nodes
    radius: float
        Distance threshold value
    dim : int, optional
        Dimension of graph
    pos : dict, optional
        A dictionary keyed by node with node positions as values.
    p : float, optional
        Which Minkowski distance metric to use.  `p` has to meet the condition
        ``1 <= p <= infinity``.

        If this argument is not specified, the :math:`L^2` metric
        (the Euclidean distance metric), p = 2 is used.
        This should not be confused with the `p` of an Erdős-Rényi random
        graph, which represents probability.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    pos_name : string, default="pos"
        The name of the node attribute which represents the position
        in 2D coordinates of the node in the returned graph.

    Returns
    -------
    Graph
        A random geometric graph, undirected and without self-loops.
        Each node has a node attribute ``'pos'`` that stores the
        position of that node in Euclidean space as provided by the
        ``pos`` keyword argument or, if ``pos`` was not provided, as
        generated by this function.

    Examples
    --------
    Create a random geometric graph on twenty nodes where nodes are joined by
    an edge if their distance is at most 0.1::

    >>> G = nx.random_geometric_graph(20, 0.1)

    Notes
    -----
    This uses a *k*-d tree to build the graph.

    The `pos` keyword argument can be used to specify node positions so you
    can create an arbitrary distribution and domain for positions.

    For example, to use a 2D Gaussian distribution of node positions with mean
    (0, 0) and standard deviation 2::

    >>> import random
    >>> n = 20
    >>> pos = {i: (random.gauss(0, 2), random.gauss(0, 2)) for i in range(n)}
    >>> G = nx.random_geometric_graph(n, 0.2, pos=pos)

    References
    ----------
    .. [1] Penrose, Mathew, *Random Geometric Graphs*,
           Oxford Studies in Probability, 5, 2003.
networkx.random_graphs
Python Library Documentation: module networkx.generators.random_graphs in networkx.generators

NAME
    networkx.generators.random_graphs - Generators for random graphs.

FUNCTIONS
    barabasi_albert_graph(n, m, seed=None, initial_graph=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns a random graph using Barabási–Albert preferential attachment

        A graph of $n$ nodes is grown by attaching new nodes each with $m$
        edges that are preferentially attached to existing nodes with high degree.

        Parameters
        ----------
        n : int
            Number of nodes
        m : int
            Number of edges to attach from a new node to existing nodes
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        initial_graph : Graph or None (default)
            Initial network for Barabási–Albert algorithm.
            It should be a connected graph for most use cases.
            A copy of `initial_graph` is used.
            If None, starts from a star graph on (m+1) nodes.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Returns
        -------
        G : Graph

        Raises
        ------
        NetworkXError
            If `m` does not satisfy ``1 <= m < n``, or
            the initial graph number of nodes m0 does not satisfy ``m <= m0 <= n``.

        References
        ----------
        .. [1] A. L. Barabási and R. Albert "Emergence of scaling in
           random networks", Science 286, pp 509-512, 1999.

    binomial_graph = gnp_random_graph(n, p, seed=None, directed=False, *, create_using=None, backend=None, **backend_kwargs)
        Returns a $G_{n,p}$ random graph, also known as an Erdős-Rényi graph
        or a binomial graph.

        The $G_{n,p}$ model chooses each of the possible edges with probability $p$.

        Parameters
        ----------
        n : int
            The number of nodes.
        p : float
            Probability for edge creation.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        directed : bool, optional (default=False)
            If True, this function returns a directed graph.
        create_using : Graph constructor, optional (default=nx.Graph or nx.DiGraph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph types are not supported and raise a ``NetworkXError``.
            By default NetworkX Graph or DiGraph are used depending on `directed`.

        See Also
        --------
        fast_gnp_random_graph

        Notes
        -----
        This algorithm [2]_ runs in $O(n^2)$ time.  For sparse graphs (that is, for
        small values of $p$), :func:`fast_gnp_random_graph` is a faster algorithm.

        :func:`binomial_graph` and :func:`erdos_renyi_graph` are
        aliases for :func:`gnp_random_graph`.

        >>> nx.binomial_graph is nx.gnp_random_graph
        True
        >>> nx.erdos_renyi_graph is nx.gnp_random_graph
        True

        References
        ----------
        .. [1] P. Erdős and A. Rényi, On Random Graphs, Publ. Math. 6, 290 (1959).
        .. [2] E. N. Gilbert, Random Graphs, Ann. Math. Stat., 30, 1141 (1959).

    connected_watts_strogatz_graph(n, k, p, tries=100, seed=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns a connected Watts–Strogatz small-world graph.

        Attempts to generate a connected graph by repeated generation of
        Watts–Strogatz small-world graphs.  An exception is raised if the maximum
        number of tries is exceeded.

        Parameters
        ----------
        n : int
            The number of nodes
        k : int
            Each node is joined with its `k` nearest neighbors in a ring
            topology.
        p : float
            The probability of rewiring each edge
        tries : int
            Number of attempts to generate a connected graph.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Notes
        -----
        First create a ring over $n$ nodes [1]_.  Then each node in the ring is joined
        to its $k$ nearest neighbors (or $k - 1$ neighbors if $k$ is odd).
        Then shortcuts are created by replacing some edges as follows: for each
        edge $(u, v)$ in the underlying "$n$-ring with $k$ nearest neighbors"
        with probability $p$ replace it with a new edge $(u, w)$ with uniformly
        random choice of existing node $w$.
        The entire process is repeated until a connected graph results.

        See Also
        --------
        newman_watts_strogatz_graph
        watts_strogatz_graph

        References
        ----------
        .. [1] Duncan J. Watts and Steven H. Strogatz,
           Collective dynamics of small-world networks,
           Nature, 393, pp. 440--442, 1998.

    dense_gnm_random_graph(n, m, seed=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns a $G_{n,m}$ random graph.

        In the $G_{n,m}$ model, a graph is chosen uniformly at random from the set
        of all graphs with $n$ nodes and $m$ edges.

        This algorithm should be faster than :func:`gnm_random_graph` for dense
        graphs.

        Parameters
        ----------
        n : int
            The number of nodes.
        m : int
            The number of edges.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        See Also
        --------
        gnm_random_graph

        Notes
        -----
        Algorithm by Keith M. Briggs Mar 31, 2006.
        Inspired by Knuth's Algorithm S (Selection sampling technique),
        in section 3.4.2 of [1]_.

        References
        ----------
        .. [1] Donald E. Knuth, The Art of Computer Programming,
            Volume 2/Seminumerical algorithms, Third Edition, Addison-Wesley, 1997.

    dual_barabasi_albert_graph(n, m1, m2, p, seed=None, initial_graph=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns a random graph using dual Barabási–Albert preferential attachment

        A graph of $n$ nodes is grown by attaching new nodes each with either $m_1$
        edges (with probability $p$) or $m_2$ edges (with probability $1-p$) that
        are preferentially attached to existing nodes with high degree.

        Parameters
        ----------
        n : int
            Number of nodes
        m1 : int
            Number of edges to link each new node to existing nodes with probability $p$
        m2 : int
            Number of edges to link each new node to existing nodes with probability $1-p$
        p : float
            The probability of attaching $m_1$ edges (as opposed to $m_2$ edges)
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        initial_graph : Graph or None (default)
            Initial network for Barabási–Albert algorithm.
            A copy of `initial_graph` is used.
            It should be connected for most use cases.
            If None, starts from an star graph on max(m1, m2) + 1 nodes.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Returns
        -------
        G : Graph

        Raises
        ------
        NetworkXError
            If `m1` and `m2` do not satisfy ``1 <= m1,m2 < n``, or
            `p` does not satisfy ``0 <= p <= 1``, or
            the initial graph number of nodes m0 does not satisfy m1, m2 <= m0 <= n.

        References
        ----------
        .. [1] N. Moshiri "The dual-Barabasi-Albert model", arXiv:1810.10538.

    erdos_renyi_graph = gnp_random_graph(n, p, seed=None, directed=False, *, create_using=None, backend=None, **backend_kwargs)
        Returns a $G_{n,p}$ random graph, also known as an Erdős-Rényi graph
        or a binomial graph.

        The $G_{n,p}$ model chooses each of the possible edges with probability $p$.

        Parameters
        ----------
        n : int
            The number of nodes.
        p : float
            Probability for edge creation.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        directed : bool, optional (default=False)
            If True, this function returns a directed graph.
        create_using : Graph constructor, optional (default=nx.Graph or nx.DiGraph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph types are not supported and raise a ``NetworkXError``.
            By default NetworkX Graph or DiGraph are used depending on `directed`.

        See Also
        --------
        fast_gnp_random_graph

        Notes
        -----
        This algorithm [2]_ runs in $O(n^2)$ time.  For sparse graphs (that is, for
        small values of $p$), :func:`fast_gnp_random_graph` is a faster algorithm.

        :func:`binomial_graph` and :func:`erdos_renyi_graph` are
        aliases for :func:`gnp_random_graph`.

        >>> nx.binomial_graph is nx.gnp_random_graph
        True
        >>> nx.erdos_renyi_graph is nx.gnp_random_graph
        True

        References
        ----------
        .. [1] P. Erdős and A. Rényi, On Random Graphs, Publ. Math. 6, 290 (1959).
        .. [2] E. N. Gilbert, Random Graphs, Ann. Math. Stat., 30, 1141 (1959).

    extended_barabasi_albert_graph(n, m, p, q, seed=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns an extended Barabási–Albert model graph.

        An extended Barabási–Albert model graph is a random graph constructed
        using preferential attachment. The extended model allows new edges,
        rewired edges or new nodes. Based on the probabilities $p$ and $q$
        with $p + q < 1$, the growing behavior of the graph is determined as:

        1) With $p$ probability, $m$ new edges are added to the graph,
        starting from randomly chosen existing nodes and attached preferentially at the
        other end.

        2) With $q$ probability, $m$ existing edges are rewired
        by randomly choosing an edge and rewiring one end to a preferentially chosen node.

        3) With $(1 - p - q)$ probability, $m$ new nodes are added to the graph
        with edges attached preferentially.

        When $p = q = 0$, the model behaves just like the Barabási–Alber model.

        Parameters
        ----------
        n : int
            Number of nodes
        m : int
            Number of edges with which a new node attaches to existing nodes
        p : float
            Probability value for adding an edge between existing nodes. p + q < 1
        q : float
            Probability value of rewiring of existing edges. p + q < 1
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Returns
        -------
        G : Graph

        Raises
        ------
        NetworkXError
            If `m` does not satisfy ``1 <= m < n`` or ``1 >= p + q``

        References
        ----------
        .. [1] Albert, R., & Barabási, A. L. (2000)
           Topology of evolving networks: local events and universality
           Physical review letters, 85(24), 5234.

    fast_gnp_random_graph(n, p, seed=None, directed=False, *, create_using=None, backend=None, **backend_kwargs)
        Returns a $G_{n,p}$ random graph, also known as an Erdős-Rényi graph or
        a binomial graph.

        Parameters
        ----------
        n : int
            The number of nodes.
        p : float
            Probability for edge creation.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        directed : bool, optional (default=False)
            If True, this function returns a directed graph.
        create_using : Graph constructor, optional (default=nx.Graph or nx.DiGraph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph types are not supported and raise a ``NetworkXError``.
            By default NetworkX Graph or DiGraph are used depending on `directed`.

        Notes
        -----
        The $G_{n,p}$ graph algorithm chooses each of the $[n (n - 1)] / 2$
        (undirected) or $n (n - 1)$ (directed) possible edges with probability $p$.

        This algorithm [1]_ runs in $O(n + m)$ time, where `m` is the expected number of
        edges, which equals $p n (n - 1) / 2$. This should be faster than
        :func:`gnp_random_graph` when $p$ is small and the expected number of edges
        is small (that is, the graph is sparse).

        See Also
        --------
        gnp_random_graph

        References
        ----------
        .. [1] Vladimir Batagelj and Ulrik Brandes,
           "Efficient generation of large random networks",
           Phys. Rev. E, 71, 036113, 2005.

    gnm_random_graph(n, m, seed=None, directed=False, *, create_using=None, backend=None, **backend_kwargs)
        Returns a $G_{n,m}$ random graph.

        In the $G_{n,m}$ model, a graph is chosen uniformly at random from the set
        of all graphs with $n$ nodes and $m$ edges.

        This algorithm should be faster than :func:`dense_gnm_random_graph` for
        sparse graphs.

        Parameters
        ----------
        n : int
            The number of nodes.
        m : int
            The number of edges.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        directed : bool, optional (default=False)
            If True return a directed graph
        create_using : Graph constructor, optional (default=nx.Graph or nx.DiGraph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph types are not supported and raise a ``NetworkXError``.
            By default NetworkX Graph or DiGraph are used depending on `directed`.

        See also
        --------
        dense_gnm_random_graph

    gnp_random_graph(n, p, seed=None, directed=False, *, create_using=None, backend=None, **backend_kwargs)
        Returns a $G_{n,p}$ random graph, also known as an Erdős-Rényi graph
        or a binomial graph.

        The $G_{n,p}$ model chooses each of the possible edges with probability $p$.

        Parameters
        ----------
        n : int
            The number of nodes.
        p : float
            Probability for edge creation.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        directed : bool, optional (default=False)
            If True, this function returns a directed graph.
        create_using : Graph constructor, optional (default=nx.Graph or nx.DiGraph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph types are not supported and raise a ``NetworkXError``.
            By default NetworkX Graph or DiGraph are used depending on `directed`.

        See Also
        --------
        fast_gnp_random_graph

        Notes
        -----
        This algorithm [2]_ runs in $O(n^2)$ time.  For sparse graphs (that is, for
        small values of $p$), :func:`fast_gnp_random_graph` is a faster algorithm.

        :func:`binomial_graph` and :func:`erdos_renyi_graph` are
        aliases for :func:`gnp_random_graph`.

        >>> nx.binomial_graph is nx.gnp_random_graph
        True
        >>> nx.erdos_renyi_graph is nx.gnp_random_graph
        True

        References
        ----------
        .. [1] P. Erdős and A. Rényi, On Random Graphs, Publ. Math. 6, 290 (1959).
        .. [2] E. N. Gilbert, Random Graphs, Ann. Math. Stat., 30, 1141 (1959).

    newman_watts_strogatz_graph(n, k, p, seed=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns a Newman–Watts–Strogatz small-world graph.

        Parameters
        ----------
        n : int
            The number of nodes.
        k : int
            Each node is joined with its `k` nearest neighbors in a ring
            topology.
        p : float
            The probability of adding a new edge for each edge.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Notes
        -----
        First create a ring over $n$ nodes [1]_.  Then each node in the ring is
        connected with its $k$ nearest neighbors (or $k - 1$ neighbors if $k$
        is odd).  Then shortcuts are created by adding new edges as follows: for
        each edge $(u, v)$ in the underlying "$n$-ring with $k$ nearest
        neighbors" with probability $p$ add a new edge $(u, w)$ with
        randomly-chosen existing node $w$.  In contrast with
        :func:`watts_strogatz_graph`, no edges are removed.

        See Also
        --------
        watts_strogatz_graph

        References
        ----------
        .. [1] M. E. J. Newman and D. J. Watts,
           Renormalization group analysis of the small-world network model,
           Physics Letters A, 263, 341, 1999.
           https://doi.org/10.1016/S0375-9601(99)00757-4

    powerlaw_cluster_graph(n, m, p, seed=None, *, create_using=None, backend=None, **backend_kwargs)
        Holme and Kim algorithm for growing graphs with powerlaw
        degree distribution and approximate average clustering.

        Parameters
        ----------
        n : int
            the number of nodes
        m : int
            the number of random edges to add for each new node
        p : float,
            Probability of adding a triangle after adding a random edge
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Notes
        -----
        The average clustering has a hard time getting above a certain
        cutoff that depends on `m`.  This cutoff is often quite low.  The
        transitivity (fraction of triangles to possible triangles) seems to
        decrease with network size.

        It is essentially the Barabási–Albert (BA) growth model with an
        extra step that each random edge is followed by a chance of
        making an edge to one of its neighbors too (and thus a triangle).

        This algorithm improves on BA in the sense that it enables a
        higher average clustering to be attained if desired.

        It seems possible to have a disconnected graph with this algorithm
        since the initial `m` nodes may not be all linked to a new node
        on the first iteration like the BA model.

        Raises
        ------
        NetworkXError
            If `m` does not satisfy ``1 <= m <= n`` or `p` does not
            satisfy ``0 <= p <= 1``.

        References
        ----------
        .. [1] P. Holme and B. J. Kim,
           "Growing scale-free networks with tunable clustering",
           Phys. Rev. E, 65, 026107, 2002.

    random_kernel_graph(n, kernel_integral, kernel_root=None, seed=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns an random graph based on the specified kernel.

        The algorithm chooses each of the $[n(n-1)]/2$ possible edges with
        probability specified by a kernel $\kappa(x,y)$ [1]_.  The kernel
        $\kappa(x,y)$ must be a symmetric (in $x,y$), non-negative,
        bounded function.

        Parameters
        ----------
        n : int
            The number of nodes
        kernel_integral : function
            Function that returns the definite integral of the kernel $\kappa(x,y)$,
            $F(y,a,b) := \int_a^b \kappa(x,y)dx$
        kernel_root: function (optional)
            Function that returns the root $b$ of the equation $F(y,a,b) = r$.
            If None, the root is found using :func:`scipy.optimize.brentq`
            (this requires SciPy).
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Notes
        -----
        The kernel is specified through its definite integral which must be
        provided as one of the arguments. If the integral and root of the
        kernel integral can be found in $O(1)$ time then this algorithm runs in
        time $O(n+m)$ where m is the expected number of edges [2]_.

        The nodes are set to integers from $0$ to $n-1$.

        Examples
        --------
        Generate an Erdős–Rényi random graph $G(n,c/n)$, with kernel
        $\kappa(x,y)=c$ where $c$ is the mean expected degree.

        >>> def integral(u, w, z):
        ...     return c * (z - w)
        >>> def root(u, w, r):
        ...     return r / c + w
        >>> c = 1
        >>> graph = nx.random_kernel_graph(1000, integral, root)

        See Also
        --------
        gnp_random_graph
        expected_degree_graph

        References
        ----------
        .. [1] Bollobás, Béla,  Janson, S. and Riordan, O.
           "The phase transition in inhomogeneous random graphs",
           *Random Structures Algorithms*, 31, 3--122, 2007.

        .. [2] Hagberg A, Lemons N (2015),
           "Fast Generation of Sparse Random Kernel Graphs".
           PLoS ONE 10(9): e0135177, 2015. doi:10.1371/journal.pone.0135177

    random_lobster(n, p1, p2, seed=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns a random lobster graph.

        A lobster is a tree that reduces to a caterpillar when pruning all
        leaf nodes. A caterpillar is a tree that reduces to a path graph
        when pruning all leaf nodes; setting `p2` to zero produces a caterpillar.

        This implementation iterates on the probabilities `p1` and `p2` to add
        edges at levels 1 and 2, respectively. Graphs are therefore constructed
        iteratively with uniform randomness at each level rather than being selected
        uniformly at random from the set of all possible lobsters.

        Parameters
        ----------
        n : int
            The expected number of nodes in the backbone
        p1 : float
            Probability of adding an edge to the backbone
        p2 : float
            Probability of adding an edge one level beyond backbone
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        create_using : Graph constructor, optional (default=nx.Grap)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Raises
        ------
        NetworkXError
            If `p1` or `p2` parameters are >= 1 because the while loops would never finish.

    random_powerlaw_tree(n, gamma=3, seed=None, tries=100, *, create_using=None, backend=None, **backend_kwargs)
        Returns a tree with a power law degree distribution.

        Parameters
        ----------
        n : int
            The number of nodes.
        gamma : float
            Exponent of the power law.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        tries : int
            Number of attempts to adjust the sequence to make it a tree.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Raises
        ------
        NetworkXError
            If no valid sequence is found within the maximum number of
            attempts.

        Notes
        -----
        A trial power law degree sequence is chosen and then elements are
        swapped with new elements from a powerlaw distribution until the
        sequence makes a tree (by checking, for example, that the number of
        edges is one smaller than the number of nodes).

    random_powerlaw_tree_sequence(n, gamma=3, seed=None, tries=100, *, backend=None, **backend_kwargs)
        Returns a degree sequence for a tree with a power law distribution.

        Parameters
        ----------
        n : int,
            The number of nodes.
        gamma : float
            Exponent of the power law.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        tries : int
            Number of attempts to adjust the sequence to make it a tree.

        Raises
        ------
        NetworkXError
            If no valid sequence is found within the maximum number of
            attempts.

        Notes
        -----
        A trial power law degree sequence is chosen and then elements are
        swapped with new elements from a power law distribution until
        the sequence makes a tree (by checking, for example, that the number of
        edges is one smaller than the number of nodes).

    random_regular_graph(d, n, seed=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns a random $d$-regular graph on $n$ nodes.

        A regular graph is a graph where each node has the same number of neighbors.

        The resulting graph has no self-loops or parallel edges.

        Parameters
        ----------
        d : int
          The degree of each node.
        n : integer
          The number of nodes. The value of $n \times d$ must be even.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Notes
        -----
        The nodes are numbered from $0$ to $n - 1$.

        Kim and Vu's paper [2]_ shows that this algorithm samples in an
        asymptotically uniform way from the space of random graphs when
        $d = O(n^{1 / 3 - \epsilon})$.

        Raises
        ------

        NetworkXError
            If $n \times d$ is odd or $d$ is greater than or equal to $n$.

        References
        ----------
        .. [1] A. Steger and N. Wormald,
           Generating random regular graphs quickly,
           Probability and Computing 8 (1999), 377-396, 1999.
           https://doi.org/10.1017/S0963548399003867

        .. [2] Jeong Han Kim and Van H. Vu,
           Generating random regular graphs,
           Proceedings of the thirty-fifth ACM symposium on Theory of computing,
           San Diego, CA, USA, pp 213--222, 2003.
           http://portal.acm.org/citation.cfm?id=780542.780576

    random_shell_graph(constructor, seed=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns a random shell graph for the constructor given.

        Parameters
        ----------
        constructor : list of three-tuples
            Represents the parameters for a shell, starting at the center
            shell.  Each element of the list must be of the form `(n, m,
            d)`, where `n` is the number of nodes in the shell, `m` is
            the number of edges in the shell, and `d` is the ratio of
            inter-shell (next) edges to intra-shell edges. If `d` is zero,
            there will be no intra-shell edges, and if `d` is one there
            will be all possible intra-shell edges.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. Graph instances are not supported.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        Examples
        --------
        >>> constructor = [(10, 20, 0.8), (20, 40, 0.8)]
        >>> G = nx.random_shell_graph(constructor)

    watts_strogatz_graph(n, k, p, seed=None, *, create_using=None, backend=None, **backend_kwargs)
        Returns a Watts–Strogatz small-world graph.

        Parameters
        ----------
        n : int
            The number of nodes
        k : int
            Each node is joined with its `k` nearest neighbors in a ring
            topology.
        p : float
            The probability of rewiring each edge
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.
        create_using : Graph constructor, optional (default=nx.Graph)
            Graph type to create. If graph instance, then cleared before populated.
            Multigraph and directed types are not supported and raise a ``NetworkXError``.

        See Also
        --------
        newman_watts_strogatz_graph
        connected_watts_strogatz_graph

        Notes
        -----
        First create a ring over $n$ nodes [1]_.  Then each node in the ring is joined
        to its $k$ nearest neighbors (or $k - 1$ neighbors if $k$ is odd).
        Then shortcuts are created by replacing some edges as follows: for each
        edge $(u, v)$ in the underlying "$n$-ring with $k$ nearest neighbors"
        with probability $p$ replace it with a new edge $(u, w)$ with uniformly
        random choice of existing node $w$.

        In contrast with :func:`newman_watts_strogatz_graph`, the random rewiring
        does not increase the number of edges. The rewired graph is not guaranteed
        to be connected as in :func:`connected_watts_strogatz_graph`.

        References
        ----------
        .. [1] Duncan J. Watts and Steven H. Strogatz,
           Collective dynamics of small-world networks,
           Nature, 393, pp. 440--442, 1998.

DATA
    __all__ = ['fast_gnp_random_graph', 'gnp_random_graph', 'dense_gnm_ran...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\random_graphs.py

networkx.random_internet_as_graph
Python Library Documentation: function random_internet_as_graph in module networkx.generators.internet_as_graphs

random_internet_as_graph(n, seed=None, *, backend=None, **backend_kwargs)
    Generates a random undirected graph resembling the Internet AS network

    Parameters
    ----------
    n: integer in [1000, 10000]
        Number of graph nodes
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G: Networkx Graph object
        A randomly generated undirected graph

    Notes
    -----
    This algorithm returns an undirected graph resembling the Internet
    Autonomous System (AS) network, it uses the approach by Elmokashfi et al.
    [1]_ and it grants the properties described in the related paper [1]_.

    Each node models an autonomous system, with an attribute 'type' specifying
    its kind; tier-1 (T), mid-level (M), customer (C) or content-provider (CP).
    Each edge models an ADV communication link (hence, bidirectional) with
    attributes:

      - type: transit|peer, the kind of commercial agreement between nodes;
      - customer: <node id>, the identifier of the node acting as customer
        ('none' if type is peer).

    References
    ----------
    .. [1] A. Elmokashfi, A. Kvalbein and C. Dovrolis, "On the Scalability of
       BGP: The Role of Topology Growth," in IEEE Journal on Selected Areas
       in Communications, vol. 28, no. 8, pp. 1250-1261, October 2010.
networkx.random_k_out_graph
Python Library Documentation: function random_k_out_graph in module networkx.generators.directed

random_k_out_graph(n, k, alpha, self_loops=True, seed=None, *, backend=None, **backend_kwargs)
    Returns a random `k`-out graph with preferential attachment.

    A random `k`-out graph with preferential attachment is a
    multidigraph generated by the following algorithm.

    1. Begin with an empty digraph, and initially set each node to have
       weight `alpha`.
    2. Choose a node `u` with out-degree less than `k` uniformly at
       random.
    3. Choose a node `v` from with probability proportional to its
       weight.
    4. Add a directed edge from `u` to `v`, and increase the weight
       of `v` by one.
    5. If each node has out-degree `k`, halt, otherwise repeat from
       step 2.

    For more information on this model of random graph, see [1].

    Parameters
    ----------
    n : int
        The number of nodes in the returned graph.

    k : int
        The out-degree of each node in the returned graph.

    alpha : float
        A positive :class:`float` representing the initial weight of
        each vertex. A higher number means that in step 3 above, nodes
        will be chosen more like a true uniformly random sample, and a
        lower number means that nodes are more likely to be chosen as
        their in-degree increases. If this parameter is not positive, a
        :exc:`ValueError` is raised.

    self_loops : bool
        If True, self-loops are allowed when generating the graph.

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    :class:`~networkx.classes.MultiDiGraph`
        A `k`-out-regular multidigraph generated according to the above
        algorithm.

    Raises
    ------
    ValueError
        If `alpha` is not positive.

    Notes
    -----
    The returned multidigraph may not be strongly connected, or even
    weakly connected.

    References
    ----------
    [1]: Peterson, Nicholas R., and Boris Pittel.
         "Distance between two random `k`-out digraphs, with and without
         preferential attachment."
         arXiv preprint arXiv:1311.5961 (2013).
         <https://arxiv.org/abs/1311.5961>
networkx.random_kernel_graph
Python Library Documentation: function random_kernel_graph in module networkx.generators.random_graphs

random_kernel_graph(n, kernel_integral, kernel_root=None, seed=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns an random graph based on the specified kernel.

    The algorithm chooses each of the $[n(n-1)]/2$ possible edges with
    probability specified by a kernel $\kappa(x,y)$ [1]_.  The kernel
    $\kappa(x,y)$ must be a symmetric (in $x,y$), non-negative,
    bounded function.

    Parameters
    ----------
    n : int
        The number of nodes
    kernel_integral : function
        Function that returns the definite integral of the kernel $\kappa(x,y)$,
        $F(y,a,b) := \int_a^b \kappa(x,y)dx$
    kernel_root: function (optional)
        Function that returns the root $b$ of the equation $F(y,a,b) = r$.
        If None, the root is found using :func:`scipy.optimize.brentq`
        (this requires SciPy).
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Notes
    -----
    The kernel is specified through its definite integral which must be
    provided as one of the arguments. If the integral and root of the
    kernel integral can be found in $O(1)$ time then this algorithm runs in
    time $O(n+m)$ where m is the expected number of edges [2]_.

    The nodes are set to integers from $0$ to $n-1$.

    Examples
    --------
    Generate an Erdős–Rényi random graph $G(n,c/n)$, with kernel
    $\kappa(x,y)=c$ where $c$ is the mean expected degree.

    >>> def integral(u, w, z):
    ...     return c * (z - w)
    >>> def root(u, w, r):
    ...     return r / c + w
    >>> c = 1
    >>> graph = nx.random_kernel_graph(1000, integral, root)

    See Also
    --------
    gnp_random_graph
    expected_degree_graph

    References
    ----------
    .. [1] Bollobás, Béla,  Janson, S. and Riordan, O.
       "The phase transition in inhomogeneous random graphs",
       *Random Structures Algorithms*, 31, 3--122, 2007.

    .. [2] Hagberg A, Lemons N (2015),
       "Fast Generation of Sparse Random Kernel Graphs".
       PLoS ONE 10(9): e0135177, 2015. doi:10.1371/journal.pone.0135177
networkx.random_labeled_rooted_forest
Python Library Documentation: function random_labeled_rooted_forest in module networkx.generators.trees

random_labeled_rooted_forest(n, *, seed=None, backend=None, **backend_kwargs)
    Returns a labeled rooted forest with `n` nodes.

    The returned forest is chosen uniformly at random using a
    generalization of Prüfer sequences [1]_ in the form described in [2]_.

    Parameters
    ----------
    n : int
        The number of nodes.
    seed : random_state
       See :ref:`Randomness<randomness>`.

    Returns
    -------
    :class:`networkx.Graph`
        A `networkx.Graph` with integer nodes 0 <= node <= `n` - 1.
        The "roots" graph attribute is a set of integers containing the roots.

    References
    ----------
    .. [1] Knuth, Donald E. "Another Enumeration of Trees."
        Canadian Journal of Mathematics, 20 (1968): 1077-1086.
        https://doi.org/10.4153/CJM-1968-104-8
    .. [2] Rubey, Martin. "Counting Spanning Trees". Diplomarbeit
        zur Erlangung des akademischen Grades Magister der
        Naturwissenschaften an der Formal- und Naturwissenschaftlichen
        Fakultät der Universität Wien. Wien, May 2000.
networkx.random_labeled_rooted_tree
Python Library Documentation: function random_labeled_rooted_tree in module networkx.generators.trees

random_labeled_rooted_tree(n, *, seed=None, backend=None, **backend_kwargs)
    Returns a labeled rooted tree with `n` nodes.

    The returned tree is chosen uniformly at random from all labeled rooted trees.

    Parameters
    ----------
    n : int
        The number of nodes
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    :class:`networkx.Graph`
        A `networkx.Graph` with integer nodes 0 <= node <= `n` - 1.
        The root of the tree is selected uniformly from the nodes.
        The "root" graph attribute identifies the root of the tree.

    Notes
    -----
    This function returns the result of :func:`random_labeled_tree`
    with a randomly selected root.

    Raises
    ------
    NetworkXPointlessConcept
        If `n` is zero (because the null graph is not a tree).
networkx.random_labeled_tree
Python Library Documentation: function random_labeled_tree in module networkx.generators.trees

random_labeled_tree(n, *, seed=None, backend=None, **backend_kwargs)
    Returns a labeled tree on `n` nodes chosen uniformly at random.

    Generating uniformly distributed random Prüfer sequences and
    converting them into the corresponding trees is a straightforward
    method of generating uniformly distributed random labeled trees.
    This function implements this method.

    Parameters
    ----------
    n : int
        The number of nodes, greater than zero.
    seed : random_state
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`

    Returns
    -------
     :class:`networkx.Graph`
        A `networkx.Graph` with nodes in the set {0, …, *n* - 1}.

    Raises
    ------
    NetworkXPointlessConcept
        If `n` is zero (because the null graph is not a tree).

    Examples
    --------
    >>> G = nx.random_labeled_tree(5, seed=42)
    >>> nx.is_tree(G)
    True
    >>> G.edges
    EdgeView([(0, 1), (0, 3), (0, 2), (2, 4)])

    A tree with *arbitrarily directed* edges can be created by assigning
    generated edges to a ``DiGraph``:

    >>> DG = nx.DiGraph()
    >>> DG.add_edges_from(G.edges)
    >>> nx.is_tree(DG)
    True
    >>> DG.edges
    OutEdgeView([(0, 1), (0, 3), (0, 2), (2, 4)])
networkx.random_layout
Python Library Documentation: function random_layout in module networkx.drawing.layout

random_layout(G, center=None, dim=2, seed=None)
    Position nodes uniformly at random in the unit square.

    For every node, a position is generated by choosing each of dim
    coordinates uniformly at random on the interval [0.0, 1.0).

    NumPy (http://scipy.org) is required for this function.

    Parameters
    ----------
    G : NetworkX graph or list of nodes
        A position will be assigned to every node in G.

    center : array-like or None
        Coordinate pair around which to center the layout.

    dim : int
        Dimension of layout.

    seed : int, RandomState instance or None  optional (default=None)
        Set the random state for deterministic node layouts.
        If int, `seed` is the seed used by the random number generator,
        if numpy.random.RandomState instance, `seed` is the random
        number generator,
        if None, the random number generator is the RandomState instance used
        by numpy.random.

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node

    Examples
    --------
    >>> G = nx.lollipop_graph(4, 3)
    >>> pos = nx.random_layout(G)
networkx.random_lobster
Python Library Documentation: function random_lobster in module networkx.generators.random_graphs

random_lobster(n, p1, p2, seed=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns a random lobster graph.

    A lobster is a tree that reduces to a caterpillar when pruning all
    leaf nodes. A caterpillar is a tree that reduces to a path graph
    when pruning all leaf nodes; setting `p2` to zero produces a caterpillar.

    This implementation iterates on the probabilities `p1` and `p2` to add
    edges at levels 1 and 2, respectively. Graphs are therefore constructed
    iteratively with uniform randomness at each level rather than being selected
    uniformly at random from the set of all possible lobsters.

    Parameters
    ----------
    n : int
        The expected number of nodes in the backbone
    p1 : float
        Probability of adding an edge to the backbone
    p2 : float
        Probability of adding an edge one level beyond backbone
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    create_using : Graph constructor, optional (default=nx.Grap)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Raises
    ------
    NetworkXError
        If `p1` or `p2` parameters are >= 1 because the while loops would never finish.
networkx.random_partition_graph
Python Library Documentation: function random_partition_graph in module networkx.generators.community

random_partition_graph(sizes, p_in, p_out, seed=None, directed=False, *, backend=None, **backend_kwargs)
    Returns the random partition graph with a partition of sizes.

    A partition graph is a graph of communities with sizes defined by
    s in sizes. Nodes in the same group are connected with probability
    p_in and nodes of different groups are connected with probability
    p_out.

    Parameters
    ----------
    sizes : list of ints
      Sizes of groups
    p_in : float
      probability of edges with in groups
    p_out : float
      probability of edges between groups
    directed : boolean optional, default=False
      Whether to create a directed graph
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : NetworkX Graph or DiGraph
      random partition graph of size sum(gs)

    Raises
    ------
    NetworkXError
      If p_in or p_out is not in [0,1]

    Examples
    --------
    >>> G = nx.random_partition_graph([10, 10, 10], 0.25, 0.01)
    >>> len(G)
    30
    >>> partition = G.graph["partition"]
    >>> len(partition)
    3

    Notes
    -----
    This is a generalization of the planted-l-partition described in
    [1]_.  It allows for the creation of groups of any size.

    The partition is store as a graph attribute 'partition'.

    References
    ----------
    .. [1] Santo Fortunato 'Community Detection in Graphs' Physical Reports
       Volume 486, Issue 3-5 p. 75-174. https://arxiv.org/abs/0906.0612
networkx.random_powerlaw_tree
Python Library Documentation: function random_powerlaw_tree in module networkx.generators.random_graphs

random_powerlaw_tree(n, gamma=3, seed=None, tries=100, *, create_using=None, backend=None, **backend_kwargs)
    Returns a tree with a power law degree distribution.

    Parameters
    ----------
    n : int
        The number of nodes.
    gamma : float
        Exponent of the power law.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    tries : int
        Number of attempts to adjust the sequence to make it a tree.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Raises
    ------
    NetworkXError
        If no valid sequence is found within the maximum number of
        attempts.

    Notes
    -----
    A trial power law degree sequence is chosen and then elements are
    swapped with new elements from a powerlaw distribution until the
    sequence makes a tree (by checking, for example, that the number of
    edges is one smaller than the number of nodes).
networkx.random_powerlaw_tree_sequence
Python Library Documentation: function random_powerlaw_tree_sequence in module networkx.generators.random_graphs

random_powerlaw_tree_sequence(n, gamma=3, seed=None, tries=100, *, backend=None, **backend_kwargs)
    Returns a degree sequence for a tree with a power law distribution.

    Parameters
    ----------
    n : int,
        The number of nodes.
    gamma : float
        Exponent of the power law.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    tries : int
        Number of attempts to adjust the sequence to make it a tree.

    Raises
    ------
    NetworkXError
        If no valid sequence is found within the maximum number of
        attempts.

    Notes
    -----
    A trial power law degree sequence is chosen and then elements are
    swapped with new elements from a power law distribution until
    the sequence makes a tree (by checking, for example, that the number of
    edges is one smaller than the number of nodes).
networkx.random_reference
Python Library Documentation: function random_reference in module networkx.algorithms.smallworld

random_reference(G, niter=1, connectivity=True, seed=None, *, backend=None, **backend_kwargs)
    Compute a random graph by swapping edges of a given graph.

    Parameters
    ----------
    G : graph
        An undirected graph with 4 or more nodes.

    niter : integer (optional, default=1)
        An edge is rewired approximately `niter` times.

    connectivity : boolean (optional, default=True)
        When True, ensure connectivity for the randomized graph.

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : graph
        The randomized graph.

    Raises
    ------
    NetworkXError
        If there are fewer than 4 nodes or 2 edges in `G`

    Notes
    -----
    The implementation is adapted from the algorithm by Maslov and Sneppen
    (2002) [1]_.

    References
    ----------
    .. [1] Maslov, Sergei, and Kim Sneppen.
           "Specificity and stability in topology of protein networks."
           Science 296.5569 (2002): 910-913.
networkx.random_regular_expander_graph
Python Library Documentation: function random_regular_expander_graph in module networkx.generators.expanders

random_regular_expander_graph(n, d, *, epsilon=0, create_using=None, max_tries=100, seed=None, backend=None, **backend_kwargs)
    Returns a random regular expander graph on $n$ nodes with degree $d$.

    An expander graph is a sparse graph with strong connectivity properties. [1]_

    More precisely the returned graph is a $(n, d, \lambda)$-expander with
    $\lambda = 2 \sqrt{d - 1} + \epsilon$, close to the Alon-Boppana bound. [2]_

    In the case where $\epsilon = 0$ it returns a Ramanujan graph.
    A Ramanujan graph has spectral gap almost as large as possible,
    which makes them excellent expanders. [3]_

    Parameters
    ----------
    n : int
      The number of nodes.
    d : int
      The degree of each node.
    epsilon : int, float, default=0
    max_tries : int, (default: 100)
      The number of allowed loops, also used in the maybe_regular_expander utility
    seed : (default: None)
      Seed used to set random number generation state. See :ref`Randomness<randomness>`.

    Raises
    ------
    NetworkXError
        If max_tries is reached

    Examples
    --------
    >>> G = nx.random_regular_expander_graph(20, 4)
    >>> nx.is_regular_expander(G)
    True

    Notes
    -----
    This loops over `maybe_regular_expander` and can be slow when
    $n$ is too big or $\epsilon$ too small.

    See Also
    --------
    maybe_regular_expander
    is_regular_expander

    References
    ----------
    .. [1] Expander graph, https://en.wikipedia.org/wiki/Expander_graph
    .. [2] Alon-Boppana bound, https://en.wikipedia.org/wiki/Alon%E2%80%93Boppana_bound
    .. [3] Ramanujan graphs, https://en.wikipedia.org/wiki/Ramanujan_graph
networkx.random_regular_graph
Python Library Documentation: function random_regular_graph in module networkx.generators.random_graphs

random_regular_graph(d, n, seed=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns a random $d$-regular graph on $n$ nodes.

    A regular graph is a graph where each node has the same number of neighbors.

    The resulting graph has no self-loops or parallel edges.

    Parameters
    ----------
    d : int
      The degree of each node.
    n : integer
      The number of nodes. The value of $n \times d$ must be even.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Notes
    -----
    The nodes are numbered from $0$ to $n - 1$.

    Kim and Vu's paper [2]_ shows that this algorithm samples in an
    asymptotically uniform way from the space of random graphs when
    $d = O(n^{1 / 3 - \epsilon})$.

    Raises
    ------

    NetworkXError
        If $n \times d$ is odd or $d$ is greater than or equal to $n$.

    References
    ----------
    .. [1] A. Steger and N. Wormald,
       Generating random regular graphs quickly,
       Probability and Computing 8 (1999), 377-396, 1999.
       https://doi.org/10.1017/S0963548399003867

    .. [2] Jeong Han Kim and Van H. Vu,
       Generating random regular graphs,
       Proceedings of the thirty-fifth ACM symposium on Theory of computing,
       San Diego, CA, USA, pp 213--222, 2003.
       http://portal.acm.org/citation.cfm?id=780542.780576
networkx.random_shell_graph
Python Library Documentation: function random_shell_graph in module networkx.generators.random_graphs

random_shell_graph(constructor, seed=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns a random shell graph for the constructor given.

    Parameters
    ----------
    constructor : list of three-tuples
        Represents the parameters for a shell, starting at the center
        shell.  Each element of the list must be of the form `(n, m,
        d)`, where `n` is the number of nodes in the shell, `m` is
        the number of edges in the shell, and `d` is the ratio of
        inter-shell (next) edges to intra-shell edges. If `d` is zero,
        there will be no intra-shell edges, and if `d` is one there
        will be all possible intra-shell edges.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. Graph instances are not supported.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    Examples
    --------
    >>> constructor = [(10, 20, 0.8), (20, 40, 0.8)]
    >>> G = nx.random_shell_graph(constructor)
networkx.random_spanning_tree
Python Library Documentation: function random_spanning_tree in module networkx.algorithms.tree.mst

random_spanning_tree(G, weight=None, *, multiplicative=True, seed=None, backend=None, **backend_kwargs)
    Sample a random spanning tree using the edges weights of `G`.

    This function supports two different methods for determining the
    probability of the graph. If ``multiplicative=True``, the probability
    is based on the product of edge weights, and if ``multiplicative=False``
    it is based on the sum of the edge weight. However, since it is
    easier to determine the total weight of all spanning trees for the
    multiplicative version, that is significantly faster and should be used if
    possible. Additionally, setting `weight` to `None` will cause a spanning tree
    to be selected with uniform probability.

    The function uses algorithm A8 in [1]_ .

    Parameters
    ----------
    G : nx.Graph
        An undirected version of the original graph.

    weight : string
        The edge key for the edge attribute holding edge weight.

    multiplicative : bool, default=True
        If `True`, the probability of each tree is the product of its edge weight
        over the sum of the product of all the spanning trees in the graph. If
        `False`, the probability is the sum of its edge weight over the sum of
        the sum of weights for all spanning trees in the graph.

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    nx.Graph
        A spanning tree using the distribution defined by the weight of the tree.

    References
    ----------
    .. [1] V. Kulkarni, Generating random combinatorial objects, Journal of
       Algorithms, 11 (1990), pp. 185–207
networkx.random_triad
Python Library Documentation: function random_triad in module networkx.algorithms.triads

random_triad(G, seed=None, *, backend=None, **backend_kwargs)
    Returns a random triad from a directed graph.

    .. deprecated:: 3.3

       random_triad is deprecated and will be removed in version 3.5.
       Use random sampling directly instead::

          G.subgraph(random.sample(list(G), 3))

    Parameters
    ----------
    G : digraph
       A NetworkX DiGraph
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G2 : subgraph
       A randomly selected triad (order-3 NetworkX DiGraph)

    Raises
    ------
    NetworkXError
        If the input Graph has less than 3 nodes.

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (1, 3), (2, 3), (3, 1), (5, 6), (5, 4), (6, 7)])
    >>> triad = nx.random_triad(G, seed=1)
    >>> triad.edges
    OutEdgeView([(1, 2)])
networkx.random_unlabeled_rooted_forest
Python Library Documentation: function random_unlabeled_rooted_forest in module networkx.generators.trees

random_unlabeled_rooted_forest(n, *, q=None, number_of_forests=None, seed=None, backend=None, **backend_kwargs)
    Returns a forest or list of forests selected at random.

    Returns one or more (depending on `number_of_forests`)
    unlabeled rooted forests with `n` nodes, and with no more than
    `q` nodes per tree, drawn uniformly at random.
    The "roots" graph attribute identifies the roots of the forest.

    Parameters
    ----------
    n : int
        The number of nodes
    q : int or None (default)
        The maximum number of nodes per tree.
    number_of_forests : int or None (default)
        If not None, this number of forests is generated and returned.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    :class:`networkx.Graph` or list of :class:`networkx.Graph`
        A single `networkx.Graph` (or a list thereof, if `number_of_forests`
        is specified) with nodes in the set {0, …, *n* - 1}.
        The "roots" graph attribute is a set containing the roots
        of the trees in the forest.

    Notes
    -----
    This function implements the algorithm "Forest" of [1]_.
    The algorithm needs to compute some counting functions
    that are relatively expensive: in case several trees are needed,
    it is advisable to use the `number_of_forests` optional argument
    to reuse the counting functions.

    Raises
    ------
    ValueError
        If `n` is non-zero but `q` is zero.

    References
    ----------
    .. [1] Wilf, Herbert S. "The uniform selection of free trees."
        Journal of Algorithms 2.2 (1981): 204-207.
        https://doi.org/10.1016/0196-6774(81)90021-3
networkx.random_unlabeled_rooted_tree
Python Library Documentation: function random_unlabeled_rooted_tree in module networkx.generators.trees

random_unlabeled_rooted_tree(n, *, number_of_trees=None, seed=None, backend=None, **backend_kwargs)
    Returns a number of unlabeled rooted trees uniformly at random

    Returns one or more (depending on `number_of_trees`)
    unlabeled rooted trees with `n` nodes drawn uniformly
    at random.

    Parameters
    ----------
    n : int
        The number of nodes
    number_of_trees : int or None (default)
        If not None, this number of trees is generated and returned.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    :class:`networkx.Graph` or list of :class:`networkx.Graph`
        A single `networkx.Graph` (or a list thereof, if `number_of_trees`
        is specified) with nodes in the set {0, …, *n* - 1}.
        The "root" graph attribute identifies the root of the tree.

    Notes
    -----
    The trees are generated using the "RANRUT" algorithm from [1]_.
    The algorithm needs to compute some counting functions
    that are relatively expensive: in case several trees are needed,
    it is advisable to use the `number_of_trees` optional argument
    to reuse the counting functions.

    Raises
    ------
    NetworkXPointlessConcept
        If `n` is zero (because the null graph is not a tree).

    References
    ----------
    .. [1] Nijenhuis, Albert, and Wilf, Herbert S.
        "Combinatorial algorithms: for computers and calculators."
        Academic Press, 1978.
        https://doi.org/10.1016/C2013-0-11243-3
networkx.random_unlabeled_tree
Python Library Documentation: function random_unlabeled_tree in module networkx.generators.trees

random_unlabeled_tree(n, *, number_of_trees=None, seed=None, backend=None, **backend_kwargs)
    Returns a tree or list of trees chosen randomly.

    Returns one or more (depending on `number_of_trees`)
    unlabeled trees with `n` nodes drawn uniformly at random.

    Parameters
    ----------
    n : int
        The number of nodes
    number_of_trees : int or None (default)
        If not None, this number of trees is generated and returned.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    :class:`networkx.Graph` or list of :class:`networkx.Graph`
        A single `networkx.Graph` (or a list thereof, if
        `number_of_trees` is specified) with nodes in the set {0, …, *n* - 1}.

    Raises
    ------
    NetworkXPointlessConcept
        If `n` is zero (because the null graph is not a tree).

    Notes
    -----
    This function generates an unlabeled tree uniformly at random using
    Wilf's algorithm "Free" of [1]_. The algorithm needs to
    compute some counting functions that are relatively expensive:
    in case several trees are needed, it is advisable to use the
    `number_of_trees` optional argument to reuse the counting
    functions.

    References
    ----------
    .. [1] Wilf, Herbert S. "The uniform selection of free trees."
        Journal of Algorithms 2.2 (1981): 204-207.
        https://doi.org/10.1016/0196-6774(81)90021-3
networkx.reaching
Python Library Documentation: module networkx.algorithms.centrality.reaching in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.reaching - Functions for computing reaching centrality of a node or a graph.

FUNCTIONS
    global_reaching_centrality(G, weight=None, normalized=True, *, backend=None, **backend_kwargs)
        Returns the global reaching centrality of a directed graph.

        The *global reaching centrality* of a weighted directed graph is the
        average over all nodes of the difference between the local reaching
        centrality of the node and the greatest local reaching centrality of
        any node in the graph [1]_. For more information on the local
        reaching centrality, see :func:`local_reaching_centrality`.
        Informally, the local reaching centrality is the proportion of the
        graph that is reachable from the neighbors of the node.

        Parameters
        ----------
        G : DiGraph
            A networkx DiGraph.

        weight : None or string, optional (default=None)
            Attribute to use for edge weights. If ``None``, each edge weight
            is assumed to be one. A higher weight implies a stronger
            connection between nodes and a *shorter* path length.

        normalized : bool, optional (default=True)
            Whether to normalize the edge weights by the total sum of edge
            weights.

        Returns
        -------
        h : float
            The global reaching centrality of the graph.

        Examples
        --------
        >>> G = nx.DiGraph()
        >>> G.add_edge(1, 2)
        >>> G.add_edge(1, 3)
        >>> nx.global_reaching_centrality(G)
        1.0
        >>> G.add_edge(3, 2)
        >>> nx.global_reaching_centrality(G)
        0.75

        See also
        --------
        local_reaching_centrality

        References
        ----------
        .. [1] Mones, Enys, Lilla Vicsek, and Tamás Vicsek.
               "Hierarchy Measure for Complex Networks."
               *PLoS ONE* 7.3 (2012): e33799.
               https://doi.org/10.1371/journal.pone.0033799

    local_reaching_centrality(G, v, paths=None, weight=None, normalized=True, *, backend=None, **backend_kwargs)
        Returns the local reaching centrality of a node in a directed
        graph.

        The *local reaching centrality* of a node in a directed graph is the
        proportion of other nodes reachable from that node [1]_.

        Parameters
        ----------
        G : DiGraph
            A NetworkX DiGraph.

        v : node
            A node in the directed graph `G`.

        paths : dictionary (default=None)
            If this is not `None` it must be a dictionary representation
            of single-source shortest paths, as computed by, for example,
            :func:`networkx.shortest_path` with source node `v`. Use this
            keyword argument if you intend to invoke this function many
            times but don't want the paths to be recomputed each time.

        weight : None or string, optional (default=None)
            Attribute to use for edge weights.  If `None`, each edge weight
            is assumed to be one. A higher weight implies a stronger
            connection between nodes and a *shorter* path length.

        normalized : bool, optional (default=True)
            Whether to normalize the edge weights by the total sum of edge
            weights.

        Returns
        -------
        h : float
            The local reaching centrality of the node ``v`` in the graph
            ``G``.

        Examples
        --------
        >>> G = nx.DiGraph()
        >>> G.add_edges_from([(1, 2), (1, 3)])
        >>> nx.local_reaching_centrality(G, 3)
        0.0
        >>> G.add_edge(3, 2)
        >>> nx.local_reaching_centrality(G, 3)
        0.5

        See also
        --------
        global_reaching_centrality

        References
        ----------
        .. [1] Mones, Enys, Lilla Vicsek, and Tamás Vicsek.
               "Hierarchy Measure for Complex Networks."
               *PLoS ONE* 7.3 (2012): e33799.
               https://doi.org/10.1371/journal.pone.0033799

DATA
    __all__ = ['global_reaching_centrality', 'local_reaching_centrality']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\reaching.py

networkx.read_adjlist
Python Library Documentation: function read_adjlist in module networkx.readwrite.adjlist

read_adjlist(path, comments='#', delimiter=None, create_using=None, nodetype=None, encoding='utf-8', *, backend=None, **backend_kwargs)
    Read graph in adjacency list format from path.

    Parameters
    ----------
    path : string or file
       Filename or file handle to read.
       Filenames ending in .gz or .bz2 will be uncompressed.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    nodetype : Python type, optional
       Convert nodes to this type.

    comments : string, optional
       Marker for comment lines

    delimiter : string, optional
       Separator for node labels.  The default is whitespace.

    Returns
    -------
    G: NetworkX graph
        The graph corresponding to the lines in adjacency list format.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_adjlist(G, "test.adjlist")
    >>> G = nx.read_adjlist("test.adjlist")

    The path can be a filehandle or a string with the name of the file. If a
    filehandle is provided, it has to be opened in 'rb' mode.

    >>> fh = open("test.adjlist", "rb")
    >>> G = nx.read_adjlist(fh)

    Filenames ending in .gz or .bz2 will be compressed.

    >>> nx.write_adjlist(G, "test.adjlist.gz")
    >>> G = nx.read_adjlist("test.adjlist.gz")

    The optional nodetype is a function to convert node strings to nodetype.

    For example

    >>> G = nx.read_adjlist("test.adjlist", nodetype=int)

    will attempt to convert all nodes to integer type.

    Since nodes must be hashable, the function nodetype must return hashable
    types (e.g. int, float, str, frozenset - or tuples of those, etc.)

    The optional create_using parameter indicates the type of NetworkX graph
    created.  The default is `nx.Graph`, an undirected graph.
    To read the data as a directed graph use

    >>> G = nx.read_adjlist("test.adjlist", create_using=nx.DiGraph)

    Notes
    -----
    This format does not store graph or node data.

    See Also
    --------
    write_adjlist
networkx.read_edgelist
Python Library Documentation: function read_edgelist in module networkx.readwrite.edgelist

read_edgelist(path, comments='#', delimiter=None, create_using=None, nodetype=None, data=True, edgetype=None, encoding='utf-8', *, backend=None, **backend_kwargs)
    Read a graph from a list of edges.

    Parameters
    ----------
    path : file or string
       File or filename to read. If a file is provided, it must be
       opened in 'rb' mode.
       Filenames ending in .gz or .bz2 will be uncompressed.
    comments : string, optional
       The character used to indicate the start of a comment. To specify that
       no character should be treated as a comment, use ``comments=None``.
    delimiter : string, optional
       The string used to separate values.  The default is whitespace.
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.
    nodetype : int, float, str, Python type, optional
       Convert node data from strings to specified type
    data : bool or list of (label,type) tuples
       Tuples specifying dictionary key names and types for edge data
    edgetype : int, float, str, Python type, optional OBSOLETE
       Convert edge data from strings to specified type and use as 'weight'
    encoding: string, optional
       Specify which encoding to use when reading file.

    Returns
    -------
    G : graph
       A networkx Graph or other type specified with create_using

    Examples
    --------
    >>> nx.write_edgelist(nx.path_graph(4), "test.edgelist")
    >>> G = nx.read_edgelist("test.edgelist")

    >>> fh = open("test.edgelist", "rb")
    >>> G = nx.read_edgelist(fh)
    >>> fh.close()

    >>> G = nx.read_edgelist("test.edgelist", nodetype=int)
    >>> G = nx.read_edgelist("test.edgelist", create_using=nx.DiGraph)

    Edgelist with data in a list:

    >>> textline = "1 2 3"
    >>> fh = open("test.edgelist", "w")
    >>> d = fh.write(textline)
    >>> fh.close()
    >>> G = nx.read_edgelist("test.edgelist", nodetype=int, data=(("weight", float),))
    >>> list(G)
    [1, 2]
    >>> list(G.edges(data=True))
    [(1, 2, {'weight': 3.0})]

    See parse_edgelist() for more examples of formatting.

    See Also
    --------
    parse_edgelist
    write_edgelist

    Notes
    -----
    Since nodes must be hashable, the function nodetype must return hashable
    types (e.g. int, float, str, frozenset - or tuples of those, etc.)
networkx.read_gexf
Python Library Documentation: function read_gexf in module networkx.readwrite.gexf

read_gexf(path, node_type=None, relabel=False, version='1.2draft', *, backend=None, **backend_kwargs)
    Read graph in GEXF format from path.

    "GEXF (Graph Exchange XML Format) is a language for describing
    complex networks structures, their associated data and dynamics" [1]_.

    Parameters
    ----------
    path : file or string
       File or file name to read.
       File names ending in .gz or .bz2 will be decompressed.
    node_type: Python type (default: None)
       Convert node ids to this type if not None.
    relabel : bool (default: False)
       If True relabel the nodes to use the GEXF node "label" attribute
       instead of the node "id" attribute as the NetworkX node label.
    version : string (default: 1.2draft)
    Version of GEFX File Format (see http://gexf.net/schema.html)
       Supported values: "1.1draft", "1.2draft"

    Returns
    -------
    graph: NetworkX graph
        If no parallel edges are found a Graph or DiGraph is returned.
        Otherwise a MultiGraph or MultiDiGraph is returned.

    Notes
    -----
    This implementation does not support mixed graphs (directed and undirected
    edges together).

    References
    ----------
    .. [1] GEXF File Format, http://gexf.net/
networkx.read_gml
Python Library Documentation: function read_gml in module networkx.readwrite.gml

read_gml(path, label='label', destringizer=None, *, backend=None, **backend_kwargs)
    Read graph in GML format from `path`.

    Parameters
    ----------
    path : filename or filehandle
        The filename or filehandle to read from.

    label : string, optional
        If not None, the parsed nodes will be renamed according to node
        attributes indicated by `label`. Default value: 'label'.

    destringizer : callable, optional
        A `destringizer` that recovers values stored as strings in GML. If it
        cannot convert a string to a value, a `ValueError` is raised. Default
        value : None.

    Returns
    -------
    G : NetworkX graph
        The parsed graph.

    Raises
    ------
    NetworkXError
        If the input cannot be parsed.

    See Also
    --------
    write_gml, parse_gml
    literal_destringizer

    Notes
    -----
    GML files are stored using a 7-bit ASCII encoding with any extended
    ASCII characters (iso8859-1) appearing as HTML character entities.
    Without specifying a `stringizer`/`destringizer`, the code is capable of
    writing `int`/`float`/`str`/`dict`/`list` data as required by the GML
    specification.  For writing other data types, and for reading data other
    than `str` you need to explicitly supply a `stringizer`/`destringizer`.

    For additional documentation on the GML file format, please see the
    `GML url <https://web.archive.org/web/20190207140002/http://www.fim.uni-passau.de/index.php?id=17297&L=1>`_.

    See the module docstring :mod:`networkx.readwrite.gml` for more details.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_gml(G, "test.gml")

    GML values are interpreted as strings by default:

    >>> H = nx.read_gml("test.gml")
    >>> H.nodes
    NodeView(('0', '1', '2', '3'))

    When a `destringizer` is provided, GML values are converted to the provided type.
    For example, integer nodes can be recovered as shown below:

    >>> J = nx.read_gml("test.gml", destringizer=int)
    >>> J.nodes
    NodeView((0, 1, 2, 3))
networkx.read_graph6
Python Library Documentation: function read_graph6 in module networkx.readwrite.graph6

read_graph6(path, *, backend=None, **backend_kwargs)
    Read simple undirected graphs in graph6 format from path.

    Parameters
    ----------
    path : file or string
       File or filename to write.

    Returns
    -------
    G : Graph or list of Graphs
       If the file contains multiple lines then a list of graphs is returned

    Raises
    ------
    NetworkXError
        If the string is unable to be parsed in graph6 format

    Examples
    --------
    You can read a graph6 file by giving the path to the file::

        >>> import tempfile
        >>> with tempfile.NamedTemporaryFile(delete=False) as f:
        ...     _ = f.write(b">>graph6<<A_\n")
        ...     _ = f.seek(0)
        ...     G = nx.read_graph6(f.name)
        >>> list(G.edges())
        [(0, 1)]

    You can also read a graph6 file by giving an open file-like object::

        >>> import tempfile
        >>> with tempfile.NamedTemporaryFile() as f:
        ...     _ = f.write(b">>graph6<<A_\n")
        ...     _ = f.seek(0)
        ...     G = nx.read_graph6(f)
        >>> list(G.edges())
        [(0, 1)]

    See Also
    --------
    from_graph6_bytes, write_graph6

    References
    ----------
    .. [1] Graph6 specification
           <http://users.cecs.anu.edu.au/~bdm/data/formats.html>
networkx.read_graphml
Python Library Documentation: function read_graphml in module networkx.readwrite.graphml

read_graphml(path, node_type=<class 'str'>, edge_key_type=<class 'int'>, force_multigraph=False, *, backend=None, **backend_kwargs)
    Read graph in GraphML format from path.

    Parameters
    ----------
    path : file or string
       File or filename to write.
       Filenames ending in .gz or .bz2 will be compressed.

    node_type: Python type (default: str)
       Convert node ids to this type

    edge_key_type: Python type (default: int)
       Convert graphml edge ids to this type. Multigraphs use id as edge key.
       Non-multigraphs add to edge attribute dict with name "id".

    force_multigraph : bool (default: False)
       If True, return a multigraph with edge keys. If False (the default)
       return a multigraph when multiedges are in the graph.

    Returns
    -------
    graph: NetworkX graph
        If parallel edges are present or `force_multigraph=True` then
        a MultiGraph or MultiDiGraph is returned. Otherwise a Graph/DiGraph.
        The returned graph is directed if the file indicates it should be.

    Notes
    -----
    Default node and edge attributes are not propagated to each node and edge.
    They can be obtained from `G.graph` and applied to node and edge attributes
    if desired using something like this:

    >>> default_color = G.graph["node_default"]["color"]  # doctest: +SKIP
    >>> for node, data in G.nodes(data=True):  # doctest: +SKIP
    ...     if "color" not in data:
    ...         data["color"] = default_color
    >>> default_color = G.graph["edge_default"]["color"]  # doctest: +SKIP
    >>> for u, v, data in G.edges(data=True):  # doctest: +SKIP
    ...     if "color" not in data:
    ...         data["color"] = default_color

    This implementation does not support mixed graphs (directed and unidirected
    edges together), hypergraphs, nested graphs, or ports.

    For multigraphs the GraphML edge "id" will be used as the edge
    key.  If not specified then they "key" attribute will be used.  If
    there is no "key" attribute a default NetworkX multigraph edge key
    will be provided.

    Files with the yEd "yfiles" extension can be read. The type of the node's
    shape is preserved in the `shape_type` node attribute.

    yEd compressed files ("file.graphmlz" extension) can be read by renaming
    the file to "file.graphml.gz".
networkx.read_leda
Python Library Documentation: function read_leda in module networkx.readwrite.leda

read_leda(path, encoding='UTF-8', *, backend=None, **backend_kwargs)
    Read graph in LEDA format from path.

    Parameters
    ----------
    path : file or string
       File or filename to read.  Filenames ending in .gz or .bz2  will be
       uncompressed.

    Returns
    -------
    G : NetworkX graph

    Examples
    --------
    G=nx.read_leda('file.leda')

    References
    ----------
    .. [1] http://www.algorithmic-solutions.info/leda_guide/graphs/leda_native_graph_fileformat.html
networkx.read_multiline_adjlist
Python Library Documentation: function read_multiline_adjlist in module networkx.readwrite.multiline_adjlist

read_multiline_adjlist(path, comments='#', delimiter=None, create_using=None, nodetype=None, edgetype=None, encoding='utf-8', *, backend=None, **backend_kwargs)
    Read graph in multi-line adjacency list format from path.

    Parameters
    ----------
    path : string or file
       Filename or file handle to read.
       Filenames ending in .gz or .bz2 will be uncompressed.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    nodetype : Python type, optional
       Convert nodes to this type.

    edgetype : Python type, optional
       Convert edge data to this type.

    comments : string, optional
       Marker for comment lines

    delimiter : string, optional
       Separator for node labels.  The default is whitespace.

    Returns
    -------
    G: NetworkX graph

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_multiline_adjlist(G, "test.adjlist")
    >>> G = nx.read_multiline_adjlist("test.adjlist")

    The path can be a file or a string with the name of the file. If a
    file s provided, it has to be opened in 'rb' mode.

    >>> fh = open("test.adjlist", "rb")
    >>> G = nx.read_multiline_adjlist(fh)

    Filenames ending in .gz or .bz2 will be compressed.

    >>> nx.write_multiline_adjlist(G, "test.adjlist.gz")
    >>> G = nx.read_multiline_adjlist("test.adjlist.gz")

    The optional nodetype is a function to convert node strings to nodetype.

    For example

    >>> G = nx.read_multiline_adjlist("test.adjlist", nodetype=int)

    will attempt to convert all nodes to integer type.

    The optional edgetype is a function to convert edge data strings to
    edgetype.

    >>> G = nx.read_multiline_adjlist("test.adjlist")

    The optional create_using parameter is a NetworkX graph container.
    The default is Graph(), an undirected graph.  To read the data as
    a directed graph use

    >>> G = nx.read_multiline_adjlist("test.adjlist", create_using=nx.DiGraph)

    Notes
    -----
    This format does not store graph, node, or edge data.

    See Also
    --------
    write_multiline_adjlist
networkx.read_pajek
Python Library Documentation: function read_pajek in module networkx.readwrite.pajek

read_pajek(path, encoding='UTF-8', *, backend=None, **backend_kwargs)
    Read graph in Pajek format from path.

    Parameters
    ----------
    path : file or string
       File or filename to write.
       Filenames ending in .gz or .bz2 will be uncompressed.

    Returns
    -------
    G : NetworkX MultiGraph or MultiDiGraph.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_pajek(G, "test.net")
    >>> G = nx.read_pajek("test.net")

    To create a Graph instead of a MultiGraph use

    >>> G1 = nx.Graph(G)

    References
    ----------
    See http://vlado.fmf.uni-lj.si/pub/networks/pajek/doc/draweps.htm
    for format information.
networkx.read_sparse6
Python Library Documentation: function read_sparse6 in module networkx.readwrite.sparse6

read_sparse6(path, *, backend=None, **backend_kwargs)
    Read an undirected graph in sparse6 format from path.

    Parameters
    ----------
    path : file or string
       File or filename to write.

    Returns
    -------
    G : Graph/Multigraph or list of Graphs/MultiGraphs
       If the file contains multiple lines then a list of graphs is returned

    Raises
    ------
    NetworkXError
        If the string is unable to be parsed in sparse6 format

    Examples
    --------
    You can read a sparse6 file by giving the path to the file::

        >>> import tempfile
        >>> with tempfile.NamedTemporaryFile(delete=False) as f:
        ...     _ = f.write(b">>sparse6<<:An\n")
        ...     _ = f.seek(0)
        ...     G = nx.read_sparse6(f.name)
        >>> list(G.edges())
        [(0, 1)]

    You can also read a sparse6 file by giving an open file-like object::

        >>> import tempfile
        >>> with tempfile.NamedTemporaryFile() as f:
        ...     _ = f.write(b">>sparse6<<:An\n")
        ...     _ = f.seek(0)
        ...     G = nx.read_sparse6(f)
        >>> list(G.edges())
        [(0, 1)]

    See Also
    --------
    read_sparse6, from_sparse6_bytes

    References
    ----------
    .. [1] Sparse6 specification
           <https://users.cecs.anu.edu.au/~bdm/data/formats.html>
networkx.read_weighted_edgelist
Python Library Documentation: function read_weighted_edgelist in module networkx.readwrite.edgelist

read_weighted_edgelist(path, comments='#', delimiter=None, create_using=None, nodetype=None, encoding='utf-8', *, backend=None, **backend_kwargs)
    Read a graph as list of edges with numeric weights.

    Parameters
    ----------
    path : file or string
       File or filename to read. If a file is provided, it must be
       opened in 'rb' mode.
       Filenames ending in .gz or .bz2 will be uncompressed.
    comments : string, optional
       The character used to indicate the start of a comment.
    delimiter : string, optional
       The string used to separate values.  The default is whitespace.
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.
    nodetype : int, float, str, Python type, optional
       Convert node data from strings to specified type
    encoding: string, optional
       Specify which encoding to use when reading file.

    Returns
    -------
    G : graph
       A networkx Graph or other type specified with create_using

    Notes
    -----
    Since nodes must be hashable, the function nodetype must return hashable
    types (e.g. int, float, str, frozenset - or tuples of those, etc.)

    Example edgelist file format.

    With numeric edge data::

     # read with
     # >>> G=nx.read_weighted_edgelist(fh)
     # source target data
     a b 1
     a c 3.14159
     d e 42

    See Also
    --------
    write_weighted_edgelist
networkx.readwrite
Python Library Documentation: package networkx.readwrite in networkx

NAME
    networkx.readwrite - A package for reading and writing graphs in various formats.

PACKAGE CONTENTS
    adjlist
    edgelist
    gexf
    gml
    graph6
    graphml
    json_graph (package)
    leda
    multiline_adjlist
    p2g
    pajek
    sparse6
    tests (package)
    text

SUBMODULES
    adjacency
    cytoscape
    node_link
    tree

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\__init__.py

networkx.reciprocity
Python Library Documentation: function reciprocity in module networkx.algorithms.reciprocity

reciprocity(G, nodes=None, *, backend=None, **backend_kwargs)
    Compute the reciprocity in a directed graph.

    The reciprocity of a directed graph is defined as the ratio
    of the number of edges pointing in both directions to the total
    number of edges in the graph.
    Formally, $r = |{(u,v) \in G|(v,u) \in G}| / |{(u,v) \in G}|$.

    The reciprocity of a single node u is defined similarly,
    it is the ratio of the number of edges in both directions to
    the total number of edges attached to node u.

    Parameters
    ----------
    G : graph
       A networkx directed graph
    nodes : container of nodes, optional (default=whole graph)
       Compute reciprocity for nodes in this container.

    Returns
    -------
    out : dictionary
       Reciprocity keyed by node label.

    Notes
    -----
    The reciprocity is not defined for isolated nodes.
    In such cases this function will return None.
networkx.reconstruct_path
Python Library Documentation: function reconstruct_path in module networkx.algorithms.shortest_paths.dense

reconstruct_path(source, target, predecessors, *, backend=None, **backend_kwargs)
    Reconstruct a path from source to target using the predecessors
    dict as returned by floyd_warshall_predecessor_and_distance

    Parameters
    ----------
    source : node
       Starting node for path

    target : node
       Ending node for path

    predecessors: dictionary
       Dictionary, keyed by source and target, of predecessors in the
       shortest path, as returned by floyd_warshall_predecessor_and_distance

    Returns
    -------
    path : list
       A list of nodes containing the shortest path from source to target

       If source and target are the same, an empty list is returned

    Notes
    -----
    This function is meant to give more applicability to the
    floyd_warshall_predecessor_and_distance function

    See Also
    --------
    floyd_warshall_predecessor_and_distance
networkx.recursive_simple_cycles
Python Library Documentation: function recursive_simple_cycles in module networkx.algorithms.cycles

recursive_simple_cycles(G, *, backend=None, **backend_kwargs)
    Find simple cycles (elementary circuits) of a directed graph.

    A `simple cycle`, or `elementary circuit`, is a closed path where
    no node appears twice. Two elementary circuits are distinct if they
    are not cyclic permutations of each other.

    This version uses a recursive algorithm to build a list of cycles.
    You should probably use the iterator version called simple_cycles().
    Warning: This recursive version uses lots of RAM!
    It appears in NetworkX for pedagogical value.

    Parameters
    ----------
    G : NetworkX DiGraph
       A directed graph

    Returns
    -------
    A list of cycles, where each cycle is represented by a list of nodes
    along the cycle.

    Example:

    >>> edges = [(0, 0), (0, 1), (0, 2), (1, 2), (2, 0), (2, 1), (2, 2)]
    >>> G = nx.DiGraph(edges)
    >>> nx.recursive_simple_cycles(G)
    [[0], [2], [0, 1, 2], [0, 2], [1, 2]]

    Notes
    -----
    The implementation follows pp. 79-80 in [1]_.

    The time complexity is $O((n+e)(c+1))$ for $n$ nodes, $e$ edges and $c$
    elementary circuits.

    References
    ----------
    .. [1] Finding all the elementary circuits of a directed graph.
       D. B. Johnson, SIAM Journal on Computing 4, no. 1, 77-84, 1975.
       https://doi.org/10.1137/0204007

    See Also
    --------
    simple_cycles, cycle_basis
networkx.regular
Python Library Documentation: module networkx.algorithms.regular in networkx.algorithms

NAME
    networkx.algorithms.regular - Functions for computing and verifying regular graphs.

FUNCTIONS
    is_k_regular(G, k, *, backend=None, **backend_kwargs)
        Determines whether the graph ``G`` is a k-regular graph.

        A k-regular graph is a graph where each vertex has degree k.

        Parameters
        ----------
        G : NetworkX graph

        Returns
        -------
        bool
            Whether the given graph is k-regular.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (2, 3), (3, 4), (4, 1)])
        >>> nx.is_k_regular(G, k=3)
        False

    is_regular(G, *, backend=None, **backend_kwargs)
        Determines whether the graph ``G`` is a regular graph.

        A regular graph is a graph where each vertex has the same degree. A
        regular digraph is a graph where the indegree and outdegree of each
        vertex are equal.

        Parameters
        ----------
        G : NetworkX graph

        Returns
        -------
        bool
            Whether the given graph or digraph is regular.

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 4), (4, 1)])
        >>> nx.is_regular(G)
        True

    k_factor(G, k, matching_weight='weight', *, backend=None, **backend_kwargs)
        Compute a k-factor of G

        A k-factor of a graph is a spanning k-regular subgraph.
        A spanning k-regular subgraph of G is a subgraph that contains
        each vertex of G and a subset of the edges of G such that each
        vertex has degree k.

        Parameters
        ----------
        G : NetworkX graph
          Undirected graph

        matching_weight: string, optional (default='weight')
           Edge data key corresponding to the edge weight.
           Used for finding the max-weighted perfect matching.
           If key not found, uses 1 as weight.

        Returns
        -------
        G2 : NetworkX graph
            A k-factor of G

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (2, 3), (3, 4), (4, 1)])
        >>> G2 = nx.k_factor(G, k=1)
        >>> G2.edges()
        EdgeView([(1, 2), (3, 4)])

        References
        ----------
        .. [1] "An algorithm for computing simple k-factors.",
           Meijer, Henk, Yurai Núñez-Rodríguez, and David Rappaport,
           Information processing letters, 2009.

DATA
    __all__ = ['is_regular', 'is_k_regular', 'k_factor']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\regular.py

networkx.relabel
Python Library Documentation: module networkx.relabel in networkx

NAME
    networkx.relabel

FUNCTIONS
    convert_node_labels_to_integers(G, first_label=0, ordering='default', label_attribute=None, *, backend=None, **backend_kwargs)
        Returns a copy of the graph G with the nodes relabeled using
        consecutive integers.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        first_label : int, optional (default=0)
           An integer specifying the starting offset in numbering nodes.
           The new integer labels are numbered first_label, ..., n-1+first_label.

        ordering : string
           "default" : inherit node ordering from G.nodes()
           "sorted"  : inherit node ordering from sorted(G.nodes())
           "increasing degree" : nodes are sorted by increasing degree
           "decreasing degree" : nodes are sorted by decreasing degree

        label_attribute : string, optional (default=None)
           Name of node attribute to store old label.  If None no attribute
           is created.

        Notes
        -----
        Node and edge attribute data are copied to the new (relabeled) graph.

        There is no guarantee that the relabeling of nodes to integers will
        give the same two integers for two (even identical graphs).
        Use the `ordering` argument to try to preserve the order.

        See Also
        --------
        relabel_nodes

    relabel_nodes(G, mapping, copy=True, *, backend=None, **backend_kwargs)
        Relabel the nodes of the graph G according to a given mapping.

        The original node ordering may not be preserved if `copy` is `False` and the
        mapping includes overlap between old and new labels.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        mapping : dictionary
           A dictionary with the old labels as keys and new labels as values.
           A partial mapping is allowed. Mapping 2 nodes to a single node is allowed.
           Any non-node keys in the mapping are ignored.

        copy : bool (optional, default=True)
           If True return a copy, or if False relabel the nodes in place.

        Examples
        --------
        To create a new graph with nodes relabeled according to a given
        dictionary:

        >>> G = nx.path_graph(3)
        >>> sorted(G)
        [0, 1, 2]
        >>> mapping = {0: "a", 1: "b", 2: "c"}
        >>> H = nx.relabel_nodes(G, mapping)
        >>> sorted(H)
        ['a', 'b', 'c']

        Nodes can be relabeled with any hashable object, including numbers
        and strings:

        >>> import string
        >>> G = nx.path_graph(26)  # nodes are integers 0 through 25
        >>> sorted(G)[:3]
        [0, 1, 2]
        >>> mapping = dict(zip(G, string.ascii_lowercase))
        >>> G = nx.relabel_nodes(G, mapping)  # nodes are characters a through z
        >>> sorted(G)[:3]
        ['a', 'b', 'c']
        >>> mapping = dict(zip(G, range(1, 27)))
        >>> G = nx.relabel_nodes(G, mapping)  # nodes are integers 1 through 26
        >>> sorted(G)[:3]
        [1, 2, 3]

        To perform a partial in-place relabeling, provide a dictionary
        mapping only a subset of the nodes, and set the `copy` keyword
        argument to False:

        >>> G = nx.path_graph(3)  # nodes 0-1-2
        >>> mapping = {0: "a", 1: "b"}  # 0->'a' and 1->'b'
        >>> G = nx.relabel_nodes(G, mapping, copy=False)
        >>> sorted(G, key=str)
        [2, 'a', 'b']

        A mapping can also be given as a function:

        >>> G = nx.path_graph(3)
        >>> H = nx.relabel_nodes(G, lambda x: x**2)
        >>> list(H)
        [0, 1, 4]

        In a multigraph, relabeling two or more nodes to the same new node
        will retain all edges, but may change the edge keys in the process:

        >>> G = nx.MultiGraph()
        >>> G.add_edge(0, 1, value="a")  # returns the key for this edge
        0
        >>> G.add_edge(0, 2, value="b")
        0
        >>> G.add_edge(0, 3, value="c")
        0
        >>> mapping = {1: 4, 2: 4, 3: 4}
        >>> H = nx.relabel_nodes(G, mapping, copy=True)
        >>> print(H[0])
        {4: {0: {'value': 'a'}, 1: {'value': 'b'}, 2: {'value': 'c'}}}

        This works for in-place relabeling too:

        >>> G = nx.relabel_nodes(G, mapping, copy=False)
        >>> print(G[0])
        {4: {0: {'value': 'a'}, 1: {'value': 'b'}, 2: {'value': 'c'}}}

        Notes
        -----
        Only the nodes specified in the mapping will be relabeled.
        Any non-node keys in the mapping are ignored.

        The keyword setting copy=False modifies the graph in place.
        Relabel_nodes avoids naming collisions by building a
        directed graph from ``mapping`` which specifies the order of
        relabelings. Naming collisions, such as a->b, b->c, are ordered
        such that "b" gets renamed to "c" before "a" gets renamed "b".
        In cases of circular mappings (e.g. a->b, b->a), modifying the
        graph is not possible in-place and an exception is raised.
        In that case, use copy=True.

        If a relabel operation on a multigraph would cause two or more
        edges to have the same source, target and key, the second edge must
        be assigned a new key to retain all edges. The new key is set
        to the lowest non-negative integer not already used as a key
        for edges between these two nodes. Note that this means non-numeric
        keys may be replaced by numeric keys.

        See Also
        --------
        convert_node_labels_to_integers

DATA
    __all__ = ['convert_node_labels_to_integers', 'relabel_nodes']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\relabel.py

networkx.relabel_gexf_graph
Python Library Documentation: function relabel_gexf_graph in module networkx.readwrite.gexf

relabel_gexf_graph(G)
    Relabel graph using "label" node keyword for node label.

    Parameters
    ----------
    G : graph
       A NetworkX graph read from GEXF data

    Returns
    -------
    H : graph
      A NetworkX graph with relabeled nodes

    Raises
    ------
    NetworkXError
        If node labels are missing or not unique while relabel=True.

    Notes
    -----
    This function relabels the nodes in a NetworkX graph with the
    "label" attribute.  It also handles relabeling the specific GEXF
    node attributes "parents", and "pid".
networkx.relabel_nodes
Python Library Documentation: function relabel_nodes in module networkx.relabel

relabel_nodes(G, mapping, copy=True, *, backend=None, **backend_kwargs)
    Relabel the nodes of the graph G according to a given mapping.

    The original node ordering may not be preserved if `copy` is `False` and the
    mapping includes overlap between old and new labels.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    mapping : dictionary
       A dictionary with the old labels as keys and new labels as values.
       A partial mapping is allowed. Mapping 2 nodes to a single node is allowed.
       Any non-node keys in the mapping are ignored.

    copy : bool (optional, default=True)
       If True return a copy, or if False relabel the nodes in place.

    Examples
    --------
    To create a new graph with nodes relabeled according to a given
    dictionary:

    >>> G = nx.path_graph(3)
    >>> sorted(G)
    [0, 1, 2]
    >>> mapping = {0: "a", 1: "b", 2: "c"}
    >>> H = nx.relabel_nodes(G, mapping)
    >>> sorted(H)
    ['a', 'b', 'c']

    Nodes can be relabeled with any hashable object, including numbers
    and strings:

    >>> import string
    >>> G = nx.path_graph(26)  # nodes are integers 0 through 25
    >>> sorted(G)[:3]
    [0, 1, 2]
    >>> mapping = dict(zip(G, string.ascii_lowercase))
    >>> G = nx.relabel_nodes(G, mapping)  # nodes are characters a through z
    >>> sorted(G)[:3]
    ['a', 'b', 'c']
    >>> mapping = dict(zip(G, range(1, 27)))
    >>> G = nx.relabel_nodes(G, mapping)  # nodes are integers 1 through 26
    >>> sorted(G)[:3]
    [1, 2, 3]

    To perform a partial in-place relabeling, provide a dictionary
    mapping only a subset of the nodes, and set the `copy` keyword
    argument to False:

    >>> G = nx.path_graph(3)  # nodes 0-1-2
    >>> mapping = {0: "a", 1: "b"}  # 0->'a' and 1->'b'
    >>> G = nx.relabel_nodes(G, mapping, copy=False)
    >>> sorted(G, key=str)
    [2, 'a', 'b']

    A mapping can also be given as a function:

    >>> G = nx.path_graph(3)
    >>> H = nx.relabel_nodes(G, lambda x: x**2)
    >>> list(H)
    [0, 1, 4]

    In a multigraph, relabeling two or more nodes to the same new node
    will retain all edges, but may change the edge keys in the process:

    >>> G = nx.MultiGraph()
    >>> G.add_edge(0, 1, value="a")  # returns the key for this edge
    0
    >>> G.add_edge(0, 2, value="b")
    0
    >>> G.add_edge(0, 3, value="c")
    0
    >>> mapping = {1: 4, 2: 4, 3: 4}
    >>> H = nx.relabel_nodes(G, mapping, copy=True)
    >>> print(H[0])
    {4: {0: {'value': 'a'}, 1: {'value': 'b'}, 2: {'value': 'c'}}}

    This works for in-place relabeling too:

    >>> G = nx.relabel_nodes(G, mapping, copy=False)
    >>> print(G[0])
    {4: {0: {'value': 'a'}, 1: {'value': 'b'}, 2: {'value': 'c'}}}

    Notes
    -----
    Only the nodes specified in the mapping will be relabeled.
    Any non-node keys in the mapping are ignored.

    The keyword setting copy=False modifies the graph in place.
    Relabel_nodes avoids naming collisions by building a
    directed graph from ``mapping`` which specifies the order of
    relabelings. Naming collisions, such as a->b, b->c, are ordered
    such that "b" gets renamed to "c" before "a" gets renamed "b".
    In cases of circular mappings (e.g. a->b, b->a), modifying the
    graph is not possible in-place and an exception is raised.
    In that case, use copy=True.

    If a relabel operation on a multigraph would cause two or more
    edges to have the same source, target and key, the second edge must
    be assigned a new key to retain all edges. The new key is set
    to the lowest non-negative integer not already used as a key
    for edges between these two nodes. Note that this means non-numeric
    keys may be replaced by numeric keys.

    See Also
    --------
    convert_node_labels_to_integers
networkx.relaxed_caveman_graph
Python Library Documentation: function relaxed_caveman_graph in module networkx.generators.community

relaxed_caveman_graph(l, k, p, seed=None, *, backend=None, **backend_kwargs)
    Returns a relaxed caveman graph.

    A relaxed caveman graph starts with `l` cliques of size `k`.  Edges are
    then randomly rewired with probability `p` to link different cliques.

    Parameters
    ----------
    l : int
      Number of groups
    k : int
      Size of cliques
    p : float
      Probability of rewiring each edge.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    G : NetworkX Graph
      Relaxed Caveman Graph

    Raises
    ------
    NetworkXError
     If p is not in [0,1]

    Examples
    --------
    >>> G = nx.relaxed_caveman_graph(2, 3, 0.1, seed=42)

    References
    ----------
    .. [1] Santo Fortunato, Community Detection in Graphs,
       Physics Reports Volume 486, Issues 3-5, February 2010, Pages 75-174.
       https://arxiv.org/abs/0906.0612
networkx.remove_edge_attributes
Python Library Documentation: function remove_edge_attributes in module networkx.classes.function

remove_edge_attributes(G, *attr_names, ebunch=None)
    Remove edge attributes from all edges in the graph.

    Parameters
    ----------
    G : NetworkX Graph

    *attr_names : List of Strings
        The attribute names to remove from the graph.

    Examples
    --------
    >>> G = nx.path_graph(3)
    >>> nx.set_edge_attributes(G, {(u, v): u + v for u, v in G.edges()}, name="weight")
    >>> nx.get_edge_attributes(G, "weight")
    {(0, 1): 1, (1, 2): 3}
    >>> remove_edge_attributes(G, "weight")
    >>> nx.get_edge_attributes(G, "weight")
    {}
networkx.remove_node_attributes
Python Library Documentation: function remove_node_attributes in module networkx.classes.function

remove_node_attributes(G, *attr_names, nbunch=None)
    Remove node attributes from all nodes in the graph.

    Parameters
    ----------
    G : NetworkX Graph

    *attr_names : List of Strings
        The attribute names to remove from the graph.

    nbunch : List of Nodes
        Remove the node attributes only from the nodes in this list.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_nodes_from([1, 2, 3], color="blue")
    >>> nx.get_node_attributes(G, "color")
    {1: 'blue', 2: 'blue', 3: 'blue'}
    >>> nx.remove_node_attributes(G, "color")
    >>> nx.get_node_attributes(G, "color")
    {}
networkx.reportviews
Python Library Documentation: module networkx.classes.reportviews in networkx.classes

NAME
    networkx.classes.reportviews - View Classes provide node, edge and degree "views" of a graph.

DESCRIPTION
    Views for nodes, edges and degree are provided for all base graph classes.
    A view means a read-only object that is quick to create, automatically
    updated when the graph changes, and provides basic access like `n in V`,
    `for n in V`, `V[n]` and sometimes set operations.

    The views are read-only iterable containers that are updated as the
    graph is updated. As with dicts, the graph should not be updated
    while iterating through the view. Views can be iterated multiple times.

    Edge and Node views also allow data attribute lookup.
    The resulting attribute dict is writable as `G.edges[3, 4]['color']='red'`
    Degree views allow lookup of degree values for single nodes.
    Weighted degree is supported with the `weight` argument.

    NodeView
    ========

        `V = G.nodes` (or `V = G.nodes()`) allows `len(V)`, `n in V`, set
        operations e.g. "G.nodes & H.nodes", and `dd = G.nodes[n]`, where
        `dd` is the node data dict. Iteration is over the nodes by default.

    NodeDataView
    ============

        To iterate over (node, data) pairs, use arguments to `G.nodes()`
        to create a DataView e.g. `DV = G.nodes(data='color', default='red')`.
        The DataView iterates as `for n, color in DV` and allows
        `(n, 'red') in DV`. Using `DV = G.nodes(data=True)`, the DataViews
        use the full datadict in writeable form also allowing contain testing as
        `(n, {'color': 'red'}) in VD`. DataViews allow set operations when
        data attributes are hashable.

    DegreeView
    ==========

        `V = G.degree` allows iteration over (node, degree) pairs as well
        as lookup: `deg=V[n]`. There are many flavors of DegreeView
        for In/Out/Directed/Multi. For Directed Graphs, `G.degree`
        counts both in and out going edges. `G.out_degree` and
        `G.in_degree` count only specific directions.
        Weighted degree using edge data attributes is provide via
        `V = G.degree(weight='attr_name')` where any string with the
        attribute name can be used. `weight=None` is the default.
        No set operations are implemented for degrees, use NodeView.

        The argument `nbunch` restricts iteration to nodes in nbunch.
        The DegreeView can still lookup any node even if nbunch is specified.

    EdgeView
    ========

        `V = G.edges` or `V = G.edges()` allows iteration over edges as well as
        `e in V`, set operations and edge data lookup `dd = G.edges[2, 3]`.
        Iteration is over 2-tuples `(u, v)` for Graph/DiGraph. For multigraphs
        edges 3-tuples `(u, v, key)` are the default but 2-tuples can be obtained
        via `V = G.edges(keys=False)`.

        Set operations for directed graphs treat the edges as a set of 2-tuples.
        For undirected graphs, 2-tuples are not a unique representation of edges.
        So long as the set being compared to contains unique representations
        of its edges, the set operations will act as expected. If the other
        set contains both `(0, 1)` and `(1, 0)` however, the result of set
        operations may contain both representations of the same edge.

    EdgeDataView
    ============

        Edge data can be reported using an EdgeDataView typically created
        by calling an EdgeView: `DV = G.edges(data='weight', default=1)`.
        The EdgeDataView allows iteration over edge tuples, membership checking
        but no set operations.

        Iteration depends on `data` and `default` and for multigraph `keys`
        If `data is False` (the default) then iterate over 2-tuples `(u, v)`.
        If `data is True` iterate over 3-tuples `(u, v, datadict)`.
        Otherwise iterate over `(u, v, datadict.get(data, default))`.
        For Multigraphs, if `keys is True`, replace `u, v` with `u, v, key`
        to create 3-tuples and 4-tuples.

        The argument `nbunch` restricts edges to those incident to nodes in nbunch.

CLASSES
    builtins.object
        DiDegreeView
            DegreeView
            DiMultiDegreeView
            InDegreeView
            InMultiDegreeView
            MultiDegreeView
            OutDegreeView
            OutMultiDegreeView
    collections.abc.Mapping(collections.abc.Collection)
        NodeView(collections.abc.Mapping, collections.abc.Set)
        OutEdgeView(collections.abc.Set, collections.abc.Mapping, EdgeViewABC)
            EdgeView
            InEdgeView
            OutMultiEdgeView
                InMultiEdgeView
                MultiEdgeView
    collections.abc.Set(collections.abc.Collection)
        NodeDataView
        NodeView(collections.abc.Mapping, collections.abc.Set)
        OutEdgeView(collections.abc.Set, collections.abc.Mapping, EdgeViewABC)
            EdgeView
            InEdgeView
            OutMultiEdgeView
                InMultiEdgeView
                MultiEdgeView
    EdgeViewABC(abc.ABC)
        OutEdgeDataView
            EdgeDataView
            InEdgeDataView
            OutMultiEdgeDataView
                InMultiEdgeDataView
                MultiEdgeDataView
        OutEdgeView(collections.abc.Set, collections.abc.Mapping, EdgeViewABC)
            EdgeView
            InEdgeView
            OutMultiEdgeView
                InMultiEdgeView
                MultiEdgeView

    class DegreeView(DiDegreeView)
     |  DegreeView(G, nbunch=None, weight=None)
     |
     |  A DegreeView class to act as G.degree for a NetworkX Graph
     |
     |  Typical usage focuses on iteration over `(node, degree)` pairs.
     |  The degree is by default the number of edges incident to the node.
     |  Optional argument `weight` enables weighted degree using the edge
     |  attribute named in the `weight` argument.  Reporting and iteration
     |  can also be restricted to a subset of nodes using `nbunch`.
     |
     |  Additional functionality include node lookup so that `G.degree[n]`
     |  reported the (possibly weighted) degree of node `n`. Calling the
     |  view creates a view with different arguments `nbunch` or `weight`.
     |
     |  Parameters
     |  ==========
     |  graph : NetworkX graph-like class
     |  nbunch : node, container of nodes, or None meaning all nodes (default=None)
     |  weight : string or None (default=None)
     |
     |  Notes
     |  -----
     |  DegreeView can still lookup any node even if nbunch is specified.
     |
     |  Examples
     |  --------
     |  >>> G = nx.path_graph(3)
     |  >>> DV = G.degree()
     |  >>> assert DV[2] == 1
     |  >>> assert G.degree[2] == 1
     |  >>> assert sum(deg for n, deg in DV) == 4
     |
     |  >>> DVweight = G.degree(weight="span")
     |  >>> G.add_edge(1, 2, span=34)
     |  >>> DVweight[2]
     |  34
     |  >>> DVweight[0]  #  default edge weight is 1
     |  1
     |  >>> sum(span for n, span in DVweight)  # sum weighted degrees
     |  70
     |
     |  >>> DVnbunch = G.degree(nbunch=(1, 2))
     |  >>> assert len(list(DVnbunch)) == 2  # iteration over nbunch only
     |
     |  Method resolution order:
     |      DegreeView
     |      DiDegreeView
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, n)
     |
     |  __iter__(self)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from DiDegreeView:
     |
     |  __call__(self, nbunch=None, weight=None)
     |      Call self as a function.
     |
     |  __init__(self, G, nbunch=None, weight=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from DiDegreeView:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class DiDegreeView(builtins.object)
     |  DiDegreeView(G, nbunch=None, weight=None)
     |
     |  A View class for degree of nodes in a NetworkX Graph
     |
     |  The functionality is like dict.items() with (node, degree) pairs.
     |  Additional functionality includes read-only lookup of node degree,
     |  and calling with optional features nbunch (for only a subset of nodes)
     |  and weight (use edge weights to compute degree).
     |
     |  Parameters
     |  ==========
     |  graph : NetworkX graph-like class
     |  nbunch : node, container of nodes, or None meaning all nodes (default=None)
     |  weight : bool or string (default=None)
     |
     |  Notes
     |  -----
     |  DegreeView can still lookup any node even if nbunch is specified.
     |
     |  Examples
     |  --------
     |  >>> G = nx.path_graph(3)
     |  >>> DV = G.degree()
     |  >>> assert DV[2] == 1
     |  >>> assert sum(deg for n, deg in DV) == 4
     |
     |  >>> DVweight = G.degree(weight="span")
     |  >>> G.add_edge(1, 2, span=34)
     |  >>> DVweight[2]
     |  34
     |  >>> DVweight[0]  #  default edge weight is 1
     |  1
     |  >>> sum(span for n, span in DVweight)  # sum weighted degrees
     |  70
     |
     |  >>> DVnbunch = G.degree(nbunch=(1, 2))
     |  >>> assert len(list(DVnbunch)) == 2  # iteration over nbunch only
     |
     |  Methods defined here:
     |
     |  __call__(self, nbunch=None, weight=None)
     |      Call self as a function.
     |
     |  __getitem__(self, n)
     |
     |  __init__(self, G, nbunch=None, weight=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors defined here:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class DiMultiDegreeView(DiDegreeView)
     |  DiMultiDegreeView(G, nbunch=None, weight=None)
     |
     |  A DegreeView class for MultiDiGraph; See DegreeView
     |
     |  Method resolution order:
     |      DiMultiDegreeView
     |      DiDegreeView
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, n)
     |
     |  __iter__(self)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from DiDegreeView:
     |
     |  __call__(self, nbunch=None, weight=None)
     |      Call self as a function.
     |
     |  __init__(self, G, nbunch=None, weight=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from DiDegreeView:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class EdgeDataView(OutEdgeDataView)
     |  EdgeDataView(viewer, nbunch=None, data=False, *, default=None)
     |
     |  A EdgeDataView class for edges of Graph
     |
     |  This view is primarily used to iterate over the edges reporting
     |  edges as node-tuples with edge data optionally reported. The
     |  argument `nbunch` allows restriction to edges incident to nodes
     |  in that container/singleton. The default (nbunch=None)
     |  reports all edges. The arguments `data` and `default` control
     |  what edge data is reported. The default `data is False` reports
     |  only node-tuples for each edge. If `data is True` the entire edge
     |  data dict is returned. Otherwise `data` is assumed to hold the name
     |  of the edge attribute to report with default `default` if  that
     |  edge attribute is not present.
     |
     |  Parameters
     |  ----------
     |  nbunch : container of nodes, node or None (default None)
     |  data : False, True or string (default False)
     |  default : default value (default None)
     |
     |  Examples
     |  --------
     |  >>> G = nx.path_graph(3)
     |  >>> G.add_edge(1, 2, foo="bar")
     |  >>> list(G.edges(data="foo", default="biz"))
     |  [(0, 1, 'biz'), (1, 2, 'bar')]
     |  >>> assert (0, 1, "biz") in G.edges(data="foo", default="biz")
     |
     |  Method resolution order:
     |      EdgeDataView
     |      OutEdgeDataView
     |      EdgeViewABC
     |      abc.ABC
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __contains__(self, e)
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutEdgeDataView:
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, viewer, nbunch=None, data=False, *, default=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from EdgeViewABC:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class EdgeView(OutEdgeView)
     |  EdgeView(G)
     |
     |  A EdgeView class for edges of a Graph
     |
     |  This densely packed View allows iteration over edges, data lookup
     |  like a dict and set operations on edges represented by node-tuples.
     |  In addition, edge data can be controlled by calling this object
     |  possibly creating an EdgeDataView. Typically edges are iterated over
     |  and reported as `(u, v)` node tuples or `(u, v, key)` node/key tuples
     |  for multigraphs. Those edge representations can also be using to
     |  lookup the data dict for any edge. Set operations also are available
     |  where those tuples are the elements of the set.
     |  Calling this object with optional arguments `data`, `default` and `keys`
     |  controls the form of the tuple (see EdgeDataView). Optional argument
     |  `nbunch` allows restriction to edges only involving certain nodes.
     |
     |  If `data is False` (the default) then iterate over 2-tuples `(u, v)`.
     |  If `data is True` iterate over 3-tuples `(u, v, datadict)`.
     |  Otherwise iterate over `(u, v, datadict.get(data, default))`.
     |  For Multigraphs, if `keys is True`, replace `u, v` with `u, v, key` above.
     |
     |  Parameters
     |  ==========
     |  graph : NetworkX graph-like class
     |  nbunch : (default= all nodes in graph) only report edges with these nodes
     |  keys : (only for MultiGraph. default=False) report edge key in tuple
     |  data : bool or string (default=False) see above
     |  default : object (default=None)
     |
     |  Examples
     |  ========
     |  >>> G = nx.path_graph(4)
     |  >>> EV = G.edges()
     |  >>> (2, 3) in EV
     |  True
     |  >>> for u, v in EV:
     |  ...     print((u, v))
     |  (0, 1)
     |  (1, 2)
     |  (2, 3)
     |  >>> assert EV & {(1, 2), (3, 4)} == {(1, 2)}
     |
     |  >>> EVdata = G.edges(data="color", default="aqua")
     |  >>> G.add_edge(2, 3, color="blue")
     |  >>> assert (2, 3, "blue") in EVdata
     |  >>> for u, v, c in EVdata:
     |  ...     print(f"({u}, {v}) has color: {c}")
     |  (0, 1) has color: aqua
     |  (1, 2) has color: aqua
     |  (2, 3) has color: blue
     |
     |  >>> EVnbunch = G.edges(nbunch=2)
     |  >>> assert (2, 3) in EVnbunch
     |  >>> assert (0, 1) not in EVnbunch
     |  >>> for u, v in EVnbunch:
     |  ...     assert u == 2 or v == 2
     |
     |  >>> MG = nx.path_graph(4, create_using=nx.MultiGraph)
     |  >>> EVmulti = MG.edges(keys=True)
     |  >>> (2, 3, 0) in EVmulti
     |  True
     |  >>> (2, 3) in EVmulti  # 2-tuples work even when keys is True
     |  True
     |  >>> key = MG.add_edge(2, 3)
     |  >>> for u, v, k in EVmulti:
     |  ...     print((u, v, k))
     |  (0, 1, 0)
     |  (1, 2, 0)
     |  (2, 3, 0)
     |  (2, 3, 1)
     |
     |  Method resolution order:
     |      EdgeView
     |      OutEdgeView
     |      collections.abc.Set
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      EdgeViewABC
     |      abc.ABC
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __contains__(self, e)
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  dataview = <class 'networkx.classes.reportviews.EdgeDataView'>
     |      A EdgeDataView class for edges of Graph
     |
     |      This view is primarily used to iterate over the edges reporting
     |      edges as node-tuples with edge data optionally reported. The
     |      argument `nbunch` allows restriction to edges incident to nodes
     |      in that container/singleton. The default (nbunch=None)
     |      reports all edges. The arguments `data` and `default` control
     |      what edge data is reported. The default `data is False` reports
     |      only node-tuples for each edge. If `data is True` the entire edge
     |      data dict is returned. Otherwise `data` is assumed to hold the name
     |      of the edge attribute to report with default `default` if  that
     |      edge attribute is not present.
     |
     |      Parameters
     |      ----------
     |      nbunch : container of nodes, node or None (default None)
     |      data : False, True or string (default False)
     |      default : default value (default None)
     |
     |      Examples
     |      --------
     |      >>> G = nx.path_graph(3)
     |      >>> G.add_edge(1, 2, foo="bar")
     |      >>> list(G.edges(data="foo", default="biz"))
     |      [(0, 1, 'biz'), (1, 2, 'bar')]
     |      >>> assert (0, 1, "biz") in G.edges(data="foo", default="biz")
     |
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutEdgeView:
     |
     |  __call__(self, nbunch=None, data=False, *, default=None)
     |      Call self as a function.
     |
     |  __getitem__(self, e)
     |      # Mapping Methods
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, G)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  data(self, data=True, default=None, nbunch=None)
     |      Return a read-only view of edge data.
     |
     |      Parameters
     |      ----------
     |      data : bool or edge attribute key
     |          If ``data=True``, then the data view maps each edge to a dictionary
     |          containing all of its attributes. If `data` is a key in the edge
     |          dictionary, then the data view maps each edge to its value for
     |          the keyed attribute. In this case, if the edge doesn't have the
     |          attribute, the `default` value is returned.
     |      default : object, default=None
     |          The value used when an edge does not have a specific attribute
     |      nbunch : container of nodes, optional (default=None)
     |          Allows restriction to edges only involving certain nodes. All edges
     |          are considered by default.
     |
     |      Returns
     |      -------
     |      dataview
     |          Returns an `EdgeDataView` for undirected Graphs, `OutEdgeDataView`
     |          for DiGraphs, `MultiEdgeDataView` for MultiGraphs and
     |          `OutMultiEdgeDataView` for MultiDiGraphs.
     |
     |      Notes
     |      -----
     |      If ``data=False``, returns an `EdgeView` without any edge data.
     |
     |      See Also
     |      --------
     |      EdgeDataView
     |      OutEdgeDataView
     |      MultiEdgeDataView
     |      OutMultiEdgeDataView
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()
     |      >>> G.add_edges_from(
     |      ...     [
     |      ...         (0, 1, {"dist": 3, "capacity": 20}),
     |      ...         (1, 2, {"dist": 4}),
     |      ...         (2, 0, {"dist": 5}),
     |      ...     ]
     |      ... )
     |
     |      Accessing edge data with ``data=True`` (the default) returns an
     |      edge data view object listing each edge with all of its attributes:
     |
     |      >>> G.edges.data()
     |      EdgeDataView([(0, 1, {'dist': 3, 'capacity': 20}), (0, 2, {'dist': 5}), (1, 2, {'dist': 4})])
     |
     |      If `data` represents a key in the edge attribute dict, a dataview listing
     |      each edge with its value for that specific key is returned:
     |
     |      >>> G.edges.data("dist")
     |      EdgeDataView([(0, 1, 3), (0, 2, 5), (1, 2, 4)])
     |
     |      `nbunch` can be used to limit the edges:
     |
     |      >>> G.edges.data("dist", nbunch=[0])
     |      EdgeDataView([(0, 1, 3), (0, 2, 5)])
     |
     |      If a specific key is not found in an edge attribute dict, the value
     |      specified by `default` is used:
     |
     |      >>> G.edges.data("capacity")
     |      EdgeDataView([(0, 1, 20), (0, 2, None), (1, 2, None)])
     |
     |      Note that there is no check that the `data` key is present in any of
     |      the edge attribute dictionaries:
     |
     |      >>> G.edges.data("speed")
     |      EdgeDataView([(0, 1, None), (0, 2, None), (1, 2, None)])
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from OutEdgeView:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Set:
     |
     |  __and__(self, other)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  __ge__(self, other)
     |      Return self>=value.
     |
     |  __gt__(self, other)
     |      Return self>value.
     |
     |  __le__(self, other)
     |      Return self<=value.
     |
     |  __lt__(self, other)
     |      Return self<value.
     |
     |  __or__(self, other)
     |      Return self|value.
     |
     |  __rand__ = __and__(self, other)
     |
     |  __ror__ = __or__(self, other)
     |
     |  __rsub__(self, other)
     |
     |  __rxor__ = __xor__(self, other)
     |
     |  __sub__(self, other)
     |
     |  __xor__(self, other)
     |
     |  isdisjoint(self, other)
     |      Return True if two sets have a null intersection.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Set:
     |
     |  __hash__ = None
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class InDegreeView(DiDegreeView)
     |  InDegreeView(G, nbunch=None, weight=None)
     |
     |  A DegreeView class to report in_degree for a DiGraph; See DegreeView
     |
     |  Method resolution order:
     |      InDegreeView
     |      DiDegreeView
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, n)
     |
     |  __iter__(self)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from DiDegreeView:
     |
     |  __call__(self, nbunch=None, weight=None)
     |      Call self as a function.
     |
     |  __init__(self, G, nbunch=None, weight=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from DiDegreeView:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class InEdgeDataView(OutEdgeDataView)
     |  InEdgeDataView(viewer, nbunch=None, data=False, *, default=None)
     |
     |  An EdgeDataView class for outward edges of DiGraph; See EdgeDataView
     |
     |  Method resolution order:
     |      InEdgeDataView
     |      OutEdgeDataView
     |      EdgeViewABC
     |      abc.ABC
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __contains__(self, e)
     |
     |  __iter__(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutEdgeDataView:
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, viewer, nbunch=None, data=False, *, default=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from EdgeViewABC:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class InEdgeView(OutEdgeView)
     |  InEdgeView(G)
     |
     |  A EdgeView class for inward edges of a DiGraph
     |
     |  Method resolution order:
     |      InEdgeView
     |      OutEdgeView
     |      collections.abc.Set
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      EdgeViewABC
     |      abc.ABC
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __contains__(self, e)
     |
     |  __getitem__(self, e)
     |
     |  __init__(self, G)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __setstate__(self, state)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  dataview = <class 'networkx.classes.reportviews.InEdgeDataView'>
     |      An EdgeDataView class for outward edges of DiGraph; See EdgeDataView
     |
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutEdgeView:
     |
     |  __call__(self, nbunch=None, data=False, *, default=None)
     |      Call self as a function.
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __len__(self)
     |      # Set methods
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  data(self, data=True, default=None, nbunch=None)
     |      Return a read-only view of edge data.
     |
     |      Parameters
     |      ----------
     |      data : bool or edge attribute key
     |          If ``data=True``, then the data view maps each edge to a dictionary
     |          containing all of its attributes. If `data` is a key in the edge
     |          dictionary, then the data view maps each edge to its value for
     |          the keyed attribute. In this case, if the edge doesn't have the
     |          attribute, the `default` value is returned.
     |      default : object, default=None
     |          The value used when an edge does not have a specific attribute
     |      nbunch : container of nodes, optional (default=None)
     |          Allows restriction to edges only involving certain nodes. All edges
     |          are considered by default.
     |
     |      Returns
     |      -------
     |      dataview
     |          Returns an `EdgeDataView` for undirected Graphs, `OutEdgeDataView`
     |          for DiGraphs, `MultiEdgeDataView` for MultiGraphs and
     |          `OutMultiEdgeDataView` for MultiDiGraphs.
     |
     |      Notes
     |      -----
     |      If ``data=False``, returns an `EdgeView` without any edge data.
     |
     |      See Also
     |      --------
     |      EdgeDataView
     |      OutEdgeDataView
     |      MultiEdgeDataView
     |      OutMultiEdgeDataView
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()
     |      >>> G.add_edges_from(
     |      ...     [
     |      ...         (0, 1, {"dist": 3, "capacity": 20}),
     |      ...         (1, 2, {"dist": 4}),
     |      ...         (2, 0, {"dist": 5}),
     |      ...     ]
     |      ... )
     |
     |      Accessing edge data with ``data=True`` (the default) returns an
     |      edge data view object listing each edge with all of its attributes:
     |
     |      >>> G.edges.data()
     |      EdgeDataView([(0, 1, {'dist': 3, 'capacity': 20}), (0, 2, {'dist': 5}), (1, 2, {'dist': 4})])
     |
     |      If `data` represents a key in the edge attribute dict, a dataview listing
     |      each edge with its value for that specific key is returned:
     |
     |      >>> G.edges.data("dist")
     |      EdgeDataView([(0, 1, 3), (0, 2, 5), (1, 2, 4)])
     |
     |      `nbunch` can be used to limit the edges:
     |
     |      >>> G.edges.data("dist", nbunch=[0])
     |      EdgeDataView([(0, 1, 3), (0, 2, 5)])
     |
     |      If a specific key is not found in an edge attribute dict, the value
     |      specified by `default` is used:
     |
     |      >>> G.edges.data("capacity")
     |      EdgeDataView([(0, 1, 20), (0, 2, None), (1, 2, None)])
     |
     |      Note that there is no check that the `data` key is present in any of
     |      the edge attribute dictionaries:
     |
     |      >>> G.edges.data("speed")
     |      EdgeDataView([(0, 1, None), (0, 2, None), (1, 2, None)])
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from OutEdgeView:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Set:
     |
     |  __and__(self, other)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  __ge__(self, other)
     |      Return self>=value.
     |
     |  __gt__(self, other)
     |      Return self>value.
     |
     |  __le__(self, other)
     |      Return self<=value.
     |
     |  __lt__(self, other)
     |      Return self<value.
     |
     |  __or__(self, other)
     |      Return self|value.
     |
     |  __rand__ = __and__(self, other)
     |
     |  __ror__ = __or__(self, other)
     |
     |  __rsub__(self, other)
     |
     |  __rxor__ = __xor__(self, other)
     |
     |  __sub__(self, other)
     |
     |  __xor__(self, other)
     |
     |  isdisjoint(self, other)
     |      Return True if two sets have a null intersection.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Set:
     |
     |  __hash__ = None
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class InMultiDegreeView(DiDegreeView)
     |  InMultiDegreeView(G, nbunch=None, weight=None)
     |
     |  A DegreeView class for inward degree of MultiDiGraph; See DegreeView
     |
     |  Method resolution order:
     |      InMultiDegreeView
     |      DiDegreeView
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, n)
     |
     |  __iter__(self)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from DiDegreeView:
     |
     |  __call__(self, nbunch=None, weight=None)
     |      Call self as a function.
     |
     |  __init__(self, G, nbunch=None, weight=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from DiDegreeView:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class InMultiEdgeDataView(OutMultiEdgeDataView)
     |  InMultiEdgeDataView(viewer, nbunch=None, data=False, *, default=None, keys=False)
     |
     |  An EdgeDataView for inward edges of MultiDiGraph; See EdgeDataView
     |
     |  Method resolution order:
     |      InMultiEdgeDataView
     |      OutMultiEdgeDataView
     |      OutEdgeDataView
     |      EdgeViewABC
     |      abc.ABC
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __contains__(self, e)
     |
     |  __iter__(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutMultiEdgeDataView:
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, viewer, nbunch=None, data=False, *, default=None, keys=False)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __len__(self)
     |
     |  __setstate__(self, state)
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from OutMultiEdgeDataView:
     |
     |  keys
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutEdgeDataView:
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from EdgeViewABC:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class InMultiEdgeView(OutMultiEdgeView)
     |  InMultiEdgeView(G)
     |
     |  A EdgeView class for inward edges of a MultiDiGraph
     |
     |  Method resolution order:
     |      InMultiEdgeView
     |      OutMultiEdgeView
     |      OutEdgeView
     |      collections.abc.Set
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      EdgeViewABC
     |      abc.ABC
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __contains__(self, e)
     |
     |  __getitem__(self, e)
     |
     |  __init__(self, G)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __setstate__(self, state)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  dataview = <class 'networkx.classes.reportviews.InMultiEdgeDataView'>
     |      An EdgeDataView for inward edges of MultiDiGraph; See EdgeDataView
     |
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutMultiEdgeView:
     |
     |  __call__(self, nbunch=None, data=False, *, default=None, keys=False)
     |      Call self as a function.
     |
     |  __len__(self)
     |
     |  data(self, data=True, default=None, nbunch=None, keys=False)
     |      Return a read-only view of edge data.
     |
     |      Parameters
     |      ----------
     |      data : bool or edge attribute key
     |          If ``data=True``, then the data view maps each edge to a dictionary
     |          containing all of its attributes. If `data` is a key in the edge
     |          dictionary, then the data view maps each edge to its value for
     |          the keyed attribute. In this case, if the edge doesn't have the
     |          attribute, the `default` value is returned.
     |      default : object, default=None
     |          The value used when an edge does not have a specific attribute
     |      nbunch : container of nodes, optional (default=None)
     |          Allows restriction to edges only involving certain nodes. All edges
     |          are considered by default.
     |
     |      Returns
     |      -------
     |      dataview
     |          Returns an `EdgeDataView` for undirected Graphs, `OutEdgeDataView`
     |          for DiGraphs, `MultiEdgeDataView` for MultiGraphs and
     |          `OutMultiEdgeDataView` for MultiDiGraphs.
     |
     |      Notes
     |      -----
     |      If ``data=False``, returns an `EdgeView` without any edge data.
     |
     |      See Also
     |      --------
     |      EdgeDataView
     |      OutEdgeDataView
     |      MultiEdgeDataView
     |      OutMultiEdgeDataView
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()
     |      >>> G.add_edges_from(
     |      ...     [
     |      ...         (0, 1, {"dist": 3, "capacity": 20}),
     |      ...         (1, 2, {"dist": 4}),
     |      ...         (2, 0, {"dist": 5}),
     |      ...     ]
     |      ... )
     |
     |      Accessing edge data with ``data=True`` (the default) returns an
     |      edge data view object listing each edge with all of its attributes:
     |
     |      >>> G.edges.data()
     |      EdgeDataView([(0, 1, {'dist': 3, 'capacity': 20}), (0, 2, {'dist': 5}), (1, 2, {'dist': 4})])
     |
     |      If `data` represents a key in the edge attribute dict, a dataview listing
     |      each edge with its value for that specific key is returned:
     |
     |      >>> G.edges.data("dist")
     |      EdgeDataView([(0, 1, 3), (0, 2, 5), (1, 2, 4)])
     |
     |      `nbunch` can be used to limit the edges:
     |
     |      >>> G.edges.data("dist", nbunch=[0])
     |      EdgeDataView([(0, 1, 3), (0, 2, 5)])
     |
     |      If a specific key is not found in an edge attribute dict, the value
     |      specified by `default` is used:
     |
     |      >>> G.edges.data("capacity")
     |      EdgeDataView([(0, 1, 20), (0, 2, None), (1, 2, None)])
     |
     |      Note that there is no check that the `data` key is present in any of
     |      the edge attribute dictionaries:
     |
     |      >>> G.edges.data("speed")
     |      EdgeDataView([(0, 1, None), (0, 2, None), (1, 2, None)])
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutEdgeView:
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from OutEdgeView:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Set:
     |
     |  __and__(self, other)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  __ge__(self, other)
     |      Return self>=value.
     |
     |  __gt__(self, other)
     |      Return self>value.
     |
     |  __le__(self, other)
     |      Return self<=value.
     |
     |  __lt__(self, other)
     |      Return self<value.
     |
     |  __or__(self, other)
     |      Return self|value.
     |
     |  __rand__ = __and__(self, other)
     |
     |  __ror__ = __or__(self, other)
     |
     |  __rsub__(self, other)
     |
     |  __rxor__ = __xor__(self, other)
     |
     |  __sub__(self, other)
     |
     |  __xor__(self, other)
     |
     |  isdisjoint(self, other)
     |      Return True if two sets have a null intersection.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Set:
     |
     |  __hash__ = None
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class MultiDegreeView(DiDegreeView)
     |  MultiDegreeView(G, nbunch=None, weight=None)
     |
     |  A DegreeView class for undirected multigraphs; See DegreeView
     |
     |  Method resolution order:
     |      MultiDegreeView
     |      DiDegreeView
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, n)
     |
     |  __iter__(self)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from DiDegreeView:
     |
     |  __call__(self, nbunch=None, weight=None)
     |      Call self as a function.
     |
     |  __init__(self, G, nbunch=None, weight=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from DiDegreeView:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class MultiEdgeDataView(OutMultiEdgeDataView)
     |  MultiEdgeDataView(viewer, nbunch=None, data=False, *, default=None, keys=False)
     |
     |  An EdgeDataView class for edges of MultiGraph; See EdgeDataView
     |
     |  Method resolution order:
     |      MultiEdgeDataView
     |      OutMultiEdgeDataView
     |      OutEdgeDataView
     |      EdgeViewABC
     |      abc.ABC
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __contains__(self, e)
     |
     |  __iter__(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutMultiEdgeDataView:
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, viewer, nbunch=None, data=False, *, default=None, keys=False)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __len__(self)
     |
     |  __setstate__(self, state)
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from OutMultiEdgeDataView:
     |
     |  keys
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutEdgeDataView:
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from EdgeViewABC:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class MultiEdgeView(OutMultiEdgeView)
     |  MultiEdgeView(G)
     |
     |  A EdgeView class for edges of a MultiGraph
     |
     |  Method resolution order:
     |      MultiEdgeView
     |      OutMultiEdgeView
     |      OutEdgeView
     |      collections.abc.Set
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      EdgeViewABC
     |      abc.ABC
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  dataview = <class 'networkx.classes.reportviews.MultiEdgeDataView'>
     |      An EdgeDataView class for edges of MultiGraph; See EdgeDataView
     |
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutMultiEdgeView:
     |
     |  __call__(self, nbunch=None, data=False, *, default=None, keys=False)
     |      Call self as a function.
     |
     |  __contains__(self, e)
     |
     |  __getitem__(self, e)
     |
     |  data(self, data=True, default=None, nbunch=None, keys=False)
     |      Return a read-only view of edge data.
     |
     |      Parameters
     |      ----------
     |      data : bool or edge attribute key
     |          If ``data=True``, then the data view maps each edge to a dictionary
     |          containing all of its attributes. If `data` is a key in the edge
     |          dictionary, then the data view maps each edge to its value for
     |          the keyed attribute. In this case, if the edge doesn't have the
     |          attribute, the `default` value is returned.
     |      default : object, default=None
     |          The value used when an edge does not have a specific attribute
     |      nbunch : container of nodes, optional (default=None)
     |          Allows restriction to edges only involving certain nodes. All edges
     |          are considered by default.
     |
     |      Returns
     |      -------
     |      dataview
     |          Returns an `EdgeDataView` for undirected Graphs, `OutEdgeDataView`
     |          for DiGraphs, `MultiEdgeDataView` for MultiGraphs and
     |          `OutMultiEdgeDataView` for MultiDiGraphs.
     |
     |      Notes
     |      -----
     |      If ``data=False``, returns an `EdgeView` without any edge data.
     |
     |      See Also
     |      --------
     |      EdgeDataView
     |      OutEdgeDataView
     |      MultiEdgeDataView
     |      OutMultiEdgeDataView
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()
     |      >>> G.add_edges_from(
     |      ...     [
     |      ...         (0, 1, {"dist": 3, "capacity": 20}),
     |      ...         (1, 2, {"dist": 4}),
     |      ...         (2, 0, {"dist": 5}),
     |      ...     ]
     |      ... )
     |
     |      Accessing edge data with ``data=True`` (the default) returns an
     |      edge data view object listing each edge with all of its attributes:
     |
     |      >>> G.edges.data()
     |      EdgeDataView([(0, 1, {'dist': 3, 'capacity': 20}), (0, 2, {'dist': 5}), (1, 2, {'dist': 4})])
     |
     |      If `data` represents a key in the edge attribute dict, a dataview listing
     |      each edge with its value for that specific key is returned:
     |
     |      >>> G.edges.data("dist")
     |      EdgeDataView([(0, 1, 3), (0, 2, 5), (1, 2, 4)])
     |
     |      `nbunch` can be used to limit the edges:
     |
     |      >>> G.edges.data("dist", nbunch=[0])
     |      EdgeDataView([(0, 1, 3), (0, 2, 5)])
     |
     |      If a specific key is not found in an edge attribute dict, the value
     |      specified by `default` is used:
     |
     |      >>> G.edges.data("capacity")
     |      EdgeDataView([(0, 1, 20), (0, 2, None), (1, 2, None)])
     |
     |      Note that there is no check that the `data` key is present in any of
     |      the edge attribute dictionaries:
     |
     |      >>> G.edges.data("speed")
     |      EdgeDataView([(0, 1, None), (0, 2, None), (1, 2, None)])
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutEdgeView:
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, G)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from OutEdgeView:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Set:
     |
     |  __and__(self, other)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  __ge__(self, other)
     |      Return self>=value.
     |
     |  __gt__(self, other)
     |      Return self>value.
     |
     |  __le__(self, other)
     |      Return self<=value.
     |
     |  __lt__(self, other)
     |      Return self<value.
     |
     |  __or__(self, other)
     |      Return self|value.
     |
     |  __rand__ = __and__(self, other)
     |
     |  __ror__ = __or__(self, other)
     |
     |  __rsub__(self, other)
     |
     |  __rxor__ = __xor__(self, other)
     |
     |  __sub__(self, other)
     |
     |  __xor__(self, other)
     |
     |  isdisjoint(self, other)
     |      Return True if two sets have a null intersection.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Set:
     |
     |  __hash__ = None
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class NodeDataView(collections.abc.Set)
     |  NodeDataView(nodedict, data=False, default=None)
     |
     |  A DataView class for nodes of a NetworkX Graph
     |
     |  The main use for this class is to iterate through node-data pairs.
     |  The data can be the entire data-dictionary for each node, or it
     |  can be a specific attribute (with default) for each node.
     |  Set operations are enabled with NodeDataView, but don't work in
     |  cases where the data is not hashable. Use with caution.
     |  Typically, set operations on nodes use NodeView, not NodeDataView.
     |  That is, they use `G.nodes` instead of `G.nodes(data='foo')`.
     |
     |  Parameters
     |  ==========
     |  graph : NetworkX graph-like class
     |  data : bool or string (default=False)
     |  default : object (default=None)
     |
     |  Method resolution order:
     |      NodeDataView
     |      collections.abc.Set
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __contains__(self, n)
     |
     |  __getitem__(self, n)
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, nodedict, data=False, default=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Set:
     |
     |  __and__(self, other)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  __ge__(self, other)
     |      Return self>=value.
     |
     |  __gt__(self, other)
     |      Return self>value.
     |
     |  __le__(self, other)
     |      Return self<=value.
     |
     |  __lt__(self, other)
     |      Return self<value.
     |
     |  __or__(self, other)
     |      Return self|value.
     |
     |  __rand__ = __and__(self, other)
     |
     |  __ror__ = __or__(self, other)
     |
     |  __rsub__(self, other)
     |
     |  __rxor__ = __xor__(self, other)
     |
     |  __sub__(self, other)
     |
     |  __xor__(self, other)
     |
     |  isdisjoint(self, other)
     |      Return True if two sets have a null intersection.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Set:
     |
     |  __hash__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class NodeView(collections.abc.Mapping, collections.abc.Set)
     |  NodeView(graph)
     |
     |  A NodeView class to act as G.nodes for a NetworkX Graph
     |
     |  Set operations act on the nodes without considering data.
     |  Iteration is over nodes. Node data can be looked up like a dict.
     |  Use NodeDataView to iterate over node data or to specify a data
     |  attribute for lookup. NodeDataView is created by calling the NodeView.
     |
     |  Parameters
     |  ----------
     |  graph : NetworkX graph-like class
     |
     |  Examples
     |  --------
     |  >>> G = nx.path_graph(3)
     |  >>> NV = G.nodes()
     |  >>> 2 in NV
     |  True
     |  >>> for n in NV:
     |  ...     print(n)
     |  0
     |  1
     |  2
     |  >>> assert NV & {1, 2, 3} == {1, 2}
     |
     |  >>> G.add_node(2, color="blue")
     |  >>> NV[2]
     |  {'color': 'blue'}
     |  >>> G.add_node(8, color="red")
     |  >>> NDV = G.nodes(data=True)
     |  >>> (2, NV[2]) in NDV
     |  True
     |  >>> for n, dd in NDV:
     |  ...     print((n, dd.get("color", "aqua")))
     |  (0, 'aqua')
     |  (1, 'aqua')
     |  (2, 'blue')
     |  (8, 'red')
     |  >>> NDV[2] == NV[2]
     |  True
     |
     |  >>> NVdata = G.nodes(data="color", default="aqua")
     |  >>> (2, NVdata[2]) in NVdata
     |  True
     |  >>> for n, dd in NVdata:
     |  ...     print((n, dd))
     |  (0, 'aqua')
     |  (1, 'aqua')
     |  (2, 'blue')
     |  (8, 'red')
     |  >>> NVdata[2] == NV[2]  # NVdata gets 'color', NV gets datadict
     |  False
     |
     |  Method resolution order:
     |      NodeView
     |      collections.abc.Mapping
     |      collections.abc.Set
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __call__(self, data=False, default=None)
     |      Call self as a function.
     |
     |  __contains__(self, n)
     |      # Set methods
     |
     |  __getitem__(self, n)
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, graph)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |      # Mapping methods
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  data(self, data=True, default=None)
     |      Return a read-only view of node data.
     |
     |      Parameters
     |      ----------
     |      data : bool or node data key, default=True
     |          If ``data=True`` (the default), return a `NodeDataView` object that
     |          maps each node to *all* of its attributes. `data` may also be an
     |          arbitrary key, in which case the `NodeDataView` maps each node to
     |          the value for the keyed attribute. In this case, if a node does
     |          not have the `data` attribute, the `default` value is used.
     |      default : object, default=None
     |          The value used when a node does not have a specific attribute.
     |
     |      Returns
     |      -------
     |      NodeDataView
     |          The layout of the returned NodeDataView depends on the value of the
     |          `data` parameter.
     |
     |      Notes
     |      -----
     |      If ``data=False``, returns a `NodeView` object without data.
     |
     |      See Also
     |      --------
     |      NodeDataView
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()
     |      >>> G.add_nodes_from(
     |      ...     [
     |      ...         (0, {"color": "red", "weight": 10}),
     |      ...         (1, {"color": "blue"}),
     |      ...         (2, {"color": "yellow", "weight": 2}),
     |      ...     ]
     |      ... )
     |
     |      Accessing node data with ``data=True`` (the default) returns a
     |      NodeDataView mapping each node to all of its attributes:
     |
     |      >>> G.nodes.data()
     |      NodeDataView({0: {'color': 'red', 'weight': 10}, 1: {'color': 'blue'}, 2: {'color': 'yellow', 'weight': 2}})
     |
     |      If `data` represents  a key in the node attribute dict, a NodeDataView mapping
     |      the nodes to the value for that specific key is returned:
     |
     |      >>> G.nodes.data("color")
     |      NodeDataView({0: 'red', 1: 'blue', 2: 'yellow'}, data='color')
     |
     |      If a specific key is not found in an attribute dict, the value specified
     |      by `default` is returned:
     |
     |      >>> G.nodes.data("weight", default=-999)
     |      NodeDataView({0: 10, 1: -999, 2: 2}, data='weight')
     |
     |      Note that there is no check that the `data` key is in any of the
     |      node attribute dictionaries:
     |
     |      >>> G.nodes.data("height")
     |      NodeDataView({0: None, 1: None, 2: None}, data='height')
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __hash__ = None
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Set:
     |
     |  __and__(self, other)
     |
     |  __ge__(self, other)
     |      Return self>=value.
     |
     |  __gt__(self, other)
     |      Return self>value.
     |
     |  __le__(self, other)
     |      Return self<=value.
     |
     |  __lt__(self, other)
     |      Return self<value.
     |
     |  __or__(self, other)
     |      Return self|value.
     |
     |  __rand__ = __and__(self, other)
     |
     |  __ror__ = __or__(self, other)
     |
     |  __rsub__(self, other)
     |
     |  __rxor__ = __xor__(self, other)
     |
     |  __sub__(self, other)
     |
     |  __xor__(self, other)
     |
     |  isdisjoint(self, other)
     |      Return True if two sets have a null intersection.
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class OutDegreeView(DiDegreeView)
     |  OutDegreeView(G, nbunch=None, weight=None)
     |
     |  A DegreeView class to report out_degree for a DiGraph; See DegreeView
     |
     |  Method resolution order:
     |      OutDegreeView
     |      DiDegreeView
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, n)
     |
     |  __iter__(self)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from DiDegreeView:
     |
     |  __call__(self, nbunch=None, weight=None)
     |      Call self as a function.
     |
     |  __init__(self, G, nbunch=None, weight=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from DiDegreeView:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class OutEdgeDataView(EdgeViewABC)
     |  OutEdgeDataView(viewer, nbunch=None, data=False, *, default=None)
     |
     |  EdgeDataView for outward edges of DiGraph; See EdgeDataView
     |
     |  Method resolution order:
     |      OutEdgeDataView
     |      EdgeViewABC
     |      abc.ABC
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __contains__(self, e)
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, viewer, nbunch=None, data=False, *, default=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from EdgeViewABC:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class OutEdgeView(collections.abc.Set, collections.abc.Mapping, EdgeViewABC)
     |  OutEdgeView(G)
     |
     |  A EdgeView class for outward edges of a DiGraph
     |
     |  Method resolution order:
     |      OutEdgeView
     |      collections.abc.Set
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      EdgeViewABC
     |      abc.ABC
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __call__(self, nbunch=None, data=False, *, default=None)
     |      Call self as a function.
     |
     |  __contains__(self, e)
     |
     |  __getitem__(self, e)
     |      # Mapping Methods
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, G)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |      # Set methods
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  data(self, data=True, default=None, nbunch=None)
     |      Return a read-only view of edge data.
     |
     |      Parameters
     |      ----------
     |      data : bool or edge attribute key
     |          If ``data=True``, then the data view maps each edge to a dictionary
     |          containing all of its attributes. If `data` is a key in the edge
     |          dictionary, then the data view maps each edge to its value for
     |          the keyed attribute. In this case, if the edge doesn't have the
     |          attribute, the `default` value is returned.
     |      default : object, default=None
     |          The value used when an edge does not have a specific attribute
     |      nbunch : container of nodes, optional (default=None)
     |          Allows restriction to edges only involving certain nodes. All edges
     |          are considered by default.
     |
     |      Returns
     |      -------
     |      dataview
     |          Returns an `EdgeDataView` for undirected Graphs, `OutEdgeDataView`
     |          for DiGraphs, `MultiEdgeDataView` for MultiGraphs and
     |          `OutMultiEdgeDataView` for MultiDiGraphs.
     |
     |      Notes
     |      -----
     |      If ``data=False``, returns an `EdgeView` without any edge data.
     |
     |      See Also
     |      --------
     |      EdgeDataView
     |      OutEdgeDataView
     |      MultiEdgeDataView
     |      OutMultiEdgeDataView
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()
     |      >>> G.add_edges_from(
     |      ...     [
     |      ...         (0, 1, {"dist": 3, "capacity": 20}),
     |      ...         (1, 2, {"dist": 4}),
     |      ...         (2, 0, {"dist": 5}),
     |      ...     ]
     |      ... )
     |
     |      Accessing edge data with ``data=True`` (the default) returns an
     |      edge data view object listing each edge with all of its attributes:
     |
     |      >>> G.edges.data()
     |      EdgeDataView([(0, 1, {'dist': 3, 'capacity': 20}), (0, 2, {'dist': 5}), (1, 2, {'dist': 4})])
     |
     |      If `data` represents a key in the edge attribute dict, a dataview listing
     |      each edge with its value for that specific key is returned:
     |
     |      >>> G.edges.data("dist")
     |      EdgeDataView([(0, 1, 3), (0, 2, 5), (1, 2, 4)])
     |
     |      `nbunch` can be used to limit the edges:
     |
     |      >>> G.edges.data("dist", nbunch=[0])
     |      EdgeDataView([(0, 1, 3), (0, 2, 5)])
     |
     |      If a specific key is not found in an edge attribute dict, the value
     |      specified by `default` is used:
     |
     |      >>> G.edges.data("capacity")
     |      EdgeDataView([(0, 1, 20), (0, 2, None), (1, 2, None)])
     |
     |      Note that there is no check that the `data` key is present in any of
     |      the edge attribute dictionaries:
     |
     |      >>> G.edges.data("speed")
     |      EdgeDataView([(0, 1, None), (0, 2, None), (1, 2, None)])
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors defined here:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  dataview = <class 'networkx.classes.reportviews.OutEdgeDataView'>
     |      EdgeDataView for outward edges of DiGraph; See EdgeDataView
     |
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Set:
     |
     |  __and__(self, other)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  __ge__(self, other)
     |      Return self>=value.
     |
     |  __gt__(self, other)
     |      Return self>value.
     |
     |  __le__(self, other)
     |      Return self<=value.
     |
     |  __lt__(self, other)
     |      Return self<value.
     |
     |  __or__(self, other)
     |      Return self|value.
     |
     |  __rand__ = __and__(self, other)
     |
     |  __ror__ = __or__(self, other)
     |
     |  __rsub__(self, other)
     |
     |  __rxor__ = __xor__(self, other)
     |
     |  __sub__(self, other)
     |
     |  __xor__(self, other)
     |
     |  isdisjoint(self, other)
     |      Return True if two sets have a null intersection.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Set:
     |
     |  __hash__ = None
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

    class OutMultiDegreeView(DiDegreeView)
     |  OutMultiDegreeView(G, nbunch=None, weight=None)
     |
     |  A DegreeView class for outward degree of MultiDiGraph; See DegreeView
     |
     |  Method resolution order:
     |      OutMultiDegreeView
     |      DiDegreeView
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __getitem__(self, n)
     |
     |  __iter__(self)
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from DiDegreeView:
     |
     |  __call__(self, nbunch=None, weight=None)
     |      Call self as a function.
     |
     |  __init__(self, G, nbunch=None, weight=None)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __len__(self)
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from DiDegreeView:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class OutMultiEdgeDataView(OutEdgeDataView)
     |  OutMultiEdgeDataView(viewer, nbunch=None, data=False, *, default=None, keys=False)
     |
     |  An EdgeDataView for outward edges of MultiDiGraph; See EdgeDataView
     |
     |  Method resolution order:
     |      OutMultiEdgeDataView
     |      OutEdgeDataView
     |      EdgeViewABC
     |      abc.ABC
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __contains__(self, e)
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, viewer, nbunch=None, data=False, *, default=None, keys=False)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  __setstate__(self, state)
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors defined here:
     |
     |  keys
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutEdgeDataView:
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from EdgeViewABC:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object

    class OutMultiEdgeView(OutEdgeView)
     |  OutMultiEdgeView(G)
     |
     |  A EdgeView class for outward edges of a MultiDiGraph
     |
     |  Method resolution order:
     |      OutMultiEdgeView
     |      OutEdgeView
     |      collections.abc.Set
     |      collections.abc.Mapping
     |      collections.abc.Collection
     |      collections.abc.Sized
     |      collections.abc.Iterable
     |      collections.abc.Container
     |      EdgeViewABC
     |      abc.ABC
     |      builtins.object
     |
     |  Methods defined here:
     |
     |  __call__(self, nbunch=None, data=False, *, default=None, keys=False)
     |      Call self as a function.
     |
     |  __contains__(self, e)
     |
     |  __getitem__(self, e)
     |
     |  __iter__(self)
     |
     |  __len__(self)
     |
     |  data(self, data=True, default=None, nbunch=None, keys=False)
     |      Return a read-only view of edge data.
     |
     |      Parameters
     |      ----------
     |      data : bool or edge attribute key
     |          If ``data=True``, then the data view maps each edge to a dictionary
     |          containing all of its attributes. If `data` is a key in the edge
     |          dictionary, then the data view maps each edge to its value for
     |          the keyed attribute. In this case, if the edge doesn't have the
     |          attribute, the `default` value is returned.
     |      default : object, default=None
     |          The value used when an edge does not have a specific attribute
     |      nbunch : container of nodes, optional (default=None)
     |          Allows restriction to edges only involving certain nodes. All edges
     |          are considered by default.
     |
     |      Returns
     |      -------
     |      dataview
     |          Returns an `EdgeDataView` for undirected Graphs, `OutEdgeDataView`
     |          for DiGraphs, `MultiEdgeDataView` for MultiGraphs and
     |          `OutMultiEdgeDataView` for MultiDiGraphs.
     |
     |      Notes
     |      -----
     |      If ``data=False``, returns an `EdgeView` without any edge data.
     |
     |      See Also
     |      --------
     |      EdgeDataView
     |      OutEdgeDataView
     |      MultiEdgeDataView
     |      OutMultiEdgeDataView
     |
     |      Examples
     |      --------
     |      >>> G = nx.Graph()
     |      >>> G.add_edges_from(
     |      ...     [
     |      ...         (0, 1, {"dist": 3, "capacity": 20}),
     |      ...         (1, 2, {"dist": 4}),
     |      ...         (2, 0, {"dist": 5}),
     |      ...     ]
     |      ... )
     |
     |      Accessing edge data with ``data=True`` (the default) returns an
     |      edge data view object listing each edge with all of its attributes:
     |
     |      >>> G.edges.data()
     |      EdgeDataView([(0, 1, {'dist': 3, 'capacity': 20}), (0, 2, {'dist': 5}), (1, 2, {'dist': 4})])
     |
     |      If `data` represents a key in the edge attribute dict, a dataview listing
     |      each edge with its value for that specific key is returned:
     |
     |      >>> G.edges.data("dist")
     |      EdgeDataView([(0, 1, 3), (0, 2, 5), (1, 2, 4)])
     |
     |      `nbunch` can be used to limit the edges:
     |
     |      >>> G.edges.data("dist", nbunch=[0])
     |      EdgeDataView([(0, 1, 3), (0, 2, 5)])
     |
     |      If a specific key is not found in an edge attribute dict, the value
     |      specified by `default` is used:
     |
     |      >>> G.edges.data("capacity")
     |      EdgeDataView([(0, 1, 20), (0, 2, None), (1, 2, None)])
     |
     |      Note that there is no check that the `data` key is present in any of
     |      the edge attribute dictionaries:
     |
     |      >>> G.edges.data("speed")
     |      EdgeDataView([(0, 1, None), (0, 2, None), (1, 2, None)])
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes defined here:
     |
     |  __abstractmethods__ = frozenset()
     |
     |  dataview = <class 'networkx.classes.reportviews.OutMultiEdgeDataView'>
     |      An EdgeDataView for outward edges of MultiDiGraph; See EdgeDataView
     |
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from OutEdgeView:
     |
     |  __getstate__(self)
     |      Helper for pickle.
     |
     |  __init__(self, G)
     |      Initialize self.  See help(type(self)) for accurate signature.
     |
     |  __repr__(self)
     |      Return repr(self).
     |
     |  __setstate__(self, state)
     |
     |  __str__(self)
     |      Return str(self).
     |
     |  ----------------------------------------------------------------------
     |  Data descriptors inherited from OutEdgeView:
     |
     |  __dict__
     |      dictionary for instance variables
     |
     |  __weakref__
     |      list of weak references to the object
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Set:
     |
     |  __and__(self, other)
     |
     |  __eq__(self, other)
     |      Return self==value.
     |
     |  __ge__(self, other)
     |      Return self>=value.
     |
     |  __gt__(self, other)
     |      Return self>value.
     |
     |  __le__(self, other)
     |      Return self<=value.
     |
     |  __lt__(self, other)
     |      Return self<value.
     |
     |  __or__(self, other)
     |      Return self|value.
     |
     |  __rand__ = __and__(self, other)
     |
     |  __ror__ = __or__(self, other)
     |
     |  __rsub__(self, other)
     |
     |  __rxor__ = __xor__(self, other)
     |
     |  __sub__(self, other)
     |
     |  __xor__(self, other)
     |
     |  isdisjoint(self, other)
     |      Return True if two sets have a null intersection.
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Set:
     |
     |  __hash__ = None
     |
     |  ----------------------------------------------------------------------
     |  Methods inherited from collections.abc.Mapping:
     |
     |  get(self, key, default=None)
     |      D.get(k[,d]) -> D[k] if k in D, else d.  d defaults to None.
     |
     |  items(self)
     |      D.items() -> a set-like object providing a view on D's items
     |
     |  keys(self)
     |      D.keys() -> a set-like object providing a view on D's keys
     |
     |  values(self)
     |      D.values() -> an object providing a view on D's values
     |
     |  ----------------------------------------------------------------------
     |  Data and other attributes inherited from collections.abc.Mapping:
     |
     |  __reversed__ = None
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Collection:
     |
     |  __subclasshook__(C)
     |      Abstract classes can override this to customize issubclass().
     |
     |      This is invoked early on by abc.ABCMeta.__subclasscheck__().
     |      It should return True, False or NotImplemented.  If it returns
     |      NotImplemented, the normal algorithm is used.  Otherwise, it
     |      overrides the normal algorithm (and the outcome is cached).
     |
     |  ----------------------------------------------------------------------
     |  Class methods inherited from collections.abc.Iterable:
     |
     |  __class_getitem__ = GenericAlias(...)
     |      Represent a PEP 585 generic type
     |
     |      E.g. for t = list[int], t.__origin__ is list and t.__args__ is (int,).

DATA
    __all__ = ['NodeView', 'NodeDataView', 'EdgeView', 'OutEdgeView', 'InE...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\classes\reportviews.py

networkx.rescale_layout
Python Library Documentation: function rescale_layout in module networkx.drawing.layout

rescale_layout(pos, scale=1)
    Returns scaled position array to (-scale, scale) in all axes.

    The function acts on NumPy arrays which hold position information.
    Each position is one row of the array. The dimension of the space
    equals the number of columns. Each coordinate in one column.

    To rescale, the mean (center) is subtracted from each axis separately.
    Then all values are scaled so that the largest magnitude value
    from all axes equals `scale` (thus, the aspect ratio is preserved).
    The resulting NumPy Array is returned (order of rows unchanged).

    Parameters
    ----------
    pos : numpy array
        positions to be scaled. Each row is a position.

    scale : number (default: 1)
        The size of the resulting extent in all directions.

    Returns
    -------
    pos : numpy array
        scaled positions. Each row is a position.

    See Also
    --------
    rescale_layout_dict
networkx.rescale_layout_dict
Python Library Documentation: function rescale_layout_dict in module networkx.drawing.layout

rescale_layout_dict(pos, scale=1)
    Return a dictionary of scaled positions keyed by node

    Parameters
    ----------
    pos : A dictionary of positions keyed by node

    scale : number (default: 1)
        The size of the resulting extent in all directions.

    Returns
    -------
    pos : A dictionary of positions keyed by node

    Examples
    --------
    >>> import numpy as np
    >>> pos = {0: np.array((0, 0)), 1: np.array((1, 1)), 2: np.array((0.5, 0.5))}
    >>> nx.rescale_layout_dict(pos)
    {0: array([-1., -1.]), 1: array([1., 1.]), 2: array([0., 0.])}

    >>> pos = {0: np.array((0, 0)), 1: np.array((-1, 1)), 2: np.array((-0.5, 0.5))}
    >>> nx.rescale_layout_dict(pos, scale=2)
    {0: array([ 2., -2.]), 1: array([-2.,  2.]), 2: array([0., 0.])}

    See Also
    --------
    rescale_layout
networkx.resistance_distance
Python Library Documentation: function resistance_distance in module networkx.algorithms.distance_measures

resistance_distance(G, nodeA=None, nodeB=None, weight=None, invert_weight=True, *, backend=None, **backend_kwargs)
    Returns the resistance distance between pairs of nodes in graph G.

    The resistance distance between two nodes of a graph is akin to treating
    the graph as a grid of resistors with a resistance equal to the provided
    weight [1]_, [2]_.

    If weight is not provided, then a weight of 1 is used for all edges.

    If two nodes are the same, the resistance distance is zero.

    Parameters
    ----------
    G : NetworkX graph
       A graph

    nodeA : node or None, optional (default=None)
      A node within graph G.
      If None, compute resistance distance using all nodes as source nodes.

    nodeB : node or None, optional (default=None)
      A node within graph G.
      If None, compute resistance distance using all nodes as target nodes.

    weight : string or None, optional (default=None)
       The edge data key used to compute the resistance distance.
       If None, then each edge has weight 1.

    invert_weight : boolean (default=True)
        Proper calculation of resistance distance requires building the
        Laplacian matrix with the reciprocal of the weight. Not required
        if the weight is already inverted. Weight cannot be zero.

    Returns
    -------
    rd : dict or float
       If `nodeA` and `nodeB` are given, resistance distance between `nodeA`
       and `nodeB`. If `nodeA` or `nodeB` is unspecified (the default), a
       dictionary of nodes with resistance distances as the value.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a directed graph.

    NetworkXError
        If `G` is not connected, or contains no nodes,
        or `nodeA` is not in `G` or `nodeB` is not in `G`.

    Examples
    --------
    >>> G = nx.Graph([(1, 2), (1, 3), (1, 4), (3, 4), (3, 5), (4, 5)])
    >>> round(nx.resistance_distance(G, 1, 3), 10)
    0.625

    Notes
    -----
    The implementation is based on Theorem A in [2]_. Self-loops are ignored.
    Multi-edges are contracted in one edge with weight equal to the harmonic sum of the weights.

    References
    ----------
    .. [1] Wikipedia
       "Resistance distance."
       https://en.wikipedia.org/wiki/Resistance_distance
    .. [2] D. J. Klein and M. Randic.
        Resistance distance.
        J. of Math. Chem. 12:81-95, 1993.
networkx.resource_allocation_index
Python Library Documentation: function resource_allocation_index in module networkx.algorithms.link_prediction

resource_allocation_index(G, ebunch=None, *, backend=None, **backend_kwargs)
    Compute the resource allocation index of all node pairs in ebunch.

    Resource allocation index of `u` and `v` is defined as

    .. math::

        \sum_{w \in \Gamma(u) \cap \Gamma(v)} \frac{1}{|\Gamma(w)|}

    where $\Gamma(u)$ denotes the set of neighbors of $u$.

    Parameters
    ----------
    G : graph
        A NetworkX undirected graph.

    ebunch : iterable of node pairs, optional (default = None)
        Resource allocation index will be computed for each pair of
        nodes given in the iterable. The pairs must be given as
        2-tuples (u, v) where u and v are nodes in the graph. If ebunch
        is None then all nonexistent edges in the graph will be used.
        Default value: None.

    Returns
    -------
    piter : iterator
        An iterator of 3-tuples in the form (u, v, p) where (u, v) is a
        pair of nodes and p is their resource allocation index.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a `DiGraph`, a `Multigraph` or a `MultiDiGraph`.

    NodeNotFound
        If `ebunch` has a node that is not in `G`.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> preds = nx.resource_allocation_index(G, [(0, 1), (2, 3)])
    >>> for u, v, p in preds:
    ...     print(f"({u}, {v}) -> {p:.8f}")
    (0, 1) -> 0.75000000
    (2, 3) -> 0.75000000

    References
    ----------
    .. [1] T. Zhou, L. Lu, Y.-C. Zhang.
       Predicting missing links via local information.
       Eur. Phys. J. B 71 (2009) 623.
       https://arxiv.org/pdf/0901.0553.pdf
networkx.restricted_view
Python Library Documentation: function restricted_view in module networkx.classes.function

restricted_view(G, nodes, edges)
    Returns a view of `G` with hidden nodes and edges.

    The resulting subgraph filters out node `nodes` and edges `edges`.
    Filtered out nodes also filter out any of their edges.

    Parameters
    ----------
    G : NetworkX Graph
    nodes : iterable
        An iterable of nodes. Nodes not present in `G` are ignored.
    edges : iterable
        An iterable of edges. Edges not present in `G` are ignored.

    Returns
    -------
    subgraph : SubGraph View
        A read-only restricted view of `G` filtering out nodes and edges.
        Changes to `G` are reflected in the view.

    Notes
    -----
    To create a mutable subgraph with its own copies of nodes
    edges and attributes use `subgraph.copy()` or `Graph(subgraph)`

    If you create a subgraph of a subgraph recursively you may end up
    with a chain of subgraph views. Such chains can get quite slow
    for lengths near 15. To avoid long chains, try to make your subgraph
    based on the original graph.  We do not rule out chains programmatically
    so that odd cases like an `edge_subgraph` of a `restricted_view`
    can be created.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> H = nx.restricted_view(G, [0], [(1, 2), (3, 4)])
    >>> list(H.nodes)
    [1, 2, 3, 4]
    >>> list(H.edges)
    [(2, 3)]
networkx.reverse
Python Library Documentation: function reverse in module networkx.algorithms.operators.unary

reverse(G, copy=True, *, backend=None, **backend_kwargs)
    Returns the reverse directed graph of G.

    Parameters
    ----------
    G : directed graph
        A NetworkX directed graph
    copy : bool
        If True, then a new graph is returned. If False, then the graph is
        reversed in place.

    Returns
    -------
    H : directed graph
        The reversed G.

    Raises
    ------
    NetworkXError
        If graph is undirected.

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (1, 3), (2, 3), (3, 4), (3, 5)])
    >>> G_reversed = nx.reverse(G)
    >>> G_reversed.edges()
    OutEdgeView([(2, 1), (3, 1), (3, 2), (4, 3), (5, 3)])
networkx.reverse_view
Python Library Documentation: function reverse_view in module networkx.classes.graphviews

reverse_view(G)
    View of `G` with edge directions reversed

    `reverse_view` returns a read-only view of the input graph where
    edge directions are reversed.

    Identical to digraph.reverse(copy=False)

    Parameters
    ----------
    G : networkx.DiGraph

    Returns
    -------
    graph : networkx.DiGraph

    Examples
    --------
    >>> G = nx.DiGraph()
    >>> G.add_edge(1, 2)
    >>> G.add_edge(2, 3)
    >>> G.edges()
    OutEdgeView([(1, 2), (2, 3)])

    >>> view = nx.reverse_view(G)
    >>> view.edges()
    OutEdgeView([(2, 1), (3, 2)])
networkx.rich_club_coefficient
Python Library Documentation: function rich_club_coefficient in module networkx.algorithms.richclub

rich_club_coefficient(G, normalized=True, Q=100, seed=None, *, backend=None, **backend_kwargs)
    Returns the rich-club coefficient of the graph `G`.

    For each degree *k*, the *rich-club coefficient* is the ratio of the
    number of actual to the number of potential edges for nodes with
    degree greater than *k*:

    .. math::

        \phi(k) = \frac{2 E_k}{N_k (N_k - 1)}

    where `N_k` is the number of nodes with degree larger than *k*, and
    `E_k` is the number of edges among those nodes.

    Parameters
    ----------
    G : NetworkX graph
        Undirected graph with neither parallel edges nor self-loops.
    normalized : bool (optional)
        Normalize using randomized network as in [1]_
    Q : float (optional, default=100)
        If `normalized` is True, perform `Q * m` double-edge
        swaps, where `m` is the number of edges in `G`, to use as a
        null-model for normalization.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    rc : dictionary
       A dictionary, keyed by degree, with rich-club coefficient values.

    Raises
    ------
    NetworkXError
        If `G` has fewer than four nodes and ``normalized=True``.
        A randomly sampled graph for normalization cannot be generated in this case.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (1, 2), (1, 3), (1, 4), (4, 5)])
    >>> rc = nx.rich_club_coefficient(G, normalized=False, seed=42)
    >>> rc[0]
    0.4

    Notes
    -----
    The rich club definition and algorithm are found in [1]_.  This
    algorithm ignores any edge weights and is not defined for directed
    graphs or graphs with parallel edges or self loops.

    Normalization is done by computing the rich club coefficient for a randomly
    sampled graph with the same degree distribution as `G` by
    repeatedly swapping the endpoints of existing edges. For graphs with fewer than 4
    nodes, it is not possible to generate a random graph with a prescribed
    degree distribution, as the degree distribution fully determines the graph
    (hence making the coefficients trivially normalized to 1).
    This function raises an exception in this case.

    Estimates for appropriate values of `Q` are found in [2]_.

    References
    ----------
    .. [1] Julian J. McAuley, Luciano da Fontoura Costa,
       and Tibério S. Caetano,
       "The rich-club phenomenon across complex network hierarchies",
       Applied Physics Letters Vol 91 Issue 8, August 2007.
       https://arxiv.org/abs/physics/0701290
    .. [2] R. Milo, N. Kashtan, S. Itzkovitz, M. E. J. Newman, U. Alon,
       "Uniform generation of random graphs with arbitrary degree
       sequences", 2006. https://arxiv.org/abs/cond-mat/0312028
networkx.richclub
Python Library Documentation: module networkx.algorithms.richclub in networkx.algorithms

NAME
    networkx.algorithms.richclub - Functions for computing rich-club coefficients.

FUNCTIONS
    rich_club_coefficient(G, normalized=True, Q=100, seed=None, *, backend=None, **backend_kwargs)
        Returns the rich-club coefficient of the graph `G`.

        For each degree *k*, the *rich-club coefficient* is the ratio of the
        number of actual to the number of potential edges for nodes with
        degree greater than *k*:

        .. math::

            \phi(k) = \frac{2 E_k}{N_k (N_k - 1)}

        where `N_k` is the number of nodes with degree larger than *k*, and
        `E_k` is the number of edges among those nodes.

        Parameters
        ----------
        G : NetworkX graph
            Undirected graph with neither parallel edges nor self-loops.
        normalized : bool (optional)
            Normalize using randomized network as in [1]_
        Q : float (optional, default=100)
            If `normalized` is True, perform `Q * m` double-edge
            swaps, where `m` is the number of edges in `G`, to use as a
            null-model for normalization.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        rc : dictionary
           A dictionary, keyed by degree, with rich-club coefficient values.

        Raises
        ------
        NetworkXError
            If `G` has fewer than four nodes and ``normalized=True``.
            A randomly sampled graph for normalization cannot be generated in this case.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (1, 2), (1, 3), (1, 4), (4, 5)])
        >>> rc = nx.rich_club_coefficient(G, normalized=False, seed=42)
        >>> rc[0]
        0.4

        Notes
        -----
        The rich club definition and algorithm are found in [1]_.  This
        algorithm ignores any edge weights and is not defined for directed
        graphs or graphs with parallel edges or self loops.

        Normalization is done by computing the rich club coefficient for a randomly
        sampled graph with the same degree distribution as `G` by
        repeatedly swapping the endpoints of existing edges. For graphs with fewer than 4
        nodes, it is not possible to generate a random graph with a prescribed
        degree distribution, as the degree distribution fully determines the graph
        (hence making the coefficients trivially normalized to 1).
        This function raises an exception in this case.

        Estimates for appropriate values of `Q` are found in [2]_.

        References
        ----------
        .. [1] Julian J. McAuley, Luciano da Fontoura Costa,
           and Tibério S. Caetano,
           "The rich-club phenomenon across complex network hierarchies",
           Applied Physics Letters Vol 91 Issue 8, August 2007.
           https://arxiv.org/abs/physics/0701290
        .. [2] R. Milo, N. Kashtan, S. Itzkovitz, M. E. J. Newman, U. Alon,
           "Uniform generation of random graphs with arbitrary degree
           sequences", 2006. https://arxiv.org/abs/cond-mat/0312028

DATA
    __all__ = ['rich_club_coefficient']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\richclub.py

networkx.ring_of_cliques
Python Library Documentation: function ring_of_cliques in module networkx.generators.community

ring_of_cliques(num_cliques, clique_size, *, backend=None, **backend_kwargs)
    Defines a "ring of cliques" graph.

    A ring of cliques graph is consisting of cliques, connected through single
    links. Each clique is a complete graph.

    Parameters
    ----------
    num_cliques : int
        Number of cliques
    clique_size : int
        Size of cliques

    Returns
    -------
    G : NetworkX Graph
        ring of cliques graph

    Raises
    ------
    NetworkXError
        If the number of cliques is lower than 2 or
        if the size of cliques is smaller than 2.

    Examples
    --------
    >>> G = nx.ring_of_cliques(8, 4)

    See Also
    --------
    connected_caveman_graph

    Notes
    -----
    The `connected_caveman_graph` graph removes a link from each clique to
    connect it with the next clique. Instead, the `ring_of_cliques` graph
    simply adds the link without removing any link from the cliques.
networkx.rooted_product
Python Library Documentation: function rooted_product in module networkx.algorithms.operators.product

rooted_product(G, H, root, *, backend=None, **backend_kwargs)
    Return the rooted product of graphs G and H rooted at root in H.

    A new graph is constructed representing the rooted product of
    the inputted graphs, G and H, with a root in H.
    A rooted product duplicates H for each nodes in G with the root
    of H corresponding to the node in G. Nodes are renamed as the direct
    product of G and H. The result is a subgraph of the cartesian product.

    Parameters
    ----------
    G,H : graph
       A NetworkX graph
    root : node
       A node in H

    Returns
    -------
    R : The rooted product of G and H with a specified root in H

    Notes
    -----
    The nodes of R are the Cartesian Product of the nodes of G and H.
    The nodes of G and H are not relabeled.
networkx.s_metric
Python Library Documentation: function s_metric in module networkx.algorithms.smetric

s_metric(G, *, backend=None, **backend_kwargs)
    Returns the s-metric [1]_ of graph.

    The s-metric is defined as the sum of the products ``deg(u) * deg(v)``
    for every edge ``(u, v)`` in `G`.

    Parameters
    ----------
    G : graph
        The graph used to compute the s-metric.

    Returns
    -------
    s : float
        The s-metric of the graph.

    References
    ----------
    .. [1] Lun Li, David Alderson, John C. Doyle, and Walter Willinger,
           Towards a Theory of Scale-Free Graphs:
           Definition, Properties, and  Implications (Extended Version), 2005.
           https://arxiv.org/abs/cond-mat/0501169
networkx.scale_free_graph
Python Library Documentation: function scale_free_graph in module networkx.generators.directed

scale_free_graph(n, alpha=0.41, beta=0.54, gamma=0.05, delta_in=0.2, delta_out=0, seed=None, initial_graph=None, *, backend=None, **backend_kwargs)
    Returns a scale-free directed graph.

    Parameters
    ----------
    n : integer
        Number of nodes in graph
    alpha : float
        Probability for adding a new node connected to an existing node
        chosen randomly according to the in-degree distribution.
    beta : float
        Probability for adding an edge between two existing nodes.
        One existing node is chosen randomly according the in-degree
        distribution and the other chosen randomly according to the out-degree
        distribution.
    gamma : float
        Probability for adding a new node connected to an existing node
        chosen randomly according to the out-degree distribution.
    delta_in : float
        Bias for choosing nodes from in-degree distribution.
    delta_out : float
        Bias for choosing nodes from out-degree distribution.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    initial_graph : MultiDiGraph instance, optional
        Build the scale-free graph starting from this initial MultiDiGraph,
        if provided.

    Returns
    -------
    MultiDiGraph

    Examples
    --------
    Create a scale-free graph on one hundred nodes::

    >>> G = nx.scale_free_graph(100)

    Notes
    -----
    The sum of `alpha`, `beta`, and `gamma` must be 1.

    References
    ----------
    .. [1] B. Bollobás, C. Borgs, J. Chayes, and O. Riordan,
           Directed scale-free graphs,
           Proceedings of the fourteenth annual ACM-SIAM Symposium on
           Discrete Algorithms, 132--139, 2003.
networkx.schultz_index
Python Library Documentation: function schultz_index in module networkx.algorithms.wiener

schultz_index(G, weight=None, *, backend=None, **backend_kwargs)
    Returns the Schultz Index (of the first kind) of `G`

    The *Schultz Index* [3]_ of a graph is the sum over all node pairs of
    distances times the sum of degrees. Consider an undirected graph `G`.
    For each node pair ``(u, v)`` compute ``dist(u, v) * (deg(u) + deg(v)``
    where ``dist`` is the shortest path length between two nodes and ``deg``
    is the degree of a node.

    The Schultz Index is the sum of these quantities over all (unordered)
    pairs of nodes.

    Parameters
    ----------
    G : NetworkX graph
        The undirected graph of interest.
    weight : string or None, optional (default: None)
        If None, every edge has weight 1.
        If a string, use this edge attribute as the edge weight.
        Any edge attribute not present defaults to 1.
        The edge weights are used to computing shortest-path distances.

    Returns
    -------
    number
        The first kind of Schultz Index of the graph `G`.

    Examples
    --------
    The Schultz Index of the (unweighted) complete graph on *n* nodes
    equals the number of pairs of the *n* nodes times ``2 * (n - 1)``,
    since each pair of nodes is at distance one and the sum of degree
    of two nodes is ``2 * (n - 1)``.

    >>> n = 10
    >>> G = nx.complete_graph(n)
    >>> nx.schultz_index(G) == (n * (n - 1) / 2) * (2 * (n - 1))
    True

    Graph that is disconnected

    >>> nx.schultz_index(nx.empty_graph(2))
    inf

    References
    ----------
    .. [1] I. Gutman, Selected properties of the Schultz molecular topological index,
           J. Chem. Inf. Comput. Sci. 34 (1994), 1087–1089.
           https://doi.org/10.1021/ci00021a009
    .. [2] M.V. Diudeaa and I. Gutman, Wiener-Type Topological Indices,
           Croatica Chemica Acta, 71 (1998), 21-51.
           https://hrcak.srce.hr/132323
    .. [3] H. P. Schultz, Topological organic chemistry. 1.
           Graph theory and topological indices of alkanes,i
           J. Chem. Inf. Comput. Sci. 29 (1989), 239–257.
networkx.second_order
Python Library Documentation: module networkx.algorithms.centrality.second_order in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.second_order - Copyright (c) 2015 – Thomson Licensing, SAS

DESCRIPTION
    Redistribution and use in source and binary forms, with or without
    modification, are permitted (subject to the limitations in the
    disclaimer below) provided that the following conditions are met:

    * Redistributions of source code must retain the above copyright
    notice, this list of conditions and the following disclaimer.

    * Redistributions in binary form must reproduce the above copyright
    notice, this list of conditions and the following disclaimer in the
    documentation and/or other materials provided with the distribution.

    * Neither the name of Thomson Licensing, or Technicolor, nor the names
    of its contributors may be used to endorse or promote products derived
    from this software without specific prior written permission.

    NO EXPRESS OR IMPLIED LICENSES TO ANY PARTY'S PATENT RIGHTS ARE
    GRANTED BY THIS LICENSE.  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT
    HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED
    WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
    MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
    DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
    LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
    CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
    SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
    BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
    WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
    OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
    IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

FUNCTIONS
    second_order_centrality(G, weight='weight', *, backend=None, **backend_kwargs)
        Compute the second order centrality for nodes of G.

        The second order centrality of a given node is the standard deviation of
        the return times to that node of a perpetual random walk on G:

        Parameters
        ----------
        G : graph
          A NetworkX connected and undirected graph.

        weight : string or None, optional (default="weight")
            The name of an edge attribute that holds the numerical value
            used as a weight. If None then each edge has weight 1.

        Returns
        -------
        nodes : dictionary
           Dictionary keyed by node with second order centrality as the value.

        Examples
        --------
        >>> G = nx.star_graph(10)
        >>> soc = nx.second_order_centrality(G)
        >>> print(sorted(soc.items(), key=lambda x: x[1])[0][0])  # pick first id
        0

        Raises
        ------
        NetworkXException
            If the graph G is empty, non connected or has negative weights.

        See Also
        --------
        betweenness_centrality

        Notes
        -----
        Lower values of second order centrality indicate higher centrality.

        The algorithm is from Kermarrec, Le Merrer, Sericola and Trédan [1]_.

        This code implements the analytical version of the algorithm, i.e.,
        there is no simulation of a random walk process involved. The random walk
        is here unbiased (corresponding to eq 6 of the paper [1]_), thus the
        centrality values are the standard deviations for random walk return times
        on the transformed input graph G (equal in-degree at each nodes by adding
        self-loops).

        Complexity of this implementation, made to run locally on a single machine,
        is O(n^3), with n the size of G, which makes it viable only for small
        graphs.

        References
        ----------
        .. [1] Anne-Marie Kermarrec, Erwan Le Merrer, Bruno Sericola, Gilles Trédan
           "Second order centrality: Distributed assessment of nodes criticity in
           complex networks", Elsevier Computer Communications 34(5):619-628, 2011.

DATA
    __all__ = ['second_order_centrality']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\second_order.py

networkx.second_order_centrality
Python Library Documentation: function second_order_centrality in module networkx.algorithms.centrality.second_order

second_order_centrality(G, weight='weight', *, backend=None, **backend_kwargs)
    Compute the second order centrality for nodes of G.

    The second order centrality of a given node is the standard deviation of
    the return times to that node of a perpetual random walk on G:

    Parameters
    ----------
    G : graph
      A NetworkX connected and undirected graph.

    weight : string or None, optional (default="weight")
        The name of an edge attribute that holds the numerical value
        used as a weight. If None then each edge has weight 1.

    Returns
    -------
    nodes : dictionary
       Dictionary keyed by node with second order centrality as the value.

    Examples
    --------
    >>> G = nx.star_graph(10)
    >>> soc = nx.second_order_centrality(G)
    >>> print(sorted(soc.items(), key=lambda x: x[1])[0][0])  # pick first id
    0

    Raises
    ------
    NetworkXException
        If the graph G is empty, non connected or has negative weights.

    See Also
    --------
    betweenness_centrality

    Notes
    -----
    Lower values of second order centrality indicate higher centrality.

    The algorithm is from Kermarrec, Le Merrer, Sericola and Trédan [1]_.

    This code implements the analytical version of the algorithm, i.e.,
    there is no simulation of a random walk process involved. The random walk
    is here unbiased (corresponding to eq 6 of the paper [1]_), thus the
    centrality values are the standard deviations for random walk return times
    on the transformed input graph G (equal in-degree at each nodes by adding
    self-loops).

    Complexity of this implementation, made to run locally on a single machine,
    is O(n^3), with n the size of G, which makes it viable only for small
    graphs.

    References
    ----------
    .. [1] Anne-Marie Kermarrec, Erwan Le Merrer, Bruno Sericola, Gilles Trédan
       "Second order centrality: Distributed assessment of nodes criticity in
       complex networks", Elsevier Computer Communications 34(5):619-628, 2011.
networkx.sedgewick_maze_graph
Python Library Documentation: function sedgewick_maze_graph in module networkx.generators.small

sedgewick_maze_graph(create_using=None, *, backend=None, **backend_kwargs)
    Return a small maze with a cycle.

    This is the maze used in Sedgewick, 3rd Edition, Part 5, Graph
    Algorithms, Chapter 18, e.g. Figure 18.2 and following [1]_.
    Nodes are numbered 0,..,7

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Small maze with a cycle

    References
    ----------
    .. [1] Figure 18.2, Chapter 18, Graph Algorithms (3rd Ed), Sedgewick
networkx.selfloop_edges
Python Library Documentation: function selfloop_edges in module networkx.classes.function

selfloop_edges(G, data=False, keys=False, default=None)
    Returns an iterator over selfloop edges.

    A selfloop edge has the same node at both ends.

    Parameters
    ----------
    G : graph
        A NetworkX graph.
    data : string or bool, optional (default=False)
        Return selfloop edges as two tuples (u, v) (data=False)
        or three-tuples (u, v, datadict) (data=True)
        or three-tuples (u, v, datavalue) (data='attrname')
    keys : bool, optional (default=False)
        If True, return edge keys with each edge.
    default : value, optional (default=None)
        Value used for edges that don't have the requested attribute.
        Only relevant if data is not True or False.

    Returns
    -------
    edgeiter : iterator over edge tuples
        An iterator over all selfloop edges.

    See Also
    --------
    nodes_with_selfloops, number_of_selfloops

    Examples
    --------
    >>> G = nx.MultiGraph()  # or Graph, DiGraph, MultiDiGraph, etc
    >>> ekey = G.add_edge(1, 1)
    >>> ekey = G.add_edge(1, 2)
    >>> list(nx.selfloop_edges(G))
    [(1, 1)]
    >>> list(nx.selfloop_edges(G, data=True))
    [(1, 1, {})]
    >>> list(nx.selfloop_edges(G, keys=True))
    [(1, 1, 0)]
    >>> list(nx.selfloop_edges(G, keys=True, data=True))
    [(1, 1, 0, {})]
networkx.semiconnected
Python Library Documentation: module networkx.algorithms.components.semiconnected in networkx.algorithms.components

NAME
    networkx.algorithms.components.semiconnected - Semiconnectedness.

FUNCTIONS
    is_semiconnected(G, *, backend=None, **backend_kwargs)
        Returns True if the graph is semiconnected, False otherwise.

        A graph is semiconnected if and only if for any pair of nodes, either one
        is reachable from the other, or they are mutually reachable.

        This function uses a theorem that states that a DAG is semiconnected
        if for any topological sort, for node $v_n$ in that sort, there is an
        edge $(v_i, v_{i+1})$. That allows us to check if a non-DAG `G` is
        semiconnected by condensing the graph: i.e. constructing a new graph `H`
        with nodes being the strongly connected components of `G`, and edges
        (scc_1, scc_2) if there is a edge $(v_1, v_2)$ in `G` for some
        $v_1 \in scc_1$ and $v_2 \in scc_2$. That results in a DAG, so we compute
        the topological sort of `H` and check if for every $n$ there is an edge
        $(scc_n, scc_{n+1})$.

        Parameters
        ----------
        G : NetworkX graph
            A directed graph.

        Returns
        -------
        semiconnected : bool
            True if the graph is semiconnected, False otherwise.

        Raises
        ------
        NetworkXNotImplemented
            If the input graph is undirected.

        NetworkXPointlessConcept
            If the graph is empty.

        Examples
        --------
        >>> G = nx.path_graph(4, create_using=nx.DiGraph())
        >>> print(nx.is_semiconnected(G))
        True
        >>> G = nx.DiGraph([(1, 2), (3, 2)])
        >>> print(nx.is_semiconnected(G))
        False

        See Also
        --------
        is_strongly_connected
        is_weakly_connected
        is_connected
        is_biconnected

DATA
    __all__ = ['is_semiconnected']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\components\semiconnected.py

networkx.set_edge_attributes
Python Library Documentation: function set_edge_attributes in module networkx.classes.function

set_edge_attributes(G, values, name=None)
    Sets edge attributes from a given value or dictionary of values.

    .. Warning:: The call order of arguments `values` and `name`
        switched between v1.x & v2.x.

    Parameters
    ----------
    G : NetworkX Graph

    values : scalar value, dict-like
        What the edge attribute should be set to.  If `values` is
        not a dictionary, then it is treated as a single attribute value
        that is then applied to every edge in `G`.  This means that if
        you provide a mutable object, like a list, updates to that object
        will be reflected in the edge attribute for each edge.  The attribute
        name will be `name`.

        If `values` is a dict or a dict of dict, it should be keyed
        by edge tuple to either an attribute value or a dict of attribute
        key/value pairs used to update the edge's attributes.
        For multigraphs, the edge tuples must be of the form ``(u, v, key)``,
        where `u` and `v` are nodes and `key` is the edge key.
        For non-multigraphs, the keys must be tuples of the form ``(u, v)``.

    name : string (optional, default=None)
        Name of the edge attribute to set if values is a scalar.

    Examples
    --------
    After computing some property of the edges of a graph, you may want
    to assign a edge attribute to store the value of that property for
    each edge::

        >>> G = nx.path_graph(3)
        >>> bb = nx.edge_betweenness_centrality(G, normalized=False)
        >>> nx.set_edge_attributes(G, bb, "betweenness")
        >>> G.edges[1, 2]["betweenness"]
        2.0

    If you provide a list as the second argument, updates to the list
    will be reflected in the edge attribute for each edge::

        >>> labels = []
        >>> nx.set_edge_attributes(G, labels, "labels")
        >>> labels.append("foo")
        >>> G.edges[0, 1]["labels"]
        ['foo']
        >>> G.edges[1, 2]["labels"]
        ['foo']

    If you provide a dictionary of dictionaries as the second argument,
    the entire dictionary will be used to update edge attributes::

        >>> G = nx.path_graph(3)
        >>> attrs = {(0, 1): {"attr1": 20, "attr2": "nothing"}, (1, 2): {"attr2": 3}}
        >>> nx.set_edge_attributes(G, attrs)
        >>> G[0][1]["attr1"]
        20
        >>> G[0][1]["attr2"]
        'nothing'
        >>> G[1][2]["attr2"]
        3

    The attributes of one Graph can be used to set those of another.

        >>> H = nx.path_graph(3)
        >>> nx.set_edge_attributes(H, G.edges)

    Note that if the dict contains edges that are not in `G`, they are
    silently ignored::

        >>> G = nx.Graph([(0, 1)])
        >>> nx.set_edge_attributes(G, {(1, 2): {"weight": 2.0}})
        >>> (1, 2) in G.edges()
        False

    For multigraphs, the `values` dict is expected to be keyed by 3-tuples
    including the edge key::

        >>> MG = nx.MultiGraph()
        >>> edges = [(0, 1), (0, 1)]
        >>> MG.add_edges_from(edges)  # Returns list of edge keys
        [0, 1]
        >>> attributes = {(0, 1, 0): {"cost": 21}, (0, 1, 1): {"cost": 7}}
        >>> nx.set_edge_attributes(MG, attributes)
        >>> MG[0][1][0]["cost"]
        21
        >>> MG[0][1][1]["cost"]
        7

    If MultiGraph attributes are desired for a Graph, you must convert the 3-tuple
    multiedge to a 2-tuple edge and the last multiedge's attribute value will
    overwrite the previous values. Continuing from the previous case we get::

        >>> H = nx.path_graph([0, 1, 2])
        >>> nx.set_edge_attributes(H, {(u, v): ed for u, v, ed in MG.edges.data()})
        >>> nx.get_edge_attributes(H, "cost")
        {(0, 1): 7}
networkx.set_node_attributes
Python Library Documentation: function set_node_attributes in module networkx.classes.function

set_node_attributes(G, values, name=None)
    Sets node attributes from a given value or dictionary of values.

    .. Warning:: The call order of arguments `values` and `name`
        switched between v1.x & v2.x.

    Parameters
    ----------
    G : NetworkX Graph

    values : scalar value, dict-like
        What the node attribute should be set to.  If `values` is
        not a dictionary, then it is treated as a single attribute value
        that is then applied to every node in `G`.  This means that if
        you provide a mutable object, like a list, updates to that object
        will be reflected in the node attribute for every node.
        The attribute name will be `name`.

        If `values` is a dict or a dict of dict, it should be keyed
        by node to either an attribute value or a dict of attribute key/value
        pairs used to update the node's attributes.

    name : string (optional, default=None)
        Name of the node attribute to set if values is a scalar.

    Examples
    --------
    After computing some property of the nodes of a graph, you may want
    to assign a node attribute to store the value of that property for
    each node::

        >>> G = nx.path_graph(3)
        >>> bb = nx.betweenness_centrality(G)
        >>> isinstance(bb, dict)
        True
        >>> nx.set_node_attributes(G, bb, "betweenness")
        >>> G.nodes[1]["betweenness"]
        1.0

    If you provide a list as the second argument, updates to the list
    will be reflected in the node attribute for each node::

        >>> G = nx.path_graph(3)
        >>> labels = []
        >>> nx.set_node_attributes(G, labels, "labels")
        >>> labels.append("foo")
        >>> G.nodes[0]["labels"]
        ['foo']
        >>> G.nodes[1]["labels"]
        ['foo']
        >>> G.nodes[2]["labels"]
        ['foo']

    If you provide a dictionary of dictionaries as the second argument,
    the outer dictionary is assumed to be keyed by node to an inner
    dictionary of node attributes for that node::

        >>> G = nx.path_graph(3)
        >>> attrs = {0: {"attr1": 20, "attr2": "nothing"}, 1: {"attr2": 3}}
        >>> nx.set_node_attributes(G, attrs)
        >>> G.nodes[0]["attr1"]
        20
        >>> G.nodes[0]["attr2"]
        'nothing'
        >>> G.nodes[1]["attr2"]
        3
        >>> G.nodes[2]
        {}

    Note that if the dictionary contains nodes that are not in `G`, the
    values are silently ignored::

        >>> G = nx.Graph()
        >>> G.add_node(0)
        >>> nx.set_node_attributes(G, {0: "red", 1: "blue"}, name="color")
        >>> G.nodes[0]["color"]
        'red'
        >>> 1 in G.nodes
        False
networkx.shell_layout
Python Library Documentation: function shell_layout in module networkx.drawing.layout

shell_layout(G, nlist=None, rotate=None, scale=1, center=None, dim=2)
    Position nodes in concentric circles.

    Parameters
    ----------
    G : NetworkX graph or list of nodes
        A position will be assigned to every node in G.

    nlist : list of lists
       List of node lists for each shell.

    rotate : angle in radians (default=pi/len(nlist))
       Angle by which to rotate the starting position of each shell
       relative to the starting position of the previous shell.
       To recreate behavior before v2.5 use rotate=0.

    scale : number (default: 1)
        Scale factor for positions.

    center : array-like or None
        Coordinate pair around which to center the layout.

    dim : int
        Dimension of layout, currently only dim=2 is supported.
        Other dimension values result in a ValueError.

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node

    Raises
    ------
    ValueError
        If dim != 2

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> shells = [[0], [1, 2, 3]]
    >>> pos = nx.shell_layout(G, shells)

    Notes
    -----
    This algorithm currently only works in two dimensions and does not
    try to minimize edge crossings.
networkx.shortest_path
Python Library Documentation: function shortest_path in module networkx.algorithms.shortest_paths.generic

shortest_path(G, source=None, target=None, weight=None, method='dijkstra', *, backend=None, **backend_kwargs)
    Compute shortest paths in the graph.

    Parameters
    ----------
    G : NetworkX graph

    source : node, optional
        Starting node for path. If not specified, compute shortest
        paths for each possible starting node.

    target : node, optional
        Ending node for path. If not specified, compute shortest
        paths to all possible nodes.

    weight : None, string or function, optional (default = None)
        If None, every edge has weight/distance/cost 1.
        If a string, use this edge attribute as the edge weight.
        Any edge attribute not present defaults to 1.
        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly
        three positional arguments: the two endpoints of an edge and
        the dictionary of edge attributes for that edge.
        The function must return a number.

    method : string, optional (default = 'dijkstra')
        The algorithm to use to compute the path.
        Supported options: 'dijkstra', 'bellman-ford'.
        Other inputs produce a ValueError.
        If `weight` is None, unweighted graph methods are used, and this
        suggestion is ignored.

    Returns
    -------
    path: list or dictionary
        All returned paths include both the source and target in the path.

        If the source and target are both specified, return a single list
        of nodes in a shortest path from the source to the target.

        If only the source is specified, return a dictionary keyed by
        targets with a list of nodes in a shortest path from the source
        to one of the targets.

        If only the target is specified, return a dictionary keyed by
        sources with a list of nodes in a shortest path from one of the
        sources to the target.

        If neither the source nor target are specified return a dictionary
        of dictionaries with path[source][target]=[list of nodes in path].

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    ValueError
        If `method` is not among the supported options.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> print(nx.shortest_path(G, source=0, target=4))
    [0, 1, 2, 3, 4]
    >>> p = nx.shortest_path(G, source=0)  # target not specified
    >>> p[3]  # shortest path from source=0 to target=3
    [0, 1, 2, 3]
    >>> p = nx.shortest_path(G, target=4)  # source not specified
    >>> p[1]  # shortest path from source=1 to target=4
    [1, 2, 3, 4]
    >>> p = dict(nx.shortest_path(G))  # source, target not specified
    >>> p[2][4]  # shortest path from source=2 to target=4
    [2, 3, 4]

    Notes
    -----
    There may be more than one shortest path between a source and target.
    This returns only one of them.

    See Also
    --------
    all_pairs_shortest_path
    all_pairs_dijkstra_path
    all_pairs_bellman_ford_path
    single_source_shortest_path
    single_source_dijkstra_path
    single_source_bellman_ford_path
networkx.shortest_path_length
Python Library Documentation: function shortest_path_length in module networkx.algorithms.shortest_paths.generic

shortest_path_length(G, source=None, target=None, weight=None, method='dijkstra', *, backend=None, **backend_kwargs)
    Compute shortest path lengths in the graph.

    Parameters
    ----------
    G : NetworkX graph

    source : node, optional
        Starting node for path.
        If not specified, compute shortest path lengths using all nodes as
        source nodes.

    target : node, optional
        Ending node for path.
        If not specified, compute shortest path lengths using all nodes as
        target nodes.

    weight : None, string or function, optional (default = None)
        If None, every edge has weight/distance/cost 1.
        If a string, use this edge attribute as the edge weight.
        Any edge attribute not present defaults to 1.
        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly
        three positional arguments: the two endpoints of an edge and
        the dictionary of edge attributes for that edge.
        The function must return a number.

    method : string, optional (default = 'dijkstra')
        The algorithm to use to compute the path length.
        Supported options: 'dijkstra', 'bellman-ford'.
        Other inputs produce a ValueError.
        If `weight` is None, unweighted graph methods are used, and this
        suggestion is ignored.

    Returns
    -------
    length: number or iterator
        If the source and target are both specified, return the length of
        the shortest path from the source to the target.

        If only the source is specified, return a dict keyed by target
        to the shortest path length from the source to that target.

        If only the target is specified, return a dict keyed by source
        to the shortest path length from that source to the target.

        If neither the source nor target are specified, return an iterator
        over (source, dictionary) where dictionary is keyed by target to
        shortest path length from source to that target.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    NetworkXNoPath
        If no path exists between source and target.

    ValueError
        If `method` is not among the supported options.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> nx.shortest_path_length(G, source=0, target=4)
    4
    >>> p = nx.shortest_path_length(G, source=0)  # target not specified
    >>> p[4]
    4
    >>> p = nx.shortest_path_length(G, target=4)  # source not specified
    >>> p[0]
    4
    >>> p = dict(nx.shortest_path_length(G))  # source,target not specified
    >>> p[0][4]
    4

    Notes
    -----
    The length of the path is always 1 less than the number of nodes involved
    in the path since the length measures the number of edges followed.

    For digraphs this returns the shortest directed path length. To find path
    lengths in the reverse direction use G.reverse(copy=False) first to flip
    the edge orientation.

    See Also
    --------
    all_pairs_shortest_path_length
    all_pairs_dijkstra_path_length
    all_pairs_bellman_ford_path_length
    single_source_shortest_path_length
    single_source_dijkstra_path_length
    single_source_bellman_ford_path_length
networkx.shortest_paths
Python Library Documentation: package networkx.algorithms.shortest_paths in networkx.algorithms

NAME
    networkx.algorithms.shortest_paths

PACKAGE CONTENTS
    astar
    dense
    generic
    tests (package)
    unweighted
    weighted

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\shortest_paths\__init__.py

networkx.shortest_simple_paths
Python Library Documentation: function shortest_simple_paths in module networkx.algorithms.simple_paths

shortest_simple_paths(G, source, target, weight=None, *, backend=None, **backend_kwargs)
    Generate all simple paths in the graph G from source to target,
       starting from shortest ones.

    A simple path is a path with no repeated nodes.

    If a weighted shortest path search is to be used, no negative weights
    are allowed.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Starting node for path

    target : node
       Ending node for path

    weight : string or function
        If it is a string, it is the name of the edge attribute to be
        used as a weight.

        If it is a function, the weight of an edge is the value returned
        by the function. The function must accept exactly three positional
        arguments: the two endpoints of an edge and the dictionary of edge
        attributes for that edge. The function must return a number or None.
        The weight function can be used to hide edges by returning None.
        So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
        will find the shortest red path.

        If None all edges are considered to have unit weight. Default
        value None.

    Returns
    -------
    path_generator: generator
       A generator that produces lists of simple paths, in order from
       shortest to longest.

    Raises
    ------
    NetworkXNoPath
       If no path exists between source and target.

    NetworkXError
       If source or target nodes are not in the input graph.

    NetworkXNotImplemented
       If the input graph is a Multi[Di]Graph.

    Examples
    --------

    >>> G = nx.cycle_graph(7)
    >>> paths = list(nx.shortest_simple_paths(G, 0, 3))
    >>> print(paths)
    [[0, 1, 2, 3], [0, 6, 5, 4, 3]]

    You can use this function to efficiently compute the k shortest/best
    paths between two nodes.

    >>> from itertools import islice
    >>> def k_shortest_paths(G, source, target, k, weight=None):
    ...     return list(
    ...         islice(nx.shortest_simple_paths(G, source, target, weight=weight), k)
    ...     )
    >>> for path in k_shortest_paths(G, 0, 3, 2):
    ...     print(path)
    [0, 1, 2, 3]
    [0, 6, 5, 4, 3]

    Notes
    -----
    This procedure is based on algorithm by Jin Y. Yen [1]_.  Finding
    the first $K$ paths requires $O(KN^3)$ operations.

    See Also
    --------
    all_shortest_paths
    shortest_path
    all_simple_paths

    References
    ----------
    .. [1] Jin Y. Yen, "Finding the K Shortest Loopless Paths in a
       Network", Management Science, Vol. 17, No. 11, Theory Series
       (Jul., 1971), pp. 712-716.
networkx.sigma
Python Library Documentation: function sigma in module networkx.algorithms.smallworld

sigma(G, niter=100, nrand=10, seed=None, *, backend=None, **backend_kwargs)
    Returns the small-world coefficient (sigma) of the given graph.

    The small-world coefficient is defined as:
    sigma = C/Cr / L/Lr
    where C and L are respectively the average clustering coefficient and
    average shortest path length of G. Cr and Lr are respectively the average
    clustering coefficient and average shortest path length of an equivalent
    random graph.

    A graph is commonly classified as small-world if sigma>1.

    Parameters
    ----------
    G : NetworkX graph
        An undirected graph.
    niter : integer (optional, default=100)
        Approximate number of rewiring per edge to compute the equivalent
        random graph.
    nrand : integer (optional, default=10)
        Number of random graphs generated to compute the average clustering
        coefficient (Cr) and average shortest path length (Lr).
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    sigma : float
        The small-world coefficient of G.

    Notes
    -----
    The implementation is adapted from Humphries et al. [1]_ [2]_.

    References
    ----------
    .. [1] The brainstem reticular formation is a small-world, not scale-free,
           network M. D. Humphries, K. Gurney and T. J. Prescott,
           Proc. Roy. Soc. B 2006 273, 503-511, doi:10.1098/rspb.2005.3354.
    .. [2] Humphries and Gurney (2008).
           "Network 'Small-World-Ness': A Quantitative Method for Determining
           Canonical Network Equivalence".
           PLoS One. 3 (4). PMID 18446219. doi:10.1371/journal.pone.0002051.
networkx.similarity
Python Library Documentation: module networkx.algorithms.similarity in networkx.algorithms

NAME
    networkx.algorithms.similarity - Functions measuring similarity using graph edit distance.

DESCRIPTION
    The graph edit distance is the number of edge/node changes needed
    to make two graphs isomorphic.

    The default algorithm/implementation is sub-optimal for some graphs.
    The problem of finding the exact Graph Edit Distance (GED) is NP-hard
    so it is often slow. If the simple interface `graph_edit_distance`
    takes too long for your graph, try `optimize_graph_edit_distance`
    and/or `optimize_edit_paths`.

    At the same time, I encourage capable people to investigate
    alternative GED algorithms, in order to improve the choices available.

FUNCTIONS
    generate_random_paths(G, sample_size, path_length=5, index_map=None, weight='weight', seed=None, *, backend=None, **backend_kwargs)
        Randomly generate `sample_size` paths of length `path_length`.

        Parameters
        ----------
        G : NetworkX graph
            A NetworkX graph
        sample_size : integer
            The number of paths to generate. This is ``R`` in [1]_.
        path_length : integer (default = 5)
            The maximum size of the path to randomly generate.
            This is ``T`` in [1]_. According to the paper, ``T >= 5`` is
            recommended.
        index_map : dictionary, optional
            If provided, this will be populated with the inverted
            index of nodes mapped to the set of generated random path
            indices within ``paths``.
        weight : string or None, optional (default="weight")
            The name of an edge attribute that holds the numerical value
            used as a weight. If None then each edge has weight 1.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        paths : generator of lists
            Generator of `sample_size` paths each with length `path_length`.

        Examples
        --------
        Note that the return value is the list of paths:

        >>> G = nx.star_graph(3)
        >>> random_path = nx.generate_random_paths(G, 2)

        By passing a dictionary into `index_map`, it will build an
        inverted index mapping of nodes to the paths in which that node is present:

        >>> G = nx.star_graph(3)
        >>> index_map = {}
        >>> random_path = nx.generate_random_paths(G, 3, index_map=index_map)
        >>> paths_containing_node_0 = [
        ...     random_path[path_idx] for path_idx in index_map.get(0, [])
        ... ]

        References
        ----------
        .. [1] Zhang, J., Tang, J., Ma, C., Tong, H., Jing, Y., & Li, J.
               Panther: Fast top-k similarity search on large networks.
               In Proceedings of the ACM SIGKDD International Conference
               on Knowledge Discovery and Data Mining (Vol. 2015-August, pp. 1445–1454).
               Association for Computing Machinery. https://doi.org/10.1145/2783258.2783267.

    graph_edit_distance(G1, G2, node_match=None, edge_match=None, node_subst_cost=None, node_del_cost=None, node_ins_cost=None, edge_subst_cost=None, edge_del_cost=None, edge_ins_cost=None, roots=None, upper_bound=None, timeout=None, *, backend=None, **backend_kwargs)
        Returns GED (graph edit distance) between graphs G1 and G2.

        Graph edit distance is a graph similarity measure analogous to
        Levenshtein distance for strings.  It is defined as minimum cost
        of edit path (sequence of node and edge edit operations)
        transforming graph G1 to graph isomorphic to G2.

        Parameters
        ----------
        G1, G2: graphs
            The two graphs G1 and G2 must be of the same type.

        node_match : callable
            A function that returns True if node n1 in G1 and n2 in G2
            should be considered equal during matching.

            The function will be called like

               node_match(G1.nodes[n1], G2.nodes[n2]).

            That is, the function will receive the node attribute
            dictionaries for n1 and n2 as inputs.

            Ignored if node_subst_cost is specified.  If neither
            node_match nor node_subst_cost are specified then node
            attributes are not considered.

        edge_match : callable
            A function that returns True if the edge attribute dictionaries
            for the pair of nodes (u1, v1) in G1 and (u2, v2) in G2 should
            be considered equal during matching.

            The function will be called like

               edge_match(G1[u1][v1], G2[u2][v2]).

            That is, the function will receive the edge attribute
            dictionaries of the edges under consideration.

            Ignored if edge_subst_cost is specified.  If neither
            edge_match nor edge_subst_cost are specified then edge
            attributes are not considered.

        node_subst_cost, node_del_cost, node_ins_cost : callable
            Functions that return the costs of node substitution, node
            deletion, and node insertion, respectively.

            The functions will be called like

               node_subst_cost(G1.nodes[n1], G2.nodes[n2]),
               node_del_cost(G1.nodes[n1]),
               node_ins_cost(G2.nodes[n2]).

            That is, the functions will receive the node attribute
            dictionaries as inputs.  The functions are expected to return
            positive numeric values.

            Function node_subst_cost overrides node_match if specified.
            If neither node_match nor node_subst_cost are specified then
            default node substitution cost of 0 is used (node attributes
            are not considered during matching).

            If node_del_cost is not specified then default node deletion
            cost of 1 is used.  If node_ins_cost is not specified then
            default node insertion cost of 1 is used.

        edge_subst_cost, edge_del_cost, edge_ins_cost : callable
            Functions that return the costs of edge substitution, edge
            deletion, and edge insertion, respectively.

            The functions will be called like

               edge_subst_cost(G1[u1][v1], G2[u2][v2]),
               edge_del_cost(G1[u1][v1]),
               edge_ins_cost(G2[u2][v2]).

            That is, the functions will receive the edge attribute
            dictionaries as inputs.  The functions are expected to return
            positive numeric values.

            Function edge_subst_cost overrides edge_match if specified.
            If neither edge_match nor edge_subst_cost are specified then
            default edge substitution cost of 0 is used (edge attributes
            are not considered during matching).

            If edge_del_cost is not specified then default edge deletion
            cost of 1 is used.  If edge_ins_cost is not specified then
            default edge insertion cost of 1 is used.

        roots : 2-tuple
            Tuple where first element is a node in G1 and the second
            is a node in G2.
            These nodes are forced to be matched in the comparison to
            allow comparison between rooted graphs.

        upper_bound : numeric
            Maximum edit distance to consider.  Return None if no edit
            distance under or equal to upper_bound exists.

        timeout : numeric
            Maximum number of seconds to execute.
            After timeout is met, the current best GED is returned.

        Examples
        --------
        >>> G1 = nx.cycle_graph(6)
        >>> G2 = nx.wheel_graph(7)
        >>> nx.graph_edit_distance(G1, G2)
        7.0

        >>> G1 = nx.star_graph(5)
        >>> G2 = nx.star_graph(5)
        >>> nx.graph_edit_distance(G1, G2, roots=(0, 0))
        0.0
        >>> nx.graph_edit_distance(G1, G2, roots=(1, 0))
        8.0

        See Also
        --------
        optimal_edit_paths, optimize_graph_edit_distance,

        is_isomorphic: test for graph edit distance of 0

        References
        ----------
        .. [1] Zeina Abu-Aisheh, Romain Raveaux, Jean-Yves Ramel, Patrick
           Martineau. An Exact Graph Edit Distance Algorithm for Solving
           Pattern Recognition Problems. 4th International Conference on
           Pattern Recognition Applications and Methods 2015, Jan 2015,
           Lisbon, Portugal. 2015,
           <10.5220/0005209202710278>. <hal-01168816>
           https://hal.archives-ouvertes.fr/hal-01168816

    optimal_edit_paths(G1, G2, node_match=None, edge_match=None, node_subst_cost=None, node_del_cost=None, node_ins_cost=None, edge_subst_cost=None, edge_del_cost=None, edge_ins_cost=None, upper_bound=None, *, backend=None, **backend_kwargs)
        Returns all minimum-cost edit paths transforming G1 to G2.

        Graph edit path is a sequence of node and edge edit operations
        transforming graph G1 to graph isomorphic to G2.  Edit operations
        include substitutions, deletions, and insertions.

        Parameters
        ----------
        G1, G2: graphs
            The two graphs G1 and G2 must be of the same type.

        node_match : callable
            A function that returns True if node n1 in G1 and n2 in G2
            should be considered equal during matching.

            The function will be called like

               node_match(G1.nodes[n1], G2.nodes[n2]).

            That is, the function will receive the node attribute
            dictionaries for n1 and n2 as inputs.

            Ignored if node_subst_cost is specified.  If neither
            node_match nor node_subst_cost are specified then node
            attributes are not considered.

        edge_match : callable
            A function that returns True if the edge attribute dictionaries
            for the pair of nodes (u1, v1) in G1 and (u2, v2) in G2 should
            be considered equal during matching.

            The function will be called like

               edge_match(G1[u1][v1], G2[u2][v2]).

            That is, the function will receive the edge attribute
            dictionaries of the edges under consideration.

            Ignored if edge_subst_cost is specified.  If neither
            edge_match nor edge_subst_cost are specified then edge
            attributes are not considered.

        node_subst_cost, node_del_cost, node_ins_cost : callable
            Functions that return the costs of node substitution, node
            deletion, and node insertion, respectively.

            The functions will be called like

               node_subst_cost(G1.nodes[n1], G2.nodes[n2]),
               node_del_cost(G1.nodes[n1]),
               node_ins_cost(G2.nodes[n2]).

            That is, the functions will receive the node attribute
            dictionaries as inputs.  The functions are expected to return
            positive numeric values.

            Function node_subst_cost overrides node_match if specified.
            If neither node_match nor node_subst_cost are specified then
            default node substitution cost of 0 is used (node attributes
            are not considered during matching).

            If node_del_cost is not specified then default node deletion
            cost of 1 is used.  If node_ins_cost is not specified then
            default node insertion cost of 1 is used.

        edge_subst_cost, edge_del_cost, edge_ins_cost : callable
            Functions that return the costs of edge substitution, edge
            deletion, and edge insertion, respectively.

            The functions will be called like

               edge_subst_cost(G1[u1][v1], G2[u2][v2]),
               edge_del_cost(G1[u1][v1]),
               edge_ins_cost(G2[u2][v2]).

            That is, the functions will receive the edge attribute
            dictionaries as inputs.  The functions are expected to return
            positive numeric values.

            Function edge_subst_cost overrides edge_match if specified.
            If neither edge_match nor edge_subst_cost are specified then
            default edge substitution cost of 0 is used (edge attributes
            are not considered during matching).

            If edge_del_cost is not specified then default edge deletion
            cost of 1 is used.  If edge_ins_cost is not specified then
            default edge insertion cost of 1 is used.

        upper_bound : numeric
            Maximum edit distance to consider.

        Returns
        -------
        edit_paths : list of tuples (node_edit_path, edge_edit_path)
           - node_edit_path : list of tuples ``(u, v)`` indicating node transformations
             between `G1` and `G2`. ``u`` is `None` for insertion, ``v`` is `None`
             for deletion.
           - edge_edit_path : list of tuples ``((u1, v1), (u2, v2))`` indicating edge
             transformations between `G1` and `G2`. ``(None, (u2,v2))`` for insertion
             and ``((u1,v1), None)`` for deletion.

        cost : numeric
            Optimal edit path cost (graph edit distance). When the cost
            is zero, it indicates that `G1` and `G2` are isomorphic.

        Examples
        --------
        >>> G1 = nx.cycle_graph(4)
        >>> G2 = nx.wheel_graph(5)
        >>> paths, cost = nx.optimal_edit_paths(G1, G2)
        >>> len(paths)
        40
        >>> cost
        5.0

        Notes
        -----
        To transform `G1` into a graph isomorphic to `G2`, apply the node
        and edge edits in the returned ``edit_paths``.
        In the case of isomorphic graphs, the cost is zero, and the paths
        represent different isomorphic mappings (isomorphisms). That is, the
        edits involve renaming nodes and edges to match the structure of `G2`.

        See Also
        --------
        graph_edit_distance, optimize_edit_paths

        References
        ----------
        .. [1] Zeina Abu-Aisheh, Romain Raveaux, Jean-Yves Ramel, Patrick
           Martineau. An Exact Graph Edit Distance Algorithm for Solving
           Pattern Recognition Problems. 4th International Conference on
           Pattern Recognition Applications and Methods 2015, Jan 2015,
           Lisbon, Portugal. 2015,
           <10.5220/0005209202710278>. <hal-01168816>
           https://hal.archives-ouvertes.fr/hal-01168816

    optimize_edit_paths(G1, G2, node_match=None, edge_match=None, node_subst_cost=None, node_del_cost=None, node_ins_cost=None, edge_subst_cost=None, edge_del_cost=None, edge_ins_cost=None, upper_bound=None, strictly_decreasing=True, roots=None, timeout=None, *, backend=None, **backend_kwargs)
        GED (graph edit distance) calculation: advanced interface.

        Graph edit path is a sequence of node and edge edit operations
        transforming graph G1 to graph isomorphic to G2.  Edit operations
        include substitutions, deletions, and insertions.

        Graph edit distance is defined as minimum cost of edit path.

        Parameters
        ----------
        G1, G2: graphs
            The two graphs G1 and G2 must be of the same type.

        node_match : callable
            A function that returns True if node n1 in G1 and n2 in G2
            should be considered equal during matching.

            The function will be called like

               node_match(G1.nodes[n1], G2.nodes[n2]).

            That is, the function will receive the node attribute
            dictionaries for n1 and n2 as inputs.

            Ignored if node_subst_cost is specified.  If neither
            node_match nor node_subst_cost are specified then node
            attributes are not considered.

        edge_match : callable
            A function that returns True if the edge attribute dictionaries
            for the pair of nodes (u1, v1) in G1 and (u2, v2) in G2 should
            be considered equal during matching.

            The function will be called like

               edge_match(G1[u1][v1], G2[u2][v2]).

            That is, the function will receive the edge attribute
            dictionaries of the edges under consideration.

            Ignored if edge_subst_cost is specified.  If neither
            edge_match nor edge_subst_cost are specified then edge
            attributes are not considered.

        node_subst_cost, node_del_cost, node_ins_cost : callable
            Functions that return the costs of node substitution, node
            deletion, and node insertion, respectively.

            The functions will be called like

               node_subst_cost(G1.nodes[n1], G2.nodes[n2]),
               node_del_cost(G1.nodes[n1]),
               node_ins_cost(G2.nodes[n2]).

            That is, the functions will receive the node attribute
            dictionaries as inputs.  The functions are expected to return
            positive numeric values.

            Function node_subst_cost overrides node_match if specified.
            If neither node_match nor node_subst_cost are specified then
            default node substitution cost of 0 is used (node attributes
            are not considered during matching).

            If node_del_cost is not specified then default node deletion
            cost of 1 is used.  If node_ins_cost is not specified then
            default node insertion cost of 1 is used.

        edge_subst_cost, edge_del_cost, edge_ins_cost : callable
            Functions that return the costs of edge substitution, edge
            deletion, and edge insertion, respectively.

            The functions will be called like

               edge_subst_cost(G1[u1][v1], G2[u2][v2]),
               edge_del_cost(G1[u1][v1]),
               edge_ins_cost(G2[u2][v2]).

            That is, the functions will receive the edge attribute
            dictionaries as inputs.  The functions are expected to return
            positive numeric values.

            Function edge_subst_cost overrides edge_match if specified.
            If neither edge_match nor edge_subst_cost are specified then
            default edge substitution cost of 0 is used (edge attributes
            are not considered during matching).

            If edge_del_cost is not specified then default edge deletion
            cost of 1 is used.  If edge_ins_cost is not specified then
            default edge insertion cost of 1 is used.

        upper_bound : numeric
            Maximum edit distance to consider.

        strictly_decreasing : bool
            If True, return consecutive approximations of strictly
            decreasing cost.  Otherwise, return all edit paths of cost
            less than or equal to the previous minimum cost.

        roots : 2-tuple
            Tuple where first element is a node in G1 and the second
            is a node in G2.
            These nodes are forced to be matched in the comparison to
            allow comparison between rooted graphs.

        timeout : numeric
            Maximum number of seconds to execute.
            After timeout is met, the current best GED is returned.

        Returns
        -------
        Generator of tuples (node_edit_path, edge_edit_path, cost)
            node_edit_path : list of tuples (u, v)
            edge_edit_path : list of tuples ((u1, v1), (u2, v2))
            cost : numeric

        See Also
        --------
        graph_edit_distance, optimize_graph_edit_distance, optimal_edit_paths

        References
        ----------
        .. [1] Zeina Abu-Aisheh, Romain Raveaux, Jean-Yves Ramel, Patrick
           Martineau. An Exact Graph Edit Distance Algorithm for Solving
           Pattern Recognition Problems. 4th International Conference on
           Pattern Recognition Applications and Methods 2015, Jan 2015,
           Lisbon, Portugal. 2015,
           <10.5220/0005209202710278>. <hal-01168816>
           https://hal.archives-ouvertes.fr/hal-01168816

    optimize_graph_edit_distance(G1, G2, node_match=None, edge_match=None, node_subst_cost=None, node_del_cost=None, node_ins_cost=None, edge_subst_cost=None, edge_del_cost=None, edge_ins_cost=None, upper_bound=None, *, backend=None, **backend_kwargs)
        Returns consecutive approximations of GED (graph edit distance)
        between graphs G1 and G2.

        Graph edit distance is a graph similarity measure analogous to
        Levenshtein distance for strings.  It is defined as minimum cost
        of edit path (sequence of node and edge edit operations)
        transforming graph G1 to graph isomorphic to G2.

        Parameters
        ----------
        G1, G2: graphs
            The two graphs G1 and G2 must be of the same type.

        node_match : callable
            A function that returns True if node n1 in G1 and n2 in G2
            should be considered equal during matching.

            The function will be called like

               node_match(G1.nodes[n1], G2.nodes[n2]).

            That is, the function will receive the node attribute
            dictionaries for n1 and n2 as inputs.

            Ignored if node_subst_cost is specified.  If neither
            node_match nor node_subst_cost are specified then node
            attributes are not considered.

        edge_match : callable
            A function that returns True if the edge attribute dictionaries
            for the pair of nodes (u1, v1) in G1 and (u2, v2) in G2 should
            be considered equal during matching.

            The function will be called like

               edge_match(G1[u1][v1], G2[u2][v2]).

            That is, the function will receive the edge attribute
            dictionaries of the edges under consideration.

            Ignored if edge_subst_cost is specified.  If neither
            edge_match nor edge_subst_cost are specified then edge
            attributes are not considered.

        node_subst_cost, node_del_cost, node_ins_cost : callable
            Functions that return the costs of node substitution, node
            deletion, and node insertion, respectively.

            The functions will be called like

               node_subst_cost(G1.nodes[n1], G2.nodes[n2]),
               node_del_cost(G1.nodes[n1]),
               node_ins_cost(G2.nodes[n2]).

            That is, the functions will receive the node attribute
            dictionaries as inputs.  The functions are expected to return
            positive numeric values.

            Function node_subst_cost overrides node_match if specified.
            If neither node_match nor node_subst_cost are specified then
            default node substitution cost of 0 is used (node attributes
            are not considered during matching).

            If node_del_cost is not specified then default node deletion
            cost of 1 is used.  If node_ins_cost is not specified then
            default node insertion cost of 1 is used.

        edge_subst_cost, edge_del_cost, edge_ins_cost : callable
            Functions that return the costs of edge substitution, edge
            deletion, and edge insertion, respectively.

            The functions will be called like

               edge_subst_cost(G1[u1][v1], G2[u2][v2]),
               edge_del_cost(G1[u1][v1]),
               edge_ins_cost(G2[u2][v2]).

            That is, the functions will receive the edge attribute
            dictionaries as inputs.  The functions are expected to return
            positive numeric values.

            Function edge_subst_cost overrides edge_match if specified.
            If neither edge_match nor edge_subst_cost are specified then
            default edge substitution cost of 0 is used (edge attributes
            are not considered during matching).

            If edge_del_cost is not specified then default edge deletion
            cost of 1 is used.  If edge_ins_cost is not specified then
            default edge insertion cost of 1 is used.

        upper_bound : numeric
            Maximum edit distance to consider.

        Returns
        -------
        Generator of consecutive approximations of graph edit distance.

        Examples
        --------
        >>> G1 = nx.cycle_graph(6)
        >>> G2 = nx.wheel_graph(7)
        >>> for v in nx.optimize_graph_edit_distance(G1, G2):
        ...     minv = v
        >>> minv
        7.0

        See Also
        --------
        graph_edit_distance, optimize_edit_paths

        References
        ----------
        .. [1] Zeina Abu-Aisheh, Romain Raveaux, Jean-Yves Ramel, Patrick
           Martineau. An Exact Graph Edit Distance Algorithm for Solving
           Pattern Recognition Problems. 4th International Conference on
           Pattern Recognition Applications and Methods 2015, Jan 2015,
           Lisbon, Portugal. 2015,
           <10.5220/0005209202710278>. <hal-01168816>
           https://hal.archives-ouvertes.fr/hal-01168816

    panther_similarity(G, source, k=5, path_length=5, c=0.5, delta=0.1, eps=None, weight='weight', *, backend=None, **backend_kwargs)
        Returns the Panther similarity of nodes in the graph `G` to node ``v``.

        Panther is a similarity metric that says "two objects are considered
        to be similar if they frequently appear on the same paths." [1]_.

        Parameters
        ----------
        G : NetworkX graph
            A NetworkX graph
        source : node
            Source node for which to find the top `k` similar other nodes
        k : int (default = 5)
            The number of most similar nodes to return.
        path_length : int (default = 5)
            How long the randomly generated paths should be (``T`` in [1]_)
        c : float (default = 0.5)
            A universal positive constant used to scale the number
            of sample random paths to generate.
        delta : float (default = 0.1)
            The probability that the similarity $S$ is not an epsilon-approximation to (R, phi),
            where $R$ is the number of random paths and $\phi$ is the probability
            that an element sampled from a set $A \subseteq D$, where $D$ is the domain.
        eps : float or None (default = None)
            The error bound. Per [1]_, a good value is ``sqrt(1/|E|)``. Therefore,
            if no value is provided, the recommended computed value will be used.
        weight : string or None, optional (default="weight")
            The name of an edge attribute that holds the numerical value
            used as a weight. If None then each edge has weight 1.

        Returns
        -------
        similarity : dictionary
            Dictionary of nodes to similarity scores (as floats). Note:
            the self-similarity (i.e., ``v``) will not be included in
            the returned dictionary. So, for ``k = 5``, a dictionary of
            top 4 nodes and their similarity scores will be returned.

        Raises
        ------
        NetworkXUnfeasible
            If `source` is an isolated node.

        NodeNotFound
            If `source` is not in `G`.

        Notes
        -----
            The isolated nodes in `G` are ignored.

        Examples
        --------
        >>> G = nx.star_graph(10)
        >>> sim = nx.panther_similarity(G, 0)

        References
        ----------
        .. [1] Zhang, J., Tang, J., Ma, C., Tong, H., Jing, Y., & Li, J.
               Panther: Fast top-k similarity search on large networks.
               In Proceedings of the ACM SIGKDD International Conference
               on Knowledge Discovery and Data Mining (Vol. 2015-August, pp. 1445–1454).
               Association for Computing Machinery. https://doi.org/10.1145/2783258.2783267.

    simrank_similarity(G, source=None, target=None, importance_factor=0.9, max_iterations=1000, tolerance=0.0001, *, backend=None, **backend_kwargs)
        Returns the SimRank similarity of nodes in the graph ``G``.

        SimRank is a similarity metric that says "two objects are considered
        to be similar if they are referenced by similar objects." [1]_.

        The pseudo-code definition from the paper is::

            def simrank(G, u, v):
                in_neighbors_u = G.predecessors(u)
                in_neighbors_v = G.predecessors(v)
                scale = C / (len(in_neighbors_u) * len(in_neighbors_v))
                return scale * sum(
                    simrank(G, w, x) for w, x in product(in_neighbors_u, in_neighbors_v)
                )

        where ``G`` is the graph, ``u`` is the source, ``v`` is the target,
        and ``C`` is a float decay or importance factor between 0 and 1.

        The SimRank algorithm for determining node similarity is defined in
        [2]_.

        Parameters
        ----------
        G : NetworkX graph
            A NetworkX graph

        source : node
            If this is specified, the returned dictionary maps each node
            ``v`` in the graph to the similarity between ``source`` and
            ``v``.

        target : node
            If both ``source`` and ``target`` are specified, the similarity
            value between ``source`` and ``target`` is returned. If
            ``target`` is specified but ``source`` is not, this argument is
            ignored.

        importance_factor : float
            The relative importance of indirect neighbors with respect to
            direct neighbors.

        max_iterations : integer
            Maximum number of iterations.

        tolerance : float
            Error tolerance used to check convergence. When an iteration of
            the algorithm finds that no similarity value changes more than
            this amount, the algorithm halts.

        Returns
        -------
        similarity : dictionary or float
            If ``source`` and ``target`` are both ``None``, this returns a
            dictionary of dictionaries, where keys are node pairs and value
            are similarity of the pair of nodes.

            If ``source`` is not ``None`` but ``target`` is, this returns a
            dictionary mapping node to the similarity of ``source`` and that
            node.

            If neither ``source`` nor ``target`` is ``None``, this returns
            the similarity value for the given pair of nodes.

        Raises
        ------
        ExceededMaxIterations
            If the algorithm does not converge within ``max_iterations``.

        NodeNotFound
            If either ``source`` or ``target`` is not in `G`.

        Examples
        --------
        >>> G = nx.cycle_graph(2)
        >>> nx.simrank_similarity(G)
        {0: {0: 1.0, 1: 0.0}, 1: {0: 0.0, 1: 1.0}}
        >>> nx.simrank_similarity(G, source=0)
        {0: 1.0, 1: 0.0}
        >>> nx.simrank_similarity(G, source=0, target=0)
        1.0

        The result of this function can be converted to a numpy array
        representing the SimRank matrix by using the node order of the
        graph to determine which row and column represent each node.
        Other ordering of nodes is also possible.

        >>> import numpy as np
        >>> sim = nx.simrank_similarity(G)
        >>> np.array([[sim[u][v] for v in G] for u in G])
        array([[1., 0.],
               [0., 1.]])
        >>> sim_1d = nx.simrank_similarity(G, source=0)
        >>> np.array([sim[0][v] for v in G])
        array([1., 0.])

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/SimRank
        .. [2] G. Jeh and J. Widom.
               "SimRank: a measure of structural-context similarity",
               In KDD'02: Proceedings of the Eighth ACM SIGKDD
               International Conference on Knowledge Discovery and Data Mining,
               pp. 538--543. ACM Press, 2002.

DATA
    __all__ = ['graph_edit_distance', 'optimal_edit_paths', 'optimize_grap...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\similarity.py

networkx.simple_cycles
Python Library Documentation: function simple_cycles in module networkx.algorithms.cycles

simple_cycles(G, length_bound=None, *, backend=None, **backend_kwargs)
    Find simple cycles (elementary circuits) of a graph.

    A "simple cycle", or "elementary circuit", is a closed path where
    no node appears twice.  In a directed graph, two simple cycles are distinct
    if they are not cyclic permutations of each other.  In an undirected graph,
    two simple cycles are distinct if they are not cyclic permutations of each
    other nor of the other's reversal.

    Optionally, the cycles are bounded in length.  In the unbounded case, we use
    a nonrecursive, iterator/generator version of Johnson's algorithm [1]_.  In
    the bounded case, we use a version of the algorithm of Gupta and
    Suzumura [2]_. There may be better algorithms for some cases [3]_ [4]_ [5]_.

    The algorithms of Johnson, and Gupta and Suzumura, are enhanced by some
    well-known preprocessing techniques.  When `G` is directed, we restrict our
    attention to strongly connected components of `G`, generate all simple cycles
    containing a certain node, remove that node, and further decompose the
    remainder into strongly connected components.  When `G` is undirected, we
    restrict our attention to biconnected components, generate all simple cycles
    containing a particular edge, remove that edge, and further decompose the
    remainder into biconnected components.

    Note that multigraphs are supported by this function -- and in undirected
    multigraphs, a pair of parallel edges is considered a cycle of length 2.
    Likewise, self-loops are considered to be cycles of length 1.  We define
    cycles as sequences of nodes; so the presence of loops and parallel edges
    does not change the number of simple cycles in a graph.

    Parameters
    ----------
    G : NetworkX Graph
       A networkx graph. Undirected, directed, and multigraphs are all supported.

    length_bound : int or None, optional (default=None)
       If `length_bound` is an int, generate all simple cycles of `G` with length at
       most `length_bound`.  Otherwise, generate all simple cycles of `G`.

    Yields
    ------
    list of nodes
       Each cycle is represented by a list of nodes along the cycle.

    Examples
    --------
    >>> G = nx.DiGraph([(0, 0), (0, 1), (0, 2), (1, 2), (2, 0), (2, 1), (2, 2)])
    >>> sorted(nx.simple_cycles(G))
    [[0], [0, 1, 2], [0, 2], [1, 2], [2]]

    To filter the cycles so that they don't include certain nodes or edges,
    copy your graph and eliminate those nodes or edges before calling.
    For example, to exclude self-loops from the above example:

    >>> H = G.copy()
    >>> H.remove_edges_from(nx.selfloop_edges(G))
    >>> sorted(nx.simple_cycles(H))
    [[0, 1, 2], [0, 2], [1, 2]]

    Notes
    -----
    When `length_bound` is None, the time complexity is $O((n+e)(c+1))$ for $n$
    nodes, $e$ edges and $c$ simple circuits.  Otherwise, when ``length_bound > 1``,
    the time complexity is $O((c+n)(k-1)d^k)$ where $d$ is the average degree of
    the nodes of `G` and $k$ = `length_bound`.

    Raises
    ------
    ValueError
        when ``length_bound < 0``.

    References
    ----------
    .. [1] Finding all the elementary circuits of a directed graph.
       D. B. Johnson, SIAM Journal on Computing 4, no. 1, 77-84, 1975.
       https://doi.org/10.1137/0204007
    .. [2] Finding All Bounded-Length Simple Cycles in a Directed Graph
       A. Gupta and T. Suzumura https://arxiv.org/abs/2105.10094
    .. [3] Enumerating the cycles of a digraph: a new preprocessing strategy.
       G. Loizou and P. Thanish, Information Sciences, v. 27, 163-182, 1982.
    .. [4] A search strategy for the elementary cycles of a directed graph.
       J.L. Szwarcfiter and P.E. Lauer, BIT NUMERICAL MATHEMATICS,
       v. 16, no. 2, 192-204, 1976.
    .. [5] Optimal Listing of Cycles and st-Paths in Undirected Graphs
        R. Ferreira and R. Grossi and A. Marino and N. Pisanti and R. Rizzi and
        G. Sacomoto https://arxiv.org/abs/1205.2766

    See Also
    --------
    cycle_basis
    chordless_cycles
networkx.simple_paths
Python Library Documentation: module networkx.algorithms.simple_paths in networkx.algorithms

NAME
    networkx.algorithms.simple_paths

FUNCTIONS
    all_simple_edge_paths(G, source, target, cutoff=None, *, backend=None, **backend_kwargs)
        Generate lists of edges for all simple paths in G from source to target.

        A simple path is a path with no repeated nodes.

        Parameters
        ----------
        G : NetworkX graph

        source : node
           Starting node for path

        target : nodes
           Single node or iterable of nodes at which to end path

        cutoff : integer, optional
            Depth to stop the search. Only paths of length <= cutoff are returned.

        Returns
        -------
        path_generator: generator
           A generator that produces lists of simple paths.  If there are no paths
           between the source and target within the given cutoff the generator
           produces no output.
           For multigraphs, the list of edges have elements of the form `(u,v,k)`.
           Where `k` corresponds to the edge key.

        Examples
        --------

        Print the simple path edges of a Graph::

            >>> g = nx.Graph([(1, 2), (2, 4), (1, 3), (3, 4)])
            >>> for path in sorted(nx.all_simple_edge_paths(g, 1, 4)):
            ...     print(path)
            [(1, 2), (2, 4)]
            [(1, 3), (3, 4)]

        Print the simple path edges of a MultiGraph. Returned edges come with
        their associated keys::

            >>> mg = nx.MultiGraph()
            >>> mg.add_edge(1, 2, key="k0")
            'k0'
            >>> mg.add_edge(1, 2, key="k1")
            'k1'
            >>> mg.add_edge(2, 3, key="k0")
            'k0'
            >>> for path in sorted(nx.all_simple_edge_paths(mg, 1, 3)):
            ...     print(path)
            [(1, 2, 'k0'), (2, 3, 'k0')]
            [(1, 2, 'k1'), (2, 3, 'k0')]

        When ``source`` is one of the targets, the empty path starting and ending at
        ``source`` without traversing any edge is considered a valid simple edge path
        and is included in the results:

            >>> G = nx.Graph()
            >>> G.add_node(0)
            >>> paths = list(nx.all_simple_edge_paths(G, 0, 0))
            >>> for path in paths:
            ...     print(path)
            []
            >>> len(paths)
            1


        Notes
        -----
        This algorithm uses a modified depth-first search to generate the
        paths [1]_.  A single path can be found in $O(V+E)$ time but the
        number of simple paths in a graph can be very large, e.g. $O(n!)$ in
        the complete graph of order $n$.

        References
        ----------
        .. [1] R. Sedgewick, "Algorithms in C, Part 5: Graph Algorithms",
           Addison Wesley Professional, 3rd ed., 2001.

        See Also
        --------
        all_shortest_paths, shortest_path, all_simple_paths

    all_simple_paths(G, source, target, cutoff=None, *, backend=None, **backend_kwargs)
        Generate all simple paths in the graph G from source to target.

        A simple path is a path with no repeated nodes.

        Parameters
        ----------
        G : NetworkX graph

        source : node
           Starting node for path

        target : nodes
           Single node or iterable of nodes at which to end path

        cutoff : integer, optional
            Depth to stop the search. Only paths of length <= cutoff are returned.

        Returns
        -------
        path_generator: generator
           A generator that produces lists of simple paths.  If there are no paths
           between the source and target within the given cutoff the generator
           produces no output. If it is possible to traverse the same sequence of
           nodes in multiple ways, namely through parallel edges, then it will be
           returned multiple times (once for each viable edge combination).

        Examples
        --------
        This iterator generates lists of nodes::

            >>> G = nx.complete_graph(4)
            >>> for path in nx.all_simple_paths(G, source=0, target=3):
            ...     print(path)
            ...
            [0, 1, 2, 3]
            [0, 1, 3]
            [0, 2, 1, 3]
            [0, 2, 3]
            [0, 3]

        You can generate only those paths that are shorter than a certain
        length by using the `cutoff` keyword argument::

            >>> paths = nx.all_simple_paths(G, source=0, target=3, cutoff=2)
            >>> print(list(paths))
            [[0, 1, 3], [0, 2, 3], [0, 3]]

        To get each path as the corresponding list of edges, you can use the
        :func:`networkx.utils.pairwise` helper function::

            >>> paths = nx.all_simple_paths(G, source=0, target=3)
            >>> for path in map(nx.utils.pairwise, paths):
            ...     print(list(path))
            [(0, 1), (1, 2), (2, 3)]
            [(0, 1), (1, 3)]
            [(0, 2), (2, 1), (1, 3)]
            [(0, 2), (2, 3)]
            [(0, 3)]

        Pass an iterable of nodes as target to generate all paths ending in any of several nodes::

            >>> G = nx.complete_graph(4)
            >>> for path in nx.all_simple_paths(G, source=0, target=[3, 2]):
            ...     print(path)
            ...
            [0, 1, 2]
            [0, 1, 2, 3]
            [0, 1, 3]
            [0, 1, 3, 2]
            [0, 2]
            [0, 2, 1, 3]
            [0, 2, 3]
            [0, 3]
            [0, 3, 1, 2]
            [0, 3, 2]

        The singleton path from ``source`` to itself is considered a simple path and is
        included in the results:

            >>> G = nx.empty_graph(5)
            >>> list(nx.all_simple_paths(G, source=0, target=0))
            [[0]]

            >>> G = nx.path_graph(3)
            >>> list(nx.all_simple_paths(G, source=0, target={0, 1, 2}))
            [[0], [0, 1], [0, 1, 2]]

        Iterate over each path from the root nodes to the leaf nodes in a
        directed acyclic graph using a functional programming approach::

            >>> from itertools import chain
            >>> from itertools import product
            >>> from itertools import starmap
            >>> from functools import partial
            >>>
            >>> chaini = chain.from_iterable
            >>>
            >>> G = nx.DiGraph([(0, 1), (1, 2), (0, 3), (3, 2)])
            >>> roots = (v for v, d in G.in_degree() if d == 0)
            >>> leaves = (v for v, d in G.out_degree() if d == 0)
            >>> all_paths = partial(nx.all_simple_paths, G)
            >>> list(chaini(starmap(all_paths, product(roots, leaves))))
            [[0, 1, 2], [0, 3, 2]]

        The same list computed using an iterative approach::

            >>> G = nx.DiGraph([(0, 1), (1, 2), (0, 3), (3, 2)])
            >>> roots = (v for v, d in G.in_degree() if d == 0)
            >>> leaves = (v for v, d in G.out_degree() if d == 0)
            >>> all_paths = []
            >>> for root in roots:
            ...     for leaf in leaves:
            ...         paths = nx.all_simple_paths(G, root, leaf)
            ...         all_paths.extend(paths)
            >>> all_paths
            [[0, 1, 2], [0, 3, 2]]

        Iterate over each path from the root nodes to the leaf nodes in a
        directed acyclic graph passing all leaves together to avoid unnecessary
        compute::

            >>> G = nx.DiGraph([(0, 1), (2, 1), (1, 3), (1, 4)])
            >>> roots = (v for v, d in G.in_degree() if d == 0)
            >>> leaves = [v for v, d in G.out_degree() if d == 0]
            >>> all_paths = []
            >>> for root in roots:
            ...     paths = nx.all_simple_paths(G, root, leaves)
            ...     all_paths.extend(paths)
            >>> all_paths
            [[0, 1, 3], [0, 1, 4], [2, 1, 3], [2, 1, 4]]

        If parallel edges offer multiple ways to traverse a given sequence of
        nodes, this sequence of nodes will be returned multiple times:

            >>> G = nx.MultiDiGraph([(0, 1), (0, 1), (1, 2)])
            >>> list(nx.all_simple_paths(G, 0, 2))
            [[0, 1, 2], [0, 1, 2]]

        Notes
        -----
        This algorithm uses a modified depth-first search to generate the
        paths [1]_.  A single path can be found in $O(V+E)$ time but the
        number of simple paths in a graph can be very large, e.g. $O(n!)$ in
        the complete graph of order $n$.

        This function does not check that a path exists between `source` and
        `target`. For large graphs, this may result in very long runtimes.
        Consider using `has_path` to check that a path exists between `source` and
        `target` before calling this function on large graphs.

        References
        ----------
        .. [1] R. Sedgewick, "Algorithms in C, Part 5: Graph Algorithms",
           Addison Wesley Professional, 3rd ed., 2001.

        See Also
        --------
        all_shortest_paths, shortest_path, has_path

    is_simple_path(G, nodes, *, backend=None, **backend_kwargs)
        Returns True if and only if `nodes` form a simple path in `G`.

        A *simple path* in a graph is a nonempty sequence of nodes in which
        no node appears more than once in the sequence, and each adjacent
        pair of nodes in the sequence is adjacent in the graph.

        Parameters
        ----------
        G : graph
            A NetworkX graph.
        nodes : list
            A list of one or more nodes in the graph `G`.

        Returns
        -------
        bool
            Whether the given list of nodes represents a simple path in `G`.

        Notes
        -----
        An empty list of nodes is not a path but a list of one node is a
        path. Here's an explanation why.

        This function operates on *node paths*. One could also consider
        *edge paths*. There is a bijection between node paths and edge
        paths.

        The *length of a path* is the number of edges in the path, so a list
        of nodes of length *n* corresponds to a path of length *n* - 1.
        Thus the smallest edge path would be a list of zero edges, the empty
        path. This corresponds to a list of one node.

        To convert between a node path and an edge path, you can use code
        like the following::

            >>> from networkx.utils import pairwise
            >>> nodes = [0, 1, 2, 3]
            >>> edges = list(pairwise(nodes))
            >>> edges
            [(0, 1), (1, 2), (2, 3)]
            >>> nodes = [edges[0][0]] + [v for u, v in edges]
            >>> nodes
            [0, 1, 2, 3]

        Examples
        --------
        >>> G = nx.cycle_graph(4)
        >>> nx.is_simple_path(G, [2, 3, 0])
        True
        >>> nx.is_simple_path(G, [0, 2])
        False

    shortest_simple_paths(G, source, target, weight=None, *, backend=None, **backend_kwargs)
        Generate all simple paths in the graph G from source to target,
           starting from shortest ones.

        A simple path is a path with no repeated nodes.

        If a weighted shortest path search is to be used, no negative weights
        are allowed.

        Parameters
        ----------
        G : NetworkX graph

        source : node
           Starting node for path

        target : node
           Ending node for path

        weight : string or function
            If it is a string, it is the name of the edge attribute to be
            used as a weight.

            If it is a function, the weight of an edge is the value returned
            by the function. The function must accept exactly three positional
            arguments: the two endpoints of an edge and the dictionary of edge
            attributes for that edge. The function must return a number or None.
            The weight function can be used to hide edges by returning None.
            So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
            will find the shortest red path.

            If None all edges are considered to have unit weight. Default
            value None.

        Returns
        -------
        path_generator: generator
           A generator that produces lists of simple paths, in order from
           shortest to longest.

        Raises
        ------
        NetworkXNoPath
           If no path exists between source and target.

        NetworkXError
           If source or target nodes are not in the input graph.

        NetworkXNotImplemented
           If the input graph is a Multi[Di]Graph.

        Examples
        --------

        >>> G = nx.cycle_graph(7)
        >>> paths = list(nx.shortest_simple_paths(G, 0, 3))
        >>> print(paths)
        [[0, 1, 2, 3], [0, 6, 5, 4, 3]]

        You can use this function to efficiently compute the k shortest/best
        paths between two nodes.

        >>> from itertools import islice
        >>> def k_shortest_paths(G, source, target, k, weight=None):
        ...     return list(
        ...         islice(nx.shortest_simple_paths(G, source, target, weight=weight), k)
        ...     )
        >>> for path in k_shortest_paths(G, 0, 3, 2):
        ...     print(path)
        [0, 1, 2, 3]
        [0, 6, 5, 4, 3]

        Notes
        -----
        This procedure is based on algorithm by Jin Y. Yen [1]_.  Finding
        the first $K$ paths requires $O(KN^3)$ operations.

        See Also
        --------
        all_shortest_paths
        shortest_path
        all_simple_paths

        References
        ----------
        .. [1] Jin Y. Yen, "Finding the K Shortest Loopless Paths in a
           Network", Management Science, Vol. 17, No. 11, Theory Series
           (Jul., 1971), pp. 712-716.

DATA
    __all__ = ['all_simple_paths', 'is_simple_path', 'shortest_simple_path...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\simple_paths.py

networkx.simrank_similarity
Python Library Documentation: function simrank_similarity in module networkx.algorithms.similarity

simrank_similarity(G, source=None, target=None, importance_factor=0.9, max_iterations=1000, tolerance=0.0001, *, backend=None, **backend_kwargs)
    Returns the SimRank similarity of nodes in the graph ``G``.

    SimRank is a similarity metric that says "two objects are considered
    to be similar if they are referenced by similar objects." [1]_.

    The pseudo-code definition from the paper is::

        def simrank(G, u, v):
            in_neighbors_u = G.predecessors(u)
            in_neighbors_v = G.predecessors(v)
            scale = C / (len(in_neighbors_u) * len(in_neighbors_v))
            return scale * sum(
                simrank(G, w, x) for w, x in product(in_neighbors_u, in_neighbors_v)
            )

    where ``G`` is the graph, ``u`` is the source, ``v`` is the target,
    and ``C`` is a float decay or importance factor between 0 and 1.

    The SimRank algorithm for determining node similarity is defined in
    [2]_.

    Parameters
    ----------
    G : NetworkX graph
        A NetworkX graph

    source : node
        If this is specified, the returned dictionary maps each node
        ``v`` in the graph to the similarity between ``source`` and
        ``v``.

    target : node
        If both ``source`` and ``target`` are specified, the similarity
        value between ``source`` and ``target`` is returned. If
        ``target`` is specified but ``source`` is not, this argument is
        ignored.

    importance_factor : float
        The relative importance of indirect neighbors with respect to
        direct neighbors.

    max_iterations : integer
        Maximum number of iterations.

    tolerance : float
        Error tolerance used to check convergence. When an iteration of
        the algorithm finds that no similarity value changes more than
        this amount, the algorithm halts.

    Returns
    -------
    similarity : dictionary or float
        If ``source`` and ``target`` are both ``None``, this returns a
        dictionary of dictionaries, where keys are node pairs and value
        are similarity of the pair of nodes.

        If ``source`` is not ``None`` but ``target`` is, this returns a
        dictionary mapping node to the similarity of ``source`` and that
        node.

        If neither ``source`` nor ``target`` is ``None``, this returns
        the similarity value for the given pair of nodes.

    Raises
    ------
    ExceededMaxIterations
        If the algorithm does not converge within ``max_iterations``.

    NodeNotFound
        If either ``source`` or ``target`` is not in `G`.

    Examples
    --------
    >>> G = nx.cycle_graph(2)
    >>> nx.simrank_similarity(G)
    {0: {0: 1.0, 1: 0.0}, 1: {0: 0.0, 1: 1.0}}
    >>> nx.simrank_similarity(G, source=0)
    {0: 1.0, 1: 0.0}
    >>> nx.simrank_similarity(G, source=0, target=0)
    1.0

    The result of this function can be converted to a numpy array
    representing the SimRank matrix by using the node order of the
    graph to determine which row and column represent each node.
    Other ordering of nodes is also possible.

    >>> import numpy as np
    >>> sim = nx.simrank_similarity(G)
    >>> np.array([[sim[u][v] for v in G] for u in G])
    array([[1., 0.],
           [0., 1.]])
    >>> sim_1d = nx.simrank_similarity(G, source=0)
    >>> np.array([sim[0][v] for v in G])
    array([1., 0.])

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/SimRank
    .. [2] G. Jeh and J. Widom.
           "SimRank: a measure of structural-context similarity",
           In KDD'02: Proceedings of the Eighth ACM SIGKDD
           International Conference on Knowledge Discovery and Data Mining,
           pp. 538--543. ACM Press, 2002.
networkx.single_source_all_shortest_paths
Python Library Documentation: function single_source_all_shortest_paths in module networkx.algorithms.shortest_paths.generic

single_source_all_shortest_paths(G, source, weight=None, method='dijkstra', *, backend=None, **backend_kwargs)
    Compute all shortest simple paths from the given source in the graph.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Starting node for path.

    weight : None, string or function, optional (default = None)
        If None, every edge has weight/distance/cost 1.
        If a string, use this edge attribute as the edge weight.
        Any edge attribute not present defaults to 1.
        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly
        three positional arguments: the two endpoints of an edge and
        the dictionary of edge attributes for that edge.
        The function must return a number.

    method : string, optional (default = 'dijkstra')
       The algorithm to use to compute the path lengths.
       Supported options: 'dijkstra', 'bellman-ford'.
       Other inputs produce a ValueError.
       If `weight` is None, unweighted graph methods are used, and this
       suggestion is ignored.

    Returns
    -------
    paths : generator of dictionary
        A generator of all paths between source and all nodes in the graph.

    Raises
    ------
    ValueError
        If `method` is not among the supported options.

    Examples
    --------
    >>> G = nx.Graph()
    >>> nx.add_path(G, [0, 1, 2, 3, 0])
    >>> dict(nx.single_source_all_shortest_paths(G, source=0))
    {0: [[0]], 1: [[0, 1]], 2: [[0, 1, 2], [0, 3, 2]], 3: [[0, 3]]}

    Notes
    -----
    There may be many shortest paths between the source and target.  If G
    contains zero-weight cycles, this function will not produce all shortest
    paths because doing so would produce infinitely many paths of unbounded
    length -- instead, we only produce the shortest simple paths.

    See Also
    --------
    shortest_path
    all_shortest_paths
    single_source_shortest_path
    all_pairs_shortest_path
    all_pairs_all_shortest_paths
networkx.single_source_bellman_ford
Python Library Documentation: function single_source_bellman_ford in module networkx.algorithms.shortest_paths.weighted

single_source_bellman_ford(G, source, target=None, weight='weight', *, backend=None, **backend_kwargs)
    Compute shortest paths and lengths in a weighted graph G.

    Uses Bellman-Ford algorithm for shortest paths.

    Parameters
    ----------
    G : NetworkX graph

    source : node label
        Starting node for path

    target : node label, optional
        Ending node for path

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

    Returns
    -------
    distance, path : pair of dictionaries, or numeric and list
        If target is None, returns a tuple of two dictionaries keyed by node.
        The first dictionary stores distance from one of the source nodes.
        The second stores the path from one of the sources to that node.
        If target is not None, returns a tuple of (distance, path) where
        distance is the distance from source to target and path is a list
        representing the path from source to target.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> length, path = nx.single_source_bellman_ford(G, 0)
    >>> length[4]
    4
    >>> for node in [0, 1, 2, 3, 4]:
    ...     print(f"{node}: {length[node]}")
    0: 0
    1: 1
    2: 2
    3: 3
    4: 4
    >>> path[4]
    [0, 1, 2, 3, 4]
    >>> length, path = nx.single_source_bellman_ford(G, 0, 1)
    >>> length
    1
    >>> path
    [0, 1]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    See Also
    --------
    single_source_dijkstra
    single_source_bellman_ford_path
    single_source_bellman_ford_path_length
networkx.single_source_bellman_ford_path
Python Library Documentation: function single_source_bellman_ford_path in module networkx.algorithms.shortest_paths.weighted

single_source_bellman_ford_path(G, source, weight='weight', *, backend=None, **backend_kwargs)
    Compute shortest path between source and all other reachable
    nodes for a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    source : node
        Starting node for path.

    weight : string or function (default="weight")
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

    Returns
    -------
    paths : dictionary
        Dictionary of shortest path lengths keyed by target.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> path = nx.single_source_bellman_ford_path(G, 0)
    >>> path[4]
    [0, 1, 2, 3, 4]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    See Also
    --------
    single_source_dijkstra, single_source_bellman_ford
networkx.single_source_bellman_ford_path_length
Python Library Documentation: function single_source_bellman_ford_path_length in module networkx.algorithms.shortest_paths.weighted

single_source_bellman_ford_path_length(G, source, weight='weight', *, backend=None, **backend_kwargs)
    Compute the shortest path length between source and all other
    reachable nodes for a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    source : node label
        Starting node for path

    weight : string or function (default="weight")
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number.

    Returns
    -------
    length : dictionary
        Dictionary of shortest path length keyed by target

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> length = nx.single_source_bellman_ford_path_length(G, 0)
    >>> length[4]
    4
    >>> for node in [0, 1, 2, 3, 4]:
    ...     print(f"{node}: {length[node]}")
    0: 0
    1: 1
    2: 2
    3: 3
    4: 4

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    See Also
    --------
    single_source_dijkstra, single_source_bellman_ford
networkx.single_source_dijkstra
Python Library Documentation: function single_source_dijkstra in module networkx.algorithms.shortest_paths.weighted

single_source_dijkstra(G, source, target=None, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
    Find shortest weighted paths and lengths from a source node.

    Compute the shortest path length between source and all other
    reachable nodes for a weighted graph.

    Uses Dijkstra's algorithm to compute shortest paths and lengths
    between a source and all other reachable nodes in a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    source : node label
        Starting node for path

    target : node label, optional
        Ending node for path

    cutoff : integer or float, optional
        Length (sum of edge weights) at which the search is stopped.
        If cutoff is provided, only return paths with summed weight <= cutoff.


    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Returns
    -------
    distance, path : pair of dictionaries, or numeric and list.
        If target is None, paths and lengths to all nodes are computed.
        The return value is a tuple of two dictionaries keyed by target nodes.
        The first dictionary stores distance to each target node.
        The second stores the path to each target node.
        If target is not None, returns a tuple (distance, path), where
        distance is the distance from source to target and path is a list
        representing the path from source to target.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> length, path = nx.single_source_dijkstra(G, 0)
    >>> length[4]
    4
    >>> for node in [0, 1, 2, 3, 4]:
    ...     print(f"{node}: {length[node]}")
    0: 0
    1: 1
    2: 2
    3: 3
    4: 4
    >>> path[4]
    [0, 1, 2, 3, 4]
    >>> length, path = nx.single_source_dijkstra(G, 0, 1)
    >>> length
    1
    >>> path
    [0, 1]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The weight function can be used to hide edges by returning None.
    So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
    will find the shortest red path.

    Based on the Python cookbook recipe (119466) at
    https://code.activestate.com/recipes/119466/

    This algorithm is not guaranteed to work if edge weights
    are negative or are floating point numbers
    (overflows and roundoff errors can cause problems).

    See Also
    --------
    single_source_dijkstra_path
    single_source_dijkstra_path_length
    single_source_bellman_ford
networkx.single_source_dijkstra_path
Python Library Documentation: function single_source_dijkstra_path in module networkx.algorithms.shortest_paths.weighted

single_source_dijkstra_path(G, source, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
    Find shortest weighted paths in G from a source node.

    Compute shortest path between source and all other reachable
    nodes for a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    source : node
        Starting node for path.

    cutoff : integer or float, optional
        Length (sum of edge weights) at which the search is stopped.
        If cutoff is provided, only return paths with summed weight <= cutoff.

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Returns
    -------
    paths : dictionary
        Dictionary of shortest path lengths keyed by target.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> path = nx.single_source_dijkstra_path(G, 0)
    >>> path[4]
    [0, 1, 2, 3, 4]

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The weight function can be used to hide edges by returning None.
    So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
    will find the shortest red path.

    See Also
    --------
    single_source_dijkstra, single_source_bellman_ford
networkx.single_source_dijkstra_path_length
Python Library Documentation: function single_source_dijkstra_path_length in module networkx.algorithms.shortest_paths.weighted

single_source_dijkstra_path_length(G, source, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
    Find shortest weighted path lengths in G from a source node.

    Compute the shortest path length between source and all other
    reachable nodes for a weighted graph.

    Parameters
    ----------
    G : NetworkX graph

    source : node label
        Starting node for path

    cutoff : integer or float, optional
        Length (sum of edge weights) at which the search is stopped.
        If cutoff is provided, only return paths with summed weight <= cutoff.

    weight : string or function
        If this is a string, then edge weights will be accessed via the
        edge attribute with this key (that is, the weight of the edge
        joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
        such edge attribute exists, the weight of the edge is assumed to
        be one.

        If this is a function, the weight of an edge is the value
        returned by the function. The function must accept exactly three
        positional arguments: the two endpoints of an edge and the
        dictionary of edge attributes for that edge. The function must
        return a number or None to indicate a hidden edge.

    Returns
    -------
    length : dict
        Dict keyed by node to shortest path length from source.

    Raises
    ------
    NodeNotFound
        If `source` is not in `G`.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> length = nx.single_source_dijkstra_path_length(G, 0)
    >>> length[4]
    4
    >>> for node in [0, 1, 2, 3, 4]:
    ...     print(f"{node}: {length[node]}")
    0: 0
    1: 1
    2: 2
    3: 3
    4: 4

    Notes
    -----
    Edge weight attributes must be numerical.
    Distances are calculated as sums of weighted edges traversed.

    The weight function can be used to hide edges by returning None.
    So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
    will find the shortest red path.

    See Also
    --------
    single_source_dijkstra, single_source_bellman_ford_path_length
networkx.single_source_shortest_path
Python Library Documentation: function single_source_shortest_path in module networkx.algorithms.shortest_paths.unweighted

single_source_shortest_path(G, source, cutoff=None, *, backend=None, **backend_kwargs)
    Compute shortest path between source
    and all other nodes reachable from source.

    Parameters
    ----------
    G : NetworkX graph

    source : node label
       Starting node for path

    cutoff : integer, optional
        Depth to stop the search. Only paths of length <= cutoff are returned.

    Returns
    -------
    paths : dictionary
        Dictionary, keyed by target, of shortest paths.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> path = nx.single_source_shortest_path(G, 0)
    >>> path[4]
    [0, 1, 2, 3, 4]

    Notes
    -----
    The shortest path is not necessarily unique. So there can be multiple
    paths between the source and each target node, all of which have the
    same 'shortest' length. For each target node, this function returns
    only one of those paths.

    See Also
    --------
    shortest_path
networkx.single_source_shortest_path_length
Python Library Documentation: function single_source_shortest_path_length in module networkx.algorithms.shortest_paths.unweighted

single_source_shortest_path_length(G, source, cutoff=None, *, backend=None, **backend_kwargs)
    Compute the shortest path lengths from source to all reachable nodes.

    Parameters
    ----------
    G : NetworkX graph

    source : node
       Starting node for path

    cutoff : integer, optional
        Depth to stop the search. Only paths of length <= cutoff are returned.

    Returns
    -------
    lengths : dict
        Dict keyed by node to shortest path length to source.

    Examples
    --------
    >>> G = nx.path_graph(5)
    >>> length = nx.single_source_shortest_path_length(G, 0)
    >>> length[4]
    4
    >>> for node in length:
    ...     print(f"{node}: {length[node]}")
    0: 0
    1: 1
    2: 2
    3: 3
    4: 4

    See Also
    --------
    shortest_path_length
networkx.single_target_shortest_path
Python Library Documentation: function single_target_shortest_path in module networkx.algorithms.shortest_paths.unweighted

single_target_shortest_path(G, target, cutoff=None, *, backend=None, **backend_kwargs)
    Compute shortest path to target from all nodes that reach target.

    Parameters
    ----------
    G : NetworkX graph

    target : node label
       Target node for path

    cutoff : integer, optional
        Depth to stop the search. Only paths of length <= cutoff are returned.

    Returns
    -------
    paths : dictionary
        Dictionary, keyed by target, of shortest paths.

    Examples
    --------
    >>> G = nx.path_graph(5, create_using=nx.DiGraph())
    >>> path = nx.single_target_shortest_path(G, 4)
    >>> path[0]
    [0, 1, 2, 3, 4]

    Notes
    -----
    The shortest path is not necessarily unique. So there can be multiple
    paths between the source and each target node, all of which have the
    same 'shortest' length. For each target node, this function returns
    only one of those paths.

    See Also
    --------
    shortest_path, single_source_shortest_path
networkx.single_target_shortest_path_length
Python Library Documentation: function single_target_shortest_path_length in module networkx.algorithms.shortest_paths.unweighted

single_target_shortest_path_length(G, target, cutoff=None, *, backend=None, **backend_kwargs)
    Compute the shortest path lengths to target from all reachable nodes.

    Parameters
    ----------
    G : NetworkX graph

    target : node
       Target node for path

    cutoff : integer, optional
        Depth to stop the search. Only paths of length <= cutoff are returned.

    Returns
    -------
    lengths : iterator
        (source, shortest path length) iterator

    Examples
    --------
    >>> G = nx.path_graph(5, create_using=nx.DiGraph())
    >>> length = dict(nx.single_target_shortest_path_length(G, 4))
    >>> length[0]
    4
    >>> for node in range(5):
    ...     print(f"{node}: {length[node]}")
    0: 4
    1: 3
    2: 2
    3: 1
    4: 0

    See Also
    --------
    single_source_shortest_path_length, shortest_path_length
networkx.small
Python Library Documentation: module networkx.generators.small in networkx.generators

NAME
    networkx.generators.small - Various small and named graphs, together with some compact generators.

FUNCTIONS
    LCF_graph(n, shift_list, repeats, create_using=None, *, backend=None, **backend_kwargs)
        Return the cubic graph specified in LCF notation.

        LCF (Lederberg-Coxeter-Fruchte) notation[1]_ is a compressed
        notation used in the generation of various cubic Hamiltonian
        graphs of high symmetry. See, for example, `dodecahedral_graph`,
        `desargues_graph`, `heawood_graph` and `pappus_graph`.

        Nodes are drawn from ``range(n)``. Each node ``n_i`` is connected with
        node ``n_i + shift % n`` where ``shift`` is given by cycling through
        the input `shift_list` `repeat` s times.

        Parameters
        ----------
        n : int
           The starting graph is the `n`-cycle with nodes ``0, ..., n-1``.
           The null graph is returned if `n` < 1.

        shift_list : list
           A list of integer shifts mod `n`, ``[s1, s2, .., sk]``

        repeats : int
           Integer specifying the number of times that shifts in `shift_list`
           are successively applied to each current node in the n-cycle
           to generate an edge between ``n_current`` and ``n_current + shift mod n``.

        Returns
        -------
        G : Graph
           A graph instance created from the specified LCF notation.

        Examples
        --------
        The utility graph $K_{3,3}$

        >>> G = nx.LCF_graph(6, [3, -3], 3)
        >>> G.edges()
        EdgeView([(0, 1), (0, 5), (0, 3), (1, 2), (1, 4), (2, 3), (2, 5), (3, 4), (4, 5)])

        The Heawood graph:

        >>> G = nx.LCF_graph(14, [5, -5], 7)
        >>> nx.is_isomorphic(G, nx.heawood_graph())
        True

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/LCF_notation

    bull_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Bull Graph

        The Bull Graph has 5 nodes and 5 edges. It is a planar undirected
        graph in the form of a triangle with two disjoint pendant edges [1]_
        The name comes from the triangle and pendant edges representing
        respectively the body and legs of a bull.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            A bull graph with 5 nodes

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Bull_graph.

    chvatal_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Chvátal Graph

        The Chvátal Graph is an undirected graph with 12 nodes and 24 edges [1]_.
        It has 370 distinct (directed) Hamiltonian cycles, giving a unique generalized
        LCF notation of order 4, two of order 6 , and 43 of order 1 [2]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            The Chvátal graph with 12 nodes and 24 edges

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Chv%C3%A1tal_graph
        .. [2] https://mathworld.wolfram.com/ChvatalGraph.html

    cubical_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the 3-regular Platonic Cubical Graph

        The skeleton of the cube (the nodes and edges) form a graph, with 8
        nodes, and 12 edges. It is a special case of the hypercube graph.
        It is one of 5 Platonic graphs, each a skeleton of its
        Platonic solid [1]_.
        Such graphs arise in parallel processing in computers.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            A cubical graph with 8 nodes and 12 edges

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Cube#Cubical_graph

    desargues_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Desargues Graph

        The Desargues Graph is a non-planar, distance-transitive cubic graph
        with 20 nodes and 30 edges [1]_.
        It is a symmetric graph. It can be represented in LCF notation
        as [5,-5,9,-9]^5 [2]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Desargues Graph with 20 nodes and 30 edges

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Desargues_graph
        .. [2] https://mathworld.wolfram.com/DesarguesGraph.html

    diamond_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Diamond graph

        The Diamond Graph is  planar undirected graph with 4 nodes and 5 edges.
        It is also sometimes known as the double triangle graph or kite graph [1]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Diamond Graph with 4 nodes and 5 edges

        References
        ----------
        .. [1] https://mathworld.wolfram.com/DiamondGraph.html

    dodecahedral_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Platonic Dodecahedral graph.

        The dodecahedral graph has 20 nodes and 30 edges. The skeleton of the
        dodecahedron forms a graph. It is one of 5 Platonic graphs [1]_.
        It can be described in LCF notation as:
        ``[10, 7, 4, -4, -7, 10, -4, 7, -7, 4]^2`` [2]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Dodecahedral Graph with 20 nodes and 30 edges

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Regular_dodecahedron#Dodecahedral_graph
        .. [2] https://mathworld.wolfram.com/DodecahedralGraph.html

    frucht_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Frucht Graph.

        The Frucht Graph is the smallest cubical graph whose
        automorphism group consists only of the identity element [1]_.
        It has 12 nodes and 18 edges and no nontrivial symmetries.
        It is planar and Hamiltonian [2]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Frucht Graph with 12 nodes and 18 edges

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Frucht_graph
        .. [2] https://mathworld.wolfram.com/FruchtGraph.html

    heawood_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Heawood Graph, a (3,6) cage.

        The Heawood Graph is an undirected graph with 14 nodes and 21 edges,
        named after Percy John Heawood [1]_.
        It is cubic symmetric, nonplanar, Hamiltonian, and can be represented
        in LCF notation as ``[5,-5]^7`` [2]_.
        It is the unique (3,6)-cage: the regular cubic graph of girth 6 with
        minimal number of vertices [3]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Heawood Graph with 14 nodes and 21 edges

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Heawood_graph
        .. [2] https://mathworld.wolfram.com/HeawoodGraph.html
        .. [3] https://www.win.tue.nl/~aeb/graphs/Heawood.html

    hoffman_singleton_graph(*, backend=None, **backend_kwargs)
        Returns the Hoffman-Singleton Graph.

        The Hoffman–Singleton graph is a symmetrical undirected graph
        with 50 nodes and 175 edges.
        All indices lie in ``Z % 5``: that is, the integers mod 5 [1]_.
        It is the only regular graph of vertex degree 7, diameter 2, and girth 5.
        It is the unique (7,5)-cage graph and Moore graph, and contains many
        copies of the Petersen graph [2]_.

        Returns
        -------
        G : networkx Graph
            Hoffman–Singleton Graph with 50 nodes and 175 edges

        Notes
        -----
        Constructed from pentagon and pentagram as follows: Take five pentagons $P_h$
        and five pentagrams $Q_i$ . Join vertex $j$ of $P_h$ to vertex $h·i+j$ of $Q_i$ [3]_.

        References
        ----------
        .. [1] https://blogs.ams.org/visualinsight/2016/02/01/hoffman-singleton-graph/
        .. [2] https://mathworld.wolfram.com/Hoffman-SingletonGraph.html
        .. [3] https://en.wikipedia.org/wiki/Hoffman%E2%80%93Singleton_graph

    house_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the House graph (square with triangle on top)

        The house graph is a simple undirected graph with
        5 nodes and 6 edges [1]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            House graph in the form of a square with a triangle on top

        References
        ----------
        .. [1] https://mathworld.wolfram.com/HouseGraph.html

    house_x_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the House graph with a cross inside the house square.

        The House X-graph is the House graph plus the two edges connecting diagonally
        opposite vertices of the square base. It is also one of the two graphs
        obtained by removing two edges from the pentatope graph [1]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            House graph with diagonal vertices connected

        References
        ----------
        .. [1] https://mathworld.wolfram.com/HouseGraph.html

    icosahedral_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Platonic Icosahedral graph.

        The icosahedral graph has 12 nodes and 30 edges. It is a Platonic graph
        whose nodes have the connectivity of the icosahedron. It is undirected,
        regular and Hamiltonian [1]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Icosahedral graph with 12 nodes and 30 edges.

        References
        ----------
        .. [1] https://mathworld.wolfram.com/IcosahedralGraph.html

    krackhardt_kite_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Krackhardt Kite Social Network.

        A 10 actor social network introduced by David Krackhardt
        to illustrate different centrality measures [1]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Krackhardt Kite graph with 10 nodes and 18 edges

        Notes
        -----
        The traditional labeling is:
        Andre=1, Beverley=2, Carol=3, Diane=4,
        Ed=5, Fernando=6, Garth=7, Heather=8, Ike=9, Jane=10.

        References
        ----------
        .. [1] Krackhardt, David. "Assessing the Political Landscape: Structure,
           Cognition, and Power in Organizations". Administrative Science Quarterly.
           35 (2): 342–369. doi:10.2307/2393394. JSTOR 2393394. June 1990.

    moebius_kantor_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Moebius-Kantor graph.

        The Möbius-Kantor graph is the cubic symmetric graph on 16 nodes.
        Its LCF notation is [5,-5]^8, and it is isomorphic to the generalized
        Petersen graph [1]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Moebius-Kantor graph

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/M%C3%B6bius%E2%80%93Kantor_graph

    octahedral_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Platonic Octahedral graph.

        The octahedral graph is the 6-node 12-edge Platonic graph having the
        connectivity of the octahedron [1]_. If 6 couples go to a party,
        and each person shakes hands with every person except his or her partner,
        then this graph describes the set of handshakes that take place;
        for this reason it is also called the cocktail party graph [2]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Octahedral graph

        References
        ----------
        .. [1] https://mathworld.wolfram.com/OctahedralGraph.html
        .. [2] https://en.wikipedia.org/wiki/Tur%C3%A1n_graph#Special_cases

    pappus_graph(*, backend=None, **backend_kwargs)
        Returns the Pappus graph.

        The Pappus graph is a cubic symmetric distance-regular graph with 18 nodes
        and 27 edges. It is Hamiltonian and can be represented in LCF notation as
        [5,7,-7,7,-7,-5]^3 [1]_.

        Returns
        -------
        G : networkx Graph
            Pappus graph

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Pappus_graph

    petersen_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Petersen graph.

        The Peterson graph is a cubic, undirected graph with 10 nodes and 15 edges [1]_.
        Julius Petersen constructed the graph as the smallest counterexample
        against the claim that a connected bridgeless cubic graph
        has an edge colouring with three colours [2]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Petersen graph

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Petersen_graph
        .. [2] https://www.win.tue.nl/~aeb/drg/graphs/Petersen.html

    sedgewick_maze_graph(create_using=None, *, backend=None, **backend_kwargs)
        Return a small maze with a cycle.

        This is the maze used in Sedgewick, 3rd Edition, Part 5, Graph
        Algorithms, Chapter 18, e.g. Figure 18.2 and following [1]_.
        Nodes are numbered 0,..,7

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Small maze with a cycle

        References
        ----------
        .. [1] Figure 18.2, Chapter 18, Graph Algorithms (3rd Ed), Sedgewick

    tetrahedral_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the 3-regular Platonic Tetrahedral graph.

        Tetrahedral graph has 4 nodes and 6 edges. It is a
        special case of the complete graph, K4, and wheel graph, W4.
        It is one of the 5 platonic graphs [1]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Tetrahedral Graph

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Tetrahedron#Tetrahedral_graph

    truncated_cube_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the skeleton of the truncated cube.

        The truncated cube is an Archimedean solid with 14 regular
        faces (6 octagonal and 8 triangular), 36 edges and 24 nodes [1]_.
        The truncated cube is created by truncating (cutting off) the tips
        of the cube one third of the way into each edge [2]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Skeleton of the truncated cube

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Truncated_cube
        .. [2] https://www.coolmath.com/reference/polyhedra-truncated-cube

    truncated_tetrahedron_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the skeleton of the truncated Platonic tetrahedron.

        The truncated tetrahedron is an Archimedean solid with 4 regular hexagonal faces,
        4 equilateral triangle faces, 12 nodes and 18 edges. It can be constructed by truncating
        all 4 vertices of a regular tetrahedron at one third of the original edge length [1]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Skeleton of the truncated tetrahedron

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Truncated_tetrahedron

    tutte_graph(create_using=None, *, backend=None, **backend_kwargs)
        Returns the Tutte graph.

        The Tutte graph is a cubic polyhedral, non-Hamiltonian graph. It has
        46 nodes and 69 edges.
        It is a counterexample to Tait's conjecture that every 3-regular polyhedron
        has a Hamiltonian cycle.
        It can be realized geometrically from a tetrahedron by multiply truncating
        three of its vertices [1]_.

        Parameters
        ----------
        create_using : NetworkX graph constructor, optional (default=nx.Graph)
           Graph type to create. If graph instance, then cleared before populated.

        Returns
        -------
        G : networkx Graph
            Tutte graph

        References
        ----------
        .. [1] https://en.wikipedia.org/wiki/Tutte_graph

DATA
    __all__ = ['LCF_graph', 'bull_graph', 'chvatal_graph', 'cubical_graph'...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\small.py

networkx.smallworld
Python Library Documentation: module networkx.algorithms.smallworld in networkx.algorithms

NAME
    networkx.algorithms.smallworld - Functions for estimating the small-world-ness of graphs.

DESCRIPTION
    A small world network is characterized by a small average shortest path length,
    and a large clustering coefficient.

    Small-worldness is commonly measured with the coefficient sigma or omega.

    Both coefficients compare the average clustering coefficient and shortest path
    length of a given graph against the same quantities for an equivalent random
    or lattice graph.

    For more information, see the Wikipedia article on small-world network [1]_.

    .. [1] Small-world network:: https://en.wikipedia.org/wiki/Small-world_network

FUNCTIONS
    lattice_reference(G, niter=5, D=None, connectivity=True, seed=None, *, backend=None, **backend_kwargs)
        Latticize the given graph by swapping edges.

        Parameters
        ----------
        G : graph
            An undirected graph.

        niter : integer (optional, default=1)
            An edge is rewired approximately niter times.

        D : numpy.array (optional, default=None)
            Distance to the diagonal matrix.

        connectivity : boolean (optional, default=True)
            Ensure connectivity for the latticized graph when set to True.

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        G : graph
            The latticized graph.

        Raises
        ------
        NetworkXError
            If there are fewer than 4 nodes or 2 edges in `G`

        Notes
        -----
        The implementation is adapted from the algorithm by Sporns et al. [1]_.
        which is inspired from the original work by Maslov and Sneppen(2002) [2]_.

        References
        ----------
        .. [1] Sporns, Olaf, and Jonathan D. Zwi.
           "The small world of the cerebral cortex."
           Neuroinformatics 2.2 (2004): 145-162.
        .. [2] Maslov, Sergei, and Kim Sneppen.
           "Specificity and stability in topology of protein networks."
           Science 296.5569 (2002): 910-913.

    omega(G, niter=5, nrand=10, seed=None, *, backend=None, **backend_kwargs)
        Returns the small-world coefficient (omega) of a graph

        The small-world coefficient of a graph G is:

        omega = Lr/L - C/Cl

        where C and L are respectively the average clustering coefficient and
        average shortest path length of G. Lr is the average shortest path length
        of an equivalent random graph and Cl is the average clustering coefficient
        of an equivalent lattice graph.

        The small-world coefficient (omega) measures how much G is like a lattice
        or a random graph. Negative values mean G is similar to a lattice whereas
        positive values mean G is a random graph.
        Values close to 0 mean that G has small-world characteristics.

        Parameters
        ----------
        G : NetworkX graph
            An undirected graph.

        niter: integer (optional, default=5)
            Approximate number of rewiring per edge to compute the equivalent
            random graph.

        nrand: integer (optional, default=10)
            Number of random graphs generated to compute the maximal clustering
            coefficient (Cr) and average shortest path length (Lr).

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.


        Returns
        -------
        omega : float
            The small-world coefficient (omega)

        Notes
        -----
        The implementation is adapted from the algorithm by Telesford et al. [1]_.

        References
        ----------
        .. [1] Telesford, Joyce, Hayasaka, Burdette, and Laurienti (2011).
               "The Ubiquity of Small-World Networks".
               Brain Connectivity. 1 (0038): 367-75.  PMC 3604768. PMID 22432451.
               doi:10.1089/brain.2011.0038.

    random_reference(G, niter=1, connectivity=True, seed=None, *, backend=None, **backend_kwargs)
        Compute a random graph by swapping edges of a given graph.

        Parameters
        ----------
        G : graph
            An undirected graph with 4 or more nodes.

        niter : integer (optional, default=1)
            An edge is rewired approximately `niter` times.

        connectivity : boolean (optional, default=True)
            When True, ensure connectivity for the randomized graph.

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        G : graph
            The randomized graph.

        Raises
        ------
        NetworkXError
            If there are fewer than 4 nodes or 2 edges in `G`

        Notes
        -----
        The implementation is adapted from the algorithm by Maslov and Sneppen
        (2002) [1]_.

        References
        ----------
        .. [1] Maslov, Sergei, and Kim Sneppen.
               "Specificity and stability in topology of protein networks."
               Science 296.5569 (2002): 910-913.

    sigma(G, niter=100, nrand=10, seed=None, *, backend=None, **backend_kwargs)
        Returns the small-world coefficient (sigma) of the given graph.

        The small-world coefficient is defined as:
        sigma = C/Cr / L/Lr
        where C and L are respectively the average clustering coefficient and
        average shortest path length of G. Cr and Lr are respectively the average
        clustering coefficient and average shortest path length of an equivalent
        random graph.

        A graph is commonly classified as small-world if sigma>1.

        Parameters
        ----------
        G : NetworkX graph
            An undirected graph.
        niter : integer (optional, default=100)
            Approximate number of rewiring per edge to compute the equivalent
            random graph.
        nrand : integer (optional, default=10)
            Number of random graphs generated to compute the average clustering
            coefficient (Cr) and average shortest path length (Lr).
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        sigma : float
            The small-world coefficient of G.

        Notes
        -----
        The implementation is adapted from Humphries et al. [1]_ [2]_.

        References
        ----------
        .. [1] The brainstem reticular formation is a small-world, not scale-free,
               network M. D. Humphries, K. Gurney and T. J. Prescott,
               Proc. Roy. Soc. B 2006 273, 503-511, doi:10.1098/rspb.2005.3354.
        .. [2] Humphries and Gurney (2008).
               "Network 'Small-World-Ness': A Quantitative Method for Determining
               Canonical Network Equivalence".
               PLoS One. 3 (4). PMID 18446219. doi:10.1371/journal.pone.0002051.

DATA
    __all__ = ['random_reference', 'lattice_reference', 'sigma', 'omega']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\smallworld.py

networkx.smetric
Python Library Documentation: module networkx.algorithms.smetric in networkx.algorithms

NAME
    networkx.algorithms.smetric

FUNCTIONS
    s_metric(G, *, backend=None, **backend_kwargs)
        Returns the s-metric [1]_ of graph.

        The s-metric is defined as the sum of the products ``deg(u) * deg(v)``
        for every edge ``(u, v)`` in `G`.

        Parameters
        ----------
        G : graph
            The graph used to compute the s-metric.

        Returns
        -------
        s : float
            The s-metric of the graph.

        References
        ----------
        .. [1] Lun Li, David Alderson, John C. Doyle, and Walter Willinger,
               Towards a Theory of Scale-Free Graphs:
               Definition, Properties, and  Implications (Extended Version), 2005.
               https://arxiv.org/abs/cond-mat/0501169

DATA
    __all__ = ['s_metric']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\smetric.py

networkx.snap_aggregation
Python Library Documentation: function snap_aggregation in module networkx.algorithms.summarization

snap_aggregation(G, node_attributes, edge_attributes=(), prefix='Supernode-', supernode_attribute='group', superedge_attribute='types', *, backend=None, **backend_kwargs)
    Creates a summary graph based on attributes and connectivity.

    This function uses the Summarization by Grouping Nodes on Attributes
    and Pairwise edges (SNAP) algorithm for summarizing a given
    graph by grouping nodes by node attributes and their edge attributes
    into supernodes in a summary graph.  This name SNAP should not be
    confused with the Stanford Network Analysis Project (SNAP).

    Here is a high-level view of how this algorithm works:

    1) Group nodes by node attribute values.

    2) Iteratively split groups until all nodes in each group have edges
    to nodes in the same groups. That is, until all the groups are homogeneous
    in their member nodes' edges to other groups.  For example,
    if all the nodes in group A only have edge to nodes in group B, then the
    group is homogeneous and does not need to be split. If all nodes in group B
    have edges with nodes in groups {A, C}, but some also have edges with other
    nodes in B, then group B is not homogeneous and needs to be split into
    groups have edges with {A, C} and a group of nodes having
    edges with {A, B, C}.  This way, viewers of the summary graph can
    assume that all nodes in the group have the exact same node attributes and
    the exact same edges.

    3) Build the output summary graph, where the groups are represented by
    super-nodes. Edges represent the edges shared between all the nodes in each
    respective groups.

    A SNAP summary graph can be used to visualize graphs that are too large to display
    or visually analyze, or to efficiently identify sets of similar nodes with similar connectivity
    patterns to other sets of similar nodes based on specified node and/or edge attributes in a graph.

    Parameters
    ----------
    G: graph
        Networkx Graph to be summarized
    node_attributes: iterable, required
        An iterable of the node attributes used to group nodes in the summarization process. Nodes
        with the same values for these attributes will be grouped together in the summary graph.
    edge_attributes: iterable, optional
        An iterable of the edge attributes considered in the summarization process.  If provided, unique
        combinations of the attribute values found in the graph are used to
        determine the edge types in the graph.  If not provided, all edges
        are considered to be of the same type.
    prefix: str
        The prefix used to denote supernodes in the summary graph. Defaults to 'Supernode-'.
    supernode_attribute: str
        The node attribute for recording the supernode groupings of nodes. Defaults to 'group'.
    superedge_attribute: str
        The edge attribute for recording the edge types of multiple edges. Defaults to 'types'.

    Returns
    -------
    networkx.Graph: summary graph

    Examples
    --------
    SNAP aggregation takes a graph and summarizes it in the context of user-provided
    node and edge attributes such that a viewer can more easily extract and
    analyze the information represented by the graph

    >>> nodes = {
    ...     "A": dict(color="Red"),
    ...     "B": dict(color="Red"),
    ...     "C": dict(color="Red"),
    ...     "D": dict(color="Red"),
    ...     "E": dict(color="Blue"),
    ...     "F": dict(color="Blue"),
    ... }
    >>> edges = [
    ...     ("A", "E", "Strong"),
    ...     ("B", "F", "Strong"),
    ...     ("C", "E", "Weak"),
    ...     ("D", "F", "Weak"),
    ... ]
    >>> G = nx.Graph()
    >>> for node in nodes:
    ...     attributes = nodes[node]
    ...     G.add_node(node, **attributes)
    >>> for source, target, type in edges:
    ...     G.add_edge(source, target, type=type)
    >>> node_attributes = ("color",)
    >>> edge_attributes = ("type",)
    >>> summary_graph = nx.snap_aggregation(
    ...     G, node_attributes=node_attributes, edge_attributes=edge_attributes
    ... )

    Notes
    -----
    The summary graph produced is called a maximum Attribute-edge
    compatible (AR-compatible) grouping.  According to [1]_, an
    AR-compatible grouping means that all nodes in each group have the same
    exact node attribute values and the same exact edges and
    edge types to one or more nodes in the same groups.  The maximal
    AR-compatible grouping is the grouping with the minimal cardinality.

    The AR-compatible grouping is the most detailed grouping provided by
    any of the SNAP algorithms.

    References
    ----------
    .. [1] Y. Tian, R. A. Hankins, and J. M. Patel. Efficient aggregation
       for graph summarization. In Proc. 2008 ACM-SIGMOD Int. Conf.
       Management of Data (SIGMOD’08), pages 567–580, Vancouver, Canada,
       June 2008.
networkx.social
Python Library Documentation: module networkx.generators.social in networkx.generators

NAME
    networkx.generators.social - Famous social networks.

FUNCTIONS
    davis_southern_women_graph(*, backend=None, **backend_kwargs)
        Returns Davis Southern women social network.

        This is a bipartite graph.

        References
        ----------
        .. [1] A. Davis, Gardner, B. B., Gardner, M. R., 1941. Deep South.
            University of Chicago Press, Chicago, IL.

    florentine_families_graph(*, backend=None, **backend_kwargs)
        Returns Florentine families graph.

        References
        ----------
        .. [1] Ronald L. Breiger and Philippa E. Pattison
           Cumulated social roles: The duality of persons and their algebras,1
           Social Networks, Volume 8, Issue 3, September 1986, Pages 215-256

    karate_club_graph(*, backend=None, **backend_kwargs)
        Returns Zachary's Karate Club graph.

        Each node in the returned graph has a node attribute 'club' that
        indicates the name of the club to which the member represented by that node
        belongs, either 'Mr. Hi' or 'Officer'. Each edge has a weight based on the
        number of contexts in which that edge's incident node members interacted.

        The dataset is derived from the 'Club After Split From Data' column of Table 3 in [1]_.
        This was in turn derived from the 'Club After Fission' column of Table 1 in the
        same paper. Note that the nodes are 0-indexed in NetworkX, but 1-indexed in the
        paper (the 'Individual Number in Matrix C' column of Table 3 starts at 1). This
        means, for example, that ``G.nodes[9]["club"]`` returns 'Officer', which
        corresponds to row 10 of Table 3 in the paper.

        Examples
        --------
        To get the name of the club to which a node belongs::

            >>> G = nx.karate_club_graph()
            >>> G.nodes[5]["club"]
            'Mr. Hi'
            >>> G.nodes[9]["club"]
            'Officer'

        References
        ----------
        .. [1] Zachary, Wayne W.
           "An Information Flow Model for Conflict and Fission in Small Groups."
           *Journal of Anthropological Research*, 33, 452--473, (1977).

    les_miserables_graph(*, backend=None, **backend_kwargs)
        Returns coappearance network of characters in the novel Les Miserables.

        References
        ----------
        .. [1] D. E. Knuth, 1993.
           The Stanford GraphBase: a platform for combinatorial computing,
           pp. 74-87. New York: AcM Press.

DATA
    __all__ = ['karate_club_graph', 'davis_southern_women_graph', 'florent...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\social.py

networkx.soft_random_geometric_graph
Python Library Documentation: function soft_random_geometric_graph in module networkx.generators.geometric

soft_random_geometric_graph(n, radius, dim=2, pos=None, p=2, p_dist=None, seed=None, *, pos_name='pos', backend=None, **backend_kwargs)
    Returns a soft random geometric graph in the unit cube.

    The soft random geometric graph [1] model places `n` nodes uniformly at
    random in the unit cube in dimension `dim`. Two nodes of distance, `dist`,
    computed by the `p`-Minkowski distance metric are joined by an edge with
    probability `p_dist` if the computed distance metric value of the nodes
    is at most `radius`, otherwise they are not joined.

    Edges within `radius` of each other are determined using a KDTree when
    SciPy is available. This reduces the time complexity from :math:`O(n^2)`
    to :math:`O(n)`.

    Parameters
    ----------
    n : int or iterable
        Number of nodes or iterable of nodes
    radius: float
        Distance threshold value
    dim : int, optional
        Dimension of graph
    pos : dict, optional
        A dictionary keyed by node with node positions as values.
    p : float, optional
        Which Minkowski distance metric to use.
        `p` has to meet the condition ``1 <= p <= infinity``.

        If this argument is not specified, the :math:`L^2` metric
        (the Euclidean distance metric), p = 2 is used.

        This should not be confused with the `p` of an Erdős-Rényi random
        graph, which represents probability.
    p_dist : function, optional
        A probability density function computing the probability of
        connecting two nodes that are of distance, dist, computed by the
        Minkowski distance metric. The probability density function, `p_dist`,
        must be any function that takes the metric value as input
        and outputs a single probability value between 0-1. The scipy.stats
        package has many probability distribution functions implemented and
        tools for custom probability distribution definitions [2], and passing
        the .pdf method of scipy.stats distributions can be used here.  If the
        probability function, `p_dist`, is not supplied, the default function
        is an exponential distribution with rate parameter :math:`\lambda=1`.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    pos_name : string, default="pos"
        The name of the node attribute which represents the position
        in 2D coordinates of the node in the returned graph.

    Returns
    -------
    Graph
        A soft random geometric graph, undirected and without self-loops.
        Each node has a node attribute ``'pos'`` that stores the
        position of that node in Euclidean space as provided by the
        ``pos`` keyword argument or, if ``pos`` was not provided, as
        generated by this function.

    Examples
    --------
    Default Graph:

    G = nx.soft_random_geometric_graph(50, 0.2)

    Custom Graph:

    Create a soft random geometric graph on 100 uniformly distributed nodes
    where nodes are joined by an edge with probability computed from an
    exponential distribution with rate parameter :math:`\lambda=1` if their
    Euclidean distance is at most 0.2.

    Notes
    -----
    This uses a *k*-d tree to build the graph.

    The `pos` keyword argument can be used to specify node positions so you
    can create an arbitrary distribution and domain for positions.

    For example, to use a 2D Gaussian distribution of node positions with mean
    (0, 0) and standard deviation 2

    The scipy.stats package can be used to define the probability distribution
    with the .pdf method used as `p_dist`.

    ::

    >>> import random
    >>> import math
    >>> n = 100
    >>> pos = {i: (random.gauss(0, 2), random.gauss(0, 2)) for i in range(n)}
    >>> p_dist = lambda dist: math.exp(-dist)
    >>> G = nx.soft_random_geometric_graph(n, 0.2, pos=pos, p_dist=p_dist)

    References
    ----------
    .. [1] Penrose, Mathew D. "Connectivity of soft random geometric graphs."
           The Annals of Applied Probability 26.2 (2016): 986-1028.
    .. [2] scipy.stats -
           https://docs.scipy.org/doc/scipy/reference/tutorial/stats.html
networkx.spanner
Python Library Documentation: function spanner in module networkx.algorithms.sparsifiers

spanner(G, stretch, weight=None, seed=None, *, backend=None, **backend_kwargs)
    Returns a spanner of the given graph with the given stretch.

    A spanner of a graph G = (V, E) with stretch t is a subgraph
    H = (V, E_S) such that E_S is a subset of E and the distance between
    any pair of nodes in H is at most t times the distance between the
    nodes in G.

    Parameters
    ----------
    G : NetworkX graph
        An undirected simple graph.

    stretch : float
        The stretch of the spanner.

    weight : object
        The edge attribute to use as distance.

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    NetworkX graph
        A spanner of the given graph with the given stretch.

    Raises
    ------
    ValueError
        If a stretch less than 1 is given.

    Notes
    -----
    This function implements the spanner algorithm by Baswana and Sen,
    see [1].

    This algorithm is a randomized las vegas algorithm: The expected
    running time is O(km) where k = (stretch + 1) // 2 and m is the
    number of edges in G. The returned graph is always a spanner of the
    given graph with the specified stretch. For weighted graphs the
    number of edges in the spanner is O(k * n^(1 + 1 / k)) where k is
    defined as above and n is the number of nodes in G. For unweighted
    graphs the number of edges is O(n^(1 + 1 / k) + kn).

    References
    ----------
    [1] S. Baswana, S. Sen. A Simple and Linear Time Randomized
    Algorithm for Computing Sparse Spanners in Weighted Graphs.
    Random Struct. Algorithms 30(4): 532-563 (2007).
networkx.sparse6
Python Library Documentation: module networkx.readwrite.sparse6 in networkx.readwrite

NAME
    networkx.readwrite.sparse6 - Functions for reading and writing graphs in the *sparse6* format.

DESCRIPTION
    The *sparse6* file format is a space-efficient format for large sparse
    graphs. For small graphs or large dense graphs, use the *graph6* file
    format.

    For more information, see the `sparse6`_ homepage.

    .. _sparse6: https://users.cecs.anu.edu.au/~bdm/data/formats.html

FUNCTIONS
    from_sparse6_bytes(string, *, backend=None, **backend_kwargs)
        Read an undirected graph in sparse6 format from string.

        Parameters
        ----------
        string : string
           Data in sparse6 format

        Returns
        -------
        G : Graph

        Raises
        ------
        NetworkXError
            If the string is unable to be parsed in sparse6 format

        Examples
        --------
        >>> G = nx.from_sparse6_bytes(b":A_")
        >>> sorted(G.edges())
        [(0, 1), (0, 1), (0, 1)]

        See Also
        --------
        read_sparse6, write_sparse6

        References
        ----------
        .. [1] Sparse6 specification
               <https://users.cecs.anu.edu.au/~bdm/data/formats.html>

    read_sparse6(path, *, backend=None, **backend_kwargs)
        Read an undirected graph in sparse6 format from path.

        Parameters
        ----------
        path : file or string
           File or filename to write.

        Returns
        -------
        G : Graph/Multigraph or list of Graphs/MultiGraphs
           If the file contains multiple lines then a list of graphs is returned

        Raises
        ------
        NetworkXError
            If the string is unable to be parsed in sparse6 format

        Examples
        --------
        You can read a sparse6 file by giving the path to the file::

            >>> import tempfile
            >>> with tempfile.NamedTemporaryFile(delete=False) as f:
            ...     _ = f.write(b">>sparse6<<:An\n")
            ...     _ = f.seek(0)
            ...     G = nx.read_sparse6(f.name)
            >>> list(G.edges())
            [(0, 1)]

        You can also read a sparse6 file by giving an open file-like object::

            >>> import tempfile
            >>> with tempfile.NamedTemporaryFile() as f:
            ...     _ = f.write(b">>sparse6<<:An\n")
            ...     _ = f.seek(0)
            ...     G = nx.read_sparse6(f)
            >>> list(G.edges())
            [(0, 1)]

        See Also
        --------
        read_sparse6, from_sparse6_bytes

        References
        ----------
        .. [1] Sparse6 specification
               <https://users.cecs.anu.edu.au/~bdm/data/formats.html>

    to_sparse6_bytes(G, nodes=None, header=True)
        Convert an undirected graph to bytes in sparse6 format.

        Parameters
        ----------
        G : Graph (undirected)

        nodes: list or iterable
           Nodes are labeled 0...n-1 in the order provided.  If None the ordering
           given by ``G.nodes()`` is used.

        header: bool
           If True add '>>sparse6<<' bytes to head of data.

        Raises
        ------
        NetworkXNotImplemented
            If the graph is directed.

        ValueError
            If the graph has at least ``2 ** 36`` nodes; the sparse6 format
            is only defined for graphs of order less than ``2 ** 36``.

        Examples
        --------
        >>> nx.to_sparse6_bytes(nx.path_graph(2))
        b'>>sparse6<<:An\n'

        See Also
        --------
        to_sparse6_bytes, read_sparse6, write_sparse6_bytes

        Notes
        -----
        The returned bytes end with a newline character.

        The format does not support edge or node labels.

        References
        ----------
        .. [1] Graph6 specification
               <https://users.cecs.anu.edu.au/~bdm/data/formats.html>

    write_sparse6(G, path, nodes=None, header=True)
        Write graph G to given path in sparse6 format.

        Parameters
        ----------
        G : Graph (undirected)

        path : file or string
           File or filename to write

        nodes: list or iterable
           Nodes are labeled 0...n-1 in the order provided.  If None the ordering
           given by G.nodes() is used.

        header: bool
           If True add '>>sparse6<<' string to head of data

        Raises
        ------
        NetworkXError
            If the graph is directed

        Examples
        --------
        You can write a sparse6 file by giving the path to the file::

            >>> import tempfile
            >>> with tempfile.NamedTemporaryFile(delete=False) as f:
            ...     nx.write_sparse6(nx.path_graph(2), f.name)
            ...     print(f.read())
            b'>>sparse6<<:An\n'

        You can also write a sparse6 file by giving an open file-like object::

            >>> with tempfile.NamedTemporaryFile() as f:
            ...     nx.write_sparse6(nx.path_graph(2), f)
            ...     _ = f.seek(0)
            ...     print(f.read())
            b'>>sparse6<<:An\n'

        See Also
        --------
        read_sparse6, from_sparse6_bytes

        Notes
        -----
        The format does not support edge or node labels.

        References
        ----------
        .. [1] Sparse6 specification
               <https://users.cecs.anu.edu.au/~bdm/data/formats.html>

DATA
    __all__ = ['from_sparse6_bytes', 'read_sparse6', 'to_sparse6_bytes', '...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\sparse6.py

networkx.sparsifiers
Python Library Documentation: module networkx.algorithms.sparsifiers in networkx.algorithms

NAME
    networkx.algorithms.sparsifiers - Functions for computing sparsifiers of graphs.

FUNCTIONS
    spanner(G, stretch, weight=None, seed=None, *, backend=None, **backend_kwargs)
        Returns a spanner of the given graph with the given stretch.

        A spanner of a graph G = (V, E) with stretch t is a subgraph
        H = (V, E_S) such that E_S is a subset of E and the distance between
        any pair of nodes in H is at most t times the distance between the
        nodes in G.

        Parameters
        ----------
        G : NetworkX graph
            An undirected simple graph.

        stretch : float
            The stretch of the spanner.

        weight : object
            The edge attribute to use as distance.

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        NetworkX graph
            A spanner of the given graph with the given stretch.

        Raises
        ------
        ValueError
            If a stretch less than 1 is given.

        Notes
        -----
        This function implements the spanner algorithm by Baswana and Sen,
        see [1].

        This algorithm is a randomized las vegas algorithm: The expected
        running time is O(km) where k = (stretch + 1) // 2 and m is the
        number of edges in G. The returned graph is always a spanner of the
        given graph with the specified stretch. For weighted graphs the
        number of edges in the spanner is O(k * n^(1 + 1 / k)) where k is
        defined as above and n is the number of nodes in G. For unweighted
        graphs the number of edges is O(n^(1 + 1 / k) + kn).

        References
        ----------
        [1] S. Baswana, S. Sen. A Simple and Linear Time Randomized
        Algorithm for Computing Sparse Spanners in Weighted Graphs.
        Random Struct. Algorithms 30(4): 532-563 (2007).

DATA
    __all__ = ['spanner']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\sparsifiers.py

networkx.spectral_bisection
Python Library Documentation: function spectral_bisection in module networkx.linalg.algebraicconnectivity

spectral_bisection(G, weight='weight', normalized=False, tol=1e-08, method='tracemin_pcg', seed=None, *, backend=None, **backend_kwargs)
    Bisect the graph using the Fiedler vector.

    This method uses the Fiedler vector to bisect a graph.
    The partition is defined by the nodes which are associated with
    either positive or negative values in the vector.

    Parameters
    ----------
    G : NetworkX Graph

    weight : str, optional (default: weight)
        The data key used to determine the weight of each edge. If None, then
        each edge has unit weight.

    normalized : bool, optional (default: False)
        Whether the normalized Laplacian matrix is used.

    tol : float, optional (default: 1e-8)
        Tolerance of relative residual in eigenvalue computation.

    method : string, optional (default: 'tracemin_pcg')
        Method of eigenvalue computation. It must be one of the tracemin
        options shown below (TraceMIN), 'lanczos' (Lanczos iteration)
        or 'lobpcg' (LOBPCG).

        The TraceMIN algorithm uses a linear system solver. The following
        values allow specifying the solver to be used.

        =============== ========================================
        Value           Solver
        =============== ========================================
        'tracemin_pcg'  Preconditioned conjugate gradient method
        'tracemin_lu'   LU factorization
        =============== ========================================

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    bisection : tuple of sets
        Sets with the bisection of nodes

    Examples
    --------
    >>> G = nx.barbell_graph(3, 0)
    >>> nx.spectral_bisection(G)
    ({0, 1, 2}, {3, 4, 5})

    References
    ----------
    .. [1] M. E. J Newman 'Networks: An Introduction', pages 364-370
       Oxford University Press 2011.
networkx.spectral_graph_forge
Python Library Documentation: function spectral_graph_forge in module networkx.generators.spectral_graph_forge

spectral_graph_forge(G, alpha, transformation='identity', seed=None, *, backend=None, **backend_kwargs)
    Returns a random simple graph with spectrum resembling that of `G`

    This algorithm, called Spectral Graph Forge (SGF), computes the
    eigenvectors of a given graph adjacency matrix, filters them and
    builds a random graph with a similar eigenstructure.
    SGF has been proved to be particularly useful for synthesizing
    realistic social networks and it can also be used to anonymize
    graph sensitive data.

    Parameters
    ----------
    G : Graph
    alpha :  float
        Ratio representing the percentage of eigenvectors of G to consider,
        values in [0,1].
    transformation : string, optional
        Represents the intended matrix linear transformation, possible values
        are 'identity' and 'modularity'
    seed : integer, random_state, or None (default)
        Indicator of numpy random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    H : Graph
        A graph with a similar eigenvector structure of the input one.

    Raises
    ------
    NetworkXError
        If transformation has a value different from 'identity' or 'modularity'

    Notes
    -----
    Spectral Graph Forge (SGF) generates a random simple graph resembling the
    global properties of the given one.
    It leverages the low-rank approximation of the associated adjacency matrix
    driven by the *alpha* precision parameter.
    SGF preserves the number of nodes of the input graph and their ordering.
    This way, nodes of output graphs resemble the properties of the input one
    and attributes can be directly mapped.

    It considers the graph adjacency matrices which can optionally be
    transformed to other symmetric real matrices (currently transformation
    options include *identity* and *modularity*).
    The *modularity* transformation, in the sense of Newman's modularity matrix
    allows the focusing on community structure related properties of the graph.

    SGF applies a low-rank approximation whose fixed rank is computed from the
    ratio *alpha* of the input graph adjacency matrix dimension.
    This step performs a filtering on the input eigenvectors similar to the low
    pass filtering common in telecommunications.

    The filtered values (after truncation) are used as input to a Bernoulli
    sampling for constructing a random adjacency matrix.

    References
    ----------
    ..  [1] L. Baldesi, C. T. Butts, A. Markopoulou, "Spectral Graph Forge:
        Graph Generation Targeting Modularity", IEEE Infocom, '18.
        https://arxiv.org/abs/1801.01715
    ..  [2] M. Newman, "Networks: an introduction", Oxford university press,
        2010

    Examples
    --------
    >>> G = nx.karate_club_graph()
    >>> H = nx.spectral_graph_forge(G, 0.3)
    >>>
networkx.spectral_layout
Python Library Documentation: function spectral_layout in module networkx.drawing.layout

spectral_layout(G, weight='weight', scale=1, center=None, dim=2)
    Position nodes using the eigenvectors of the graph Laplacian.

    Using the unnormalized Laplacian, the layout shows possible clusters of
    nodes which are an approximation of the ratio cut. If dim is the number of
    dimensions then the positions are the entries of the dim eigenvectors
    corresponding to the ascending eigenvalues starting from the second one.

    Parameters
    ----------
    G : NetworkX graph or list of nodes
        A position will be assigned to every node in G.

    weight : string or None   optional (default='weight')
        The edge attribute that holds the numerical value used for
        the edge weight.  If None, then all edge weights are 1.

    scale : number (default: 1)
        Scale factor for positions.

    center : array-like or None
        Coordinate pair around which to center the layout.

    dim : int
        Dimension of layout.

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> pos = nx.spectral_layout(G)

    Notes
    -----
    Directed graphs will be considered as undirected graphs when
    positioning the nodes.

    For larger graphs (>500 nodes) this will use the SciPy sparse
    eigenvalue solver (ARPACK).
networkx.spectral_ordering
Python Library Documentation: function spectral_ordering in module networkx.linalg.algebraicconnectivity

spectral_ordering(G, weight='weight', normalized=False, tol=1e-08, method='tracemin_pcg', seed=None, *, backend=None, **backend_kwargs)
    Compute the spectral_ordering of a graph.

    The spectral ordering of a graph is an ordering of its nodes where nodes
    in the same weakly connected components appear contiguous and ordered by
    their corresponding elements in the Fiedler vector of the component.

    Parameters
    ----------
    G : NetworkX graph
        A graph.

    weight : object, optional (default: None)
        The data key used to determine the weight of each edge. If None, then
        each edge has unit weight.

    normalized : bool, optional (default: False)
        Whether the normalized Laplacian matrix is used.

    tol : float, optional (default: 1e-8)
        Tolerance of relative residual in eigenvalue computation.

    method : string, optional (default: 'tracemin_pcg')
        Method of eigenvalue computation. It must be one of the tracemin
        options shown below (TraceMIN), 'lanczos' (Lanczos iteration)
        or 'lobpcg' (LOBPCG).

        The TraceMIN algorithm uses a linear system solver. The following
        values allow specifying the solver to be used.

        =============== ========================================
        Value           Solver
        =============== ========================================
        'tracemin_pcg'  Preconditioned conjugate gradient method
        'tracemin_lu'   LU factorization
        =============== ========================================

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    Returns
    -------
    spectral_ordering : NumPy array of floats.
        Spectral ordering of nodes.

    Raises
    ------
    NetworkXError
        If G is empty.

    Notes
    -----
    Edge weights are interpreted by their absolute values. For MultiGraph's,
    weights of parallel edges are summed. Zero-weighted edges are ignored.

    See Also
    --------
    laplacian_matrix
networkx.spectrum
Python Library Documentation: module networkx.linalg.spectrum in networkx.linalg

NAME
    networkx.linalg.spectrum - Eigenvalue spectrum of graphs.

FUNCTIONS
    adjacency_spectrum(G, weight='weight', *, backend=None, **backend_kwargs)
        Returns eigenvalues of the adjacency matrix of G.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        weight : string or None, optional (default='weight')
           The edge data key used to compute each value in the matrix.
           If None, then each edge has weight 1.

        Returns
        -------
        evals : NumPy array
          Eigenvalues

        Notes
        -----
        For MultiGraph/MultiDiGraph, the edges weights are summed.
        See to_numpy_array for other options.

        See Also
        --------
        adjacency_matrix

    bethe_hessian_spectrum(G, r=None, *, backend=None, **backend_kwargs)
        Returns eigenvalues of the Bethe Hessian matrix of G.

        Parameters
        ----------
        G : Graph
           A NetworkX Graph or DiGraph

        r : float
           Regularizer parameter

        Returns
        -------
        evals : NumPy array
          Eigenvalues

        See Also
        --------
        bethe_hessian_matrix

        References
        ----------
        .. [1] A. Saade, F. Krzakala and L. Zdeborová
           "Spectral clustering of graphs with the bethe hessian",
           Advances in Neural Information Processing Systems. 2014.

    laplacian_spectrum(G, weight='weight', *, backend=None, **backend_kwargs)
        Returns eigenvalues of the Laplacian of G

        Parameters
        ----------
        G : graph
           A NetworkX graph

        weight : string or None, optional (default='weight')
           The edge data key used to compute each value in the matrix.
           If None, then each edge has weight 1.

        Returns
        -------
        evals : NumPy array
          Eigenvalues

        Notes
        -----
        For MultiGraph/MultiDiGraph, the edges weights are summed.
        See :func:`~networkx.convert_matrix.to_numpy_array` for other options.

        See Also
        --------
        laplacian_matrix

        Examples
        --------
        The multiplicity of 0 as an eigenvalue of the laplacian matrix is equal
        to the number of connected components of G.

        >>> G = nx.Graph()  # Create a graph with 5 nodes and 3 connected components
        >>> G.add_nodes_from(range(5))
        >>> G.add_edges_from([(0, 2), (3, 4)])
        >>> nx.laplacian_spectrum(G)
        array([0., 0., 0., 2., 2.])

    modularity_spectrum(G, *, backend=None, **backend_kwargs)
        Returns eigenvalues of the modularity matrix of G.

        Parameters
        ----------
        G : Graph
           A NetworkX Graph or DiGraph

        Returns
        -------
        evals : NumPy array
          Eigenvalues

        See Also
        --------
        modularity_matrix

        References
        ----------
        .. [1] M. E. J. Newman, "Modularity and community structure in networks",
           Proc. Natl. Acad. Sci. USA, vol. 103, pp. 8577-8582, 2006.

    normalized_laplacian_spectrum(G, weight='weight', *, backend=None, **backend_kwargs)
        Return eigenvalues of the normalized Laplacian of G

        Parameters
        ----------
        G : graph
           A NetworkX graph

        weight : string or None, optional (default='weight')
           The edge data key used to compute each value in the matrix.
           If None, then each edge has weight 1.

        Returns
        -------
        evals : NumPy array
          Eigenvalues

        Notes
        -----
        For MultiGraph/MultiDiGraph, the edges weights are summed.
        See to_numpy_array for other options.

        See Also
        --------
        normalized_laplacian_matrix

DATA
    __all__ = ['laplacian_spectrum', 'adjacency_spectrum', 'modularity_spe...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\linalg\spectrum.py

networkx.spiral_layout
Python Library Documentation: function spiral_layout in module networkx.drawing.layout

spiral_layout(G, scale=1, center=None, dim=2, resolution=0.35, equidistant=False)
    Position nodes in a spiral layout.

    Parameters
    ----------
    G : NetworkX graph or list of nodes
        A position will be assigned to every node in G.
    scale : number (default: 1)
        Scale factor for positions.
    center : array-like or None
        Coordinate pair around which to center the layout.
    dim : int, default=2
        Dimension of layout, currently only dim=2 is supported.
        Other dimension values result in a ValueError.
    resolution : float, default=0.35
        The compactness of the spiral layout returned.
        Lower values result in more compressed spiral layouts.
    equidistant : bool, default=False
        If True, nodes will be positioned equidistant from each other
        by decreasing angle further from center.
        If False, nodes will be positioned at equal angles
        from each other by increasing separation further from center.

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node

    Raises
    ------
    ValueError
        If dim != 2

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> pos = nx.spiral_layout(G)
    >>> nx.draw(G, pos=pos)

    Notes
    -----
    This algorithm currently only works in two dimensions.
networkx.spring_layout
Python Library Documentation: function spring_layout in module networkx.drawing.layout

spring_layout(G, k=None, pos=None, fixed=None, iterations=50, threshold=0.0001, weight='weight', scale=1, center=None, dim=2, seed=None)
    Position nodes using Fruchterman-Reingold force-directed algorithm.

    The algorithm simulates a force-directed representation of the network
    treating edges as springs holding nodes close, while treating nodes
    as repelling objects, sometimes called an anti-gravity force.
    Simulation continues until the positions are close to an equilibrium.

    There are some hard-coded values: minimal distance between
    nodes (0.01) and "temperature" of 0.1 to ensure nodes don't fly away.
    During the simulation, `k` helps determine the distance between nodes,
    though `scale` and `center` determine the size and place after
    rescaling occurs at the end of the simulation.

    Fixing some nodes doesn't allow them to move in the simulation.
    It also turns off the rescaling feature at the simulation's end.
    In addition, setting `scale` to `None` turns off rescaling.

    Parameters
    ----------
    G : NetworkX graph or list of nodes
        A position will be assigned to every node in G.

    k : float (default=None)
        Optimal distance between nodes.  If None the distance is set to
        1/sqrt(n) where n is the number of nodes.  Increase this value
        to move nodes farther apart.

    pos : dict or None  optional (default=None)
        Initial positions for nodes as a dictionary with node as keys
        and values as a coordinate list or tuple.  If None, then use
        random initial positions.

    fixed : list or None  optional (default=None)
        Nodes to keep fixed at initial position.
        Nodes not in ``G.nodes`` are ignored.
        ValueError raised if `fixed` specified and `pos` not.

    iterations : int  optional (default=50)
        Maximum number of iterations taken

    threshold: float optional (default = 1e-4)
        Threshold for relative error in node position changes.
        The iteration stops if the error is below this threshold.

    weight : string or None   optional (default='weight')
        The edge attribute that holds the numerical value used for
        the edge weight.  Larger means a stronger attractive force.
        If None, then all edge weights are 1.

    scale : number or None (default: 1)
        Scale factor for positions. Not used unless `fixed is None`.
        If scale is None, no rescaling is performed.

    center : array-like or None
        Coordinate pair around which to center the layout.
        Not used unless `fixed is None`.

    dim : int
        Dimension of layout.

    seed : int, RandomState instance or None  optional (default=None)
        Used only for the initial positions in the algorithm.
        Set the random state for deterministic node layouts.
        If int, `seed` is the seed used by the random number generator,
        if numpy.random.RandomState instance, `seed` is the random
        number generator,
        if None, the random number generator is the RandomState instance used
        by numpy.random.

    Returns
    -------
    pos : dict
        A dictionary of positions keyed by node

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> pos = nx.spring_layout(G)

    # The same using longer but equivalent function name
    >>> pos = nx.fruchterman_reingold_layout(G)
networkx.square_clustering
Python Library Documentation: function square_clustering in module networkx.algorithms.cluster

square_clustering(G, nodes=None, *, backend=None, **backend_kwargs)
    Compute the squares clustering coefficient for nodes.

    For each node return the fraction of possible squares that exist at
    the node [1]_

    .. math::
       C_4(v) = \frac{ \sum_{u=1}^{k_v}
       \sum_{w=u+1}^{k_v} q_v(u,w) }{ \sum_{u=1}^{k_v}
       \sum_{w=u+1}^{k_v} [a_v(u,w) + q_v(u,w)]},

    where :math:`q_v(u,w)` are the number of common neighbors of :math:`u` and
    :math:`w` other than :math:`v` (ie squares), and :math:`a_v(u,w) = (k_u -
    (1+q_v(u,w)+\theta_{uv})) + (k_w - (1+q_v(u,w)+\theta_{uw}))`, where
    :math:`\theta_{uw} = 1` if :math:`u` and :math:`w` are connected and 0
    otherwise. [2]_

    Parameters
    ----------
    G : graph

    nodes : container of nodes, optional (default=all nodes in G)
       Compute clustering for nodes in this container.

    Returns
    -------
    c4 : dictionary
       A dictionary keyed by node with the square clustering coefficient value.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> print(nx.square_clustering(G, 0))
    1.0
    >>> print(nx.square_clustering(G))
    {0: 1.0, 1: 1.0, 2: 1.0, 3: 1.0, 4: 1.0}

    Notes
    -----
    While :math:`C_3(v)` (triangle clustering) gives the probability that
    two neighbors of node v are connected with each other, :math:`C_4(v)` is
    the probability that two neighbors of node v share a common
    neighbor different from v. This algorithm can be applied to both
    bipartite and unipartite networks.

    References
    ----------
    .. [1] Pedro G. Lind, Marta C. González, and Hans J. Herrmann. 2005
        Cycles and clustering in bipartite networks.
        Physical Review E (72) 056127.
    .. [2] Zhang, Peng et al. Clustering Coefficient and Community Structure of
        Bipartite Networks. Physica A: Statistical Mechanics and its Applications 387.27 (2008): 6869–6875.
        https://arxiv.org/abs/0710.0117v1
networkx.star_graph
Python Library Documentation: function star_graph in module networkx.generators.classic

star_graph(n, create_using=None, *, backend=None, **backend_kwargs)
    Return the star graph

    The star graph consists of one center node connected to n outer nodes.

    .. plot::

        >>> nx.draw(nx.star_graph(6))

    Parameters
    ----------
    n : int or iterable
        If an integer, node labels are 0 to n with center 0.
        If an iterable of nodes, the center is the first.
        Warning: n is not checked for duplicates and if present the
        resulting graph may not be as desired. Make sure you have no duplicates.
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Notes
    -----
    The graph has n+1 nodes for integer n.
    So star_graph(3) is the same as star_graph(range(4)).
networkx.stochastic
Python Library Documentation: module networkx.generators.stochastic in networkx.generators

NAME
    networkx.generators.stochastic

DESCRIPTION
    Functions for generating stochastic graphs from a given weighted directed
    graph.

FUNCTIONS
    stochastic_graph(G, copy=True, weight='weight', *, backend=None, **backend_kwargs)
        Returns a right-stochastic representation of directed graph `G`.

        A right-stochastic graph is a weighted digraph in which for each
        node, the sum of the weights of all the out-edges of that node is
        1. If the graph is already weighted (for example, via a 'weight'
        edge attribute), the reweighting takes that into account.

        Parameters
        ----------
        G : directed graph
            A :class:`~networkx.DiGraph` or :class:`~networkx.MultiDiGraph`.

        copy : boolean, optional
            If this is True, then this function returns a new graph with
            the stochastic reweighting. Otherwise, the original graph is
            modified in-place (and also returned, for convenience).

        weight : edge attribute key (optional, default='weight')
            Edge attribute key used for reading the existing weight and
            setting the new weight.  If no attribute with this key is found
            for an edge, then the edge weight is assumed to be 1. If an edge
            has a weight, it must be a positive number.

DATA
    __all__ = ['stochastic_graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\stochastic.py

networkx.stochastic_block_model
Python Library Documentation: function stochastic_block_model in module networkx.generators.community

stochastic_block_model(sizes, p, nodelist=None, seed=None, directed=False, selfloops=False, sparse=True, *, backend=None, **backend_kwargs)
    Returns a stochastic block model graph.

    This model partitions the nodes in blocks of arbitrary sizes, and places
    edges between pairs of nodes independently, with a probability that depends
    on the blocks.

    Parameters
    ----------
    sizes : list of ints
        Sizes of blocks
    p : list of list of floats
        Element (r,s) gives the density of edges going from the nodes
        of group r to nodes of group s.
        p must match the number of groups (len(sizes) == len(p)),
        and it must be symmetric if the graph is undirected.
    nodelist : list, optional
        The block tags are assigned according to the node identifiers
        in nodelist. If nodelist is None, then the ordering is the
        range [0,sum(sizes)-1].
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    directed : boolean optional, default=False
        Whether to create a directed graph or not.
    selfloops : boolean optional, default=False
        Whether to include self-loops or not.
    sparse: boolean optional, default=True
        Use the sparse heuristic to speed up the generator.

    Returns
    -------
    g : NetworkX Graph or DiGraph
        Stochastic block model graph of size sum(sizes)

    Raises
    ------
    NetworkXError
      If probabilities are not in [0,1].
      If the probability matrix is not square (directed case).
      If the probability matrix is not symmetric (undirected case).
      If the sizes list does not match nodelist or the probability matrix.
      If nodelist contains duplicate.

    Examples
    --------
    >>> sizes = [75, 75, 300]
    >>> probs = [[0.25, 0.05, 0.02], [0.05, 0.35, 0.07], [0.02, 0.07, 0.40]]
    >>> g = nx.stochastic_block_model(sizes, probs, seed=0)
    >>> len(g)
    450
    >>> H = nx.quotient_graph(g, g.graph["partition"], relabel=True)
    >>> for v in H.nodes(data=True):
    ...     print(round(v[1]["density"], 3))
    0.245
    0.348
    0.405
    >>> for v in H.edges(data=True):
    ...     print(round(1.0 * v[2]["weight"] / (sizes[v[0]] * sizes[v[1]]), 3))
    0.051
    0.022
    0.07

    See Also
    --------
    random_partition_graph
    planted_partition_graph
    gaussian_random_partition_graph
    gnp_random_graph

    References
    ----------
    .. [1] Holland, P. W., Laskey, K. B., & Leinhardt, S.,
           "Stochastic blockmodels: First steps",
           Social networks, 5(2), 109-137, 1983.
networkx.stochastic_graph
Python Library Documentation: function stochastic_graph in module networkx.generators.stochastic

stochastic_graph(G, copy=True, weight='weight', *, backend=None, **backend_kwargs)
    Returns a right-stochastic representation of directed graph `G`.

    A right-stochastic graph is a weighted digraph in which for each
    node, the sum of the weights of all the out-edges of that node is
    1. If the graph is already weighted (for example, via a 'weight'
    edge attribute), the reweighting takes that into account.

    Parameters
    ----------
    G : directed graph
        A :class:`~networkx.DiGraph` or :class:`~networkx.MultiDiGraph`.

    copy : boolean, optional
        If this is True, then this function returns a new graph with
        the stochastic reweighting. Otherwise, the original graph is
        modified in-place (and also returned, for convenience).

    weight : edge attribute key (optional, default='weight')
        Edge attribute key used for reading the existing weight and
        setting the new weight.  If no attribute with this key is found
        for an edge, then the edge weight is assumed to be 1. If an edge
        has a weight, it must be a positive number.
networkx.stoer_wagner
Python Library Documentation: function stoer_wagner in module networkx.algorithms.connectivity.stoerwagner

stoer_wagner(G, weight='weight', heap=<class 'networkx.utils.heaps.BinaryHeap'>, *, backend=None, **backend_kwargs)
    Returns the weighted minimum edge cut using the Stoer-Wagner algorithm.

    Determine the minimum edge cut of a connected graph using the
    Stoer-Wagner algorithm. In weighted cases, all weights must be
    nonnegative.

    The running time of the algorithm depends on the type of heaps used:

    ============== =============================================
    Type of heap   Running time
    ============== =============================================
    Binary heap    $O(n (m + n) \log n)$
    Fibonacci heap $O(nm + n^2 \log n)$
    Pairing heap   $O(2^{2 \sqrt{\log \log n}} nm + n^2 \log n)$
    ============== =============================================

    Parameters
    ----------
    G : NetworkX graph
        Edges of the graph are expected to have an attribute named by the
        weight parameter below. If this attribute is not present, the edge is
        considered to have unit weight.

    weight : string
        Name of the weight attribute of the edges. If the attribute is not
        present, unit weight is assumed. Default value: 'weight'.

    heap : class
        Type of heap to be used in the algorithm. It should be a subclass of
        :class:`MinHeap` or implement a compatible interface.

        If a stock heap implementation is to be used, :class:`BinaryHeap` is
        recommended over :class:`PairingHeap` for Python implementations without
        optimized attribute accesses (e.g., CPython) despite a slower
        asymptotic running time. For Python implementations with optimized
        attribute accesses (e.g., PyPy), :class:`PairingHeap` provides better
        performance. Default value: :class:`BinaryHeap`.

    Returns
    -------
    cut_value : integer or float
        The sum of weights of edges in a minimum cut.

    partition : pair of node lists
        A partitioning of the nodes that defines a minimum cut.

    Raises
    ------
    NetworkXNotImplemented
        If the graph is directed or a multigraph.

    NetworkXError
        If the graph has less than two nodes, is not connected or has a
        negative-weighted edge.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_edge("x", "a", weight=3)
    >>> G.add_edge("x", "b", weight=1)
    >>> G.add_edge("a", "c", weight=3)
    >>> G.add_edge("b", "c", weight=5)
    >>> G.add_edge("b", "d", weight=4)
    >>> G.add_edge("d", "e", weight=2)
    >>> G.add_edge("c", "y", weight=2)
    >>> G.add_edge("e", "y", weight=3)
    >>> cut_value, partition = nx.stoer_wagner(G)
    >>> cut_value
    4
networkx.strong_product
Python Library Documentation: function strong_product in module networkx.algorithms.operators.product

strong_product(G, H, *, backend=None, **backend_kwargs)
    Returns the strong product of G and H.

    The strong product $P$ of the graphs $G$ and $H$ has a node set that
    is the Cartesian product of the node sets, $V(P)=V(G) \times V(H)$.
    $P$ has an edge $((u,x), (v,y))$ if any of the following conditions
    are met:

    - $u=v$ and $(x,y)$ is an edge in $H$
    - $x=y$ and $(u,v)$ is an edge in $G$
    - $(u,v)$ is an edge in $G$ and $(x,y)$ is an edge in $H$

    Parameters
    ----------
    G, H: graphs
     Networkx graphs.

    Returns
    -------
    P: NetworkX graph
     The Cartesian product of G and H. P will be a multi-graph if either G
     or H is a multi-graph. Will be a directed if G and H are directed,
     and undirected if G and H are undirected.

    Raises
    ------
    NetworkXError
     If G and H are not both directed or both undirected.

    Notes
    -----
    Node attributes in P are two-tuple of the G and H node attributes.
    Missing attributes are assigned None.

    Examples
    --------
    >>> G = nx.Graph()
    >>> H = nx.Graph()
    >>> G.add_node(0, a1=True)
    >>> H.add_node("a", a2="Spam")
    >>> P = nx.strong_product(G, H)
    >>> list(P)
    [(0, 'a')]

    Edge attributes and edge keys (for multigraphs) are also copied to the
    new product graph
networkx.strongly_connected
Python Library Documentation: module networkx.algorithms.components.strongly_connected in networkx.algorithms.components

NAME
    networkx.algorithms.components.strongly_connected - Strongly connected components.

FUNCTIONS
    condensation(G, scc=None, *, backend=None, **backend_kwargs)
        Returns the condensation of G.

        The condensation of G is the graph with each of the strongly connected
        components contracted into a single node.

        Parameters
        ----------
        G : NetworkX DiGraph
           A directed graph.

        scc:  list or generator (optional, default=None)
           Strongly connected components. If provided, the elements in
           `scc` must partition the nodes in `G`. If not provided, it will be
           calculated as scc=nx.strongly_connected_components(G).

        Returns
        -------
        C : NetworkX DiGraph
           The condensation graph C of G.  The node labels are integers
           corresponding to the index of the component in the list of
           strongly connected components of G.  C has a graph attribute named
           'mapping' with a dictionary mapping the original nodes to the
           nodes in C to which they belong.  Each node in C also has a node
           attribute 'members' with the set of original nodes in G that
           form the SCC that the node in C represents.

        Raises
        ------
        NetworkXNotImplemented
            If G is undirected.

        Examples
        --------
        Contracting two sets of strongly connected nodes into two distinct SCC
        using the barbell graph.

        >>> G = nx.barbell_graph(4, 0)
        >>> G.remove_edge(3, 4)
        >>> G = nx.DiGraph(G)
        >>> H = nx.condensation(G)
        >>> H.nodes.data()
        NodeDataView({0: {'members': {0, 1, 2, 3}}, 1: {'members': {4, 5, 6, 7}}})
        >>> H.graph["mapping"]
        {0: 0, 1: 0, 2: 0, 3: 0, 4: 1, 5: 1, 6: 1, 7: 1}

        Contracting a complete graph into one single SCC.

        >>> G = nx.complete_graph(7, create_using=nx.DiGraph)
        >>> H = nx.condensation(G)
        >>> H.nodes
        NodeView((0,))
        >>> H.nodes.data()
        NodeDataView({0: {'members': {0, 1, 2, 3, 4, 5, 6}}})

        Notes
        -----
        After contracting all strongly connected components to a single node,
        the resulting graph is a directed acyclic graph.

    is_strongly_connected(G, *, backend=None, **backend_kwargs)
        Test directed graph for strong connectivity.

        A directed graph is strongly connected if and only if every vertex in
        the graph is reachable from every other vertex.

        Parameters
        ----------
        G : NetworkX Graph
           A directed graph.

        Returns
        -------
        connected : bool
          True if the graph is strongly connected, False otherwise.

        Examples
        --------
        >>> G = nx.DiGraph([(0, 1), (1, 2), (2, 3), (3, 0), (2, 4), (4, 2)])
        >>> nx.is_strongly_connected(G)
        True
        >>> G.remove_edge(2, 3)
        >>> nx.is_strongly_connected(G)
        False

        Raises
        ------
        NetworkXNotImplemented
            If G is undirected.

        See Also
        --------
        is_weakly_connected
        is_semiconnected
        is_connected
        is_biconnected
        strongly_connected_components

        Notes
        -----
        For directed graphs only.

    kosaraju_strongly_connected_components(G, source=None, *, backend=None, **backend_kwargs)
        Generate nodes in strongly connected components of graph.

        Parameters
        ----------
        G : NetworkX Graph
            A directed graph.

        Returns
        -------
        comp : generator of sets
            A generator of sets of nodes, one for each strongly connected
            component of G.

        Raises
        ------
        NetworkXNotImplemented
            If G is undirected.

        Examples
        --------
        Generate a sorted list of strongly connected components, largest first.

        >>> G = nx.cycle_graph(4, create_using=nx.DiGraph())
        >>> nx.add_cycle(G, [10, 11, 12])
        >>> [
        ...     len(c)
        ...     for c in sorted(
        ...         nx.kosaraju_strongly_connected_components(G), key=len, reverse=True
        ...     )
        ... ]
        [4, 3]

        If you only want the largest component, it's more efficient to
        use max instead of sort.

        >>> largest = max(nx.kosaraju_strongly_connected_components(G), key=len)

        See Also
        --------
        strongly_connected_components

        Notes
        -----
        Uses Kosaraju's algorithm.

    number_strongly_connected_components(G, *, backend=None, **backend_kwargs)
        Returns number of strongly connected components in graph.

        Parameters
        ----------
        G : NetworkX graph
           A directed graph.

        Returns
        -------
        n : integer
           Number of strongly connected components

        Raises
        ------
        NetworkXNotImplemented
            If G is undirected.

        Examples
        --------
        >>> G = nx.DiGraph(
        ...     [(0, 1), (1, 2), (2, 0), (2, 3), (4, 5), (3, 4), (5, 6), (6, 3), (6, 7)]
        ... )
        >>> nx.number_strongly_connected_components(G)
        3

        See Also
        --------
        strongly_connected_components
        number_connected_components
        number_weakly_connected_components

        Notes
        -----
        For directed graphs only.

    strongly_connected_components(G, *, backend=None, **backend_kwargs)
        Generate nodes in strongly connected components of graph.

        Parameters
        ----------
        G : NetworkX Graph
            A directed graph.

        Returns
        -------
        comp : generator of sets
            A generator of sets of nodes, one for each strongly connected
            component of G.

        Raises
        ------
        NetworkXNotImplemented
            If G is undirected.

        Examples
        --------
        Generate a sorted list of strongly connected components, largest first.

        >>> G = nx.cycle_graph(4, create_using=nx.DiGraph())
        >>> nx.add_cycle(G, [10, 11, 12])
        >>> [
        ...     len(c)
        ...     for c in sorted(nx.strongly_connected_components(G), key=len, reverse=True)
        ... ]
        [4, 3]

        If you only want the largest component, it's more efficient to
        use max instead of sort.

        >>> largest = max(nx.strongly_connected_components(G), key=len)

        See Also
        --------
        connected_components
        weakly_connected_components
        kosaraju_strongly_connected_components

        Notes
        -----
        Uses Tarjan's algorithm[1]_ with Nuutila's modifications[2]_.
        Nonrecursive version of algorithm.

        References
        ----------
        .. [1] Depth-first search and linear graph algorithms, R. Tarjan
           SIAM Journal of Computing 1(2):146-160, (1972).

        .. [2] On finding the strongly connected components in a directed graph.
           E. Nuutila and E. Soisalon-Soinen
           Information Processing Letters 49(1): 9-14, (1994)..

DATA
    __all__ = ['number_strongly_connected_components', 'strongly_connected...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\components\strongly_connected.py

networkx.strongly_connected_components
Python Library Documentation: function strongly_connected_components in module networkx.algorithms.components.strongly_connected

strongly_connected_components(G, *, backend=None, **backend_kwargs)
    Generate nodes in strongly connected components of graph.

    Parameters
    ----------
    G : NetworkX Graph
        A directed graph.

    Returns
    -------
    comp : generator of sets
        A generator of sets of nodes, one for each strongly connected
        component of G.

    Raises
    ------
    NetworkXNotImplemented
        If G is undirected.

    Examples
    --------
    Generate a sorted list of strongly connected components, largest first.

    >>> G = nx.cycle_graph(4, create_using=nx.DiGraph())
    >>> nx.add_cycle(G, [10, 11, 12])
    >>> [
    ...     len(c)
    ...     for c in sorted(nx.strongly_connected_components(G), key=len, reverse=True)
    ... ]
    [4, 3]

    If you only want the largest component, it's more efficient to
    use max instead of sort.

    >>> largest = max(nx.strongly_connected_components(G), key=len)

    See Also
    --------
    connected_components
    weakly_connected_components
    kosaraju_strongly_connected_components

    Notes
    -----
    Uses Tarjan's algorithm[1]_ with Nuutila's modifications[2]_.
    Nonrecursive version of algorithm.

    References
    ----------
    .. [1] Depth-first search and linear graph algorithms, R. Tarjan
       SIAM Journal of Computing 1(2):146-160, (1972).

    .. [2] On finding the strongly connected components in a directed graph.
       E. Nuutila and E. Soisalon-Soinen
       Information Processing Letters 49(1): 9-14, (1994)..
networkx.structuralholes
Python Library Documentation: module networkx.algorithms.structuralholes in networkx.algorithms

NAME
    networkx.algorithms.structuralholes - Functions for computing measures of structural holes.

FUNCTIONS
    constraint(G, nodes=None, weight=None, *, backend=None, **backend_kwargs)
        Returns the constraint on all nodes in the graph ``G``.

        The *constraint* is a measure of the extent to which a node *v* is
        invested in those nodes that are themselves invested in the
        neighbors of *v*. Formally, the *constraint on v*, denoted `c(v)`,
        is defined by

        .. math::

           c(v) = \sum_{w \in N(v) \setminus \{v\}} \ell(v, w)

        where $N(v)$ is the subset of the neighbors of `v` that are either
        predecessors or successors of `v` and $\ell(v, w)$ is the local
        constraint on `v` with respect to `w` [1]_. For the definition of local
        constraint, see :func:`local_constraint`.

        Parameters
        ----------
        G : NetworkX graph
            The graph containing ``v``. This can be either directed or undirected.

        nodes : container, optional
            Container of nodes in the graph ``G`` to compute the constraint. If
            None, the constraint of every node is computed.

        weight : None or string, optional
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.

        Returns
        -------
        dict
            Dictionary with nodes as keys and the constraint on the node as values.

        See also
        --------
        local_constraint

        References
        ----------
        .. [1] Burt, Ronald S.
               "Structural holes and good ideas".
               American Journal of Sociology (110): 349–399.

    effective_size(G, nodes=None, weight=None, *, backend=None, **backend_kwargs)
        Returns the effective size of all nodes in the graph ``G``.

        The *effective size* of a node's ego network is based on the concept
        of redundancy. A person's ego network has redundancy to the extent
        that her contacts are connected to each other as well. The
        nonredundant part of a person's relationships is the effective
        size of her ego network [1]_.  Formally, the effective size of a
        node $u$, denoted $e(u)$, is defined by

        .. math::

           e(u) = \sum_{v \in N(u) \setminus \{u\}}
           \left(1 - \sum_{w \in N(v)} p_{uw} m_{vw}\right)

        where $N(u)$ is the set of neighbors of $u$ and $p_{uw}$ is the
        normalized mutual weight of the (directed or undirected) edges
        joining $u$ and $v$, for each vertex $u$ and $v$ [1]_. And $m_{vw}$
        is the mutual weight of $v$ and $w$ divided by $v$ highest mutual
        weight with any of its neighbors. The *mutual weight* of $u$ and $v$
        is the sum of the weights of edges joining them (edge weights are
        assumed to be one if the graph is unweighted).

        For the case of unweighted and undirected graphs, Borgatti proposed
        a simplified formula to compute effective size [2]_

        .. math::

           e(u) = n - \frac{2t}{n}

        where `t` is the number of ties in the ego network (not including
        ties to ego) and `n` is the number of nodes (excluding ego).

        Parameters
        ----------
        G : NetworkX graph
            The graph containing ``v``. Directed graphs are treated like
            undirected graphs when computing neighbors of ``v``.

        nodes : container, optional
            Container of nodes in the graph ``G`` to compute the effective size.
            If None, the effective size of every node is computed.

        weight : None or string, optional
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.

        Returns
        -------
        dict
            Dictionary with nodes as keys and the effective size of the node as values.

        Notes
        -----
        Burt also defined the related concept of *efficiency* of a node's ego
        network, which is its effective size divided by the degree of that
        node [1]_. So you can easily compute efficiency:

        >>> G = nx.DiGraph()
        >>> G.add_edges_from([(0, 1), (0, 2), (1, 0), (2, 1)])
        >>> esize = nx.effective_size(G)
        >>> efficiency = {n: v / G.degree(n) for n, v in esize.items()}

        See also
        --------
        constraint

        References
        ----------
        .. [1] Burt, Ronald S.
               *Structural Holes: The Social Structure of Competition.*
               Cambridge: Harvard University Press, 1995.

        .. [2] Borgatti, S.
               "Structural Holes: Unpacking Burt's Redundancy Measures"
               CONNECTIONS 20(1):35-38.
               http://www.analytictech.com/connections/v20(1)/holes.htm

    local_constraint(G, u, v, weight=None, *, backend=None, **backend_kwargs)
        Returns the local constraint on the node ``u`` with respect to
        the node ``v`` in the graph ``G``.

        Formally, the *local constraint on u with respect to v*, denoted
        $\ell(u, v)$, is defined by

        .. math::

           \ell(u, v) = \left(p_{uv} + \sum_{w \in N(v)} p_{uw} p_{wv}\right)^2,

        where $N(v)$ is the set of neighbors of $v$ and $p_{uv}$ is the
        normalized mutual weight of the (directed or undirected) edges
        joining $u$ and $v$, for each vertex $u$ and $v$ [1]_. The *mutual
        weight* of $u$ and $v$ is the sum of the weights of edges joining
        them (edge weights are assumed to be one if the graph is
        unweighted).

        Parameters
        ----------
        G : NetworkX graph
            The graph containing ``u`` and ``v``. This can be either
            directed or undirected.

        u : node
            A node in the graph ``G``.

        v : node
            A node in the graph ``G``.

        weight : None or string, optional
          If None, all edge weights are considered equal.
          Otherwise holds the name of the edge attribute used as weight.

        Returns
        -------
        float
            The constraint of the node ``v`` in the graph ``G``.

        See also
        --------
        constraint

        References
        ----------
        .. [1] Burt, Ronald S.
               "Structural holes and good ideas".
               American Journal of Sociology (110): 349–399.

DATA
    __all__ = ['constraint', 'local_constraint', 'effective_size']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\structuralholes.py

networkx.subgraph
Python Library Documentation: function subgraph in module networkx.classes.function

subgraph(G, nbunch)
    Returns the subgraph induced on nodes in nbunch.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    nbunch : list, iterable
       A container of nodes that will be iterated through once (thus
       it should be an iterator or be iterable).  Each element of the
       container should be a valid node type: any hashable type except
       None.  If nbunch is None, return all edges data in the graph.
       Nodes in nbunch that are not in the graph will be (quietly)
       ignored.

    Notes
    -----
    subgraph(G) calls G.subgraph()
networkx.subgraph_alg
Python Library Documentation: module networkx.algorithms.centrality.subgraph_alg in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.subgraph_alg - Subraph centrality and communicability betweenness.

FUNCTIONS
    communicability_betweenness_centrality(G, *, backend=None, **backend_kwargs)
        Returns subgraph communicability for all pairs of nodes in G.

        Communicability betweenness measure makes use of the number of walks
        connecting every pair of nodes as the basis of a betweenness centrality
        measure.

        Parameters
        ----------
        G: graph

        Returns
        -------
        nodes : dictionary
            Dictionary of nodes with communicability betweenness as the value.

        Raises
        ------
        NetworkXError
            If the graph is not undirected and simple.

        Notes
        -----
        Let `G=(V,E)` be a simple undirected graph with `n` nodes and `m` edges,
        and `A` denote the adjacency matrix of `G`.

        Let `G(r)=(V,E(r))` be the graph resulting from
        removing all edges connected to node `r` but not the node itself.

        The adjacency matrix for `G(r)` is `A+E(r)`,  where `E(r)` has nonzeros
        only in row and column `r`.

        The subraph betweenness of a node `r`  is [1]_

        .. math::

             \omega_{r} = \frac{1}{C}\sum_{p}\sum_{q}\frac{G_{prq}}{G_{pq}},
             p\neq q, q\neq r,

        where
        `G_{prq}=(e^{A}_{pq} - (e^{A+E(r)})_{pq}`  is the number of walks
        involving node r,
        `G_{pq}=(e^{A})_{pq}` is the number of closed walks starting
        at node `p` and ending at node `q`,
        and `C=(n-1)^{2}-(n-1)` is a normalization factor equal to the
        number of terms in the sum.

        The resulting `\omega_{r}` takes values between zero and one.
        The lower bound cannot be attained for a connected
        graph, and the upper bound is attained in the star graph.

        References
        ----------
        .. [1] Ernesto Estrada, Desmond J. Higham, Naomichi Hatano,
           "Communicability Betweenness in Complex Networks"
           Physica A 388 (2009) 764-774.
           https://arxiv.org/abs/0905.4102

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (1, 2), (1, 5), (5, 4), (2, 4), (2, 3), (4, 3), (3, 6)])
        >>> cbc = nx.communicability_betweenness_centrality(G)
        >>> print([f"{node} {cbc[node]:0.2f}" for node in sorted(cbc)])
        ['0 0.03', '1 0.45', '2 0.51', '3 0.45', '4 0.40', '5 0.19', '6 0.03']

    estrada_index(G, *, backend=None, **backend_kwargs)
        Returns the Estrada index of a the graph G.

        The Estrada Index is a topological index of folding or 3D "compactness" ([1]_).

        Parameters
        ----------
        G: graph

        Returns
        -------
        estrada index: float

        Raises
        ------
        NetworkXError
            If the graph is not undirected and simple.

        Notes
        -----
        Let `G=(V,E)` be a simple undirected graph with `n` nodes  and let
        `\lambda_{1}\leq\lambda_{2}\leq\cdots\lambda_{n}`
        be a non-increasing ordering of the eigenvalues of its adjacency
        matrix `A`. The Estrada index is ([1]_, [2]_)

        .. math::
            EE(G)=\sum_{j=1}^n e^{\lambda _j}.

        References
        ----------
        .. [1] E. Estrada, "Characterization of 3D molecular structure",
           Chem. Phys. Lett. 319, 713 (2000).
           https://doi.org/10.1016/S0009-2614(00)00158-5
        .. [2] José Antonio de la Peñaa, Ivan Gutman, Juan Rada,
           "Estimating the Estrada index",
           Linear Algebra and its Applications. 427, 1 (2007).
           https://doi.org/10.1016/j.laa.2007.06.020

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (1, 2), (1, 5), (5, 4), (2, 4), (2, 3), (4, 3), (3, 6)])
        >>> ei = nx.estrada_index(G)
        >>> print(f"{ei:0.5}")
        20.55

    subgraph_centrality(G, *, backend=None, **backend_kwargs)
        Returns subgraph centrality for each node in G.

        Subgraph centrality  of a node `n` is the sum of weighted closed
        walks of all lengths starting and ending at node `n`. The weights
        decrease with path length. Each closed walk is associated with a
        connected subgraph ([1]_).

        Parameters
        ----------
        G: graph

        Returns
        -------
        nodes : dictionary
           Dictionary of nodes with subgraph centrality as the value.

        Raises
        ------
        NetworkXError
           If the graph is not undirected and simple.

        See Also
        --------
        subgraph_centrality_exp:
            Alternative algorithm of the subgraph centrality for each node of G.

        Notes
        -----
        This version of the algorithm computes eigenvalues and eigenvectors
        of the adjacency matrix.

        Subgraph centrality of a node `u` in G can be found using
        a spectral decomposition of the adjacency matrix [1]_,

        .. math::

           SC(u)=\sum_{j=1}^{N}(v_{j}^{u})^2 e^{\lambda_{j}},

        where `v_j` is an eigenvector of the adjacency matrix `A` of G
        corresponding to the eigenvalue `\lambda_j`.

        Examples
        --------
        (Example from [1]_)
        >>> G = nx.Graph(
        ...     [
        ...         (1, 2),
        ...         (1, 5),
        ...         (1, 8),
        ...         (2, 3),
        ...         (2, 8),
        ...         (3, 4),
        ...         (3, 6),
        ...         (4, 5),
        ...         (4, 7),
        ...         (5, 6),
        ...         (6, 7),
        ...         (7, 8),
        ...     ]
        ... )
        >>> sc = nx.subgraph_centrality(G)
        >>> print([f"{node} {sc[node]:0.2f}" for node in sorted(sc)])
        ['1 3.90', '2 3.90', '3 3.64', '4 3.71', '5 3.64', '6 3.71', '7 3.64', '8 3.90']

        References
        ----------
        .. [1] Ernesto Estrada, Juan A. Rodriguez-Velazquez,
           "Subgraph centrality in complex networks",
           Physical Review E 71, 056103 (2005).
           https://arxiv.org/abs/cond-mat/0504730

    subgraph_centrality_exp(G, *, backend=None, **backend_kwargs)
        Returns the subgraph centrality for each node of G.

        Subgraph centrality  of a node `n` is the sum of weighted closed
        walks of all lengths starting and ending at node `n`. The weights
        decrease with path length. Each closed walk is associated with a
        connected subgraph ([1]_).

        Parameters
        ----------
        G: graph

        Returns
        -------
        nodes:dictionary
            Dictionary of nodes with subgraph centrality as the value.

        Raises
        ------
        NetworkXError
            If the graph is not undirected and simple.

        See Also
        --------
        subgraph_centrality:
            Alternative algorithm of the subgraph centrality for each node of G.

        Notes
        -----
        This version of the algorithm exponentiates the adjacency matrix.

        The subgraph centrality of a node `u` in G can be found using
        the matrix exponential of the adjacency matrix of G [1]_,

        .. math::

            SC(u)=(e^A)_{uu} .

        References
        ----------
        .. [1] Ernesto Estrada, Juan A. Rodriguez-Velazquez,
           "Subgraph centrality in complex networks",
           Physical Review E 71, 056103 (2005).
           https://arxiv.org/abs/cond-mat/0504730

        Examples
        --------
        (Example from [1]_)
        >>> G = nx.Graph(
        ...     [
        ...         (1, 2),
        ...         (1, 5),
        ...         (1, 8),
        ...         (2, 3),
        ...         (2, 8),
        ...         (3, 4),
        ...         (3, 6),
        ...         (4, 5),
        ...         (4, 7),
        ...         (5, 6),
        ...         (6, 7),
        ...         (7, 8),
        ...     ]
        ... )
        >>> sc = nx.subgraph_centrality_exp(G)
        >>> print([f"{node} {sc[node]:0.2f}" for node in sorted(sc)])
        ['1 3.90', '2 3.90', '3 3.64', '4 3.71', '5 3.64', '6 3.71', '7 3.64', '8 3.90']

DATA
    __all__ = ['subgraph_centrality_exp', 'subgraph_centrality', 'communic...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\subgraph_alg.py

networkx.subgraph_centrality
Python Library Documentation: function subgraph_centrality in module networkx.algorithms.centrality.subgraph_alg

subgraph_centrality(G, *, backend=None, **backend_kwargs)
    Returns subgraph centrality for each node in G.

    Subgraph centrality  of a node `n` is the sum of weighted closed
    walks of all lengths starting and ending at node `n`. The weights
    decrease with path length. Each closed walk is associated with a
    connected subgraph ([1]_).

    Parameters
    ----------
    G: graph

    Returns
    -------
    nodes : dictionary
       Dictionary of nodes with subgraph centrality as the value.

    Raises
    ------
    NetworkXError
       If the graph is not undirected and simple.

    See Also
    --------
    subgraph_centrality_exp:
        Alternative algorithm of the subgraph centrality for each node of G.

    Notes
    -----
    This version of the algorithm computes eigenvalues and eigenvectors
    of the adjacency matrix.

    Subgraph centrality of a node `u` in G can be found using
    a spectral decomposition of the adjacency matrix [1]_,

    .. math::

       SC(u)=\sum_{j=1}^{N}(v_{j}^{u})^2 e^{\lambda_{j}},

    where `v_j` is an eigenvector of the adjacency matrix `A` of G
    corresponding to the eigenvalue `\lambda_j`.

    Examples
    --------
    (Example from [1]_)
    >>> G = nx.Graph(
    ...     [
    ...         (1, 2),
    ...         (1, 5),
    ...         (1, 8),
    ...         (2, 3),
    ...         (2, 8),
    ...         (3, 4),
    ...         (3, 6),
    ...         (4, 5),
    ...         (4, 7),
    ...         (5, 6),
    ...         (6, 7),
    ...         (7, 8),
    ...     ]
    ... )
    >>> sc = nx.subgraph_centrality(G)
    >>> print([f"{node} {sc[node]:0.2f}" for node in sorted(sc)])
    ['1 3.90', '2 3.90', '3 3.64', '4 3.71', '5 3.64', '6 3.71', '7 3.64', '8 3.90']

    References
    ----------
    .. [1] Ernesto Estrada, Juan A. Rodriguez-Velazquez,
       "Subgraph centrality in complex networks",
       Physical Review E 71, 056103 (2005).
       https://arxiv.org/abs/cond-mat/0504730
networkx.subgraph_centrality_exp
Python Library Documentation: function subgraph_centrality_exp in module networkx.algorithms.centrality.subgraph_alg

subgraph_centrality_exp(G, *, backend=None, **backend_kwargs)
    Returns the subgraph centrality for each node of G.

    Subgraph centrality  of a node `n` is the sum of weighted closed
    walks of all lengths starting and ending at node `n`. The weights
    decrease with path length. Each closed walk is associated with a
    connected subgraph ([1]_).

    Parameters
    ----------
    G: graph

    Returns
    -------
    nodes:dictionary
        Dictionary of nodes with subgraph centrality as the value.

    Raises
    ------
    NetworkXError
        If the graph is not undirected and simple.

    See Also
    --------
    subgraph_centrality:
        Alternative algorithm of the subgraph centrality for each node of G.

    Notes
    -----
    This version of the algorithm exponentiates the adjacency matrix.

    The subgraph centrality of a node `u` in G can be found using
    the matrix exponential of the adjacency matrix of G [1]_,

    .. math::

        SC(u)=(e^A)_{uu} .

    References
    ----------
    .. [1] Ernesto Estrada, Juan A. Rodriguez-Velazquez,
       "Subgraph centrality in complex networks",
       Physical Review E 71, 056103 (2005).
       https://arxiv.org/abs/cond-mat/0504730

    Examples
    --------
    (Example from [1]_)
    >>> G = nx.Graph(
    ...     [
    ...         (1, 2),
    ...         (1, 5),
    ...         (1, 8),
    ...         (2, 3),
    ...         (2, 8),
    ...         (3, 4),
    ...         (3, 6),
    ...         (4, 5),
    ...         (4, 7),
    ...         (5, 6),
    ...         (6, 7),
    ...         (7, 8),
    ...     ]
    ... )
    >>> sc = nx.subgraph_centrality_exp(G)
    >>> print([f"{node} {sc[node]:0.2f}" for node in sorted(sc)])
    ['1 3.90', '2 3.90', '3 3.64', '4 3.71', '5 3.64', '6 3.71', '7 3.64', '8 3.90']
networkx.subgraph_view
Python Library Documentation: function subgraph_view in module networkx.classes.graphviews

subgraph_view(G, *, filter_node=<function no_filter at 0x0000029EB2F0AFC0>, filter_edge=<function no_filter at 0x0000029EB2F0AFC0>)
    View of `G` applying a filter on nodes and edges.

    `subgraph_view` provides a read-only view of the input graph that excludes
    nodes and edges based on the outcome of two filter functions `filter_node`
    and `filter_edge`.

    The `filter_node` function takes one argument --- the node --- and returns
    `True` if the node should be included in the subgraph, and `False` if it
    should not be included.

    The `filter_edge` function takes two (or three arguments if `G` is a
    multi-graph) --- the nodes describing an edge, plus the edge-key if
    parallel edges are possible --- and returns `True` if the edge should be
    included in the subgraph, and `False` if it should not be included.

    Both node and edge filter functions are called on graph elements as they
    are queried, meaning there is no up-front cost to creating the view.

    Parameters
    ----------
    G : networkx.Graph
        A directed/undirected graph/multigraph

    filter_node : callable, optional
        A function taking a node as input, which returns `True` if the node
        should appear in the view.

    filter_edge : callable, optional
        A function taking as input the two nodes describing an edge (plus the
        edge-key if `G` is a multi-graph), which returns `True` if the edge
        should appear in the view.

    Returns
    -------
    graph : networkx.Graph
        A read-only graph view of the input graph.

    Examples
    --------
    >>> G = nx.path_graph(6)

    Filter functions operate on the node, and return `True` if the node should
    appear in the view:

    >>> def filter_node(n1):
    ...     return n1 != 5
    >>> view = nx.subgraph_view(G, filter_node=filter_node)
    >>> view.nodes()
    NodeView((0, 1, 2, 3, 4))

    We can use a closure pattern to filter graph elements based on additional
    data --- for example, filtering on edge data attached to the graph:

    >>> G[3][4]["cross_me"] = False
    >>> def filter_edge(n1, n2):
    ...     return G[n1][n2].get("cross_me", True)
    >>> view = nx.subgraph_view(G, filter_edge=filter_edge)
    >>> view.edges()
    EdgeView([(0, 1), (1, 2), (2, 3), (4, 5)])

    >>> view = nx.subgraph_view(
    ...     G,
    ...     filter_node=filter_node,
    ...     filter_edge=filter_edge,
    ... )
    >>> view.nodes()
    NodeView((0, 1, 2, 3, 4))
    >>> view.edges()
    EdgeView([(0, 1), (1, 2), (2, 3)])
networkx.sudoku
Python Library Documentation: module networkx.generators.sudoku in networkx.generators

NAME
    networkx.generators.sudoku - Generator for Sudoku graphs

DESCRIPTION
    This module gives a generator for n-Sudoku graphs. It can be used to develop
    algorithms for solving or generating Sudoku puzzles.

    A completed Sudoku grid is a 9x9 array of integers between 1 and 9, with no
    number appearing twice in the same row, column, or 3x3 box.

    +---------+---------+---------+
    | | 8 6 4 | | 3 7 1 | | 2 5 9 |
    | | 3 2 5 | | 8 4 9 | | 7 6 1 |
    | | 9 7 1 | | 2 6 5 | | 8 4 3 |
    +---------+---------+---------+
    | | 4 3 6 | | 1 9 2 | | 5 8 7 |
    | | 1 9 8 | | 6 5 7 | | 4 3 2 |
    | | 2 5 7 | | 4 8 3 | | 9 1 6 |
    +---------+---------+---------+
    | | 6 8 9 | | 7 3 4 | | 1 2 5 |
    | | 7 1 3 | | 5 2 8 | | 6 9 4 |
    | | 5 4 2 | | 9 1 6 | | 3 7 8 |
    +---------+---------+---------+


    The Sudoku graph is an undirected graph with 81 vertices, corresponding to
    the cells of a Sudoku grid. It is a regular graph of degree 20. Two distinct
    vertices are adjacent if and only if the corresponding cells belong to the
    same row, column, or box. A completed Sudoku grid corresponds to a vertex
    coloring of the Sudoku graph with nine colors.

    More generally, the n-Sudoku graph is a graph with n^4 vertices, corresponding
    to the cells of an n^2 by n^2 grid. Two distinct vertices are adjacent if and
    only if they belong to the same row, column, or n by n box.

    References
    ----------
    .. [1] Herzberg, A. M., & Murty, M. R. (2007). Sudoku squares and chromatic
        polynomials. Notices of the AMS, 54(6), 708-717.
    .. [2] Sander, Torsten (2009), "Sudoku graphs are integral",
        Electronic Journal of Combinatorics, 16 (1): Note 25, 7pp, MR 2529816
    .. [3] Wikipedia contributors. "Glossary of Sudoku." Wikipedia, The Free
        Encyclopedia, 3 Dec. 2019. Web. 22 Dec. 2019.

FUNCTIONS
    sudoku_graph(n=3, *, backend=None, **backend_kwargs)
        Returns the n-Sudoku graph. The default value of n is 3.

        The n-Sudoku graph is a graph with n^4 vertices, corresponding to the
        cells of an n^2 by n^2 grid. Two distinct vertices are adjacent if and
        only if they belong to the same row, column, or n-by-n box.

        Parameters
        ----------
        n: integer
           The order of the Sudoku graph, equal to the square root of the
           number of rows. The default is 3.

        Returns
        -------
        NetworkX graph
            The n-Sudoku graph Sud(n).

        Examples
        --------
        >>> G = nx.sudoku_graph()
        >>> G.number_of_nodes()
        81
        >>> G.number_of_edges()
        810
        >>> sorted(G.neighbors(42))
        [6, 15, 24, 33, 34, 35, 36, 37, 38, 39, 40, 41, 43, 44, 51, 52, 53, 60, 69, 78]
        >>> G = nx.sudoku_graph(2)
        >>> G.number_of_nodes()
        16
        >>> G.number_of_edges()
        56

        References
        ----------
        .. [1] Herzberg, A. M., & Murty, M. R. (2007). Sudoku squares and chromatic
           polynomials. Notices of the AMS, 54(6), 708-717.
        .. [2] Sander, Torsten (2009), "Sudoku graphs are integral",
           Electronic Journal of Combinatorics, 16 (1): Note 25, 7pp, MR 2529816
        .. [3] Wikipedia contributors. "Glossary of Sudoku." Wikipedia, The Free
           Encyclopedia, 3 Dec. 2019. Web. 22 Dec. 2019.

DATA
    __all__ = ['sudoku_graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\sudoku.py

networkx.sudoku_graph
Python Library Documentation: function sudoku_graph in module networkx.generators.sudoku

sudoku_graph(n=3, *, backend=None, **backend_kwargs)
    Returns the n-Sudoku graph. The default value of n is 3.

    The n-Sudoku graph is a graph with n^4 vertices, corresponding to the
    cells of an n^2 by n^2 grid. Two distinct vertices are adjacent if and
    only if they belong to the same row, column, or n-by-n box.

    Parameters
    ----------
    n: integer
       The order of the Sudoku graph, equal to the square root of the
       number of rows. The default is 3.

    Returns
    -------
    NetworkX graph
        The n-Sudoku graph Sud(n).

    Examples
    --------
    >>> G = nx.sudoku_graph()
    >>> G.number_of_nodes()
    81
    >>> G.number_of_edges()
    810
    >>> sorted(G.neighbors(42))
    [6, 15, 24, 33, 34, 35, 36, 37, 38, 39, 40, 41, 43, 44, 51, 52, 53, 60, 69, 78]
    >>> G = nx.sudoku_graph(2)
    >>> G.number_of_nodes()
    16
    >>> G.number_of_edges()
    56

    References
    ----------
    .. [1] Herzberg, A. M., & Murty, M. R. (2007). Sudoku squares and chromatic
       polynomials. Notices of the AMS, 54(6), 708-717.
    .. [2] Sander, Torsten (2009), "Sudoku graphs are integral",
       Electronic Journal of Combinatorics, 16 (1): Note 25, 7pp, MR 2529816
    .. [3] Wikipedia contributors. "Glossary of Sudoku." Wikipedia, The Free
       Encyclopedia, 3 Dec. 2019. Web. 22 Dec. 2019.
networkx.summarization
Python Library Documentation: module networkx.algorithms.summarization in networkx.algorithms

NAME
    networkx.algorithms.summarization

DESCRIPTION
    Graph summarization finds smaller representations of graphs resulting in faster
    runtime of algorithms, reduced storage needs, and noise reduction.
    Summarization has applications in areas such as visualization, pattern mining,
    clustering and community detection, and more.  Core graph summarization
    techniques are grouping/aggregation, bit-compression,
    simplification/sparsification, and influence based. Graph summarization
    algorithms often produce either summary graphs in the form of supergraphs or
    sparsified graphs, or a list of independent structures. Supergraphs are the
    most common product, which consist of supernodes and original nodes and are
    connected by edges and superedges, which represent aggregate edges between
    nodes and supernodes.

    Grouping/aggregation based techniques compress graphs by representing
    close/connected nodes and edges in a graph by a single node/edge in a
    supergraph. Nodes can be grouped together into supernodes based on their
    structural similarities or proximity within a graph to reduce the total number
    of nodes in a graph. Edge-grouping techniques group edges into lossy/lossless
    nodes called compressor or virtual nodes to reduce the total number of edges in
    a graph. Edge-grouping techniques can be lossless, meaning that they can be
    used to re-create the original graph, or techniques can be lossy, requiring
    less space to store the summary graph, but at the expense of lower
    reconstruction accuracy of the original graph.

    Bit-compression techniques minimize the amount of information needed to
    describe the original graph, while revealing structural patterns in the
    original graph.  The two-part minimum description length (MDL) is often used to
    represent the model and the original graph in terms of the model.  A key
    difference between graph compression and graph summarization is that graph
    summarization focuses on finding structural patterns within the original graph,
    whereas graph compression focuses on compressions the original graph to be as
    small as possible.  **NOTE**: Some bit-compression methods exist solely to
    compress a graph without creating a summary graph or finding comprehensible
    structural patterns.

    Simplification/Sparsification techniques attempt to create a sparse
    representation of a graph by removing unimportant nodes and edges from the
    graph.  Sparsified graphs differ from supergraphs created by
    grouping/aggregation by only containing a subset of the original nodes and
    edges of the original graph.

    Influence based techniques aim to find a high-level description of influence
    propagation in a large graph.  These methods are scarce and have been mostly
    applied to social graphs.

    *dedensification* is a grouping/aggregation based technique to compress the
    neighborhoods around high-degree nodes in unweighted graphs by adding
    compressor nodes that summarize multiple edges of the same type to
    high-degree nodes (nodes with a degree greater than a given threshold).
    Dedensification was developed for the purpose of increasing performance of
    query processing around high-degree nodes in graph databases and enables direct
    operations on the compressed graph.  The structural patterns surrounding
    high-degree nodes in the original is preserved while using fewer edges and
    adding a small number of compressor nodes.  The degree of nodes present in the
    original graph is also preserved. The current implementation of dedensification
    supports graphs with one edge type.

    For more information on graph summarization, see `Graph Summarization Methods
    and Applications: A Survey <https://dl.acm.org/doi/abs/10.1145/3186727>`_

FUNCTIONS
    dedensify(G, threshold, prefix=None, copy=True, *, backend=None, **backend_kwargs)
        Compresses neighborhoods around high-degree nodes

        Reduces the number of edges to high-degree nodes by adding compressor nodes
        that summarize multiple edges of the same type to high-degree nodes (nodes
        with a degree greater than a given threshold).  Dedensification also has
        the added benefit of reducing the number of edges around high-degree nodes.
        The implementation currently supports graphs with a single edge type.

        Parameters
        ----------
        G: graph
           A networkx graph
        threshold: int
           Minimum degree threshold of a node to be considered a high degree node.
           The threshold must be greater than or equal to 2.
        prefix: str or None, optional (default: None)
           An optional prefix for denoting compressor nodes
        copy: bool, optional (default: True)
           Indicates if dedensification should be done inplace

        Returns
        -------
        dedensified networkx graph : (graph, set)
            2-tuple of the dedensified graph and set of compressor nodes

        Notes
        -----
        According to the algorithm in [1]_, removes edges in a graph by
        compressing/decompressing the neighborhoods around high degree nodes by
        adding compressor nodes that summarize multiple edges of the same type
        to high-degree nodes.  Dedensification will only add a compressor node when
        doing so will reduce the total number of edges in the given graph. This
        implementation currently supports graphs with a single edge type.

        Examples
        --------
        Dedensification will only add compressor nodes when doing so would result
        in fewer edges::

            >>> original_graph = nx.DiGraph()
            >>> original_graph.add_nodes_from(
            ...     ["1", "2", "3", "4", "5", "6", "A", "B", "C"]
            ... )
            >>> original_graph.add_edges_from(
            ...     [
            ...         ("1", "C"), ("1", "B"),
            ...         ("2", "C"), ("2", "B"), ("2", "A"),
            ...         ("3", "B"), ("3", "A"), ("3", "6"),
            ...         ("4", "C"), ("4", "B"), ("4", "A"),
            ...         ("5", "B"), ("5", "A"),
            ...         ("6", "5"),
            ...         ("A", "6")
            ...     ]
            ... )
            >>> c_graph, c_nodes = nx.dedensify(original_graph, threshold=2)
            >>> original_graph.number_of_edges()
            15
            >>> c_graph.number_of_edges()
            14

        A dedensified, directed graph can be "densified" to reconstruct the
        original graph::

            >>> original_graph = nx.DiGraph()
            >>> original_graph.add_nodes_from(
            ...     ["1", "2", "3", "4", "5", "6", "A", "B", "C"]
            ... )
            >>> original_graph.add_edges_from(
            ...     [
            ...         ("1", "C"), ("1", "B"),
            ...         ("2", "C"), ("2", "B"), ("2", "A"),
            ...         ("3", "B"), ("3", "A"), ("3", "6"),
            ...         ("4", "C"), ("4", "B"), ("4", "A"),
            ...         ("5", "B"), ("5", "A"),
            ...         ("6", "5"),
            ...         ("A", "6")
            ...     ]
            ... )
            >>> c_graph, c_nodes = nx.dedensify(original_graph, threshold=2)
            >>> # re-densifies the compressed graph into the original graph
            >>> for c_node in c_nodes:
            ...     all_neighbors = set(nx.all_neighbors(c_graph, c_node))
            ...     out_neighbors = set(c_graph.neighbors(c_node))
            ...     for out_neighbor in out_neighbors:
            ...         c_graph.remove_edge(c_node, out_neighbor)
            ...     in_neighbors = all_neighbors - out_neighbors
            ...     for in_neighbor in in_neighbors:
            ...         c_graph.remove_edge(in_neighbor, c_node)
            ...         for out_neighbor in out_neighbors:
            ...             c_graph.add_edge(in_neighbor, out_neighbor)
            ...     c_graph.remove_node(c_node)
            ...
            >>> nx.is_isomorphic(original_graph, c_graph)
            True

        References
        ----------
        .. [1] Maccioni, A., & Abadi, D. J. (2016, August).
           Scalable pattern matching over compressed graphs via dedensification.
           In Proceedings of the 22nd ACM SIGKDD International Conference on
           Knowledge Discovery and Data Mining (pp. 1755-1764).
           http://www.cs.umd.edu/~abadi/papers/graph-dedense.pdf

    snap_aggregation(G, node_attributes, edge_attributes=(), prefix='Supernode-', supernode_attribute='group', superedge_attribute='types', *, backend=None, **backend_kwargs)
        Creates a summary graph based on attributes and connectivity.

        This function uses the Summarization by Grouping Nodes on Attributes
        and Pairwise edges (SNAP) algorithm for summarizing a given
        graph by grouping nodes by node attributes and their edge attributes
        into supernodes in a summary graph.  This name SNAP should not be
        confused with the Stanford Network Analysis Project (SNAP).

        Here is a high-level view of how this algorithm works:

        1) Group nodes by node attribute values.

        2) Iteratively split groups until all nodes in each group have edges
        to nodes in the same groups. That is, until all the groups are homogeneous
        in their member nodes' edges to other groups.  For example,
        if all the nodes in group A only have edge to nodes in group B, then the
        group is homogeneous and does not need to be split. If all nodes in group B
        have edges with nodes in groups {A, C}, but some also have edges with other
        nodes in B, then group B is not homogeneous and needs to be split into
        groups have edges with {A, C} and a group of nodes having
        edges with {A, B, C}.  This way, viewers of the summary graph can
        assume that all nodes in the group have the exact same node attributes and
        the exact same edges.

        3) Build the output summary graph, where the groups are represented by
        super-nodes. Edges represent the edges shared between all the nodes in each
        respective groups.

        A SNAP summary graph can be used to visualize graphs that are too large to display
        or visually analyze, or to efficiently identify sets of similar nodes with similar connectivity
        patterns to other sets of similar nodes based on specified node and/or edge attributes in a graph.

        Parameters
        ----------
        G: graph
            Networkx Graph to be summarized
        node_attributes: iterable, required
            An iterable of the node attributes used to group nodes in the summarization process. Nodes
            with the same values for these attributes will be grouped together in the summary graph.
        edge_attributes: iterable, optional
            An iterable of the edge attributes considered in the summarization process.  If provided, unique
            combinations of the attribute values found in the graph are used to
            determine the edge types in the graph.  If not provided, all edges
            are considered to be of the same type.
        prefix: str
            The prefix used to denote supernodes in the summary graph. Defaults to 'Supernode-'.
        supernode_attribute: str
            The node attribute for recording the supernode groupings of nodes. Defaults to 'group'.
        superedge_attribute: str
            The edge attribute for recording the edge types of multiple edges. Defaults to 'types'.

        Returns
        -------
        networkx.Graph: summary graph

        Examples
        --------
        SNAP aggregation takes a graph and summarizes it in the context of user-provided
        node and edge attributes such that a viewer can more easily extract and
        analyze the information represented by the graph

        >>> nodes = {
        ...     "A": dict(color="Red"),
        ...     "B": dict(color="Red"),
        ...     "C": dict(color="Red"),
        ...     "D": dict(color="Red"),
        ...     "E": dict(color="Blue"),
        ...     "F": dict(color="Blue"),
        ... }
        >>> edges = [
        ...     ("A", "E", "Strong"),
        ...     ("B", "F", "Strong"),
        ...     ("C", "E", "Weak"),
        ...     ("D", "F", "Weak"),
        ... ]
        >>> G = nx.Graph()
        >>> for node in nodes:
        ...     attributes = nodes[node]
        ...     G.add_node(node, **attributes)
        >>> for source, target, type in edges:
        ...     G.add_edge(source, target, type=type)
        >>> node_attributes = ("color",)
        >>> edge_attributes = ("type",)
        >>> summary_graph = nx.snap_aggregation(
        ...     G, node_attributes=node_attributes, edge_attributes=edge_attributes
        ... )

        Notes
        -----
        The summary graph produced is called a maximum Attribute-edge
        compatible (AR-compatible) grouping.  According to [1]_, an
        AR-compatible grouping means that all nodes in each group have the same
        exact node attribute values and the same exact edges and
        edge types to one or more nodes in the same groups.  The maximal
        AR-compatible grouping is the grouping with the minimal cardinality.

        The AR-compatible grouping is the most detailed grouping provided by
        any of the SNAP algorithms.

        References
        ----------
        .. [1] Y. Tian, R. A. Hankins, and J. M. Patel. Efficient aggregation
           for graph summarization. In Proc. 2008 ACM-SIGMOD Int. Conf.
           Management of Data (SIGMOD’08), pages 567–580, Vancouver, Canada,
           June 2008.

DATA
    __all__ = ['dedensify', 'snap_aggregation']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\summarization.py

networkx.swap
Python Library Documentation: module networkx.algorithms.swap in networkx.algorithms

NAME
    networkx.algorithms.swap - Swap edges in a graph.

FUNCTIONS
    connected_double_edge_swap(G, nswap=1, _window_threshold=3, seed=None, *, backend=None, **backend_kwargs)
        Attempts the specified number of double-edge swaps in the graph `G`.

        A double-edge swap removes two randomly chosen edges `(u, v)` and `(x,
        y)` and creates the new edges `(u, x)` and `(v, y)`::

         u--v            u  v
                becomes  |  |
         x--y            x  y

        If either `(u, x)` or `(v, y)` already exist, then no swap is performed
        so the actual number of swapped edges is always *at most* `nswap`.

        Parameters
        ----------
        G : graph
           An undirected graph

        nswap : integer (optional, default=1)
           Number of double-edge swaps to perform

        _window_threshold : integer

           The window size below which connectedness of the graph will be checked
           after each swap.

           The "window" in this function is a dynamically updated integer that
           represents the number of swap attempts to make before checking if the
           graph remains connected. It is an optimization used to decrease the
           running time of the algorithm in exchange for increased complexity of
           implementation.

           If the window size is below this threshold, then the algorithm checks
           after each swap if the graph remains connected by checking if there is a
           path joining the two nodes whose edge was just removed. If the window
           size is above this threshold, then the algorithm performs do all the
           swaps in the window and only then check if the graph is still connected.

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        int
           The number of successful swaps

        Raises
        ------

        NetworkXError

           If the input graph is not connected, or if the graph has fewer than four
           nodes.

        Notes
        -----

        The initial graph `G` must be connected, and the resulting graph is
        connected. The graph `G` is modified in place.

        References
        ----------
        .. [1] C. Gkantsidis and M. Mihail and E. Zegura,
               The Markov chain simulation method for generating connected
               power law random graphs, 2003.
               http://citeseer.ist.psu.edu/gkantsidis03markov.html

    directed_edge_swap(G, *, nswap=1, max_tries=100, seed=None, backend=None, **backend_kwargs)
        Swap three edges in a directed graph while keeping the node degrees fixed.

        A directed edge swap swaps three edges such that a -> b -> c -> d becomes
        a -> c -> b -> d. This pattern of swapping allows all possible states with the
        same in- and out-degree distribution in a directed graph to be reached.

        If the swap would create parallel edges (e.g. if a -> c already existed in the
        previous example), another attempt is made to find a suitable trio of edges.

        Parameters
        ----------
        G : DiGraph
           A directed graph

        nswap : integer (optional, default=1)
           Number of three-edge (directed) swaps to perform

        max_tries : integer (optional, default=100)
           Maximum number of attempts to swap edges

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        G : DiGraph
           The graph after the edges are swapped.

        Raises
        ------
        NetworkXError
            If `G` is not directed, or
            If nswap > max_tries, or
            If there are fewer than 4 nodes or 3 edges in `G`.
        NetworkXAlgorithmError
            If the number of swap attempts exceeds `max_tries` before `nswap` swaps are made

        Notes
        -----
        Does not enforce any connectivity constraints.

        The graph G is modified in place.

        A later swap is allowed to undo a previous swap.

        References
        ----------
        .. [1] Erdős, Péter L., et al. “A Simple Havel-Hakimi Type Algorithm to Realize
               Graphical Degree Sequences of Directed Graphs.” ArXiv:0905.4913 [Math],
               Jan. 2010. https://doi.org/10.48550/arXiv.0905.4913.
               Published  2010 in Elec. J. Combinatorics (17(1)). R66.
               http://www.combinatorics.org/Volume_17/PDF/v17i1r66.pdf
        .. [2] “Combinatorics - Reaching All Possible Simple Directed Graphs with a given
               Degree Sequence with 2-Edge Swaps.” Mathematics Stack Exchange,
               https://math.stackexchange.com/questions/22272/. Accessed 30 May 2022.

    double_edge_swap(G, nswap=1, max_tries=100, seed=None, *, backend=None, **backend_kwargs)
        Swap two edges in the graph while keeping the node degrees fixed.

        A double-edge swap removes two randomly chosen edges u-v and x-y
        and creates the new edges u-x and v-y::

         u--v            u  v
                becomes  |  |
         x--y            x  y

        If either the edge u-x or v-y already exist no swap is performed
        and another attempt is made to find a suitable edge pair.

        Parameters
        ----------
        G : graph
           An undirected graph

        nswap : integer (optional, default=1)
           Number of double-edge swaps to perform

        max_tries : integer (optional)
           Maximum number of attempts to swap edges

        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        G : graph
           The graph after double edge swaps.

        Raises
        ------
        NetworkXError
            If `G` is directed, or
            If `nswap` > `max_tries`, or
            If there are fewer than 4 nodes or 2 edges in `G`.
        NetworkXAlgorithmError
            If the number of swap attempts exceeds `max_tries` before `nswap` swaps are made

        Notes
        -----
        Does not enforce any connectivity constraints.

        The graph G is modified in place.

DATA
    __all__ = ['double_edge_swap', 'connected_double_edge_swap', 'directed...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\swap.py

networkx.symmetric_difference
Python Library Documentation: function symmetric_difference in module networkx.algorithms.operators.binary

symmetric_difference(G, H, *, backend=None, **backend_kwargs)
    Returns new graph with edges that exist in either G or H but not both.

    The node sets of H and G must be the same.

    Parameters
    ----------
    G,H : graph
       A NetworkX graph.  G and H must have the same node sets.

    Returns
    -------
    D : A new graph with the same type as G.

    Notes
    -----
    Attributes from the graph, nodes, and edges are not copied to the new
    graph.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (1, 2), (1, 3)])
    >>> H = nx.Graph([(0, 1), (1, 2), (0, 3)])
    >>> R = nx.symmetric_difference(G, H)
    >>> R.nodes
    NodeView((0, 1, 2, 3))
    >>> R.edges
    EdgeView([(0, 2), (0, 3), (1, 3)])
networkx.tadpole_graph
Python Library Documentation: function tadpole_graph in module networkx.generators.classic

tadpole_graph(m, n, create_using=None, *, backend=None, **backend_kwargs)
    Returns the (m,n)-tadpole graph; ``C_m`` connected to ``P_n``.

    This graph on m+n nodes connects a cycle of size `m` to a path of length `n`.
    It looks like a tadpole. It is also called a kite graph or a dragon graph.

    .. plot::

        >>> nx.draw(nx.tadpole_graph(3, 5))

    Parameters
    ----------
    m, n : int or iterable container of nodes
        If an integer, nodes are from ``range(m)`` and ``range(m,m+n)``.
        If a container of nodes, those nodes appear in the graph.
        Warning: `m` and `n` are not checked for duplicates and if present the
        resulting graph may not be as desired.

        The nodes for `m` appear in the cycle graph $C_m$ and the nodes
        for `n` appear in the path $P_n$.
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    Networkx graph
       A cycle of size `m` connected to a path of length `n`.

    Raises
    ------
    NetworkXError
        If ``m < 2``. The tadpole graph is undefined for ``m<2``.

    Notes
    -----
    The 2 subgraphs are joined via an edge ``(m-1, m)``.
    If ``n=0``, this is a cycle graph.
    `m` and/or `n` can be a container of nodes instead of an integer.
networkx.tensor_product
Python Library Documentation: function tensor_product in module networkx.algorithms.operators.product

tensor_product(G, H, *, backend=None, **backend_kwargs)
    Returns the tensor product of G and H.

    The tensor product $P$ of the graphs $G$ and $H$ has a node set that
    is the Cartesian product of the node sets, $V(P)=V(G) \times V(H)$.
    $P$ has an edge $((u,v), (x,y))$ if and only if $(u,x)$ is an edge in $G$
    and $(v,y)$ is an edge in $H$.

    Tensor product is sometimes also referred to as the categorical product,
    direct product, cardinal product or conjunction.


    Parameters
    ----------
    G, H: graphs
     Networkx graphs.

    Returns
    -------
    P: NetworkX graph
     The tensor product of G and H. P will be a multi-graph if either G
     or H is a multi-graph, will be a directed if G and H are directed,
     and undirected if G and H are undirected.

    Raises
    ------
    NetworkXError
     If G and H are not both directed or both undirected.

    Notes
    -----
    Node attributes in P are two-tuple of the G and H node attributes.
    Missing attributes are assigned None.

    Examples
    --------
    >>> G = nx.Graph()
    >>> H = nx.Graph()
    >>> G.add_node(0, a1=True)
    >>> H.add_node("a", a2="Spam")
    >>> P = nx.tensor_product(G, H)
    >>> list(P)
    [(0, 'a')]

    Edge attributes and edge keys (for multigraphs) are also copied to the
    new product graph
networkx.tetrahedral_graph
Python Library Documentation: function tetrahedral_graph in module networkx.generators.small

tetrahedral_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the 3-regular Platonic Tetrahedral graph.

    Tetrahedral graph has 4 nodes and 6 edges. It is a
    special case of the complete graph, K4, and wheel graph, W4.
    It is one of the 5 platonic graphs [1]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Tetrahedral Graph

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Tetrahedron#Tetrahedral_graph
networkx.text
Python Library Documentation: module networkx.readwrite.text in networkx.readwrite

NAME
    networkx.readwrite.text - Text-based visual representations of graphs

FUNCTIONS
    generate_network_text(graph, with_labels=True, sources=None, max_depth=None, ascii_only=False, vertical_chains=False)
        Generate lines in the "network text" format

        This works via a depth-first traversal of the graph and writing a line for
        each unique node encountered. Non-tree edges are written to the right of
        each node, and connection to a non-tree edge is indicated with an ellipsis.
        This representation works best when the input graph is a forest, but any
        graph can be represented.

        This notation is original to networkx, although it is simple enough that it
        may be known in existing literature. See #5602 for details. The procedure
        is summarized as follows:

        1. Given a set of source nodes (which can be specified, or automatically
        discovered via finding the (strongly) connected components and choosing one
        node with minimum degree from each), we traverse the graph in depth first
        order.

        2. Each reachable node will be printed exactly once on it's own line.

        3. Edges are indicated in one of four ways:

            a. a parent "L-style" connection on the upper left. This corresponds to
            a traversal in the directed DFS tree.

            b. a backref "<-style" connection shown directly on the right. For
            directed graphs, these are drawn for any incoming edges to a node that
            is not a parent edge. For undirected graphs, these are drawn for only
            the non-parent edges that have already been represented (The edges that
            have not been represented will be handled in the recursive case).

            c. a child "L-style" connection on the lower right. Drawing of the
            children are handled recursively.

            d. if ``vertical_chains`` is true, and a parent node only has one child
            a "vertical-style" edge is drawn between them.

        4. The children of each node (wrt the directed DFS tree) are drawn
        underneath and to the right of it. In the case that a child node has already
        been drawn the connection is replaced with an ellipsis ("...") to indicate
        that there is one or more connections represented elsewhere.

        5. If a maximum depth is specified, an edge to nodes past this maximum
        depth will be represented by an ellipsis.

        6. If a node has a truthy "collapse" value, then we do not traverse past
        that node.

        Parameters
        ----------
        graph : nx.DiGraph | nx.Graph
            Graph to represent

        with_labels : bool | str
            If True will use the "label" attribute of a node to display if it
            exists otherwise it will use the node value itself. If given as a
            string, then that attribute name will be used instead of "label".
            Defaults to True.

        sources : List
            Specifies which nodes to start traversal from. Note: nodes that are not
            reachable from one of these sources may not be shown. If unspecified,
            the minimal set of nodes needed to reach all others will be used.

        max_depth : int | None
            The maximum depth to traverse before stopping. Defaults to None.

        ascii_only : Boolean
            If True only ASCII characters are used to construct the visualization

        vertical_chains : Boolean
            If True, chains of nodes will be drawn vertically when possible.

        Yields
        ------
        str : a line of generated text

        Examples
        --------
        >>> graph = nx.path_graph(10)
        >>> graph.add_node("A")
        >>> graph.add_node("B")
        >>> graph.add_node("C")
        >>> graph.add_node("D")
        >>> graph.add_edge(9, "A")
        >>> graph.add_edge(9, "B")
        >>> graph.add_edge(9, "C")
        >>> graph.add_edge("C", "D")
        >>> graph.add_edge("C", "E")
        >>> graph.add_edge("C", "F")
        >>> nx.write_network_text(graph)
        ╙── 0
            └── 1
                └── 2
                    └── 3
                        └── 4
                            └── 5
                                └── 6
                                    └── 7
                                        └── 8
                                            └── 9
                                                ├── A
                                                ├── B
                                                └── C
                                                    ├── D
                                                    ├── E
                                                    └── F
        >>> nx.write_network_text(graph, vertical_chains=True)
        ╙── 0
            │
            1
            │
            2
            │
            3
            │
            4
            │
            5
            │
            6
            │
            7
            │
            8
            │
            9
            ├── A
            ├── B
            └── C
                ├── D
                ├── E
                └── F

    write_network_text(graph, path=None, with_labels=True, sources=None, max_depth=None, ascii_only=False, end='\n', vertical_chains=False)
        Creates a nice text representation of a graph

        This works via a depth-first traversal of the graph and writing a line for
        each unique node encountered. Non-tree edges are written to the right of
        each node, and connection to a non-tree edge is indicated with an ellipsis.
        This representation works best when the input graph is a forest, but any
        graph can be represented.

        Parameters
        ----------
        graph : nx.DiGraph | nx.Graph
            Graph to represent

        path : string or file or callable or None
           Filename or file handle for data output.
           if a function, then it will be called for each generated line.
           if None, this will default to "sys.stdout.write"

        with_labels : bool | str
            If True will use the "label" attribute of a node to display if it
            exists otherwise it will use the node value itself. If given as a
            string, then that attribute name will be used instead of "label".
            Defaults to True.

        sources : List
            Specifies which nodes to start traversal from. Note: nodes that are not
            reachable from one of these sources may not be shown. If unspecified,
            the minimal set of nodes needed to reach all others will be used.

        max_depth : int | None
            The maximum depth to traverse before stopping. Defaults to None.

        ascii_only : Boolean
            If True only ASCII characters are used to construct the visualization

        end : string
            The line ending character

        vertical_chains : Boolean
            If True, chains of nodes will be drawn vertically when possible.

        Examples
        --------
        >>> graph = nx.balanced_tree(r=2, h=2, create_using=nx.DiGraph)
        >>> nx.write_network_text(graph)
        ╙── 0
            ├─╼ 1
            │   ├─╼ 3
            │   └─╼ 4
            └─╼ 2
                ├─╼ 5
                └─╼ 6

        >>> # A near tree with one non-tree edge
        >>> graph.add_edge(5, 1)
        >>> nx.write_network_text(graph)
        ╙── 0
            ├─╼ 1 ╾ 5
            │   ├─╼ 3
            │   └─╼ 4
            └─╼ 2
                ├─╼ 5
                │   └─╼  ...
                └─╼ 6

        >>> graph = nx.cycle_graph(5)
        >>> nx.write_network_text(graph)
        ╙── 0
            ├── 1
            │   └── 2
            │       └── 3
            │           └── 4 ─ 0
            └──  ...

        >>> graph = nx.cycle_graph(5, nx.DiGraph)
        >>> nx.write_network_text(graph, vertical_chains=True)
        ╙── 0 ╾ 4
            ╽
            1
            ╽
            2
            ╽
            3
            ╽
            4
            └─╼  ...

        >>> nx.write_network_text(graph, vertical_chains=True, ascii_only=True)
        +-- 0 <- 4
            !
            1
            !
            2
            !
            3
            !
            4
            L->  ...

        >>> graph = nx.generators.barbell_graph(4, 2)
        >>> nx.write_network_text(graph, vertical_chains=False)
        ╙── 4
            ├── 5
            │   └── 6
            │       ├── 7
            │       │   ├── 8 ─ 6
            │       │   │   └── 9 ─ 6, 7
            │       │   └──  ...
            │       └──  ...
            └── 3
                ├── 0
                │   ├── 1 ─ 3
                │   │   └── 2 ─ 0, 3
                │   └──  ...
                └──  ...
        >>> nx.write_network_text(graph, vertical_chains=True)
        ╙── 4
            ├── 5
            │   │
            │   6
            │   ├── 7
            │   │   ├── 8 ─ 6
            │   │   │   │
            │   │   │   9 ─ 6, 7
            │   │   └──  ...
            │   └──  ...
            └── 3
                ├── 0
                │   ├── 1 ─ 3
                │   │   │
                │   │   2 ─ 0, 3
                │   └──  ...
                └──  ...

        >>> graph = nx.complete_graph(5, create_using=nx.Graph)
        >>> nx.write_network_text(graph)
        ╙── 0
            ├── 1
            │   ├── 2 ─ 0
            │   │   ├── 3 ─ 0, 1
            │   │   │   └── 4 ─ 0, 1, 2
            │   │   └──  ...
            │   └──  ...
            └──  ...

        >>> graph = nx.complete_graph(3, create_using=nx.DiGraph)
        >>> nx.write_network_text(graph)
        ╙── 0 ╾ 1, 2
            ├─╼ 1 ╾ 2
            │   ├─╼ 2 ╾ 0
            │   │   └─╼  ...
            │   └─╼  ...
            └─╼  ...

DATA
    __all__ = ['generate_network_text', 'write_network_text']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\readwrite\text.py

networkx.thresholded_random_geometric_graph
Python Library Documentation: function thresholded_random_geometric_graph in module networkx.generators.geometric

thresholded_random_geometric_graph(n, radius, theta, dim=2, pos=None, weight=None, p=2, seed=None, *, pos_name='pos', weight_name='weight', backend=None, **backend_kwargs)
    Returns a thresholded random geometric graph in the unit cube.

    The thresholded random geometric graph [1] model places `n` nodes
    uniformly at random in the unit cube of dimensions `dim`. Each node
    `u` is assigned a weight :math:`w_u`. Two nodes `u` and `v` are
    joined by an edge if they are within the maximum connection distance,
    `radius` computed by the `p`-Minkowski distance and the summation of
    weights :math:`w_u` + :math:`w_v` is greater than or equal
    to the threshold parameter `theta`.

    Edges within `radius` of each other are determined using a KDTree when
    SciPy is available. This reduces the time complexity from :math:`O(n^2)`
    to :math:`O(n)`.

    Parameters
    ----------
    n : int or iterable
        Number of nodes or iterable of nodes
    radius: float
        Distance threshold value
    theta: float
        Threshold value
    dim : int, optional
        Dimension of graph
    pos : dict, optional
        A dictionary keyed by node with node positions as values.
    weight : dict, optional
        Node weights as a dictionary of numbers keyed by node.
    p : float, optional (default 2)
        Which Minkowski distance metric to use.  `p` has to meet the condition
        ``1 <= p <= infinity``.

        If this argument is not specified, the :math:`L^2` metric
        (the Euclidean distance metric), p = 2 is used.

        This should not be confused with the `p` of an Erdős-Rényi random
        graph, which represents probability.
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    pos_name : string, default="pos"
        The name of the node attribute which represents the position
        in 2D coordinates of the node in the returned graph.
    weight_name : string, default="weight"
        The name of the node attribute which represents the weight
        of the node in the returned graph.

    Returns
    -------
    Graph
        A thresholded random geographic graph, undirected and without
        self-loops.

        Each node has a node attribute ``'pos'`` that stores the
        position of that node in Euclidean space as provided by the
        ``pos`` keyword argument or, if ``pos`` was not provided, as
        generated by this function. Similarly, each node has a nodethre
        attribute ``'weight'`` that stores the weight of that node as
        provided or as generated.

    Examples
    --------
    Default Graph:

    G = nx.thresholded_random_geometric_graph(50, 0.2, 0.1)

    Custom Graph:

    Create a thresholded random geometric graph on 50 uniformly distributed
    nodes where nodes are joined by an edge if their sum weights drawn from
    a exponential distribution with rate = 5 are >= theta = 0.1 and their
    Euclidean distance is at most 0.2.

    Notes
    -----
    This uses a *k*-d tree to build the graph.

    The `pos` keyword argument can be used to specify node positions so you
    can create an arbitrary distribution and domain for positions.

    For example, to use a 2D Gaussian distribution of node positions with mean
    (0, 0) and standard deviation 2

    If weights are not specified they are assigned to nodes by drawing randomly
    from the exponential distribution with rate parameter :math:`\lambda=1`.
    To specify weights from a different distribution, use the `weight` keyword
    argument::

    ::

    >>> import random
    >>> import math
    >>> n = 50
    >>> pos = {i: (random.gauss(0, 2), random.gauss(0, 2)) for i in range(n)}
    >>> w = {i: random.expovariate(5.0) for i in range(n)}
    >>> G = nx.thresholded_random_geometric_graph(n, 0.2, 0.1, 2, pos, w)

    References
    ----------
    .. [1] http://cole-maclean.github.io/blog/files/thesis.pdf
networkx.time_dependent
Python Library Documentation: module networkx.algorithms.time_dependent in networkx.algorithms

NAME
    networkx.algorithms.time_dependent - Time dependent algorithms.

FUNCTIONS
    cd_index(G, node, time_delta, *, time='time', weight=None, backend=None, **backend_kwargs)
        Compute the CD index for `node` within the graph `G`.

        Calculates the CD index for the given node of the graph,
        considering only its predecessors who have the `time` attribute
        smaller than or equal to the `time` attribute of the `node`
        plus `time_delta`.

        Parameters
        ----------
        G : graph
           A directed networkx graph whose nodes have `time` attributes and optionally
           `weight` attributes (if a weight is not given, it is considered 1).
        node : node
           The node for which the CD index is calculated.
        time_delta : numeric or timedelta
           Amount of time after the `time` attribute of the `node`. The value of
           `time_delta` must support comparison with the `time` node attribute. For
           example, if the `time` attribute of the nodes are `datetime.datetime`
           objects, then `time_delta` should be a `datetime.timedelta` object.
        time : string (Optional, default is "time")
            The name of the node attribute that will be used for the calculations.
        weight : string (Optional, default is None)
            The name of the node attribute used as weight.

        Returns
        -------
        float
           The CD index calculated for the node `node` within the graph `G`.

        Raises
        ------
        NetworkXError
           If not all nodes have a `time` attribute or
           `time_delta` and `time` attribute types are not compatible or
           `n` equals 0.

        NetworkXNotImplemented
            If `G` is a non-directed graph or a multigraph.

        Examples
        --------
        >>> from datetime import datetime, timedelta
        >>> G = nx.DiGraph()
        >>> nodes = {
        ...     1: {"time": datetime(2015, 1, 1)},
        ...     2: {"time": datetime(2012, 1, 1), "weight": 4},
        ...     3: {"time": datetime(2010, 1, 1)},
        ...     4: {"time": datetime(2008, 1, 1)},
        ...     5: {"time": datetime(2014, 1, 1)},
        ... }
        >>> G.add_nodes_from([(n, nodes[n]) for n in nodes])
        >>> edges = [(1, 3), (1, 4), (2, 3), (3, 4), (3, 5)]
        >>> G.add_edges_from(edges)
        >>> delta = timedelta(days=5 * 365)
        >>> nx.cd_index(G, 3, time_delta=delta, time="time")
        0.5
        >>> nx.cd_index(G, 3, time_delta=delta, time="time", weight="weight")
        0.12

        Integers can also be used for the time values:
        >>> node_times = {1: 2015, 2: 2012, 3: 2010, 4: 2008, 5: 2014}
        >>> nx.set_node_attributes(G, node_times, "new_time")
        >>> nx.cd_index(G, 3, time_delta=4, time="new_time")
        0.5
        >>> nx.cd_index(G, 3, time_delta=4, time="new_time", weight="weight")
        0.12

        Notes
        -----
        This method implements the algorithm for calculating the CD index,
        as described in the paper by Funk and Owen-Smith [1]_. The CD index
        is used in order to check how consolidating or destabilizing a patent
        is, hence the nodes of the graph represent patents and the edges show
        the citations between these patents. The mathematical model is given
        below:

        .. math::
            CD_{t}=\frac{1}{n_{t}}\sum_{i=1}^{n}\frac{-2f_{it}b_{it}+f_{it}}{w_{it}},

        where `f_{it}` equals 1 if `i` cites the focal patent else 0, `b_{it}` equals
        1 if `i` cites any of the focal patents successors else 0, `n_{t}` is the number
        of forward citations in `i` and `w_{it}` is a matrix of weight for patent `i`
        at time `t`.

        The `datetime.timedelta` package can lead to off-by-one issues when converting
        from years to days. In the example above `timedelta(days=5 * 365)` looks like
        5 years, but it isn't because of leap year days. So it gives the same result
        as `timedelta(days=4 * 365)`. But using `timedelta(days=5 * 365 + 1)` gives
        a 5 year delta **for this choice of years** but may not if the 5 year gap has
        more than 1 leap year. To avoid these issues, use integers to represent years,
        or be very careful when you convert units of time.

        References
        ----------
        .. [1] Funk, Russell J., and Jason Owen-Smith.
               "A dynamic network measure of technological change."
               Management science 63, no. 3 (2017): 791-817.
               http://russellfunk.org/cdindex/static/papers/funk_ms_2017.pdf

DATA
    __all__ = ['cd_index']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\time_dependent.py

networkx.time_series
Python Library Documentation: module networkx.generators.time_series in networkx.generators

NAME
    networkx.generators.time_series - Time Series Graphs

FUNCTIONS
    visibility_graph(series, *, backend=None, **backend_kwargs)
        Return a Visibility Graph of an input Time Series.

        A visibility graph converts a time series into a graph. The constructed graph
        uses integer nodes to indicate which event in the series the node represents.
        Edges are formed as follows: consider a bar plot of the series and view that
        as a side view of a landscape with a node at the top of each bar. An edge
        means that the nodes can be connected by a straight "line-of-sight" without
        being obscured by any bars between the nodes.

        The resulting graph inherits several properties of the series in its structure.
        Thereby, periodic series convert into regular graphs, random series convert
        into random graphs, and fractal series convert into scale-free networks [1]_.

        Parameters
        ----------
        series : Sequence[Number]
           A Time Series sequence (iterable and sliceable) of numeric values
           representing times.

        Returns
        -------
        NetworkX Graph
            The Visibility Graph of the input series

        Examples
        --------
        >>> series_list = [range(10), [2, 1, 3, 2, 1, 3, 2, 1, 3, 2, 1, 3]]
        >>> for s in series_list:
        ...     g = nx.visibility_graph(s)
        ...     print(g)
        Graph with 10 nodes and 9 edges
        Graph with 12 nodes and 18 edges

        References
        ----------
        .. [1] Lacasa, Lucas, Bartolo Luque, Fernando Ballesteros, Jordi Luque, and Juan Carlos Nuno.
               "From time series to complex networks: The visibility graph." Proceedings of the
               National Academy of Sciences 105, no. 13 (2008): 4972-4975.
               https://www.pnas.org/doi/10.1073/pnas.0709247105

DATA
    __all__ = ['visibility_graph']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\time_series.py

networkx.to_dict_of_dicts
Python Library Documentation: function to_dict_of_dicts in module networkx.convert

to_dict_of_dicts(G, nodelist=None, edge_data=None)
    Returns adjacency representation of graph as a dictionary of dictionaries.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    nodelist : list
       Use only nodes specified in nodelist

    edge_data : scalar, optional
       If provided, the value of the dictionary will be set to `edge_data` for
       all edges. Usual values could be `1` or `True`. If `edge_data` is
       `None` (the default), the edgedata in `G` is used, resulting in a
       dict-of-dict-of-dicts. If `G` is a MultiGraph, the result will be a
       dict-of-dict-of-dict-of-dicts. See Notes for an approach to customize
       handling edge data. `edge_data` should *not* be a container.

    Returns
    -------
    dod : dict
       A nested dictionary representation of `G`. Note that the level of
       nesting depends on the type of `G` and the value of `edge_data`
       (see Examples).

    See Also
    --------
    from_dict_of_dicts, to_dict_of_lists

    Notes
    -----
    For a more custom approach to handling edge data, try::

        dod = {
            n: {nbr: custom(n, nbr, dd) for nbr, dd in nbrdict.items()}
            for n, nbrdict in G.adj.items()
        }

    where `custom` returns the desired edge data for each edge between `n` and
    `nbr`, given existing edge data `dd`.

    Examples
    --------
    >>> G = nx.path_graph(3)
    >>> nx.to_dict_of_dicts(G)
    {0: {1: {}}, 1: {0: {}, 2: {}}, 2: {1: {}}}

    Edge data is preserved by default (``edge_data=None``), resulting
    in dict-of-dict-of-dicts where the innermost dictionary contains the
    edge data:

    >>> G = nx.Graph()
    >>> G.add_edges_from(
    ...     [
    ...         (0, 1, {"weight": 1.0}),
    ...         (1, 2, {"weight": 2.0}),
    ...         (2, 0, {"weight": 1.0}),
    ...     ]
    ... )
    >>> d = nx.to_dict_of_dicts(G)
    >>> d  # doctest: +SKIP
    {0: {1: {'weight': 1.0}, 2: {'weight': 1.0}},
     1: {0: {'weight': 1.0}, 2: {'weight': 2.0}},
     2: {1: {'weight': 2.0}, 0: {'weight': 1.0}}}
    >>> d[1][2]["weight"]
    2.0

    If `edge_data` is not `None`, edge data in the original graph (if any) is
    replaced:

    >>> d = nx.to_dict_of_dicts(G, edge_data=1)
    >>> d
    {0: {1: 1, 2: 1}, 1: {0: 1, 2: 1}, 2: {1: 1, 0: 1}}
    >>> d[1][2]
    1

    This also applies to MultiGraphs: edge data is preserved by default:

    >>> G = nx.MultiGraph()
    >>> G.add_edge(0, 1, key="a", weight=1.0)
    'a'
    >>> G.add_edge(0, 1, key="b", weight=5.0)
    'b'
    >>> d = nx.to_dict_of_dicts(G)
    >>> d  # doctest: +SKIP
    {0: {1: {'a': {'weight': 1.0}, 'b': {'weight': 5.0}}},
     1: {0: {'a': {'weight': 1.0}, 'b': {'weight': 5.0}}}}
    >>> d[0][1]["b"]["weight"]
    5.0

    But multi edge data is lost if `edge_data` is not `None`:

    >>> d = nx.to_dict_of_dicts(G, edge_data=10)
    >>> d
    {0: {1: 10}, 1: {0: 10}}
networkx.to_dict_of_lists
Python Library Documentation: function to_dict_of_lists in module networkx.convert

to_dict_of_lists(G, nodelist=None, *, backend=None, **backend_kwargs)
    Returns adjacency representation of graph as a dictionary of lists.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    nodelist : list
       Use only nodes specified in nodelist

    Notes
    -----
    Completely ignores edge data for MultiGraph and MultiDiGraph.
networkx.to_directed
Python Library Documentation: function to_directed in module networkx.classes.function

to_directed(graph)
    Returns a directed view of the graph `graph`.

    Identical to graph.to_directed(as_view=True)
    Note that graph.to_directed defaults to `as_view=False`
    while this function always provides a view.
networkx.to_edgelist
Python Library Documentation: function to_edgelist in module networkx.convert

to_edgelist(G, nodelist=None, *, backend=None, **backend_kwargs)
    Returns a list of edges in the graph.

    Parameters
    ----------
    G : graph
       A NetworkX graph

    nodelist : list
       Use only nodes specified in nodelist
networkx.to_graph6_bytes
Python Library Documentation: function to_graph6_bytes in module networkx.readwrite.graph6

to_graph6_bytes(G, nodes=None, header=True)
    Convert a simple undirected graph to bytes in graph6 format.

    Parameters
    ----------
    G : Graph (undirected)

    nodes: list or iterable
       Nodes are labeled 0...n-1 in the order provided.  If None the ordering
       given by ``G.nodes()`` is used.

    header: bool
       If True add '>>graph6<<' bytes to head of data.

    Raises
    ------
    NetworkXNotImplemented
        If the graph is directed or is a multigraph.

    ValueError
        If the graph has at least ``2 ** 36`` nodes; the graph6 format
        is only defined for graphs of order less than ``2 ** 36``.

    Examples
    --------
    >>> nx.to_graph6_bytes(nx.path_graph(2))
    b'>>graph6<<A_\n'

    See Also
    --------
    from_graph6_bytes, read_graph6, write_graph6_bytes

    Notes
    -----
    The returned bytes end with a newline character.

    The format does not support edge or node labels, parallel edges or
    self loops. If self loops are present they are silently ignored.

    References
    ----------
    .. [1] Graph6 specification
           <http://users.cecs.anu.edu.au/~bdm/data/formats.html>
networkx.to_latex
Python Library Documentation: function to_latex in module networkx.drawing.nx_latex

to_latex(Gbunch, pos='pos', tikz_options='', default_node_options='', node_options='node_options', node_label='node_label', default_edge_options='', edge_options='edge_options', edge_label='edge_label', edge_label_options='edge_label_options', caption='', latex_label='', sub_captions=None, sub_labels=None, n_rows=1, as_document=True, document_wrapper='\\documentclass{{report}}\n\\usepackage{{tikz}}\n\\usepackage{{subcaption}}\n\n\\begin{{document}}\n{content}\n\\end{{document}}', figure_wrapper='\\begin{{figure}}\n{content}{caption}{label}\n\\end{{figure}}', subfigure_wrapper='  \\begin{{subfigure}}{{{size}\\textwidth}}\n{content}{caption}{label}\n  \\end{{subfigure}}')
    Return latex code to draw the graph(s) in `Gbunch`

    The TikZ drawing utility in LaTeX is used to draw the graph(s).
    If `Gbunch` is a graph, it is drawn in a figure environment.
    If `Gbunch` is an iterable of graphs, each is drawn in a subfigure environment
    within a single figure environment.

    If `as_document` is True, the figure is wrapped inside a document environment
    so that the resulting string is ready to be compiled by LaTeX. Otherwise,
    the string is ready for inclusion in a larger tex document using ``\include``
    or ``\input`` statements.

    Parameters
    ==========
    Gbunch : NetworkX graph or iterable of NetworkX graphs
        The NetworkX graph to be drawn or an iterable of graphs
        to be drawn inside subfigures of a single figure.
    pos : string or list of strings
        The name of the node attribute on `G` that holds the position of each node.
        Positions can be sequences of length 2 with numbers for (x,y) coordinates.
        They can also be strings to denote positions in TikZ style, such as (x, y)
        or (angle:radius).
        If a dict, it should be keyed by node to a position.
        If an empty dict, a circular layout is computed by TikZ.
        If you are drawing many graphs in subfigures, use a list of position dicts.
    tikz_options : string
        The tikzpicture options description defining the options for the picture.
        Often large scale options like `[scale=2]`.
    default_node_options : string
        The draw options for a path of nodes. Individual node options override these.
    node_options : string or dict
        The name of the node attribute on `G` that holds the options for each node.
        Or a dict keyed by node to a string holding the options for that node.
    node_label : string or dict
        The name of the node attribute on `G` that holds the node label (text)
        displayed for each node. If the attribute is "" or not present, the node
        itself is drawn as a string. LaTeX processing such as ``"$A_1$"`` is allowed.
        Or a dict keyed by node to a string holding the label for that node.
    default_edge_options : string
        The options for the scope drawing all edges. The default is "[-]" for
        undirected graphs and "[->]" for directed graphs.
    edge_options : string or dict
        The name of the edge attribute on `G` that holds the options for each edge.
        If the edge is a self-loop and ``"loop" not in edge_options`` the option
        "loop," is added to the options for the self-loop edge. Hence you can
        use "[loop above]" explicitly, but the default is "[loop]".
        Or a dict keyed by edge to a string holding the options for that edge.
    edge_label : string or dict
        The name of the edge attribute on `G` that holds the edge label (text)
        displayed for each edge. If the attribute is "" or not present, no edge
        label is drawn.
        Or a dict keyed by edge to a string holding the label for that edge.
    edge_label_options : string or dict
        The name of the edge attribute on `G` that holds the label options for
        each edge. For example, "[sloped,above,blue]". The default is no options.
        Or a dict keyed by edge to a string holding the label options for that edge.
    caption : string
        The caption string for the figure environment
    latex_label : string
        The latex label used for the figure for easy referral from the main text
    sub_captions : list of strings
        The sub_caption string for each subfigure in the figure
    sub_latex_labels : list of strings
        The latex label for each subfigure in the figure
    n_rows : int
        The number of rows of subfigures to arrange for multiple graphs
    as_document : bool
        Whether to wrap the latex code in a document environment for compiling
    document_wrapper : formatted text string with variable ``content``.
        This text is called to evaluate the content embedded in a document
        environment with a preamble setting up TikZ.
    figure_wrapper : formatted text string
        This text is evaluated with variables ``content``, ``caption`` and ``label``.
        It wraps the content and if a caption is provided, adds the latex code for
        that caption, and if a label is provided, adds the latex code for a label.
    subfigure_wrapper : formatted text string
        This text evaluate variables ``size``, ``content``, ``caption`` and ``label``.
        It wraps the content and if a caption is provided, adds the latex code for
        that caption, and if a label is provided, adds the latex code for a label.
        The size is the vertical size of each row of subfigures as a fraction.

    Returns
    =======
    latex_code : string
        The text string which draws the desired graph(s) when compiled by LaTeX.

    See Also
    ========
    write_latex
    to_latex_raw
networkx.to_latex_raw
Python Library Documentation: function to_latex_raw in module networkx.drawing.nx_latex

to_latex_raw(G, pos='pos', tikz_options='', default_node_options='', node_options='node_options', node_label='label', default_edge_options='', edge_options='edge_options', edge_label='label', edge_label_options='edge_label_options')
    Return a string of the LaTeX/TikZ code to draw `G`

    This function produces just the code for the tikzpicture
    without any enclosing environment.

    Parameters
    ==========
    G : NetworkX graph
        The NetworkX graph to be drawn
    pos : string or dict (default "pos")
        The name of the node attribute on `G` that holds the position of each node.
        Positions can be sequences of length 2 with numbers for (x,y) coordinates.
        They can also be strings to denote positions in TikZ style, such as (x, y)
        or (angle:radius).
        If a dict, it should be keyed by node to a position.
        If an empty dict, a circular layout is computed by TikZ.
    tikz_options : string
        The tikzpicture options description defining the options for the picture.
        Often large scale options like `[scale=2]`.
    default_node_options : string
        The draw options for a path of nodes. Individual node options override these.
    node_options : string or dict
        The name of the node attribute on `G` that holds the options for each node.
        Or a dict keyed by node to a string holding the options for that node.
    node_label : string or dict
        The name of the node attribute on `G` that holds the node label (text)
        displayed for each node. If the attribute is "" or not present, the node
        itself is drawn as a string. LaTeX processing such as ``"$A_1$"`` is allowed.
        Or a dict keyed by node to a string holding the label for that node.
    default_edge_options : string
        The options for the scope drawing all edges. The default is "[-]" for
        undirected graphs and "[->]" for directed graphs.
    edge_options : string or dict
        The name of the edge attribute on `G` that holds the options for each edge.
        If the edge is a self-loop and ``"loop" not in edge_options`` the option
        "loop," is added to the options for the self-loop edge. Hence you can
        use "[loop above]" explicitly, but the default is "[loop]".
        Or a dict keyed by edge to a string holding the options for that edge.
    edge_label : string or dict
        The name of the edge attribute on `G` that holds the edge label (text)
        displayed for each edge. If the attribute is "" or not present, no edge
        label is drawn.
        Or a dict keyed by edge to a string holding the label for that edge.
    edge_label_options : string or dict
        The name of the edge attribute on `G` that holds the label options for
        each edge. For example, "[sloped,above,blue]". The default is no options.
        Or a dict keyed by edge to a string holding the label options for that edge.

    Returns
    =======
    latex_code : string
       The text string which draws the desired graph(s) when compiled by LaTeX.

    See Also
    ========
    to_latex
    write_latex
networkx.to_nested_tuple
Python Library Documentation: function to_nested_tuple in module networkx.algorithms.tree.coding

to_nested_tuple(T, root, canonical_form=False, *, backend=None, **backend_kwargs)
    Returns a nested tuple representation of the given tree.

    The nested tuple representation of a tree is defined
    recursively. The tree with one node and no edges is represented by
    the empty tuple, ``()``. A tree with ``k`` subtrees is represented
    by a tuple of length ``k`` in which each element is the nested tuple
    representation of a subtree.

    Parameters
    ----------
    T : NetworkX graph
        An undirected graph object representing a tree.

    root : node
        The node in ``T`` to interpret as the root of the tree.

    canonical_form : bool
        If ``True``, each tuple is sorted so that the function returns
        a canonical form for rooted trees. This means "lighter" subtrees
        will appear as nested tuples before "heavier" subtrees. In this
        way, each isomorphic rooted tree has the same nested tuple
        representation.

    Returns
    -------
    tuple
        A nested tuple representation of the tree.

    Notes
    -----
    This function is *not* the inverse of :func:`from_nested_tuple`; the
    only guarantee is that the rooted trees are isomorphic.

    See also
    --------
    from_nested_tuple
    to_prufer_sequence

    Examples
    --------
    The tree need not be a balanced binary tree::

        >>> T = nx.Graph()
        >>> T.add_edges_from([(0, 1), (0, 2), (0, 3)])
        >>> T.add_edges_from([(1, 4), (1, 5)])
        >>> T.add_edges_from([(3, 6), (3, 7)])
        >>> root = 0
        >>> nx.to_nested_tuple(T, root)
        (((), ()), (), ((), ()))

    Continuing the above example, if ``canonical_form`` is ``True``, the
    nested tuples will be sorted::

        >>> nx.to_nested_tuple(T, root, canonical_form=True)
        ((), ((), ()), ((), ()))

    Even the path graph can be interpreted as a tree::

        >>> T = nx.path_graph(4)
        >>> root = 0
        >>> nx.to_nested_tuple(T, root)
        ((((),),),)
networkx.to_networkx_graph
Python Library Documentation: function to_networkx_graph in module networkx.convert

to_networkx_graph(data, create_using=None, multigraph_input=False)
    Make a NetworkX graph from a known data structure.

    The preferred way to call this is automatically
    from the class constructor

    >>> d = {0: {1: {"weight": 1}}}  # dict-of-dicts single edge (0,1)
    >>> G = nx.Graph(d)

    instead of the equivalent

    >>> G = nx.from_dict_of_dicts(d)

    Parameters
    ----------
    data : object to be converted

        Current known types are:
         any NetworkX graph
         dict-of-dicts
         dict-of-lists
         container (e.g. set, list, tuple) of edges
         iterator (e.g. itertools.chain) that produces edges
         generator of edges
         Pandas DataFrame (row per edge)
         2D numpy array
         scipy sparse array
         pygraphviz agraph

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.

    multigraph_input : bool (default False)
        If True and  data is a dict_of_dicts,
        try to create a multigraph assuming dict_of_dict_of_lists.
        If data and create_using are both multigraphs then create
        a multigraph from a multigraph.
networkx.to_numpy_array
Python Library Documentation: function to_numpy_array in module networkx.convert_matrix

to_numpy_array(G, nodelist=None, dtype=None, order=None, multigraph_weight=<built-in function sum>, weight='weight', nonedge=0.0, *, backend=None, **backend_kwargs)
    Returns the graph adjacency matrix as a NumPy array.

    Parameters
    ----------
    G : graph
        The NetworkX graph used to construct the NumPy array.

    nodelist : list, optional
        The rows and columns are ordered according to the nodes in `nodelist`.
        If `nodelist` is ``None``, then the ordering is produced by ``G.nodes()``.

    dtype : NumPy data type, optional
        A NumPy data type used to initialize the array. If None, then the NumPy
        default is used. The dtype can be structured if `weight=None`, in which
        case the dtype field names are used to look up edge attributes. The
        result is a structured array where each named field in the dtype
        corresponds to the adjacency for that edge attribute. See examples for
        details.

    order : {'C', 'F'}, optional
        Whether to store multidimensional data in C- or Fortran-contiguous
        (row- or column-wise) order in memory. If None, then the NumPy default
        is used.

    multigraph_weight : callable, optional
        An function that determines how weights in multigraphs are handled.
        The function should accept a sequence of weights and return a single
        value. The default is to sum the weights of the multiple edges.

    weight : string or None optional (default = 'weight')
        The edge attribute that holds the numerical value used for
        the edge weight. If an edge does not have that attribute, then the
        value 1 is used instead. `weight` must be ``None`` if a structured
        dtype is used.

    nonedge : array_like (default = 0.0)
        The value used to represent non-edges in the adjacency matrix.
        The array values corresponding to nonedges are typically set to zero.
        However, this could be undesirable if there are array values
        corresponding to actual edges that also have the value zero. If so,
        one might prefer nonedges to have some other value, such as ``nan``.

    Returns
    -------
    A : NumPy ndarray
        Graph adjacency matrix

    Raises
    ------
    NetworkXError
        If `dtype` is a structured dtype and `G` is a multigraph
    ValueError
        If `dtype` is a structured dtype and `weight` is not `None`

    See Also
    --------
    from_numpy_array

    Notes
    -----
    For directed graphs, entry ``i, j`` corresponds to an edge from ``i`` to ``j``.

    Entries in the adjacency matrix are given by the `weight` edge attribute.
    When an edge does not have a weight attribute, the value of the entry is
    set to the number 1.  For multiple (parallel) edges, the values of the
    entries are determined by the `multigraph_weight` parameter. The default is
    to sum the weight attributes for each of the parallel edges.

    When `nodelist` does not contain every node in `G`, the adjacency matrix is
    built from the subgraph of `G` that is induced by the nodes in `nodelist`.

    The convention used for self-loop edges in graphs is to assign the
    diagonal array entry value to the weight attribute of the edge
    (or the number 1 if the edge has no weight attribute). If the
    alternate convention of doubling the edge weight is desired the
    resulting NumPy array can be modified as follows:

    >>> import numpy as np
    >>> G = nx.Graph([(1, 1)])
    >>> A = nx.to_numpy_array(G)
    >>> A
    array([[1.]])
    >>> A[np.diag_indices_from(A)] *= 2
    >>> A
    array([[2.]])

    Examples
    --------
    >>> G = nx.MultiDiGraph()
    >>> G.add_edge(0, 1, weight=2)
    0
    >>> G.add_edge(1, 0)
    0
    >>> G.add_edge(2, 2, weight=3)
    0
    >>> G.add_edge(2, 2)
    1
    >>> nx.to_numpy_array(G, nodelist=[0, 1, 2])
    array([[0., 2., 0.],
           [1., 0., 0.],
           [0., 0., 4.]])

    When `nodelist` argument is used, nodes of `G` which do not appear in the `nodelist`
    and their edges are not included in the adjacency matrix. Here is an example:

    >>> G = nx.Graph()
    >>> G.add_edge(3, 1)
    >>> G.add_edge(2, 0)
    >>> G.add_edge(2, 1)
    >>> G.add_edge(3, 0)
    >>> nx.to_numpy_array(G, nodelist=[1, 2, 3])
    array([[0., 1., 1.],
           [1., 0., 0.],
           [1., 0., 0.]])

    This function can also be used to create adjacency matrices for multiple
    edge attributes with structured dtypes:

    >>> G = nx.Graph()
    >>> G.add_edge(0, 1, weight=10)
    >>> G.add_edge(1, 2, cost=5)
    >>> G.add_edge(2, 3, weight=3, cost=-4.0)
    >>> dtype = np.dtype([("weight", int), ("cost", float)])
    >>> A = nx.to_numpy_array(G, dtype=dtype, weight=None)
    >>> A["weight"]
    array([[ 0, 10,  0,  0],
           [10,  0,  1,  0],
           [ 0,  1,  0,  3],
           [ 0,  0,  3,  0]])
    >>> A["cost"]
    array([[ 0.,  1.,  0.,  0.],
           [ 1.,  0.,  5.,  0.],
           [ 0.,  5.,  0., -4.],
           [ 0.,  0., -4.,  0.]])

    As stated above, the argument "nonedge" is useful especially when there are
    actually edges with weight 0 in the graph. Setting a nonedge value different than 0,
    makes it much clearer to differentiate such 0-weighted edges and actual nonedge values.

    >>> G = nx.Graph()
    >>> G.add_edge(3, 1, weight=2)
    >>> G.add_edge(2, 0, weight=0)
    >>> G.add_edge(2, 1, weight=0)
    >>> G.add_edge(3, 0, weight=1)
    >>> nx.to_numpy_array(G, nonedge=-1.0)
    array([[-1.,  2., -1.,  1.],
           [ 2., -1.,  0., -1.],
           [-1.,  0., -1.,  0.],
           [ 1., -1.,  0., -1.]])
networkx.to_pandas_adjacency
Python Library Documentation: function to_pandas_adjacency in module networkx.convert_matrix

to_pandas_adjacency(G, nodelist=None, dtype=None, order=None, multigraph_weight=<built-in function sum>, weight='weight', nonedge=0.0, *, backend=None, **backend_kwargs)
    Returns the graph adjacency matrix as a Pandas DataFrame.

    Parameters
    ----------
    G : graph
        The NetworkX graph used to construct the Pandas DataFrame.

    nodelist : list, optional
       The rows and columns are ordered according to the nodes in `nodelist`.
       If `nodelist` is None, then the ordering is produced by G.nodes().

    multigraph_weight : {sum, min, max}, optional
        An operator that determines how weights in multigraphs are handled.
        The default is to sum the weights of the multiple edges.

    weight : string or None, optional
        The edge attribute that holds the numerical value used for
        the edge weight.  If an edge does not have that attribute, then the
        value 1 is used instead.

    nonedge : float, optional
        The matrix values corresponding to nonedges are typically set to zero.
        However, this could be undesirable if there are matrix values
        corresponding to actual edges that also have the value zero. If so,
        one might prefer nonedges to have some other value, such as nan.

    Returns
    -------
    df : Pandas DataFrame
       Graph adjacency matrix

    Notes
    -----
    For directed graphs, entry i,j corresponds to an edge from i to j.

    The DataFrame entries are assigned to the weight edge attribute. When
    an edge does not have a weight attribute, the value of the entry is set to
    the number 1.  For multiple (parallel) edges, the values of the entries
    are determined by the 'multigraph_weight' parameter.  The default is to
    sum the weight attributes for each of the parallel edges.

    When `nodelist` does not contain every node in `G`, the matrix is built
    from the subgraph of `G` that is induced by the nodes in `nodelist`.

    The convention used for self-loop edges in graphs is to assign the
    diagonal matrix entry value to the weight attribute of the edge
    (or the number 1 if the edge has no weight attribute).  If the
    alternate convention of doubling the edge weight is desired the
    resulting Pandas DataFrame can be modified as follows::

        >>> import pandas as pd
        >>> G = nx.Graph([(1, 1), (2, 2)])
        >>> df = nx.to_pandas_adjacency(G)
        >>> df
             1    2
        1  1.0  0.0
        2  0.0  1.0
        >>> diag_idx = list(range(len(df)))
        >>> df.iloc[diag_idx, diag_idx] *= 2
        >>> df
             1    2
        1  2.0  0.0
        2  0.0  2.0

    Examples
    --------
    >>> G = nx.MultiDiGraph()
    >>> G.add_edge(0, 1, weight=2)
    0
    >>> G.add_edge(1, 0)
    0
    >>> G.add_edge(2, 2, weight=3)
    0
    >>> G.add_edge(2, 2)
    1
    >>> nx.to_pandas_adjacency(G, nodelist=[0, 1, 2], dtype=int)
       0  1  2
    0  0  2  0
    1  1  0  0
    2  0  0  4
networkx.to_pandas_edgelist
Python Library Documentation: function to_pandas_edgelist in module networkx.convert_matrix

to_pandas_edgelist(G, source='source', target='target', nodelist=None, dtype=None, edge_key=None, *, backend=None, **backend_kwargs)
    Returns the graph edge list as a Pandas DataFrame.

    Parameters
    ----------
    G : graph
        The NetworkX graph used to construct the Pandas DataFrame.

    source : str or int, optional
        A valid column name (string or integer) for the source nodes (for the
        directed case).

    target : str or int, optional
        A valid column name (string or integer) for the target nodes (for the
        directed case).

    nodelist : list, optional
       Use only nodes specified in nodelist

    dtype : dtype, default None
        Use to create the DataFrame. Data type to force.
        Only a single dtype is allowed. If None, infer.

    edge_key : str or int or None, optional (default=None)
        A valid column name (string or integer) for the edge keys (for the
        multigraph case). If None, edge keys are not stored in the DataFrame.

    Returns
    -------
    df : Pandas DataFrame
       Graph edge list

    Examples
    --------
    >>> G = nx.Graph(
    ...     [
    ...         ("A", "B", {"cost": 1, "weight": 7}),
    ...         ("C", "E", {"cost": 9, "weight": 10}),
    ...     ]
    ... )
    >>> df = nx.to_pandas_edgelist(G, nodelist=["A", "C"])
    >>> df[["source", "target", "cost", "weight"]]
      source target  cost  weight
    0      A      B     1       7
    1      C      E     9      10

    >>> G = nx.MultiGraph([("A", "B", {"cost": 1}), ("A", "B", {"cost": 9})])
    >>> df = nx.to_pandas_edgelist(G, nodelist=["A", "C"], edge_key="ekey")
    >>> df[["source", "target", "cost", "ekey"]]
      source target  cost  ekey
    0      A      B     1     0
    1      A      B     9     1
networkx.to_prufer_sequence
Python Library Documentation: function to_prufer_sequence in module networkx.algorithms.tree.coding

to_prufer_sequence(T, *, backend=None, **backend_kwargs)
    Returns the Prüfer sequence of the given tree.

    A *Prüfer sequence* is a list of *n* - 2 numbers between 0 and
    *n* - 1, inclusive. The tree corresponding to a given Prüfer
    sequence can be recovered by repeatedly joining a node in the
    sequence with a node with the smallest potential degree according to
    the sequence.

    Parameters
    ----------
    T : NetworkX graph
        An undirected graph object representing a tree.

    Returns
    -------
    list
        The Prüfer sequence of the given tree.

    Raises
    ------
    NetworkXPointlessConcept
        If the number of nodes in `T` is less than two.

    NotATree
        If `T` is not a tree.

    KeyError
        If the set of nodes in `T` is not {0, …, *n* - 1}.

    Notes
    -----
    There is a bijection from labeled trees to Prüfer sequences. This
    function is the inverse of the :func:`from_prufer_sequence`
    function.

    Sometimes Prüfer sequences use nodes labeled from 1 to *n* instead
    of from 0 to *n* - 1. This function requires nodes to be labeled in
    the latter form. You can use :func:`~networkx.relabel_nodes` to
    relabel the nodes of your tree to the appropriate format.

    This implementation is from [1]_ and has a running time of
    $O(n)$.

    See also
    --------
    to_nested_tuple
    from_prufer_sequence

    References
    ----------
    .. [1] Wang, Xiaodong, Lei Wang, and Yingjie Wu.
           "An optimal algorithm for Prufer codes."
           *Journal of Software Engineering and Applications* 2.02 (2009): 111.
           <https://doi.org/10.4236/jsea.2009.22016>

    Examples
    --------
    There is a bijection between Prüfer sequences and labeled trees, so
    this function is the inverse of the :func:`from_prufer_sequence`
    function:

    >>> edges = [(0, 3), (1, 3), (2, 3), (3, 4), (4, 5)]
    >>> tree = nx.Graph(edges)
    >>> sequence = nx.to_prufer_sequence(tree)
    >>> sequence
    [3, 3, 3, 4]
    >>> tree2 = nx.from_prufer_sequence(sequence)
    >>> list(tree2.edges()) == edges
    True
networkx.to_scipy_sparse_array
Python Library Documentation: function to_scipy_sparse_array in module networkx.convert_matrix

to_scipy_sparse_array(G, nodelist=None, dtype=None, weight='weight', format='csr', *, backend=None, **backend_kwargs)
    Returns the graph adjacency matrix as a SciPy sparse array.

    Parameters
    ----------
    G : graph
        The NetworkX graph used to construct the sparse array.

    nodelist : list, optional
       The rows and columns are ordered according to the nodes in `nodelist`.
       If `nodelist` is None, then the ordering is produced by ``G.nodes()``.

    dtype : NumPy data-type, optional
        A valid NumPy dtype used to initialize the array. If None, then the
        NumPy default is used.

    weight : string or None, optional (default='weight')
        The edge attribute that holds the numerical value used for
        the edge weight.  If None then all edge weights are 1.

    format : str in {'bsr', 'csr', 'csc', 'coo', 'lil', 'dia', 'dok'}
        The format of the sparse array to be returned (default 'csr').  For
        some algorithms different implementations of sparse arrays
        can perform better.  See [1]_ for details.

    Returns
    -------
    A : SciPy sparse array
       Graph adjacency matrix.

    Notes
    -----
    For directed graphs, matrix entry ``i, j`` corresponds to an edge from
    ``i`` to ``j``.

    The values of the adjacency matrix are populated using the edge attribute held in
    parameter `weight`. When an edge does not have that attribute, the
    value of the entry is 1.

    For multiple edges the matrix values are the sums of the edge weights.

    When `nodelist` does not contain every node in `G`, the adjacency matrix
    is built from the subgraph of `G` that is induced by the nodes in
    `nodelist`.

    The convention used for self-loop edges in graphs is to assign the
    diagonal matrix entry value to the weight attribute of the edge
    (or the number 1 if the edge has no weight attribute).  If the
    alternate convention of doubling the edge weight is desired the
    resulting array can be modified as follows::

        >>> G = nx.Graph([(1, 1)])
        >>> A = nx.to_scipy_sparse_array(G)
        >>> A.toarray()
        array([[1]])
        >>> A.setdiag(A.diagonal() * 2)
        >>> A.toarray()
        array([[2]])

    Examples
    --------

    Basic usage:

    >>> G = nx.path_graph(4)
    >>> A = nx.to_scipy_sparse_array(G)
    >>> A  # doctest: +SKIP
    <Compressed Sparse Row sparse array of dtype 'int64'
        with 6 stored elements and shape (4, 4)>

    >>> A.toarray()
    array([[0, 1, 0, 0],
           [1, 0, 1, 0],
           [0, 1, 0, 1],
           [0, 0, 1, 0]])

    .. note:: The `toarray` method is used in these examples to better visualize
       the adjacancy matrix. For a dense representation of the adjaceny matrix,
       use `to_numpy_array` instead.

    Directed graphs:

    >>> G = nx.DiGraph([(0, 1), (1, 2), (2, 3)])
    >>> nx.to_scipy_sparse_array(G).toarray()
    array([[0, 1, 0, 0],
           [0, 0, 1, 0],
           [0, 0, 0, 1],
           [0, 0, 0, 0]])

    >>> H = G.reverse()
    >>> H.edges
    OutEdgeView([(1, 0), (2, 1), (3, 2)])
    >>> nx.to_scipy_sparse_array(H).toarray()
    array([[0, 0, 0, 0],
           [1, 0, 0, 0],
           [0, 1, 0, 0],
           [0, 0, 1, 0]])

    By default, the order of the rows/columns of the adjacency matrix is determined
    by the ordering of the nodes in `G`:

    >>> G = nx.Graph()
    >>> G.add_nodes_from([3, 5, 0, 1])
    >>> G.add_edges_from([(1, 3), (1, 5)])
    >>> nx.to_scipy_sparse_array(G).toarray()
    array([[0, 0, 0, 1],
           [0, 0, 0, 1],
           [0, 0, 0, 0],
           [1, 1, 0, 0]])

    The ordering of the rows can be changed with `nodelist`:

    >>> ordered = [0, 1, 3, 5]
    >>> nx.to_scipy_sparse_array(G, nodelist=ordered).toarray()
    array([[0, 0, 0, 0],
           [0, 0, 1, 1],
           [0, 1, 0, 0],
           [0, 1, 0, 0]])

    If `nodelist` contains a subset of the nodes in `G`, the adjacency matrix
    for the node-induced subgraph is produced:

    >>> nx.to_scipy_sparse_array(G, nodelist=[1, 3, 5]).toarray()
    array([[0, 1, 1],
           [1, 0, 0],
           [1, 0, 0]])

    The values of the adjacency matrix are drawn from the edge attribute
    specified by the `weight` parameter:

    >>> G = nx.path_graph(4)
    >>> nx.set_edge_attributes(
    ...     G, values={(0, 1): 1, (1, 2): 10, (2, 3): 2}, name="weight"
    ... )
    >>> nx.set_edge_attributes(
    ...     G, values={(0, 1): 50, (1, 2): 35, (2, 3): 10}, name="capacity"
    ... )
    >>> nx.to_scipy_sparse_array(G).toarray()  # Default weight="weight"
    array([[ 0,  1,  0,  0],
           [ 1,  0, 10,  0],
           [ 0, 10,  0,  2],
           [ 0,  0,  2,  0]])
    >>> nx.to_scipy_sparse_array(G, weight="capacity").toarray()
    array([[ 0, 50,  0,  0],
           [50,  0, 35,  0],
           [ 0, 35,  0, 10],
           [ 0,  0, 10,  0]])

    Any edges that don't have a `weight` attribute default to 1:

    >>> G[1][2].pop("capacity")
    35
    >>> nx.to_scipy_sparse_array(G, weight="capacity").toarray()
    array([[ 0, 50,  0,  0],
           [50,  0,  1,  0],
           [ 0,  1,  0, 10],
           [ 0,  0, 10,  0]])

    When `G` is a multigraph, the values in the adjacency matrix are given by
    the sum of the `weight` edge attribute over each edge key:

    >>> G = nx.MultiDiGraph([(0, 1), (0, 1), (0, 1), (2, 0)])
    >>> nx.to_scipy_sparse_array(G).toarray()
    array([[0, 3, 0],
           [0, 0, 0],
           [1, 0, 0]])

    References
    ----------
    .. [1] Scipy Dev. References, "Sparse Arrays",
       https://docs.scipy.org/doc/scipy/reference/sparse.html
networkx.to_sparse6_bytes
Python Library Documentation: function to_sparse6_bytes in module networkx.readwrite.sparse6

to_sparse6_bytes(G, nodes=None, header=True)
    Convert an undirected graph to bytes in sparse6 format.

    Parameters
    ----------
    G : Graph (undirected)

    nodes: list or iterable
       Nodes are labeled 0...n-1 in the order provided.  If None the ordering
       given by ``G.nodes()`` is used.

    header: bool
       If True add '>>sparse6<<' bytes to head of data.

    Raises
    ------
    NetworkXNotImplemented
        If the graph is directed.

    ValueError
        If the graph has at least ``2 ** 36`` nodes; the sparse6 format
        is only defined for graphs of order less than ``2 ** 36``.

    Examples
    --------
    >>> nx.to_sparse6_bytes(nx.path_graph(2))
    b'>>sparse6<<:An\n'

    See Also
    --------
    to_sparse6_bytes, read_sparse6, write_sparse6_bytes

    Notes
    -----
    The returned bytes end with a newline character.

    The format does not support edge or node labels.

    References
    ----------
    .. [1] Graph6 specification
           <https://users.cecs.anu.edu.au/~bdm/data/formats.html>
networkx.to_undirected
Python Library Documentation: function to_undirected in module networkx.classes.function

to_undirected(graph)
    Returns an undirected view of the graph `graph`.

    Identical to graph.to_undirected(as_view=True)
    Note that graph.to_undirected defaults to `as_view=False`
    while this function always provides a view.
networkx.topological_generations
Python Library Documentation: function topological_generations in module networkx.algorithms.dag

topological_generations(G, *, backend=None, **backend_kwargs)
    Stratifies a DAG into generations.

    A topological generation is node collection in which ancestors of a node in each
    generation are guaranteed to be in a previous generation, and any descendants of
    a node are guaranteed to be in a following generation. Nodes are guaranteed to
    be in the earliest possible generation that they can belong to.

    Parameters
    ----------
    G : NetworkX digraph
        A directed acyclic graph (DAG)

    Yields
    ------
    sets of nodes
        Yields sets of nodes representing each generation.

    Raises
    ------
    NetworkXError
        Generations are defined for directed graphs only. If the graph
        `G` is undirected, a :exc:`NetworkXError` is raised.

    NetworkXUnfeasible
        If `G` is not a directed acyclic graph (DAG) no topological generations
        exist and a :exc:`NetworkXUnfeasible` exception is raised.  This can also
        be raised if `G` is changed while the returned iterator is being processed

    RuntimeError
        If `G` is changed while the returned iterator is being processed.

    Examples
    --------
    >>> DG = nx.DiGraph([(2, 1), (3, 1)])
    >>> [sorted(generation) for generation in nx.topological_generations(DG)]
    [[2, 3], [1]]

    Notes
    -----
    The generation in which a node resides can also be determined by taking the
    max-path-distance from the node to the farthest leaf node. That value can
    be obtained with this function using `enumerate(topological_generations(G))`.

    See also
    --------
    topological_sort
networkx.topological_sort
Python Library Documentation: function topological_sort in module networkx.algorithms.dag

topological_sort(G, *, backend=None, **backend_kwargs)
    Returns a generator of nodes in topologically sorted order.

    A topological sort is a nonunique permutation of the nodes of a
    directed graph such that an edge from u to v implies that u
    appears before v in the topological sort order. This ordering is
    valid only if the graph has no directed cycles.

    Parameters
    ----------
    G : NetworkX digraph
        A directed acyclic graph (DAG)

    Yields
    ------
    nodes
        Yields the nodes in topological sorted order.

    Raises
    ------
    NetworkXError
        Topological sort is defined for directed graphs only. If the graph `G`
        is undirected, a :exc:`NetworkXError` is raised.

    NetworkXUnfeasible
        If `G` is not a directed acyclic graph (DAG) no topological sort exists
        and a :exc:`NetworkXUnfeasible` exception is raised.  This can also be
        raised if `G` is changed while the returned iterator is being processed

    RuntimeError
        If `G` is changed while the returned iterator is being processed.

    Examples
    --------
    To get the reverse order of the topological sort:

    >>> DG = nx.DiGraph([(1, 2), (2, 3)])
    >>> list(reversed(list(nx.topological_sort(DG))))
    [3, 2, 1]

    If your DiGraph naturally has the edges representing tasks/inputs
    and nodes representing people/processes that initiate tasks, then
    topological_sort is not quite what you need. You will have to change
    the tasks to nodes with dependence reflected by edges. The result is
    a kind of topological sort of the edges. This can be done
    with :func:`networkx.line_graph` as follows:

    >>> list(nx.topological_sort(nx.line_graph(DG)))
    [(1, 2), (2, 3)]

    Notes
    -----
    This algorithm is based on a description and proof in
    "Introduction to Algorithms: A Creative Approach" [1]_ .

    See also
    --------
    is_directed_acyclic_graph, lexicographical_topological_sort

    References
    ----------
    .. [1] Manber, U. (1989).
       *Introduction to Algorithms - A Creative Approach.* Addison-Wesley.
networkx.total_spanning_tree_weight
Python Library Documentation: function total_spanning_tree_weight in module networkx.linalg.laplacianmatrix

total_spanning_tree_weight(G, weight=None, root=None, *, backend=None, **backend_kwargs)
    Returns the total weight of all spanning trees of `G`.

    Kirchoff's Tree Matrix Theorem [1]_, [2]_ states that the determinant of any
    cofactor of the Laplacian matrix of a graph is the number of spanning trees
    in the graph. For a weighted Laplacian matrix, it is the sum across all
    spanning trees of the multiplicative weight of each tree. That is, the
    weight of each tree is the product of its edge weights.

    For unweighted graphs, the total weight equals the number of spanning trees in `G`.

    For directed graphs, the total weight follows by summing over all directed
    spanning trees in `G` that start in the `root` node [3]_.

    .. deprecated:: 3.3

       ``total_spanning_tree_weight`` is deprecated and will be removed in v3.5.
       Use ``nx.number_of_spanning_trees(G)`` instead.

    Parameters
    ----------
    G : NetworkX Graph

    weight : string or None, optional (default=None)
        The key for the edge attribute holding the edge weight.
        If None, then each edge has weight 1.

    root : node (only required for directed graphs)
       A node in the directed graph `G`.

    Returns
    -------
    total_weight : float
        Undirected graphs:
            The sum of the total multiplicative weights for all spanning trees in `G`.
        Directed graphs:
            The sum of the total multiplicative weights for all spanning trees of `G`,
            rooted at node `root`.

    Raises
    ------
    NetworkXPointlessConcept
        If `G` does not contain any nodes.

    NetworkXError
        If the graph `G` is not (weakly) connected,
        or if `G` is directed and the root node is not specified or not in G.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> round(nx.total_spanning_tree_weight(G))
    125

    >>> G = nx.Graph()
    >>> G.add_edge(1, 2, weight=2)
    >>> G.add_edge(1, 3, weight=1)
    >>> G.add_edge(2, 3, weight=1)
    >>> round(nx.total_spanning_tree_weight(G, "weight"))
    5

    Notes
    -----
    Self-loops are excluded. Multi-edges are contracted in one edge
    equal to the sum of the weights.

    References
    ----------
    .. [1] Wikipedia
       "Kirchhoff's theorem."
       https://en.wikipedia.org/wiki/Kirchhoff%27s_theorem
    .. [2] Kirchhoff, G. R.
        Über die Auflösung der Gleichungen, auf welche man
        bei der Untersuchung der linearen Vertheilung
        Galvanischer Ströme geführt wird
        Annalen der Physik und Chemie, vol. 72, pp. 497-508, 1847.
    .. [3] Margoliash, J.
        "Matrix-Tree Theorem for Directed Graphs"
        https://www.math.uchicago.edu/~may/VIGRE/VIGRE2010/REUPapers/Margoliash.pdf
networkx.tournament
Python Library Documentation: module networkx.algorithms.tournament in networkx.algorithms

NAME
    networkx.algorithms.tournament - Functions concerning tournament graphs.

DESCRIPTION
    A `tournament graph`_ is a complete oriented graph. In other words, it
    is a directed graph in which there is exactly one directed edge joining
    each pair of distinct nodes. For each function in this module that
    accepts a graph as input, you must provide a tournament graph. The
    responsibility is on the caller to ensure that the graph is a tournament
    graph:

        >>> G = nx.DiGraph([(0, 1), (1, 2), (2, 0)])
        >>> nx.is_tournament(G)
        True

    To access the functions in this module, you must access them through the
    :mod:`networkx.tournament` module::

        >>> nx.tournament.is_reachable(G, 0, 1)
        True

    .. _tournament graph: https://en.wikipedia.org/wiki/Tournament_%28graph_theory%29

FUNCTIONS
    hamiltonian_path(G, *, backend=None, **backend_kwargs)
        Returns a Hamiltonian path in the given tournament graph.

        Each tournament has a Hamiltonian path. If furthermore, the
        tournament is strongly connected, then the returned Hamiltonian path
        is a Hamiltonian cycle (by joining the endpoints of the path).

        Parameters
        ----------
        G : NetworkX graph
            A directed graph representing a tournament.

        Returns
        -------
        path : list
            A list of nodes which form a Hamiltonian path in `G`.

        Examples
        --------
        >>> G = nx.DiGraph([(0, 1), (0, 2), (0, 3), (1, 2), (1, 3), (2, 3)])
        >>> nx.is_tournament(G)
        True
        >>> nx.tournament.hamiltonian_path(G)
        [0, 1, 2, 3]

        Notes
        -----
        This is a recursive implementation with an asymptotic running time
        of $O(n^2)$, ignoring multiplicative polylogarithmic factors, where
        $n$ is the number of nodes in the graph.

    is_reachable(G, s, t, *, backend=None, **backend_kwargs)
        Decides whether there is a path from `s` to `t` in the
        tournament.

        This function is more theoretically efficient than the reachability
        checks than the shortest path algorithms in
        :mod:`networkx.algorithms.shortest_paths`.

        The given graph **must** be a tournament, otherwise this function's
        behavior is undefined.

        Parameters
        ----------
        G : NetworkX graph
            A directed graph representing a tournament.

        s : node
            A node in the graph.

        t : node
            A node in the graph.

        Returns
        -------
        bool
            Whether there is a path from `s` to `t` in `G`.

        Examples
        --------
        >>> G = nx.DiGraph([(1, 0), (1, 3), (1, 2), (2, 3), (2, 0), (3, 0)])
        >>> nx.is_tournament(G)
        True
        >>> nx.tournament.is_reachable(G, 1, 3)
        True
        >>> nx.tournament.is_reachable(G, 3, 2)
        False

        Notes
        -----
        Although this function is more theoretically efficient than the
        generic shortest path functions, a speedup requires the use of
        parallelism. Though it may in the future, the current implementation
        does not use parallelism, thus you may not see much of a speedup.

        This algorithm comes from [1].

        References
        ----------
        .. [1] Tantau, Till.
               "A note on the complexity of the reachability problem for
               tournaments."
               *Electronic Colloquium on Computational Complexity*. 2001.
               <http://eccc.hpi-web.de/report/2001/092/>

    is_strongly_connected(G, *, backend=None, **backend_kwargs)
        Decides whether the given tournament is strongly connected.

        This function is more theoretically efficient than the
        :func:`~networkx.algorithms.components.is_strongly_connected`
        function.

        The given graph **must** be a tournament, otherwise this function's
        behavior is undefined.

        Parameters
        ----------
        G : NetworkX graph
            A directed graph representing a tournament.

        Returns
        -------
        bool
            Whether the tournament is strongly connected.

        Examples
        --------
        >>> G = nx.DiGraph([(0, 1), (0, 2), (1, 2), (1, 3), (2, 3), (3, 0)])
        >>> nx.is_tournament(G)
        True
        >>> nx.tournament.is_strongly_connected(G)
        True
        >>> G.remove_edge(3, 0)
        >>> G.add_edge(0, 3)
        >>> nx.is_tournament(G)
        True
        >>> nx.tournament.is_strongly_connected(G)
        False

        Notes
        -----
        Although this function is more theoretically efficient than the
        generic strong connectivity function, a speedup requires the use of
        parallelism. Though it may in the future, the current implementation
        does not use parallelism, thus you may not see much of a speedup.

        This algorithm comes from [1].

        References
        ----------
        .. [1] Tantau, Till.
               "A note on the complexity of the reachability problem for
               tournaments."
               *Electronic Colloquium on Computational Complexity*. 2001.
               <http://eccc.hpi-web.de/report/2001/092/>

    is_tournament(G, *, backend=None, **backend_kwargs)
        Returns True if and only if `G` is a tournament.

        A tournament is a directed graph, with neither self-loops nor
        multi-edges, in which there is exactly one directed edge joining
        each pair of distinct nodes.

        Parameters
        ----------
        G : NetworkX graph
            A directed graph representing a tournament.

        Returns
        -------
        bool
            Whether the given graph is a tournament graph.

        Examples
        --------
        >>> G = nx.DiGraph([(0, 1), (1, 2), (2, 0)])
        >>> nx.is_tournament(G)
        True

        Notes
        -----
        Some definitions require a self-loop on each node, but that is not
        the convention used here.

    random_tournament(n, seed=None, *, backend=None, **backend_kwargs)
        Returns a random tournament graph on `n` nodes.

        Parameters
        ----------
        n : int
            The number of nodes in the returned graph.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        G : DiGraph
            A tournament on `n` nodes, with exactly one directed edge joining
            each pair of distinct nodes.

        Notes
        -----
        This algorithm adds, for each pair of distinct nodes, an edge with
        uniformly random orientation. In other words, `\binom{n}{2}` flips
        of an unbiased coin decide the orientations of the edges in the
        graph.

    score_sequence(G, *, backend=None, **backend_kwargs)
        Returns the score sequence for the given tournament graph.

        The score sequence is the sorted list of the out-degrees of the
        nodes of the graph.

        Parameters
        ----------
        G : NetworkX graph
            A directed graph representing a tournament.

        Returns
        -------
        list
            A sorted list of the out-degrees of the nodes of `G`.

        Examples
        --------
        >>> G = nx.DiGraph([(1, 0), (1, 3), (0, 2), (0, 3), (2, 1), (3, 2)])
        >>> nx.is_tournament(G)
        True
        >>> nx.tournament.score_sequence(G)
        [1, 1, 2, 2]

DATA
    __all__ = ['hamiltonian_path', 'is_reachable', 'is_strongly_connected'...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\tournament.py

networkx.transitive_closure
Python Library Documentation: function transitive_closure in module networkx.algorithms.dag

transitive_closure(G, reflexive=False, *, backend=None, **backend_kwargs)
    Returns transitive closure of a graph

    The transitive closure of G = (V,E) is a graph G+ = (V,E+) such that
    for all v, w in V there is an edge (v, w) in E+ if and only if there
    is a path from v to w in G.

    Handling of paths from v to v has some flexibility within this definition.
    A reflexive transitive closure creates a self-loop for the path
    from v to v of length 0. The usual transitive closure creates a
    self-loop only if a cycle exists (a path from v to v with length > 0).
    We also allow an option for no self-loops.

    Parameters
    ----------
    G : NetworkX Graph
        A directed/undirected graph/multigraph.
    reflexive : Bool or None, optional (default: False)
        Determines when cycles create self-loops in the Transitive Closure.
        If True, trivial cycles (length 0) create self-loops. The result
        is a reflexive transitive closure of G.
        If False (the default) non-trivial cycles create self-loops.
        If None, self-loops are not created.

    Returns
    -------
    NetworkX graph
        The transitive closure of `G`

    Raises
    ------
    NetworkXError
        If `reflexive` not in `{None, True, False}`

    Examples
    --------
    The treatment of trivial (i.e. length 0) cycles is controlled by the
    `reflexive` parameter.

    Trivial (i.e. length 0) cycles do not create self-loops when
    ``reflexive=False`` (the default)::

        >>> DG = nx.DiGraph([(1, 2), (2, 3)])
        >>> TC = nx.transitive_closure(DG, reflexive=False)
        >>> TC.edges()
        OutEdgeView([(1, 2), (1, 3), (2, 3)])

    However, nontrivial (i.e. length greater than 0) cycles create self-loops
    when ``reflexive=False`` (the default)::

        >>> DG = nx.DiGraph([(1, 2), (2, 3), (3, 1)])
        >>> TC = nx.transitive_closure(DG, reflexive=False)
        >>> TC.edges()
        OutEdgeView([(1, 2), (1, 3), (1, 1), (2, 3), (2, 1), (2, 2), (3, 1), (3, 2), (3, 3)])

    Trivial cycles (length 0) create self-loops when ``reflexive=True``::

        >>> DG = nx.DiGraph([(1, 2), (2, 3)])
        >>> TC = nx.transitive_closure(DG, reflexive=True)
        >>> TC.edges()
        OutEdgeView([(1, 2), (1, 1), (1, 3), (2, 3), (2, 2), (3, 3)])

    And the third option is not to create self-loops at all when ``reflexive=None``::

        >>> DG = nx.DiGraph([(1, 2), (2, 3), (3, 1)])
        >>> TC = nx.transitive_closure(DG, reflexive=None)
        >>> TC.edges()
        OutEdgeView([(1, 2), (1, 3), (2, 3), (2, 1), (3, 1), (3, 2)])

    References
    ----------
    .. [1] https://www.ics.uci.edu/~eppstein/PADS/PartialOrder.py
networkx.transitive_closure_dag
Python Library Documentation: function transitive_closure_dag in module networkx.algorithms.dag

transitive_closure_dag(G, topo_order=None, *, backend=None, **backend_kwargs)
    Returns the transitive closure of a directed acyclic graph.

    This function is faster than the function `transitive_closure`, but fails
    if the graph has a cycle.

    The transitive closure of G = (V,E) is a graph G+ = (V,E+) such that
    for all v, w in V there is an edge (v, w) in E+ if and only if there
    is a non-null path from v to w in G.

    Parameters
    ----------
    G : NetworkX DiGraph
        A directed acyclic graph (DAG)

    topo_order: list or tuple, optional
        A topological order for G (if None, the function will compute one)

    Returns
    -------
    NetworkX DiGraph
        The transitive closure of `G`

    Raises
    ------
    NetworkXNotImplemented
        If `G` is not directed
    NetworkXUnfeasible
        If `G` has a cycle

    Examples
    --------
    >>> DG = nx.DiGraph([(1, 2), (2, 3)])
    >>> TC = nx.transitive_closure_dag(DG)
    >>> TC.edges()
    OutEdgeView([(1, 2), (1, 3), (2, 3)])

    Notes
    -----
    This algorithm is probably simple enough to be well-known but I didn't find
    a mention in the literature.
networkx.transitive_reduction
Python Library Documentation: function transitive_reduction in module networkx.algorithms.dag

transitive_reduction(G, *, backend=None, **backend_kwargs)
    Returns transitive reduction of a directed graph

    The transitive reduction of G = (V,E) is a graph G- = (V,E-) such that
    for all v,w in V there is an edge (v,w) in E- if and only if (v,w) is
    in E and there is no path from v to w in G with length greater than 1.

    Parameters
    ----------
    G : NetworkX DiGraph
        A directed acyclic graph (DAG)

    Returns
    -------
    NetworkX DiGraph
        The transitive reduction of `G`

    Raises
    ------
    NetworkXError
        If `G` is not a directed acyclic graph (DAG) transitive reduction is
        not uniquely defined and a :exc:`NetworkXError` exception is raised.

    Examples
    --------
    To perform transitive reduction on a DiGraph:

    >>> DG = nx.DiGraph([(1, 2), (2, 3), (1, 3)])
    >>> TR = nx.transitive_reduction(DG)
    >>> list(TR.edges)
    [(1, 2), (2, 3)]

    To avoid unnecessary data copies, this implementation does not return a
    DiGraph with node/edge data.
    To perform transitive reduction on a DiGraph and transfer node/edge data:

    >>> DG = nx.DiGraph()
    >>> DG.add_edges_from([(1, 2), (2, 3), (1, 3)], color="red")
    >>> TR = nx.transitive_reduction(DG)
    >>> TR.add_nodes_from(DG.nodes(data=True))
    >>> TR.add_edges_from((u, v, DG.edges[u, v]) for u, v in TR.edges)
    >>> list(TR.edges(data=True))
    [(1, 2, {'color': 'red'}), (2, 3, {'color': 'red'})]

    References
    ----------
    https://en.wikipedia.org/wiki/Transitive_reduction
networkx.transitivity
Python Library Documentation: function transitivity in module networkx.algorithms.cluster

transitivity(G, *, backend=None, **backend_kwargs)
    Compute graph transitivity, the fraction of all possible triangles
    present in G.

    Possible triangles are identified by the number of "triads"
    (two edges with a shared vertex).

    The transitivity is

    .. math::

        T = 3\frac{\#triangles}{\#triads}.

    Parameters
    ----------
    G : graph

    Returns
    -------
    out : float
       Transitivity

    Notes
    -----
    Self loops are ignored.

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> print(nx.transitivity(G))
    1.0
networkx.traversal
Python Library Documentation: package networkx.algorithms.traversal in networkx.algorithms

NAME
    networkx.algorithms.traversal

PACKAGE CONTENTS
    beamsearch
    breadth_first_search
    depth_first_search
    edgebfs
    edgedfs
    tests (package)

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\traversal\__init__.py

networkx.tree
Python Library Documentation: package networkx.algorithms.tree in networkx.algorithms

NAME
    networkx.algorithms.tree

PACKAGE CONTENTS
    branchings
    coding
    decomposition
    mst
    operations
    recognition
    tests (package)

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\tree\__init__.py

networkx.tree_all_pairs_lowest_common_ancestor
Python Library Documentation: function tree_all_pairs_lowest_common_ancestor in module networkx.algorithms.lowest_common_ancestors

tree_all_pairs_lowest_common_ancestor(G, root=None, pairs=None, *, backend=None, **backend_kwargs)
    Yield the lowest common ancestor for sets of pairs in a tree.

    Parameters
    ----------
    G : NetworkX directed graph (must be a tree)

    root : node, optional (default: None)
        The root of the subtree to operate on.
        If None, assume the entire graph has exactly one source and use that.

    pairs : iterable or iterator of pairs of nodes, optional (default: None)
        The pairs of interest. If None, Defaults to all pairs of nodes
        under `root` that have a lowest common ancestor.

    Returns
    -------
    lcas : generator of tuples `((u, v), lca)` where `u` and `v` are nodes
        in `pairs` and `lca` is their lowest common ancestor.

    Examples
    --------
    >>> import pprint
    >>> G = nx.DiGraph([(1, 3), (2, 4), (1, 2)])
    >>> pprint.pprint(dict(nx.tree_all_pairs_lowest_common_ancestor(G)))
    {(1, 1): 1,
     (2, 1): 1,
     (2, 2): 2,
     (3, 1): 1,
     (3, 2): 1,
     (3, 3): 3,
     (3, 4): 1,
     (4, 1): 1,
     (4, 2): 2,
     (4, 4): 4}

    We can also use `pairs` argument to specify the pairs of nodes for which we
    want to compute lowest common ancestors. Here is an example:

    >>> dict(nx.tree_all_pairs_lowest_common_ancestor(G, pairs=[(1, 4), (2, 3)]))
    {(2, 3): 1, (1, 4): 1}

    Notes
    -----
    Only defined on non-null trees represented with directed edges from
    parents to children. Uses Tarjan's off-line lowest-common-ancestors
    algorithm. Runs in time $O(4 \times (V + E + P))$ time, where 4 is the largest
    value of the inverse Ackermann function likely to ever come up in actual
    use, and $P$ is the number of pairs requested (or $V^2$ if all are needed).

    Tarjan, R. E. (1979), "Applications of path compression on balanced trees",
    Journal of the ACM 26 (4): 690-715, doi:10.1145/322154.322161.

    See Also
    --------
    all_pairs_lowest_common_ancestor: similar routine for general DAGs
    lowest_common_ancestor: just a single pair for general DAGs
networkx.tree_broadcast_center
Python Library Documentation: function tree_broadcast_center in module networkx.algorithms.broadcasting

tree_broadcast_center(G, *, backend=None, **backend_kwargs)
    Return the Broadcast Center of the tree `G`.

    The broadcast center of a graph G denotes the set of nodes having
    minimum broadcast time [1]_. This is a linear algorithm for determining
    the broadcast center of a tree with ``N`` nodes, as a by-product it also
    determines the broadcast time from the broadcast center.

    Parameters
    ----------
    G : undirected graph
        The graph should be an undirected tree

    Returns
    -------
    BC : (int, set) tuple
        minimum broadcast number of the tree, set of broadcast centers

    Raises
    ------
    NetworkXNotImplemented
        If the graph is directed or is a multigraph.

    References
    ----------
    .. [1] Slater, P.J., Cockayne, E.J., Hedetniemi, S.T,
       Information dissemination in trees. SIAM J.Comput. 10(4), 692–701 (1981)
networkx.tree_broadcast_time
Python Library Documentation: function tree_broadcast_time in module networkx.algorithms.broadcasting

tree_broadcast_time(G, node=None, *, backend=None, **backend_kwargs)
    Return the Broadcast Time of the tree `G`.

    The minimum broadcast time of a node is defined as the minimum amount
    of time required to complete broadcasting starting from the
    originator. The broadcast time of a graph is the maximum over
    all nodes of the minimum broadcast time from that node [1]_.
    This function returns the minimum broadcast time of `node`.
    If `node` is None the broadcast time for the graph is returned.

    Parameters
    ----------
    G : undirected graph
        The graph should be an undirected tree
    node: int, optional
        index of starting node. If `None`, the algorithm returns the broadcast
        time of the tree.

    Returns
    -------
    BT : int
        Broadcast Time of a node in a tree

    Raises
    ------
    NetworkXNotImplemented
        If the graph is directed or is a multigraph.

    References
    ----------
    .. [1] Harutyunyan, H. A. and Li, Z.
        "A Simple Construction of Broadcast Graphs."
        In Computing and Combinatorics. COCOON 2019
        (Ed. D. Z. Du and C. Tian.) Springer, pp. 240-253, 2019.
networkx.tree_data
Python Library Documentation: function tree_data in module networkx.readwrite.json_graph.tree

tree_data(G, root, ident='id', children='children')
    Returns data in tree format that is suitable for JSON serialization
    and use in JavaScript documents.

    Parameters
    ----------
    G : NetworkX graph
       G must be an oriented tree

    root : node
       The root of the tree

    ident : string
        Attribute name for storing NetworkX-internal graph data. `ident` must
        have a different value than `children`. The default is 'id'.

    children : string
        Attribute name for storing NetworkX-internal graph data. `children`
        must have a different value than `ident`. The default is 'children'.

    Returns
    -------
    data : dict
       A dictionary with node-link formatted data.

    Raises
    ------
    NetworkXError
        If `children` and `ident` attributes are identical.

    Examples
    --------
    >>> from networkx.readwrite import json_graph
    >>> G = nx.DiGraph([(1, 2)])
    >>> data = json_graph.tree_data(G, root=1)

    To serialize with json

    >>> import json
    >>> s = json.dumps(data)

    Notes
    -----
    Node attributes are stored in this format but keys
    for attributes must be strings if you want to serialize with JSON.

    Graph and edge attributes are not stored.

    See Also
    --------
    tree_graph, node_link_data, adjacency_data
networkx.tree_graph
Python Library Documentation: function tree_graph in module networkx.readwrite.json_graph.tree

tree_graph(data, ident='id', children='children', *, backend=None, **backend_kwargs)
    Returns graph from tree data format.

    Parameters
    ----------
    data : dict
        Tree formatted graph data

    ident : string
        Attribute name for storing NetworkX-internal graph data. `ident` must
        have a different value than `children`. The default is 'id'.

    children : string
        Attribute name for storing NetworkX-internal graph data. `children`
        must have a different value than `ident`. The default is 'children'.

    Returns
    -------
    G : NetworkX DiGraph

    Examples
    --------
    >>> from networkx.readwrite import json_graph
    >>> G = nx.DiGraph([(1, 2)])
    >>> data = json_graph.tree_data(G, root=1)
    >>> H = json_graph.tree_graph(data)

    See Also
    --------
    tree_data, node_link_data, adjacency_data
networkx.trees
Python Library Documentation: module networkx.generators.trees in networkx.generators

NAME
    networkx.generators.trees - Functions for generating trees.

DESCRIPTION
    The functions sampling trees at random in this module come
    in two variants: labeled and unlabeled. The labeled variants
    sample from every possible tree with the given number of nodes
    uniformly at random. The unlabeled variants sample from every
    possible *isomorphism class* of trees with the given number
    of nodes uniformly at random.

    To understand the difference, consider the following example.
    There are two isomorphism classes of trees with four nodes.
    One is that of the path graph, the other is that of the
    star graph. The unlabeled variant will return a line graph or
    a star graph with probability 1/2.

    The labeled variant will return the line graph
    with probability 3/4 and the star graph with probability 1/4,
    because there are more labeled variants of the line graph
    than of the star graph. More precisely, the line graph has
    an automorphism group of order 2, whereas the star graph has
    an automorphism group of order 6, so the line graph has three
    times as many labeled variants as the star graph, and thus
    three more chances to be drawn.

    Additionally, some functions in this module can sample rooted
    trees and forests uniformly at random. A rooted tree is a tree
    with a designated root node. A rooted forest is a disjoint union
    of rooted trees.

FUNCTIONS
    prefix_tree(paths, *, backend=None, **backend_kwargs)
        Creates a directed prefix tree from a list of paths.

        Usually the paths are described as strings or lists of integers.

        A "prefix tree" represents the prefix structure of the strings.
        Each node represents a prefix of some string. The root represents
        the empty prefix with children for the single letter prefixes which
        in turn have children for each double letter prefix starting with
        the single letter corresponding to the parent node, and so on.

        More generally the prefixes do not need to be strings. A prefix refers
        to the start of a sequence. The root has children for each one element
        prefix and they have children for each two element prefix that starts
        with the one element sequence of the parent, and so on.

        Note that this implementation uses integer nodes with an attribute.
        Each node has an attribute "source" whose value is the original element
        of the path to which this node corresponds. For example, suppose `paths`
        consists of one path: "can". Then the nodes `[1, 2, 3]` which represent
        this path have "source" values "c", "a" and "n".

        All the descendants of a node have a common prefix in the sequence/path
        associated with that node. From the returned tree, the prefix for each
        node can be constructed by traversing the tree up to the root and
        accumulating the "source" values along the way.

        The root node is always `0` and has "source" attribute `None`.
        The root is the only node with in-degree zero.
        The nil node is always `-1` and has "source" attribute `"NIL"`.
        The nil node is the only node with out-degree zero.


        Parameters
        ----------
        paths: iterable of paths
            An iterable of paths which are themselves sequences.
            Matching prefixes among these sequences are identified with
            nodes of the prefix tree. One leaf of the tree is associated
            with each path. (Identical paths are associated with the same
            leaf of the tree.)


        Returns
        -------
        tree: DiGraph
            A directed graph representing an arborescence consisting of the
            prefix tree generated by `paths`. Nodes are directed "downward",
            from parent to child. A special "synthetic" root node is added
            to be the parent of the first node in each path. A special
            "synthetic" leaf node, the "nil" node `-1`, is added to be the child
            of all nodes representing the last element in a path. (The
            addition of this nil node technically makes this not an
            arborescence but a directed acyclic graph; removing the nil node
            makes it an arborescence.)


        Notes
        -----
        The prefix tree is also known as a *trie*.


        Examples
        --------
        Create a prefix tree from a list of strings with common prefixes::

            >>> paths = ["ab", "abs", "ad"]
            >>> T = nx.prefix_tree(paths)
            >>> list(T.edges)
            [(0, 1), (1, 2), (1, 4), (2, -1), (2, 3), (3, -1), (4, -1)]

        The leaf nodes can be obtained as predecessors of the nil node::

            >>> root, NIL = 0, -1
            >>> list(T.predecessors(NIL))
            [2, 3, 4]

        To recover the original paths that generated the prefix tree,
        traverse up the tree from the node `-1` to the node `0`::

            >>> recovered = []
            >>> for v in T.predecessors(NIL):
            ...     prefix = ""
            ...     while v != root:
            ...         prefix = str(T.nodes[v]["source"]) + prefix
            ...         v = next(T.predecessors(v))  # only one predecessor
            ...     recovered.append(prefix)
            >>> sorted(recovered)
            ['ab', 'abs', 'ad']

    prefix_tree_recursive(paths, *, backend=None, **backend_kwargs)
        Recursively creates a directed prefix tree from a list of paths.

        The original recursive version of prefix_tree for comparison. It is
        the same algorithm but the recursion is unrolled onto a stack.

        Usually the paths are described as strings or lists of integers.

        A "prefix tree" represents the prefix structure of the strings.
        Each node represents a prefix of some string. The root represents
        the empty prefix with children for the single letter prefixes which
        in turn have children for each double letter prefix starting with
        the single letter corresponding to the parent node, and so on.

        More generally the prefixes do not need to be strings. A prefix refers
        to the start of a sequence. The root has children for each one element
        prefix and they have children for each two element prefix that starts
        with the one element sequence of the parent, and so on.

        Note that this implementation uses integer nodes with an attribute.
        Each node has an attribute "source" whose value is the original element
        of the path to which this node corresponds. For example, suppose `paths`
        consists of one path: "can". Then the nodes `[1, 2, 3]` which represent
        this path have "source" values "c", "a" and "n".

        All the descendants of a node have a common prefix in the sequence/path
        associated with that node. From the returned tree, ehe prefix for each
        node can be constructed by traversing the tree up to the root and
        accumulating the "source" values along the way.

        The root node is always `0` and has "source" attribute `None`.
        The root is the only node with in-degree zero.
        The nil node is always `-1` and has "source" attribute `"NIL"`.
        The nil node is the only node with out-degree zero.


        Parameters
        ----------
        paths: iterable of paths
            An iterable of paths which are themselves sequences.
            Matching prefixes among these sequences are identified with
            nodes of the prefix tree. One leaf of the tree is associated
            with each path. (Identical paths are associated with the same
            leaf of the tree.)


        Returns
        -------
        tree: DiGraph
            A directed graph representing an arborescence consisting of the
            prefix tree generated by `paths`. Nodes are directed "downward",
            from parent to child. A special "synthetic" root node is added
            to be the parent of the first node in each path. A special
            "synthetic" leaf node, the "nil" node `-1`, is added to be the child
            of all nodes representing the last element in a path. (The
            addition of this nil node technically makes this not an
            arborescence but a directed acyclic graph; removing the nil node
            makes it an arborescence.)


        Notes
        -----
        The prefix tree is also known as a *trie*.


        Examples
        --------
        Create a prefix tree from a list of strings with common prefixes::

            >>> paths = ["ab", "abs", "ad"]
            >>> T = nx.prefix_tree(paths)
            >>> list(T.edges)
            [(0, 1), (1, 2), (1, 4), (2, -1), (2, 3), (3, -1), (4, -1)]

        The leaf nodes can be obtained as predecessors of the nil node.

            >>> root, NIL = 0, -1
            >>> list(T.predecessors(NIL))
            [2, 3, 4]

        To recover the original paths that generated the prefix tree,
        traverse up the tree from the node `-1` to the node `0`::

            >>> recovered = []
            >>> for v in T.predecessors(NIL):
            ...     prefix = ""
            ...     while v != root:
            ...         prefix = str(T.nodes[v]["source"]) + prefix
            ...         v = next(T.predecessors(v))  # only one predecessor
            ...     recovered.append(prefix)
            >>> sorted(recovered)
            ['ab', 'abs', 'ad']

    random_labeled_rooted_forest(n, *, seed=None, backend=None, **backend_kwargs)
        Returns a labeled rooted forest with `n` nodes.

        The returned forest is chosen uniformly at random using a
        generalization of Prüfer sequences [1]_ in the form described in [2]_.

        Parameters
        ----------
        n : int
            The number of nodes.
        seed : random_state
           See :ref:`Randomness<randomness>`.

        Returns
        -------
        :class:`networkx.Graph`
            A `networkx.Graph` with integer nodes 0 <= node <= `n` - 1.
            The "roots" graph attribute is a set of integers containing the roots.

        References
        ----------
        .. [1] Knuth, Donald E. "Another Enumeration of Trees."
            Canadian Journal of Mathematics, 20 (1968): 1077-1086.
            https://doi.org/10.4153/CJM-1968-104-8
        .. [2] Rubey, Martin. "Counting Spanning Trees". Diplomarbeit
            zur Erlangung des akademischen Grades Magister der
            Naturwissenschaften an der Formal- und Naturwissenschaftlichen
            Fakultät der Universität Wien. Wien, May 2000.

    random_labeled_rooted_tree(n, *, seed=None, backend=None, **backend_kwargs)
        Returns a labeled rooted tree with `n` nodes.

        The returned tree is chosen uniformly at random from all labeled rooted trees.

        Parameters
        ----------
        n : int
            The number of nodes
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        :class:`networkx.Graph`
            A `networkx.Graph` with integer nodes 0 <= node <= `n` - 1.
            The root of the tree is selected uniformly from the nodes.
            The "root" graph attribute identifies the root of the tree.

        Notes
        -----
        This function returns the result of :func:`random_labeled_tree`
        with a randomly selected root.

        Raises
        ------
        NetworkXPointlessConcept
            If `n` is zero (because the null graph is not a tree).

    random_labeled_tree(n, *, seed=None, backend=None, **backend_kwargs)
        Returns a labeled tree on `n` nodes chosen uniformly at random.

        Generating uniformly distributed random Prüfer sequences and
        converting them into the corresponding trees is a straightforward
        method of generating uniformly distributed random labeled trees.
        This function implements this method.

        Parameters
        ----------
        n : int
            The number of nodes, greater than zero.
        seed : random_state
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`

        Returns
        -------
         :class:`networkx.Graph`
            A `networkx.Graph` with nodes in the set {0, …, *n* - 1}.

        Raises
        ------
        NetworkXPointlessConcept
            If `n` is zero (because the null graph is not a tree).

        Examples
        --------
        >>> G = nx.random_labeled_tree(5, seed=42)
        >>> nx.is_tree(G)
        True
        >>> G.edges
        EdgeView([(0, 1), (0, 3), (0, 2), (2, 4)])

        A tree with *arbitrarily directed* edges can be created by assigning
        generated edges to a ``DiGraph``:

        >>> DG = nx.DiGraph()
        >>> DG.add_edges_from(G.edges)
        >>> nx.is_tree(DG)
        True
        >>> DG.edges
        OutEdgeView([(0, 1), (0, 3), (0, 2), (2, 4)])

    random_unlabeled_rooted_forest(n, *, q=None, number_of_forests=None, seed=None, backend=None, **backend_kwargs)
        Returns a forest or list of forests selected at random.

        Returns one or more (depending on `number_of_forests`)
        unlabeled rooted forests with `n` nodes, and with no more than
        `q` nodes per tree, drawn uniformly at random.
        The "roots" graph attribute identifies the roots of the forest.

        Parameters
        ----------
        n : int
            The number of nodes
        q : int or None (default)
            The maximum number of nodes per tree.
        number_of_forests : int or None (default)
            If not None, this number of forests is generated and returned.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        :class:`networkx.Graph` or list of :class:`networkx.Graph`
            A single `networkx.Graph` (or a list thereof, if `number_of_forests`
            is specified) with nodes in the set {0, …, *n* - 1}.
            The "roots" graph attribute is a set containing the roots
            of the trees in the forest.

        Notes
        -----
        This function implements the algorithm "Forest" of [1]_.
        The algorithm needs to compute some counting functions
        that are relatively expensive: in case several trees are needed,
        it is advisable to use the `number_of_forests` optional argument
        to reuse the counting functions.

        Raises
        ------
        ValueError
            If `n` is non-zero but `q` is zero.

        References
        ----------
        .. [1] Wilf, Herbert S. "The uniform selection of free trees."
            Journal of Algorithms 2.2 (1981): 204-207.
            https://doi.org/10.1016/0196-6774(81)90021-3

    random_unlabeled_rooted_tree(n, *, number_of_trees=None, seed=None, backend=None, **backend_kwargs)
        Returns a number of unlabeled rooted trees uniformly at random

        Returns one or more (depending on `number_of_trees`)
        unlabeled rooted trees with `n` nodes drawn uniformly
        at random.

        Parameters
        ----------
        n : int
            The number of nodes
        number_of_trees : int or None (default)
            If not None, this number of trees is generated and returned.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        :class:`networkx.Graph` or list of :class:`networkx.Graph`
            A single `networkx.Graph` (or a list thereof, if `number_of_trees`
            is specified) with nodes in the set {0, …, *n* - 1}.
            The "root" graph attribute identifies the root of the tree.

        Notes
        -----
        The trees are generated using the "RANRUT" algorithm from [1]_.
        The algorithm needs to compute some counting functions
        that are relatively expensive: in case several trees are needed,
        it is advisable to use the `number_of_trees` optional argument
        to reuse the counting functions.

        Raises
        ------
        NetworkXPointlessConcept
            If `n` is zero (because the null graph is not a tree).

        References
        ----------
        .. [1] Nijenhuis, Albert, and Wilf, Herbert S.
            "Combinatorial algorithms: for computers and calculators."
            Academic Press, 1978.
            https://doi.org/10.1016/C2013-0-11243-3

    random_unlabeled_tree(n, *, number_of_trees=None, seed=None, backend=None, **backend_kwargs)
        Returns a tree or list of trees chosen randomly.

        Returns one or more (depending on `number_of_trees`)
        unlabeled trees with `n` nodes drawn uniformly at random.

        Parameters
        ----------
        n : int
            The number of nodes
        number_of_trees : int or None (default)
            If not None, this number of trees is generated and returned.
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        :class:`networkx.Graph` or list of :class:`networkx.Graph`
            A single `networkx.Graph` (or a list thereof, if
            `number_of_trees` is specified) with nodes in the set {0, …, *n* - 1}.

        Raises
        ------
        NetworkXPointlessConcept
            If `n` is zero (because the null graph is not a tree).

        Notes
        -----
        This function generates an unlabeled tree uniformly at random using
        Wilf's algorithm "Free" of [1]_. The algorithm needs to
        compute some counting functions that are relatively expensive:
        in case several trees are needed, it is advisable to use the
        `number_of_trees` optional argument to reuse the counting
        functions.

        References
        ----------
        .. [1] Wilf, Herbert S. "The uniform selection of free trees."
            Journal of Algorithms 2.2 (1981): 204-207.
            https://doi.org/10.1016/0196-6774(81)90021-3

DATA
    __all__ = ['prefix_tree', 'prefix_tree_recursive', 'random_labeled_tre...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\generators\trees.py

networkx.triad_graph
Python Library Documentation: function triad_graph in module networkx.generators.triads

triad_graph(triad_name, *, backend=None, **backend_kwargs)
    Returns the triad graph with the given name.

    Each string in the following tuple is a valid triad name::

        (
            "003",
            "012",
            "102",
            "021D",
            "021U",
            "021C",
            "111D",
            "111U",
            "030T",
            "030C",
            "201",
            "120D",
            "120U",
            "120C",
            "210",
            "300",
        )

    Each triad name corresponds to one of the possible valid digraph on
    three nodes.

    Parameters
    ----------
    triad_name : string
        The name of a triad, as described above.

    Returns
    -------
    :class:`~networkx.DiGraph`
        The digraph on three nodes with the given name. The nodes of the
        graph are the single-character strings 'a', 'b', and 'c'.

    Raises
    ------
    ValueError
        If `triad_name` is not the name of a triad.

    See also
    --------
    triadic_census
networkx.triad_type
Python Library Documentation: function triad_type in module networkx.algorithms.triads

triad_type(G, *, backend=None, **backend_kwargs)
    Returns the sociological triad type for a triad.

    Parameters
    ----------
    G : digraph
       A NetworkX DiGraph with 3 nodes

    Returns
    -------
    triad_type : str
       A string identifying the triad type

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 1)])
    >>> nx.triad_type(G)
    '030C'
    >>> G.add_edge(1, 3)
    >>> nx.triad_type(G)
    '120C'

    Notes
    -----
    There can be 6 unique edges in a triad (order-3 DiGraph) (so 2^^6=64 unique
    triads given 3 nodes). These 64 triads each display exactly 1 of 16
    topologies of triads (topologies can be permuted). These topologies are
    identified by the following notation:

    {m}{a}{n}{type} (for example: 111D, 210, 102)

    Here:

    {m}     = number of mutual ties (takes 0, 1, 2, 3); a mutual tie is (0,1)
              AND (1,0)
    {a}     = number of asymmetric ties (takes 0, 1, 2, 3); an asymmetric tie
              is (0,1) BUT NOT (1,0) or vice versa
    {n}     = number of null ties (takes 0, 1, 2, 3); a null tie is NEITHER
              (0,1) NOR (1,0)
    {type}  = a letter (takes U, D, C, T) corresponding to up, down, cyclical
              and transitive. This is only used for topologies that can have
              more than one form (eg: 021D and 021U).

    References
    ----------
    .. [1] Snijders, T. (2012). "Transitivity and triads." University of
        Oxford.
        https://web.archive.org/web/20170830032057/http://www.stats.ox.ac.uk/~snijders/Trans_Triads_ha.pdf
networkx.triadic_census
Python Library Documentation: function triadic_census in module networkx.algorithms.triads

triadic_census(G, nodelist=None, *, backend=None, **backend_kwargs)
    Determines the triadic census of a directed graph.

    The triadic census is a count of how many of the 16 possible types of
    triads are present in a directed graph. If a list of nodes is passed, then
    only those triads are taken into account which have elements of nodelist in them.

    Parameters
    ----------
    G : digraph
       A NetworkX DiGraph
    nodelist : list
        List of nodes for which you want to calculate triadic census

    Returns
    -------
    census : dict
       Dictionary with triad type as keys and number of occurrences as values.

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 1), (3, 4), (4, 1), (4, 2)])
    >>> triadic_census = nx.triadic_census(G)
    >>> for key, value in triadic_census.items():
    ...     print(f"{key}: {value}")
    003: 0
    012: 0
    102: 0
    021D: 0
    021U: 0
    021C: 0
    111D: 0
    111U: 0
    030T: 2
    030C: 2
    201: 0
    120D: 0
    120U: 0
    120C: 0
    210: 0
    300: 0

    Notes
    -----
    This algorithm has complexity $O(m)$ where $m$ is the number of edges in
    the graph.

    For undirected graphs, the triadic census can be computed by first converting
    the graph into a directed graph using the ``G.to_directed()`` method.
    After this conversion, only the triad types 003, 102, 201 and 300 will be
    present in the undirected scenario.

    Raises
    ------
    ValueError
        If `nodelist` contains duplicate nodes or nodes not in `G`.
        If you want to ignore this you can preprocess with `set(nodelist) & G.nodes`

    See also
    --------
    triad_graph

    References
    ----------
    .. [1] Vladimir Batagelj and Andrej Mrvar, A subquadratic triad census
        algorithm for large sparse networks with small maximum degree,
        University of Ljubljana,
        http://vlado.fmf.uni-lj.si/pub/networks/doc/triads/triads.pdf
networkx.triads
Python Library Documentation: module networkx.algorithms.triads in networkx.algorithms

NAME
    networkx.algorithms.triads - Functions for analyzing triads of a graph.

FUNCTIONS
    all_triads(G, *, backend=None, **backend_kwargs)
        A generator of all possible triads in G.

        Parameters
        ----------
        G : digraph
           A NetworkX DiGraph

        Returns
        -------
        all_triads : generator of DiGraphs
           Generator of triads (order-3 DiGraphs)

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 1), (3, 4), (4, 1), (4, 2)])
        >>> for triad in nx.all_triads(G):
        ...     print(triad.edges)
        [(1, 2), (2, 3), (3, 1)]
        [(1, 2), (4, 1), (4, 2)]
        [(3, 1), (3, 4), (4, 1)]
        [(2, 3), (3, 4), (4, 2)]

    all_triplets(G, *, backend=None, **backend_kwargs)
        Returns a generator of all possible sets of 3 nodes in a DiGraph.

        .. deprecated:: 3.3

           all_triplets is deprecated and will be removed in NetworkX version 3.5.
           Use `itertools.combinations` instead::

              all_triplets = itertools.combinations(G, 3)

        Parameters
        ----------
        G : digraph
           A NetworkX DiGraph

        Returns
        -------
        triplets : generator of 3-tuples
           Generator of tuples of 3 nodes

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 4)])
        >>> list(nx.all_triplets(G))
        [(1, 2, 3), (1, 2, 4), (1, 3, 4), (2, 3, 4)]

    is_triad(G, *, backend=None, **backend_kwargs)
        Returns True if the graph G is a triad, else False.

        Parameters
        ----------
        G : graph
           A NetworkX Graph

        Returns
        -------
        istriad : boolean
           Whether G is a valid triad

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 1)])
        >>> nx.is_triad(G)
        True
        >>> G.add_edge(0, 1)
        >>> nx.is_triad(G)
        False

    random_triad(G, seed=None, *, backend=None, **backend_kwargs)
        Returns a random triad from a directed graph.

        .. deprecated:: 3.3

           random_triad is deprecated and will be removed in version 3.5.
           Use random sampling directly instead::

              G.subgraph(random.sample(list(G), 3))

        Parameters
        ----------
        G : digraph
           A NetworkX DiGraph
        seed : integer, random_state, or None (default)
            Indicator of random number generation state.
            See :ref:`Randomness<randomness>`.

        Returns
        -------
        G2 : subgraph
           A randomly selected triad (order-3 NetworkX DiGraph)

        Raises
        ------
        NetworkXError
            If the input Graph has less than 3 nodes.

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (1, 3), (2, 3), (3, 1), (5, 6), (5, 4), (6, 7)])
        >>> triad = nx.random_triad(G, seed=1)
        >>> triad.edges
        OutEdgeView([(1, 2)])

    triad_type(G, *, backend=None, **backend_kwargs)
        Returns the sociological triad type for a triad.

        Parameters
        ----------
        G : digraph
           A NetworkX DiGraph with 3 nodes

        Returns
        -------
        triad_type : str
           A string identifying the triad type

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 1)])
        >>> nx.triad_type(G)
        '030C'
        >>> G.add_edge(1, 3)
        >>> nx.triad_type(G)
        '120C'

        Notes
        -----
        There can be 6 unique edges in a triad (order-3 DiGraph) (so 2^^6=64 unique
        triads given 3 nodes). These 64 triads each display exactly 1 of 16
        topologies of triads (topologies can be permuted). These topologies are
        identified by the following notation:

        {m}{a}{n}{type} (for example: 111D, 210, 102)

        Here:

        {m}     = number of mutual ties (takes 0, 1, 2, 3); a mutual tie is (0,1)
                  AND (1,0)
        {a}     = number of asymmetric ties (takes 0, 1, 2, 3); an asymmetric tie
                  is (0,1) BUT NOT (1,0) or vice versa
        {n}     = number of null ties (takes 0, 1, 2, 3); a null tie is NEITHER
                  (0,1) NOR (1,0)
        {type}  = a letter (takes U, D, C, T) corresponding to up, down, cyclical
                  and transitive. This is only used for topologies that can have
                  more than one form (eg: 021D and 021U).

        References
        ----------
        .. [1] Snijders, T. (2012). "Transitivity and triads." University of
            Oxford.
            https://web.archive.org/web/20170830032057/http://www.stats.ox.ac.uk/~snijders/Trans_Triads_ha.pdf

    triadic_census(G, nodelist=None, *, backend=None, **backend_kwargs)
        Determines the triadic census of a directed graph.

        The triadic census is a count of how many of the 16 possible types of
        triads are present in a directed graph. If a list of nodes is passed, then
        only those triads are taken into account which have elements of nodelist in them.

        Parameters
        ----------
        G : digraph
           A NetworkX DiGraph
        nodelist : list
            List of nodes for which you want to calculate triadic census

        Returns
        -------
        census : dict
           Dictionary with triad type as keys and number of occurrences as values.

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (2, 3), (3, 1), (3, 4), (4, 1), (4, 2)])
        >>> triadic_census = nx.triadic_census(G)
        >>> for key, value in triadic_census.items():
        ...     print(f"{key}: {value}")
        003: 0
        012: 0
        102: 0
        021D: 0
        021U: 0
        021C: 0
        111D: 0
        111U: 0
        030T: 2
        030C: 2
        201: 0
        120D: 0
        120U: 0
        120C: 0
        210: 0
        300: 0

        Notes
        -----
        This algorithm has complexity $O(m)$ where $m$ is the number of edges in
        the graph.

        For undirected graphs, the triadic census can be computed by first converting
        the graph into a directed graph using the ``G.to_directed()`` method.
        After this conversion, only the triad types 003, 102, 201 and 300 will be
        present in the undirected scenario.

        Raises
        ------
        ValueError
            If `nodelist` contains duplicate nodes or nodes not in `G`.
            If you want to ignore this you can preprocess with `set(nodelist) & G.nodes`

        See also
        --------
        triad_graph

        References
        ----------
        .. [1] Vladimir Batagelj and Andrej Mrvar, A subquadratic triad census
            algorithm for large sparse networks with small maximum degree,
            University of Ljubljana,
            http://vlado.fmf.uni-lj.si/pub/networks/doc/triads/triads.pdf

    triads_by_type(G, *, backend=None, **backend_kwargs)
        Returns a list of all triads for each triad type in a directed graph.
        There are exactly 16 different types of triads possible. Suppose 1, 2, 3 are three
        nodes, they will be classified as a particular triad type if their connections
        are as follows:

        - 003: 1, 2, 3
        - 012: 1 -> 2, 3
        - 102: 1 <-> 2, 3
        - 021D: 1 <- 2 -> 3
        - 021U: 1 -> 2 <- 3
        - 021C: 1 -> 2 -> 3
        - 111D: 1 <-> 2 <- 3
        - 111U: 1 <-> 2 -> 3
        - 030T: 1 -> 2 -> 3, 1 -> 3
        - 030C: 1 <- 2 <- 3, 1 -> 3
        - 201: 1 <-> 2 <-> 3
        - 120D: 1 <- 2 -> 3, 1 <-> 3
        - 120U: 1 -> 2 <- 3, 1 <-> 3
        - 120C: 1 -> 2 -> 3, 1 <-> 3
        - 210: 1 -> 2 <-> 3, 1 <-> 3
        - 300: 1 <-> 2 <-> 3, 1 <-> 3

        Refer to the :doc:`example gallery </auto_examples/graph/plot_triad_types>`
        for visual examples of the triad types.

        Parameters
        ----------
        G : digraph
           A NetworkX DiGraph

        Returns
        -------
        tri_by_type : dict
           Dictionary with triad types as keys and lists of triads as values.

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (1, 3), (2, 3), (3, 1), (5, 6), (5, 4), (6, 7)])
        >>> dict = nx.triads_by_type(G)
        >>> dict["120C"][0].edges()
        OutEdgeView([(1, 2), (1, 3), (2, 3), (3, 1)])
        >>> dict["012"][0].edges()
        OutEdgeView([(1, 2)])

        References
        ----------
        .. [1] Snijders, T. (2012). "Transitivity and triads." University of
            Oxford.
            https://web.archive.org/web/20170830032057/http://www.stats.ox.ac.uk/~snijders/Trans_Triads_ha.pdf

DATA
    __all__ = ['triadic_census', 'is_triad', 'all_triplets', 'all_triads',...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\triads.py

networkx.triads_by_type
Python Library Documentation: function triads_by_type in module networkx.algorithms.triads

triads_by_type(G, *, backend=None, **backend_kwargs)
    Returns a list of all triads for each triad type in a directed graph.
    There are exactly 16 different types of triads possible. Suppose 1, 2, 3 are three
    nodes, they will be classified as a particular triad type if their connections
    are as follows:

    - 003: 1, 2, 3
    - 012: 1 -> 2, 3
    - 102: 1 <-> 2, 3
    - 021D: 1 <- 2 -> 3
    - 021U: 1 -> 2 <- 3
    - 021C: 1 -> 2 -> 3
    - 111D: 1 <-> 2 <- 3
    - 111U: 1 <-> 2 -> 3
    - 030T: 1 -> 2 -> 3, 1 -> 3
    - 030C: 1 <- 2 <- 3, 1 -> 3
    - 201: 1 <-> 2 <-> 3
    - 120D: 1 <- 2 -> 3, 1 <-> 3
    - 120U: 1 -> 2 <- 3, 1 <-> 3
    - 120C: 1 -> 2 -> 3, 1 <-> 3
    - 210: 1 -> 2 <-> 3, 1 <-> 3
    - 300: 1 <-> 2 <-> 3, 1 <-> 3

    Refer to the :doc:`example gallery </auto_examples/graph/plot_triad_types>`
    for visual examples of the triad types.

    Parameters
    ----------
    G : digraph
       A NetworkX DiGraph

    Returns
    -------
    tri_by_type : dict
       Dictionary with triad types as keys and lists of triads as values.

    Examples
    --------
    >>> G = nx.DiGraph([(1, 2), (1, 3), (2, 3), (3, 1), (5, 6), (5, 4), (6, 7)])
    >>> dict = nx.triads_by_type(G)
    >>> dict["120C"][0].edges()
    OutEdgeView([(1, 2), (1, 3), (2, 3), (3, 1)])
    >>> dict["012"][0].edges()
    OutEdgeView([(1, 2)])

    References
    ----------
    .. [1] Snijders, T. (2012). "Transitivity and triads." University of
        Oxford.
        https://web.archive.org/web/20170830032057/http://www.stats.ox.ac.uk/~snijders/Trans_Triads_ha.pdf
networkx.triangles
Python Library Documentation: function triangles in module networkx.algorithms.cluster

triangles(G, nodes=None, *, backend=None, **backend_kwargs)
    Compute the number of triangles.

    Finds the number of triangles that include a node as one vertex.

    Parameters
    ----------
    G : graph
       A networkx graph

    nodes : node, iterable of nodes, or None (default=None)
        If a singleton node, return the number of triangles for that node.
        If an iterable, compute the number of triangles for each of those nodes.
        If `None` (the default) compute the number of triangles for all nodes in `G`.

    Returns
    -------
    out : dict or int
       If `nodes` is a container of nodes, returns number of triangles keyed by node (dict).
       If `nodes` is a specific node, returns number of triangles for the node (int).

    Examples
    --------
    >>> G = nx.complete_graph(5)
    >>> print(nx.triangles(G, 0))
    6
    >>> print(nx.triangles(G))
    {0: 6, 1: 6, 2: 6, 3: 6, 4: 6}
    >>> print(list(nx.triangles(G, [0, 1]).values()))
    [6, 6]

    Notes
    -----
    Self loops are ignored.
networkx.triangular_lattice_graph
Python Library Documentation: function triangular_lattice_graph in module networkx.generators.lattice

triangular_lattice_graph(m, n, periodic=False, with_positions=True, create_using=None, *, backend=None, **backend_kwargs)
    Returns the $m$ by $n$ triangular lattice graph.

    The `triangular lattice graph`_ is a two-dimensional `grid graph`_ in
    which each square unit has a diagonal edge (each grid unit has a chord).

    The returned graph has $m$ rows and $n$ columns of triangles. Rows and
    columns include both triangles pointing up and down. Rows form a strip
    of constant height. Columns form a series of diamond shapes, staggered
    with the columns on either side. Another way to state the size is that
    the nodes form a grid of `m+1` rows and `(n + 1) // 2` columns.
    The odd row nodes are shifted horizontally relative to the even rows.

    Directed graph types have edges pointed up or right.

    Positions of nodes are computed by default or `with_positions is True`.
    The position of each node (embedded in a euclidean plane) is stored in
    the graph using equilateral triangles with sidelength 1.
    The height between rows of nodes is thus $\sqrt(3)/2$.
    Nodes lie in the first quadrant with the node $(0, 0)$ at the origin.

    .. _triangular lattice graph: http://mathworld.wolfram.com/TriangularGrid.html
    .. _grid graph: http://www-cs-students.stanford.edu/~amitp/game-programming/grids/
    .. _Triangular Tiling: https://en.wikipedia.org/wiki/Triangular_tiling

    Parameters
    ----------
    m : int
        The number of rows in the lattice.

    n : int
        The number of columns in the lattice.

    periodic : bool (default: False)
        If True, join the boundary vertices of the grid using periodic
        boundary conditions. The join between boundaries is the final row
        and column of triangles. This means there is one row and one column
        fewer nodes for the periodic lattice. Periodic lattices require
        `m >= 3`, `n >= 5` and are allowed but misaligned if `m` or `n` are odd

    with_positions : bool (default: True)
        Store the coordinates of each node in the graph node attribute 'pos'.
        The coordinates provide a lattice with equilateral triangles.
        Periodic positions shift the nodes vertically in a nonlinear way so
        the edges don't overlap so much.

    create_using : NetworkX graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    NetworkX graph
        The *m* by *n* triangular lattice graph.
networkx.trivial_graph
Python Library Documentation: function trivial_graph in module networkx.generators.classic

trivial_graph(create_using=None, *, backend=None, **backend_kwargs)
    Return the Trivial graph with one node (with label 0) and no edges.

    .. plot::

        >>> nx.draw(nx.trivial_graph(), with_labels=True)
networkx.trophic
Python Library Documentation: module networkx.algorithms.centrality.trophic in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.trophic - Trophic levels

FUNCTIONS
    trophic_differences(G, weight='weight', *, backend=None, **backend_kwargs)
        Compute the trophic differences of the edges of a directed graph.

        The trophic difference $x_ij$ for each edge is defined in Johnson et al.
        [1]_ as:

        .. math::
            x_ij = s_j - s_i

        Where $s_i$ is the trophic level of node $i$.

        Parameters
        ----------
        G : DiGraph
            A directed networkx graph

        Returns
        -------
        diffs : dict
            Dictionary of edges with trophic differences as the value.

        References
        ----------
        .. [1] Samuel Johnson, Virginia Dominguez-Garcia, Luca Donetti, Miguel A.
            Munoz (2014) PNAS "Trophic coherence determines food-web stability"

    trophic_incoherence_parameter(G, weight='weight', cannibalism=False, *, backend=None, **backend_kwargs)
        Compute the trophic incoherence parameter of a graph.

        Trophic coherence is defined as the homogeneity of the distribution of
        trophic distances: the more similar, the more coherent. This is measured by
        the standard deviation of the trophic differences and referred to as the
        trophic incoherence parameter $q$ by [1].

        Parameters
        ----------
        G : DiGraph
            A directed networkx graph

        cannibalism: Boolean
            If set to False, self edges are not considered in the calculation

        Returns
        -------
        trophic_incoherence_parameter : float
            The trophic coherence of a graph

        References
        ----------
        .. [1] Samuel Johnson, Virginia Dominguez-Garcia, Luca Donetti, Miguel A.
            Munoz (2014) PNAS "Trophic coherence determines food-web stability"

    trophic_levels(G, weight='weight', *, backend=None, **backend_kwargs)
        Compute the trophic levels of nodes.

        The trophic level of a node $i$ is

        .. math::

            s_i = 1 + \frac{1}{k^{in}_i} \sum_{j} a_{ij} s_j

        where $k^{in}_i$ is the in-degree of i

        .. math::

            k^{in}_i = \sum_{j} a_{ij}

        and nodes with $k^{in}_i = 0$ have $s_i = 1$ by convention.

        These are calculated using the method outlined in Levine [1]_.

        Parameters
        ----------
        G : DiGraph
            A directed networkx graph

        Returns
        -------
        nodes : dict
            Dictionary of nodes with trophic level as the value.

        References
        ----------
        .. [1] Stephen Levine (1980) J. theor. Biol. 83, 195-207

DATA
    __all__ = ['trophic_levels', 'trophic_differences', 'trophic_incoheren...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\trophic.py

networkx.trophic_differences
Python Library Documentation: function trophic_differences in module networkx.algorithms.centrality.trophic

trophic_differences(G, weight='weight', *, backend=None, **backend_kwargs)
    Compute the trophic differences of the edges of a directed graph.

    The trophic difference $x_ij$ for each edge is defined in Johnson et al.
    [1]_ as:

    .. math::
        x_ij = s_j - s_i

    Where $s_i$ is the trophic level of node $i$.

    Parameters
    ----------
    G : DiGraph
        A directed networkx graph

    Returns
    -------
    diffs : dict
        Dictionary of edges with trophic differences as the value.

    References
    ----------
    .. [1] Samuel Johnson, Virginia Dominguez-Garcia, Luca Donetti, Miguel A.
        Munoz (2014) PNAS "Trophic coherence determines food-web stability"
networkx.trophic_incoherence_parameter
Python Library Documentation: function trophic_incoherence_parameter in module networkx.algorithms.centrality.trophic

trophic_incoherence_parameter(G, weight='weight', cannibalism=False, *, backend=None, **backend_kwargs)
    Compute the trophic incoherence parameter of a graph.

    Trophic coherence is defined as the homogeneity of the distribution of
    trophic distances: the more similar, the more coherent. This is measured by
    the standard deviation of the trophic differences and referred to as the
    trophic incoherence parameter $q$ by [1].

    Parameters
    ----------
    G : DiGraph
        A directed networkx graph

    cannibalism: Boolean
        If set to False, self edges are not considered in the calculation

    Returns
    -------
    trophic_incoherence_parameter : float
        The trophic coherence of a graph

    References
    ----------
    .. [1] Samuel Johnson, Virginia Dominguez-Garcia, Luca Donetti, Miguel A.
        Munoz (2014) PNAS "Trophic coherence determines food-web stability"
networkx.trophic_levels
Python Library Documentation: function trophic_levels in module networkx.algorithms.centrality.trophic

trophic_levels(G, weight='weight', *, backend=None, **backend_kwargs)
    Compute the trophic levels of nodes.

    The trophic level of a node $i$ is

    .. math::

        s_i = 1 + \frac{1}{k^{in}_i} \sum_{j} a_{ij} s_j

    where $k^{in}_i$ is the in-degree of i

    .. math::

        k^{in}_i = \sum_{j} a_{ij}

    and nodes with $k^{in}_i = 0$ have $s_i = 1$ by convention.

    These are calculated using the method outlined in Levine [1]_.

    Parameters
    ----------
    G : DiGraph
        A directed networkx graph

    Returns
    -------
    nodes : dict
        Dictionary of nodes with trophic level as the value.

    References
    ----------
    .. [1] Stephen Levine (1980) J. theor. Biol. 83, 195-207
networkx.truncated_cube_graph
Python Library Documentation: function truncated_cube_graph in module networkx.generators.small

truncated_cube_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the skeleton of the truncated cube.

    The truncated cube is an Archimedean solid with 14 regular
    faces (6 octagonal and 8 triangular), 36 edges and 24 nodes [1]_.
    The truncated cube is created by truncating (cutting off) the tips
    of the cube one third of the way into each edge [2]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Skeleton of the truncated cube

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Truncated_cube
    .. [2] https://www.coolmath.com/reference/polyhedra-truncated-cube
networkx.truncated_tetrahedron_graph
Python Library Documentation: function truncated_tetrahedron_graph in module networkx.generators.small

truncated_tetrahedron_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the skeleton of the truncated Platonic tetrahedron.

    The truncated tetrahedron is an Archimedean solid with 4 regular hexagonal faces,
    4 equilateral triangle faces, 12 nodes and 18 edges. It can be constructed by truncating
    all 4 vertices of a regular tetrahedron at one third of the original edge length [1]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Skeleton of the truncated tetrahedron

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Truncated_tetrahedron
networkx.turan_graph
Python Library Documentation: function turan_graph in module networkx.generators.classic

turan_graph(n, r, *, backend=None, **backend_kwargs)
    Return the Turan Graph

    The Turan Graph is a complete multipartite graph on $n$ nodes
    with $r$ disjoint subsets. That is, edges connect each node to
    every node not in its subset.

    Given $n$ and $r$, we create a complete multipartite graph with
    $r-(n \mod r)$ partitions of size $n/r$, rounded down, and
    $n \mod r$ partitions of size $n/r+1$, rounded down.

    .. plot::

        >>> nx.draw(nx.turan_graph(6, 2))

    Parameters
    ----------
    n : int
        The number of nodes.
    r : int
        The number of partitions.
        Must be less than or equal to n.

    Notes
    -----
    Must satisfy $1 <= r <= n$.
    The graph has $(r-1)(n^2)/(2r)$ edges, rounded down.
networkx.tutte_graph
Python Library Documentation: function tutte_graph in module networkx.generators.small

tutte_graph(create_using=None, *, backend=None, **backend_kwargs)
    Returns the Tutte graph.

    The Tutte graph is a cubic polyhedral, non-Hamiltonian graph. It has
    46 nodes and 69 edges.
    It is a counterexample to Tait's conjecture that every 3-regular polyhedron
    has a Hamiltonian cycle.
    It can be realized geometrically from a tetrahedron by multiply truncating
    three of its vertices [1]_.

    Parameters
    ----------
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Returns
    -------
    G : networkx Graph
        Tutte graph

    References
    ----------
    .. [1] https://en.wikipedia.org/wiki/Tutte_graph
networkx.tutte_polynomial
Python Library Documentation: function tutte_polynomial in module networkx.algorithms.polynomials

tutte_polynomial(G, *, backend=None, **backend_kwargs)
    Returns the Tutte polynomial of `G`

    This function computes the Tutte polynomial via an iterative version of
    the deletion-contraction algorithm.

    The Tutte polynomial `T_G(x, y)` is a fundamental graph polynomial invariant in
    two variables. It encodes a wide array of information related to the
    edge-connectivity of a graph; "Many problems about graphs can be reduced to
    problems of finding and evaluating the Tutte polynomial at certain values" [1]_.
    In fact, every deletion-contraction-expressible feature of a graph is a
    specialization of the Tutte polynomial [2]_ (see Notes for examples).

    There are several equivalent definitions; here are three:

    Def 1 (rank-nullity expansion): For `G` an undirected graph, `n(G)` the
    number of vertices of `G`, `E` the edge set of `G`, `V` the vertex set of
    `G`, and `c(A)` the number of connected components of the graph with vertex
    set `V` and edge set `A` [3]_:

    .. math::

        T_G(x, y) = \sum_{A \in E} (x-1)^{c(A) - c(E)} (y-1)^{c(A) + |A| - n(G)}

    Def 2 (spanning tree expansion): Let `G` be an undirected graph, `T` a spanning
    tree of `G`, and `E` the edge set of `G`. Let `E` have an arbitrary strict
    linear order `L`. Let `B_e` be the unique minimal nonempty edge cut of
    $E \setminus T \cup {e}$. An edge `e` is internally active with respect to
    `T` and `L` if `e` is the least edge in `B_e` according to the linear order
    `L`. The internal activity of `T` (denoted `i(T)`) is the number of edges
    in $E \setminus T$ that are internally active with respect to `T` and `L`.
    Let `P_e` be the unique path in $T \cup {e}$ whose source and target vertex
    are the same. An edge `e` is externally active with respect to `T` and `L`
    if `e` is the least edge in `P_e` according to the linear order `L`. The
    external activity of `T` (denoted `e(T)`) is the number of edges in
    $E \setminus T$ that are externally active with respect to `T` and `L`.
    Then [4]_ [5]_:

    .. math::

        T_G(x, y) = \sum_{T \text{ a spanning tree of } G} x^{i(T)} y^{e(T)}

    Def 3 (deletion-contraction recurrence): For `G` an undirected graph, `G-e`
    the graph obtained from `G` by deleting edge `e`, `G/e` the graph obtained
    from `G` by contracting edge `e`, `k(G)` the number of cut-edges of `G`,
    and `l(G)` the number of self-loops of `G`:

    .. math::
        T_G(x, y) = \begin{cases}
           x^{k(G)} y^{l(G)}, & \text{if all edges are cut-edges or self-loops} \\
           T_{G-e}(x, y) + T_{G/e}(x, y), & \text{otherwise, for an arbitrary edge $e$ not a cut-edge or loop}
        \end{cases}

    Parameters
    ----------
    G : NetworkX graph

    Returns
    -------
    instance of `sympy.core.add.Add`
        A Sympy expression representing the Tutte polynomial for `G`.

    Examples
    --------
    >>> C = nx.cycle_graph(5)
    >>> nx.tutte_polynomial(C)
    x**4 + x**3 + x**2 + x + y

    >>> D = nx.diamond_graph()
    >>> nx.tutte_polynomial(D)
    x**3 + 2*x**2 + 2*x*y + x + y**2 + y

    Notes
    -----
    Some specializations of the Tutte polynomial:

    - `T_G(1, 1)` counts the number of spanning trees of `G`
    - `T_G(1, 2)` counts the number of connected spanning subgraphs of `G`
    - `T_G(2, 1)` counts the number of spanning forests in `G`
    - `T_G(0, 2)` counts the number of strong orientations of `G`
    - `T_G(2, 0)` counts the number of acyclic orientations of `G`

    Edge contraction is defined and deletion-contraction is introduced in [6]_.
    Combinatorial meaning of the coefficients is introduced in [7]_.
    Universality, properties, and applications are discussed in [8]_.

    Practically, up-front computation of the Tutte polynomial may be useful when
    users wish to repeatedly calculate edge-connectivity-related information
    about one or more graphs.

    References
    ----------
    .. [1] M. Brandt,
       "The Tutte Polynomial."
       Talking About Combinatorial Objects Seminar, 2015
       https://math.berkeley.edu/~brandtm/talks/tutte.pdf
    .. [2] A. Björklund, T. Husfeldt, P. Kaski, M. Koivisto,
       "Computing the Tutte polynomial in vertex-exponential time"
       49th Annual IEEE Symposium on Foundations of Computer Science, 2008
       https://ieeexplore.ieee.org/abstract/document/4691000
    .. [3] Y. Shi, M. Dehmer, X. Li, I. Gutman,
       "Graph Polynomials," p. 14
    .. [4] Y. Shi, M. Dehmer, X. Li, I. Gutman,
       "Graph Polynomials," p. 46
    .. [5] A. Nešetril, J. Goodall,
       "Graph invariants, homomorphisms, and the Tutte polynomial"
       https://iuuk.mff.cuni.cz/~andrew/Tutte.pdf
    .. [6] D. B. West,
       "Introduction to Graph Theory," p. 84
    .. [7] G. Coutinho,
       "A brief introduction to the Tutte polynomial"
       Structural Analysis of Complex Networks, 2011
       https://homepages.dcc.ufmg.br/~gabriel/seminars/coutinho_tuttepolynomial_seminar.pdf
    .. [8] J. A. Ellis-Monaghan, C. Merino,
       "Graph polynomials and their applications I: The Tutte polynomial"
       Structural Analysis of Complex Networks, 2011
       https://arxiv.org/pdf/0803.3079.pdf
networkx.unary
Python Library Documentation: module networkx.algorithms.operators.unary in networkx.algorithms.operators

NAME
    networkx.algorithms.operators.unary - Unary operations on graphs

FUNCTIONS
    complement(G, *, backend=None, **backend_kwargs)
        Returns the graph complement of G.

        Parameters
        ----------
        G : graph
           A NetworkX graph

        Returns
        -------
        GC : A new graph.

        Notes
        -----
        Note that `complement` does not create self-loops and also
        does not produce parallel edges for MultiGraphs.

        Graph, node, and edge data are not propagated to the new graph.

        Examples
        --------
        >>> G = nx.Graph([(1, 2), (1, 3), (2, 3), (3, 4), (3, 5)])
        >>> G_complement = nx.complement(G)
        >>> G_complement.edges()  # This shows the edges of the complemented graph
        EdgeView([(1, 4), (1, 5), (2, 4), (2, 5), (4, 5)])

    reverse(G, copy=True, *, backend=None, **backend_kwargs)
        Returns the reverse directed graph of G.

        Parameters
        ----------
        G : directed graph
            A NetworkX directed graph
        copy : bool
            If True, then a new graph is returned. If False, then the graph is
            reversed in place.

        Returns
        -------
        H : directed graph
            The reversed G.

        Raises
        ------
        NetworkXError
            If graph is undirected.

        Examples
        --------
        >>> G = nx.DiGraph([(1, 2), (1, 3), (2, 3), (3, 4), (3, 5)])
        >>> G_reversed = nx.reverse(G)
        >>> G_reversed.edges()
        OutEdgeView([(2, 1), (3, 1), (3, 2), (4, 3), (5, 3)])

DATA
    __all__ = ['complement', 'reverse']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\operators\unary.py

networkx.uniform_random_intersection_graph
Python Library Documentation: function uniform_random_intersection_graph in module networkx.generators.intersection

uniform_random_intersection_graph(n, m, p, seed=None, *, backend=None, **backend_kwargs)
    Returns a uniform random intersection graph.

    Parameters
    ----------
    n : int
        The number of nodes in the first bipartite set (nodes)
    m : int
        The number of nodes in the second bipartite set (attributes)
    p : float
        Probability of connecting nodes between bipartite sets
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.

    See Also
    --------
    gnp_random_graph

    References
    ----------
    .. [1] K.B. Singer-Cohen, Random Intersection Graphs, 1995,
       PhD thesis, Johns Hopkins University
    .. [2] Fill, J. A., Scheinerman, E. R., and Singer-Cohen, K. B.,
       Random intersection graphs when m = !(n):
       An equivalence theorem relating the evolution of the g(n, m, p)
       and g(n, p) models. Random Struct. Algorithms 16, 2 (2000), 156–176.
networkx.union
Python Library Documentation: function union in module networkx.algorithms.operators.binary

union(G, H, rename=(), *, backend=None, **backend_kwargs)
    Combine graphs G and H. The names of nodes must be unique.

    A name collision between the graphs will raise an exception.

    A renaming facility is provided to avoid name collisions.


    Parameters
    ----------
    G, H : graph
       A NetworkX graph

    rename : iterable , optional
       Node names of G and H can be changed by specifying the tuple
       rename=('G-','H-') (for example).  Node "u" in G is then renamed
       "G-u" and "v" in H is renamed "H-v".

    Returns
    -------
    U : A union graph with the same type as G.

    See Also
    --------
    compose
    :func:`~networkx.Graph.update`
    disjoint_union

    Notes
    -----
    To combine graphs that have common nodes, consider compose(G, H)
    or the method, Graph.update().

    disjoint_union() is similar to union() except that it avoids name clashes
    by relabeling the nodes with sequential integers.

    Edge and node attributes are propagated from G and H to the union graph.
    Graph attributes are also propagated, but if they are present in both G and H,
    then the value from H is used.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (1, 2)])
    >>> H = nx.Graph([(0, 1), (0, 3), (1, 3), (1, 2)])
    >>> U = nx.union(G, H, rename=("G", "H"))
    >>> U.nodes
    NodeView(('G0', 'G1', 'G2', 'H0', 'H1', 'H3', 'H2'))
    >>> U.edges
    EdgeView([('G0', 'G1'), ('G0', 'G2'), ('G1', 'G2'), ('H0', 'H1'), ('H0', 'H3'), ('H1', 'H3'), ('H1', 'H2')])
networkx.union_all
Python Library Documentation: function union_all in module networkx.algorithms.operators.all

union_all(graphs, rename=(), *, backend=None, **backend_kwargs)
    Returns the union of all graphs.

    The graphs must be disjoint, otherwise an exception is raised.

    Parameters
    ----------
    graphs : iterable
       Iterable of NetworkX graphs

    rename : iterable , optional
       Node names of graphs can be changed by specifying the tuple
       rename=('G-','H-') (for example).  Node "u" in G is then renamed
       "G-u" and "v" in H is renamed "H-v". Infinite generators (like itertools.count)
       are also supported.

    Returns
    -------
    U : a graph with the same type as the first graph in list

    Raises
    ------
    ValueError
       If `graphs` is an empty list.

    NetworkXError
        In case of mixed type graphs, like MultiGraph and Graph, or directed and undirected graphs.

    Notes
    -----
    For operating on mixed type graphs, they should be converted to the same type.
    >>> G = nx.Graph()
    >>> H = nx.DiGraph()
    >>> GH = union_all([nx.DiGraph(G), H])

    To force a disjoint union with node relabeling, use
    disjoint_union_all(G,H) or convert_node_labels_to integers().

    Graph, edge, and node attributes are propagated to the union graph.
    If a graph attribute is present in multiple graphs, then the value
    from the last graph in the list with that attribute is used.

    Examples
    --------
    >>> G1 = nx.Graph([(1, 2), (2, 3)])
    >>> G2 = nx.Graph([(4, 5), (5, 6)])
    >>> result_graph = nx.union_all([G1, G2])
    >>> result_graph.nodes()
    NodeView((1, 2, 3, 4, 5, 6))
    >>> result_graph.edges()
    EdgeView([(1, 2), (2, 3), (4, 5), (5, 6)])

    See Also
    --------
    union
    disjoint_union_all
networkx.unweighted
Python Library Documentation: module networkx.algorithms.shortest_paths.unweighted in networkx.algorithms.shortest_paths

NAME
    networkx.algorithms.shortest_paths.unweighted - Shortest path algorithms for unweighted graphs.

FUNCTIONS
    all_pairs_shortest_path(G, cutoff=None, *, backend=None, **backend_kwargs)
        Compute shortest paths between all nodes.

        Parameters
        ----------
        G : NetworkX graph

        cutoff : integer, optional
            Depth at which to stop the search. Only paths of length at most
            `cutoff` are returned.

        Returns
        -------
        paths : iterator
            Dictionary, keyed by source and target, of shortest paths.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> path = dict(nx.all_pairs_shortest_path(G))
        >>> print(path[0][4])
        [0, 1, 2, 3, 4]

        Notes
        -----
        There may be multiple shortest paths with the same length between
        two nodes. For each pair, this function returns only one of those paths.

        See Also
        --------
        floyd_warshall
        all_pairs_all_shortest_paths

    all_pairs_shortest_path_length(G, cutoff=None, *, backend=None, **backend_kwargs)
        Computes the shortest path lengths between all nodes in `G`.

        Parameters
        ----------
        G : NetworkX graph

        cutoff : integer, optional
            Depth at which to stop the search. Only paths of length at most
            `cutoff` are returned.

        Returns
        -------
        lengths : iterator
            (source, dictionary) iterator with dictionary keyed by target and
            shortest path length as the key value.

        Notes
        -----
        The iterator returned only has reachable node pairs.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> length = dict(nx.all_pairs_shortest_path_length(G))
        >>> for node in [0, 1, 2, 3, 4]:
        ...     print(f"1 - {node}: {length[1][node]}")
        1 - 0: 1
        1 - 1: 0
        1 - 2: 1
        1 - 3: 2
        1 - 4: 3
        >>> length[3][2]
        1
        >>> length[2][2]
        0

    bidirectional_shortest_path(G, source, target, *, backend=None, **backend_kwargs)
        Returns a list of nodes in a shortest path between source and target.

        Parameters
        ----------
        G : NetworkX graph

        source : node label
           starting node for path

        target : node label
           ending node for path

        Returns
        -------
        path: list
           List of nodes in a path from source to target.

        Raises
        ------
        NetworkXNoPath
           If no path exists between source and target.

        Examples
        --------
        >>> G = nx.Graph()
        >>> nx.add_path(G, [0, 1, 2, 3, 0, 4, 5, 6, 7, 4])
        >>> nx.bidirectional_shortest_path(G, 2, 6)
        [2, 1, 0, 4, 5, 6]

        See Also
        --------
        shortest_path

        Notes
        -----
        This algorithm is used by shortest_path(G, source, target).

    predecessor(G, source, target=None, cutoff=None, return_seen=None, *, backend=None, **backend_kwargs)
        Returns dict of predecessors for the path from source to all nodes in G.

        Parameters
        ----------
        G : NetworkX graph

        source : node label
           Starting node for path

        target : node label, optional
           Ending node for path. If provided only predecessors between
           source and target are returned

        cutoff : integer, optional
            Depth to stop the search. Only paths of length <= cutoff are returned.

        return_seen : bool, optional (default=None)
            Whether to return a dictionary, keyed by node, of the level (number of
            hops) to reach the node (as seen during breadth-first-search).

        Returns
        -------
        pred : dictionary
            Dictionary, keyed by node, of predecessors in the shortest path.


        (pred, seen): tuple of dictionaries
            If `return_seen` argument is set to `True`, then a tuple of dictionaries
            is returned. The first element is the dictionary, keyed by node, of
            predecessors in the shortest path. The second element is the dictionary,
            keyed by node, of the level (number of hops) to reach the node (as seen
            during breadth-first-search).

        Examples
        --------
        >>> G = nx.path_graph(4)
        >>> list(G)
        [0, 1, 2, 3]
        >>> nx.predecessor(G, 0)
        {0: [], 1: [0], 2: [1], 3: [2]}
        >>> nx.predecessor(G, 0, return_seen=True)
        ({0: [], 1: [0], 2: [1], 3: [2]}, {0: 0, 1: 1, 2: 2, 3: 3})

    single_source_shortest_path(G, source, cutoff=None, *, backend=None, **backend_kwargs)
        Compute shortest path between source
        and all other nodes reachable from source.

        Parameters
        ----------
        G : NetworkX graph

        source : node label
           Starting node for path

        cutoff : integer, optional
            Depth to stop the search. Only paths of length <= cutoff are returned.

        Returns
        -------
        paths : dictionary
            Dictionary, keyed by target, of shortest paths.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> path = nx.single_source_shortest_path(G, 0)
        >>> path[4]
        [0, 1, 2, 3, 4]

        Notes
        -----
        The shortest path is not necessarily unique. So there can be multiple
        paths between the source and each target node, all of which have the
        same 'shortest' length. For each target node, this function returns
        only one of those paths.

        See Also
        --------
        shortest_path

    single_source_shortest_path_length(G, source, cutoff=None, *, backend=None, **backend_kwargs)
        Compute the shortest path lengths from source to all reachable nodes.

        Parameters
        ----------
        G : NetworkX graph

        source : node
           Starting node for path

        cutoff : integer, optional
            Depth to stop the search. Only paths of length <= cutoff are returned.

        Returns
        -------
        lengths : dict
            Dict keyed by node to shortest path length to source.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> length = nx.single_source_shortest_path_length(G, 0)
        >>> length[4]
        4
        >>> for node in length:
        ...     print(f"{node}: {length[node]}")
        0: 0
        1: 1
        2: 2
        3: 3
        4: 4

        See Also
        --------
        shortest_path_length

    single_target_shortest_path(G, target, cutoff=None, *, backend=None, **backend_kwargs)
        Compute shortest path to target from all nodes that reach target.

        Parameters
        ----------
        G : NetworkX graph

        target : node label
           Target node for path

        cutoff : integer, optional
            Depth to stop the search. Only paths of length <= cutoff are returned.

        Returns
        -------
        paths : dictionary
            Dictionary, keyed by target, of shortest paths.

        Examples
        --------
        >>> G = nx.path_graph(5, create_using=nx.DiGraph())
        >>> path = nx.single_target_shortest_path(G, 4)
        >>> path[0]
        [0, 1, 2, 3, 4]

        Notes
        -----
        The shortest path is not necessarily unique. So there can be multiple
        paths between the source and each target node, all of which have the
        same 'shortest' length. For each target node, this function returns
        only one of those paths.

        See Also
        --------
        shortest_path, single_source_shortest_path

    single_target_shortest_path_length(G, target, cutoff=None, *, backend=None, **backend_kwargs)
        Compute the shortest path lengths to target from all reachable nodes.

        Parameters
        ----------
        G : NetworkX graph

        target : node
           Target node for path

        cutoff : integer, optional
            Depth to stop the search. Only paths of length <= cutoff are returned.

        Returns
        -------
        lengths : iterator
            (source, shortest path length) iterator

        Examples
        --------
        >>> G = nx.path_graph(5, create_using=nx.DiGraph())
        >>> length = dict(nx.single_target_shortest_path_length(G, 4))
        >>> length[0]
        4
        >>> for node in range(5):
        ...     print(f"{node}: {length[node]}")
        0: 4
        1: 3
        2: 2
        3: 1
        4: 0

        See Also
        --------
        single_source_shortest_path_length, shortest_path_length

DATA
    __all__ = ['bidirectional_shortest_path', 'single_source_shortest_path...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\shortest_paths\unweighted.py

networkx.utils
Python Library Documentation: package networkx.utils in networkx

NAME
    networkx.utils

PACKAGE CONTENTS
    backends
    configs
    decorators
    heaps
    mapped_queue
    misc
    random_sequence
    rcm
    tests (package)
    union_find

DATA
    config = NetworkXConfig(backend_priority=BackendPrioritie..., fallback...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\utils\__init__.py

networkx.vf2pp_all_isomorphisms
Python Library Documentation: function vf2pp_all_isomorphisms in module networkx.algorithms.isomorphism.vf2pp

vf2pp_all_isomorphisms(G1, G2, node_label=None, default_label=None, *, backend=None, **backend_kwargs)
    Yields all the possible mappings between G1 and G2.

    Parameters
    ----------
    G1, G2 : NetworkX Graph or MultiGraph instances.
        The two graphs to check for isomorphism.

    node_label : str, optional
        The name of the node attribute to be used when comparing nodes.
        The default is `None`, meaning node attributes are not considered
        in the comparison. Any node that doesn't have the `node_label`
        attribute uses `default_label` instead.

    default_label : scalar
        Default value to use when a node doesn't have an attribute
        named `node_label`. Default is `None`.

    Yields
    ------
    dict
        Isomorphic mapping between the nodes in `G1` and `G2`.
networkx.vf2pp_is_isomorphic
Python Library Documentation: function vf2pp_is_isomorphic in module networkx.algorithms.isomorphism.vf2pp

vf2pp_is_isomorphic(G1, G2, node_label=None, default_label=None, *, backend=None, **backend_kwargs)
    Examines whether G1 and G2 are isomorphic.

    Parameters
    ----------
    G1, G2 : NetworkX Graph or MultiGraph instances.
        The two graphs to check for isomorphism.

    node_label : str, optional
        The name of the node attribute to be used when comparing nodes.
        The default is `None`, meaning node attributes are not considered
        in the comparison. Any node that doesn't have the `node_label`
        attribute uses `default_label` instead.

    default_label : scalar
        Default value to use when a node doesn't have an attribute
        named `node_label`. Default is `None`.

    Returns
    -------
    bool
        True if the two graphs are isomorphic, False otherwise.
networkx.vf2pp_isomorphism
Python Library Documentation: function vf2pp_isomorphism in module networkx.algorithms.isomorphism.vf2pp

vf2pp_isomorphism(G1, G2, node_label=None, default_label=None, *, backend=None, **backend_kwargs)
    Return an isomorphic mapping between `G1` and `G2` if it exists.

    Parameters
    ----------
    G1, G2 : NetworkX Graph or MultiGraph instances.
        The two graphs to check for isomorphism.

    node_label : str, optional
        The name of the node attribute to be used when comparing nodes.
        The default is `None`, meaning node attributes are not considered
        in the comparison. Any node that doesn't have the `node_label`
        attribute uses `default_label` instead.

    default_label : scalar
        Default value to use when a node doesn't have an attribute
        named `node_label`. Default is `None`.

    Returns
    -------
    dict or None
        Node mapping if the two graphs are isomorphic. None otherwise.
networkx.visibility_graph
Python Library Documentation: function visibility_graph in module networkx.generators.time_series

visibility_graph(series, *, backend=None, **backend_kwargs)
    Return a Visibility Graph of an input Time Series.

    A visibility graph converts a time series into a graph. The constructed graph
    uses integer nodes to indicate which event in the series the node represents.
    Edges are formed as follows: consider a bar plot of the series and view that
    as a side view of a landscape with a node at the top of each bar. An edge
    means that the nodes can be connected by a straight "line-of-sight" without
    being obscured by any bars between the nodes.

    The resulting graph inherits several properties of the series in its structure.
    Thereby, periodic series convert into regular graphs, random series convert
    into random graphs, and fractal series convert into scale-free networks [1]_.

    Parameters
    ----------
    series : Sequence[Number]
       A Time Series sequence (iterable and sliceable) of numeric values
       representing times.

    Returns
    -------
    NetworkX Graph
        The Visibility Graph of the input series

    Examples
    --------
    >>> series_list = [range(10), [2, 1, 3, 2, 1, 3, 2, 1, 3, 2, 1, 3]]
    >>> for s in series_list:
    ...     g = nx.visibility_graph(s)
    ...     print(g)
    Graph with 10 nodes and 9 edges
    Graph with 12 nodes and 18 edges

    References
    ----------
    .. [1] Lacasa, Lucas, Bartolo Luque, Fernando Ballesteros, Jordi Luque, and Juan Carlos Nuno.
           "From time series to complex networks: The visibility graph." Proceedings of the
           National Academy of Sciences 105, no. 13 (2008): 4972-4975.
           https://www.pnas.org/doi/10.1073/pnas.0709247105
networkx.vitality
Python Library Documentation: module networkx.algorithms.vitality in networkx.algorithms

NAME
    networkx.algorithms.vitality - Vitality measures.

FUNCTIONS
    closeness_vitality(G, node=None, weight=None, wiener_index=None, *, backend=None, **backend_kwargs)
        Returns the closeness vitality for nodes in the graph.

        The *closeness vitality* of a node, defined in Section 3.6.2 of [1],
        is the change in the sum of distances between all node pairs when
        excluding that node.

        Parameters
        ----------
        G : NetworkX graph
            A strongly-connected graph.

        weight : string
            The name of the edge attribute used as weight. This is passed
            directly to the :func:`~networkx.wiener_index` function.

        node : object
            If specified, only the closeness vitality for this node will be
            returned. Otherwise, a dictionary mapping each node to its
            closeness vitality will be returned.

        Other parameters
        ----------------
        wiener_index : number
            If you have already computed the Wiener index of the graph
            `G`, you can provide that value here. Otherwise, it will be
            computed for you.

        Returns
        -------
        dictionary or float
            If `node` is None, this function returns a dictionary
            with nodes as keys and closeness vitality as the
            value. Otherwise, it returns only the closeness vitality for the
            specified `node`.

            The closeness vitality of a node may be negative infinity if
            removing that node would disconnect the graph.

        Examples
        --------
        >>> G = nx.cycle_graph(3)
        >>> nx.closeness_vitality(G)
        {0: 2.0, 1: 2.0, 2: 2.0}

        See Also
        --------
        closeness_centrality

        References
        ----------
        .. [1] Ulrik Brandes, Thomas Erlebach (eds.).
               *Network Analysis: Methodological Foundations*.
               Springer, 2005.
               <http://books.google.com/books?id=TTNhSm7HYrIC>

DATA
    __all__ = ['closeness_vitality']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\vitality.py

networkx.volume
Python Library Documentation: function volume in module networkx.algorithms.cuts

volume(G, S, weight=None, *, backend=None, **backend_kwargs)
    Returns the volume of a set of nodes.

    The *volume* of a set *S* is the sum of the (out-)degrees of nodes
    in *S* (taking into account parallel edges in multigraphs). [1]

    Parameters
    ----------
    G : NetworkX graph

    S : collection
        A collection of nodes in `G`.

    weight : object
        Edge attribute key to use as weight. If not specified, edges
        have weight one.

    Returns
    -------
    number
        The volume of the set of nodes represented by `S` in the graph
        `G`.

    See also
    --------
    conductance
    cut_size
    edge_expansion
    edge_boundary
    normalized_cut_size

    References
    ----------
    .. [1] David Gleich.
           *Hierarchical Directed Spectral Graph Partitioning*.
           <https://www.cs.purdue.edu/homes/dgleich/publications/Gleich%202005%20-%20hierarchical%20directed%20spectral.pdf>
networkx.voronoi
Python Library Documentation: module networkx.algorithms.voronoi in networkx.algorithms

NAME
    networkx.algorithms.voronoi - Functions for computing the Voronoi cells of a graph.

FUNCTIONS
    voronoi_cells(G, center_nodes, weight='weight', *, backend=None, **backend_kwargs)
        Returns the Voronoi cells centered at `center_nodes` with respect
        to the shortest-path distance metric.

        If $C$ is a set of nodes in the graph and $c$ is an element of $C$,
        the *Voronoi cell* centered at a node $c$ is the set of all nodes
        $v$ that are closer to $c$ than to any other center node in $C$ with
        respect to the shortest-path distance metric. [1]_

        For directed graphs, this will compute the "outward" Voronoi cells,
        as defined in [1]_, in which distance is measured from the center
        nodes to the target node. For the "inward" Voronoi cells, use the
        :meth:`DiGraph.reverse` method to reverse the orientation of the
        edges before invoking this function on the directed graph.

        Parameters
        ----------
        G : NetworkX graph

        center_nodes : set
            A nonempty set of nodes in the graph `G` that represent the
            center of the Voronoi cells.

        weight : string or function
            The edge attribute (or an arbitrary function) representing the
            weight of an edge. This keyword argument is as described in the
            documentation for :func:`~networkx.multi_source_dijkstra_path`,
            for example.

        Returns
        -------
        dictionary
            A mapping from center node to set of all nodes in the graph
            closer to that center node than to any other center node. The
            keys of the dictionary are the element of `center_nodes`, and
            the values of the dictionary form a partition of the nodes of
            `G`.

        Examples
        --------
        To get only the partition of the graph induced by the Voronoi cells,
        take the collection of all values in the returned dictionary::

            >>> G = nx.path_graph(6)
            >>> center_nodes = {0, 3}
            >>> cells = nx.voronoi_cells(G, center_nodes)
            >>> partition = set(map(frozenset, cells.values()))
            >>> sorted(map(sorted, partition))
            [[0, 1], [2, 3, 4, 5]]

        Raises
        ------
        ValueError
            If `center_nodes` is empty.

        References
        ----------
        .. [1] Erwig, Martin. (2000),"The graph Voronoi diagram with applications."
            *Networks*, 36: 156--163.
            https://doi.org/10.1002/1097-0037(200010)36:3<156::AID-NET2>3.0.CO;2-L

DATA
    __all__ = ['voronoi_cells']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\voronoi.py

networkx.voronoi_cells
Python Library Documentation: function voronoi_cells in module networkx.algorithms.voronoi

voronoi_cells(G, center_nodes, weight='weight', *, backend=None, **backend_kwargs)
    Returns the Voronoi cells centered at `center_nodes` with respect
    to the shortest-path distance metric.

    If $C$ is a set of nodes in the graph and $c$ is an element of $C$,
    the *Voronoi cell* centered at a node $c$ is the set of all nodes
    $v$ that are closer to $c$ than to any other center node in $C$ with
    respect to the shortest-path distance metric. [1]_

    For directed graphs, this will compute the "outward" Voronoi cells,
    as defined in [1]_, in which distance is measured from the center
    nodes to the target node. For the "inward" Voronoi cells, use the
    :meth:`DiGraph.reverse` method to reverse the orientation of the
    edges before invoking this function on the directed graph.

    Parameters
    ----------
    G : NetworkX graph

    center_nodes : set
        A nonempty set of nodes in the graph `G` that represent the
        center of the Voronoi cells.

    weight : string or function
        The edge attribute (or an arbitrary function) representing the
        weight of an edge. This keyword argument is as described in the
        documentation for :func:`~networkx.multi_source_dijkstra_path`,
        for example.

    Returns
    -------
    dictionary
        A mapping from center node to set of all nodes in the graph
        closer to that center node than to any other center node. The
        keys of the dictionary are the element of `center_nodes`, and
        the values of the dictionary form a partition of the nodes of
        `G`.

    Examples
    --------
    To get only the partition of the graph induced by the Voronoi cells,
    take the collection of all values in the returned dictionary::

        >>> G = nx.path_graph(6)
        >>> center_nodes = {0, 3}
        >>> cells = nx.voronoi_cells(G, center_nodes)
        >>> partition = set(map(frozenset, cells.values()))
        >>> sorted(map(sorted, partition))
        [[0, 1], [2, 3, 4, 5]]

    Raises
    ------
    ValueError
        If `center_nodes` is empty.

    References
    ----------
    .. [1] Erwig, Martin. (2000),"The graph Voronoi diagram with applications."
        *Networks*, 36: 156--163.
        https://doi.org/10.1002/1097-0037(200010)36:3<156::AID-NET2>3.0.CO;2-L
networkx.voterank
Python Library Documentation: function voterank in module networkx.algorithms.centrality.voterank_alg

voterank(G, number_of_nodes=None, *, backend=None, **backend_kwargs)
    Select a list of influential nodes in a graph using VoteRank algorithm

    VoteRank [1]_ computes a ranking of the nodes in a graph G based on a
    voting scheme. With VoteRank, all nodes vote for each of its in-neighbors
    and the node with the highest votes is elected iteratively. The voting
    ability of out-neighbors of elected nodes is decreased in subsequent turns.

    Parameters
    ----------
    G : graph
        A NetworkX graph.

    number_of_nodes : integer, optional
        Number of ranked nodes to extract (default all nodes).

    Returns
    -------
    voterank : list
        Ordered list of computed seeds.
        Only nodes with positive number of votes are returned.

    Examples
    --------
    >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 4)])
    >>> nx.voterank(G)
    [0, 1]

    The algorithm can be used both for undirected and directed graphs.
    However, the directed version is different in two ways:
    (i) nodes only vote for their in-neighbors and
    (ii) only the voting ability of elected node and its out-neighbors are updated:

    >>> G = nx.DiGraph([(0, 1), (2, 1), (2, 3), (3, 4)])
    >>> nx.voterank(G)
    [2, 3]

    Notes
    -----
    Each edge is treated independently in case of multigraphs.

    References
    ----------
    .. [1] Zhang, J.-X. et al. (2016).
        Identifying a set of influential spreaders in complex networks.
        Sci. Rep. 6, 27823; doi: 10.1038/srep27823.
networkx.voterank_alg
Python Library Documentation: module networkx.algorithms.centrality.voterank_alg in networkx.algorithms.centrality

NAME
    networkx.algorithms.centrality.voterank_alg - Algorithm to select influential nodes in a graph using VoteRank.

FUNCTIONS
    voterank(G, number_of_nodes=None, *, backend=None, **backend_kwargs)
        Select a list of influential nodes in a graph using VoteRank algorithm

        VoteRank [1]_ computes a ranking of the nodes in a graph G based on a
        voting scheme. With VoteRank, all nodes vote for each of its in-neighbors
        and the node with the highest votes is elected iteratively. The voting
        ability of out-neighbors of elected nodes is decreased in subsequent turns.

        Parameters
        ----------
        G : graph
            A NetworkX graph.

        number_of_nodes : integer, optional
            Number of ranked nodes to extract (default all nodes).

        Returns
        -------
        voterank : list
            Ordered list of computed seeds.
            Only nodes with positive number of votes are returned.

        Examples
        --------
        >>> G = nx.Graph([(0, 1), (0, 2), (0, 3), (1, 4)])
        >>> nx.voterank(G)
        [0, 1]

        The algorithm can be used both for undirected and directed graphs.
        However, the directed version is different in two ways:
        (i) nodes only vote for their in-neighbors and
        (ii) only the voting ability of elected node and its out-neighbors are updated:

        >>> G = nx.DiGraph([(0, 1), (2, 1), (2, 3), (3, 4)])
        >>> nx.voterank(G)
        [2, 3]

        Notes
        -----
        Each edge is treated independently in case of multigraphs.

        References
        ----------
        .. [1] Zhang, J.-X. et al. (2016).
            Identifying a set of influential spreaders in complex networks.
            Sci. Rep. 6, 27823; doi: 10.1038/srep27823.

DATA
    __all__ = ['voterank']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\centrality\voterank_alg.py

networkx.walks
Python Library Documentation: module networkx.algorithms.walks in networkx.algorithms

NAME
    networkx.algorithms.walks - Function for computing walks in a graph.

FUNCTIONS
    number_of_walks(G, walk_length, *, backend=None, **backend_kwargs)
        Returns the number of walks connecting each pair of nodes in `G`

        A *walk* is a sequence of nodes in which each adjacent pair of nodes
        in the sequence is adjacent in the graph. A walk can repeat the same
        edge and go in the opposite direction just as people can walk on a
        set of paths, but standing still is not counted as part of the walk.

        This function only counts the walks with `walk_length` edges. Note that
        the number of nodes in the walk sequence is one more than `walk_length`.
        The number of walks can grow very quickly on a larger graph
        and with a larger walk length.

        Parameters
        ----------
        G : NetworkX graph

        walk_length : int
            A nonnegative integer representing the length of a walk.

        Returns
        -------
        dict
            A dictionary of dictionaries in which outer keys are source
            nodes, inner keys are target nodes, and inner values are the
            number of walks of length `walk_length` connecting those nodes.

        Raises
        ------
        ValueError
            If `walk_length` is negative

        Examples
        --------

        >>> G = nx.Graph([(0, 1), (1, 2)])
        >>> walks = nx.number_of_walks(G, 2)
        >>> walks
        {0: {0: 1, 1: 0, 2: 1}, 1: {0: 0, 1: 2, 2: 0}, 2: {0: 1, 1: 0, 2: 1}}
        >>> total_walks = sum(sum(tgts.values()) for _, tgts in walks.items())

        You can also get the number of walks from a specific source node using the
        returned dictionary. For example, number of walks of length 1 from node 0
        can be found as follows:

        >>> walks = nx.number_of_walks(G, 1)
        >>> walks[0]
        {0: 0, 1: 1, 2: 0}
        >>> sum(walks[0].values())  # walks from 0 of length 1
        1

        Similarly, a target node can also be specified:

        >>> walks[0][1]
        1

DATA
    __all__ = ['number_of_walks']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\walks.py

networkx.watts_strogatz_graph
Python Library Documentation: function watts_strogatz_graph in module networkx.generators.random_graphs

watts_strogatz_graph(n, k, p, seed=None, *, create_using=None, backend=None, **backend_kwargs)
    Returns a Watts–Strogatz small-world graph.

    Parameters
    ----------
    n : int
        The number of nodes
    k : int
        Each node is joined with its `k` nearest neighbors in a ring
        topology.
    p : float
        The probability of rewiring each edge
    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    create_using : Graph constructor, optional (default=nx.Graph)
        Graph type to create. If graph instance, then cleared before populated.
        Multigraph and directed types are not supported and raise a ``NetworkXError``.

    See Also
    --------
    newman_watts_strogatz_graph
    connected_watts_strogatz_graph

    Notes
    -----
    First create a ring over $n$ nodes [1]_.  Then each node in the ring is joined
    to its $k$ nearest neighbors (or $k - 1$ neighbors if $k$ is odd).
    Then shortcuts are created by replacing some edges as follows: for each
    edge $(u, v)$ in the underlying "$n$-ring with $k$ nearest neighbors"
    with probability $p$ replace it with a new edge $(u, w)$ with uniformly
    random choice of existing node $w$.

    In contrast with :func:`newman_watts_strogatz_graph`, the random rewiring
    does not increase the number of edges. The rewired graph is not guaranteed
    to be connected as in :func:`connected_watts_strogatz_graph`.

    References
    ----------
    .. [1] Duncan J. Watts and Steven H. Strogatz,
       Collective dynamics of small-world networks,
       Nature, 393, pp. 440--442, 1998.
networkx.waxman_graph
Python Library Documentation: function waxman_graph in module networkx.generators.geometric

waxman_graph(n, beta=0.4, alpha=0.1, L=None, domain=(0, 0, 1, 1), metric=None, seed=None, *, pos_name='pos', backend=None, **backend_kwargs)
    Returns a Waxman random graph.

    The Waxman random graph model places `n` nodes uniformly at random
    in a rectangular domain. Each pair of nodes at distance `d` is
    joined by an edge with probability

    .. math::
            p = \beta \exp(-d / \alpha L).

    This function implements both Waxman models, using the `L` keyword
    argument.

    * Waxman-1: if `L` is not specified, it is set to be the maximum distance
      between any pair of nodes.
    * Waxman-2: if `L` is specified, the distance between a pair of nodes is
      chosen uniformly at random from the interval `[0, L]`.

    Parameters
    ----------
    n : int or iterable
        Number of nodes or iterable of nodes
    beta: float
        Model parameter
    alpha: float
        Model parameter
    L : float, optional
        Maximum distance between nodes.  If not specified, the actual distance
        is calculated.
    domain : four-tuple of numbers, optional
        Domain size, given as a tuple of the form `(x_min, y_min, x_max,
        y_max)`.
    metric : function
        A metric on vectors of numbers (represented as lists or
        tuples). This must be a function that accepts two lists (or
        tuples) as input and yields a number as output. The function
        must also satisfy the four requirements of a `metric`_.
        Specifically, if $d$ is the function and $x$, $y$,
        and $z$ are vectors in the graph, then $d$ must satisfy

        1. $d(x, y) \ge 0$,
        2. $d(x, y) = 0$ if and only if $x = y$,
        3. $d(x, y) = d(y, x)$,
        4. $d(x, z) \le d(x, y) + d(y, z)$.

        If this argument is not specified, the Euclidean distance metric is
        used.

        .. _metric: https://en.wikipedia.org/wiki/Metric_%28mathematics%29

    seed : integer, random_state, or None (default)
        Indicator of random number generation state.
        See :ref:`Randomness<randomness>`.
    pos_name : string, default="pos"
        The name of the node attribute which represents the position
        in 2D coordinates of the node in the returned graph.

    Returns
    -------
    Graph
        A random Waxman graph, undirected and without self-loops. Each
        node has a node attribute ``'pos'`` that stores the position of
        that node in Euclidean space as generated by this function.

    Examples
    --------
    Specify an alternate distance metric using the ``metric`` keyword
    argument. For example, to use the "`taxicab metric`_" instead of the
    default `Euclidean metric`_::

        >>> dist = lambda x, y: sum(abs(a - b) for a, b in zip(x, y))
        >>> G = nx.waxman_graph(10, 0.5, 0.1, metric=dist)

    .. _taxicab metric: https://en.wikipedia.org/wiki/Taxicab_geometry
    .. _Euclidean metric: https://en.wikipedia.org/wiki/Euclidean_distance

    Notes
    -----
    Starting in NetworkX 2.0 the parameters alpha and beta align with their
    usual roles in the probability distribution. In earlier versions their
    positions in the expression were reversed. Their position in the calling
    sequence reversed as well to minimize backward incompatibility.

    References
    ----------
    .. [1]  B. M. Waxman, *Routing of multipoint connections*.
       IEEE J. Select. Areas Commun. 6(9),(1988) 1617--1622.
networkx.weakly_connected
Python Library Documentation: module networkx.algorithms.components.weakly_connected in networkx.algorithms.components

NAME
    networkx.algorithms.components.weakly_connected - Weakly connected components.

FUNCTIONS
    is_weakly_connected(G, *, backend=None, **backend_kwargs)
        Test directed graph for weak connectivity.

        A directed graph is weakly connected if and only if the graph
        is connected when the direction of the edge between nodes is ignored.

        Note that if a graph is strongly connected (i.e. the graph is connected
        even when we account for directionality), it is by definition weakly
        connected as well.

        Parameters
        ----------
        G : NetworkX Graph
            A directed graph.

        Returns
        -------
        connected : bool
            True if the graph is weakly connected, False otherwise.

        Raises
        ------
        NetworkXNotImplemented
            If G is undirected.

        Examples
        --------
        >>> G = nx.DiGraph([(0, 1), (2, 1)])
        >>> G.add_node(3)
        >>> nx.is_weakly_connected(G)  # node 3 is not connected to the graph
        False
        >>> G.add_edge(2, 3)
        >>> nx.is_weakly_connected(G)
        True

        See Also
        --------
        is_strongly_connected
        is_semiconnected
        is_connected
        is_biconnected
        weakly_connected_components

        Notes
        -----
        For directed graphs only.

    number_weakly_connected_components(G, *, backend=None, **backend_kwargs)
        Returns the number of weakly connected components in G.

        Parameters
        ----------
        G : NetworkX graph
            A directed graph.

        Returns
        -------
        n : integer
            Number of weakly connected components

        Raises
        ------
        NetworkXNotImplemented
            If G is undirected.

        Examples
        --------
        >>> G = nx.DiGraph([(0, 1), (2, 1), (3, 4)])
        >>> nx.number_weakly_connected_components(G)
        2

        See Also
        --------
        weakly_connected_components
        number_connected_components
        number_strongly_connected_components

        Notes
        -----
        For directed graphs only.

    weakly_connected_components(G, *, backend=None, **backend_kwargs)
        Generate weakly connected components of G.

        Parameters
        ----------
        G : NetworkX graph
            A directed graph

        Returns
        -------
        comp : generator of sets
            A generator of sets of nodes, one for each weakly connected
            component of G.

        Raises
        ------
        NetworkXNotImplemented
            If G is undirected.

        Examples
        --------
        Generate a sorted list of weakly connected components, largest first.

        >>> G = nx.path_graph(4, create_using=nx.DiGraph())
        >>> nx.add_path(G, [10, 11, 12])
        >>> [
        ...     len(c)
        ...     for c in sorted(nx.weakly_connected_components(G), key=len, reverse=True)
        ... ]
        [4, 3]

        If you only want the largest component, it's more efficient to
        use max instead of sort:

        >>> largest_cc = max(nx.weakly_connected_components(G), key=len)

        See Also
        --------
        connected_components
        strongly_connected_components

        Notes
        -----
        For directed graphs only.

DATA
    __all__ = ['number_weakly_connected_components', 'weakly_connected_com...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\components\weakly_connected.py

networkx.weakly_connected_components
Python Library Documentation: function weakly_connected_components in module networkx.algorithms.components.weakly_connected

weakly_connected_components(G, *, backend=None, **backend_kwargs)
    Generate weakly connected components of G.

    Parameters
    ----------
    G : NetworkX graph
        A directed graph

    Returns
    -------
    comp : generator of sets
        A generator of sets of nodes, one for each weakly connected
        component of G.

    Raises
    ------
    NetworkXNotImplemented
        If G is undirected.

    Examples
    --------
    Generate a sorted list of weakly connected components, largest first.

    >>> G = nx.path_graph(4, create_using=nx.DiGraph())
    >>> nx.add_path(G, [10, 11, 12])
    >>> [
    ...     len(c)
    ...     for c in sorted(nx.weakly_connected_components(G), key=len, reverse=True)
    ... ]
    [4, 3]

    If you only want the largest component, it's more efficient to
    use max instead of sort:

    >>> largest_cc = max(nx.weakly_connected_components(G), key=len)

    See Also
    --------
    connected_components
    strongly_connected_components

    Notes
    -----
    For directed graphs only.
networkx.weighted
Python Library Documentation: module networkx.algorithms.shortest_paths.weighted in networkx.algorithms.shortest_paths

NAME
    networkx.algorithms.shortest_paths.weighted - Shortest path algorithms for weighted graphs.

FUNCTIONS
    all_pairs_bellman_ford_path(G, weight='weight', *, backend=None, **backend_kwargs)
        Compute shortest paths between all nodes in a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        weight : string or function (default="weight")
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

        Returns
        -------
        paths : iterator
            (source, dictionary) iterator with dictionary keyed by target and
            shortest path as the key value.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> path = dict(nx.all_pairs_bellman_ford_path(G))
        >>> path[0][4]
        [0, 1, 2, 3, 4]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        See Also
        --------
        floyd_warshall, all_pairs_dijkstra_path

    all_pairs_bellman_ford_path_length(G, weight='weight', *, backend=None, **backend_kwargs)
        Compute shortest path lengths between all nodes in a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        weight : string or function (default="weight")
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

        Returns
        -------
        distance : iterator
            (source, dictionary) iterator with dictionary keyed by target and
            shortest path length as the key value.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> length = dict(nx.all_pairs_bellman_ford_path_length(G))
        >>> for node in [0, 1, 2, 3, 4]:
        ...     print(f"1 - {node}: {length[1][node]}")
        1 - 0: 1
        1 - 1: 0
        1 - 2: 1
        1 - 3: 2
        1 - 4: 3
        >>> length[3][2]
        1
        >>> length[2][2]
        0

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The dictionary returned only has keys for reachable node pairs.

    all_pairs_dijkstra(G, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
        Find shortest weighted paths and lengths between all nodes.

        Parameters
        ----------
        G : NetworkX graph

        cutoff : integer or float, optional
            Length (sum of edge weights) at which the search is stopped.
            If cutoff is provided, only return paths with summed weight <= cutoff.

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edge[u][v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Yields
        ------
        (node, (distance, path)) : (node obj, (dict, dict))
            Each source node has two associated dicts. The first holds distance
            keyed by target and the second holds paths keyed by target.
            (See single_source_dijkstra for the source/target node terminology.)
            If desired you can apply `dict()` to this function to create a dict
            keyed by source node to the two dicts.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> len_path = dict(nx.all_pairs_dijkstra(G))
        >>> len_path[3][0][1]
        2
        >>> for node in [0, 1, 2, 3, 4]:
        ...     print(f"3 - {node}: {len_path[3][0][node]}")
        3 - 0: 3
        3 - 1: 2
        3 - 2: 1
        3 - 3: 0
        3 - 4: 1
        >>> len_path[3][1][1]
        [3, 2, 1]
        >>> for n, (dist, path) in nx.all_pairs_dijkstra(G):
        ...     print(path[1])
        [0, 1]
        [1]
        [2, 1]
        [3, 2, 1]
        [4, 3, 2, 1]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The yielded dicts only have keys for reachable nodes.

    all_pairs_dijkstra_path(G, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
        Compute shortest paths between all nodes in a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        cutoff : integer or float, optional
            Length (sum of edge weights) at which the search is stopped.
            If cutoff is provided, only return paths with summed weight <= cutoff.

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Returns
        -------
        paths : iterator
            (source, dictionary) iterator with dictionary keyed by target and
            shortest path as the key value.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> path = dict(nx.all_pairs_dijkstra_path(G))
        >>> path[0][4]
        [0, 1, 2, 3, 4]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        See Also
        --------
        floyd_warshall, all_pairs_bellman_ford_path

    all_pairs_dijkstra_path_length(G, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
        Compute shortest path lengths between all nodes in a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        cutoff : integer or float, optional
            Length (sum of edge weights) at which the search is stopped.
            If cutoff is provided, only return paths with summed weight <= cutoff.

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Returns
        -------
        distance : iterator
            (source, dictionary) iterator with dictionary keyed by target and
            shortest path length as the key value.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> length = dict(nx.all_pairs_dijkstra_path_length(G))
        >>> for node in [0, 1, 2, 3, 4]:
        ...     print(f"1 - {node}: {length[1][node]}")
        1 - 0: 1
        1 - 1: 0
        1 - 2: 1
        1 - 3: 2
        1 - 4: 3
        >>> length[3][2]
        1
        >>> length[2][2]
        0

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The dictionary returned only has keys for reachable node pairs.

    bellman_ford_path(G, source, target, weight='weight', *, backend=None, **backend_kwargs)
        Returns the shortest path from source to target in a weighted graph G.

        Parameters
        ----------
        G : NetworkX graph

        source : node
            Starting node

        target : node
            Ending node

        weight : string or function (default="weight")
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

        Returns
        -------
        path : list
            List of nodes in a shortest path.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        NetworkXNoPath
            If no path exists between source and target.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> nx.bellman_ford_path(G, 0, 4)
        [0, 1, 2, 3, 4]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        See Also
        --------
        dijkstra_path, bellman_ford_path_length

    bellman_ford_path_length(G, source, target, weight='weight', *, backend=None, **backend_kwargs)
        Returns the shortest path length from source to target
        in a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        source : node label
            starting node for path

        target : node label
            ending node for path

        weight : string or function (default="weight")
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

        Returns
        -------
        length : number
            Shortest path length.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        NetworkXNoPath
            If no path exists between source and target.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> nx.bellman_ford_path_length(G, 0, 4)
        4

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        See Also
        --------
        dijkstra_path_length, bellman_ford_path

    bellman_ford_predecessor_and_distance(G, source, target=None, weight='weight', heuristic=False, *, backend=None, **backend_kwargs)
        Compute shortest path lengths and predecessors on shortest paths
        in weighted graphs.

        The algorithm has a running time of $O(mn)$ where $n$ is the number of
        nodes and $m$ is the number of edges.  It is slower than Dijkstra but
        can handle negative edge weights.

        If a negative cycle is detected, you can use :func:`find_negative_cycle`
        to return the cycle and examine it. Shortest paths are not defined when
        a negative cycle exists because once reached, the path can cycle forever
        to build up arbitrarily low weights.

        Parameters
        ----------
        G : NetworkX graph
            The algorithm works for all types of graphs, including directed
            graphs and multigraphs.

        source: node label
            Starting node for path

        target : node label, optional
            Ending node for path

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

        heuristic : bool
            Determines whether to use a heuristic to early detect negative
            cycles at a hopefully negligible cost.

        Returns
        -------
        pred, dist : dictionaries
            Returns two dictionaries keyed by node to predecessor in the
            path and to the distance from the source respectively.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        NetworkXUnbounded
            If the (di)graph contains a negative (di)cycle, the
            algorithm raises an exception to indicate the presence of the
            negative (di)cycle.  Note: any negative weight edge in an
            undirected graph is a negative cycle.

        Examples
        --------
        >>> G = nx.path_graph(5, create_using=nx.DiGraph())
        >>> pred, dist = nx.bellman_ford_predecessor_and_distance(G, 0)
        >>> sorted(pred.items())
        [(0, []), (1, [0]), (2, [1]), (3, [2]), (4, [3])]
        >>> sorted(dist.items())
        [(0, 0), (1, 1), (2, 2), (3, 3), (4, 4)]

        >>> pred, dist = nx.bellman_ford_predecessor_and_distance(G, 0, 1)
        >>> sorted(pred.items())
        [(0, []), (1, [0]), (2, [1]), (3, [2]), (4, [3])]
        >>> sorted(dist.items())
        [(0, 0), (1, 1), (2, 2), (3, 3), (4, 4)]

        >>> G = nx.cycle_graph(5, create_using=nx.DiGraph())
        >>> G[1][2]["weight"] = -7
        >>> nx.bellman_ford_predecessor_and_distance(G, 0)
        Traceback (most recent call last):
            ...
        networkx.exception.NetworkXUnbounded: Negative cycle detected.

        See Also
        --------
        find_negative_cycle

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The dictionaries returned only have keys for nodes reachable from
        the source.

        In the case where the (di)graph is not connected, if a component
        not containing the source contains a negative (di)cycle, it
        will not be detected.

        In NetworkX v2.1 and prior, the source node had predecessor `[None]`.
        In NetworkX v2.2 this changed to the source node having predecessor `[]`

    bidirectional_dijkstra(G, source, target, weight='weight', *, backend=None, **backend_kwargs)
        Dijkstra's algorithm for shortest paths using bidirectional search.

        Parameters
        ----------
        G : NetworkX graph

        source : node
            Starting node.

        target : node
            Ending node.

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Returns
        -------
        length, path : number and list
            length is the distance from source to target.
            path is a list of nodes on a path from source to target.

        Raises
        ------
        NodeNotFound
            If `source` or `target` is not in `G`.

        NetworkXNoPath
            If no path exists between source and target.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> length, path = nx.bidirectional_dijkstra(G, 0, 4)
        >>> print(length)
        4
        >>> print(path)
        [0, 1, 2, 3, 4]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The weight function can be used to hide edges by returning None.
        So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
        will find the shortest red path.

        In practice  bidirectional Dijkstra is much more than twice as fast as
        ordinary Dijkstra.

        Ordinary Dijkstra expands nodes in a sphere-like manner from the
        source. The radius of this sphere will eventually be the length
        of the shortest path. Bidirectional Dijkstra will expand nodes
        from both the source and the target, making two spheres of half
        this radius. Volume of the first sphere is `\pi*r*r` while the
        others are `2*\pi*r/2*r/2`, making up half the volume.

        This algorithm is not guaranteed to work if edge weights
        are negative or are floating point numbers
        (overflows and roundoff errors can cause problems).

        See Also
        --------
        shortest_path
        shortest_path_length

    dijkstra_path(G, source, target, weight='weight', *, backend=None, **backend_kwargs)
        Returns the shortest weighted path from source to target in G.

        Uses Dijkstra's Method to compute the shortest weighted path
        between two nodes in a graph.

        Parameters
        ----------
        G : NetworkX graph

        source : node
            Starting node

        target : node
            Ending node

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Returns
        -------
        path : list
            List of nodes in a shortest path.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        NetworkXNoPath
            If no path exists between source and target.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> print(nx.dijkstra_path(G, 0, 4))
        [0, 1, 2, 3, 4]

        Find edges of shortest path in Multigraph

        >>> G = nx.MultiDiGraph()
        >>> G.add_weighted_edges_from([(1, 2, 0.75), (1, 2, 0.5), (2, 3, 0.5), (1, 3, 1.5)])
        >>> nodes = nx.dijkstra_path(G, 1, 3)
        >>> edges = nx.utils.pairwise(nodes)
        >>> list(
        ...     (u, v, min(G[u][v], key=lambda k: G[u][v][k].get("weight", 1)))
        ...     for u, v in edges
        ... )
        [(1, 2, 1), (2, 3, 0)]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The weight function can be used to hide edges by returning None.
        So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
        will find the shortest red path.

        The weight function can be used to include node weights.

        >>> def func(u, v, d):
        ...     node_u_wt = G.nodes[u].get("node_weight", 1)
        ...     node_v_wt = G.nodes[v].get("node_weight", 1)
        ...     edge_wt = d.get("weight", 1)
        ...     return node_u_wt / 2 + node_v_wt / 2 + edge_wt

        In this example we take the average of start and end node
        weights of an edge and add it to the weight of the edge.

        The function :func:`single_source_dijkstra` computes both
        path and length-of-path if you need both, use that.

        See Also
        --------
        bidirectional_dijkstra
        bellman_ford_path
        single_source_dijkstra

    dijkstra_path_length(G, source, target, weight='weight', *, backend=None, **backend_kwargs)
        Returns the shortest weighted path length in G from source to target.

        Uses Dijkstra's Method to compute the shortest weighted path length
        between two nodes in a graph.

        Parameters
        ----------
        G : NetworkX graph

        source : node label
            starting node for path

        target : node label
            ending node for path

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Returns
        -------
        length : number
            Shortest path length.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        NetworkXNoPath
            If no path exists between source and target.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> nx.dijkstra_path_length(G, 0, 4)
        4

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The weight function can be used to hide edges by returning None.
        So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
        will find the shortest red path.

        The function :func:`single_source_dijkstra` computes both
        path and length-of-path if you need both, use that.

        See Also
        --------
        bidirectional_dijkstra
        bellman_ford_path_length
        single_source_dijkstra

    dijkstra_predecessor_and_distance(G, source, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
        Compute weighted shortest path length and predecessors.

        Uses Dijkstra's Method to obtain the shortest weighted paths
        and return dictionaries of predecessors for each node and
        distance for each node from the `source`.

        Parameters
        ----------
        G : NetworkX graph

        source : node label
            Starting node for path

        cutoff : integer or float, optional
            Length (sum of edge weights) at which the search is stopped.
            If cutoff is provided, only return paths with summed weight <= cutoff.

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Returns
        -------
        pred, distance : dictionaries
            Returns two dictionaries representing a list of predecessors
            of a node and the distance to each node.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The list of predecessors contains more than one element only when
        there are more than one shortest paths to the key node.

        Examples
        --------
        >>> G = nx.path_graph(5, create_using=nx.DiGraph())
        >>> pred, dist = nx.dijkstra_predecessor_and_distance(G, 0)
        >>> sorted(pred.items())
        [(0, []), (1, [0]), (2, [1]), (3, [2]), (4, [3])]
        >>> sorted(dist.items())
        [(0, 0), (1, 1), (2, 2), (3, 3), (4, 4)]

        >>> pred, dist = nx.dijkstra_predecessor_and_distance(G, 0, 1)
        >>> sorted(pred.items())
        [(0, []), (1, [0])]
        >>> sorted(dist.items())
        [(0, 0), (1, 1)]

    find_negative_cycle(G, source, weight='weight', *, backend=None, **backend_kwargs)
        Returns a cycle with negative total weight if it exists.

        Bellman-Ford is used to find shortest_paths. That algorithm
        stops if there exists a negative cycle. This algorithm
        picks up from there and returns the found negative cycle.

        The cycle consists of a list of nodes in the cycle order. The last
        node equals the first to make it a cycle.
        You can look up the edge weights in the original graph. In the case
        of multigraphs the relevant edge is the minimal weight edge between
        the nodes in the 2-tuple.

        If the graph has no negative cycle, a NetworkXError is raised.

        Parameters
        ----------
        G : NetworkX graph

        source: node label
            The search for the negative cycle will start from this node.

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

        Examples
        --------
        >>> G = nx.DiGraph()
        >>> G.add_weighted_edges_from(
        ...     [(0, 1, 2), (1, 2, 2), (2, 0, 1), (1, 4, 2), (4, 0, -5)]
        ... )
        >>> nx.find_negative_cycle(G, 0)
        [4, 0, 1, 4]

        Returns
        -------
        cycle : list
            A list of nodes in the order of the cycle found. The last node
            equals the first to indicate a cycle.

        Raises
        ------
        NetworkXError
            If no negative cycle is found.

    goldberg_radzik(G, source, weight='weight', *, backend=None, **backend_kwargs)
        Compute shortest path lengths and predecessors on shortest paths
        in weighted graphs.

        The algorithm has a running time of $O(mn)$ where $n$ is the number of
        nodes and $m$ is the number of edges.  It is slower than Dijkstra but
        can handle negative edge weights.

        Parameters
        ----------
        G : NetworkX graph
            The algorithm works for all types of graphs, including directed
            graphs and multigraphs.

        source: node label
            Starting node for path

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

        Returns
        -------
        pred, dist : dictionaries
            Returns two dictionaries keyed by node to predecessor in the
            path and to the distance from the source respectively.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        NetworkXUnbounded
            If the (di)graph contains a negative (di)cycle, the
            algorithm raises an exception to indicate the presence of the
            negative (di)cycle.  Note: any negative weight edge in an
            undirected graph is a negative cycle.

            As of NetworkX v3.2, a zero weight cycle is no longer
            incorrectly reported as a negative weight cycle.


        Examples
        --------
        >>> G = nx.path_graph(5, create_using=nx.DiGraph())
        >>> pred, dist = nx.goldberg_radzik(G, 0)
        >>> sorted(pred.items())
        [(0, None), (1, 0), (2, 1), (3, 2), (4, 3)]
        >>> sorted(dist.items())
        [(0, 0), (1, 1), (2, 2), (3, 3), (4, 4)]

        >>> G = nx.cycle_graph(5, create_using=nx.DiGraph())
        >>> G[1][2]["weight"] = -7
        >>> nx.goldberg_radzik(G, 0)
        Traceback (most recent call last):
            ...
        networkx.exception.NetworkXUnbounded: Negative cycle detected.

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The dictionaries returned only have keys for nodes reachable from
        the source.

        In the case where the (di)graph is not connected, if a component
        not containing the source contains a negative (di)cycle, it
        will not be detected.

    johnson(G, weight='weight', *, backend=None, **backend_kwargs)
        Uses Johnson's Algorithm to compute shortest paths.

        Johnson's Algorithm finds a shortest path between each pair of
        nodes in a weighted graph even if negative weights are present.

        Parameters
        ----------
        G : NetworkX graph

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

        Returns
        -------
        distance : dictionary
            Dictionary, keyed by source and target, of shortest paths.

        Examples
        --------
        >>> graph = nx.DiGraph()
        >>> graph.add_weighted_edges_from(
        ...     [("0", "3", 3), ("0", "1", -5), ("0", "2", 2), ("1", "2", 4), ("2", "3", 1)]
        ... )
        >>> paths = nx.johnson(graph, weight="weight")
        >>> paths["0"]["2"]
        ['0', '1', '2']

        Notes
        -----
        Johnson's algorithm is suitable even for graphs with negative weights. It
        works by using the Bellman–Ford algorithm to compute a transformation of
        the input graph that removes all negative weights, allowing Dijkstra's
        algorithm to be used on the transformed graph.

        The time complexity of this algorithm is $O(n^2 \log n + n m)$,
        where $n$ is the number of nodes and $m$ the number of edges in the
        graph. For dense graphs, this may be faster than the Floyd–Warshall
        algorithm.

        See Also
        --------
        floyd_warshall_predecessor_and_distance
        floyd_warshall_numpy
        all_pairs_shortest_path
        all_pairs_shortest_path_length
        all_pairs_dijkstra_path
        bellman_ford_predecessor_and_distance
        all_pairs_bellman_ford_path
        all_pairs_bellman_ford_path_length

    multi_source_dijkstra(G, sources, target=None, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
        Find shortest weighted paths and lengths from a given set of
        source nodes.

        Uses Dijkstra's algorithm to compute the shortest paths and lengths
        between one of the source nodes and the given `target`, or all other
        reachable nodes if not specified, for a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        sources : non-empty set of nodes
            Starting nodes for paths. If this is just a set containing a
            single node, then all paths computed by this function will start
            from that node. If there are two or more nodes in the set, the
            computed paths may begin from any one of the start nodes.

        target : node label, optional
            Ending node for path

        cutoff : integer or float, optional
            Length (sum of edge weights) at which the search is stopped.
            If cutoff is provided, only return paths with summed weight <= cutoff.

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Returns
        -------
        distance, path : pair of dictionaries, or numeric and list
            If target is None, returns a tuple of two dictionaries keyed by node.
            The first dictionary stores distance from one of the source nodes.
            The second stores the path from one of the sources to that node.
            If target is not None, returns a tuple of (distance, path) where
            distance is the distance from source to target and path is a list
            representing the path from source to target.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> length, path = nx.multi_source_dijkstra(G, {0, 4})
        >>> for node in [0, 1, 2, 3, 4]:
        ...     print(f"{node}: {length[node]}")
        0: 0
        1: 1
        2: 2
        3: 1
        4: 0
        >>> path[1]
        [0, 1]
        >>> path[3]
        [4, 3]

        >>> length, path = nx.multi_source_dijkstra(G, {0, 4}, 1)
        >>> length
        1
        >>> path
        [0, 1]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The weight function can be used to hide edges by returning None.
        So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
        will find the shortest red path.

        Based on the Python cookbook recipe (119466) at
        https://code.activestate.com/recipes/119466/

        This algorithm is not guaranteed to work if edge weights
        are negative or are floating point numbers
        (overflows and roundoff errors can cause problems).

        Raises
        ------
        ValueError
            If `sources` is empty.
        NodeNotFound
            If any of `sources` is not in `G`.

        See Also
        --------
        multi_source_dijkstra_path
        multi_source_dijkstra_path_length

    multi_source_dijkstra_path(G, sources, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
        Find shortest weighted paths in G from a given set of source
        nodes.

        Compute shortest path between any of the source nodes and all other
        reachable nodes for a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        sources : non-empty set of nodes
            Starting nodes for paths. If this is just a set containing a
            single node, then all paths computed by this function will start
            from that node. If there are two or more nodes in the set, the
            computed paths may begin from any one of the start nodes.

        cutoff : integer or float, optional
            Length (sum of edge weights) at which the search is stopped.
            If cutoff is provided, only return paths with summed weight <= cutoff.

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Returns
        -------
        paths : dictionary
            Dictionary of shortest paths keyed by target.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> path = nx.multi_source_dijkstra_path(G, {0, 4})
        >>> path[1]
        [0, 1]
        >>> path[3]
        [4, 3]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The weight function can be used to hide edges by returning None.
        So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
        will find the shortest red path.

        Raises
        ------
        ValueError
            If `sources` is empty.
        NodeNotFound
            If any of `sources` is not in `G`.

        See Also
        --------
        multi_source_dijkstra, multi_source_bellman_ford

    multi_source_dijkstra_path_length(G, sources, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
        Find shortest weighted path lengths in G from a given set of
        source nodes.

        Compute the shortest path length between any of the source nodes and
        all other reachable nodes for a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        sources : non-empty set of nodes
            Starting nodes for paths. If this is just a set containing a
            single node, then all paths computed by this function will start
            from that node. If there are two or more nodes in the set, the
            computed paths may begin from any one of the start nodes.

        cutoff : integer or float, optional
            Length (sum of edge weights) at which the search is stopped.
            If cutoff is provided, only return paths with summed weight <= cutoff.

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Returns
        -------
        length : dict
            Dict keyed by node to shortest path length to nearest source.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> length = nx.multi_source_dijkstra_path_length(G, {0, 4})
        >>> for node in [0, 1, 2, 3, 4]:
        ...     print(f"{node}: {length[node]}")
        0: 0
        1: 1
        2: 2
        3: 1
        4: 0

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The weight function can be used to hide edges by returning None.
        So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
        will find the shortest red path.

        Raises
        ------
        ValueError
            If `sources` is empty.
        NodeNotFound
            If any of `sources` is not in `G`.

        See Also
        --------
        multi_source_dijkstra

    negative_edge_cycle(G, weight='weight', heuristic=True, *, backend=None, **backend_kwargs)
        Returns True if there exists a negative edge cycle anywhere in G.

        Parameters
        ----------
        G : NetworkX graph

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

        heuristic : bool
            Determines whether to use a heuristic to early detect negative
            cycles at a negligible cost. In case of graphs with a negative cycle,
            the performance of detection increases by at least an order of magnitude.

        Returns
        -------
        negative_cycle : bool
            True if a negative edge cycle exists, otherwise False.

        Examples
        --------
        >>> G = nx.cycle_graph(5, create_using=nx.DiGraph())
        >>> print(nx.negative_edge_cycle(G))
        False
        >>> G[1][2]["weight"] = -7
        >>> print(nx.negative_edge_cycle(G))
        True

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        This algorithm uses bellman_ford_predecessor_and_distance() but finds
        negative cycles on any component by first adding a new node connected to
        every node, and starting bellman_ford_predecessor_and_distance on that
        node.  It then removes that extra node.

    single_source_bellman_ford(G, source, target=None, weight='weight', *, backend=None, **backend_kwargs)
        Compute shortest paths and lengths in a weighted graph G.

        Uses Bellman-Ford algorithm for shortest paths.

        Parameters
        ----------
        G : NetworkX graph

        source : node label
            Starting node for path

        target : node label, optional
            Ending node for path

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

        Returns
        -------
        distance, path : pair of dictionaries, or numeric and list
            If target is None, returns a tuple of two dictionaries keyed by node.
            The first dictionary stores distance from one of the source nodes.
            The second stores the path from one of the sources to that node.
            If target is not None, returns a tuple of (distance, path) where
            distance is the distance from source to target and path is a list
            representing the path from source to target.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> length, path = nx.single_source_bellman_ford(G, 0)
        >>> length[4]
        4
        >>> for node in [0, 1, 2, 3, 4]:
        ...     print(f"{node}: {length[node]}")
        0: 0
        1: 1
        2: 2
        3: 3
        4: 4
        >>> path[4]
        [0, 1, 2, 3, 4]
        >>> length, path = nx.single_source_bellman_ford(G, 0, 1)
        >>> length
        1
        >>> path
        [0, 1]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        See Also
        --------
        single_source_dijkstra
        single_source_bellman_ford_path
        single_source_bellman_ford_path_length

    single_source_bellman_ford_path(G, source, weight='weight', *, backend=None, **backend_kwargs)
        Compute shortest path between source and all other reachable
        nodes for a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        source : node
            Starting node for path.

        weight : string or function (default="weight")
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

        Returns
        -------
        paths : dictionary
            Dictionary of shortest path lengths keyed by target.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> path = nx.single_source_bellman_ford_path(G, 0)
        >>> path[4]
        [0, 1, 2, 3, 4]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        See Also
        --------
        single_source_dijkstra, single_source_bellman_ford

    single_source_bellman_ford_path_length(G, source, weight='weight', *, backend=None, **backend_kwargs)
        Compute the shortest path length between source and all other
        reachable nodes for a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        source : node label
            Starting node for path

        weight : string or function (default="weight")
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number.

        Returns
        -------
        length : dictionary
            Dictionary of shortest path length keyed by target

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> length = nx.single_source_bellman_ford_path_length(G, 0)
        >>> length[4]
        4
        >>> for node in [0, 1, 2, 3, 4]:
        ...     print(f"{node}: {length[node]}")
        0: 0
        1: 1
        2: 2
        3: 3
        4: 4

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        See Also
        --------
        single_source_dijkstra, single_source_bellman_ford

    single_source_dijkstra(G, source, target=None, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
        Find shortest weighted paths and lengths from a source node.

        Compute the shortest path length between source and all other
        reachable nodes for a weighted graph.

        Uses Dijkstra's algorithm to compute shortest paths and lengths
        between a source and all other reachable nodes in a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        source : node label
            Starting node for path

        target : node label, optional
            Ending node for path

        cutoff : integer or float, optional
            Length (sum of edge weights) at which the search is stopped.
            If cutoff is provided, only return paths with summed weight <= cutoff.


        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Returns
        -------
        distance, path : pair of dictionaries, or numeric and list.
            If target is None, paths and lengths to all nodes are computed.
            The return value is a tuple of two dictionaries keyed by target nodes.
            The first dictionary stores distance to each target node.
            The second stores the path to each target node.
            If target is not None, returns a tuple (distance, path), where
            distance is the distance from source to target and path is a list
            representing the path from source to target.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> length, path = nx.single_source_dijkstra(G, 0)
        >>> length[4]
        4
        >>> for node in [0, 1, 2, 3, 4]:
        ...     print(f"{node}: {length[node]}")
        0: 0
        1: 1
        2: 2
        3: 3
        4: 4
        >>> path[4]
        [0, 1, 2, 3, 4]
        >>> length, path = nx.single_source_dijkstra(G, 0, 1)
        >>> length
        1
        >>> path
        [0, 1]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The weight function can be used to hide edges by returning None.
        So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
        will find the shortest red path.

        Based on the Python cookbook recipe (119466) at
        https://code.activestate.com/recipes/119466/

        This algorithm is not guaranteed to work if edge weights
        are negative or are floating point numbers
        (overflows and roundoff errors can cause problems).

        See Also
        --------
        single_source_dijkstra_path
        single_source_dijkstra_path_length
        single_source_bellman_ford

    single_source_dijkstra_path(G, source, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
        Find shortest weighted paths in G from a source node.

        Compute shortest path between source and all other reachable
        nodes for a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        source : node
            Starting node for path.

        cutoff : integer or float, optional
            Length (sum of edge weights) at which the search is stopped.
            If cutoff is provided, only return paths with summed weight <= cutoff.

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Returns
        -------
        paths : dictionary
            Dictionary of shortest path lengths keyed by target.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> path = nx.single_source_dijkstra_path(G, 0)
        >>> path[4]
        [0, 1, 2, 3, 4]

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The weight function can be used to hide edges by returning None.
        So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
        will find the shortest red path.

        See Also
        --------
        single_source_dijkstra, single_source_bellman_ford

    single_source_dijkstra_path_length(G, source, cutoff=None, weight='weight', *, backend=None, **backend_kwargs)
        Find shortest weighted path lengths in G from a source node.

        Compute the shortest path length between source and all other
        reachable nodes for a weighted graph.

        Parameters
        ----------
        G : NetworkX graph

        source : node label
            Starting node for path

        cutoff : integer or float, optional
            Length (sum of edge weights) at which the search is stopped.
            If cutoff is provided, only return paths with summed weight <= cutoff.

        weight : string or function
            If this is a string, then edge weights will be accessed via the
            edge attribute with this key (that is, the weight of the edge
            joining `u` to `v` will be ``G.edges[u, v][weight]``). If no
            such edge attribute exists, the weight of the edge is assumed to
            be one.

            If this is a function, the weight of an edge is the value
            returned by the function. The function must accept exactly three
            positional arguments: the two endpoints of an edge and the
            dictionary of edge attributes for that edge. The function must
            return a number or None to indicate a hidden edge.

        Returns
        -------
        length : dict
            Dict keyed by node to shortest path length from source.

        Raises
        ------
        NodeNotFound
            If `source` is not in `G`.

        Examples
        --------
        >>> G = nx.path_graph(5)
        >>> length = nx.single_source_dijkstra_path_length(G, 0)
        >>> length[4]
        4
        >>> for node in [0, 1, 2, 3, 4]:
        ...     print(f"{node}: {length[node]}")
        0: 0
        1: 1
        2: 2
        3: 3
        4: 4

        Notes
        -----
        Edge weight attributes must be numerical.
        Distances are calculated as sums of weighted edges traversed.

        The weight function can be used to hide edges by returning None.
        So ``weight = lambda u, v, d: 1 if d['color']=="red" else None``
        will find the shortest red path.

        See Also
        --------
        single_source_dijkstra, single_source_bellman_ford_path_length

DATA
    __all__ = ['dijkstra_path', 'dijkstra_path_length', 'bidirectional_dij...

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\shortest_paths\weighted.py

networkx.weisfeiler_lehman_graph_hash
Python Library Documentation: function weisfeiler_lehman_graph_hash in module networkx.algorithms.graph_hashing

weisfeiler_lehman_graph_hash(G, edge_attr=None, node_attr=None, iterations=3, digest_size=16, *, backend=None, **backend_kwargs)
    Return Weisfeiler Lehman (WL) graph hash.

    The function iteratively aggregates and hashes neighborhoods of each node.
    After each node's neighbors are hashed to obtain updated node labels,
    a hashed histogram of resulting labels is returned as the final hash.

    Hashes are identical for isomorphic graphs and strong guarantees that
    non-isomorphic graphs will get different hashes. See [1]_ for details.

    If no node or edge attributes are provided, the degree of each node
    is used as its initial label.
    Otherwise, node and/or edge labels are used to compute the hash.

    Parameters
    ----------
    G : graph
        The graph to be hashed.
        Can have node and/or edge attributes. Can also have no attributes.
    edge_attr : string, optional (default=None)
        The key in edge attribute dictionary to be used for hashing.
        If None, edge labels are ignored.
    node_attr: string, optional (default=None)
        The key in node attribute dictionary to be used for hashing.
        If None, and no edge_attr given, use the degrees of the nodes as labels.
    iterations: int, optional (default=3)
        Number of neighbor aggregations to perform.
        Should be larger for larger graphs.
    digest_size: int, optional (default=16)
        Size (in bits) of blake2b hash digest to use for hashing node labels.

    Returns
    -------
    h : string
        Hexadecimal string corresponding to hash of the input graph.

    Examples
    --------
    Two graphs with edge attributes that are isomorphic, except for
    differences in the edge labels.

    >>> G1 = nx.Graph()
    >>> G1.add_edges_from(
    ...     [
    ...         (1, 2, {"label": "A"}),
    ...         (2, 3, {"label": "A"}),
    ...         (3, 1, {"label": "A"}),
    ...         (1, 4, {"label": "B"}),
    ...     ]
    ... )
    >>> G2 = nx.Graph()
    >>> G2.add_edges_from(
    ...     [
    ...         (5, 6, {"label": "B"}),
    ...         (6, 7, {"label": "A"}),
    ...         (7, 5, {"label": "A"}),
    ...         (7, 8, {"label": "A"}),
    ...     ]
    ... )

    Omitting the `edge_attr` option, results in identical hashes.

    >>> nx.weisfeiler_lehman_graph_hash(G1)
    '7bc4dde9a09d0b94c5097b219891d81a'
    >>> nx.weisfeiler_lehman_graph_hash(G2)
    '7bc4dde9a09d0b94c5097b219891d81a'

    With edge labels, the graphs are no longer assigned
    the same hash digest.

    >>> nx.weisfeiler_lehman_graph_hash(G1, edge_attr="label")
    'c653d85538bcf041d88c011f4f905f10'
    >>> nx.weisfeiler_lehman_graph_hash(G2, edge_attr="label")
    '3dcd84af1ca855d0eff3c978d88e7ec7'

    Notes
    -----
    To return the WL hashes of each subgraph of a graph, use
    `weisfeiler_lehman_subgraph_hashes`

    Similarity between hashes does not imply similarity between graphs.

    References
    ----------
    .. [1] Shervashidze, Nino, Pascal Schweitzer, Erik Jan Van Leeuwen,
       Kurt Mehlhorn, and Karsten M. Borgwardt. Weisfeiler Lehman
       Graph Kernels. Journal of Machine Learning Research. 2011.
       http://www.jmlr.org/papers/volume12/shervashidze11a/shervashidze11a.pdf

    See also
    --------
    weisfeiler_lehman_subgraph_hashes
networkx.weisfeiler_lehman_subgraph_hashes
Python Library Documentation: function weisfeiler_lehman_subgraph_hashes in module networkx.algorithms.graph_hashing

weisfeiler_lehman_subgraph_hashes(G, edge_attr=None, node_attr=None, iterations=3, digest_size=16, include_initial_labels=False, *, backend=None, **backend_kwargs)
    Return a dictionary of subgraph hashes by node.

    Dictionary keys are nodes in `G`, and values are a list of hashes.
    Each hash corresponds to a subgraph rooted at a given node u in `G`.
    Lists of subgraph hashes are sorted in increasing order of depth from
    their root node, with the hash at index i corresponding to a subgraph
    of nodes at most i edges distance from u. Thus, each list will contain
    `iterations` elements - a hash for a subgraph at each depth. If
    `include_initial_labels` is set to `True`, each list will additionally
    have contain a hash of the initial node label (or equivalently a
    subgraph of depth 0) prepended, totalling ``iterations + 1`` elements.

    The function iteratively aggregates and hashes neighborhoods of each node.
    This is achieved for each step by replacing for each node its label from
    the previous iteration with its hashed 1-hop neighborhood aggregate.
    The new node label is then appended to a list of node labels for each
    node.

    To aggregate neighborhoods for a node $u$ at each step, all labels of
    nodes adjacent to $u$ are concatenated. If the `edge_attr` parameter is set,
    labels for each neighboring node are prefixed with the value of this attribute
    along the connecting edge from this neighbor to node $u$. The resulting string
    is then hashed to compress this information into a fixed digest size.

    Thus, at the $i$-th iteration, nodes within $i$ hops influence any given
    hashed node label. We can therefore say that at depth $i$ for node $u$
    we have a hash for a subgraph induced by the $i$-hop neighborhood of $u$.

    The output can be used to create general Weisfeiler-Lehman graph kernels,
    or generate features for graphs or nodes - for example to generate 'words' in
    a graph as seen in the 'graph2vec' algorithm.
    See [1]_ & [2]_ respectively for details.

    Hashes are identical for isomorphic subgraphs and there exist strong
    guarantees that non-isomorphic graphs will get different hashes.
    See [1]_ for details.

    If no node or edge attributes are provided, the degree of each node
    is used as its initial label.
    Otherwise, node and/or edge labels are used to compute the hash.

    Parameters
    ----------
    G : graph
        The graph to be hashed.
        Can have node and/or edge attributes. Can also have no attributes.
    edge_attr : string, optional (default=None)
        The key in edge attribute dictionary to be used for hashing.
        If None, edge labels are ignored.
    node_attr : string, optional (default=None)
        The key in node attribute dictionary to be used for hashing.
        If None, and no edge_attr given, use the degrees of the nodes as labels.
        If None, and edge_attr is given, each node starts with an identical label.
    iterations : int, optional (default=3)
        Number of neighbor aggregations to perform.
        Should be larger for larger graphs.
    digest_size : int, optional (default=16)
        Size (in bits) of blake2b hash digest to use for hashing node labels.
        The default size is 16 bits.
    include_initial_labels : bool, optional (default=False)
        If True, include the hashed initial node label as the first subgraph
        hash for each node.

    Returns
    -------
    node_subgraph_hashes : dict
        A dictionary with each key given by a node in G, and each value given
        by the subgraph hashes in order of depth from the key node.

    Examples
    --------
    Finding similar nodes in different graphs:

    >>> G1 = nx.Graph()
    >>> G1.add_edges_from([(1, 2), (2, 3), (2, 4), (3, 5), (4, 6), (5, 7), (6, 7)])
    >>> G2 = nx.Graph()
    >>> G2.add_edges_from([(1, 3), (2, 3), (1, 6), (1, 5), (4, 6)])
    >>> g1_hashes = nx.weisfeiler_lehman_subgraph_hashes(
    ...     G1, iterations=3, digest_size=8
    ... )
    >>> g2_hashes = nx.weisfeiler_lehman_subgraph_hashes(
    ...     G2, iterations=3, digest_size=8
    ... )

    Even though G1 and G2 are not isomorphic (they have different numbers of edges),
    the hash sequence of depth 3 for node 1 in G1 and node 5 in G2 are similar:

    >>> g1_hashes[1]
    ['a93b64973cfc8897', 'db1b43ae35a1878f', '57872a7d2059c1c0']
    >>> g2_hashes[5]
    ['a93b64973cfc8897', 'db1b43ae35a1878f', '1716d2a4012fa4bc']

    The first 2 WL subgraph hashes match. From this we can conclude that it's very
    likely the neighborhood of 2 hops around these nodes are isomorphic.

    However the 3-hop neighborhoods of ``G1`` and ``G2`` are not isomorphic since the
    3rd hashes in the lists above are not equal.

    These nodes may be candidates to be classified together since their local topology
    is similar.

    Notes
    -----
    To hash the full graph when subgraph hashes are not needed, use
    `weisfeiler_lehman_graph_hash` for efficiency.

    Similarity between hashes does not imply similarity between graphs.

    References
    ----------
    .. [1] Shervashidze, Nino, Pascal Schweitzer, Erik Jan Van Leeuwen,
       Kurt Mehlhorn, and Karsten M. Borgwardt. Weisfeiler Lehman
       Graph Kernels. Journal of Machine Learning Research. 2011.
       http://www.jmlr.org/papers/volume12/shervashidze11a/shervashidze11a.pdf
    .. [2] Annamalai Narayanan, Mahinthan Chandramohan, Rajasekar Venkatesan,
       Lihui Chen, Yang Liu and Shantanu Jaiswa. graph2vec: Learning
       Distributed Representations of Graphs. arXiv. 2017
       https://arxiv.org/pdf/1707.05005.pdf

    See also
    --------
    weisfeiler_lehman_graph_hash
networkx.wheel_graph
Python Library Documentation: function wheel_graph in module networkx.generators.classic

wheel_graph(n, create_using=None, *, backend=None, **backend_kwargs)
    Return the wheel graph

    The wheel graph consists of a hub node connected to a cycle of (n-1) nodes.

    .. plot::

        >>> nx.draw(nx.wheel_graph(5))

    Parameters
    ----------
    n : int or iterable
        If an integer, node labels are 0 to n with center 0.
        If an iterable of nodes, the center is the first.
        Warning: n is not checked for duplicates and if present the
        resulting graph may not be as desired. Make sure you have no duplicates.
    create_using : NetworkX graph constructor, optional (default=nx.Graph)
       Graph type to create. If graph instance, then cleared before populated.

    Node labels are the integers 0 to n - 1.
networkx.wiener
Python Library Documentation: module networkx.algorithms.wiener in networkx.algorithms

NAME
    networkx.algorithms.wiener - Functions related to the Wiener Index of a graph.

DESCRIPTION
    The Wiener Index is a topological measure of a graph
    related to the distance between nodes and their degree.
    The Schultz Index and Gutman Index are similar measures.
    They are used categorize molecules via the network of
    atoms connected by chemical bonds. The indices are
    correlated with functional aspects of the molecules.

    References
    ----------
    .. [1] `Wikipedia: Wiener Index <https://en.wikipedia.org/wiki/Wiener_index>`_
    .. [2] M.V. Diudeaa and I. Gutman, Wiener-Type Topological Indices,
           Croatica Chemica Acta, 71 (1998), 21-51.
           https://hrcak.srce.hr/132323

FUNCTIONS
    gutman_index(G, weight=None, *, backend=None, **backend_kwargs)
        Returns the Gutman Index for the graph `G`.

        The *Gutman Index* measures the topology of networks, especially for molecule
        networks of atoms connected by bonds [1]_. It is also called the Schultz Index
        of the second kind [2]_.

        Consider an undirected graph `G` with node set ``V``.
        The Gutman Index of a graph is the sum over all (unordered) pairs of nodes
        of nodes ``(u, v)``, with distance ``dist(u, v)`` and degrees ``deg(u)``
        and ``deg(v)``, of ``dist(u, v) * deg(u) * deg(v)``

        Parameters
        ----------
        G : NetworkX graph

        weight : string or None, optional (default: None)
            If None, every edge has weight 1.
            If a string, use this edge attribute as the edge weight.
            Any edge attribute not present defaults to 1.
            The edge weights are used to computing shortest-path distances.

        Returns
        -------
        number
            The Gutman Index of the graph `G`.

        Examples
        --------
        The Gutman Index of the (unweighted) complete graph on *n* nodes
        equals the number of pairs of the *n* nodes times ``(n - 1) * (n - 1)``,
        since each pair of nodes is at distance one and the product of degree of two
        vertices is ``(n - 1) * (n - 1)``.

        >>> n = 10
        >>> G = nx.complete_graph(n)
        >>> nx.gutman_index(G) == (n * (n - 1) / 2) * ((n - 1) * (n - 1))
        True

        Graphs that are disconnected

        >>> G = nx.empty_graph(2)
        >>> nx.gutman_index(G)
        inf

        References
        ----------
        .. [1] M.V. Diudeaa and I. Gutman, Wiener-Type Topological Indices,
               Croatica Chemica Acta, 71 (1998), 21-51.
               https://hrcak.srce.hr/132323
        .. [2] I. Gutman, Selected properties of the Schultz molecular topological index,
               J. Chem. Inf. Comput. Sci. 34 (1994), 1087–1089.
               https://doi.org/10.1021/ci00021a009

    schultz_index(G, weight=None, *, backend=None, **backend_kwargs)
        Returns the Schultz Index (of the first kind) of `G`

        The *Schultz Index* [3]_ of a graph is the sum over all node pairs of
        distances times the sum of degrees. Consider an undirected graph `G`.
        For each node pair ``(u, v)`` compute ``dist(u, v) * (deg(u) + deg(v)``
        where ``dist`` is the shortest path length between two nodes and ``deg``
        is the degree of a node.

        The Schultz Index is the sum of these quantities over all (unordered)
        pairs of nodes.

        Parameters
        ----------
        G : NetworkX graph
            The undirected graph of interest.
        weight : string or None, optional (default: None)
            If None, every edge has weight 1.
            If a string, use this edge attribute as the edge weight.
            Any edge attribute not present defaults to 1.
            The edge weights are used to computing shortest-path distances.

        Returns
        -------
        number
            The first kind of Schultz Index of the graph `G`.

        Examples
        --------
        The Schultz Index of the (unweighted) complete graph on *n* nodes
        equals the number of pairs of the *n* nodes times ``2 * (n - 1)``,
        since each pair of nodes is at distance one and the sum of degree
        of two nodes is ``2 * (n - 1)``.

        >>> n = 10
        >>> G = nx.complete_graph(n)
        >>> nx.schultz_index(G) == (n * (n - 1) / 2) * (2 * (n - 1))
        True

        Graph that is disconnected

        >>> nx.schultz_index(nx.empty_graph(2))
        inf

        References
        ----------
        .. [1] I. Gutman, Selected properties of the Schultz molecular topological index,
               J. Chem. Inf. Comput. Sci. 34 (1994), 1087–1089.
               https://doi.org/10.1021/ci00021a009
        .. [2] M.V. Diudeaa and I. Gutman, Wiener-Type Topological Indices,
               Croatica Chemica Acta, 71 (1998), 21-51.
               https://hrcak.srce.hr/132323
        .. [3] H. P. Schultz, Topological organic chemistry. 1.
               Graph theory and topological indices of alkanes,i
               J. Chem. Inf. Comput. Sci. 29 (1989), 239–257.

    wiener_index(G, weight=None, *, backend=None, **backend_kwargs)
        Returns the Wiener index of the given graph.

        The *Wiener index* of a graph is the sum of the shortest-path
        (weighted) distances between each pair of reachable nodes.
        For pairs of nodes in undirected graphs, only one orientation
        of the pair is counted.

        Parameters
        ----------
        G : NetworkX graph

        weight : string or None, optional (default: None)
            If None, every edge has weight 1.
            If a string, use this edge attribute as the edge weight.
            Any edge attribute not present defaults to 1.
            The edge weights are used to computing shortest-path distances.

        Returns
        -------
        number
            The Wiener index of the graph `G`.

        Raises
        ------
        NetworkXError
            If the graph `G` is not connected.

        Notes
        -----
        If a pair of nodes is not reachable, the distance is assumed to be
        infinity. This means that for graphs that are not
        strongly-connected, this function returns ``inf``.

        The Wiener index is not usually defined for directed graphs, however
        this function uses the natural generalization of the Wiener index to
        directed graphs.

        Examples
        --------
        The Wiener index of the (unweighted) complete graph on *n* nodes
        equals the number of pairs of the *n* nodes, since each pair of
        nodes is at distance one::

            >>> n = 10
            >>> G = nx.complete_graph(n)
            >>> nx.wiener_index(G) == n * (n - 1) / 2
            True

        Graphs that are not strongly-connected have infinite Wiener index::

            >>> G = nx.empty_graph(2)
            >>> nx.wiener_index(G)
            inf

        References
        ----------
        .. [1] `Wikipedia: Wiener Index <https://en.wikipedia.org/wiki/Wiener_index>`_

DATA
    __all__ = ['wiener_index', 'schultz_index', 'gutman_index']

FILE
    c:\users\youse\appdata\local\programs\python\python312\lib\site-packages\networkx\algorithms\wiener.py

networkx.wiener_index
Python Library Documentation: function wiener_index in module networkx.algorithms.wiener

wiener_index(G, weight=None, *, backend=None, **backend_kwargs)
    Returns the Wiener index of the given graph.

    The *Wiener index* of a graph is the sum of the shortest-path
    (weighted) distances between each pair of reachable nodes.
    For pairs of nodes in undirected graphs, only one orientation
    of the pair is counted.

    Parameters
    ----------
    G : NetworkX graph

    weight : string or None, optional (default: None)
        If None, every edge has weight 1.
        If a string, use this edge attribute as the edge weight.
        Any edge attribute not present defaults to 1.
        The edge weights are used to computing shortest-path distances.

    Returns
    -------
    number
        The Wiener index of the graph `G`.

    Raises
    ------
    NetworkXError
        If the graph `G` is not connected.

    Notes
    -----
    If a pair of nodes is not reachable, the distance is assumed to be
    infinity. This means that for graphs that are not
    strongly-connected, this function returns ``inf``.

    The Wiener index is not usually defined for directed graphs, however
    this function uses the natural generalization of the Wiener index to
    directed graphs.

    Examples
    --------
    The Wiener index of the (unweighted) complete graph on *n* nodes
    equals the number of pairs of the *n* nodes, since each pair of
    nodes is at distance one::

        >>> n = 10
        >>> G = nx.complete_graph(n)
        >>> nx.wiener_index(G) == n * (n - 1) / 2
        True

    Graphs that are not strongly-connected have infinite Wiener index::

        >>> G = nx.empty_graph(2)
        >>> nx.wiener_index(G)
        inf

    References
    ----------
    .. [1] `Wikipedia: Wiener Index <https://en.wikipedia.org/wiki/Wiener_index>`_
networkx.windmill_graph
Python Library Documentation: function windmill_graph in module networkx.generators.community

windmill_graph(n, k, *, backend=None, **backend_kwargs)
    Generate a windmill graph.
    A windmill graph is a graph of `n` cliques each of size `k` that are all
    joined at one node.
    It can be thought of as taking a disjoint union of `n` cliques of size `k`,
    selecting one point from each, and contracting all of the selected points.
    Alternatively, one could generate `n` cliques of size `k-1` and one node
    that is connected to all other nodes in the graph.

    Parameters
    ----------
    n : int
        Number of cliques
    k : int
        Size of cliques

    Returns
    -------
    G : NetworkX Graph
        windmill graph with n cliques of size k

    Raises
    ------
    NetworkXError
        If the number of cliques is less than two
        If the size of the cliques are less than two

    Examples
    --------
    >>> G = nx.windmill_graph(4, 5)

    Notes
    -----
    The node labeled `0` will be the node connected to all other nodes.
    Note that windmill graphs are usually denoted `Wd(k,n)`, so the parameters
    are in the opposite order as the parameters of this method.
networkx.within_inter_cluster
Python Library Documentation: function within_inter_cluster in module networkx.algorithms.link_prediction

within_inter_cluster(G, ebunch=None, delta=0.001, community='community', *, backend=None, **backend_kwargs)
    Compute the ratio of within- and inter-cluster common neighbors
    of all node pairs in ebunch.

    For two nodes `u` and `v`, if a common neighbor `w` belongs to the
    same community as them, `w` is considered as within-cluster common
    neighbor of `u` and `v`. Otherwise, it is considered as
    inter-cluster common neighbor of `u` and `v`. The ratio between the
    size of the set of within- and inter-cluster common neighbors is
    defined as the WIC measure. [1]_

    Parameters
    ----------
    G : graph
        A NetworkX undirected graph.

    ebunch : iterable of node pairs, optional (default = None)
        The WIC measure will be computed for each pair of nodes given in
        the iterable. The pairs must be given as 2-tuples (u, v) where
        u and v are nodes in the graph. If ebunch is None then all
        nonexistent edges in the graph will be used.
        Default value: None.

    delta : float, optional (default = 0.001)
        Value to prevent division by zero in case there is no
        inter-cluster common neighbor between two nodes. See [1]_ for
        details. Default value: 0.001.

    community : string, optional (default = 'community')
        Nodes attribute name containing the community information.
        G[u][community] identifies which community u belongs to. Each
        node belongs to at most one community. Default value: 'community'.

    Returns
    -------
    piter : iterator
        An iterator of 3-tuples in the form (u, v, p) where (u, v) is a
        pair of nodes and p is their WIC measure.

    Raises
    ------
    NetworkXNotImplemented
        If `G` is a `DiGraph`, a `Multigraph` or a `MultiDiGraph`.

    NetworkXAlgorithmError
        - If `delta` is less than or equal to zero.
        - If no community information is available for a node in `ebunch` or in `G` (if `ebunch` is `None`).

    NodeNotFound
        If `ebunch` has a node that is not in `G`.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_edges_from([(0, 1), (0, 2), (0, 3), (1, 4), (2, 4), (3, 4)])
    >>> G.nodes[0]["community"] = 0
    >>> G.nodes[1]["community"] = 1
    >>> G.nodes[2]["community"] = 0
    >>> G.nodes[3]["community"] = 0
    >>> G.nodes[4]["community"] = 0
    >>> preds = nx.within_inter_cluster(G, [(0, 4)])
    >>> for u, v, p in preds:
    ...     print(f"({u}, {v}) -> {p:.8f}")
    (0, 4) -> 1.99800200
    >>> preds = nx.within_inter_cluster(G, [(0, 4)], delta=0.5)
    >>> for u, v, p in preds:
    ...     print(f"({u}, {v}) -> {p:.8f}")
    (0, 4) -> 1.33333333

    References
    ----------
    .. [1] Jorge Carlos Valverde-Rebaza and Alneu de Andrade Lopes.
       Link prediction in complex networks based on cluster information.
       In Proceedings of the 21st Brazilian conference on Advances in
       Artificial Intelligence (SBIA'12)
       https://doi.org/10.1007/978-3-642-34459-6_10
networkx.write_adjlist
Python Library Documentation: function write_adjlist in module networkx.readwrite.adjlist

write_adjlist(G, path, comments='#', delimiter=' ', encoding='utf-8')
    Write graph G in single-line adjacency-list format to path.


    Parameters
    ----------
    G : NetworkX graph

    path : string or file
       Filename or file handle for data output.
       Filenames ending in .gz or .bz2 will be compressed.

    comments : string, optional
       Marker for comment lines

    delimiter : string, optional
       Separator for node labels

    encoding : string, optional
       Text encoding.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_adjlist(G, "test.adjlist")

    The path can be a filehandle or a string with the name of the file. If a
    filehandle is provided, it has to be opened in 'wb' mode.

    >>> fh = open("test.adjlist", "wb")
    >>> nx.write_adjlist(G, fh)

    Notes
    -----
    The default `delimiter=" "` will result in unexpected results if node names contain
    whitespace characters. To avoid this problem, specify an alternate delimiter when spaces are
    valid in node names.
    NB: This option is not available for data that isn't user-generated.

    This format does not store graph, node, or edge data.

    See Also
    --------
    read_adjlist, generate_adjlist
networkx.write_edgelist
Python Library Documentation: function write_edgelist in module networkx.readwrite.edgelist

write_edgelist(G, path, comments='#', delimiter=' ', data=True, encoding='utf-8')
    Write graph as a list of edges.

    Parameters
    ----------
    G : graph
       A NetworkX graph
    path : file or string
       File or filename to write. If a file is provided, it must be
       opened in 'wb' mode. Filenames ending in .gz or .bz2 will be compressed.
    comments : string, optional
       The character used to indicate the start of a comment
    delimiter : string, optional
       The string used to separate values.  The default is whitespace.
    data : bool or list, optional
       If False write no edge data.
       If True write a string representation of the edge data dictionary..
       If a list (or other iterable) is provided, write the  keys specified
       in the list.
    encoding: string, optional
       Specify which encoding to use when writing file.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_edgelist(G, "test.edgelist")
    >>> G = nx.path_graph(4)
    >>> fh = open("test.edgelist", "wb")
    >>> nx.write_edgelist(G, fh)
    >>> nx.write_edgelist(G, "test.edgelist.gz")
    >>> nx.write_edgelist(G, "test.edgelist.gz", data=False)

    >>> G = nx.Graph()
    >>> G.add_edge(1, 2, weight=7, color="red")
    >>> nx.write_edgelist(G, "test.edgelist", data=False)
    >>> nx.write_edgelist(G, "test.edgelist", data=["color"])
    >>> nx.write_edgelist(G, "test.edgelist", data=["color", "weight"])

    See Also
    --------
    read_edgelist
    write_weighted_edgelist
networkx.write_gexf
Python Library Documentation: function write_gexf in module networkx.readwrite.gexf

write_gexf(G, path, encoding='utf-8', prettyprint=True, version='1.2draft')
    Write G in GEXF format to path.

    "GEXF (Graph Exchange XML Format) is a language for describing
    complex networks structures, their associated data and dynamics" [1]_.

    Node attributes are checked according to the version of the GEXF
    schemas used for parameters which are not user defined,
    e.g. visualization 'viz' [2]_. See example for usage.

    Parameters
    ----------
    G : graph
       A NetworkX graph
    path : file or string
       File or file name to write.
       File names ending in .gz or .bz2 will be compressed.
    encoding : string (optional, default: 'utf-8')
       Encoding for text data.
    prettyprint : bool (optional, default: True)
       If True use line breaks and indenting in output XML.
    version: string (optional, default: '1.2draft')
       The version of GEXF to be used for nodes attributes checking

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_gexf(G, "test.gexf")

    # visualization data
    >>> G.nodes[0]["viz"] = {"size": 54}
    >>> G.nodes[0]["viz"]["position"] = {"x": 0, "y": 1}
    >>> G.nodes[0]["viz"]["color"] = {"r": 0, "g": 0, "b": 256}


    Notes
    -----
    This implementation does not support mixed graphs (directed and undirected
    edges together).

    The node id attribute is set to be the string of the node label.
    If you want to specify an id use set it as node data, e.g.
    node['a']['id']=1 to set the id of node 'a' to 1.

    References
    ----------
    .. [1] GEXF File Format, http://gexf.net/
    .. [2] GEXF schema, http://gexf.net/schema.html
networkx.write_gml
Python Library Documentation: function write_gml in module networkx.readwrite.gml

write_gml(G, path, stringizer=None)
    Write a graph `G` in GML format to the file or file handle `path`.

    Parameters
    ----------
    G : NetworkX graph
        The graph to be converted to GML.

    path : filename or filehandle
        The filename or filehandle to write. Files whose names end with .gz or
        .bz2 will be compressed.

    stringizer : callable, optional
        A `stringizer` which converts non-int/non-float/non-dict values into
        strings. If it cannot convert a value into a string, it should raise a
        `ValueError` to indicate that. Default value: None.

    Raises
    ------
    NetworkXError
        If `stringizer` cannot convert a value into a string, or the value to
        convert is not a string while `stringizer` is None.

    See Also
    --------
    read_gml, generate_gml
    literal_stringizer

    Notes
    -----
    Graph attributes named 'directed', 'multigraph', 'node' or
    'edge', node attributes named 'id' or 'label', edge attributes
    named 'source' or 'target' (or 'key' if `G` is a multigraph)
    are ignored because these attribute names are used to encode the graph
    structure.

    GML files are stored using a 7-bit ASCII encoding with any extended
    ASCII characters (iso8859-1) appearing as HTML character entities.
    Without specifying a `stringizer`/`destringizer`, the code is capable of
    writing `int`/`float`/`str`/`dict`/`list` data as required by the GML
    specification.  For writing other data types, and for reading data other
    than `str` you need to explicitly supply a `stringizer`/`destringizer`.

    Note that while we allow non-standard GML to be read from a file, we make
    sure to write GML format. In particular, underscores are not allowed in
    attribute names.
    For additional documentation on the GML file format, please see the
    `GML url <https://web.archive.org/web/20190207140002/http://www.fim.uni-passau.de/index.php?id=17297&L=1>`_.

    See the module docstring :mod:`networkx.readwrite.gml` for more details.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_gml(G, "test.gml")

    Filenames ending in .gz or .bz2 will be compressed.

    >>> nx.write_gml(G, "test.gml.gz")
networkx.write_graph6
Python Library Documentation: function write_graph6 in module networkx.readwrite.graph6

write_graph6(G, path, nodes=None, header=True)
    Write a simple undirected graph to a path in graph6 format.

    Parameters
    ----------
    G : Graph (undirected)

    path : str
       The path naming the file to which to write the graph.

    nodes: list or iterable
       Nodes are labeled 0...n-1 in the order provided.  If None the ordering
       given by ``G.nodes()`` is used.

    header: bool
       If True add '>>graph6<<' string to head of data

    Raises
    ------
    NetworkXNotImplemented
        If the graph is directed or is a multigraph.

    ValueError
        If the graph has at least ``2 ** 36`` nodes; the graph6 format
        is only defined for graphs of order less than ``2 ** 36``.

    Examples
    --------
    You can write a graph6 file by giving the path to a file::

        >>> import tempfile
        >>> with tempfile.NamedTemporaryFile(delete=False) as f:
        ...     nx.write_graph6(nx.path_graph(2), f.name)
        ...     _ = f.seek(0)
        ...     print(f.read())
        b'>>graph6<<A_\n'

    See Also
    --------
    from_graph6_bytes, read_graph6

    Notes
    -----
    The function writes a newline character after writing the encoding
    of the graph.

    The format does not support edge or node labels, parallel edges or
    self loops.  If self loops are present they are silently ignored.

    References
    ----------
    .. [1] Graph6 specification
           <http://users.cecs.anu.edu.au/~bdm/data/formats.html>
networkx.write_graphml
Python Library Documentation: function write_graphml_lxml in module networkx.readwrite.graphml

write_graphml_lxml(G, path, encoding='utf-8', prettyprint=True, infer_numeric_types=False, named_key_ids=False, edge_id_from_attribute=None)
    Write G in GraphML XML format to path

    This function uses the LXML framework and should be faster than
    the version using the xml library.

    Parameters
    ----------
    G : graph
       A networkx graph
    path : file or string
       File or filename to write.
       Filenames ending in .gz or .bz2 will be compressed.
    encoding : string (optional)
       Encoding for text data.
    prettyprint : bool (optional)
       If True use line breaks and indenting in output XML.
    infer_numeric_types : boolean
       Determine if numeric types should be generalized.
       For example, if edges have both int and float 'weight' attributes,
       we infer in GraphML that both are floats.
    named_key_ids : bool (optional)
       If True use attr.name as value for key elements' id attribute.
    edge_id_from_attribute : dict key (optional)
        If provided, the graphml edge id is set by looking up the corresponding
        edge data attribute keyed by this parameter. If `None` or the key does not exist in edge data,
        the edge id is set by the edge key if `G` is a MultiGraph, else the edge id is left unset.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_graphml_lxml(G, "fourpath.graphml")

    Notes
    -----
    This implementation does not support mixed graphs (directed
    and unidirected edges together) hyperedges, nested graphs, or ports.
networkx.write_graphml_lxml
Python Library Documentation: function write_graphml_lxml in module networkx.readwrite.graphml

write_graphml_lxml(G, path, encoding='utf-8', prettyprint=True, infer_numeric_types=False, named_key_ids=False, edge_id_from_attribute=None)
    Write G in GraphML XML format to path

    This function uses the LXML framework and should be faster than
    the version using the xml library.

    Parameters
    ----------
    G : graph
       A networkx graph
    path : file or string
       File or filename to write.
       Filenames ending in .gz or .bz2 will be compressed.
    encoding : string (optional)
       Encoding for text data.
    prettyprint : bool (optional)
       If True use line breaks and indenting in output XML.
    infer_numeric_types : boolean
       Determine if numeric types should be generalized.
       For example, if edges have both int and float 'weight' attributes,
       we infer in GraphML that both are floats.
    named_key_ids : bool (optional)
       If True use attr.name as value for key elements' id attribute.
    edge_id_from_attribute : dict key (optional)
        If provided, the graphml edge id is set by looking up the corresponding
        edge data attribute keyed by this parameter. If `None` or the key does not exist in edge data,
        the edge id is set by the edge key if `G` is a MultiGraph, else the edge id is left unset.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_graphml_lxml(G, "fourpath.graphml")

    Notes
    -----
    This implementation does not support mixed graphs (directed
    and unidirected edges together) hyperedges, nested graphs, or ports.
networkx.write_graphml_xml
Python Library Documentation: function write_graphml_xml in module networkx.readwrite.graphml

write_graphml_xml(G, path, encoding='utf-8', prettyprint=True, infer_numeric_types=False, named_key_ids=False, edge_id_from_attribute=None)
    Write G in GraphML XML format to path

    Parameters
    ----------
    G : graph
       A networkx graph
    path : file or string
       File or filename to write.
       Filenames ending in .gz or .bz2 will be compressed.
    encoding : string (optional)
       Encoding for text data.
    prettyprint : bool (optional)
       If True use line breaks and indenting in output XML.
    infer_numeric_types : boolean
       Determine if numeric types should be generalized.
       For example, if edges have both int and float 'weight' attributes,
       we infer in GraphML that both are floats.
    named_key_ids : bool (optional)
       If True use attr.name as value for key elements' id attribute.
    edge_id_from_attribute : dict key (optional)
        If provided, the graphml edge id is set by looking up the corresponding
        edge data attribute keyed by this parameter. If `None` or the key does not exist in edge data,
        the edge id is set by the edge key if `G` is a MultiGraph, else the edge id is left unset.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_graphml(G, "test.graphml")

    Notes
    -----
    This implementation does not support mixed graphs (directed
    and unidirected edges together) hyperedges, nested graphs, or ports.
networkx.write_latex
Python Library Documentation: function write_latex in module networkx.drawing.nx_latex

write_latex(Gbunch, path, **options)
    Write the latex code to draw the graph(s) onto `path`.

    This convenience function creates the latex drawing code as a string
    and writes that to a file ready to be compiled when `as_document` is True
    or ready to be ``import`` ed or ``include`` ed into your main LaTeX document.

    The `path` argument can be a string filename or a file handle to write to.

    Parameters
    ----------
    Gbunch : NetworkX graph or iterable of NetworkX graphs
        If Gbunch is a graph, it is drawn in a figure environment.
        If Gbunch is an iterable of graphs, each is drawn in a subfigure
        environment within a single figure environment.
    path : filename
        Filename or file handle to write to
    options : dict
        By default, TikZ is used with options: (others are ignored)::

            pos : string or dict or list
                The name of the node attribute on `G` that holds the position of each node.
                Positions can be sequences of length 2 with numbers for (x,y) coordinates.
                They can also be strings to denote positions in TikZ style, such as (x, y)
                or (angle:radius).
                If a dict, it should be keyed by node to a position.
                If an empty dict, a circular layout is computed by TikZ.
                If you are drawing many graphs in subfigures, use a list of position dicts.
            tikz_options : string
                The tikzpicture options description defining the options for the picture.
                Often large scale options like `[scale=2]`.
            default_node_options : string
                The draw options for a path of nodes. Individual node options override these.
            node_options : string or dict
                The name of the node attribute on `G` that holds the options for each node.
                Or a dict keyed by node to a string holding the options for that node.
            node_label : string or dict
                The name of the node attribute on `G` that holds the node label (text)
                displayed for each node. If the attribute is "" or not present, the node
                itself is drawn as a string. LaTeX processing such as ``"$A_1$"`` is allowed.
                Or a dict keyed by node to a string holding the label for that node.
            default_edge_options : string
                The options for the scope drawing all edges. The default is "[-]" for
                undirected graphs and "[->]" for directed graphs.
            edge_options : string or dict
                The name of the edge attribute on `G` that holds the options for each edge.
                If the edge is a self-loop and ``"loop" not in edge_options`` the option
                "loop," is added to the options for the self-loop edge. Hence you can
                use "[loop above]" explicitly, but the default is "[loop]".
                Or a dict keyed by edge to a string holding the options for that edge.
            edge_label : string or dict
                The name of the edge attribute on `G` that holds the edge label (text)
                displayed for each edge. If the attribute is "" or not present, no edge
                label is drawn.
                Or a dict keyed by edge to a string holding the label for that edge.
            edge_label_options : string or dict
                The name of the edge attribute on `G` that holds the label options for
                each edge. For example, "[sloped,above,blue]". The default is no options.
                Or a dict keyed by edge to a string holding the label options for that edge.
            caption : string
                The caption string for the figure environment
            latex_label : string
                The latex label used for the figure for easy referral from the main text
            sub_captions : list of strings
                The sub_caption string for each subfigure in the figure
            sub_latex_labels : list of strings
                The latex label for each subfigure in the figure
            n_rows : int
                The number of rows of subfigures to arrange for multiple graphs
            as_document : bool
                Whether to wrap the latex code in a document environment for compiling
            document_wrapper : formatted text string with variable ``content``.
                This text is called to evaluate the content embedded in a document
                environment with a preamble setting up the TikZ syntax.
            figure_wrapper : formatted text string
                This text is evaluated with variables ``content``, ``caption`` and ``label``.
                It wraps the content and if a caption is provided, adds the latex code for
                that caption, and if a label is provided, adds the latex code for a label.
            subfigure_wrapper : formatted text string
                This text evaluate variables ``size``, ``content``, ``caption`` and ``label``.
                It wraps the content and if a caption is provided, adds the latex code for
                that caption, and if a label is provided, adds the latex code for a label.
                The size is the vertical size of each row of subfigures as a fraction.

    See Also
    ========
    to_latex
networkx.write_multiline_adjlist
Python Library Documentation: function write_multiline_adjlist in module networkx.readwrite.multiline_adjlist

write_multiline_adjlist(G, path, delimiter=' ', comments='#', encoding='utf-8')
    Write the graph G in multiline adjacency list format to path

    Parameters
    ----------
    G : NetworkX graph

    path : string or file
       Filename or file handle to write to.
       Filenames ending in .gz or .bz2 will be compressed.

    comments : string, optional
       Marker for comment lines

    delimiter : string, optional
       Separator for node labels

    encoding : string, optional
       Text encoding.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_multiline_adjlist(G, "test.adjlist")

    The path can be a file handle or a string with the name of the file. If a
    file handle is provided, it has to be opened in 'wb' mode.

    >>> fh = open("test.adjlist", "wb")
    >>> nx.write_multiline_adjlist(G, fh)

    Filenames ending in .gz or .bz2 will be compressed.

    >>> nx.write_multiline_adjlist(G, "test.adjlist.gz")

    See Also
    --------
    read_multiline_adjlist
networkx.write_network_text
Python Library Documentation: function write_network_text in module networkx.readwrite.text

write_network_text(graph, path=None, with_labels=True, sources=None, max_depth=None, ascii_only=False, end='\n', vertical_chains=False)
    Creates a nice text representation of a graph

    This works via a depth-first traversal of the graph and writing a line for
    each unique node encountered. Non-tree edges are written to the right of
    each node, and connection to a non-tree edge is indicated with an ellipsis.
    This representation works best when the input graph is a forest, but any
    graph can be represented.

    Parameters
    ----------
    graph : nx.DiGraph | nx.Graph
        Graph to represent

    path : string or file or callable or None
       Filename or file handle for data output.
       if a function, then it will be called for each generated line.
       if None, this will default to "sys.stdout.write"

    with_labels : bool | str
        If True will use the "label" attribute of a node to display if it
        exists otherwise it will use the node value itself. If given as a
        string, then that attribute name will be used instead of "label".
        Defaults to True.

    sources : List
        Specifies which nodes to start traversal from. Note: nodes that are not
        reachable from one of these sources may not be shown. If unspecified,
        the minimal set of nodes needed to reach all others will be used.

    max_depth : int | None
        The maximum depth to traverse before stopping. Defaults to None.

    ascii_only : Boolean
        If True only ASCII characters are used to construct the visualization

    end : string
        The line ending character

    vertical_chains : Boolean
        If True, chains of nodes will be drawn vertically when possible.

    Examples
    --------
    >>> graph = nx.balanced_tree(r=2, h=2, create_using=nx.DiGraph)
    >>> nx.write_network_text(graph)
    ╙── 0
        ├─╼ 1
        │   ├─╼ 3
        │   └─╼ 4
        └─╼ 2
            ├─╼ 5
            └─╼ 6

    >>> # A near tree with one non-tree edge
    >>> graph.add_edge(5, 1)
    >>> nx.write_network_text(graph)
    ╙── 0
        ├─╼ 1 ╾ 5
        │   ├─╼ 3
        │   └─╼ 4
        └─╼ 2
            ├─╼ 5
            │   └─╼  ...
            └─╼ 6

    >>> graph = nx.cycle_graph(5)
    >>> nx.write_network_text(graph)
    ╙── 0
        ├── 1
        │   └── 2
        │       └── 3
        │           └── 4 ─ 0
        └──  ...

    >>> graph = nx.cycle_graph(5, nx.DiGraph)
    >>> nx.write_network_text(graph, vertical_chains=True)
    ╙── 0 ╾ 4
        ╽
        1
        ╽
        2
        ╽
        3
        ╽
        4
        └─╼  ...

    >>> nx.write_network_text(graph, vertical_chains=True, ascii_only=True)
    +-- 0 <- 4
        !
        1
        !
        2
        !
        3
        !
        4
        L->  ...

    >>> graph = nx.generators.barbell_graph(4, 2)
    >>> nx.write_network_text(graph, vertical_chains=False)
    ╙── 4
        ├── 5
        │   └── 6
        │       ├── 7
        │       │   ├── 8 ─ 6
        │       │   │   └── 9 ─ 6, 7
        │       │   └──  ...
        │       └──  ...
        └── 3
            ├── 0
            │   ├── 1 ─ 3
            │   │   └── 2 ─ 0, 3
            │   └──  ...
            └──  ...
    >>> nx.write_network_text(graph, vertical_chains=True)
    ╙── 4
        ├── 5
        │   │
        │   6
        │   ├── 7
        │   │   ├── 8 ─ 6
        │   │   │   │
        │   │   │   9 ─ 6, 7
        │   │   └──  ...
        │   └──  ...
        └── 3
            ├── 0
            │   ├── 1 ─ 3
            │   │   │
            │   │   2 ─ 0, 3
            │   └──  ...
            └──  ...

    >>> graph = nx.complete_graph(5, create_using=nx.Graph)
    >>> nx.write_network_text(graph)
    ╙── 0
        ├── 1
        │   ├── 2 ─ 0
        │   │   ├── 3 ─ 0, 1
        │   │   │   └── 4 ─ 0, 1, 2
        │   │   └──  ...
        │   └──  ...
        └──  ...

    >>> graph = nx.complete_graph(3, create_using=nx.DiGraph)
    >>> nx.write_network_text(graph)
    ╙── 0 ╾ 1, 2
        ├─╼ 1 ╾ 2
        │   ├─╼ 2 ╾ 0
        │   │   └─╼  ...
        │   └─╼  ...
        └─╼  ...
networkx.write_pajek
Python Library Documentation: function write_pajek in module networkx.readwrite.pajek

write_pajek(G, path, encoding='UTF-8')
    Write graph in Pajek format to path.

    Parameters
    ----------
    G : graph
       A Networkx graph
    path : file or string
       File or filename to write.
       Filenames ending in .gz or .bz2 will be compressed.

    Examples
    --------
    >>> G = nx.path_graph(4)
    >>> nx.write_pajek(G, "test.net")

    Warnings
    --------
    Optional node attributes and edge attributes must be non-empty strings.
    Otherwise it will not be written into the file. You will need to
    convert those attributes to strings if you want to keep them.

    References
    ----------
    See http://vlado.fmf.uni-lj.si/pub/networks/pajek/doc/draweps.htm
    for format information.
networkx.write_sparse6
Python Library Documentation: function write_sparse6 in module networkx.readwrite.sparse6

write_sparse6(G, path, nodes=None, header=True)
    Write graph G to given path in sparse6 format.

    Parameters
    ----------
    G : Graph (undirected)

    path : file or string
       File or filename to write

    nodes: list or iterable
       Nodes are labeled 0...n-1 in the order provided.  If None the ordering
       given by G.nodes() is used.

    header: bool
       If True add '>>sparse6<<' string to head of data

    Raises
    ------
    NetworkXError
        If the graph is directed

    Examples
    --------
    You can write a sparse6 file by giving the path to the file::

        >>> import tempfile
        >>> with tempfile.NamedTemporaryFile(delete=False) as f:
        ...     nx.write_sparse6(nx.path_graph(2), f.name)
        ...     print(f.read())
        b'>>sparse6<<:An\n'

    You can also write a sparse6 file by giving an open file-like object::

        >>> with tempfile.NamedTemporaryFile() as f:
        ...     nx.write_sparse6(nx.path_graph(2), f)
        ...     _ = f.seek(0)
        ...     print(f.read())
        b'>>sparse6<<:An\n'

    See Also
    --------
    read_sparse6, from_sparse6_bytes

    Notes
    -----
    The format does not support edge or node labels.

    References
    ----------
    .. [1] Sparse6 specification
           <https://users.cecs.anu.edu.au/~bdm/data/formats.html>
networkx.write_weighted_edgelist
Python Library Documentation: function write_weighted_edgelist in module networkx.readwrite.edgelist

write_weighted_edgelist(G, path, comments='#', delimiter=' ', encoding='utf-8')
    Write graph G as a list of edges with numeric weights.

    Parameters
    ----------
    G : graph
       A NetworkX graph
    path : file or string
       File or filename to write. If a file is provided, it must be
       opened in 'wb' mode.
       Filenames ending in .gz or .bz2 will be compressed.
    comments : string, optional
       The character used to indicate the start of a comment
    delimiter : string, optional
       The string used to separate values.  The default is whitespace.
    encoding: string, optional
       Specify which encoding to use when writing file.

    Examples
    --------
    >>> G = nx.Graph()
    >>> G.add_edge(1, 2, weight=7)
    >>> nx.write_weighted_edgelist(G, "test.weighted.edgelist")

    See Also
    --------
    read_edgelist
    write_edgelist
    read_weighted_edgelist