
    01iV                       S r SSKJr  / SQrSSKJr  SSKJr  SSKJr  SSK	J
r
JrJrJrJrJrJrJrJr  SSKJrJrJrJr  SS	KJrJrJrJr  \
(       a  SS
KJr  S r " S S5      r  " S S5      r! " S S\5      r"\\#/\$4   r%\\\$\#4   \\\$\#4   4   r&\\&S4   r'\\\'\#4      r(\\#\\$\#4   4   r) " S S5      r*\/ S4   r+ " S S5      r,S!S jr-S"S jr. S#     S$S jjr/S%S jr0\" 5       r1S&S jr2S&S jr3S'S jr4S  r5g)(a  
A collection of utilities for canonicalizing and inspecting graphs.

Among other things, they solve of the problem of deterministic bnode
comparisons.

Warning: the time to canonicalize bnodes may increase exponentially on
degenerate larger graphs. Use with care!

Example of comparing two graphs:

```python
>>> g1 = Graph().parse(format='n3', data='''
...     @prefix : <http://example.org/ns#> .
...     <http://example.org> :rel
...         <http://example.org/same>,
...         [ :label "Same" ],
...         <http://example.org/a>,
...         [ :label "A" ] .
... ''')
>>> g2 = Graph().parse(format='n3', data='''
...     @prefix : <http://example.org/ns#> .
...     <http://example.org> :rel
...         <http://example.org/same>,
...         [ :label "Same" ],
...         <http://example.org/b>,
...         [ :label "B" ] .
... ''')
>>>
>>> iso1 = to_isomorphic(g1)
>>> iso2 = to_isomorphic(g2)

```

These are not isomorphic

```python
>>> iso1 == iso2
False

```

Diff the two graphs:

```python
>>> in_both, in_first, in_second = graph_diff(iso1, iso2)

```

Present in both:

```python
>>> def dump_nt_sorted(g):
...     for l in sorted(g.serialize(format='nt').splitlines()):
...         if l: print(l.decode('ascii'))
>>> dump_nt_sorted(in_both) #doctest: +SKIP
<http://example.org>
    <http://example.org/ns#rel> <http://example.org/same> .
<http://example.org>
    <http://example.org/ns#rel> _:cbcaabaaba17fecbc304a64f8edee4335e .
_:cbcaabaaba17fecbc304a64f8edee4335e
    <http://example.org/ns#label> "Same" .
```

Only in first:

```python
>>> dump_nt_sorted(in_first) #doctest: +SKIP
<http://example.org>
    <http://example.org/ns#rel> <http://example.org/a> .
<http://example.org>
    <http://example.org/ns#rel> _:cb124e4c6da0579f810c0ffe4eff485bd9 .
_:cb124e4c6da0579f810c0ffe4eff485bd9
    <http://example.org/ns#label> "A" .
```

Only in second:

```python
>>> dump_nt_sorted(in_second) #doctest: +SKIP
<http://example.org>
    <http://example.org/ns#rel> <http://example.org/b> .
<http://example.org>
    <http://example.org/ns#rel> _:cb558f30e21ddfc05ca53108348338ade8 .
_:cb558f30e21ddfc05ca53108348338ade8
    <http://example.org/ns#label> "B" .
```
    )annotations)IsomorphicGraphto_isomorphic
isomorphicto_canonical_graph
graph_diffsimilar)defaultdict)datetime)sha256)	TYPE_CHECKINGCallableDictIteratorListOptionalSetTupleUnion)ConjunctiveGraphGraphReadOnlyGraphAggregate_TripleType)BNodeIdentifiedNodeNodeURIRef)HASHc                n    U R                   S-  S-  S-  nXR                  -  nXR                  S-  -  nU$ )N   <   g    .A)dayssecondsmicroseconds)tdresults     H/home/james-whalen/.local/lib/python3.13/site-packages/rdflib/compare.py_total_secondsr(      s;    WWr\B#F
jjF
oo	))FM    c                       \ rS rSrS rS rSrg)_runtime   c                    Xl         g Nlabelselfr0   s     r'   __init___runtime.__init__       
r)   c                Z   ^ ^ T R                   c  TR                  S-   T l         UU 4S jnU$ )Nr+   c                    > [         R                  " 5       nT" U 0 UD6nSU;   a9  US   b3  US   n[        [         R                  " 5       U-
  5      UTR                  '   U$ )Nstats)r   nowr(   r0   )argskwargsstartr&   r8   fr2   s        r'   	wrapped_f$_runtime.__call__.<locals>.wrapped_f   sZ    LLNE''F& VG_%@w$28<<>E3I$Jdjj!Mr)   r0   __name__r2   r=   r>   s   `` r'   __call___runtime.__call__   s*    ::j0DJ	 r)   r/   NrA   
__module____qualname____firstlineno__r3   rC   __static_attributes__ r)   r'   r+   r+          r)   r+   c                       \ rS rSrS rS rSrg)_call_count   c                    Xl         g r.   r/   r1   s     r'   r3   _call_count.__init__   r5   r)   c                Z   ^ ^ T R                   c  TR                  S-   T l         UU 4S jnU$ )Nr+   c                    > SU;   aA  US   b;  US   nTR                   U;  a  SUTR                   '   UTR                   ==   S-  ss'   T" U 0 UD6$ )Nr8   r      r/   )r:   r;   r8   r=   r2   s      r'   r>   '_call_count.__call__.<locals>.wrapped_f   s[    & VG_%@w::U*()E$**%djj!Q&!d%f%%r)   r@   rB   s   `` r'   rC   _call_count.__call__   s*    ::j0DJ	& r)   r/   NrE   rJ   r)   r'   rM   rM      rK   r)   rM   c                  X   ^  \ rS rSrSrU 4S jrS rS rU 4S jrS
S jr	S
S jr
S	rU =r$ )r      a  An implementation of the RGDA1 graph digest algorithm.

An implementation of RGDA1 (publication below),
a combination of Sayers & Karp's graph digest algorithm using
sum and SHA-256 <http://www.hpl.hp.com/techreports/2003/HPL-2003-235R1.pdf>
and traces <http://pallini.di.uniroma1.it>, an average case
polynomial time algorithm for graph canonicalization.

McCusker, J. P. (2015). WebSig: A Digital Signature Framework for the Web.
Rensselaer Polytechnic Institute, Troy, NY.
http://gradworks.umi.com/3727015.pdf
c                .   > [         [        U ]
  " S0 UD6  g )NrJ   )superr   r3   )r2   r;   	__class__s     r'   r3   IsomorphicGraph.__init__   s    ot-77r)   c                    [        U[        5      (       d  g[        U 5      [        U5      :w  a  gU R                  5       UR                  5       :H  $ )zGraph isomorphism testing.F)
isinstancer   leninternal_hashr2   others     r'   __eq__IsomorphicGraph.__eq__   sB    %11Y#e*$!!#u':':'<<<r)   c                .    U R                  U5      (       + $ )z#Negative graph isomorphism testing.)rb   r`   s     r'   __ne__IsomorphicGraph.__ne__   s    ;;u%%%r)   c                (   > [         [        U ]  5       $ r.   )rY   r   __hash__)r2   rZ   s    r'   rh   IsomorphicGraph.__hash__   s    _d466r)   c                     U R                  US9$ )z*Synonym for IsomorphicGraph.internal_hash.r8   )r_   r2   r8   s     r'   graph_digestIsomorphicGraph.graph_digest   s    !!!..r)   c                2    [        U 5      R                  US9$ )z
This is defined instead of `__hash__` to avoid a circular recursion
scenario with the Memory store for rdflib which requires a hash lookup
in order to return a generator of triples.
rk   _TripleCanonicalizerto_hashrl   s     r'   r_   IsomorphicGraph.internal_hash   s     $D)111>>r)   rJ   r.   )rA   rF   rG   rH   __doc__r3   rb   re   rh   rm   r_   rI   __classcell__)rZ   s   @r'   r   r      s+    8=&7/? ?r)   r   .c                  d    \ rS rSr  S       SS jjrS rS rSSS jjrSS jrS r	S	 r
S
rg)Color   Nc                L    Uc  0 nX@l         X0l        Xl        X l        S U l        g r.   )_hash_cachecolornodeshashfunc_hash_color)r2   r|   r}   r{   
hash_caches        r'   r3   Color.__init__   s,     J%

 r)   c                <    U R                  5       u  pSU< SU< S3$ )NzColor z (z nodes)key)r2   r|   r{   s      r'   __str__Color.__str__   s    xxzu(-u55r)   c                L    [        U R                  5      U R                  5       4$ r.   )r^   r|   
hash_colorr2   s    r'   r   	Color.key   s    DJJ!233r)   c                V   Uc  U R                   nXR                  ;   a  U R                  U   $ S n[        U[        5      (       a  U" U5      $ SnU H;  nX0R	                  SR                  U Vs/ s H
  oR" U5      PM     sn5      5      -  nM=     SU-  nX`R                  U'   U$ s  snf )Nc                b    [        U [        5      (       a  U R                  5       $ [        U 5      $ r.   )r]   r   n3strxs    r'   	stringify#Color.hash_color.<locals>.stringify   s#    !T""ttv1vr)   r    %x)r{   rz   r]   r   r}   join)r2   r{   r   valuetripler   vals          r'   r   Color.hash_color   s    =JJE$$$##E**	 eT""U##F]]3886,J6aYq\6,J#KLLE %<"%
 -Ks   /B&c                z   0 nU R                    GH  n[        U R                  5      nUR                    H  nUUR                  US U45       VVV	s/ s H  u  pxn	SXR	                  5       4PM     sn	nn-  nUUR                  US U45       VVV	s/ s H  u  pxoR	                  5       US4PM     sn	nn-  nM     [        U5      nU R	                  U5      n
X;  a#  [        / U R                  XPR                  S9nXU
'   X:   R                   R                  U5        GM     UR                  5       $ s  sn	nnf s  sn	nnf )NrS      r   )r|   listr{   triplesr   tuplerw   r}   rz   appendvalues)r2   Wgraphcolorsn	new_colornodesponew_hash_colorcs               r'   distinguishColor.distinguish  s$   #%A/3DJJ/?I:?--DRV:X:XwqQQ<<>*:X 	 :?--tUV:X:XwqQ\\^Q*:X 		   i(I!__Y7N+"dmmYCSCST)*~&"((//2   }}s   D/D6c                2    [        U R                  5      S:H  $ )NrS   )r^   r|   r   s    r'   discreteColor.discrete!  s    4::!##r)   c                p    [        U R                  S S  U R                  U R                  U R                  S9$ Nr   )rw   r|   r}   r{   rz   r   s    r'   copy
Color.copy$  s.    JJqM4==$**AQAQ
 	
r)   )rz   r~   r{   r}   r|   )rJ   N)r|   zList[IdentifiedNode]r}   HashFuncr{   ColorItemTupler   	HashCacher.   )r{   zOptional[Tuple[ColorItem, ...]]returnr   )r   rw   r   r   )rA   rF   rG   rH   r3   r   r   r   r   r   r   rI   rJ   r)   r'   rw   rw      sS    
 !# $ #    	 
  64*($
r)   rw   r   c                      \ rS rSr\4SS jjrSS jrSS jrS rSS jr	SS jr
\" S5      SSS
 jj5       rSS jr S     SS jjr\" S5      S	S/4       SS jj5       rSSS jjr    SS jrSrg	)rq   i-  c                <   ^ Xl         SU4S jjn0 U l        X0l        g )Nc                   > T" 5       nUR                  [        U 5      R                  S5      5        [        UR	                  5       S5      $ )Nutf8   )updater   encodeint	hexdigest)r   hr}   s     r'   	_hashfunc0_TripleCanonicalizer.__init__.<locals>._hashfunc1  s6    
AHHSV]]6*+q{{}b))r)   )r   r   )r   rz   r}   )r2   r   r}   r   s     ` r'   r3   _TripleCanonicalizer.__init__.  s    
	*
 ')!r)   c                v    [        U Vs/ s H  o"R                  5       (       a  M  UPM     sn5      S:H  $ s  snf Nr   )r^   r   )r2   coloringr   s      r'   	_discrete_TripleCanonicalizer._discrete9  s*    x<x!zz|Ax<=BB<s   66c                   [        5       n[        5       n[        [         5      U l        U R                   GH  u  p4n[        X4U/5      n[        U Vs/ s H  n[	        U[
        5      (       d  M  UPM     sn5      n[        U5      S:  d  MX  X&U-
  -  nX-  n[	        U[
        5      (       a  U R                  U   R                  U5        [	        U[
        5      (       a  U R                  U   R                  U5        [	        U[
        5      (       d  M  U R                  U   R                  U5        U R                  U   R                  U5        GM     [        U5      S:  a[  [        [        U5      U R                  U R                  S9/U Vs/ s H#  n[        U/U R                  XpR                  S9PM%     sn-   $ / $ s  snf s  snf )a4  Finds an initial color for the graph.

Finds an initial color of the graph by finding all blank nodes and
non-blank nodes that are adjacent. Nodes that are not adjacent to blank
nodes are not included, as they are a) already colored (by URI or literal)
and b) do not factor into the color of any blank node.
r   r   )setr
   
_neighborsr   r]   r   r^   addrw   r   r}   rz   )	r2   bnodesothersr   r   r   r|   r   bs	            r'   _initial_color#_TripleCanonicalizer._initial_color<  s|    !U%c*zzGA!q	NE>1Au)=Q>?A1vz!)#a''OOA&**1-a''OOA&**1-a''OOA&**1-OOA&**1- " v;?$v,$BRBRST  	X  A qc4==!8H8HI	X   I' ?Xs   G
/G
*Gc                   [        UR                  5      nUR                  [        UR                  5      45        UR                  R                  U5        [        U/U R                  [        U5      U R                  S9nU$ r   )
r   r{   r   r^   r|   removerw   r}   r   rz   )r2   r{   
individualr   r   s        r'   _individuate!_TripleCanonicalizer._individuate^  sg    %	#ekk*,-:&L$--y)9dFVFV
 r)   c              #     #    U Vs/ s H  o"R                  5       (       a  M  UPM     sn H  nUR                   H  nX24v   M
     M     g s  snf 7fr.   )r   r|   )r2   r   r   r   s       r'   _get_candidates$_TripleCanonicalizer._get_candidatesh  s<     %:XZZ\!X:Ag   ;:s   AAA(Ac                H   [        US SS9nUS S  n[        U5      S:  a  U R                  U5      (       d  UR                  5       nUS S   H  n[        UR                  5      S:  d$  [        UR                  S   [        5      (       d  M@  [        UR                  X0R                  5      S SS9nUR                  U5        UR                  U5         UR                  U5      nUS U U-   X&S-   S  -   nM     [        U5      S:  a  U R                  U5      (       d  M  / n[        5       nU HV  n	U	R                  5       n
X;   a)  X   R                  R                  U	R                  5        MA  UR                  U	5        XU
'   MX     U$ ! [         a    USS  U-   n GMT  f = f)Nc                "    U R                  5       $ r.   r   r   s    r'   <lambda>._TripleCanonicalizer._refine.<locals>.<lambda>n  s
    !%%'r)   T)r   reverser   rS   c                "    U R                  5       $ r.   r   r   s    r'   r   r   v  s
    aeegr)   )sortedr^   r   popr|   r]   r   r   r   r   extendindex
ValueErrordictr   r   )r2   r   sequencer   r   r   sicombined_colorscombined_color_mapr{   
color_hashs              r'   _refine_TripleCanonicalizer._refinem  s   ((94HA;(max(@(@Aa[qww<!#z!''!*e'D'D#a4- $F
 OOA&OOF+9%^^A.#+CR=6#9H!VX<N#N ! (max(@(@  (*/3vE))+J/".44;;EKKH&&u-16:.   & 9#)!":#89s   !F

F! F!to_hash_runtimeNc                    SnU R                  US9 HC  nX R                  SR                  U Vs/ s H  oDR                  5       PM     sn5      5      -  nME     Ub  SU-  US'   U$ s  snf )Nr   rk   r   r   rm   )canonical_triplesr}   r   r   )r2   r8   r&   r   r   s        r'   rr   _TripleCanonicalizer.to_hash  sk    ,,5,9FmmCHHf-Efddff-E$FGGF :$(6ME.! .Fs   A&c                   U Vs/ s H  o"R                  5       PM     nnU R                  U5      (       d  U Vs/ s H  o3R                  5       (       a  M  UPM     snS   nUR                  S   nU R	                  XE5      nUR                  U5        U R                  X/5      nU R                  U5      (       d  M  U$ s  snf s  snf r   )r   r   r   r|   r   r   r   )r2   r   r   r   r{   r   r   s          r'   _experimental_path'_TripleCanonicalizer._experimental_path  s    &./hFFHh/..** (=1

Q=a@E;;q>D))%6IOOI&||Hk:H ..**  0=s   B?CCc                    U(       d  [        [        5      n[        U6  HH  n[        U Vs/ s H  oDR                  S   PM     sn5      nU H
  nXRU   -  nM     U H  nXRU'   M	     MJ     U$ s  snf r   )r
   r   zipr|   )r2   	colorings	groupingsgroupr   gr   s          r'   _create_generator&_TripleCanonicalizer._create_generator  sr    
 #C(I)_E/AWWQZ/0Aq\!  ! 	 %  0s   A-
individuationsr   c                   Ub  SU;  a  SUS'   US==   S-  ss'   U R                  U5      n/ nS nS nS n[        [        5      n	[        5       n
U GH  u  pX;   a)  X   U
-  n[        U5      S:  a  U
R	                  U5        M4  U
R	                  U5        / nS nU H.  nUR                  5       nUR                  U5        UU:X  d  M,  UnM0     U R                  X5      nUR                  U5        U R                  UU/5      n[        U Vs/ s H  nUR                  5       PM     sn5      nU R                  U5      n[        U Vs/ s H  nUR                  5       PM     sn5      nU(       a  U R                  UU/U	5      n	UnUb  UU:  a
  U/nUnUnGMG  UU:  a1  Ub+  [        US   [        5      (       a  US==   S-  ss'   GMx  GM{  GM~  UU:w  a  UR                  U5        GM  Uc  GM  [        US   [        5      (       d  GM  US==   S-  ss'   GM     U Vs/ s H  nU R                  U5      (       d  M  UPM     nn[        U5      S:X  ag  S nS nU HX  nUS   /nU R!                  XUS9n[        W Vs/ s H  nUR                  5       PM     sn5      nUb  UU:  d  MN  U/nUnUS   nMZ     UUS'   US   $ s  snf s  snf s  snf s  snf )Npruningsr   rS   r8   depth)r   r
   r   r^   r   r   r   r   r   r   r   r   r   r]   r   r   _traces)r2   r   r8   r  
candidatesbest
best_scorebest_experimental_scorelast_coloring	generatorvisited	candidater{   vcoloring_copy
color_copyr   c_copyr   refined_coloringcolor_scoreexperimentalexperimental_scorer   r   
best_depthds                              r'   r  _TripleCanonicalizer._traces  s    5!8 !E*aA))(3
"$
"&+6s+;	 U *I%(72q6A:KK	*KK	")+MJ$$V,:!'J	 
 ))*@I  +#||MI;G2B C2BQ2B CDK22=AL!$|%D|!aeeg|%D!E 22"L19	 )M!Z+%=()(
*<'k)$E*4Es)K)K*%*% *L$#'>>,- $E*4Es)K)K*%*%O !+P 37&L$Q$..:Kq$&Lx=AJJ 1XJ LLaLH	#6F$G6FQUUW6F$GH%z)A ){H!,J!"1J ! "E!H{I !D%D* 'M %Hs   K 
K
K
=K
<K
c              #  *  #    Ub  [         R                  " 5       nU R                  5       nUb3  [        U R                  5      US'   [        S[        U5      S-
  5      US'   U R                  X3S S  5      nUb2  [        [         R                  " 5       W-
  5      US'   [        U5      US'   U R                  U5      (       d  S/nU R                  X1US9nUb  US   US'   OUb
  SUS	'   SUS'   Ub  [        U5      US
'   [        U Vs/ s H!  oUR                  S   UR                  5       4PM#     sn5      nUb$  [        [         R                  " 5       W-
  5      US'   U R                   H!  n[        U R                  Xv5      5      nUv   M#     g s  snf 7f)Ntriple_countr   rS   adjacent_nodesinitial_coloring_runtimeinitial_color_countr  
tree_depthr   color_countcanonicalize_triples_runtime)r   r9   r   r^   r   maxr   r(   r   r  r   r|   r   r   _canonicalize_bnodes)	r2   r8   start_coloringr   r  r   bnode_labelsr   r&   s	            r'   r   &_TripleCanonicalizer.canonical_triples  s    %\\^N&&($'

OE.!&)!S]Q->&?E"#<<1+60>/1E,- ,/x=E'(~~h''CE||H|GH &+Ahl#&'E"#"#E,#&x=E- (,3;<8aggaj!,,.)8<)
 4B/5E01 jjF444VJKFL ! =s   DF(F.A%Fc              #  t   #    U H.  n[        U[        5      (       a  [        SX#   -  S9v   M*  Uv   M0     g 7f)Nzcb%s)r   )r]   r   )r2   r   labelsterms       r'   r   )_TripleCanonicalizer._canonicalize_bnodes  s5     
 D$&&&6<"788
	 s   68)rz   r   r   r}   )r   r   r}   _HashT)r   List[Color]r   bool)r   r)  )r   r)  r   zIterator[Tuple[Node, Color]])r   r)  r   r)  r   r)  r.   )r8   Optional[Stats])r   r)  r   r)  )r   zList[List[Color]]r   zOptional[Dict[Node, Set[Node]]]r   zDict[Node, Set[Node]])r   r)  r8   r+  r  z	List[int]r   r)  )r   r   r%  zDict[Node, str])rA   rF   rG   rH   r   r3   r   r   r   r   r   r+   rr   r   r   rM   r  r   r   rI   rJ   r)   r'   rq   rq   -  s    8> 	"C D
>   ! 6:$ 3 
	 !" "&3	EE E 	E
 
E #EN"H		  	r)   rq   c                    [        U [        5      (       a  U $ [        5       n[        U S5      (       a  [        U R                  S9nX-  nU$ )N
identifier)r-  )r]   r   hasattrr-  )r   r&   s     r'   r   r   &  sE    %))Ful## E,<,<=
OFMr)   c                n    [        U 5      R                  5       n[        U5      R                  5       nX#:H  $ )aJ  Compare graph for equality.

Uses an algorithm to compute unique hashes which takes bnodes into account.

Example:
    ```python
    >>> g1 = Graph().parse(format='n3', data='''
    ...     @prefix : <http://example.org/ns#> .
    ...     <http://example.org> :rel <http://example.org/a> .
    ...     <http://example.org> :rel <http://example.org/b> .
    ...     <http://example.org> :rel [ :label "A bnode." ] .
    ... ''')
    >>> g2 = Graph().parse(format='n3', data='''
    ...     @prefix ns: <http://example.org/ns#> .
    ...     <http://example.org> ns:rel [ ns:label "A bnode." ] .
    ...     <http://example.org> ns:rel <http://example.org/b>,
    ...             <http://example.org/a> .
    ... ''')
    >>> isomorphic(g1, g2)
    True
    >>> g3 = Graph().parse(format='n3', data='''
    ...     @prefix : <http://example.org/ns#> .
    ...     <http://example.org> :rel <http://example.org/a> .
    ...     <http://example.org> :rel <http://example.org/b> .
    ...     <http://example.org> :rel <http://example.org/c> .
    ... ''')
    >>> isomorphic(g1, g3)
    False

    ```
rp   )graph1graph2gd1gd2s       r'   r   r   0  s3    @ v
&
.
.
0C
v
&
.
.
0C:r)   Nc                d    [        5       nU[        U 5      R                  US9-  n[        U/5      $ )zCreates a canonical, read-only graph.

Creates a canonical, read-only graph where all bnode id:s are based on
deterministical SHA-256 checksums, correlated with the graph contents.
rk   )r   rq   r   r   )g1r8   r   s      r'   r   r   U  s6     GE	!"%77e7DDE!5'**r)   c                N    [        U 5      n[        U5      nX#-  nX#-
  nX2-
  nXEU4$ )zEReturns three sets of triples: "in both", "in first" and "in second".)r   )r5  g2cg1cg2in_bothin_first	in_seconds          r'   r   r   b  s8     R
 C
R
 CiGyH	Iy))r)   c                8    [        S [        X5       5       5      $ )a$  Checks if the two graphs are "similar".

Checks if the two graphs are "similar", by comparing sorted triples where
all bnodes have been replaced by a singular mock bnode (the
`_MOCK_BNODE`).

This is a much cheaper, but less reliable, alternative to the comparison
algorithm in `isomorphic`.
c              3  .   #    U  H  u  pX:H  v   M     g 7fr.   rJ   ).0t1t2s      r'   	<genexpr>similar.<locals>.<genexpr>z  s     I(HHRrx(Hs   )all_squashed_graphs_triples)r5  r7  s     r'   r	   r	   p  s     I(@(HIIIr)   c              #     #    [        [        [        U 5      5      [        [        U5      5      5       H
  u  p#X#4v   M     g 7fr.   )r   r   _squash_graph)r5  r7  r@  rA  s       r'   rE  rE  }  s4     f]2./b8I1JKf Ls   A Ac                    S U  5       $ )Nc              3  8   #    U  H  n[        U5      v   M     g 7fr.   )_squash_bnodes)r?  r   s     r'   rB   _squash_graph.<locals>.<genexpr>  s     7vN6""s   rJ   )r   s    r'   rG  rG    s    777r)   c                &    [        S U  5       5      $ )Nc              3  n   #    U  H+  n[        U[        5      =(       a    [        =(       d    Uv   M-     g 7fr.   )r]   r   _MOCK_BNODE)r?  ts     r'   rB  !_squash_bnodes.<locals>.<genexpr>  s$     Mf*Q&6;<1<fs   35)r   )r   s    r'   rJ  rJ    s    MfMMMr)   )r   r   r   r   )r0  r   r1  r   r   r*  r.   )r5  r   r8   r+  r   r   )r5  r   r7  r   r   zTuple[Graph, Graph, Graph])r5  r   r7  r   )r   r   )6rt   
__future__r   __all__collectionsr
   r   hashlibr   typingr   r   r   r   r   r   r   r   r   rdflib.graphr   r   r   r   rdflib.termr   r   r   r   _hashlibr   r(   r+   rM   r   r   r   r   	ColorItemr   r   Statsrw   r(  rq   r   r   r   r   rN  r	   rE  rG  rJ  rJ   r)   r'   <module>r[     sU  Wr # $  
 
 
 V U ; ; & &*?& *?Z SE3J%S/65c?:;	y#~&T.#-./	S%S/!"F
 F
R 
"f*	v vr"L )-
+
+%
+
+* g
J
8Nr)   