
\c           @  s~  d  Z  d d l m Z m Z d d l m Z d d l m Z m	 Z
 d d l m Z m Z d d l m Z d d l m Z d d l m Z d d	 l m Z d d
 l m Z dZ d  Z d   Z d   Z d   Z d   Z d   Z d   Z d   Z  d   Z! d   Z" d   Z# e$ d  Z% d   Z& e$ d  Z' d   Z( d   Z) d   Z* d   Z+ d   Z, d   Z- d   Z. d    Z/ d!   Z0 d"   Z1 d#   Z2 d$   Z3 d%   Z4 d&   Z5 d'   Z6 d(   Z7 d)   Z8 d*   Z9 d+   Z: d,   Z; d-   Z< d.   Z= d/   Z> d0   Z? d1   Z@ d2   ZA d3   ZB d4   ZC d5   ZD d6   ZE d7   ZF d8   ZG d9   ZH d:   ZI d;   ZJ d<   ZK d=   ZL d>   ZM d?   ZN i eM d@ 6eN dA 6ZO dB   ZP dC   ZQ dD   ZR eS dE  ZT dF   ZU dG   ZV dH   ZW dI   ZX dJ   ZY dK   ZZ dL   Z[ dM   Z\ dN   Z] i eW dO 6e\ dP 6e] dQ 6Z^ dZ dR  Z_ dS   Z` dT   Za dU   Zb dV   Zc dW dX  Zd dY   Ze dZ S([   sA   Dense univariate polynomials with coefficients in Galois fields. i(   t   print_functiont   division(   t   uniform(   t   ceilt   sqrt(   t
   SYMPY_INTSt   range(   t   prod(   t	   factorint(   t   query(   t   ExactQuotientFailed(   t   _sort_factorsc   
      C  s   t  | d | j } | j } xX t |  |  D]G \ } } | | } | j | |  \ } }	 }	 | | | | | 7} q. W| | S(   s  
    Chinese Remainder Theorem.

    Given a set of integer residues ``u_0,...,u_n`` and a set of
    co-prime integer moduli ``m_0,...,m_n``, returns an integer
    ``u``, such that ``u = u_i mod m_i`` for ``i = ``0,...,n``.

    Examples
    ========

    Consider a set of residues ``U = [49, 76, 65]``
    and a set of moduli ``M = [99, 97, 95]``. Then we have::

       >>> from sympy.polys.domains import ZZ
       >>> from sympy.polys.galoistools import gf_crt
       >>> from sympy.ntheory.modular import solve_congruence

       >>> gf_crt([49, 76, 65], [99, 97, 95], ZZ)
       639985

    This is the correct result because::

       >>> [639985 % m for m in [99, 97, 95]]
       [49, 76, 65]

    Note: this is a low-level routine with no error checking.

    See Also
    ========

    sympy.ntheory.modular.crt : a higher level crt routine
    sympy.ntheory.modular.solve_congruence

    t   start(   R   t   onet   zerot   zipt   gcdex(
   t   Ut   Mt   Kt   pt   vt   ut   mt   et   st   _(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_crt   s    #	
c         C  sv   g  g  } } t  |  d | j } xD |  D]< } | j | |  | j | j | d |  d |  q) W| | | f S(   s  
    First part of the Chinese Remainder Theorem.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_crt1

    >>> gf_crt1([99, 97, 95], ZZ)
    (912285, [9215, 9405, 9603], [62, 24, 12])

    R   ii    (   R   R   t   appendR   (   R   R   t   Et   SR   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_crt1>   s    )c         C  sS   | j  } x? t |  | | |  D]( \ } } }	 }
 | |	 | |
 | 7} q W| | S(   s`  
    Second part of the Chinese Remainder Theorem.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_crt2

    >>> U = [49, 76, 65]
    >>> M = [99, 97, 95]
    >>> p = 912285
    >>> E = [9215, 9405, 9603]
    >>> S = [62, 24, 12]

    >>> gf_crt2(U, M, p, E, S, ZZ)
    639985

    (   R   R   (   R   R   R   R   R   R   R   R   R   R   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_crt2V   s    	(c         C  s    |  | d k r |  S|  | Sd S(   s   
    Coerce ``a mod p`` to an integer in the range ``[-p/2, p/2]``.

    Examples
    ========

    >>> from sympy.polys.galoistools import gf_int

    >>> gf_int(2, 7)
    2
    >>> gf_int(5, 7)
    -2

    i   N(    (   t   aR   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_intr   s    c         C  s   t  |   d S(   s   
    Return the leading degree of ``f``.

    Examples
    ========

    >>> from sympy.polys.galoistools import gf_degree

    >>> gf_degree([1, 1, 2, 0])
    3
    >>> gf_degree([])
    -1

    i   (   t   len(   t   f(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt	   gf_degree   s    c         C  s   |  s | j  S|  d Sd S(   s   
    Return the leading coefficient of ``f``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_LC

    >>> gf_LC([3, 0, 1], ZZ)
    3

    i    N(   R   (   R$   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_LC   s    c         C  s   |  s | j  S|  d Sd S(   s   
    Return the trailing coefficient of ``f``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_TC

    >>> gf_TC([3, 0, 1], ZZ)
    1

    iN(   R   (   R$   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_TC   s    c         C  sH   |  s |  d r |  Sd } x" |  D] } | r2 Pq" | d 7} q" W|  | S(   s   
    Remove leading zeros from ``f``.


    Examples
    ========

    >>> from sympy.polys.galoistools import gf_strip

    >>> gf_strip([0, 0, 0, 3, 0, 1])
    [3, 0, 1]

    i    i   (    (   R$   t   kt   coeff(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_strip   s    c         C  s!   t  g  |  D] } | | ^ q
  S(   s   
    Reduce all coefficients modulo ``p``.

    Examples
    ========

    >>> from sympy.polys.galoistools import gf_trunc

    >>> gf_trunc([7, -2, 3], 5)
    [2, 3, 3]

    (   R*   (   R$   R   R!   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_trunc   s    c         C  s   t  t t | |    |  S(   s   
    Normalize all coefficients in ``K``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_normal

    >>> gf_normal([5, 10, 21, -3], 5, ZZ)
    [1, 2]

    (   R+   t   listt   map(   R$   R   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt	   gf_normal   s    c         C  s   t  |  j    g  } } t | t  rh x t | d d  D]& } | j |  j | | j  |  q; WnI | \ } x= t | d d  D]) } | j |  j | f | j  |  q Wt | |  S(   s  
    Create a ``GF(p)[x]`` polynomial from a dict.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_from_dict

    >>> gf_from_dict({10: ZZ(4), 4: ZZ(33), 0: ZZ(-1)}, 5, ZZ)
    [4, 0, 0, 0, 0, 0, 3, 0, 0, 0, 4]

    i(	   t   maxt   keyst
   isinstanceR   R   R   t   getR   R+   (   R$   R   R   t   nt   hR(   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_from_dict   s    '	'c         C  sv   t  |   i  } } x\ t d | d  D]G } | rM t |  | | |  } n |  | | } | r' | | | <q' q' W| S(   sA  
    Convert a ``GF(p)[x]`` polynomial to a dict.

    Examples
    ========

    >>> from sympy.polys.galoistools import gf_to_dict

    >>> gf_to_dict([4, 0, 0, 0, 0, 0, 3, 0, 0, 0, 4], 5)
    {0: -1, 4: -2, 10: -1}
    >>> gf_to_dict([4, 0, 0, 0, 0, 0, 3, 0, 0, 0, 4], 5, symmetric=False)
    {0: 4, 4: 3, 10: 4}

    i    i   (   R%   R   R"   (   R$   R   t	   symmetricR3   t   resultR(   R!   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt
   gf_to_dict  s    c         C  s   t  |  |  S(   s   
    Create a ``GF(p)[x]`` polynomial from ``Z[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_from_int_poly

    >>> gf_from_int_poly([7, -2, 3], 5)
    [2, 3, 3]

    (   R+   (   R$   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_from_int_poly7  s    c         C  s.   | r& g  |  D] } t  | |  ^ q S|  Sd S(   s  
    Convert a ``GF(p)[x]`` polynomial to ``Z[x]``.


    Examples
    ========

    >>> from sympy.polys.galoistools import gf_to_int_poly

    >>> gf_to_int_poly([2, 3, 3], 5)
    [2, -2, -2]
    >>> gf_to_int_poly([2, 3, 3], 5, symmetric=False)
    [2, 3, 3]

    N(   R"   (   R$   R   R6   t   c(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_to_int_polyH  s     c         C  s   g  |  D] } | | ^ q S(   s   
    Negate a polynomial in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_neg

    >>> gf_neg([3, 2, 1, 0], 5, ZZ)
    [2, 3, 4, 0]

    (    (   R$   R   R   R)   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_neg^  s    c         C  s[   |  s | | } n3 |  d | | } t  |   d k rF |  d  | g S| sP g  S| g Sd S(   s  
    Compute ``f + a`` where ``f`` in ``GF(p)[x]`` and ``a`` in ``GF(p)``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_add_ground

    >>> gf_add_ground([3, 2, 4], 2, 5, ZZ)
    [3, 2, 1]

    ii   N(   R#   (   R$   R!   R   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_add_groundo  s    c         C  s\   |  s | | } n3 |  d | | } t  |   d k rG |  d  | g S| sQ g  S| g Sd S(   s  
    Compute ``f - a`` where ``f`` in ``GF(p)[x]`` and ``a`` in ``GF(p)``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_sub_ground

    >>> gf_sub_ground([3, 2, 4], 2, 5, ZZ)
    [3, 2, 2]

    ii   N(   R#   (   R$   R!   R   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_sub_ground  s    c         C  s-   | s
 g  Sg  |  D] } | | | ^ q Sd S(   s  
    Compute ``f * a`` where ``f`` in ``GF(p)[x]`` and ``a`` in ``GF(p)``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_mul_ground

    >>> gf_mul_ground([3, 2, 4], 2, 5, ZZ)
    [1, 4, 3]

    N(    (   R$   R!   R   R   t   b(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_mul_ground  s    c         C  s   t  |  | j | |  | |  S(   s  
    Compute ``f/a`` where ``f`` in ``GF(p)[x]`` and ``a`` in ``GF(p)``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_quo_ground

    >>> gf_quo_ground(ZZ.map([3, 2, 4]), ZZ(2), 5, ZZ)
    [4, 1, 2]

    (   R@   t   invert(   R$   R!   R   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_quo_ground  s    c   
      C  s   |  s
 | S| s |  St  |   } t  |  } | | k rl t g  t |  |  D] \ } } | | | ^ qK  St | |  } | | k r |  |  |  | }	 }  n | |  | | }	 } |	 g  t |  |  D] \ } } | | | ^ q Sd S(   s   
    Add polynomials in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_add

    >>> gf_add([3, 2, 4], [2, 2, 2], 5, ZZ)
    [4, 1]

    N(   R%   R*   R   t   abs(
   R$   t   gR   R   t   dft   dgR!   R?   R(   R4   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_add  s    4c   
      C  s  | s
 |  S|  s  t  | | |  St |   } t |  } | | k rx t g  t |  |  D] \ } } | | | ^ qW  St | |  } | | k r |  |  |  | }	 }  n! t  | |  | |  | | }	 } |	 g  t |  |  D] \ } } | | | ^ q Sd S(   s   
    Subtract polynomials in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_sub

    >>> gf_sub([3, 2, 4], [2, 2, 2], 5, ZZ)
    [1, 0, 2]

    N(   R<   R%   R*   R   RC   (
   R$   RD   R   R   RE   RF   R!   R?   R(   R4   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_sub  s    4!c         C  s   t  |   } t  |  } | | } d g | d } x t d | d  D]k } | j }	 xK t t d | |  t | |  d  D]  }
 |	 |  |
 | | |
 7}	 q W|	 | | | <qG Wt |  S(   s   
    Multiply polynomials in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_mul

    >>> gf_mul([3, 2, 4], [2, 2, 2], 5, ZZ)
    [1, 0, 3, 2, 3]

    i    i   (   R%   R   R   R/   t   minR*   (   R$   RD   R   R   RE   RF   t   dhR4   t   iR)   t   j(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_mul  s    
	0c         C  s  t  |   } d | } d g | d } x t d | d  D] } | j } t d | |  } t | |  }	 |	 | d }
 | |
 d d }	 x5 t | |	 d  D]  } | |  | |  | | 7} q W| | 7} |
 d @r |  |	 d } | | d 7} n  | | | | <q; Wt |  S(   s   
    Square polynomials in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_sqr

    >>> gf_sqr([3, 2, 4], 5, ZZ)
    [4, 2, 3, 1, 1]

    i   i    i   (   R%   R   R   R/   RI   R*   (   R$   R   R   RE   RJ   R4   RK   R)   t   jmint   jmaxR3   RL   t   elem(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_sqr1  s"    
	

c         C  s"   t  |  t | | | |  | |  S(   s  
    Returns ``f + g*h`` where ``f``, ``g``, ``h`` in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_add_mul
    >>> gf_add_mul([3, 2, 4], [2, 2, 2], [1, 4], 5, ZZ)
    [2, 3, 2, 2]
    (   RG   RM   (   R$   RD   R4   R   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt
   gf_add_mul\  s    c         C  s"   t  |  t | | | |  | |  S(   s  
    Compute ``f - g*h`` where ``f``, ``g``, ``h`` in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_sub_mul

    >>> gf_sub_mul([3, 2, 4], [2, 2, 2], [1, 4], 5, ZZ)
    [3, 3, 2, 1]

    (   RH   RM   (   R$   RD   R4   R   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt
   gf_sub_mulk  s    c         C  sx   t  |   t k r! |  \ } }  n	 | j } | g } x> |  D]6 \ } } t | | | |  } t | | | |  } q: W| S(   s  
    Expand results of :func:`factor` in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_expand

    >>> gf_expand([([3, 2, 4], 1), ([2, 2], 2), ([3, 1], 3)], 5, ZZ)
    [4, 3, 0, 3, 0, 1, 4, 1]

    (   t   typet   tupleR   t   gf_powRM   (   t   FR   R   t   lcRD   R$   R(   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt	   gf_expand|  s    		c         C  sD  t  |   } t  |  } | s- t d   n | | k  rC g  |  f S| j | d |  } t |   | | | d } } }	 x t d | d  D] }
 | |
 } xW t t d | |
  t | |
 |	  d  D]( } | | |
 | | | | | 8} q W|
 | k r| | 9} n  | | | |
 <q W| | d  t | | d  f S(   s	  
    Division with remainder in ``GF(p)[x]``.

    Given univariate polynomials ``f`` and ``g`` with coefficients in a
    finite field with ``p`` elements, returns polynomials ``q`` and ``r``
    (quotient and remainder) such that ``f = q*g + r``.

    Consider polynomials ``x**3 + x + 1`` and ``x**2 + x`` in GF(2)::

       >>> from sympy.polys.domains import ZZ
       >>> from sympy.polys.galoistools import gf_div, gf_add_mul

       >>> gf_div(ZZ.map([1, 0, 1, 1]), ZZ.map([1, 1, 0]), 2, ZZ)
       ([1, 1], [1])

    As result we obtained quotient ``x + 1`` and remainder ``1``, thus::

       >>> gf_add_mul(ZZ.map([1]), ZZ.map([1, 1]), ZZ.map([1, 1, 0]), 2, ZZ)
       [1, 0, 1, 1]

    References
    ==========

    .. [1] [Monagan93]_
    .. [2] [Gathen99]_

    s   polynomial divisioni    i   (   R%   t   ZeroDivisionErrorRA   R,   R   R/   RI   R*   (   R$   RD   R   R   RE   RF   t   invR4   t   dqt   drRK   R)   RL   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_div  s     
"
4&c         C  s   t  |  | | |  d S(   s   
    Compute polynomial remainder in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_rem

    >>> gf_rem(ZZ.map([1, 0, 1, 1]), ZZ.map([1, 1, 0]), 2, ZZ)
    [1]

    i   (   R^   (   R$   RD   R   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_rem  s    c         C  s  t  |   } t  |  } | s- t d   n | | k  r= g  S| j | d |  } |  | | | d } } }	 x t d | d  D]| }
 | |
 } xW t t d | |
  t | |
 |	  d  D]( } | | |
 | | | | | 8} q W| | | | |
 <q W| | d  S(   sG  
    Compute exact quotient in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_quo

    >>> gf_quo(ZZ.map([1, 0, 1, 1]), ZZ.map([1, 1, 0]), 2, ZZ)
    [1, 1]
    >>> gf_quo(ZZ.map([1, 0, 3, 2, 3]), ZZ.map([2, 2, 2]), 5, ZZ)
    [3, 2, 4]

    s   polynomial divisioni    i   (   R%   RZ   RA   R   R/   RI   (   R$   RD   R   R   RE   RF   R[   R4   R\   R]   RK   R)   RL   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_quo  s    
4&c         C  s8   t  |  | | |  \ } } | s% | St |  |   d S(   s  
    Compute polynomial quotient in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_exquo

    >>> gf_exquo(ZZ.map([1, 0, 3, 2, 3]), ZZ.map([2, 2, 2]), 5, ZZ)
    [3, 2, 4]

    >>> gf_exquo(ZZ.map([1, 0, 1, 1]), ZZ.map([1, 1, 0]), 2, ZZ)
    Traceback (most recent call last):
    ...
    ExactQuotientFailed: [1, 1, 0] does not divide [1, 0, 1, 1]

    N(   R^   R
   (   R$   RD   R   R   t   qt   r(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_exquo  s    c         C  s    |  s
 |  S|  | j  g | Sd S(   s   
    Efficiently multiply ``f`` by ``x**n``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_lshift

    >>> gf_lshift([3, 2, 4], 4, ZZ)
    [3, 2, 4, 0, 0, 0, 0]

    N(   R   (   R$   R3   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt	   gf_lshift!  s    c         C  s(   | s |  g  f S|  |  |  | f Sd S(   s   
    Efficiently divide ``f`` by ``x**n``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_rshift

    >>> gf_rshift([1, 2, 3, 4, 0], 3, ZZ)
    ([1, 2], [3, 4, 0])

    N(    (   R$   R3   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt	   gf_rshift5  s    
c         C  s   | s | j  g S| d k r  |  S| d k r< t |  | |  S| j  g } x\ t r | d @r} t | |  | |  } | d 8} n  | d L} | s Pn  t |  | |  }  qK W| S(   s   
    Compute ``f**n`` in ``GF(p)[x]`` using repeated squaring.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_pow

    >>> gf_pow([3, 2, 4], 3, 5, ZZ)
    [2, 4, 4, 2, 2, 1, 4]

    i   i   (   R   RQ   t   TrueRM   (   R$   R3   R   R   R4   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyRV   I  s     
	

c         C  s)  t  |   } | d k r g  Sd g | } d g | d <| | k  r x t d |  D]9 } t | | d | |  } t | |  | |  | | <qR Wn | d k r%t | j | j g | |  | |  | d <x\ t d |  D]H } t | | d | d | |  | | <t | | |  | |  | | <q Wn  | S(   sh  
    return the list of ``x**(i*p) mod g in Z_p`` for ``i = 0, .., n - 1``
    where ``n = gf_degree(g)``

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_frobenius_monomial_base
    >>> g = ZZ.map([1, 0, 2, 1])
    >>> gf_frobenius_monomial_base(g, 5, ZZ)
    [[1], [4, 4, 2], [1, 2]]

    i    i   i   (   R%   R   Rd   R_   t
   gf_pow_modR   R   RM   (   RD   R   R   R3   R?   RK   t   mon(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_frobenius_monomial_basen  s     (%$c   
      C  s   t  |  } t  |   | k r6 t |  | | |  }  n  |  s@ g  St  |   } |  d g } xQ t d | d  D]< } t | | |  | | | |  }	 t | |	 | |  } qm W| S(   sT  
    compute gf_pow_mod(f, p, g, p, K) using the Frobenius map

    Parameters
    ==========

    f, g : polynomials in ``GF(p)[x]``
    b : frobenius monomial base
    p : prime number
    K : domain

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_frobenius_monomial_base, gf_frobenius_map
    >>> f = ZZ.map([2, 1 , 0, 1])
    >>> g = ZZ.map([1, 0, 2, 1])
    >>> p = 5
    >>> b = gf_frobenius_monomial_base(g, p, ZZ)
    >>> r = gf_frobenius_map(f, g, b, p, ZZ)
    >>> gf_frobenius_map(f, g, b, p, ZZ)
    [4, 0, 3]
    ii   (   R%   R_   R   R@   RG   (
   R$   RD   R?   R   R   R   R3   t   sfRK   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_frobenius_map  s    !c   
      C  s   t  |  | | |  }  |  } |  } xY t d |  D]H } t | | | | |  } t | | | |  } t  | | | |  } q1 Wt | | d d | | |  }	 |	 S(   s   
    utility function for ``gf_edf_zassenhaus``
    Compute ``f**((p**n - 1) // 2)`` in ``GF(p)[x]/(g)``
    ``f**((p**n - 1) // 2) = (f*f**p*...*f**(p**n - 1))**((p - 1) // 2)``
    i   i   (   R_   R   Rk   RM   Rg   (
   R$   R3   RD   R?   R   R   R4   Rb   RK   t   res(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   _gf_pow_pnm1d2  s     c         C  s   | s | j  g S| d k r/ t |  | | |  S| d k rZ t t |  | |  | | |  S| j  g } x t r | d @r t | |  | |  } t | | | |  } | d 8} n  | d L} | s Pn  t |  | |  }  t |  | | |  }  qi W| S(   s*  
    Compute ``f**n`` in ``GF(p)[x]/(g)`` using repeated squaring.

    Given polynomials ``f`` and ``g`` in ``GF(p)[x]`` and a non-negative
    integer ``n``, efficiently computes ``f**n (mod g)`` i.e. the remainder
    of ``f**n`` from division by ``g``, using the repeated squaring algorithm.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_pow_mod

    >>> gf_pow_mod(ZZ.map([3, 2, 4]), 3, ZZ.map([1, 1]), 5, ZZ)
    []

    References
    ==========

    .. [1] [Gathen99]_

    i   i   (   R   R_   RQ   Rf   RM   (   R$   R3   RD   R   R   R4   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyRg     s$    
	

c         C  s=   x& | r( | t  |  | | |  }  } q Wt |  | |  d S(   s   
    Euclidean Algorithm in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_gcd

    >>> gf_gcd(ZZ.map([3, 2, 4]), ZZ.map([2, 2, 3]), 5, ZZ)
    [1, 3]

    i   (   R_   t   gf_monic(   R$   RD   R   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_gcd  s    	 c         C  sY   |  s | r g  St  t |  | | |  t |  | | |  | |  } t | | |  d S(   s   
    Compute polynomial LCM in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_lcm

    >>> gf_lcm(ZZ.map([3, 2, 4]), ZZ.map([2, 2, 3]), 5, ZZ)
    [1, 2, 0, 4]

    i   (   R`   RM   Ro   Rn   (   R$   RD   R   R   R4   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_lcm	  s
    c         C  s[   |  r | r g  g  g  f St  |  | | |  } | t |  | | |  t | | | |  f S(   s   
    Compute polynomial GCD and cofactors in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_cofactors

    >>> gf_cofactors(ZZ.map([3, 2, 4]), ZZ.map([2, 2, 3]), 5, ZZ)
    ([1, 3], [3, 3], [2, 1])

    (   Ro   R`   (   R$   RD   R   R   R4   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_cofactors   s
    c         C  s  |  p	 | s | j  g g  g  f St |  | |  \ } } t | | |  \ } } |  sq g  | j | |  g | f S| s | j | |  g g  | f S| j | |  g g  } }	 g  | j | |  g }
 } x t rt | | | |  \ } } | s Pn  t | | |  | \ } } } | j | |  } t | |	 | | |  } t |
 | | | |  } t | | | |  |	 }	 } t | | | |  | } }
 q W|	 | | f S(   s  
    Extended Euclidean Algorithm in ``GF(p)[x]``.

    Given polynomials ``f`` and ``g`` in ``GF(p)[x]``, computes polynomials
    ``s``, ``t`` and ``h``, such that ``h = gcd(f, g)`` and ``s*f + t*g = h``.
    The typical application of EEA is solving polynomial diophantine equations.

    Consider polynomials ``f = (x + 7) (x + 1)``, ``g = (x + 7) (x**2 + 1)``
    in ``GF(11)[x]``. Application of Extended Euclidean Algorithm gives::

       >>> from sympy.polys.domains import ZZ
       >>> from sympy.polys.galoistools import gf_gcdex, gf_mul, gf_add

       >>> s, t, g = gf_gcdex(ZZ.map([1, 8, 7]), ZZ.map([1, 7, 1, 7]), 11, ZZ)
       >>> s, t, g
       ([5, 6], [6], [1, 7])

    As result we obtained polynomials ``s = 5*x + 6`` and ``t = 6``, and
    additionally ``gcd(f, g) = x + 7``. This is correct because::

       >>> S = gf_mul(s, ZZ.map([1, 8, 7]), 11, ZZ)
       >>> T = gf_mul(t, ZZ.map([1, 7, 1, 7]), 11, ZZ)

       >>> gf_add(S, T, 11, ZZ) == [1, 7]
       True

    References
    ==========

    .. [1] [Gathen99]_

    (   R   Rn   RA   Rf   R^   RS   R@   (   R$   RD   R   R   t   p0t   r0t   p1t   r1t   s0t   s1t   t0t   t1t   Qt   RRX   R[   R   t   t(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_gcdex7  s*    !	 c         C  sY   |  s | j  g  f S|  d } | j |  r< | t |   f S| t |  | | |  f Sd S(   s   
    Compute LC and a monic polynomial in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_monic

    >>> gf_monic(ZZ.map([3, 2, 4]), 5, ZZ)
    (3, [1, 4, 3])

    i    N(   R   t   is_oneR,   RB   (   R$   R   R   RX   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyRn   y  s    
c         C  s}   t  |   } | j g | | } } xM |  d  D]A } | | |  9} | | ;} | re | | | | <n  | d 8} q. Wt |  S(   s   
    Differentiate polynomial in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_diff

    >>> gf_diff([3, 2, 4], 5, ZZ)
    [1, 2]

    ii   (   R%   R   R*   (   R$   R   R   RE   R4   R3   R)   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_diff  s    
c         C  s<   | j  } x, |  D]$ } | | 9} | | 7} | | ;} q W| S(   s   
    Evaluate ``f(a)`` in ``GF(p)`` using Horner scheme.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_eval

    >>> gf_eval([3, 2, 4], 2, 5, ZZ)
    0

    (   R   (   R$   R!   R   R   R7   R:   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_eval  s    	

c         C  s&   g  | D] } t  |  | | |  ^ q S(   s  
    Evaluate ``f(a)`` for ``a`` in ``[a_1, ..., a_n]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_multi_eval

    >>> gf_multi_eval([3, 2, 4], [0, 1, 2, 3, 4], 5, ZZ)
    [4, 4, 0, 2, 0]

    (   R   (   R$   t   AR   R   R!   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_multi_eval  s    c         C  s   t  |  d k r7 t t |  t | |  | |  g  S|  sA g  S|  d g } x< |  d D]0 } t | | | |  } t | | | |  } qY W| S(   s  
    Compute polynomial composition ``f(g)`` in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_compose

    >>> gf_compose([3, 2, 4], [2, 2, 2], 5, ZZ)
    [2, 4, 0, 3, 0]

    i   i    (   R#   R*   R   R&   RM   R=   (   R$   RD   R   R   R4   R:   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt
   gf_compose  s    %c         C  so   |  s
 g  S|  d g } xQ |  d D]E } t  | | | |  } t | | | |  } t | | | |  } q" W| S(   s&  
    Compute polynomial composition ``g(h)`` in ``GF(p)[x]/(f)``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_compose_mod

    >>> gf_compose_mod(ZZ.map([3, 2, 4]), ZZ.map([2, 2, 2]), ZZ.map([4, 3]), 5, ZZ)
    [4]

    i    i   (   RM   R=   R_   (   RD   R4   R$   R   R   t   compR!   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_compose_mod  s    c         C  s  t  |  | | | |  } | } | d @rF t |  | | |  }	 | }
 n |  }	 | }
 | d L} x | r t | t  | | | | |  | |  } t  | | | | |  } | d @r t |	 t  | |
 | | |  | |  }	 t  | |
 | | |  }
 n  | d L} q_ Wt  |  |
 | | |  |	 f S(   s  
    Compute polynomial trace map in ``GF(p)[x]/(f)``.

    Given a polynomial ``f`` in ``GF(p)[x]``, polynomials ``a``, ``b``,
    ``c`` in the quotient ring ``GF(p)[x]/(f)`` such that ``b = c**t
    (mod f)`` for some positive power ``t`` of ``p``, and a positive
    integer ``n``, returns a mapping::

       a -> a**t**n, a + a**t + a**t**2 + ... + a**t**n (mod f)

    In factorization context, ``b = x**p mod f`` and ``c = x mod f``.
    This way we can efficiently compute trace polynomials in equal
    degree factorization routine, much faster than with other methods,
    like iterated Frobenius algorithm, for large degrees.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_trace_map

    >>> gf_trace_map([1, 2], [4, 4], [1, 1], 4, [3, 2, 4], 5, ZZ)
    ([1, 3], [1, 3])

    References
    ==========

    .. [1] [Gathen92]_

    i   (   R   RG   (   R!   R?   R:   R3   R$   R   R   R   R   R   t   V(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_trace_map  s     
	
	'
'c   	      C  s   t  |  | | |  }  |  } |  } xY t d |  D]H } t | | | | |  } t | | | |  } t  | | | |  } q1 W| S(   s&   
    utility for ``gf_edf_shoup``
    i   (   R_   R   Rk   RG   (	   R$   R3   RD   R?   R   R   R4   Rb   RK   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   _gf_trace_mapH  s    c         C  s?   | j  g g  t d |   D]! } | t t d |    ^ q S(   s  
    Generate a random polynomial in ``GF(p)[x]`` of degree ``n``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_random
    >>> gf_random(10, 5, ZZ) #doctest: +SKIP
    [1, 2, 3, 2, 1, 1, 1, 2, 0, 4, 2]

    i    (   R   R   t   intR   (   R3   R   R   RK   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt	   gf_randomV  s    c         C  s9   x2 t  r4 t |  | |  } t | | |  r | Sq Wd S(   s,  
    Generate random irreducible polynomial of degree ``n`` in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_irreducible
    >>> gf_irreducible(10, 5, ZZ) #doctest: +SKIP
    [1, 4, 2, 2, 3, 2, 4, 1, 4, 0, 4]

    N(   Rf   R   t   gf_irreducible_p(   R3   R   R   R$   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_irreduciblef  s    	c   
      C  s  t  |   } | d k r t St |  | |  \ } }  | d k  r t | j | j g | |  | |  } } x8t d | d  D]g } t | | j | j g | |  } t |  | | |  | j g k r t	 | | |  | |  } q| t
 Sq| Wn t |  | |  }	 t | j | j g |  |	 | |  } } x| t d | d  D]g } t | | j | j g | |  } t |  | | |  | j g k rt | |  |	 | |  } q8t
 Sq8Wt S(   s_  
    Ben-Or's polynomial irreducibility test over finite fields.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_irred_p_ben_or

    >>> gf_irred_p_ben_or(ZZ.map([1, 4, 2, 2, 3, 2, 4, 1, 4, 0, 4]), 5, ZZ)
    True
    >>> gf_irred_p_ben_or(ZZ.map([3, 2, 4]), 5, ZZ)
    False

    i   i   i    i   (   R%   Rf   Rn   Rg   R   R   R   RH   Ro   R   t   FalseRi   Rk   (
   R$   R   R   R3   R   t   HR4   RK   RD   R?   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_irred_p_ben_ory  s&    (!!(!!c   
        s  t  |       d k r t St |  | |  \ } }  | j | j g }   f d   t    D } t |  | |  } | d } xx t d    D]g } | | k r t | | | |  }	 t	 |  |	 | |  | j g k r t
 Sn  t | |  | | |  } q W| | k S(   s[  
    Rabin's polynomial irreducibility test over finite fields.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_irred_p_rabin

    >>> gf_irred_p_rabin(ZZ.map([1, 4, 2, 2, 3, 2, 4, 1, 4, 0, 4]), 5, ZZ)
    True
    >>> gf_irred_p_rabin(ZZ.map([3, 2, 4]), 5, ZZ)
    False

    i   c           s   h  |  ] }   |  q S(    (    (   t   .0t   d(   R3   (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pys	   <setcomp>  s   	 (   R%   Rf   Rn   R   R   R   Ri   R   RH   Ro   R   Rk   (
   R$   R   R   R   t   xt   indicesR?   R4   RK   RD   (    (   R3   s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_irred_p_rabin  s    
!s   ben-ort   rabinc         C  sG   t  d  } | d k	 r1 t | |  | |  } n t |  | |  } | S(   s[  
    Test irreducibility of a polynomial ``f`` in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_irreducible_p

    >>> gf_irreducible_p(ZZ.map([1, 4, 2, 2, 3, 2, 4, 1, 4, 0, 4]), 5, ZZ)
    True
    >>> gf_irreducible_p(ZZ.map([3, 2, 4]), 5, ZZ)
    False

    t   GF_IRRED_METHODN(   R	   t   Nonet   _irred_methodsR   (   R$   R   R   t   methodt   irred(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyR     s
    c         C  sQ   t  |  | |  \ } }  |  s" t St |  t |  | |  | |  | j g k Sd S(   s5  
    Return ``True`` if ``f`` is square-free in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_sqf_p

    >>> gf_sqf_p(ZZ.map([3, 2, 4]), 5, ZZ)
    True
    >>> gf_sqf_p(ZZ.map([2, 4, 4, 2, 2, 1, 4]), 5, ZZ)
    False

    N(   Rn   Rf   Ro   R   R   (   R$   R   R   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_sqf_p  s    c         C  sT   t  |  | |  \ } } | j g } x) | D]! \ }  } t | |  | |  } q+ W| S(   s  
    Return square-free part of a ``GF(p)[x]`` polynomial.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_sqf_part

    >>> gf_sqf_part(ZZ.map([1, 1, 3, 0, 1, 0, 2, 2, 1]), 5, ZZ)
    [1, 4, 3]

    (   t   gf_sqf_listR   RM   (   R$   R   R   R   t   sqfRD   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_sqf_part  s
    c         C  s  d t  g  t |  f \ } } } } t |  | |  \ } }  t |   d k  rX | g  f Sxut rt |  | |  }	 |	 g  k rit |  |	 | |  }
 t |  |
 | |  } d } x | | j g k rDt |
 | | |  } t | | | |  } t |  d k r| j	 | | | f  n  t |
 | | |  | | d }
 } } q W|
 | j g k r`t } qi|
 }  n  | st |   | } x- t
 d | d  D] } |  | | |  | <qW|  | d  | | }  } q[ Pq[ W| rt d   n  | | f S(   s  
    Return the square-free decomposition of a ``GF(p)[x]`` polynomial.

    Given a polynomial ``f`` in ``GF(p)[x]``, returns the leading coefficient
    of ``f`` and a square-free decomposition ``f_1**e_1 f_2**e_2 ... f_k**e_k``
    such that all ``f_i`` are monic polynomials and ``(f_i, f_j)`` for ``i != j``
    are co-prime and ``e_1 ... e_k`` are given in increasing order. All trivial
    terms (i.e. ``f_i = 1``) aren't included in the output.

    Consider polynomial ``f = x**11 + 1`` over ``GF(11)[x]``::

       >>> from sympy.polys.domains import ZZ

       >>> from sympy.polys.galoistools import (
       ...     gf_from_dict, gf_diff, gf_sqf_list, gf_pow,
       ... )
       ... # doctest: +NORMALIZE_WHITESPACE

       >>> f = gf_from_dict({11: ZZ(1), 0: ZZ(1)}, 11, ZZ)

    Note that ``f'(x) = 0``::

       >>> gf_diff(f, 11, ZZ)
       []

    This phenomenon doesn't happen in characteristic zero. However we can
    still compute square-free decomposition of ``f`` using ``gf_sqf()``::

       >>> gf_sqf_list(f, 11, ZZ)
       (1, [([1, 1], 11)])

    We obtained factorization ``f = (x + 1)**11``. This is correct because::

       >>> gf_pow([1, 1], 11, 11, ZZ) == f
       True

    References
    ==========

    .. [1] [Geddes92]_

    i   i    s   'all=True' is not supported yet(   R   R   Rn   R%   Rf   R   Ro   R`   R   R   R   t
   ValueError(   R$   R   R   t   allR3   R   t   factorsRb   RX   RW   RD   R4   RK   t   GR   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyR     s8    +$
	+		c         C  s  t  |   t |  } } | j g | j g | d } t |  g g  g | d } x t d | d | d  D] } | d |  d | g | d } }	 xA t d |  D]0 }
 | j | |
 d |	 |  |
 d |  q W| | st |  | | | <n  | } qq W| S(   sd  
    Calculate Berlekamp's ``Q`` matrix.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_Qmatrix

    >>> gf_Qmatrix([3, 2, 4], 5, ZZ)
    [[1, 0],
     [3, 4]]

    >>> gf_Qmatrix([1, 0, 0, 0, 1], 5, ZZ)
    [[1, 0, 0, 0],
     [0, 4, 0, 0],
     [0, 0, 1, 0],
     [0, 0, 0, 4]]

    i   i(   R%   R   R   R   R,   R   R   (   R$   R   R   R3   Rb   Ra   Rz   RK   t   qqR:   RL   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt
   gf_Qmatrixx  s    "%.

c         C  s  g  |  D] } t  |  ^ q t |   }  } x8 t d |  D]' } |  | | | j | |  | | <q< Wx_t d |  D]N} x, t | |  D] } |  | | r Pq q Wqw | j |  | | |  } x5 t d |  D]$ } |  | | | | |  | | <q WxI t d |  D]8 } |  | | }	 |  | | |  | | <|	 |  | | <qWxx t d |  D]g } | | k rZ|  | | } xD t d |  D]0 } |  | | |  | | | | |  | | <qWqZqZWqw Wx| t d |  D]k } xb t d |  D]Q } | | k r%| j |  | | | |  | | <q|  | | | |  | | <qWqWg  }
 x* |  D]" } t |  rU|
 j |  qUqUW|
 S(   s_  
    Compute a basis of the kernel of ``Q``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_Qmatrix, gf_Qbasis

    >>> gf_Qbasis(gf_Qmatrix([1, 0, 0, 0, 1], 5, ZZ), 5, ZZ)
    [[1, 0, 0, 0], [0, 0, 1, 0]]

    >>> gf_Qbasis(gf_Qmatrix([3, 2, 4], 5, ZZ), 5, ZZ)
    [[1, 0]]

    i    (   R,   R#   R   R   RA   t   anyR   (   Rz   R   R   Ra   R3   R(   RK   R[   RL   R|   t   basis(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt	   gf_Qbasis  s<    ,%"9$#c         C  s  t  |  | |  } t | | |  } x6 t |  D]( \ } } t t t |    | | <q1 W|  g } x	t d t |   D] } x t |  D] }  | j }	 x |	 | k  rit	 | | |	 | |  }
 t
 |  |
 | |  } | | j g k r1| |  k r1| j |   t |  | | |  }  | j |  | g  n  t |  t |  k rYt | d t S|	 | j 7}	 q Wq Wq| Wt | d t S(   s  
    Factor a square-free ``f`` in ``GF(p)[x]`` for small ``p``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_berlekamp

    >>> gf_berlekamp([1, 0, 0, 0, 1], 5, ZZ)
    [[1, 0, 2], [1, 0, 3]]

    i   t   multiple(   R   R   t	   enumerateR*   R,   t   reversedR   R#   R   R>   Ro   R   t   removeR`   t   extendR   R   (   R$   R   R   Rz   R   RK   R   R   R(   R   RD   R4   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_berlekamp  s&     		c         C  s6  d | j  | j g g  } } } t |  | |  } x d | t |   k rt | |  | | |  } t |  t | | j  | j g | |  | |  } | | j  g k r | j | | f  t |  | | |  }  t	 | |  | |  } t |  | |  } n  | d 7} q5 W|  | j  g k r.| |  t |   f g S| Sd S(   s{  
    Cantor-Zassenhaus: Deterministic Distinct Degree Factorization

    Given a monic square-free polynomial ``f`` in ``GF(p)[x]``, computes
    partial distinct degree factorization ``f_1 ... f_d`` of ``f`` where
    ``deg(f_i) != deg(f_j)`` for ``i != j``. The result is returned as a
    list of pairs ``(f_i, e_i)`` where ``deg(f_i) > 0`` and ``e_i > 0``
    is an argument to the equal degree factorization routine.

    Consider the polynomial ``x**15 - 1`` in ``GF(11)[x]``::

       >>> from sympy.polys.domains import ZZ
       >>> from sympy.polys.galoistools import gf_from_dict

       >>> f = gf_from_dict({15: ZZ(1), 0: ZZ(-1)}, 11, ZZ)

    Distinct degree factorization gives::

       >>> from sympy.polys.galoistools import gf_ddf_zassenhaus

       >>> gf_ddf_zassenhaus(f, 11, ZZ)
       [([1, 0, 0, 0, 0, 10], 1), ([1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1], 2)]

    which means ``x**15 - 1 = (x**5 - 1) (x**10 + x**5 + 1)``. To obtain
    factorization into irreducibles, use equal degree factorization
    procedure (EDF) with each of the factors.

    References
    ==========

    .. [1] [Gathen99]_
    .. [2] [Geddes92]_

    i   i   N(
   R   R   Ri   R%   Rk   Ro   RH   R   R`   R_   (   R$   R   R   RK   RD   R   R?   R4   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_ddf_zassenhaus
  s    # 0c         C  s  |  g } t  |   | k r | St  |   | } | d k rP t |  | |  } n  xGt |  | k  rt d | d | |  } | d k r | } xP t d d | | d  D]3 }	 t | d |  | |  } t | | | |  } q Wt |  | | |  }
 nB t | | |  | | |  } t |  t	 | | j
 | |  | |  }
 |
 | j
 g k rS |
 |  k rS t |
 | | |  t t |  |
 | |  | | |  } qS qS Wt | d t S(   s  
    Cantor-Zassenhaus: Probabilistic Equal Degree Factorization

    Given a monic square-free polynomial ``f`` in ``GF(p)[x]`` and
    an integer ``n``, such that ``n`` divides ``deg(f)``, returns all
    irreducible factors ``f_1,...,f_d`` of ``f``, each of degree ``n``.
    EDF procedure gives complete factorization over Galois fields.

    Consider the square-free polynomial ``f = x**3 + x**2 + x + 1`` in
    ``GF(5)[x]``. Let's compute its irreducible factors of degree one::

       >>> from sympy.polys.domains import ZZ
       >>> from sympy.polys.galoistools import gf_edf_zassenhaus

       >>> gf_edf_zassenhaus([1,1,1,1], 1, 5, ZZ)
       [[1, 1], [1, 2], [1, 3]]

    References
    ==========

    .. [1] [Gathen99]_
    .. [2] [Geddes92]_

    i   i   i    R   (   R%   Ri   R#   R   R   Rg   RG   Ro   Rm   R>   R   t   gf_edf_zassenhausR`   R   R   (   R$   R3   R   R   R   t   NR?   Rb   R4   RK   RD   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyR   C  s(    	"',c         C  s  t  |   } t t t | d    } t |  | |  } t | j | j g |  | | |  } | j | j g | g | j g | d } x? t d | d  D]* } t | | d |  | | |  | | <q W| | | |  } } | g | j g | d }	 x; t d |  D]* } t	 |	 | d | |  | |  |	 | <q
Wg  }
 x@t
 |	  D]2\ } } | j g | d } } xM | D]E } t | | | |  } t | | | |  } t | |  | |  } quWt |  | | |  } t |  | | |  }  x t |  D] } t | | | |  } t | | | |  } | | j g k rY|
 j | | | d | f  n  t | | | |  | d } } qWqKW|  | j g k r|
 j |  t  |   f  n  |
 S(   s  
    Kaltofen-Shoup: Deterministic Distinct Degree Factorization

    Given a monic square-free polynomial ``f`` in ``GF(p)[x]``, computes
    partial distinct degree factorization ``f_1,...,f_d`` of ``f`` where
    ``deg(f_i) != deg(f_j)`` for ``i != j``. The result is returned as a
    list of pairs ``(f_i, e_i)`` where ``deg(f_i) > 0`` and ``e_i > 0``
    is an argument to the equal degree factorization routine.

    This algorithm is an improved version of Zassenhaus algorithm for
    large ``deg(f)`` and modulus ``p`` (especially for ``deg(f) ~ lg(p)``).

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_ddf_shoup, gf_from_dict

    >>> f = gf_from_dict({6: ZZ(1), 5: ZZ(-1), 4: ZZ(1), 3: ZZ(1), 1: ZZ(-1)}, 3, ZZ)

    >>> gf_ddf_shoup(f, 3, ZZ)
    [([1, 1, 0], 1), ([1, 1, 0, 1, 2], 2)]

    References
    ==========

    .. [1] [Kaltofen98]_
    .. [2] [Shoup95]_
    .. [3] [Gathen92]_

    i   i   (   R%   R   t   _ceilt   _sqrtRi   Rk   R   R   R   R   R   RH   RM   R_   Ro   R`   R   R   (   R$   R   R   R3   R(   R?   R4   R   RK   R   R   R   RL   R   RD   RW   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_ddf_shoup{  s:     $*(("(c         C  s  t  |   t |  } } | s# g  S| | k r6 |  g S|  g | j | j g } } t | d | |  } | d k rt | | |  | |  }	 t | |	 | | d |  | |  d }
 t |  |
 | |  } t |  | | |  } t	 | | | |  t	 | | | |  } n t
 |  | |  } t | | |  | | |  }
 t |
 | d d |  | |  }	 t |  |	 | |  } t |  t |	 | j | |  | |  } t |  t | | | |  | |  } t	 | | | |  t	 | | | |  t	 | | | |  } t | d t S(   s  
    Gathen-Shoup: Probabilistic Equal Degree Factorization

    Given a monic square-free polynomial ``f`` in ``GF(p)[x]`` and integer
    ``n`` such that ``n`` divides ``deg(f)``, returns all irreducible factors
    ``f_1,...,f_d`` of ``f``, each of degree ``n``. This is a complete
    factorization over Galois fields.

    This algorithm is an improved version of Zassenhaus algorithm for
    large ``deg(f)`` and modulus ``p`` (especially for ``deg(f) ~ lg(p)``).

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_edf_shoup

    >>> gf_edf_shoup(ZZ.map([1, 2837, 2277]), 1, 2917, ZZ)
    [[1, 852], [1, 1985]]

    References
    ==========

    .. [1] [Shoup91]_
    .. [2] [Gathen92]_

    i   i   R   (   R%   R   R   R   R   Rg   R   Ro   R`   t   gf_edf_shoupRi   R   R>   RM   R   R   (   R$   R3   R   R   R   Ra   R   R   Rb   R4   R   t   h1t   h2R?   t   h3(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyR     s,    & '$;c         C  sR   g  } x9 t  |  | |  D]% \ } } | t | | | |  7} q Wt | d t S(   s  
    Factor a square-free ``f`` in ``GF(p)[x]`` for medium ``p``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_zassenhaus

    >>> gf_zassenhaus(ZZ.map([1, 4, 3]), 5, ZZ)
    [[1, 1], [1, 3]]

    R   (   R   R   R   R   (   R$   R   R   R   t   factorR3   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_zassenhaus  s    c         C  sR   g  } x9 t  |  | |  D]% \ } } | t | | | |  7} q Wt | d t S(   s  
    Factor a square-free ``f`` in ``GF(p)[x]`` for large ``p``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_shoup

    >>> gf_shoup(ZZ.map([1, 4, 3]), 5, ZZ)
    [[1, 1], [1, 3]]

    R   (   R   R   R   R   (   R$   R   R   R   R   R3   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_shoup  s    t	   berlekampt
   zassenhaust   shoupc         C  s   t  |  | |  \ } }  t |   d k  r4 | g  f S| pC t d  } | d k	 rk t | |  | |  } n t |  | |  } | | f S(   s  
    Factor a square-free polynomial ``f`` in ``GF(p)[x]``.

    Examples
    ========

    >>> from sympy.polys.domains import ZZ
    >>> from sympy.polys.galoistools import gf_factor_sqf

    >>> gf_factor_sqf(ZZ.map([3, 2, 4]), 5, ZZ)
    (3, [[1, 1], [1, 3]])

    i   t   GF_FACTOR_METHODN(   Rn   R%   R	   R   t   _factor_methodsR   (   R$   R   R   R   RX   R   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_factor_sqf8  s    
c         C  s   t  |  | |  \ } }  t |   d k  r4 | g  f Sg  } xX t |  | |  d D]@ \ } } x1 t | | |  d D] } | j | | f  qt WqQ W| t |  f S(   s  
    Factor (non square-free) polynomials in ``GF(p)[x]``.

    Given a possibly non square-free polynomial ``f`` in ``GF(p)[x]``,
    returns its complete factorization into irreducibles::

                 f_1(x)**e_1 f_2(x)**e_2 ... f_d(x)**e_d

    where each ``f_i`` is a monic polynomial and ``gcd(f_i, f_j) == 1``,
    for ``i != j``.  The result is given as a tuple consisting of the
    leading coefficient of ``f`` and a list of factors of ``f`` with
    their multiplicities.

    The algorithm proceeds by first computing square-free decomposition
    of ``f`` and then iteratively factoring each of square-free factors.

    Consider a non square-free polynomial ``f = (7*x + 1) (x + 2)**2`` in
    ``GF(11)[x]``. We obtain its factorization into irreducibles as follows::

       >>> from sympy.polys.domains import ZZ
       >>> from sympy.polys.galoistools import gf_factor

       >>> gf_factor(ZZ.map([5, 2, 7, 2]), 11, ZZ)
       (5, [([1, 2], 1), ([1, 8], 2)])

    We arrived with factorization ``f = 5 (x + 2) (x + 8)**2``. We didn't
    recover the exact form of the input polynomial because we requested to
    get monic factors of ``f`` and its leading coefficient separately.

    Square-free factors of ``f`` can be factored into irreducibles over
    ``GF(p)`` using three very different methods:

    Berlekamp
        efficient for very small values of ``p`` (usually ``p < 25``)
    Cantor-Zassenhaus
        efficient on average input and with "typical" ``p``
    Shoup-Kaltofen-Gathen
        efficient with very large inputs and modulus

    If you want to use a specific factorization method, instead of the default
    one, set ``GF_FACTOR_METHOD`` with one of ``berlekamp``, ``zassenhaus`` or
    ``shoup`` values.

    References
    ==========

    .. [1] [Gathen99]_

    i   (   Rn   R%   R   R   R   R   (   R$   R   R   RX   R   RD   R3   R4   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt	   gf_factorU  s    2
#c         C  s/   d } x" |  D] } | | 9} | | 7} q W| S(   s   
    Value of polynomial 'f' at 'a' in field R.

    Examples
    ========

    >>> from sympy.polys.galoistools import gf_value

    >>> gf_value([1, 7, 2, 4], 11)
    2204

    i    (    (   R$   R!   R7   R:   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   gf_value  s
    
c         C  s   d d l  m } |  | d k rG | | d k r@ t t |   Sg  Sn  | |  |  \ } } } | | d k rs g  Sg  t |  D]$ } | | | | | | | ^ q S(   s  
    Returns the values of x satisfying a*x congruent b mod(m)

    Here m is positive integer and a, b are natural numbers.
    This function returns only those values of x which are distinct mod(m).

    Examples
    ========

    >>> from sympy.polys.galoistools import linear_congruence

    >>> linear_congruence(3, 12, 15)
    [4, 9, 14]

    There are 3 solutions distinct mod(15) since gcd(a, m) = gcd(3, 15) = 3.

    References
    ==========

    .. [1] https://en.wikipedia.org/wiki/Linear_congruence_theorem

    i(   R   i    (   t   sympy.polys.polytoolsR   R,   R   (   R!   R?   R   R   Rb   R   RD   R|   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   linear_congruence  s    c         C  sY   d d l  m } t | | |  } t | |   } t | |   | | } t | | |  S(   s0  
    Used in gf_csolve to generate solutions of f(x) cong 0 mod(p**(s + 1))
    from the solutions of f(x) cong 0 mod(p**s).

    Examples
    ========

    >>> from sympy.polys.galoistools import _raise_mod_power
    >>> from sympy.polys.galoistools import csolve_prime

    These is the solutions of f(x) = x**2 + x + 7 cong 0 mod(3)

    >>> f = [1, 1, 7]
    >>> csolve_prime(f, 3)
    [1]
    >>> [ i for i in range(3) if not (i**2 + i + 7) % 3]
    [1]

    The solutions of f(x) cong 0 mod(9) are constructed from the
    values returned from _raise_mod_power:

    >>> x, s, p = 1, 1, 3
    >>> V = _raise_mod_power(x, s, p, f)
    >>> [x + v * p**s for v in V]
    [1, 4, 7]

    And these are confirmed with the following:

    >>> [ i for i in range(3**2) if not (i**2 + i + 7) % 3**2]
    [1, 4, 7]

    i(   t   ZZ(   t   sympy.polys.domainsR   R   R   R   (   R   R   R   R$   R   t   f_ft   alphat   beta(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   _raise_mod_power  s
    !i   c         C  s  d d l  m } g  t |  D]' } t |  | | |  d k r | ^ q } | d k rZ | Sg  } t t | d g t |    } x | r| j   \ } }	 |	 | k r | j |  q |	 d }
 | |	 } | j	 g  t
 | |	 | |   D] } | | | |
 f ^ q  q Wt |  S(   sU  
    Solutions of f(x) congruent 0 mod(p**e).

    Examples
    ========

    >>> from sympy.polys.galoistools import csolve_prime

    >>> csolve_prime([1, 1, 7], 3, 1)
    [1]
    >>> csolve_prime([1, 1, 7], 3, 2)
    [1, 4, 7]

    Solutions [7, 4, 1] (mod 3**2) are generated by ``_raise_mod_power()``
    from solution [1] (mod 3).
    i(   R   i    i   (   R   R   R   R   R,   R   R#   t   popR   R   R   t   sorted(   R$   R   R   R   RK   t   X1t   XR   R   R   Rw   t   psR   (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   csolve_prime  s    :"	

Ac         C  s   d d l  m } t |  } g  | j   D] \ } } t |  | |  ^ q) } t t t |   } g  g } x; | D]3 }	 g  | D]  }
 |	 D] } |
 | g ^ q q } qr Wg  | j   D] \ } } t | |  ^ q } t	 g  | D] } t
 | | |  ^ q  S(   s=  
    To solve f(x) congruent 0 mod(n).

    n is divided into canonical factors and f(x) cong 0 mod(p**e) will be
    solved for each factor. Applying the Chinese Remainder Theorem to the
    results returns the final answers.

    Examples
    ========

    Solve [1, 1, 7] congruent 0 mod(189):

    >>> from sympy.polys.galoistools import gf_csolve
    >>> gf_csolve([1, 1, 7], 189)
    [13, 49, 76, 112, 139, 175]

    References
    ==========

    .. [1] 'An introduction to the Theory of Numbers' 5th Edition by Ivan Niven,
           Zuckerman and Montgomery.

    i(   R   (   R   R   R   t   itemsR   R,   R-   RU   t   powR   R   (   R$   R3   R   t   PR   R   R   t   poolst   permst   poolR   t   yt   dist_factorst   per(    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt	   gf_csolve	  s    1	1.N(f   t   __doc__t
   __future__R    R   t   randomR   t   mathR   R   R   R   t   sympy.core.compatibilityR   R   t   sympy.core.mulR   t   sympy.ntheoryR   t   sympy.polys.polyconfigR	   t   sympy.polys.polyerrorsR
   t   sympy.polys.polyutilsR   R   R   R   R    R"   R%   R&   R'   R*   R+   R.   R5   Rf   R8   R9   R;   R<   R=   R>   R@   RB   RG   RH   RM   RQ   RR   RS   RY   R^   R_   R`   Rc   Rd   Re   RV   Ri   Rk   Rm   Rg   Ro   Rp   Rq   R}   Rn   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   R   (    (    (    s6   lib/python2.7/site-packages/sympy/polys/galoistools.pyt   <module>   s   .																	#	#		+				6		'				%	 	%		1				B							7				-	)
			Y	(	>	,	9	8	L	?		
	@		#	("