Ticket #12555: 12555_CA.patch

File 12555_CA.patch, 88.6 KB (added by roed, 15 months ago)
  • new file sage/rings/padics/CA_template.pxi

    # HG changeset patch
    # User David Roe <roed@math.harvard.edu>
    # Date 1330837831 28800
    # Node ID 7499e540d8aab77ef8248e6078c7fc898405e54f
    # Parent  1bcc70085997c9c22eb530a00ce71617c988d495
    #12555: capped absolute templates
    
    diff --git a/sage/rings/padics/CA_template.pxi b/sage/rings/padics/CA_template.pxi
    new file mode 100644
    - +  
     1""" 
     2Capped absolute template for complete discrete valuation rings. 
     3 
     4In order to use this template you need to write a linkage file and gluing file. 
     5For an example see mpz_linkage.pxi (linkage file) and padic_capped_absolute_element.pyx (gluing file). 
     6 
     7The linkage file implements a common API that is then used in the class CAElement defined here. 
     8See the documentation of mpz_linkage.pxi for the functions needed. 
     9 
     10The gluing file does the following: 
     11 
     12- includes "../../ext/cdefs.pxi" 
     13- ctypedef's celement to be the appropriate type (e.g. mpz_t) 
     14- includes the linkage file 
     15- includes this template 
     16- defines a concrete class inheriting from CRElement, and implements any desired extra methods 
     17 
     18AUTHORS: 
     19 
     20- David Roe (2012-3-1) -- initial version 
     21""" 
     22 
     23#***************************************************************************** 
     24#       Copyright (C) 2012 David Roe <roed.math@gmail.com> 
     25#                          William Stein <wstein@gmail.com> 
     26# 
     27#  Distributed under the terms of the GNU General Public License (GPL) 
     28# 
     29#                  http://www.gnu.org/licenses/ 
     30#***************************************************************************** 
     31 
     32# This file implements common functionality among template elements 
     33include "padic_template_element.pxi" 
     34 
     35from sage.structure.element cimport Element 
     36from sage.rings.padics.common_conversion cimport comb_prec, _process_args_and_kwds 
     37from sage.rings.integer_ring import ZZ 
     38from sage.rings.rational_field import QQ 
     39from sage.categories.sets_cat import Sets 
     40from sage.categories.sets_with_partial_maps import SetsWithPartialMaps 
     41from sage.categories.homset import Hom 
     42 
     43cdef class CAElement(pAdicTemplateElement): 
     44    cdef int _set(self, x, long val, long xprec, absprec, relprec) except -1: 
     45        """ 
     46        TESTS:: 
     47 
     48            sage: R = ZpCA(5) 
     49            sage: a = R(17,5); a #indirect doctest 
     50            2 + 3*5 + O(5^5) 
     51            sage: a = R(75, absprec = 5, relprec = 4); a #indirect doctest 
     52            3*5^2 + O(5^5) 
     53            sage: a = R(25/9, absprec = 5); a #indirect doctest 
     54            4*5^2 + 2*5^3 + O(5^5) 
     55            sage: a = R(25/9, absprec = 5, relprec = 4); a #indirect doctest 
     56            4*5^2 + 2*5^3 + O(5^5) 
     57        """ 
     58        cconstruct(self.value, self.prime_pow) 
     59        cdef long rprec = comb_prec(relprec, self.prime_pow.prec_cap) 
     60        cdef long aprec = comb_prec(absprec, min(self.prime_pow.prec_cap, xprec)) 
     61        if aprec <= val: 
     62            csetzero(self.value, self.prime_pow) 
     63            self.absprec = aprec 
     64        else: 
     65            self.absprec = min(aprec, val + rprec) 
     66            cconv(self.value, x, self.absprec, 0, self.prime_pow) 
     67 
     68    cdef CAElement _new_c(self): 
     69        """ 
     70        Creates a new element with the same basic info. 
     71 
     72        TESTS:: 
     73 
     74            sage: R = ZpCA(5); R(6,5) * R(7,8) #indirect doctest 
     75            2 + 3*5 + 5^2 + O(5^5) 
     76        """ 
     77        cdef CAElement ans = PY_NEW(self.__class__) 
     78        ans._parent = self._parent 
     79        ans.prime_pow = self.prime_pow 
     80        cconstruct(ans.value, ans.prime_pow) 
     81        return ans 
     82 
     83    cdef int check_preccap(self) except -1: 
     84        """ 
     85        Checks that this element doesn't have precision higher than allowed by the precision cap. 
     86 
     87        TESTS:: 
     88 
     89            sage: ZpCA(5)(1).lift_to_precision(30) 
     90            Traceback (most recent call last): 
     91            ... 
     92            PrecisionError: Precision higher than allowed by the precision cap. 
     93        """ 
     94        if self.absprec > self.prime_pow.prec_cap: 
     95            raise PrecisionError("Precision higher than allowed by the precision cap.") 
     96 
     97    def __copy__(self): 
     98        """ 
     99        Returns a copy of ``self``. 
     100 
     101        EXAMPLES:: 
     102 
     103            sage: a = ZpCA(5,6)(17); b = copy(a) 
     104            sage: a == b 
     105            True 
     106            sage: a is b 
     107            False 
     108        """ 
     109        cdef CAElement ans = self._new_c() 
     110        ans.absprec = self.absprec 
     111        ccopy(ans.value, self.value, ans.prime_pow) 
     112        return ans 
     113 
     114    def __dealloc__(self): 
     115        """ 
     116        Deallocation. 
     117 
     118        TESTS:: 
     119 
     120            sage: R = ZpCA(5) 
     121            sage: a = R(17) 
     122            sage: del(a) 
     123        """ 
     124        cdestruct(self.value, self.prime_pow) 
     125 
     126    def __reduce__(self): 
     127        """ 
     128        Pickling. 
     129 
     130        TESTS:: 
     131         
     132            sage: a = ZpCA(5)(-3) 
     133            sage: type(a) 
     134            <type 'sage.rings.padics.padic_capped_absolute_element.pAdicCappedAbsoluteElement'> 
     135            sage: loads(dumps(a)) == a 
     136            True 
     137        """ 
     138        return unpickle_cae_v2, (self.__class__, self.parent(), cpickle(self.value, self.prime_pow), self.absprec) 
     139 
     140    def __richcmp__(self, right, int op): 
     141        """ 
     142        Comparison. 
     143 
     144        TESTS:: 
     145 
     146            sage: R = ZpCA(5) 
     147            sage: a = R(17) 
     148            sage: b = R(21) 
     149            sage: a == b 
     150            False 
     151            sage: a < b 
     152            True 
     153        """ 
     154        return (<Element>self)._richcmp(right, op) 
     155 
     156    cpdef ModuleElement _neg_(self): 
     157        """ 
     158        Returns the negation of self. 
     159 
     160        EXAMPLES:: 
     161         
     162            sage: R = Zp(5, prec=10, type='capped-abs') 
     163            sage: a = R(1) 
     164            sage: -a #indirect doctest 
     165            4 + 4*5 + 4*5^2 + 4*5^3 + 4*5^4 + 4*5^5 + 4*5^6 + 4*5^7 + 4*5^8 + 4*5^9 + O(5^10) 
     166        """ 
     167        cdef CAElement ans = self._new_c() 
     168        ans.absprec = self.absprec 
     169        cneg(ans.value, self.value, ans.absprec, ans.prime_pow) 
     170        creduce_small(ans.value, ans.value, ans.absprec, ans.prime_pow) 
     171        return ans 
     172 
     173    cpdef ModuleElement _add_(self, ModuleElement _right): 
     174        """ 
     175        Addition. 
     176         
     177        EXAMPLES:: 
     178         
     179            sage: R = ZpCA(13, 4) 
     180            sage: R(2) + R(3) #indirect doctest 
     181            5 + O(13^4) 
     182            sage: R(12) + R(1) 
     183            13 + O(13^4) 
     184        """ 
     185        cdef CAElement right = <CAElement>_right 
     186        cdef CAElement ans = self._new_c() 
     187        ans.absprec = min(self.absprec, right.absprec) 
     188        cadd(ans.value, self.value, right.value, ans.absprec, ans.prime_pow) 
     189        creduce_small(ans.value, ans.value, ans.absprec, ans.prime_pow) 
     190        return ans 
     191 
     192    cpdef ModuleElement _sub_(self, ModuleElement _right): 
     193        """ 
     194        Subtraction. 
     195         
     196        EXAMPLES:: 
     197         
     198            sage: R = ZpCA(13, 4) 
     199            sage: R(10) - R(10) #indirect doctest 
     200            O(13^4) 
     201            sage: R(10) - R(11) 
     202            12 + 12*13 + 12*13^2 + 12*13^3 + O(13^4) 
     203        """ 
     204        cdef CAElement right = <CAElement>_right 
     205        cdef CAElement ans = self._new_c() 
     206        ans.absprec = min(self.absprec, right.absprec) 
     207        csub(ans.value, self.value, right.value, ans.absprec, ans.prime_pow) 
     208        creduce_small(ans.value, ans.value, ans.absprec, ans.prime_pow) 
     209        return ans 
     210 
     211    def __invert__(self): 
     212        """ 
     213        Returns the multiplicative inverse of ``self``. 
     214         
     215        EXAMPLES:: 
     216         
     217            sage: R = ZpCA(17) 
     218            sage: ~R(-1) == R(-1) 
     219            True 
     220            sage: ~R(5) * 5 
     221            1 + O(17^20) 
     222            sage: ~R(5) 
     223            7 + 3*17 + 10*17^2 + 13*17^3 + 6*17^4 + 3*17^5 + 10*17^6 + 13*17^7 + 6*17^8 + 3*17^9 + 10*17^10 + 13*17^11 + 6*17^12 + 3*17^13 + 10*17^14 + 13*17^15 + 6*17^16 + 3*17^17 + 10*17^18 + 13*17^19 + O(17^20) 
     224            sage: ~R(-1) == R(-1) #indirect doctest 
     225            True 
     226        """ 
     227        return self.parent().fraction_field()(self).__invert__() 
     228 
     229    cpdef RingElement _mul_(self, RingElement _right): 
     230        """ 
     231        Multiplication. 
     232         
     233        EXAMPLES:: 
     234         
     235            sage: R = ZpCA(5) 
     236            sage: a = R(20,5); b = R(75, 4); a * b #indirect doctest 
     237            2*5^3 + 2*5^4 + O(5^5) 
     238        """ 
     239        cdef CAElement right = <CAElement>_right         
     240        cdef CAElement ans = self._new_c() 
     241        cdef long vals, valr 
     242        if self.absprec == self.prime_pow.prec_cap and right.absprec == self.prime_pow.prec_cap: 
     243            ans.absprec = self.absprec 
     244        else: 
     245            vals = self.valuation_c() 
     246            valr = right.valuation_c() 
     247            ans.absprec = min(vals + valr + min(self.absprec - vals, right.absprec - valr), self.prime_pow.prec_cap) 
     248        cmul(ans.value, self.value, right.value, ans.absprec, ans.prime_pow) 
     249        creduce(ans.value, ans.value, ans.absprec, ans.prime_pow) 
     250        return ans 
     251 
     252    cpdef RingElement _div_(self, RingElement right): 
     253        """ 
     254        Division. 
     255 
     256        EXAMPLES:: 
     257 
     258            sage: R = ZpCA(13, 4) 
     259            sage: R(2) / R(3) # indirect doctest 
     260            5 + 4*13 + 4*13^2 + 4*13^3 + O(13^4) 
     261            sage: a = R(169 * 2) / R(13); a 
     262            2*13 + O(13^3) 
     263            sage: R(13) / R(169 * 2) 
     264            7*13^-1 + 6 + O(13) 
     265            sage: ~a 
     266            7*13^-1 + 6 + O(13) 
     267            sage: 1 / a 
     268            7*13^-1 + 6 + O(13) 
     269        """ 
     270        K = self.parent().fraction_field() 
     271        return K(self) / K(right) 
     272 
     273    def __pow__(CAElement self, _right, dummy): 
     274        """ 
     275        Exponentiation. 
     276         
     277        EXAMPLES:: 
     278         
     279            sage: R = ZpCA(11, 5) 
     280            sage: R(1/2)^5 
     281            10 + 7*11 + 11^2 + 5*11^3 + 4*11^4 + O(11^5) 
     282            sage: R(1/32) 
     283            10 + 7*11 + 11^2 + 5*11^3 + 4*11^4 + O(11^5) 
     284            sage: R(1/2)^5 == R(1/32) 
     285            True 
     286            sage: R(3)^1000 
     287            1 + 4*11^2 + 3*11^3 + 7*11^4 + O(11^5) 
     288        """ 
     289        cdef long base_level, exp_prec, relprec, val 
     290        cdef mpz_t tmp 
     291        cdef Integer right 
     292        cdef CAElement base, ans = self._new_c() 
     293        if isinstance(_right, (int, long, Integer)) and _right == 0: 
     294            # return 1 to maximum precision 
     295            ans.absprec = self.prime_pow.prec_cap 
     296            csetone(ans.value, ans.prime_pow) 
     297        elif ciszero(self.value, self.prime_pow): 
     298            # If a positive integer exponent, return an inexact zero of valuation right * self.ordp.  Otherwise raise an error. 
     299            if isinstance(_right, (int, long)): 
     300                _right = Integer(_right) 
     301            if PY_TYPE_CHECK(_right, Integer): 
     302                if _right < 0: 
     303                    raise ValueError, "Need more precision" 
     304                if self.absprec == self.prime_pow.prec_cap or mpz_cmp_si((<Integer>_right).value, self.prime_pow.prec_cap / self.absprec + 1) > 0: 
     305                    ans.absprec = self.prime_pow.prec_cap 
     306                else: 
     307                    ans.absprec = min(self.prime_pow.prec_cap, self.absprec * mpz_get_si((<Integer>_right).value)) 
     308                csetzero(ans.value, ans.prime_pow) 
     309            elif PY_TYPE_CHECK(_right, Rational) or (PY_TYPE_CHECK(_right, pAdicGenericElement) and _right._is_base_elt(self.prime_pow.prime)): 
     310                raise ValueError("Need more precision") 
     311            else: 
     312                raise TypeError, "exponent must be an integer, rational or base p-adic with the same prime" 
     313        else: 
     314            val = self.valuation_c() 
     315            relprec = self.absprec - self.valuation_c() 
     316            # pow_helper is defined in padic_template_element.pxi 
     317            right = pow_helper(&relprec, &exp_prec, val, self.absprec - val, _right, self.prime_pow.prime) 
     318            if exp_prec == 0: 
     319                # a p-adic exponent with no relative precision 
     320                ans.absprec = 0 
     321                csetzero(ans.value, ans.prime_pow) 
     322                return ans 
     323            mpz_init_set_si(tmp, val) 
     324            mpz_mul(tmp, right.value, tmp) 
     325            if mpz_cmp_si(tmp, self.prime_pow.prec_cap) >= 0: 
     326                ans.absprec = self.prime_pow.prec_cap 
     327                csetzero(ans.value, ans.prime_pow) 
     328            else: 
     329                ans.absprec = min(mpz_get_si(tmp) + relprec, self.prime_pow.prec_cap) 
     330                if right < 0: 
     331                    base = ~self 
     332                    right = -right 
     333                else: 
     334                    base = self 
     335                cpow(ans.value, base.value, right.value, ans.absprec, ans.prime_pow) 
     336            mpz_clear(tmp) 
     337        return ans 
     338         
     339    cdef pAdicTemplateElement _lshift_c(self, long shift): 
     340        """ 
     341        Multiplies by ``p^shift``. 
     342 
     343        TESTS:: 
     344 
     345            sage: R = ZpCA(5); a = R(17); a << 2 
     346            2*5^2 + 3*5^3 + O(5^20) 
     347        """ 
     348        if shift < 0: 
     349            return self._rshift_c(-shift) 
     350        elif shift == 0: 
     351            return self 
     352        cdef CAElement ans = self._new_c() 
     353        if shift >= self.prime_pow.prec_cap: 
     354            csetzero(ans.value, ans.prime_pow) 
     355            ans.absprec = self.prime_pow.prec_cap 
     356        else: 
     357            ans.absprec = min(self.absprec + shift, self.prime_pow.prec_cap) 
     358            cshift(ans.value, self.value, shift, ans.absprec, ans.prime_pow, False) 
     359        return ans 
     360 
     361    cdef pAdicTemplateElement _rshift_c(self, long shift): 
     362        """ 
     363        Divides by ``p^shift`` and truncates. 
     364 
     365        TESTS:: 
     366 
     367            sage: R = ZpCA(5); a = R(77); a >> 1 
     368            3*5 + O(5^19) 
     369        """ 
     370        if shift < 0: 
     371            return self._lshift_c(-shift) 
     372        elif shift == 0: 
     373            return self 
     374        cdef CAElement ans = self._new_c() 
     375        if shift >= self.absprec: 
     376            csetzero(ans.value, ans.prime_pow) 
     377            ans.absprec = 0 
     378        else: 
     379            ans.absprec = self.absprec - shift 
     380            cshift(ans.value, self.value, -shift, ans.absprec, ans.prime_pow, False) 
     381        return ans 
     382 
     383    def add_bigoh(self, absprec): 
     384        """ 
     385        Returns a new element with absolute precision decreased to 
     386        ``prec``.  The precision never increases. 
     387         
     388        INPUT: 
     389         
     390        - ``self`` -- a `p`-adic element 
     391         
     392        - ``prec`` -- an integer 
     393             
     394        OUTPUT: 
     395         
     396        - ``element`` -- ``self`` with precision set to the minimum of ``self's`` precision and ``prec`` 
     397         
     398        EXAMPLES:: 
     399         
     400            sage: R = Zp(7,4,'capped-abs','series'); a = R(8); a.add_bigoh(1) 
     401            1 + O(7) 
     402 
     403            sage: k = ZpCA(3,5) 
     404            sage: a = k(41); a 
     405            2 + 3 + 3^2 + 3^3 + O(3^5) 
     406            sage: a.add_bigoh(7) 
     407            2 + 3 + 3^2 + 3^3 + O(3^5) 
     408            sage: a.add_bigoh(3) 
     409            2 + 3 + 3^2 + O(3^3)             
     410        """ 
     411        cdef long aprec, newprec 
     412        if PY_TYPE_CHECK(absprec, int): 
     413            aprec = absprec 
     414        else: 
     415            if not PY_TYPE_CHECK(absprec, Integer): 
     416                absprec = Integer(absprec) 
     417            aprec = mpz_get_si((<Integer>absprec).value) 
     418        if aprec >= self.absprec: 
     419            return self 
     420        cdef CAElement ans = self._new_c() 
     421        ans.absprec = aprec 
     422        creduce(ans.value, self.value, ans.absprec, ans.prime_pow) 
     423        return ans 
     424 
     425    cpdef bint _is_exact_zero(self) except -1: 
     426        return False 
     427 
     428    cpdef bint _is_inexact_zero(self) except -1: 
     429        """ 
     430        Returns ``True`` if ``self`` is indistinguishable from zero. 
     431         
     432        EXAMPLES:: 
     433         
     434            sage: R = ZpCA(7, 5) 
     435            sage: R(7^5)._is_inexact_zero() 
     436            True 
     437            sage: R(0,4)._is_inexact_zero() 
     438            True 
     439            sage: R(0)._is_inexact_zero() 
     440            True 
     441        """ 
     442        return ciszero(self.value, self.prime_pow) 
     443 
     444    def is_zero(self, absprec = None): 
     445        r""" 
     446        Returns whether ``self`` is zero modulo ``p^absprec``. 
     447         
     448        INPUT: 
     449         
     450        - ``self`` -- a `p`-adic element 
     451         
     452        - ``prec`` -- an integer 
     453 
     454        OUTPUT: 
     455         
     456        - ``boolean`` -- whether self is zero 
     457           
     458        EXAMPLES:: 
     459         
     460            sage: R = ZpCA(17, 6) 
     461            sage: R(0).is_zero() 
     462            True 
     463            sage: R(17^6).is_zero() 
     464            True 
     465            sage: R(17^2).is_zero(absprec=2) 
     466            True 
     467        """ 
     468        cdef bint iszero = ciszero(self.value, self.prime_pow) 
     469        if absprec is None: 
     470            return iszero 
     471        cdef long val = self.valuation_c() 
     472        if isinstance(absprec, int): 
     473            if iszero and absprec > self.absprec: 
     474                raise PrecisionError, "Not enough precision to determine if element is zero" 
     475            return val >= absprec 
     476        if not PY_TYPE_CHECK(absprec, Integer): 
     477            absprec = Integer(absprec) 
     478        if iszero: 
     479            if mpz_cmp_si((<Integer>absprec).value, val) > 0: 
     480                raise PrecisionError, "Not enough precision to determine if element is zero" 
     481            else: 
     482                return True 
     483        return mpz_cmp_si((<Integer>absprec).value, val) <= 0 
     484 
     485    def __nonzero__(self): 
     486        return not ciszero(self.value, self.prime_pow) 
     487 
     488    def is_equal_to(self, _right, absprec=None): 
     489        r""" 
     490        Returns whether ``self`` is equal to ``right`` modulo ``p^absprec``. 
     491 
     492        INPUT: 
     493         
     494        - ``self`` -- a `p`-adic element 
     495         
     496        - ``right`` -- a `p`-adic element with the same parent 
     497         
     498        - ``absprec`` -- an integer 
     499 
     500        OUTPUT: 
     501         
     502        - ``boolean`` -- whether ``self`` is equal to ``right`` 
     503           
     504        EXAMPLES:: 
     505         
     506            sage: R = ZpCA(2, 6) 
     507            sage: R(13).is_equal_to(R(13)) 
     508            True 
     509            sage: R(13).is_equal_to(R(13+2^10)) 
     510            True 
     511            sage: R(13).is_equal_to(R(17), 2) 
     512            True 
     513            sage: R(13).is_equal_to(R(17), 5) 
     514            False 
     515        """ 
     516        cdef CAElement right 
     517        cdef long aprec, rprec, sval, rval 
     518        if self.parent() is _right.parent(): 
     519            right = <CAElement>_right 
     520        else: 
     521            right = <CAElement>self.parent()(_right) 
     522        if absprec is None: 
     523            aprec = min(self.absprec, right.absprec) 
     524        else: 
     525            if not PY_TYPE_CHECK(absprec, Integer): 
     526                absprec = Integer(absprec) 
     527            if mpz_fits_slong_p((<Integer>absprec).value) == 0: 
     528                if mpz_sgn((<Integer>absprec).value) < 0: 
     529                    return True 
     530                else: 
     531                    raise PrecisionError, "Elements not known to enough precision" 
     532            aprec = mpz_get_si((<Integer>absprec).value) 
     533            if aprec > self.absprec or aprec > right.absprec: 
     534                raise PrecisionError, "Elements not known to enough precision" 
     535        return ccmp(self.value, right.value, aprec, aprec < self.absprec, aprec < right.absprec, self.prime_pow) == 0 
     536 
     537    cdef int _cmp_units(self, pAdicGenericElement _right): 
     538        cdef CAElement right = <CAElement>_right 
     539        cdef long aprec = min(self.absprec, right.absprec) 
     540        if aprec == 0: 
     541            return 0 
     542        return ccmp(self.value, right.value, aprec, aprec < self.absprec, aprec < right.absprec, self.prime_pow) 
     543 
     544    cdef pAdicTemplateElement lift_to_precision_c(self, long absprec): 
     545        if absprec <= self.absprec: 
     546            return self 
     547        cdef CAElement ans = self._new_c() 
     548        ccopy(ans.value, self.value, ans.prime_pow) 
     549        ans.absprec = absprec 
     550        return ans 
     551 
     552    def list(self, lift_mode = 'simple'): 
     553        """ 
     554        Returns a list of coefficients of `p` starting with `p^0` 
     555         
     556        INPUT: 
     557         
     558        - ``self`` -- a `p`-adic element 
     559         
     560        - ``lift_mode`` -- ``'simple'``, ``'smallest'`` or 
     561          ``'teichmuller'`` (default ``'simple'``) 
     562 
     563        OUTPUT: 
     564         
     565        - ``list`` -- the list of coefficients of ``self`` 
     566 
     567        NOTES: 
     568         
     569        - Returns a list `[a_0, a_1, \ldots, a_n]` so that: 
     570 
     571          + If ``lift_mode = 'simple'``, `a_i` is an integer with `0 
     572            \le a_i < p`. 
     573 
     574          + If ``lift_mode = 'smallest'``, `a_i` is an integer with 
     575            `-p/2 < a_i \le p/2`. 
     576 
     577          + If ``lift_mode = 'teichmuller'``, `a_i` has the same 
     578            parent as `self` and `a_i^p \equiv a_i` modulo 
     579            ``p^(self.precision_absolute() - i)`` 
     580 
     581        - `\sum_{i = 0}^n a_i \cdot p^i =` ``self``, modulo the 
     582          precision of ``self``. 
     583             
     584 
     585        EXAMPLES:: 
     586         
     587            sage: R = ZpCA(7,6); a = R(12837162817); a 
     588            3 + 4*7 + 4*7^2 + 4*7^4 + O(7^6) 
     589            sage: L = a.list(); L 
     590            [3, 4, 4, 0, 4] 
     591            sage: sum([L[i] * 7^i for i in range(len(L))]) == a 
     592            True 
     593            sage: L = a.list('smallest'); L 
     594            [3, -3, -2, 1, -3, 1] 
     595            sage: sum([L[i] * 7^i for i in range(len(L))]) == a 
     596            True 
     597            sage: L = a.list('teichmuller'); L 
     598            [3 + 4*7 + 6*7^2 + 3*7^3 + 2*7^5 + O(7^6), 
     599            O(7^5), 
     600            5 + 2*7 + 3*7^3 + O(7^4), 
     601            1 + O(7^3), 
     602            3 + 4*7 + O(7^2), 
     603            5 + O(7)] 
     604            sage: sum([L[i] * 7^i for i in range(len(L))]) 
     605            3 + 4*7 + 4*7^2 + 4*7^4 + O(7^6) 
     606        """ 
     607        if ciszero(self.value, self.prime_pow): 
     608            return [] 
     609        if lift_mode == 'teichmuller': 
     610            return self.teichmuller_list() 
     611        elif lift_mode == 'simple': 
     612            return clist(self.value, self.absprec, True, self.prime_pow) 
     613        elif lift_mode == 'smallest': 
     614            return clist(self.value, self.absprec, False, self.prime_pow) 
     615        else: 
     616            raise ValueError, "unknown lift_mode" 
     617 
     618    def teichmuller_list(self): 
     619        r""" 
     620        Returns a list `[a_0, a_1,\ldots, a_n]` such that 
     621 
     622        - `a_i^p = a_i` 
     623 
     624        - ``self`` equals `\sum_{i = 0}^n a_i p^i` 
     625 
     626        - if `a_i \ne 0`, the absolute precision of `a_i` is 
     627          ``self.precision_relative() - i`` 
     628 
     629        EXAMPLES:: 
     630 
     631            sage: R = ZpCA(5,5); R(14).list('teichmuller') #indirect doctest 
     632            [4 + 4*5 + 4*5^2 + 4*5^3 + 4*5^4 + O(5^5), 
     633            3 + 3*5 + 2*5^2 + 3*5^3 + O(5^4), 
     634            2 + 5 + 2*5^2 + O(5^3), 
     635            1 + O(5^2), 
     636            4 + O(5)] 
     637        """ 
     638        ans = PyList_New(0) 
     639        if ciszero(self.value, self.prime_pow): 
     640            return ans 
     641        cdef long curpower = self.absprec 
     642        cdef CAElement list_elt 
     643        cdef CAElement tmp = self._new_c() 
     644        ccopy(tmp.value, self.value, self.prime_pow) 
     645        while not ciszero(tmp.value, tmp.prime_pow) and curpower > 0: 
     646            list_elt = self._new_c() 
     647            cteichmuller(list_elt.value, tmp.value, curpower, self.prime_pow) 
     648            if ciszero(list_elt.value, self.prime_pow): 
     649                cshift0(tmp.value, tmp.value, -1, curpower-1, self.prime_pow) 
     650            else: 
     651                csub(tmp.value, tmp.value, list_elt.value, curpower, self.prime_pow) 
     652                cshift0(tmp.value, tmp.value, -1, curpower-1, self.prime_pow) 
     653                creduce(tmp.value, tmp.value, curpower-1, self.prime_pow) 
     654            list_elt.absprec = curpower 
     655            curpower -= 1 
     656            PyList_Append(ans, list_elt) 
     657        return ans 
     658 
     659    def _teichmuller_set(self): 
     660        """ 
     661        Sets ``self`` to be the Teichmuller representative with the 
     662        same residue as ``self``. 
     663 
     664        WARNING: 
     665 
     666        This function modifies ``self``, which is not safe.  Elements 
     667        are supposed to be immutable. 
     668 
     669        EXAMPLES:: 
     670 
     671            sage: R = ZpCA(17,5); a = R(11) 
     672            sage: a 
     673            11 + O(17^5) 
     674            sage: a._teichmuller_set(); a 
     675            11 + 14*17 + 2*17^2 + 12*17^3 + 15*17^4 + O(17^5) 
     676            sage: a.list('teichmuller') 
     677            [11 + 14*17 + 2*17^2 + 12*17^3 + 15*17^4 + O(17^5)] 
     678        """ 
     679        if self.valuation_c() > 0: 
     680            csetzero(self.value, self.prime_pow) 
     681            self.absprec = self.prime_pow.prec_cap 
     682        elif self.absprec == 0: 
     683            raise ValueError("not enough precision") 
     684        else: 
     685            cteichmuller(self.value, self.value, self.absprec, self.prime_pow) 
     686 
     687    def precision_absolute(self): 
     688        """ 
     689        Returns the absolute precision of ``self``. 
     690 
     691        This is the power of the maximal ideal modulo which this 
     692        element is defined. 
     693         
     694        INPUT: 
     695         
     696        - ``self`` -- a `p`-adic element 
     697             
     698        OUTPUT: 
     699         
     700        - ``integer`` -- the absolute precision of ``self`` 
     701             
     702        EXAMPLES:: 
     703         
     704            sage: R = Zp(7,4,'capped-abs'); a = R(7); a.precision_absolute() 
     705            4 
     706       """ 
     707        cdef Integer ans = PY_NEW(Integer) 
     708        mpz_set_si(ans.value, self.absprec) 
     709        return ans 
     710 
     711    def precision_relative(self): 
     712        """ 
     713        Returns the relative precision of ``self``. 
     714 
     715        This is the power of the maximal ideal modulo which the unit 
     716        part of ``self`` is defined. 
     717         
     718        INPUT: 
     719         
     720        - ``self`` -- a `p`-adic element 
     721             
     722        OUTPUT: 
     723         
     724        - ``integer`` -- the relative precision of ``self`` 
     725 
     726        EXAMPLES:: 
     727         
     728            sage: R = Zp(7,4,'capped-abs'); a = R(7); a.precision_relative() 
     729            3 
     730       """ 
     731        cdef Integer ans = PY_NEW(Integer) 
     732        mpz_set_si(ans.value, self.absprec - self.valuation_c()) 
     733        return ans 
     734 
     735    cpdef pAdicTemplateElement unit_part(CAElement self): 
     736        r""" 
     737        Returns the unit part of ``self``. 
     738 
     739        INPUT: 
     740         
     741        - ``self`` -- a `p`-adic element 
     742             
     743        OUTPUT: 
     744         
     745        - `p`-adic element -- the unit part of ``self`` 
     746             
     747        EXAMPLES:: 
     748         
     749            sage: R = Zp(17,4,'capped-abs', 'val-unit') 
     750            sage: a = R(18*17) 
     751            sage: a.unit_part() 
     752            18 + O(17^3) 
     753            sage: type(a) 
     754            <type 'sage.rings.padics.padic_capped_absolute_element.pAdicCappedAbsoluteElement'> 
     755        """ 
     756        cdef CAElement ans = (<CAElement>self)._new_c() 
     757        cdef long val = cremove(ans.value, (<CAElement>self).value, (<CAElement>self).absprec, (<CAElement>self).prime_pow) 
     758        ans.absprec = (<CAElement>self).absprec - val 
     759        return ans 
     760 
     761    cdef long valuation_c(self): 
     762        """ 
     763        Returns the valuation of this element. 
     764 
     765        TESTS:: 
     766         
     767            sage: R = ZpCA(5) 
     768            sage: R(5^5*1827).valuation() 
     769            5 
     770            sage: R(1).valuation() 
     771            0 
     772            sage: R(2).valuation() 
     773            0 
     774            sage: R(5).valuation() 
     775            1 
     776            sage: R(10).valuation() 
     777            1 
     778            sage: R(25).valuation() 
     779            2 
     780            sage: R(50).valuation() 
     781            2             
     782            sage: R(0).valuation() 
     783            20 
     784            sage: R(0,6).valuation() 
     785            6 
     786        """ 
     787        # for backward compatibility 
     788        return cvaluation(self.value, self.absprec, self.prime_pow) 
     789 
     790    cpdef val_unit(self): 
     791        """ 
     792        Returns a 2-tuple, the first element set to the valuation of 
     793        ``self``, and the second to the unit part of ``self``. 
     794 
     795        If ``self = 0``, then the unit part is ``O(p^0)``. 
     796 
     797        EXAMPLES:: 
     798         
     799            sage: R = ZpCA(5) 
     800            sage: a = R(75, 6); b = a - a 
     801            sage: a.val_unit() 
     802            (2, 3 + O(5^4)) 
     803            sage: b.val_unit() 
     804            (6, O(5^0)) 
     805        """ 
     806        cdef CAElement unit = self._new_c() 
     807        cdef Integer valuation = PY_NEW(Integer) 
     808        cdef long val = cremove(unit.value, self.value, self.absprec, self.prime_pow) 
     809        mpz_set_si(valuation.value, val) 
     810        unit.absprec = self.absprec - val 
     811        return valuation, unit 
     812 
     813    def __hash__(self): 
     814        """ 
     815        Hashing. 
     816         
     817        EXAMPLES:: 
     818         
     819            sage: R = ZpCA(11, 5) 
     820            sage: hash(R(3)) == hash(3) 
     821            True 
     822        """ 
     823        return chash(self.value, 0, self.absprec, self.prime_pow) 
     824 
     825cdef class pAdicCoercion_ZZ_CA(RingHomomorphism_coercion): 
     826    """ 
     827    The canonical inclusion from ZZ to a capped absolute ring. 
     828 
     829    EXAMPLES:: 
     830 
     831        sage: f = ZpCA(5).coerce_map_from(ZZ); f 
     832        Ring Coercion morphism: 
     833          From: Integer Ring 
     834          To:   5-adic Ring with capped absolute precision 20 
     835    """ 
     836    def __init__(self, R): 
     837        """ 
     838        Initialization. 
     839 
     840        EXAMPLES:: 
     841 
     842            sage: f = ZpCA(5).coerce_map_from(ZZ); type(f) 
     843            <type 'sage.rings.padics.padic_capped_absolute_element.pAdicCoercion_ZZ_CA'> 
     844        """ 
     845        RingHomomorphism_coercion.__init__(self, ZZ.Hom(R), check=False) 
     846        self._zero = R._element_constructor(R, 0) 
     847        self._section = pAdicConvert_CA_ZZ(R) 
     848 
     849    cpdef Element _call_(self, x): 
     850        """ 
     851        Evaluation. 
     852 
     853        EXAMPLES:: 
     854 
     855            sage: f = ZpCA(5).coerce_map_from(ZZ) 
     856            sage: f(0).parent() 
     857            5-adic Ring with capped absolute precision 20 
     858            sage: f(5) 
     859            5 + O(5^20) 
     860        """ 
     861        if mpz_sgn((<Integer>x).value) == 0: 
     862            return self._zero 
     863        cdef CAElement ans = self._zero._new_c() 
     864        ans.absprec = ans.prime_pow.prec_cap 
     865        cconv_mpzt(ans.value, (<Integer>x).value, ans.absprec, True, ans.prime_pow) 
     866        return ans 
     867 
     868    cpdef Element _call_with_args(self, x, args=(), kwds={}): 
     869        """ 
     870        This function is used when some precision cap is passed in (relative or absolute or both). 
     871 
     872        See the documentation for pAdicCappedAbsoluteElement.__init__ for more details. 
     873 
     874        EXAMPLES:: 
     875 
     876            sage: R = ZpCA(5,4) 
     877            sage: type(R(10,2)) 
     878            <type 'sage.rings.padics.padic_capped_absolute_element.pAdicCappedAbsoluteElement'> 
     879            sage: R(10,2) 
     880            2*5 + O(5^2) 
     881            sage: R(10,3,1) 
     882            2*5 + O(5^2) 
     883            sage: R(10,absprec=2) 
     884            2*5 + O(5^2) 
     885            sage: R(10,relprec=2) 
     886            2*5 + O(5^3) 
     887            sage: R(10,absprec=1) 
     888            O(5) 
     889            sage: R(10,empty=True) 
     890            O(5^0) 
     891        """ 
     892        cdef long val, aprec, rprec 
     893        cdef CAElement ans 
     894        _process_args_and_kwds(&aprec, &rprec, args, kwds, True, self._zero.prime_pow) 
     895        if mpz_sgn((<Integer>x).value) == 0: 
     896            if aprec >= self._zero.prime_pow.prec_cap: 
     897                return self._zero 
     898            ans = self._zero._new_c() 
     899            csetzero(ans.value, ans.prime_pow) 
     900            ans.absprec = aprec 
     901        else: 
     902            val = get_ordp(x, self._zero.prime_pow) 
     903            ans = self._zero._new_c() 
     904            if aprec <= val: 
     905                csetzero(ans.value, ans.prime_pow) 
     906                ans.absprec = aprec 
     907            else: 
     908                ans.absprec = min(aprec, val + rprec) 
     909                cconv_mpzt(ans.value, (<Integer>x).value, ans.absprec, True, self._zero.prime_pow) 
     910        return ans 
     911 
     912    def section(self): 
     913        """ 
     914        Returns a map back to ZZ that approximates an element of Zp by an integer. 
     915 
     916        EXAMPLES:: 
     917 
     918            sage: f = ZpCA(5).coerce_map_from(ZZ).section() 
     919            sage: f(ZpCA(5)(-1)) - 5^20 
     920            -1 
     921        """ 
     922        return self._section 
     923 
     924cdef class pAdicConvert_CA_ZZ(RingMap): 
     925    """ 
     926    The map from a capped absolute ring back to ZZ that returns the the smallest non-negative integer 
     927    approximation to its input which is accurate up to the precision. 
     928 
     929    If the input is not in the closure of the image of ZZ, raises a ValueError. 
     930 
     931    EXAMPLES:: 
     932 
     933        sage: f = ZpCA(5).coerce_map_from(ZZ).section(); f 
     934        Set-theoretic ring morphism: 
     935          From: 5-adic Ring with capped absolute precision 20 
     936          To:   Integer Ring 
     937    """ 
     938    def __init__(self, R): 
     939        """ 
     940        Initialization. 
     941 
     942        EXAMPLES:: 
     943 
     944            sage: f = ZpCA(5).coerce_map_from(ZZ).section(); type(f) 
     945            <type 'sage.rings.padics.padic_capped_absolute_element.pAdicConvert_CA_ZZ'> 
     946            sage: f.category() 
     947            Category of hom sets in Category of sets 
     948        """ 
     949        if R.degree() > 1 or R.characteristic() != 0 or R.residue_characteristic() == 0: 
     950            RingMap.__init__(self, Hom(R, ZZ, SetsWithPartialMaps())) 
     951        else: 
     952            RingMap.__init__(self, Hom(R, ZZ, Sets())) 
     953 
     954    cpdef Element _call_(self, _x): 
     955        """ 
     956        Evaluation. 
     957 
     958        EXAMPLES:: 
     959 
     960            sage: f = ZpCA(5).coerce_map_from(ZZ).section() 
     961            sage: f(ZpCA(5)(-1)) - 5^20 
     962            -1 
     963            sage: f(ZpCA(5)(0)) 
     964            0 
     965        """ 
     966        cdef Integer ans = PY_NEW(Integer) 
     967        cdef CAElement x = <CAElement>_x 
     968        cconv_mpzt_out(ans.value, x.value, 0, x.absprec, x.prime_pow) 
     969        return ans 
     970 
     971cdef class pAdicConvert_QQ_CA(Morphism): 
     972    """ 
     973    The inclusion map from QQ to a capped absolute ring that is defined 
     974    on all elements with non-negative p-adic valuation. 
     975 
     976    EXAMPLES:: 
     977     
     978        sage: f = ZpCA(5).convert_map_from(QQ); f 
     979        Generic morphism: 
     980          From: Rational Field 
     981          To:   5-adic Ring with capped absolute precision 20 
     982    """ 
     983    def __init__(self, R): 
     984        """ 
     985        Initialization. 
     986 
     987        EXAMPLES:: 
     988 
     989            sage: f = ZpCA(5).convert_map_from(QQ); type(f) 
     990            <type 'sage.rings.padics.padic_capped_absolute_element.pAdicConvert_QQ_CA'> 
     991        """ 
     992        Morphism.__init__(self, Hom(QQ, R, SetsWithPartialMaps())) 
     993        self._zero = R._element_constructor(R, 0) 
     994 
     995    cpdef Element _call_(self, x): 
     996        """ 
     997        Evaluation. 
     998 
     999        EXAMPLES:: 
     1000 
     1001            sage: f = ZpCA(5,4).convert_map_from(QQ) 
     1002            sage: f(1/7) 
     1003            3 + 3*5 + 2*5^3 + O(5^4) 
     1004            sage: f(0) 
     1005            O(5^4) 
     1006        """ 
     1007        if mpq_sgn((<Rational>x).value) == 0: 
     1008            return self._zero 
     1009        cdef CAElement ans = self._zero._new_c() 
     1010        cconv_mpqt(ans.value, (<Rational>x).value, ans.prime_pow.prec_cap, True, ans.prime_pow) 
     1011        ans.absprec = ans.prime_pow.prec_cap 
     1012        return ans 
     1013 
     1014    cpdef Element _call_with_args(self, x, args=(), kwds={}): 
     1015        """ 
     1016        This function is used when some precision cap is passed in (relative or absolute or both). 
     1017 
     1018        See the documentation for pAdicCappedAbsoluteElement.__init__ for more details. 
     1019 
     1020        EXAMPLES:: 
     1021 
     1022            sage: R = ZpCA(5,4) 
     1023            sage: type(R(10/3,2)) 
     1024            <type 'sage.rings.padics.padic_capped_absolute_element.pAdicCappedAbsoluteElement'> 
     1025            sage: R(10/3,2) 
     1026            4*5 + O(5^2) 
     1027            sage: R(10/3,3,1) 
     1028            4*5 + O(5^2) 
     1029            sage: R(10/3,absprec=2) 
     1030            4*5 + O(5^2) 
     1031            sage: R(10/3,relprec=2) 
     1032            4*5 + 5^2 + O(5^3) 
     1033            sage: R(10/3,absprec=1) 
     1034            O(5) 
     1035            sage: R(10/3,empty=True) 
     1036            O(5^0) 
     1037            sage: R(3/100,relprec=3) 
     1038            Traceback (most recent call last): 
     1039            ... 
     1040            ValueError: p divides denominator 
     1041        """ 
     1042        cdef long val, aprec, rprec 
     1043        cdef CAElement ans 
     1044        _process_args_and_kwds(&aprec, &rprec, args, kwds, True, self._zero.prime_pow) 
     1045        if mpq_sgn((<Rational>x).value) == 0: 
     1046            if aprec >= self._zero.prime_pow.prec_cap: 
     1047                return self._zero 
     1048            ans = self._zero._new_c() 
     1049            csetzero(ans.value, ans.prime_pow) 
     1050            ans.absprec = aprec 
     1051        else: 
     1052            val = get_ordp(x, self._zero.prime_pow) 
     1053            ans = self._zero._new_c() 
     1054            if aprec <= val: 
     1055                csetzero(ans.value, ans.prime_pow) 
     1056                ans.absprec = aprec 
     1057            else: 
     1058                ans.absprec = min(aprec, val + rprec) 
     1059                cconv_mpqt(ans.value, (<Rational>x).value, ans.absprec, True, self._zero.prime_pow) 
     1060        return ans 
     1061 
     1062def unpickle_cae_v2(cls, parent, value, absprec): 
     1063    cdef CAElement ans = PY_NEW(cls) 
     1064    ans._parent = parent 
     1065    ans.prime_pow = <PowComputer_class?>parent.prime_pow 
     1066    cconstruct(ans.value, ans.prime_pow) 
     1067    cunpickle(ans.value, value, ans.prime_pow) 
     1068    ans.absprec = absprec 
     1069    return ans 
  • new file sage/rings/padics/CA_template_header.pxi

    diff --git a/sage/rings/padics/CA_template_header.pxi b/sage/rings/padics/CA_template_header.pxi
    new file mode 100644
    - +  
     1 
     2 
     3include "padic_template_element_header.pxi" 
     4 
     5from sage.categories.morphism cimport Morphism 
     6from sage.rings.morphism cimport RingHomomorphism_coercion, RingMap 
     7 
     8cdef class CAElement(pAdicTemplateElement): 
     9    cdef celement value 
     10    cdef long absprec 
     11 
     12    cdef CAElement _new_c(self) 
     13 
     14cdef class pAdicCoercion_ZZ_CA(RingHomomorphism_coercion): 
     15    cdef CAElement _zero 
     16    cdef RingMap _section 
     17cdef class pAdicConvert_CA_ZZ(RingMap): 
     18    pass 
     19cdef class pAdicConvert_QQ_CA(Morphism): 
     20    cdef CAElement _zero 
     21    cdef RingMap _section 
     22# There should also be a pAdicConvert_CA_QQ for extension rings.... 
  • sage/rings/padics/padic_capped_absolute_element.pxd

    diff --git a/sage/rings/padics/padic_capped_absolute_element.pxd b/sage/rings/padics/padic_capped_absolute_element.pxd
    a b  
    11include "../../ext/cdefs.pxi" 
    22 
    3 from sage.rings.padics.padic_base_generic_element cimport pAdicBaseGenericElement 
    4 from sage.structure.element cimport CommutativeRingElement, RingElement, ModuleElement, Element 
    5 from sage.rings.padics.pow_computer cimport PowComputer_class 
    6 from sage.rings.integer cimport Integer 
    7 from sage.rings.rational cimport Rational 
     3ctypedef mpz_t celement 
     4from sage.libs.pari.gen cimport gen as pari_gen 
    85 
    9 cdef class pAdicCappedAbsoluteElement(pAdicBaseGenericElement): 
    10     cdef mpz_t value 
    11     cdef unsigned long absprec 
     6include "CA_template_header.pxi" 
    127 
    13     cdef pAdicCappedAbsoluteElement _new_c(self) 
    14     cpdef RingElement _invert_c_impl(self) 
    15     cpdef ModuleElement _neg_(self) 
    16     cdef pAdicCappedAbsoluteElement _lshift_c(pAdicCappedAbsoluteElement self, long shift) 
    17     cdef pAdicCappedAbsoluteElement _rshift_c(pAdicCappedAbsoluteElement self, long shift) 
    18     cdef object teichmuller_list(pAdicCappedAbsoluteElement self) 
    19     cpdef pAdicCappedAbsoluteElement unit_part(self) 
    20     cpdef Integer lift(self) 
     8cdef class pAdicCappedAbsoluteElement(CAElement): 
     9    cdef lift_c(self) 
     10    cdef pari_gen _to_gen(self) 
  • sage/rings/padics/padic_capped_absolute_element.pyx

    diff --git a/sage/rings/padics/padic_capped_absolute_element.pyx b/sage/rings/padics/padic_capped_absolute_element.pyx
    a b  
    11""" 
    2 `p`-Adic Capped Absolute Element 
     2`p`-Adic Capped Absolute Elements 
    33 
    44Elements of `p`-Adic Rings with Absolute Precision Cap 
    55 
     
    1111""" 
    1212 
    1313#***************************************************************************** 
    14 #       Copyright (C) 2007 David Roe <roed@math.harvard.edu> 
    15 #                          William Stein <wstein@gmail.com> 
     14#       Copyright (C) 2007-2012 David Roe <roed.math@gmail.com> 
     15#                               William Stein <wstein@gmail.com> 
    1616# 
    1717#  Distributed under the terms of the GNU General Public License (GPL) 
    1818# 
    1919#                  http://www.gnu.org/licenses/ 
    2020#***************************************************************************** 
    2121 
    22 include "../../libs/ntl/decl.pxi" 
    23 include "../../ext/gmp.pxi" 
    24 include "../../ext/interrupt.pxi" 
    25 include "../../ext/stdsage.pxi" 
     22include "../../libs/linkages/padics/mpz.pxi" 
     23include "CA_template.pxi" 
    2624 
    27 cimport sage.rings.padics.padic_generic_element 
     25from sage.libs.pari.gen cimport PariInstance 
     26cdef PariInstance P = sage.libs.pari.all.pari 
     27from sage.rings.finite_rings.integer_mod import Mod 
    2828 
    29 cimport sage.rings.rational 
    30 cimport sage.rings.padics.pow_computer 
    31 from sage.rings.padics.pow_computer cimport PowComputer_base 
    32 from sage.rings.padics.padic_printing cimport pAdicPrinter_class 
    33 from sage.rings.padics.padic_generic_element cimport pAdicGenericElement 
    34  
    35 import sage.rings.padics.padic_generic_element 
    36 import sage.rings.finite_rings.integer_mod 
    37 import sage.libs.pari.gen 
    38 import sage.rings.integer 
    39 import sage.rings.rational 
    40  
    41 from sage.rings.infinity import infinity 
    42 from sage.rings.finite_rings.integer_mod import Mod 
    43 from sage.rings.padics.precision_error import PrecisionError 
    44  
    45 pari = sage.libs.pari.gen.pari 
    46 pari_gen = sage.libs.pari.gen.gen 
    47 PariError = sage.libs.pari.gen.PariError 
    48  
    49 cdef class pAdicCappedAbsoluteElement(pAdicBaseGenericElement): 
    50     def __init__(pAdicCappedAbsoluteElement self, parent, x, absprec=infinity, relprec = infinity, empty=False): 
    51         """ 
    52         EXAMPLES:: 
     29cdef class pAdicCappedAbsoluteElement(CAElement): 
     30    """ 
     31    EXAMPLES:: 
    5332         
    54             sage: R = ZpCA(3, 5) 
    55             sage: R(2) 
    56             2 + O(3^5) 
    57             sage: R(2, absprec=2) 
    58             2 + O(3^2) 
    59             sage: R(3, relprec=2) 
    60             3 + O(3^3) 
    61             sage: R(Qp(3)(10)) 
    62             1 + 3^2 + O(3^5) 
    63             sage: R(pari(6)) 
    64             2*3 + O(3^5) 
    65             sage: R(pari(1/2)) 
    66             2 + 3 + 3^2 + 3^3 + 3^4 + O(3^5) 
    67             sage: R(1/2) 
    68             2 + 3 + 3^2 + 3^3 + 3^4 + O(3^5) 
    69             sage: R(mod(-1, 3^7)) 
    70             2 + 2*3 + 2*3^2 + 2*3^3 + 2*3^4 + O(3^5) 
    71             sage: R(mod(-1, 3^2)) 
    72             2 + 2*3 + O(3^2) 
    73             sage: R(3 + O(3^2)) 
    74             3 + O(3^2) 
    75         """ 
    76         mpz_init(self.value) 
    77         pAdicBaseGenericElement.__init__(self,parent) 
    78         if empty: 
    79             return 
    80         if absprec is infinity or absprec > parent.precision_cap(): 
    81             absprec = parent.precision_cap() 
    82         elif not PY_TYPE_CHECK(absprec, Integer): 
    83             absprec = Integer(absprec) 
    84         if relprec is not infinity and not PY_TYPE_CHECK(relprec, Integer): 
    85             relprec = Integer(relprec) 
    86         if PY_TYPE_CHECK(x, pAdicGenericElement): 
    87             if x.valuation() < 0: 
    88                 raise ValueError, "element valuation cannot be negative." 
    89             if parent.prime() != x.parent().prime(): 
    90                 raise TypeError, "Cannot coerce between p-adic parents with different primes" 
    91         #if isinstance(x, pAdicLazyElement): 
    92         #    # We may be doing unnecessary precision increases here... 
    93         #    if relprec is infinity: 
    94         #        try: 
    95         #            x.set_precision_absolute(absprec) 
    96         #        except PrecisionError: 
    97         #            pass 
    98         #    else: 
    99         #        try: 
    100         #            x.set_precision_relative(relprec) 
    101         #        except PrecisionError: 
    102         #            try: 
    103         #                x.set_precision_absolute(absprec) 
    104         #            except PrecisionError: 
    105         #                pass 
    106         cdef mpz_t modulus 
    107         cdef Integer tmp 
    108         cdef unsigned long k 
    109         if PY_TYPE_CHECK(x, pAdicBaseGenericElement): 
    110             self._set_from_Integer(x._integer_(), min(absprec, x.precision_absolute()), relprec) 
    111             return 
    112         elif isinstance(x, (int, long)): 
    113             x = Integer(x) 
    114         elif isinstance(x, pari_gen): 
    115             if x.type() == "t_PADIC": 
    116                 if x.variable() != self.prime_pow.prime: 
    117                     raise TypeError, "Cannot coerce a pari p-adic with the wrong prime." 
    118                 absprec = min(Integer(x.padicprec(parent.prime())), absprec) 
    119                 x = x.lift() 
    120             if x.type() == "t_INT": 
    121                 x = Integer(x) 
    122             elif x.type() == "t_FRAC": 
    123                 x = Rational(x) 
    124             else: 
    125                 raise TypeError, "unsupported coercion from pari: only p-adics, integers and rationals allowed" 
    126          
    127         elif sage.rings.finite_rings.integer_mod.is_IntegerMod(x): 
    128             mpz_init_set(modulus, (<Integer>x.modulus()).value) 
    129             k = mpz_remove(modulus, modulus, self.prime_pow.prime.value) 
    130             if mpz_cmp_ui(modulus, 1) == 0: 
    131                 if mpz_cmp_ui((<Integer>absprec).value, k) > 0: 
    132                     absprec = PY_NEW(Integer) 
    133                     mpz_set_ui((<Integer>absprec).value, k) 
    134                 x = x.lift() 
    135                 mpz_clear(modulus) 
    136             else: 
    137                 mpz_clear(modulus) 
    138                 raise TypeError, "cannot coerce from the given integer mod ring (not a power of the same prime)" 
    139         if PY_TYPE_CHECK(x, Integer): 
    140             self._set_from_Integer(x, absprec, relprec) 
    141             return 
    142         if PY_TYPE_CHECK(x, Rational): 
    143             self._set_from_Rational(x, absprec, relprec) 
    144             return 
    145         self._set_from_Rational(Rational(x), absprec, relprec) 
    146          
    147     def __dealloc__(self): 
    148         """ 
    149         Deallocation. 
    150  
    151         TESTS:: 
    152  
    153             sage: R = ZpCA(5) 
    154             sage: a = R(17) 
    155             sage: del(a) 
    156         """ 
    157         mpz_clear(self.value) 
    158          
    159     def __reduce__(self): 
    160         """ 
    161         Pickling. 
    162  
    163         TESTS:: 
    164          
    165             sage: a = ZpCA(5)(-3) 
    166             sage: type(a) 
    167             <type 'sage.rings.padics.padic_capped_absolute_element.pAdicCappedAbsoluteElement'> 
    168             sage: loads(dumps(a)) == a 
    169             True 
    170         """ 
    171         return make_pAdicCappedAbsoluteElement, (self.parent(), self.lift(), self.absprec) 
    172  
    173     cdef bint _set_prec_abs(self, long absprec) except -1: 
    174         """ 
    175         Sets ``self.absprec``. 
    176  
    177         TESTS:: 
    178  
    179             sage: R = ZpCA(5) 
    180             sage: a = R(17,5); a #indirect doctest 
    181             2 + 3*5 + O(5^5) 
    182         """ 
    183         self.absprec = absprec 
    184  
    185     cdef bint _set_prec_both(self, long absprec, long relprec) except -1: 
    186         """ 
    187         Sets ``self.absprec``. 
    188  
    189         TESTS:: 
    190  
    191             sage: R = ZpCA(5) 
    192             sage: a = R(75, absprec = 5, relprec = 4); a #indirect doctest 
    193             3*5^2 + O(5^5) 
    194         """ 
    195         self.absprec = absprec 
    196         cdef long ordp 
    197         if relprec < absprec: 
    198             ordp = self.valuation_c() 
    199             if ordp + relprec < absprec: 
    200                 self.absprec = ordp + relprec 
    201  
    202     cdef int _set_from_Integer(pAdicCappedAbsoluteElement self, Integer x, absprec, relprec) except -1: 
    203         """ 
    204         Set ``self.value`` and ``self.absprec``. 
    205          
    206         ``absprec`` must be positive. 
    207  
    208         TESTS:: 
    209  
    210             sage: R = ZpCA(5) 
    211             sage: a = R(75, absprec = 5, relprec = 4); a #indirect doctest 
    212             3*5^2 + O(5^5)         
    213         """ 
    214         if relprec is not infinity and mpz_sgn((<Integer>relprec).value) == -1: 
    215             raise ValueError, "relprec must be positive" 
    216         if absprec is not infinity and mpz_sgn((<Integer>absprec).value) == -1: 
    217             raise ValueError, "absprec must be positive" 
    218         if relprec is infinity or mpz_fits_ulong_p((<Integer>relprec).value) == 0: 
    219             if absprec is infinity or mpz_cmp_ui((<Integer>absprec).value, self.prime_pow.prec_cap) >= 0: 
    220                 return self._set_from_mpz_abs(x.value, self.prime_pow.prec_cap) 
    221             else: 
    222                 return self._set_from_mpz_abs(x.value, mpz_get_si((<Integer>absprec).value)) 
    223         else: 
    224             if absprec is infinity or mpz_cmp_ui((<Integer>absprec).value, self.prime_pow.prec_cap) >= 0: 
    225                 return self._set_from_mpz_both(x.value, self.prime_pow.prec_cap, mpz_get_si((<Integer>relprec).value)) 
    226             else: 
    227                 return self._set_from_mpz_both(x.value, mpz_get_si((<Integer>absprec).value), mpz_get_si((<Integer>relprec).value)) 
    228  
    229     cdef int _set_from_Rational(pAdicCappedAbsoluteElement self, Rational x, absprec, relprec) except -1: 
    230         """ 
    231         Set ``self.value`` and ``self.absprec``. 
    232         ``absprec`` must be positive. 
    233  
    234         TESTS:: 
    235  
    236             sage: R = ZpCA(5) 
    237             sage: a = R(25/9, absprec = 5, relprec = 4); a #indirect doctest 
    238             4*5^2 + 2*5^3 + O(5^5) 
    239         """ 
    240         if relprec is not infinity and mpz_sgn((<Integer>relprec).value) == -1: 
    241             raise ValueError, "relprec must be positive" 
    242         if absprec is not infinity and mpz_sgn((<Integer>absprec).value) == -1: 
    243             raise ValueError, "absprec must be positive" 
    244         if relprec is infinity or mpz_fits_ulong_p((<Integer>relprec).value) == 0: 
    245             if absprec is infinity or mpz_cmp_ui((<Integer>absprec).value, self.prime_pow.prec_cap) >= 0: 
    246                 return self._set_from_mpq_abs(x.value, self.prime_pow.prec_cap) 
    247             else: 
    248                 return self._set_from_mpq_abs(x.value, mpz_get_si((<Integer>absprec).value)) 
    249         else: 
    250             if absprec is infinity or mpz_cmp_ui((<Integer>absprec).value, self.prime_pow.prec_cap) >= 0: 
    251                 return self._set_from_mpq_both(x.value, self.prime_pow.prec_cap, mpz_get_si((<Integer>relprec).value)) 
    252             else: 
    253                 return self._set_from_mpq_both(x.value, mpz_get_si((<Integer>absprec).value), mpz_get_si((<Integer>relprec).value)) 
    254  
    255     cdef int _set_from_mpz_abs(self, mpz_t x, long absprec) except -1: 
    256         """ 
    257         ``self.prime_pow`` must already be set. 
    258  
    259         TESTS:: 
    260  
    261             sage: R = ZpCA(5) 
    262             sage: a = R(17,5); a #indirect doctest 
    263             2 + 3*5 + O(5^5) 
    264         """ 
    265         self._set_prec_abs(absprec) 
    266         if mpz_sgn(x) == -1 or mpz_cmp(x, self.prime_pow.pow_mpz_t_tmp(self.absprec)[0]) >= 0: 
    267             sig_on() 
    268             mpz_mod(self.value, x, self.prime_pow.pow_mpz_t_tmp(self.absprec)[0]) 
    269             sig_off() 
    270         else: 
    271             mpz_set(self.value, x) 
    272         return 0 
    273  
    274     cdef int _set_from_mpz_both(self, mpz_t x, long absprec, long relprec) except -1: 
    275         """ 
    276         ``self.prime_pow`` must already be set 
    277  
    278         TESTS:: 
    279  
    280             sage: R = ZpCA(5) 
    281             sage: a = R(75, absprec = 5, relprec = 4); a #indirect doctest 
    282             3*5^2 + O(5^5)         
    283         """ 
    284         if mpz_sgn(x) == 0: 
    285             mpz_set(self.value, x) 
    286             return 0 
    287         mpz_set(self.value, x) 
    288         self._set_prec_both(absprec, relprec) 
    289         if mpz_sgn(x) == -1 or mpz_cmp(x, self.prime_pow.pow_mpz_t_tmp(self.absprec)[0]) >= 0: 
    290             sig_on() 
    291             mpz_mod(self.value, x, self.prime_pow.pow_mpz_t_tmp(self.absprec)[0]) 
    292             sig_off() 
    293         return 0 
    294  
    295     cdef int _set_from_mpq_abs(self, mpq_t x, long absprec) except -1: 
    296         """ 
    297         ``self.prime_pow`` must already be set. 
    298  
    299         TESTS:: 
    300  
    301             sage: R = ZpCA(5) 
    302             sage: a = R(25/9, absprec = 5); a #indirect doctest 
    303             4*5^2 + 2*5^3 + O(5^5) 
    304         """ 
    305         self._set_prec_abs(absprec) 
    306         if mpz_divisible_p(mpq_denref(x), self.prime_pow.prime.value): 
    307             raise ValueError, "p divides denominator" 
    308         sig_on() 
    309         mpz_invert(self.value, mpq_denref(x), self.prime_pow.pow_mpz_t_tmp(absprec)[0]) 
    310         mpz_mul(self.value, self.value, mpq_numref(x)) 
    311         mpz_mod(self.value, self.value, self.prime_pow.pow_mpz_t_tmp(absprec)[0]) 
    312         sig_off() 
    313         return 0 
    314  
    315     cdef int _set_from_mpq_both(self, mpq_t x, long absprec, long relprec) except -1: 
    316         """ 
    317         ``self.prime_pow`` must already be set 
    318  
    319         TESTS:: 
    320  
    321             sage: R = ZpCA(5) 
    322             sage: a = R(25/9, absprec = 5, relprec = 4); a #indirect doctest 
    323             4*5^2 + 2*5^3 + O(5^5) 
    324         """ 
    325         cdef long k 
    326         cdef mpz_t tmp 
    327         if mpq_sgn(x) == 0: 
    328             mpz_set_ui(self.value, 0) 
    329             return 0 
    330         mpz_init(tmp) 
    331         sig_on() 
    332         k = mpz_remove(tmp, mpq_numref(x), self.prime_pow.prime.value) 
    333         sig_off() 
    334         mpz_clear(tmp) 
    335         self.absprec = k + relprec 
    336         if self.absprec > absprec: 
    337             self.absprec = absprec 
    338         return self._set_from_mpq_abs(x, self.absprec) 
    339  
    340     cdef int _set_mpz_into(pAdicCappedAbsoluteElement self, mpz_t dest) except -1: 
    341         """ 
    342         Sets ``dest`` to a lift of ``self``. 
    343  
    344         TESTS:: 
    345  
    346             sage: R = ZpCA(5); S.<a> = ZqCA(25) 
    347             sage: S(R(17)) 
    348             2 + 3*5 + O(5^20) 
    349         """ 
    350         mpz_set(dest, self.value) 
    351         return 0 
    352  
    353     cdef int _set_mpq_into(pAdicCappedAbsoluteElement self, mpq_t dest) except -1: 
    354         """ 
    355         Sets ``dest`` to a lift of ``self``. 
    356  
    357         Not currently used internally. 
    358         """ 
    359         mpq_set_z(dest, self.value) 
    360         return 0 
    361          
    362     cdef pAdicCappedAbsoluteElement _new_c(self): 
    363         """ 
    364         Creates a new element with the same basic info. 
    365  
    366         TESTS:: 
    367  
    368             sage: R = ZpCA(5); R(6,5) * R(7,8) #indirect doctest 
    369             2 + 3*5 + 5^2 + O(5^5) 
    370         """ 
    371         cdef pAdicCappedAbsoluteElement x 
    372         x = PY_NEW(pAdicCappedAbsoluteElement) 
    373         x._parent = self._parent 
    374         x.prime_pow = self.prime_pow 
    375         mpz_init(x.value) 
    376         return x 
    377  
    378     cpdef bint _is_inexact_zero(self) except -1: 
    379         """ 
    380         Returns ``True`` if ``self`` is indistinguishable from zero. 
    381          
    382         EXAMPLES:: 
    383          
    384             sage: R = ZpCA(7, 5) 
    385             sage: R(7^5)._is_inexact_zero() 
    386             True 
    387             sage: R(0,4)._is_inexact_zero() 
    388             True 
    389             sage: R(0)._is_inexact_zero() 
    390             True 
    391         """ 
    392         return mpz_sgn(self.value) == 0 
    393  
    394     def __richcmp__(left, right, op): 
    395         """ 
    396         Comparison. 
    397  
    398         TESTS:: 
    399  
    400             sage: R = ZpCA(5) 
    401             sage: a = R(17) 
    402             sage: b = R(21) 
    403             sage: a == b 
    404             False 
    405             sage: a < b 
    406             True 
    407         """ 
    408         return (<Element>left)._richcmp(right, op) 
    409  
    410     def __invert__(self): 
    411         """ 
    412         Returns the multiplicative inverse of ``self``. 
    413          
    414         EXAMPLES:: 
    415          
    416             sage: R = ZpCA(17) 
    417             sage: ~R(-1) == R(-1) 
    418             True 
    419             sage: ~R(5) * 5 
    420             1 + O(17^20) 
    421             sage: ~R(5) 
    422             7 + 3*17 + 10*17^2 + 13*17^3 + 6*17^4 + 3*17^5 + 10*17^6 + 13*17^7 + 6*17^8 + 3*17^9 + 10*17^10 + 13*17^11 + 6*17^12 + 3*17^13 + 10*17^14 + 13*17^15 + 6*17^16 + 3*17^17 + 10*17^18 + 13*17^19 + O(17^20) 
    423         """ 
    424         return self._invert_c_impl() 
    425  
    426     cpdef RingElement _invert_c_impl(self): 
    427         """ 
    428         Returns the multiplicative inverse of ``self``. 
    429  
    430         EXAMPLES:: 
    431  
    432             sage: R = ZpCA(17) 
    433             sage: ~R(-1) == R(-1) #indirect doctest 
    434             True 
    435         """ 
    436         return self.parent().fraction_field()(self).__invert__() 
    437  
    438     cpdef ModuleElement _neg_(self): 
    439         """ 
    440         Returns the negation of self. 
    441  
    442         EXAMPLES:: 
    443          
    444             sage: R = Zp(5, prec=10, type='capped-abs') 
    445             sage: a = R(1) 
    446             sage: -a #indirect doctest 
    447             4 + 4*5 + 4*5^2 + 4*5^3 + 4*5^4 + 4*5^5 + 4*5^6 + 4*5^7 + 4*5^8 + 4*5^9 + O(5^10) 
    448         """ 
    449         if mpz_sgn(self.value) == 0: 
    450             return self 
    451         cdef pAdicCappedAbsoluteElement ans 
    452         ans = self._new_c() 
    453         ans.absprec = self.absprec 
    454         mpz_sub(ans.value, self.prime_pow.pow_mpz_t_tmp(self.absprec)[0], self.value) 
    455         return ans 
    456  
    457     def __pow__(pAdicCappedAbsoluteElement self, right, dummy): 
    458         """ 
    459         Exponentiation. 
    460          
    461         EXAMPLES:: 
    462          
    463             sage: R = ZpCA(11, 5) 
    464             sage: R(1/2)^5 
    465             10 + 7*11 + 11^2 + 5*11^3 + 4*11^4 + O(11^5) 
    466             sage: R(1/32) 
    467             10 + 7*11 + 11^2 + 5*11^3 + 4*11^4 + O(11^5) 
    468             sage: R(1/2)^5 == R(1/32) 
    469             True 
    470             sage: R(3)^1000 
    471             1 + 4*11^2 + 3*11^3 + 7*11^4 + O(11^5) 
    472         """ 
    473         # p-adic exponents and correct precisions!!! 
    474         if not self and not right: 
    475             raise ArithmeticError, "0^0 is undefined." 
    476         cdef Integer new, absprec 
    477         cdef long val 
    478         new = Integer(right) #Need to make sure that this works for p-adic exponents 
    479         val = self.valuation_c() 
    480         if (val > 0) and isinstance(right, pAdicBaseGenericElement): 
    481             raise ValueError, "Can only have p-adic exponent if base is a unit" 
    482         if (new < 0): 
    483             return (~self).__pow__(-new) 
    484         cdef pAdicCappedAbsoluteElement ans 
    485         cdef Integer preccap 
    486         preccap = <Integer>self.parent().precision_cap() 
    487         ans = self._new_c() 
    488         if val > 0: 
    489             if new * val >= preccap: 
    490                 ans._set_from_Integer(Integer(0), preccap, infinity) 
    491             else: 
    492                 absprec = <Integer> min(self.precision_relative() + new * val, preccap) 
    493                 ans._set_prec_abs(mpz_get_ui(absprec.value)) 
    494                 sig_on() 
    495                 mpz_powm(ans.value, self.value, new.value, self.prime_pow.pow_mpz_t_tmp(ans.absprec)[0]) 
    496                 sig_off() 
    497         else: 
    498             ans.absprec = self.absprec 
    499             sig_on() 
    500             mpz_powm(ans.value, self.value, new.value, self.prime_pow.pow_mpz_t_tmp(self.absprec)[0]) 
    501             sig_off() 
    502         return ans 
    503  
    504     cpdef ModuleElement _add_(self, ModuleElement _right): 
    505         """ 
    506         Addition. 
    507          
    508         EXAMPLES:: 
    509          
    510             sage: R = ZpCA(13, 4) 
    511             sage: R(2) + R(3) #indirect doctest 
    512             5 + O(13^4) 
    513             sage: R(12) + R(1) 
    514             13 + O(13^4) 
    515         """ 
    516         cdef pAdicCappedAbsoluteElement ans 
    517         cdef pAdicCappedAbsoluteElement right = <pAdicCappedAbsoluteElement> _right 
    518         ans = self._new_c() 
    519         if self.absprec < right.absprec: 
    520             ans.absprec = self.absprec 
    521         else: 
    522             ans.absprec = right.absprec 
    523         mpz_add(ans.value, self.value, right.value) 
    524         if mpz_cmp(ans.value, self.prime_pow.pow_mpz_t_tmp(ans.absprec)[0]) >= 0: 
    525             mpz_mod(ans.value, ans.value, self.prime_pow.pow_mpz_t_tmp(ans.absprec)[0]) 
    526         return ans 
    527  
    528     cpdef RingElement _div_(self, RingElement right): 
    529         """ 
    530         Division. 
    531  
    532         EXAMPLES:: 
    533  
    534             sage: R = ZpCA(13, 4) 
    535             sage: R(2) / R(3) # indirect doctest 
    536             5 + 4*13 + 4*13^2 + 4*13^3 + O(13^4) 
    537             sage: a = R(169 * 2) / R(13); a 
    538             2*13 + O(13^3) 
    539             sage: R(13) / R(169 * 2) 
    540             7*13^-1 + 6 + O(13) 
    541             sage: ~a 
    542             7*13^-1 + 6 + O(13) 
    543             sage: 1 / a 
    544             7*13^-1 + 6 + O(13) 
    545         """ 
    546         return self * (~right) 
    547  
    548     def __lshift__(pAdicCappedAbsoluteElement self, shift): 
    549         """ 
    550         Multiplies ``self`` by ``p^shift``. 
    551  
    552         If ``shift < -self.ordp()``, digits will be truncated.  See 
    553         ``__rshift__`` for details. 
    554          
    555         EXAMPLES: 
    556          
    557         We create a capped absolute ring:: 
    558          
    559             sage: R = Zp(5, 20, 'capped-abs'); a = R(1000); a 
    560             3*5^3 + 5^4 + O(5^20) 
    561  
    562         Shifting to the right is the same as dividing by a power of 
    563         the uniformizer `p` of the `p`-adic ring.:: 
    564          
    565             sage: a >> 1 
    566             3*5^2 + 5^3 + O(5^19) 
    567  
    568         Shifting to the left is the same as multiplying by a power of 
    569         `p`:: 
    570          
    571             sage: a << 2 
    572             3*5^5 + 5^6 + O(5^20) 
    573             sage: a*5^2 
    574             3*5^5 + 5^6 + O(5^20)         
    575  
    576         Shifting by a negative integer to the left is the same as 
    577         right shifting by the absolute value:: 
    578  
    579             sage: a << -3 
    580             3 + 5 + O(5^17) 
    581             sage: a >> 3 
    582             3 + 5 + O(5^17) 
    583         """ 
    584         cdef pAdicCappedAbsoluteElement ans 
    585         if not PY_TYPE_CHECK(shift, Integer): 
    586             shift = Integer(shift) 
    587         if mpz_fits_slong_p((<Integer>shift).value) == 0: 
    588             ans = self._new_c() 
    589             mpz_set_ui(ans.value, 0) 
    590             if mpz_sgn((<Integer>shift).value) == 1: 
    591                 ans._set_prec_abs(self.prime_pow.prec_cap) 
    592             else: 
    593                 ans._set_prec_abs(0) 
    594             return ans 
    595         return self._lshift_c(mpz_get_si((<Integer>shift).value)) 
    596  
    597     cdef pAdicCappedAbsoluteElement _lshift_c(pAdicCappedAbsoluteElement self, long shift): 
    598         """ 
    599         Multiplies ``self`` by ``p^shift``. 
    600  
    601         If ``shift < -self.ordp()``, digits will be truncated.  See 
    602         ``__rshift__`` for details. 
    603          
    604         EXAMPLES:: 
    605  
    606             sage: R = ZpCA(5); a = R(17); a << 2 
    607             2*5^2 + 3*5^3 + O(5^20) 
    608         """ 
    609         cdef unsigned long prec_cap, ansprec 
    610         cdef pAdicCappedAbsoluteElement ans 
    611         cdef PowComputer_class powerer 
    612         if shift < 0: 
    613             return self._rshift_c(-shift) 
    614         prec_cap = self.prime_pow.prec_cap 
    615         if shift >= prec_cap: # if we ever start caching valuation, this check should change 
    616             ans = self._new_c() 
    617             mpz_set_ui(ans.value, 0) 
    618             ans._set_prec_abs(prec_cap) 
    619             return ans 
    620         elif shift > 0: 
    621             ans = self._new_c() 
    622             ansprec = shift + self.absprec 
    623             if ansprec > prec_cap: 
    624                 ansprec = prec_cap 
    625             ans._set_prec_abs(ansprec) 
    626             mpz_mul(ans.value, self.value, self.prime_pow.pow_mpz_t_tmp(shift)[0]) 
    627             if mpz_cmp(ans.value, ans.prime_pow.pow_mpz_t_top()[0]) >= 0: 
    628                 mpz_mod(ans.value, ans.value, ans.prime_pow.pow_mpz_t_top()[0]) 
    629             return ans 
    630         else: 
    631             return self 
    632  
    633     def __rshift__(pAdicCappedAbsoluteElement self, shift): 
    634         """ 
    635         Divides by ``p^shift``, and truncates. 
    636          
    637         EXAMPLES:: 
    638          
    639             sage: R = Zp(997, 7, 'capped-abs'); a = R(123456878908); a 
    640             964*997 + 572*997^2 + 124*997^3 + O(997^7) 
    641  
    642         Shifting to the right divides by a power of `p`, but dropping 
    643         terms with negative valuation:: 
    644              
    645             sage: a >> 3 
    646             124 + O(997^4) 
    647  
    648         A negative shift multiplies by that power of `p`.:: 
    649          
    650             sage: a >> -3 
    651             964*997^4 + 572*997^5 + 124*997^6 + O(997^7) 
    652         """ 
    653         cdef pAdicCappedAbsoluteElement ans 
    654         if not PY_TYPE_CHECK(shift, Integer): 
    655             shift = Integer(shift) 
    656         if mpz_fits_slong_p((<Integer>shift).value) == 0: 
    657             ans = self._new_c() 
    658             mpz_set_ui(ans.value, 0) 
    659             if mpz_sgn((<Integer>shift).value) == -1: 
    660                 ans._set_prec_abs(self.prime_pow.prec_cap) 
    661             else: 
    662                 ans._set_prec_abs(0) 
    663             return ans 
    664         return self._rshift_c(mpz_get_si((<Integer>shift).value)) 
    665  
    666     cdef pAdicCappedAbsoluteElement _rshift_c(pAdicCappedAbsoluteElement self, long shift): 
    667         """ 
    668         Divides by ``p^shift`` and truncates. 
    669  
    670         EXAMPLES:: 
    671  
    672             sage: R = ZpCA(5); a = R(77); a >> 1 
    673             3*5 + O(5^19) 
    674         """ 
    675         cdef unsigned long prec_cap, ansprec 
    676         cdef pAdicCappedAbsoluteElement ans 
    677         if shift < 0: 
    678             return self._lshift_c(-shift) 
    679         prec_cap = self.prime_pow.prec_cap 
    680         if shift >= self.absprec: 
    681             ans = self._new_c() 
    682             mpz_set_ui(ans.value, 0) 
    683             ans._set_prec_abs(0) 
    684             return ans 
    685         elif shift > 0: 
    686             ans = self._new_c() 
    687             ansprec = self.absprec - shift 
    688             ans._set_prec_abs(ansprec) 
    689             mpz_fdiv_q(ans.value, self.value, self.prime_pow.pow_mpz_t_tmp(shift)[0]) 
    690             return ans 
    691         else: 
    692             return self 
    693  
    694     cpdef RingElement _mul_(self, RingElement _right): 
    695         """ 
    696         Multiplication. 
    697          
    698         EXAMPLES:: 
    699          
    700             sage: R = ZpCA(5) 
    701             sage: a = R(20,5); b = R(75, 4); a * b #indirect doctest 
    702             2*5^3 + 2*5^4 + O(5^5) 
    703         """ 
    704         cdef pAdicCappedAbsoluteElement ans 
    705         cdef pAdicCappedAbsoluteElement right = <pAdicCappedAbsoluteElement> _right 
    706         cdef unsigned long sval, rval, prec1, prec2, prec_cap 
    707         ans = self._new_c() 
    708         prec_cap = self.prime_pow.prec_cap 
    709         sval = self.valuation_c() 
    710         rval = right.valuation_c() 
    711         prec1 = sval + right.absprec 
    712         prec2 = rval + self.absprec 
    713         if prec1 < prec2: 
    714             if prec_cap < prec1: 
    715                 ans._set_prec_abs(prec_cap) 
    716             else: 
    717                 ans._set_prec_abs(prec1) 
    718         else: 
    719             if prec_cap < prec2: 
    720                 ans._set_prec_abs(prec_cap) 
    721             else: 
    722                 ans._set_prec_abs(prec2) 
    723         mpz_mul(ans.value, self.value, right.value) 
    724         mpz_mod(ans.value, ans.value, self.prime_pow.pow_mpz_t_tmp(ans.absprec)[0]) 
    725         return ans 
    726  
    727     cpdef ModuleElement _sub_(self, ModuleElement _right): 
    728         """ 
    729         Subtraction. 
    730          
    731         EXAMPLES:: 
    732          
    733             sage: R = ZpCA(13, 4) 
    734             sage: R(10) - R(10) #indirect doctest 
    735             O(13^4) 
    736             sage: R(10) - R(11) 
    737             12 + 12*13 + 12*13^2 + 12*13^3 + O(13^4) 
    738         """ 
    739         cdef pAdicCappedAbsoluteElement ans 
    740         cdef pAdicCappedAbsoluteElement right = <pAdicCappedAbsoluteElement> _right 
    741         ans = self._new_c() 
    742         if self.absprec < right.absprec: 
    743             ans.absprec = self.absprec 
    744         else: 
    745             ans.absprec = right.absprec 
    746         mpz_sub(ans.value, self.value, right.value) 
    747         if mpz_sgn(ans.value) == -1 or mpz_cmp(ans.value, self.prime_pow.pow_mpz_t_tmp(ans.absprec)[0]) >= 0: 
    748             mpz_mod(ans.value, ans.value, self.prime_pow.pow_mpz_t_tmp(ans.absprec)[0]) 
    749         return ans 
    750  
    751     def add_bigoh(pAdicCappedAbsoluteElement self, absprec): 
    752         """ 
    753         Returns a new element with absolute precision decreased to 
    754         ``prec``.  The precision never increases. 
    755          
    756         INPUT: 
    757          
    758         - ``self`` -- a `p`-adic element 
    759          
    760         - ``prec`` -- an integer 
    761              
    762         OUTPUT: 
    763          
    764         - ``element`` -- ``self`` with precision set to the minimum of ``self's`` precision and ``prec`` 
    765          
    766         EXAMPLES:: 
    767          
    768             sage: R = Zp(7,4,'capped-abs','series'); a = R(8); a.add_bigoh(1) 
    769             1 + O(7) 
    770  
    771             sage: k = ZpCA(3,5) 
    772             sage: a = k(41); a 
    773             2 + 3 + 3^2 + 3^3 + O(3^5) 
    774             sage: a.add_bigoh(7) 
    775             2 + 3 + 3^2 + 3^3 + O(3^5) 
    776             sage: a.add_bigoh(3) 
    777             2 + 3 + 3^2 + O(3^3)             
    778         """ 
    779         cdef pAdicCappedAbsoluteElement ans 
    780         cdef unsigned long newprec 
    781         cdef Integer _absprec 
    782         if not PY_TYPE_CHECK(absprec, Integer): 
    783             _absprec = Integer(absprec) 
    784         else: 
    785             _absprec = <Integer>absprec 
    786         if mpz_fits_ulong_p(_absprec.value) == 0: 
    787             if mpz_sgn((<Integer>absprec).value) == -1: 
    788                 ans = self._new_c() 
    789                 ans._set_prec_abs(0) 
    790                 mpz_set_ui(ans.value, 0) 
    791                 return ans 
    792             else: 
    793                 return self 
    794         newprec = mpz_get_ui(_absprec.value) 
    795         if newprec >= self.absprec: 
    796             return self 
    797         elif newprec <= 0: 
    798             ans = self._new_c() 
    799             ans._set_prec_abs(0) 
    800             mpz_set_ui(ans.value, 0) 
    801             return ans 
    802         else: 
    803             ans = self._new_c() 
    804             ans._set_prec_abs(newprec) 
    805             mpz_set(ans.value, self.value) 
    806             if mpz_cmp(ans.value, self.prime_pow.pow_mpz_t_tmp(ans.absprec)[0]) >= 0: 
    807                 mpz_mod(ans.value, ans.value, self.prime_pow.pow_mpz_t_tmp(ans.absprec)[0]) 
    808             return ans 
    809  
    810     def __copy__(pAdicCappedAbsoluteElement self): 
    811         """ 
    812         Returns a copy of ``self``. 
    813  
    814         EXAMPLES:: 
    815  
    816             sage: a = ZpCA(5,6)(17); b = copy(a) 
    817             sage: a == b 
    818             True 
    819             sage: a is b 
    820             False 
    821         """ 
    822         cdef pAdicCappedAbsoluteElement ans 
    823         ans = self._new_c() 
    824         ans.absprec = self.absprec 
    825         mpz_set(ans.value, self.value) 
    826         return ans 
    827  
    828     def is_zero(self, absprec = None): 
    829         r""" 
    830         Returns whether ``self`` is zero modulo ``p^absprec``. 
    831          
    832         INPUT: 
    833          
    834         - ``self`` -- a `p`-adic element 
    835          
    836         - ``prec`` -- an integer 
    837  
    838         OUTPUT: 
    839          
    840         - ``boolean`` -- whether self is zero 
    841            
    842         EXAMPLES:: 
    843          
    844             sage: R = ZpCA(17, 6) 
    845             sage: R(0).is_zero() 
    846             True 
    847             sage: R(17^6).is_zero() 
    848             True 
    849             sage: R(17^2).is_zero(absprec=2) 
    850             True 
    851         """ 
    852         if absprec is None: 
    853             return mpz_sgn(self.value) == 0 
    854         cdef Integer _absprec 
    855         if not PY_TYPE_CHECK(absprec, Integer): 
    856             _absprec = Integer(absprec) 
    857         else: 
    858             _absprec = <Integer>absprec 
    859         if mpz_cmp_ui(_absprec.value, self.absprec) > 0: 
    860             raise PrecisionError, "Not enough precision to determine if element is zero" 
    861         cdef mpz_t tmp 
    862         mpz_init(tmp) 
    863         cdef unsigned long aprec 
    864         aprec = mpz_get_ui(_absprec.value) 
    865         mpz_mod(tmp, self.value, self.prime_pow.pow_mpz_t_tmp(aprec)[0]) 
    866         if mpz_sgn(tmp) == 0: 
    867             mpz_clear(tmp) 
    868             return True 
    869         else: 
    870             mpz_clear(tmp) 
    871             return False 
    872  
    873     def is_equal_to(pAdicCappedAbsoluteElement self, pAdicCappedAbsoluteElement right, absprec = None): 
    874         r""" 
    875         Returns whether ``self`` is equal to ``right`` modulo ``p^absprec``. 
    876  
    877         INPUT: 
    878          
    879         - ``self`` -- a `p`-adic element 
    880          
    881         - ``right`` -- a `p`-adic element with the same parent 
    882          
    883         - ``absprec`` -- an integer 
    884  
    885         OUTPUT: 
    886          
    887         - ``boolean`` -- whether ``self`` is equal to ``right`` 
    888            
    889         EXAMPLES:: 
    890          
    891             sage: R = ZpCA(2, 6) 
    892             sage: R(13).is_equal_to(R(13)) 
    893             True 
    894             sage: R(13).is_equal_to(R(13+2^10)) 
    895             True 
    896             sage: R(13).is_equal_to(R(17), 2) 
    897             True 
    898             sage: R(13).is_equal_to(R(17), 5) 
    899             False 
    900         """ 
    901         cdef unsigned long aprec 
    902         if absprec is None: 
    903             if self.absprec < right.absprec: 
    904                 aprec = self.absprec 
    905             else: 
    906                 aprec = right.absprec 
    907         else: 
    908             if not PY_TYPE_CHECK(absprec, Integer): 
    909                 absprec = Integer(absprec) 
    910             if mpz_fits_slong_p((<Integer>absprec).value) == 0: 
    911                 if mpz_sgn((<Integer>absprec).value) == 1: 
    912                     raise PrecisionError, "Elements are not known to specified precision" 
    913                 else: 
    914                     return True 
    915             aprec = mpz_get_ui((<Integer>absprec).value) 
    916             if aprec > self.absprec or aprec > right.absprec: 
    917                 raise PrecisionError, "Elements are not known to specified precision"                 
    918         cdef mpz_t tmp1, tmp2 
    919         mpz_init(tmp1) 
    920         mpz_init(tmp2) 
    921         mpz_mod(tmp1, self.value, self.prime_pow.pow_mpz_t_tmp(aprec)[0]) 
    922         mpz_mod(tmp2, (right).value, self.prime_pow.pow_mpz_t_tmp(aprec)[0]) 
    923         if mpz_cmp(tmp1, tmp2) == 0: 
    924             mpz_clear(tmp1) 
    925             mpz_clear(tmp2) 
    926             return True 
    927         else: 
    928             mpz_clear(tmp1) 
    929             mpz_clear(tmp2) 
    930             return False 
    931  
    932     cpdef Integer lift(self): 
     33        sage: R = ZpCA(3, 5) 
     34        sage: R(2) 
     35        2 + O(3^5) 
     36        sage: R(2, absprec=2) 
     37        2 + O(3^2) 
     38        sage: R(3, relprec=2) 
     39        3 + O(3^3) 
     40        sage: R(Qp(3)(10)) 
     41        1 + 3^2 + O(3^5) 
     42        sage: R(pari(6)) 
     43        2*3 + O(3^5) 
     44        sage: R(pari(1/2)) 
     45        2 + 3 + 3^2 + 3^3 + 3^4 + O(3^5) 
     46        sage: R(1/2) 
     47        2 + 3 + 3^2 + 3^3 + 3^4 + O(3^5) 
     48        sage: R(mod(-1, 3^7)) 
     49        2 + 2*3 + 2*3^2 + 2*3^3 + 2*3^4 + O(3^5) 
     50        sage: R(mod(-1, 3^2)) 
     51        2 + 2*3 + O(3^2) 
     52        sage: R(3 + O(3^2)) 
     53        3 + O(3^2) 
     54    """ 
     55    def lift(self): 
    93356        """ 
    93457        Returns an integer congruent to this `p`-adic element modulo 
    93558        ``p^self.absprec()``. 
     
    94265            sage: R(-1).lift() 
    94366            3486784400 
    94467        """ 
    945         cdef Integer ans 
    946         ans = PY_NEW(Integer) 
     68        return self.lift_c() 
     69 
     70    cdef lift_c(self): 
     71        """ 
     72        Implementation of lift 
     73 
     74        TESTS:: 
     75 
     76            sage: ZpCA(3,3)(1/4).lift() # indirect doctest 
     77            7 
     78        """ 
     79        cdef Integer ans = PY_NEW(Integer) 
    94780        mpz_set(ans.value, self.value) 
    94881        return ans 
    94982 
    950     def lift_to_precision(self, absprec): 
     83    def _pari_(self): 
    95184        """ 
    952         Returns a `p`-adic integer congruent to this `p`-adic element 
    953         modulo ``p^absprec`` with precision at least ``absprec``. 
     85        Conversion to pari. 
    95486 
    955         If such lifting would yield an element with precision greater 
    956         than allowed by the precision cap of ``self``'s parent, an 
    957         error is raised. 
    958          
     87        EXAMPLES:: 
     88 
     89            sage: R = ZpCA(5) 
     90            sage: pari(R(1777)) #indirect doctest 
     91            2 + 5^2 + 4*5^3 + 2*5^4 + O(5^20) 
     92            sage: pari(R(0,0)) 
     93            O(5^0) 
     94        """ 
     95        return self._to_gen() 
     96 
     97    cdef pari_gen _to_gen(self): 
     98        """ 
     99        Converts this element to an equivalent pari element. 
     100 
    959101        EXAMPLES:: 
    960102         
    961             sage: R = ZpCA(17) 
    962             sage: R(-1,2).lift_to_precision(10) 
    963             16 + 16*17 + O(17^10) 
    964             sage: R(1,15).lift_to_precision(10) 
    965             1 + O(17^15) 
    966             sage: R(1,15).lift_to_precision(30) 
    967             Traceback (most recent call last): 
    968             ... 
    969             PrecisionError: Precision higher than allowed by the precision cap. 
     103            sage: R = Zp(5, 10); a = R(17); pari(a) #indirect doctest 
     104            2 + 3*5 + O(5^10) 
     105            sage: pari(R(0)) 
     106            0 
     107            sage: pari(R(0,5)) 
     108            O(5^5) 
    970109        """ 
    971         cdef pAdicCappedAbsoluteElement ans 
    972         cdef unsigned long prec_cap 
    973         cdef unsigned long dest_prec 
    974         prec_cap = self.prime_pow.prec_cap 
    975         if not PY_TYPE_CHECK(absprec, Integer): 
    976             absprec = Integer(absprec) 
    977         if mpz_fits_ulong_p((<Integer>absprec).value) == 0: 
    978             ans = self._new_c() 
    979             ans._set_prec_abs(prec_cap) 
    980             mpz_set(ans.value, self.value) 
    981         else: 
    982             dest_prec = mpz_get_ui((<Integer>absprec).value) 
    983             if prec_cap < dest_prec: 
    984                 raise PrecisionError, "Precision higher than allowed by the precision cap." 
    985             if dest_prec <= self.absprec: 
    986                 return self 
    987             else: 
    988                 ans = self._new_c() 
    989                 ans._set_prec_abs(dest_prec) 
    990                 mpz_set(ans.value, self.value) 
    991         return ans 
     110        # holder is defined in the linkage file 
     111        cdef long val = mpz_remove(holder.value, self.value, self.prime_pow.prime.value) 
     112        return P.new_gen_from_padic(val, self.absprec - val, 
     113                                    self.prime_pow.prime.value, 
     114                                    self.prime_pow.pow_mpz_t_tmp(self.absprec - val)[0], 
     115                                    holder.value) 
    992116 
    993     def list(pAdicCappedAbsoluteElement self, lift_mode = 'simple'): 
     117    def _integer_(self, Z=None): 
     118        r""" 
     119        Converts self to an integer 
     120 
     121        TESTS:: 
     122         
     123            sage: R = ZpCA(5, prec = 4); a = R(642); a 
     124            2 + 3*5 + O(5^4) 
     125            sage: a._integer_() 
     126            17 
    994127        """ 
    995         Returns a list of coefficients of `p` starting with `p^0` 
    996          
     128        return self.lift_c() 
     129 
     130    def residue(self, absprec=1): 
     131        r""" 
     132        Reduces ``self`` modulo ``p^absprec`` 
     133 
    997134        INPUT: 
    998135         
    999136        - ``self`` -- a `p`-adic element 
    1000137         
    1001         - ``lift_mode`` -- ``'simple'``, ``'smallest'`` or 
    1002           ``'teichmuller'`` (default ``'simple'``) 
    1003  
     138        - ``absprec`` - an integer 
     139             
    1004140        OUTPUT: 
    1005141         
    1006         - ``list`` -- the list of coefficients of ``self`` 
    1007  
    1008         NOTES: 
    1009          
    1010         - Returns a list `[a_0, a_1, \ldots, a_n]` so that: 
    1011  
    1012           + If ``lift_mode = 'simple'``, `a_i` is an integer with `0 
    1013             \le a_i < p`. 
    1014  
    1015           + If ``lift_mode = 'smallest'``, `a_i` is an integer with 
    1016             `-p/2 < a_i \le p/2`. 
    1017  
    1018           + If ``lift_mode = 'teichmuller'``, `a_i` has the same 
    1019             parent as `self` and `a_i^p \equiv a_i` modulo 
    1020             ``p^(self.precision_absolute() - i)`` 
    1021  
    1022         - `\sum_{i = 0}^n a_i \cdot p^i =` ``self``, modulo the 
    1023           precision of ``self``. 
    1024              
     142        - element of `\mathbb{Z}/p^{\mbox{absprec}} \mathbb{Z}` -- 
     143          ``self`` reduced modulo ``p^absprec``. 
    1025144 
    1026145        EXAMPLES:: 
    1027146         
    1028             sage: R = ZpCA(7,6); a = R(12837162817); a 
    1029             3 + 4*7 + 4*7^2 + 4*7^4 + O(7^6) 
    1030             sage: L = a.list(); L 
    1031             [3, 4, 4, 0, 4] 
    1032             sage: sum([L[i] * 7^i for i in range(len(L))]) == a 
    1033             True 
    1034             sage: L = a.list('smallest'); L 
    1035             [3, -3, -2, 1, -3, 1] 
    1036             sage: sum([L[i] * 7^i for i in range(len(L))]) == a 
    1037             True 
    1038             sage: L = a.list('teichmuller'); L 
    1039             [3 + 4*7 + 6*7^2 + 3*7^3 + 2*7^5 + O(7^6), 
    1040             O(7^5), 
    1041             5 + 2*7 + 3*7^3 + O(7^4), 
    1042             1 + O(7^3), 
    1043             3 + 4*7 + O(7^2), 
    1044             5 + O(7)] 
    1045             sage: sum([L[i] * 7^i for i in range(len(L))]) 
    1046             3 + 4*7 + 4*7^2 + 4*7^4 + O(7^6) 
     147            sage: R = Zp(7,4,'capped-abs'); a = R(8); a.residue(1) 
     148            1 
    1047149        """ 
    1048         if lift_mode == 'teichmuller': 
    1049             return self.teichmuller_list() 
    1050         if lift_mode == 'simple': 
    1051             return (<pAdicPrinter_class>self.parent()._printer).base_p_list(self.value, True) 
    1052         elif lift_mode == 'smallest': 
    1053             return (<pAdicPrinter_class>self.parent()._printer).base_p_list(self.value, False) 
    1054         else: 
    1055             raise ValueError 
    1056  
    1057     cdef object teichmuller_list(pAdicCappedAbsoluteElement self): 
    1058         r""" 
    1059         Returns a list `[a_0, a_1,\ldots, a_n]` such that 
    1060          
    1061         - `a_i^p = a_i` 
    1062  
    1063         - ``self`` equals `\sum_{i = 0}^n a_i p^i` 
    1064          
    1065         - if `a_i \ne 0`, the absolute precision of `a_i` is 
    1066           ``self.precision_relative() - i`` 
    1067  
    1068         EXAMPLES:: 
    1069  
    1070             sage: R = ZpFM(5,5); R(14).list('teichmuller') #indirect doctest 
    1071             [4 + 4*5 + 4*5^2 + 4*5^3 + 4*5^4 + O(5^5), 
    1072             3 + 3*5 + 2*5^2 + 3*5^3 + 5^4 + O(5^5), 
    1073             2 + 5 + 2*5^2 + 5^3 + 3*5^4 + O(5^5), 
    1074             1 + O(5^5), 
    1075             4 + 4*5 + 4*5^2 + 4*5^3 + 4*5^4 + O(5^5)] 
    1076         """ 
    1077         # May eventually want to add a dict to store teichmuller lifts already seen, if p small enough 
    1078         cdef unsigned long curpower 
    1079         cdef mpz_t tmp, tmp2 
    1080         cdef pAdicCappedAbsoluteElement list_elt 
    1081         ans = PyList_New(0) 
    1082         curpower = self.absprec 
    1083         mpz_init_set(tmp, self.value) 
    1084         mpz_init(tmp2) 
    1085         while mpz_sgn(tmp) != 0: 
    1086             list_elt = self._new_c() 
    1087             list_elt._set_prec_abs(curpower) 
    1088             mpz_mod(list_elt.value, tmp, self.prime_pow.prime.value) 
    1089             mpz_set(tmp2, self.prime_pow.pow_mpz_t_tmp(curpower)[0]) 
    1090             self.teichmuller_set_c(list_elt.value, tmp2) 
    1091             mpz_sub(tmp, tmp, list_elt.value) 
    1092             mpz_divexact(tmp, tmp, self.prime_pow.prime.value) 
    1093             curpower -= 1 
    1094             mpz_mod(tmp, tmp, self.prime_pow.pow_mpz_t_tmp(curpower)[0]) 
    1095             PyList_Append(ans, list_elt) 
    1096         mpz_clear(tmp2) 
    1097         mpz_clear(tmp) 
    1098         return ans 
    1099  
    1100     def _teichmuller_set(self): 
    1101         """ 
    1102         Sets ``self`` to be the Teichmuller representative with the 
    1103         same residue as ``self``. 
    1104  
    1105         WARNING: 
    1106  
    1107         This function modifies ``self``, which is not safe.  Elements 
    1108         are supposed to be immutable. 
    1109  
    1110         EXAMPLES:: 
    1111  
    1112             sage: R = ZpCA(17,5); a = R(11) 
    1113             sage: a 
    1114             11 + O(17^5) 
    1115             sage: a._teichmuller_set(); a 
    1116             11 + 14*17 + 2*17^2 + 12*17^3 + 15*17^4 + O(17^5) 
    1117             sage: a.list('teichmuller') 
    1118             [11 + 14*17 + 2*17^2 + 12*17^3 + 15*17^4 + O(17^5)] 
    1119         """ 
    1120         cdef mpz_t tmp 
    1121         mpz_init_set(tmp, self.prime_pow.pow_mpz_t_tmp(self.absprec)[0]) 
    1122         self.teichmuller_set_c(self.value, tmp) 
    1123         mpz_clear(tmp) 
     150        cdef Integer selfvalue, modulus 
     151        if not PY_TYPE_CHECK(absprec, Integer): 
     152            absprec = Integer(absprec) 
     153        if mpz_cmp_si((<Integer>absprec).value, self.absprec) > 0: 
     154            raise PrecisionError, "Not enough precision known in order to compute residue." 
     155        elif mpz_sgn((<Integer>absprec).value) < 0: 
     156            raise ValueError, "cannot reduce modulo a negative power of p" 
     157        cdef long aprec = mpz_get_ui((<Integer>absprec).value) 
     158        modulus = PY_NEW(Integer) 
     159        mpz_set(modulus.value, self.prime_pow.pow_mpz_t_tmp(aprec)[0]) 
     160        selfvalue = PY_NEW(Integer) 
     161        mpz_set(selfvalue.value, self.value) 
     162        return Mod(selfvalue, modulus) 
    1124163 
    1125164    def multiplicative_order(self): 
    1126165        r""" 
     
    1176215            mpz_clear(ppow_minus_one) 
    1177216            return infinity 
    1178217 
    1179     def padded_list(self, n, list_mode = 'simple'): 
    1180         """ 
    1181         Returns a list of coefficients of `p` starting with `p^0` up 
    1182         to `p^n` exclusive (padded with zeros if needed) 
    1183          
    1184         INPUT: 
    1185          
    1186         - ``self`` -- a `p`-adic element 
    1187          
    1188         - ``n`` - an integer 
    1189              
    1190         OUTPUT: 
    1191          
    1192         - ``list`` -- the list of coefficients of ``self`` 
    1193  
    1194         EXAMPLES:: 
    1195          
    1196             sage: R = Zp(7,4,'capped-abs'); a = R(2*7+7**2); a.padded_list(5) 
    1197             [0, 2, 1, 0, 0] 
    1198  
    1199         NOTE: 
    1200          
    1201         this differs from the padded_list method of padic_field_element 
    1202          
    1203         the slice operators throw an error if asked for a slice above 
    1204         the precision, while this function works 
    1205         """ 
    1206         if list_mode == 'simple' or list_mode == 'smallest': 
    1207             zero = Integer(0) 
    1208         else: 
    1209             zero = self.parent()(0, 0) 
    1210         L = self.list() 
    1211         return L[:n] + [zero] * (n - len(L)) 
    1212  
    1213     def precision_absolute(self): 
    1214         """ 
    1215         Returns the absolute precision of ``self``. 
    1216  
    1217         This is the power of the maximal ideal modulo which this 
    1218         element is defined. 
    1219          
    1220         INPUT: 
    1221          
    1222         - ``self`` -- a `p`-adic element 
    1223              
    1224         OUTPUT: 
    1225          
    1226         - ``integer`` -- the absolute precision of ``self`` 
    1227              
    1228         EXAMPLES:: 
    1229          
    1230             sage: R = Zp(7,4,'capped-abs'); a = R(7); a.precision_absolute() 
    1231             4 
    1232        """ 
    1233         cdef Integer ans 
    1234         ans = PY_NEW(Integer) 
    1235         mpz_set_si(ans.value, self.absprec) 
    1236         return ans 
    1237  
    1238     def precision_relative(self): 
    1239         """ 
    1240         Returns the relative precision of ``self``. 
    1241  
    1242         This is the power of the maximal ideal modulo which the unit 
    1243         part of ``self`` is defined. 
    1244          
    1245         INPUT: 
    1246          
    1247         - ``self`` -- a `p`-adic element 
    1248              
    1249         OUTPUT: 
    1250          
    1251         - ``integer`` -- the relative precision of ``self`` 
    1252  
    1253         EXAMPLES:: 
    1254          
    1255             sage: R = Zp(7,4,'capped-abs'); a = R(7); a.precision_relative() 
    1256             3 
    1257        """ 
    1258         cdef Integer ans 
    1259         ans = PY_NEW(Integer) 
    1260         mpz_set_si(ans.value, self.absprec - self.valuation_c()) 
    1261         return ans 
    1262  
    1263     def residue(self, absprec = 1): 
    1264         r""" 
    1265         Reduces ``self`` modulo ``p^absprec`` 
    1266  
    1267         INPUT: 
    1268          
    1269         - ``self`` -- a `p`-adic element 
    1270          
    1271         - ``absprec`` - an integer 
    1272              
    1273         OUTPUT: 
    1274          
    1275         - element of `\mathbb{Z}/p^{\mbox{absprec}} \mathbb{Z}` -- 
    1276           ``self`` reduced modulo ``p^absprec``. 
    1277  
    1278         EXAMPLES:: 
    1279          
    1280             sage: R = Zp(7,4,'capped-abs'); a = R(8); a.residue(1) 
    1281             1 
    1282         """ 
    1283         if absprec > self.precision_absolute(): 
    1284             raise PrecisionError, "Not enough precision known in order to compute residue." 
    1285         elif absprec < 0: 
    1286             raise ValueError, "cannot reduce modulo a negative power of p" 
    1287         cdef Integer selfvalue 
    1288         selfvalue = PY_NEW(Integer) 
    1289         mpz_set(selfvalue.value, self.value) 
    1290         return Mod(selfvalue, self.parent().prime_pow(absprec)) 
    1291  
    1292          
    1293218    #def square_root(self): 
    1294219    #    r""" 
    1295220    #    Returns the square root of this p-adic number 
     
    1334259    #    except PariError: 
    1335260    #        raise ValueError, "element is not a square" # should eventually change to return an element of an extension field 
    1336261 
    1337     cpdef pAdicCappedAbsoluteElement unit_part(self): 
    1338         r""" 
    1339         Returns the unit part of ``self``. 
    1340  
    1341         INPUT: 
    1342          
    1343         - ``self`` -- a `p`-adic element 
    1344              
    1345         OUTPUT: 
    1346          
    1347         - `p`-adic element -- the unit part of ``self`` 
    1348              
    1349         EXAMPLES:: 
    1350          
    1351             sage: R = Zp(17,4,'capped-abs', 'val-unit') 
    1352             sage: a = R(18*17) 
    1353             sage: a.unit_part() 
    1354             18 + O(17^3) 
    1355             sage: type(a) 
    1356             <type 'sage.rings.padics.padic_capped_absolute_element.pAdicCappedAbsoluteElement'> 
    1357         """ 
    1358         cdef pAdicCappedAbsoluteElement ans 
    1359         cdef unsigned long v 
    1360         if mpz_sgn(self.value) == 0: 
    1361             ans = self._new_c() 
    1362             mpz_set_ui(ans.value, 0) 
    1363             ans._set_prec_abs(0) 
    1364             return ans 
    1365         elif mpz_divisible_p(self.value, self.prime_pow.prime.value): 
    1366             ans = self._new_c() 
    1367             sig_on() 
    1368             v = mpz_remove(ans.value, self.value, self.prime_pow.prime.value) 
    1369             sig_off() 
    1370             ans._set_prec_abs(self.absprec - v) 
    1371             return ans 
    1372         else: 
    1373             return self 
    1374  
    1375     def valuation(self): 
    1376         """ 
    1377         Returns the valuation of ``self``, ie the largest power of `p` 
    1378         dividing ``self``. 
    1379  
    1380         EXAMPLES:: 
    1381  
    1382             sage: R = ZpCA(5) 
    1383             sage: R(5^5*1827).valuation() 
    1384             5 
    1385  
    1386         TESTS:: 
    1387          
    1388             sage: R(1).valuation() 
    1389             0 
    1390             sage: R(2).valuation() 
    1391             0 
    1392             sage: R(5).valuation() 
    1393             1 
    1394             sage: R(10).valuation() 
    1395             1 
    1396             sage: R(25).valuation() 
    1397             2 
    1398             sage: R(50).valuation() 
    1399             2             
    1400             sage: R(0).valuation() 
    1401             20 
    1402         """ 
    1403         # We override this, rather than using the valuation in 
    1404         # padic_generic_element, for speed reasons. 
    1405          
    1406         cdef Integer ans 
    1407         ans = PY_NEW(Integer) 
    1408         mpz_set_ui(ans.value, self.valuation_c()) 
    1409         return ans 
    1410  
    1411     cdef long valuation_c(self): 
    1412         """ 
    1413         Returns the valuation of ``self``, ie the largest power of `p` 
    1414         dividing ``self``. 
    1415  
    1416         EXAMPLES:: 
    1417  
    1418             sage: R = ZpCA(5) 
    1419             sage: a = R(0,6) 
    1420             sage: a.valuation() #indirect doctest 
    1421             6 
    1422         """ 
    1423         if mpz_sgn(self.value) == 0: 
    1424             return self.absprec 
    1425         cdef mpz_t tmp 
    1426         cdef long ans 
    1427         mpz_init(tmp) 
    1428         ans = mpz_remove(tmp, self.value, self.prime_pow.prime.value) 
    1429         mpz_clear(tmp) 
    1430         return ans 
    1431  
    1432     cpdef val_unit(self): 
    1433         """ 
    1434         Returns a 2-tuple, the first element set to the valuation of 
    1435         ``self``, and the second to the unit part of ``self``. 
    1436  
    1437         If ``self = 0``, then the unit part is ``O(p^0)``. 
    1438  
    1439         EXAMPLES:: 
    1440          
    1441             sage: R = ZpCA(5) 
    1442             sage: a = R(75, 6); b = a - a 
    1443             sage: a.val_unit() 
    1444             (2, 3 + O(5^4)) 
    1445             sage: b.val_unit() 
    1446             (6, O(5^0)) 
    1447         """ 
    1448         cdef pAdicCappedAbsoluteElement unit 
    1449         cdef Integer val 
    1450         cdef unsigned long v 
    1451         val = PY_NEW(Integer) 
    1452         if mpz_sgn(self.value) == 0: 
    1453             unit = self._new_c() 
    1454             mpz_set_ui(unit.value, 0) 
    1455             unit._set_prec_abs(0) 
    1456             mpz_set_ui(val.value, self.absprec) 
    1457             return (val, unit) 
    1458         elif mpz_divisible_p(self.value, self.prime_pow.prime.value): 
    1459             unit = self._new_c() 
    1460             v = mpz_remove(unit.value, self.value, self.prime_pow.prime.value) 
    1461             unit._set_prec_abs(self.absprec - v) 
    1462             mpz_set_ui(val.value, v) 
    1463             return (val, unit) 
    1464         else: 
    1465             mpz_set_ui(val.value, 0) 
    1466             return (val, self) 
    1467  
    1468     def __hash__(self): 
    1469         """ 
    1470         Hashing. 
    1471          
    1472         EXAMPLES:: 
    1473          
    1474             sage: R = ZpCA(11, 5) 
    1475             sage: hash(R(3)) == hash(3) 
    1476             True 
    1477         """ 
    1478         return hash(self.lift()) 
    1479  
    1480262def make_pAdicCappedAbsoluteElement(parent, x, absprec): 
    1481263    """ 
    1482264    Unpickles a capped absolute element. 
     
    1488270        sage: a = make_pAdicCappedAbsoluteElement(R, 17*25, 5); a 
    1489271        2*5^2 + 3*5^3 + O(5^5) 
    1490272    """ 
    1491     return parent(x, absprec=absprec) 
     273    return unpickle_cae_v2(pAdicCappedAbsoluteElement, parent, x, absprec)