Ticket #12080: trac_12080_manin_constant.patch

File trac_12080_manin_constant.patch, 6.3 KB (added by wuthrich, 3 years ago)

patch exported against 4.7.2

  • sage/schemes/elliptic_curves/ell_rational_field.py

    # HG changeset patch
    # User Chris Wuthrich <christian.wuthrich@gmail.com>
    # Date 1322505476 0
    # Node ID 7fb1c96400c8b006f5a0e8ea17e929c6999a5c21
    # Parent  9e29a3d84c48c399daaf3920bcb8b17273a0e876
    trac #12080: corrections for the manin constant
    
    diff --git a/sage/schemes/elliptic_curves/ell_rational_field.py b/sage/schemes/elliptic_curves/ell_rational_field.py
    a b  
    31393139         
    31403140         
    31413141        Moreover for all algorithms, computing a certain value of an 
    3142         `L`-function "uses a heuristic method that discerns when 
     3142        `L`-function 'uses a heuristic method that discerns when 
    31433143        the real-number approximation to the modular degree is within 
    3144         epsilon [=0.01 for algorithm="sympow"] of the same integer for 3 
     3144        epsilon [=0.01 for algorithm='sympow'] of the same integer for 3 
    31453145        consecutive trials (which occur maybe every 25000 coefficients or 
    31463146        so). Probably it could just round at some point. For rigour, you 
    31473147        would need to bound the tail by assuming (essentially) that all the 
     
    31503150        that it doesn't do the sum in 1-2-3-4 order; it uses 
    31513151        1-2-4-8--3-6-12-24-9-18- (Euler product style) instead, and so you 
    31523152        have to guess ahead of time at what point to curtail this 
    3153         expansion." (Quote from an email of Mark Watkins.) 
     3153        expansion.' (Quote from an email of Mark Watkins.) 
    31543154         
    31553155        .. note:: 
    31563156 
     
    43594359 
    43604360    def manin_constant(self): 
    43614361        r""" 
    4362         Return the Manin constant of this elliptic curve. 
     4362        Return the Manin constant of this elliptic curve. If `\phi: X_0(N) \to E` is the modular 
     4363        parametrization of minimal degree, then the Manin constant `c` is defined to be the rational 
     4364        number `c` such that `\phi^*(\omega_E) = c\cdot \omega_f` where `\omega_E` is a Neron differential and `\omega_f = f(q) dq/q` is the differential on `X_0(N)` corresponding to the 
     4365        newform `f` attached to the isogeny class of `E`.  
     4366 
     4367        It is known that the Manin constant is an integer. It is conjectured that in each class there is at least one, more precisely the so-called strong Weil curve or `X_0(N)`-optimal curve, that has Manin constant `1`. 
    43634368 
    43644369        OUTPUT: 
    4365              
     4370 
    43664371        an integer 
    43674372 
    43684373        This function only works if the curve is in the installed 
     
    43744379            sage: EllipticCurve('11a1').manin_constant() 
    43754380            1 
    43764381            sage: EllipticCurve('11a2').manin_constant() 
    4377             5 
     4382            1 
    43784383            sage: EllipticCurve('11a3').manin_constant() 
    43794384            5 
    43804385 
    43814386        Check that it works even if the curve is non-minimal:: 
    43824387 
    4383             sage: EllipticCurve('11a1').short_weierstrass_model().manin_constant() 
    4384             1 
    4385  
    4386         An example where the isogeny class is large, so it's not completely 
    4387         trivial to find the minimal degree of an isogeny to the optimal curve:: 
    4388  
    4389             sage: [EllipticCurve('210b%s'%i).manin_constant() for i in [1..8]] 
    4390             [1, 2, 3, 4, 4, 6, 12, 12] 
    4391  
    4392         Make sure the special case 990h is treated correctly, i.e., that 990h3 has 
    4393         Manin constant 1:: 
    4394  
    4395             sage: [EllipticCurve('990h%s'%i).manin_constant() for i in [1..4]] 
    4396             [3, 6, 1, 2] 
    4397          
    4398         This plots helps you see that the above Manin constants are 
    4399         right.  Note that the vertex labels are 0-based unlike the 
    4400         Cremona isogeny labels:: 
    4401  
    4402             sage: EllipticCurve('210b1').isogeny_graph().plot(edge_labels=True) 
    4403         """ 
    4404         label = self.cremona_label() 
    4405         optimal = self.optimal_curve() 
    4406         if optimal == self: 
    4407             return Integer(1) 
    4408         L, v = self._shortest_paths() 
    4409         i = L.index(optimal) 
    4410         return v[i] 
    4411          
     4388            sage: EllipticCurve('11a3').change_weierstrass_model([1/35,0,0,0]).manin_constant() 
     4389            5 
     4390 
     4391        Rather complicated examples (see #12080) :: 
     4392 
     4393            sage: [ EllipticCurve('27a%s'%i).manin_constant() for i in [1,2,3,4]]  
     4394            [1, 1, 3, 3] 
     4395            sage: [ EllipticCurve('80b%s'%i).manin_constant() for i in [1,2,3,4]]  
     4396            [1, 2, 1, 2] 
     4397 
     4398        """ 
     4399        from sage.databases.cremona import CremonaDatabase 
     4400 
     4401        if self.conductor() > CremonaDatabase().largest_conductor(): 
     4402            raise NotImplementedError, "The Manin constant can only be evaluated for curves in Cremona's tables. If you have not done so, you may wish to install the optional large database." 
     4403 
     4404        E = self.minimal_model() 
     4405        C = self.optimal_curve() 
     4406        _, m = C.isogeny_class() 
     4407        ma = max(max(x) for x in m) 
     4408        OmC = C.period_lattice().basis() 
     4409        OmE = E.period_lattice().basis() 
     4410        q_plus = QQ(gp.bestappr(OmE[0]/OmC[0],ma+1) ) 
     4411        n_plus = q_plus.numerator() 
     4412 
     4413        cinf_E = E.real_components() 
     4414        cinf_C = C.real_components() 
     4415        OmC_minus = OmC[1].imag() 
     4416        if cinf_C == 1: 
     4417            OmC_minus *= 2 
     4418        OmE_minus = OmE[1].imag() 
     4419        if cinf_E == 1: 
     4420            OmE_minus *= 2 
     4421        q_minus = QQ(gp.bestappr(OmE_minus/OmC_minus, ma+1)) 
     4422        n_minus = q_minus.numerator() 
     4423        n = ZZ(n_minus * n_plus) 
     4424 
     4425        if cinf_C == cinf_E: 
     4426            return n 
     4427        # otherwise they have different number of connected component and we have to adjust for this 
     4428        elif cinf_C > cinf_E: 
     4429            if ZZ(n_plus) % 2 == 0 and ZZ(n_minus) % 2 == 0: 
     4430                return n // 2 
     4431            else: 
     4432                return n 
     4433        else: #if cinf_C < cinf_E: 
     4434            if q_plus.denominator() % 2 == 0 and q_minus.denominator() % 2 == 0: 
     4435                return n 
     4436            else: 
     4437                return n*2 
     4438 
    44124439    def _shortest_paths(self): 
    44134440        r""" 
    44144441        Technical internal function that returns the list of isogenies 
     
    44244451        OUTPUT: 
    44254452 
    44264453        list, dict 
    4427              
     4454 
    44284455        EXAMPLES:: 
    44294456 
    44304457            sage: EllipticCurve('11a1')._shortest_paths() 
     
    44834510        # to the optimal curve. 
    44844511        v = [deg for num, deg in v.iteritems() if deg]  # get just the degrees 
    44854512        return arith.LCM(v) 
    4486          
    4487          
    44884513 
    44894514    ########################################################## 
    44904515    # Galois Representations