
    \h>                     6    S SK Jr  S SKJr   " S S5      rS rg)    combinations)GrayCodec                   8   \ rS rSrSrSrSrSrSrSr	S r
S rS rS rS rS	 rS
 rS rS rS r\S 5       r\S 5       r\S 5       r\S 5       r\S 5       r\S 5       r\S 5       r\S 5       r\S 5       r\S 5       r\S 5       r \S 5       r!\S 5       r"Sr#g)Subset   a  
Represents a basic subset object.

Explanation
===========

We generate subsets using essentially two techniques,
binary enumeration and lexicographic enumeration.
The Subset class takes two arguments, the first one
describes the initial subset to consider and the second
describes the superset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.next_binary().subset
['b']
>>> a.prev_binary().subset
['c']
Nc                     [        U5      [        U5      :  a  [        S5      eU H"  nX2;  d  M
  [        SR                  U5      5      e   [        R	                  U 5      nXl        X$l        U$ )a  
Default constructor.

It takes the ``subset`` and its ``superset`` as its parameters.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.subset
['c', 'd']
>>> a.superset
['a', 'b', 'c', 'd']
>>> a.size
2
zRInvalid arguments have been provided. The superset must be larger than the subset.zFThe superset provided is invalid as it does not contain the element {})len
ValueErrorformatobject__new___subset	_superset)clssubsetsupersetelemobjs        S/var/www/auris/envauris/lib/python3.13/site-packages/sympy/combinatorics/subsets.pyr   Subset.__new__$   su    $ v;X& H I ID#  ">>DfTlL L  nnS! 
    c                     [        U[        5      (       d  [        $ U R                  UR                  :H  =(       a    U R                  UR                  :H  $ )zReturn a boolean indicating whether a == b on the basis of
whether both objects are of the class Subset and if the values
of the subset and superset attributes are the same.
)
isinstancer   NotImplementedr   r   )selfothers     r   __eq__Subset.__eq__B   s<    
 %((!!{{ell*Nt}}/NNr   c                 B   [         R                  U R                  U R                  5      n[	        SR                  U5      S5      U-   SU R                  -  -  n[        U5      SS R                  U R                  S5      n[         R                  U R                  U5      $ )a  
This is a helper function. It iterates over the
binary subsets by ``k`` steps. This variable can be
both positive or negative.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.iterate_binary(-2).subset
['d']
>>> a = Subset(['a', 'b', 'c'], ['a', 'b', 'c', 'd'])
>>> a.iterate_binary(2).subset
[]

See Also
========

next_binary, prev_binary
    N0)
r   bitlist_from_subsetr   r   intjoinsuperset_sizebinrjustsubset_from_bitlist)r   kbin_listnbitss        r   iterate_binarySubset.iterate_binaryK   s    , --dkk4==I"A&*a1C1C.CC1vabz 2 2C8))$-->>r   c                 $    U R                  S5      $ )aE  
Generates the next binary ordered subset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.next_binary().subset
['b']
>>> a = Subset(['a', 'b', 'c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.next_binary().subset
[]

See Also
========

prev_binary, iterate_binary
   r/   r   s    r   next_binarySubset.next_binaryf   s    ( ""1%%r   c                 $    U R                  S5      $ )aI  
Generates the previous binary ordered subset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset([], ['a', 'b', 'c', 'd'])
>>> a.prev_binary().subset
['a', 'b', 'c', 'd']
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.prev_binary().subset
['c']

See Also
========

next_binary, iterate_binary
r3   r4   s    r   prev_binarySubset.prev_binary|   s    ( ""2&&r   c                 D   U R                   S-
  n[        R                  U R                  U R                  5      nX;   a}  US-
  U;   a  UR                  US-
  5        OUR                  U5        US-
  nUS:  a  X;  a  US-
  nUS:  a  X;  a  M  US:  a%  UR                  U5        UR                  US-   5        O1X;  a  US:  a  US-
  nX;  a  US:  a  M  UR                  US-   5        / nU R                  nU H  nUR                  XA   5        M     [        X45      $ )aF  
Generates the next lexicographically ordered subset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.next_lexicographic().subset
['d']
>>> a = Subset(['d'], ['a', 'b', 'c', 'd'])
>>> a.next_lexicographic().subset
[]

See Also
========

prev_lexicographic
r2   r   r'   r   subset_indicesr   r   removeappendr   iindicesret_set	super_sets        r   next_lexicographicSubset.next_lexicographic   s   ( "''T]]C<1uq1u%q!E1f!1AA 1f!16NN1%NN1Q3'"qAvE "qAvNN1q5!MM	ANN9<( g))r   c                    U R                   S-
  n[        R                  U R                  U R                  5      nUS:  a  X;  a  US-
  nUS:  a  X;  a  M  US:X  d	  US-
  U;   a  UR                  U5        OIUS:  a%  UR                  U5        UR                  US-
  5        UR                  U R                   S-
  5        / nU R                  nU H  nUR                  XA   5        M     [        X45      $ )aI  
Generates the previous lexicographically ordered subset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset([], ['a', 'b', 'c', 'd'])
>>> a.prev_lexicographic().subset
['d']
>>> a = Subset(['c','d'], ['a', 'b', 'c', 'd'])
>>> a.prev_lexicographic().subset
['c']

See Also
========

next_lexicographic
r2   r   r<   r@   s        r   prev_lexicographicSubset.prev_lexicographic   s    ( "''T]]C1f)AA 1f) 6QUg%NN1Avq!q1u%NN4--12MM	ANN9<( g))r   c                     [         R                  " U R                  U R                  U-   U R                  -  5      n[
        R                  U R                  U5      $ )aV  
Helper function used for prev_gray and next_gray.
It performs ``k`` step overs to get the respective Gray codes.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset([1, 2, 3], [1, 2, 3, 4])
>>> a.iterate_graycode(3).subset
[1, 4]
>>> a.iterate_graycode(-2).subset
[1, 2, 4]

See Also
========

next_gray, prev_gray
)r   unrankr'   	rank_graycardinalityr   r*   r   )r   r+   unranked_codes      r   iterate_graycodeSubset.iterate_graycode   sN    ( !(:(:(,(:d>N>N'NP))$--*79 	9r   c                 $    U R                  S5      $ )z
Generates the next Gray code ordered subset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset([1, 2, 3], [1, 2, 3, 4])
>>> a.next_gray().subset
[1, 3]

See Also
========

iterate_graycode, prev_gray
r2   rO   r4   s    r   	next_graySubset.next_gray   s    " $$Q''r   c                 $    U R                  S5      $ )z
Generates the previous Gray code ordered subset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset([2, 3, 4], [1, 2, 3, 4, 5])
>>> a.prev_gray().subset
[2, 3, 4, 5]

See Also
========

iterate_graycode, next_gray
r8   rR   r4   s    r   	prev_graySubset.prev_gray  s    " $$R((r   c                     U R                   cH  [        SR                  [        R	                  U R
                  U R                  5      5      S5      U l         U R                   $ )a  
Computes the binary ordered rank.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset([], ['a','b','c','d'])
>>> a.rank_binary
0
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.rank_binary
3

See Also
========

iterate_binary, unrank_binary
r!   r"   )_rank_binaryr%   r&   r   r$   r   r   r4   s    r   rank_binarySubset.rank_binary&  sT    * $ #BGG**4;;+/==:%;<=!?D    r   c                    ^ U R                   cI  U4S jm[        R                  U R                  U R                  5      nT" XSU R
                  5      U l         U R                   $ )a	  
Computes the lexicographic ranking of the subset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.rank_lexicographic
14
>>> a = Subset([2, 4, 5], [1, 2, 3, 4, 5, 6])
>>> a.rank_lexicographic
43
c                    > U/ :X  d  X#:  a  gX!;   a!  UR                  U5        ST" XUS-   U5      -   $ SX2-
  S-
  -  T" XUS-   U5      -   $ )Nr   r2   r"   )r>   )r   subset_indexrA   r-   _ranklexs       r   r_   +Subset.rank_lexicographic.<locals>._ranklexR  s`    2%$ ''*xAE1EEE1519~QUA(NNNr   r   )	_rank_lexr   r=   r   r   r'   )r   rB   r_   s     @r   rank_lexicographicSubset.rank_lexicographicA  sQ      >>!O ++DKKGG%dQ8J8JKDN~~r   c                     U R                   cL  [        R                  U R                  U R                  5      n[        [        U5      US9R                  U l         U R                   $ )a   
Computes the Gray code ranking of the subset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset(['c','d'], ['a','b','c','d'])
>>> a.rank_gray
2
>>> a = Subset([2, 4, 5], [1, 2, 3, 4, 5, 6])
>>> a.rank_gray
27

See Also
========

iterate_graycode, unrank_gray
)start)_rank_graycoder   r$   r   r   r   r
   rank)r   r.   s     r   rL   Subset.rank_gray]  sO    * &--dkk4==ID"*3t9D"A"F"FD"""r   c                     U R                   $ )z
Gets the subset represented by the current instance.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.subset
['c', 'd']

See Also
========

superset, size, superset_size, cardinality
)r   r4   s    r   r   Subset.subsetw  s    $ ||r   c                 ,    [        U R                  5      $ )z
Gets the size of the subset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.size
2

See Also
========

subset, superset, superset_size, cardinality
)r
   r   r4   s    r   sizeSubset.size  s    $ 4;;r   c                     U R                   $ )z
Gets the superset of the subset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.superset
['a', 'b', 'c', 'd']

See Also
========

subset, size, superset_size, cardinality
)r   r4   s    r   r   Subset.superset  s    $ ~~r   c                 ,    [        U R                  5      $ )z
Returns the size of the superset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.superset_size
4

See Also
========

subset, superset, size, cardinality
)r
   r   r4   s    r   r'   Subset.superset_size  s    $ 4==!!r   c                      SU R                   -  $ )z
Returns the number of all possible subsets.

Examples
========

>>> from sympy.combinatorics import Subset
>>> a = Subset(['c', 'd'], ['a', 'b', 'c', 'd'])
>>> a.cardinality
16

See Also
========

subset, superset, size, superset_size
r"   )r'   r4   s    r   rM   Subset.cardinality  s    $ 4%%&&r   c                     [        U5      [        U5      :w  a  [        S5      e/ n[        [        U5      5       H   nX$   S:X  d  M  UR                  X   5        M"     [	        X15      $ )z
Gets the subset defined by the bitlist.

Examples
========

>>> from sympy.combinatorics import Subset
>>> Subset.subset_from_bitlist(['a', 'b', 'c', 'd'], '0011').subset
['c', 'd']

See Also
========

bitlist_from_subset
z$The sizes of the lists are not equal1)r
   r   ranger?   r   )r   rD   bitlistrC   rA   s        r   r*   Subset.subset_from_bitlist  s]    " y>S\)CDDs7|$AzS y|, % g))r   c                     S/[        U5      -  n[        U[        5      (       a  UR                  n[        R	                  X5       H  nSX4'   M	     SR                  U5      $ )z
Gets the bitlist corresponding to a subset.

Examples
========

>>> from sympy.combinatorics import Subset
>>> Subset.bitlist_from_subset(['c', 'd'], ['a', 'b', 'c', 'd'])
'0011'

See Also
========

subset_from_bitlist
r#   ru   r!   )r
   r   r   r   r=   r&   )r   r   r   rw   rA   s        r   r$   Subset.bitlist_from_subset  sU    " %#h-'ff%%]]F&&v8AGJ 9wwwr   c                 z    [        U5      SS R                  [        U5      S5      n[        R	                  X#5      $ )z
Gets the binary ordered subset of the specified rank.

Examples
========

>>> from sympy.combinatorics import Subset
>>> Subset.unrank_binary(4, ['a', 'b', 'c', 'd']).subset
['b']

See Also
========

iterate_binary, rank_binary
r"   Nr#   )r(   r)   r
   r   r*   )r   rg   r   r.   s       r   unrank_binarySubset.unrank_binary  s5    " 4y}""3x=#6))(99r   c                 l    [         R                  " [        U5      U5      n[        R	                  X#5      $ )a  
Gets the Gray code ordered subset of the specified rank.

Examples
========

>>> from sympy.combinatorics import Subset
>>> Subset.unrank_gray(4, ['a', 'b', 'c']).subset
['a', 'b']
>>> Subset.unrank_gray(0, ['a', 'b', 'c']).subset
[]

See Also
========

iterate_graycode, rank_gray
)r   rK   r
   r   r*   )r   rg   r   graycode_bitlists       r   unrank_graySubset.unrank_gray   s*    & $??3x=$?))(EEr   c                     X!pC[        U5      n0 n[        U5       H*  u  pxX;   d  M  XvU'   UR                  U5        U(       a  M*    O   / $ U V	s/ s H  oU	   PM	     sn	$ s  sn	f )a  Return indices of subset in superset in a list; the list is empty
if all elements of ``subset`` are not in ``superset``.

Examples
========

    >>> from sympy.combinatorics import Subset
    >>> superset = [1, 3, 2, 5, 4]
    >>> Subset.subset_indices([3, 2, 1], superset)
    [1, 2, 0]
    >>> Subset.subset_indices([1, 6], superset)
    []
    >>> Subset.subset_indices([], superset)
    []

)set	enumerater>   )
r   r   r   absbdrA   aibis
             r   r=   Subset.subset_indices6  sg    $ 1Vq\EAx"		"r " I !""""""s   A )rY   rf   ra   )$__name__
__module____qualname____firstlineno____doc__rY   ra   rf   r   r   r   r   r/   r5   r9   rE   rH   rO   rS   rV   propertyrZ   rb   rL   r   rl   r   r'   rM   classmethodr*   r$   r|   r   r=   __static_attributes__ r   r   r   r      s]   . LINGI<O?6&,',+*Z&*P92(&)& ! !4  6 # #2  &    &  & " "& ' '& * *0    . : :& F F* # #r   r   c                     [        X5      $ )aw  
Finds the subsets of size ``k`` in lexicographic order.

This uses the itertools generator.

Examples
========

>>> from sympy.combinatorics.subsets import ksubsets
>>> list(ksubsets([1, 2, 3], 2))
[(1, 2), (1, 3), (2, 3)]
>>> list(ksubsets([1, 2, 3, 4, 5], 2))
[(1, 2), (1, 3), (1, 4), (1, 5), (2, 3), (2, 4),     (2, 5), (3, 4), (3, 5), (4, 5)]

See Also
========

Subset
r   )r   r+   s     r   ksubsetsr   V  s    * $$r   N)	itertoolsr   sympy.combinatorics.graycoder   r   r   r   r   r   <module>r      s    " 1M	# M	#`%r   