ó
ť"ˇLc           @   s  d  Z  d d l m Z m Z d d l m Z m Z d d' d  Z d   Z d   Z d	   Z	 d
   Z
 d   Z d d  Z d d  Z d   Z d   Z d& d  Z d d d  Z e Z d   Z d   Z e Z d   Z d   Z e d  Z e d d  Z d& d d  Z e e d  Z e e d  Z e e e d  Z  d    Z! d!   Z" d"   Z# e a$ g  Z% d#   Z& d$   Z' e( d% k re) a$ e#   n  d& S((   s   Matrix manipulation, with adjoined rows, Gauss-Jordan algoithms for
different types or fields and rings, inversion.
Omits general gauss_jordanMod
i˙˙˙˙(   t   ZModt   AnyMod(   t   mgcdt   xgcdg      đ?i
   c   	   	   C   s  t  |   t  |  d  } } xt d |  D]} | } xL t | d |  D]7 } t |  | |  t |  | |  k rM | } qM qM W|  | |  | |  | <|  | <t |  | |  | k rĂ t Sxo t | d |  D]Z } |  | | |  | | } x7 t | |  D]& } |  | | c |  | | | 8<qWq× Wq- WxŮ t | d d d  D]Á } |  | | } xh t d |  D]W } xN t | d | d d  D]2 } |  | | c |  | | |  | | | 8<qWqtW|  | | c | :<x+ t | |  D] } |  | | c | :<qóWqPWt S(   s^  Puts given matrix (2D array) into the Reduced Row Echelon Form.
     Returns True if successful, False if 'm' is singular.
     Specifically designed to minimize float roundoff.
     NOTE: make sure all the matrix items support fractions!
           An int matrix will NOT work!
     Written by Jarno Elonen in April 2005, released into Public Domaini    i   i˙˙˙˙i˙˙˙˙(   t   lent   ranget   abst   Falset   True(	   t   mt   epst   ht   wt   yt   maxrowt   y2t   ct   x(    (    s   C:\anh\www\331\gaussJordan.pyt   gauss_jordan	   s,    (,!4c   	   	   C   sa  t  |   t  |  d  } } t d |   xt d |  D]} t d |  x3 t | |  D] } |  | | d k r] Pq] q] Wt S| | k rÂ |  | |  | |  | <|  | <t d | | |   n  |  | | d k r5d |  | | } x+ t | |  D] } |  | | c | 9<qř Wt d | d t |  |   n  xc t | d |  D]N } |  | | } x7 t | |  D]& } |  | | c |  | | | 8<qmWqIW| d | k  r: t d | d	 | |   q: q: Wx t | d d d
  D]m } xd t d |  D]S } xJ t | d | d d
  D]. } |  | | c |  | | |  | | 8<qWqőWqßWt d |   t S(   sŠ  Puts given matrix (2D array) into the Reduced Row Echelon Form.
  Returns True if successful, False if 'm' is singular.
  Assumes all element operations are calulated exactly,
  as in a finite field or the rational numbers, but NOT float.
  Use function gauss_jordan for float calculation.
  Use other varants for rings with 0-divisors.
  Based on floating point code by Jarno Elonen,April 2005,
  released into Public Domaini    s
   Starting ms   Working on rows	   swap rowsi   s   Normalizing rows   Multiple by inverses   Zeroed columns	   below rowi˙˙˙˙s   Final, after back substitutioni˙˙˙˙(   R   t   commentMR   t   commentR   t   intR   (	   R	   R   R   R   t   pivott   invR   R   R   (    (    s   C:\anh\www\331\gaussJordan.pyt   gauss_jordanExactField'   s8     ( !4c   	   	   C   sj  t  |   t  |  d  } } t d |   x¤t d |  D]} t d |  x: t | |  D]% } |  | | j d d k r] Pq] q] Wt S| | k rÉ |  | |  | |  | <|  | <t d | | |   n  |  | | d k r>|  | | j   } x+ t | |  D] } |  | | c | 9<qWt d | d t |  |   n  xc t | d |  D]N } |  | | } x7 t | |  D]& } |  | | c |  | | | 8<qvWqRW| d | k  r: t d	 | d
 | |   q: q: Wx t | d d d  D]m } xd t d |  D]S } xJ t | d | d d  D]. } |  | | c |  | | |  | | 8<qWqţWqčWt d |   t S(   s  Puts given matrix (2D array) into the Reduced Row Echelon Form.
  Returns True if successful, False if 'm' is singular.
  Assumes all elements are in Z/nZ with n a powr of 2.  One line changed
  Based on floating point code by Jarno Elonen,April 2005,
  released into Public Domaini    s
   Starting ms   Working on rowi   s	   swap rowsi   s   Normalizing rows   Multiple by inverses   Zeroed columns	   below rowi˙˙˙˙s   Final, after back substitutioni˙˙˙˙(	   R   R   R   R   t   valueR   t   inverseR   R   (	   R	   R   R   R   R   R   R   R   R   (    (    s   C:\anh\www\331\gaussJordan.pyt   gauss_jordanModPow2N   s8    ( !4c         C   sO  t  |   t  |  d  } } |  d d j   } t d |   xut d |  D]d} t d |  x3 t | |  D] } |  | | d k rq Pqq qq Wt S| | k rÖ |  | |  | |  | <|  | <t d | | |   n  x[t | d |  D]F} t |  | |  } t |  | |  } t | |  \ }	 }
 } } } g  t | |  D]( } |
 |  | | | |  | | ^ qFg  t | |  D]( } | |  | | | |  | | ^ q|  | | )|  | | )t d | d |
 d | d	 | d | d
 d | d | d | d	 | d | |   t |
 | | |  d k sę t	  qę Wt
 t |  | |  |  \ }	 } } |	 d k rjt Sx+ t | |  D] } |  | | c | 9<qzWt d | d | | |   qN Wx t | d d d  D]m } xd t d |  D]S } xJ t | d | d d  D]. } |  | | c |  | | |  | | 8<qWqăWqÍWt d |   t S(   s  Puts given matrix (2D array) into the Reduced Row Echelon Form.
  Returns True if successful, False if 'm' is singular.
  Assumes all element are modular with some mod n.
  This version is the most general.  More efficient alternatives:
  If n is prime: gauss_jordanExactField
  If n is a power of 2: gauss_jordanModPow2
  Based on floating point code by Jarno Elonen,April 2005,
  released into Public Domaini    s
   Starting ms   working on rows	   swap rowsi   t   rows   <-s   * rowt   +s   
s   normalize rows   Mult by inversei˙˙˙˙s%   Back substitute to get final solutioni˙˙˙˙(   R   t   modulusR   R   R   R   R   R   R   t   AssertionErrorR   R   (   R	   R   R   t   NR   R   R   t   at   bt   gcdt   st   tt   ut   vt   iR   R   (    (    s   C:\anh\www\331\gaussJordan.pyt   gauss_jordanModr   sB     ;R$%(&!4c          G   s#   t  r x |  D]
 } | Gq WHn  d S(   s%   print variable length parameter list.N(   t   VERBOSE(   t   argst   arg(    (    s   C:\anh\www\331\gaussJordan.pyR   Ł   s    c          G   s)   t  r% t |  d    t |  d  n  d S(   s>   Print variable length parameter list, with a matrix/list last.i˙˙˙˙N(   R*   R   t   display(   R+   (    (    s   C:\anh\www\331\gaussJordan.pyR   Ş   s    g        c         C   s6   g  t  |   D]% } g  t  |  D] } | ^ q  ^ q S(   s9    Make a matrix with given height, width, filled with elt.(   R   (   t   heightt   widtht   eltt   jR(   (    (    s   C:\anh\www\331\gaussJordan.pyt   makeMat°   s    c         C   sA   t  |  |  | |  } x$ t |  D] \ } } | | | <q# W| S(   s]   Return the ientity matrix of size height.
    The value of ONE sets the type of the elements.(   R2   t	   enumerate(   R.   t   ONEt   ansR(   t   r(    (    s   C:\anh\www\331\gaussJordan.pyt   identity´   s    c         C   s/   x( t  |   D] \ } } | | | 7} q Wd S(   s;   mutate matrix m, appending rows of matrix b(of same height)N(   R3   (   R	   R"   R(   R6   (    (    s   C:\anh\www\331\gaussJordan.pyt   adjoinź   s    c         C   s   x |  D] } | | | 5q Wd S(   s0    mutate m, removing column c: start <= c < past.N(    (   R	   t   startt   pastR6   (    (    s   C:\anh\www\331\gaussJordan.pyt   collapseColumnsÁ   s    c   
      C   s!  t  |  d t  s |  g }  n  t |   } t |  d  } t  | d t  s` t | g  } n  | t |  k sx t  t | d  } | d k rŚ t | |  } n  xt t |  D]f } x] t |  D]O } d } x2 t |  D]$ }	 | |  | |	 | |	 | 7} qß W| | | | <qĆ Wqł W| S(   s  Multiply matrices m1*m2, using ans as place for the answer if not None.
    Returns the answer.
    If m1 is a simple list, it is taken as a row matrix.
    If m2 is a simple list, it is taken as a column matrix.
    The result is always a new matrix (list of lists).
    i    N(   t
   isinstancet   listR   t	   transposeR   t   NoneR2   R   (
   t   m1t   m2R5   R   t   kR   R6   R   t   totR(   (    (    s   C:\anh\www\331\gaussJordan.pyt   mulĆ   s"    "i   c         C   sT   t  |  t  rD g  t |  |  D]! \ } } t | | | |  ^ q S|  | | | S(   sg   return a*m1 + b*m2 for same sized matrices/lists m1 and m2,
    and scalar (not list) multipliers a, b.(   R<   R=   t   zipt   linComb(   R@   RA   R!   R"   t   r1t   r2(    (    s   C:\anh\www\331\gaussJordan.pyRF   ŕ   s    5c         C   s   t  |  | d d  S(   s7   return m1 - m2 for same sized matrices/lists m1 and m2.i   i˙˙˙˙(   RF   (   R@   RA   (    (    s   C:\anh\www\331\gaussJordan.pyt   subë   s    c         C   s9   t  |  t  r/ g  |  D] } t | |  ^ q S| |   S(   sÖ   Return a new matrix/list with all elements e of matrix m replaced by
    cls(e).  The name is chosen to suggest a class conversion,
    but any function could be used for 1-1 replacements of non-list elements.
    (   R<   R=   t
   matConvert(   t   matt   clsR6   (    (    s   C:\anh\www\331\gaussJordan.pyRJ   ď   s     c         C   s   d   } t  |  |  S(   s?   Return a matrix/list copying each non-list element in matrix m.c         S   s   |  S(   N(    (   R   (    (    s   C:\anh\www\331\gaussJordan.pyt   sameü   s    (   RJ   (   R	   RM   (    (    s   C:\anh\www\331\gaussJordan.pyt   copyMatú   s    	c         C   s]   t  |  d t  s |  g }  n  g  t t |  d   D]# } g  |  D] } | | ^ qC ^ q6 S(   s˘   Return a new matrix that is the transpose of m.
    If a single list is provided rather than a list of lists, it is treated
    as a single row matrix, [m]. 
    i    (   R<   R=   R   R   (   R	   R1   R6   (    (    s   C:\anh\www\331\gaussJordan.pyR>      s    c         C   s   t  | d t  } | } | r/ t |  } n  t |   }  t |  |  | |   } t |  d t |    | r t |   d | (n |  | (| S(   sŁ   solve mx = v for square matrix m, replacing v with the solution x.
    If v is a single list, it is understood as a column matrix.
    Return True on success.
    i    (   R<   R=   R>   RN   R8   R;   R   (   R	   R'   t   gjt   isVect   vOrigt   success(    (    s   C:\anh\www\331\gaussJordan.pyt   mxvSolve	  s    s   ignore!c         C   sP   |  d d |  d d d } t  t |   |  } t |  | |  } | |  (| S(   sÁ   Return True and convert m to its inverse in place if possible,
    using Gauss-Jordan variant gj.
    Return False otherwise, and m is not meaningful.
    cls is ignored - obsolete, not needed.i    i   (   R7   R   RS   (   R	   RO   RL   R4   R'   RR   (    (    s   C:\anh\www\331\gaussJordan.pyt   invert  s
    i   c         C   sŰ   t  |  t  s% | r | Gn  |  GHd St  |  d t  sS | sG d } n  |  g }  n  | ra | GHn  t  |  d d t  rĄ d G|  d d j   GHt |  t  }  n  x3 |  D]+ } x! | D] } t | t |   Gqľ WHq¨ Wd S(   s4   Pretty print a matrix or list; also prints a scalar.Ni    s   Plain list:s   Elements are mod(   R<   R=   R   R   RJ   R   t   formatt   str(   R	   t   labelt   colWidthR6   R   (    (    s   C:\anh\www\331\gaussJordan.pyR-   )  s$     	c         C   s   t  |  |  }  t |   } t |  d | j  t |  t t |   | d    t |  d  | |   sr d GHn t |  d | j  t | | |  d S(   s   Show off inversion of matrix m using Gauss-Jordan version f,
    where the elements e of m are transformed first to cls(e).
    s   Matrix to reduce, using i   s   With lines adjoineds   Failed!s   After GJ variant N(   RJ   RN   R-   t	   func_nameR8   R7   R   t
   showInvert(   R	   RL   t   ft   mc(    (    s   C:\anh\www\331\gaussJordan.pyt   showOff=  s    "c         C   s   t  |  d  t |  |  } t t  t | |  s= d GHn  t   t  | d  t |  |  } t d |  | t t	 |   | d   k s t
  d S(   s   Show off inversion of matrix m using Gauss-Jordan version gj,
    where the elements e of m are transformed first to cls(e).
    s,   Matrix; Now do inverse in one function call:s   Not invertiblet   Inverteds   Multiply and checki   N(   R-   t
   convertMatt
   setVerboseR   RT   t
   oldVerboseRD   R   R7   R   R   (   R	   RO   RL   R\   t   check(    (    s   C:\anh\www\331\gaussJordan.pyRZ   L  s    
c         C   sŰ   t  |  |  }  t  | |  } t |  d  t | d  t |  } t | d t  } t |  t |  | |  s| d GHn  t   t | d  t |  |  } | r¸ t	 |  d } n  t
 d |  | | k s× t  d S(   s   Show off inversion of matrix m using Gauss-Jordan version gj,
    where the elements e of m are transformed first to cls(e).
    t   Matrixs   v:i    s   Not invertiblet   Solutions   Multiply and checkN(   RJ   R-   RN   R<   R=   R`   RS   Ra   RD   R>   R   R   (   R	   R'   RO   RL   t   verboset   vcRP   Rb   (    (    s   C:\anh\www\331\gaussJordan.pyt   showMxvSolve[  s     
c          G   s#   t  t d d d d d g |   d S(   s>   See linComb for parameters.  Display all parametersand result.s#   Testing linComb, return a*m1 + b*m2R@   RA   R!   R"   N(   t   showOpRF   (   t   param(    (    s   C:\anh\www\331\gaussJordan.pyt   showLinCombp  s    c         G   sR   | d GHx/ t  |  D]! \ } } t | | | d  q Wt |  |   d  d  S(   Ni    i   t   result(   R3   R-   (   R[   t   labelsRi   R(   t   p(    (    s   C:\anh\www\331\gaussJordan.pyRh   v  s    	c          C   s  d d g d d g g }  d d g d d g g } d d g d d	 g g } d
 d	 d g d d d g d d d g g } d
 d	 d g d d d g d d d g g } d d d g d d d g d d d g g } t  d  } t  d  } t  d  } t  d  }	 t  d  }
 t |   t |  t |  t  }  t | t  } t |  | t  t | | t  t | | t  t | | t  d d d g } t | | t |  t | | t  t | | t  t | |	 t  t | |
 t  t |  | d d   t	 t
 d! d" d# g t | |  t | |   d$ S(%   s   test of GassJordan versions.g      đ?g       @g      @g      @g        i   i   i   i   iX   iw   i   i   i%   i7   i   i5   i   i!   iT   i   i   i   i   ii   i,   i   i   iZ   i´   i   i˙˙˙˙s   Testing sub(m1,m2)R@   RA   N(   R    R]   RJ   R   R   R   Rg   R)   Rj   Rh   RI   (   R	   RA   t   m3t   m4t   m5t   m6t   Mod11t   Mod16t   Mod128t   Mod90t   Mod180R'   (    (    s   C:\anh\www\331\gaussJordan.pyt   test|  sJ    			

c         C   s   t  j t  |  a d S(   sL   Set global verbosity, remember old value; pair with an oldVerbose call.
    N(   t   _V_STACKt   appendR*   (   Re   (    (    s   C:\anh\www\331\gaussJordan.pyR`   Ź  s    c           C   s   t  j   a d S(   s<   Recall last global verbosity value remembered by setVerbose.N(   Rx   t   popR*   (    (    (    s   C:\anh\www\331\gaussJordan.pyRa   ł  s    t   __main__Nl    d(	 (*   t   __doc__t	   mod_arithR    R   R   R   R   R   R   R)   R   R   R2   R7   R8   R;   R?   RD   RF   t   addRI   RJ   R_   RN   R>   RS   RT   R-   t   floatR]   RZ   R   Rg   Rj   Rh   Rw   R*   Rx   R`   Ra   t   __name__R   (    (    (    s   C:\anh\www\331\gaussJordan.pyt   <module>   sH   	'	$	1														-		