
    *e                    \    d Z ddlmZ ddlmZmZmZmZ  ed          ZddZ	ddZ
ddZdS )z&Helpers for manipulations with graphs.    )annotations)AbstractSetIterableIteratorTypeVarTverticesAbstractSet[T]edgesdict[T, list[T]]returnIterator[set[T]]c              #     K   t                      g i g dfd| D ]}|vr |          E d{V  dS )a  Compute Strongly Connected Components of a directed graph.

    Args:
      vertices: the labels for the vertices
      edges: for each vertex, gives the target vertices of its outgoing edges

    Returns:
      An iterator yielding strongly connected components, each
      represented as a set of vertices.  Each input vertex will occur
      exactly once; vertices not part of a SCC are returned as
      singleton sets.

    From https://code.activestate.com/recipes/578507/.
    vr   r   r   c              3    K   t                    | <                       |                                |                     |          D ]T}|vr |          E d {V  |vr8|         d         k     r&                                 |         d         k     &Ud         |          k    rW                                 t          |          d                    }|          d =                     |           |V  d S d S )N)lenappendpopsetupdate)	r   wscc
boundariesdfsr   
identifiedindexstacks	      0lib/python3.11/site-packages/mypy/graph_utils.pyr   z*strongly_connected_components.<locals>.dfs    s8     u::aQ%(###q 	% 	%A~~3q66!!!!!!!!*$$AhB//NN$$$ AhB// b>U1X%%NNeE!HJJ'((CeAhjj!c"""IIIII &%    N)r   r   r   r   )r   )r	   r   r   r   r   r   r   r   s    ` @@@@@r   strongly_connected_componentsr!   
   s      " JEEJ          &   E>>s1vv r    sccslist[set[T]])dict[AbstractSet[T], set[AbstractSet[T]]]c                    d | D             i }| D ]N}t                      }|D ])}|                    fd||         D                        *||t          |          <   O|S )zLUse original edges to organize SCCs in a graph by dependencies between them.c                8    i | ]}|D ]}|t          |          S  )	frozenset).0r   r   s      r   
<dictcomp>z prepare_sccs.<locals>.<dictcomp><   s-    >>>S#>>Qq)C..>>>>r    c              3  (   K   | ]}|         V  d S )Nr'   )r)   xsccsmaps     r   	<genexpr>zprepare_sccs.<locals>.<genexpr>A   s'      55q
555555r    )r   r   r(   )r"   r   datar   depsr   r-   s         @r   prepare_sccsr1   8   s     ?>D>>>G68D $ $$'EE 	6 	6AKK5555E!H5555555#Ys^^Kr    r/   dict[T, set[T]]Iterable[set[T]]c              #    K   |                                  D ]\  }}|                    |           t          j        |                                  t          |                                           z
  D ]}t                      | |<   	 d |                                  D             sn%V  fd|                                  D             } F| rJ d|             dS )a  Topological sort.

    Args:
      data: A map from vertices to all vertices that it has an edge
            connecting it to.  NOTE: This data structure
            is modified in place -- for normalization purposes,
            self-dependencies are removed and entries representing
            orphans are added.

    Returns:
      An iterator yielding sets of vertices that have an equivalent
      ordering.

    Example:
      Suppose the input has the following structure:

        {A: {B, C}, B: {D}, C: {D}}

      This is normalized to:

        {A: {B, C}, B: {D}, C: {D}, D: {}}

      The algorithm will yield the following values:

        {D}
        {B, C}
        {A}

    From https://code.activestate.com/recipes/577413/.
    Tc                    h | ]	\  }}||
S r'   r'   )r)   itemdeps      r   	<setcomp>ztopsort.<locals>.<setcomp>k   s!    ???)$3????r    c                *    i | ]\  }}|v	||z
  S r'   r'   )r)   r6   r7   readys      r   r*   ztopsort.<locals>.<dictcomp>o   s.    WWW	cTQVEVEVsU{EVEVEVr    z#A cyclic dependency exists amongst N)itemsdiscardr   unionvalueskeys)r/   kr   r6   r:   s       @r   topsortrA   F   s      @ 

  1			!	4;;==)C		,<,<<  UUT

X??tzz||??? 	WWWWTZZ\\WWWX CCC4CCCCCCCr    N)r	   r
   r   r   r   r   )r"   r#   r   r   r   r$   )r/   r2   r   r3   )__doc__
__future__r   typingr   r   r   r   r   r!   r1   rA   r'   r    r   <module>rE      s    , , " " " " " " ; ; ; ; ; ; ; ; ; ; ; ;GCLL+ + + +\   *D *D *D *D *D *Dr    