@@ -2310,8 +2310,8 @@ def gens(self, proof=None, **kwds):
23102310 over Rational Field
23112311 sage: E1.gens() # random (if database not used)
23122312 [(-400 : 8000 : 1), (0 : -8000 : 1)]
2313- sage: E1.gens(algorithm="pari")
2314- [(-400 : 8000 : 1), (0 : 0 : 1)]
2313+ sage: E1.gens(algorithm="pari") #random
2314+ [(-400 : 8000 : 1), (0 : -8000 : 1)]
23152315
23162316 """
23172317 if proof is None :
@@ -2965,86 +2965,119 @@ def point_search(self, height_limit, verbose=False, rank_bound=None):
29652965 points = self .saturation (points , verbose = verbose )[0 ]
29662966 return points
29672967
2968- def selmer_rank (self ):
2968+ def selmer_rank (self , algorithm = "pari" ):
29692969 r"""
2970- The rank of the 2-Selmer group of the curve.
2970+ Return the rank of the 2-Selmer group of the curve.
29712971
2972- EXAMPLES: The following is the curve 960D1, which has rank 0, but
2973- Sha of order 4.
2972+ INPUT:
29742973
2975- ::
2974+ - ``algorithm`` -- (default:``'pari'``)
2975+ either ``'pari'`` or ``'mwrank'``
29762976
2977- sage: E = EllipticCurve([0, -1, 0, -900, -10098])
2978- sage: E.selmer_rank()
2979- 3
2980-
2981- Here the Selmer rank is equal to the 2-torsion rank (=1) plus
2982- the 2-rank of Sha (=2), and the rank itself is zero::
2977+ EXAMPLES:
2978+ This example has rank 1, Sha[2] of order 4 and
2979+ a single rational 2-torsion point::
29832980
2984- sage: E.rank()
2985- 0
2981+ sage: E = EllipticCurve([1, 1, 1, 508, -2551])
2982+ sage: E.selmer_rank()
2983+ 4
2984+ sage: E.selmer_rank(algorithm="mwrank")
2985+ 4
29862986
2987- In contrast, for the curve 571A, also with rank 0 and Sha of
2988- order 4, we get a worse bound ::
2987+ The following is the curve 960d1, which has rank 0, but
2988+ Sha of order 4 ::
29892989
2990- sage: E = EllipticCurve([0, -1, 1 , -929 , -10595 ])
2990+ sage: E = EllipticCurve([0, -1, 0 , -900 , -10098 ])
29912991 sage: E.selmer_rank()
2992- 2
2993- sage: E.rank_bound( )
2994- 2
2992+ 3
2993+ sage: E.selmer_rank(algorithm="mwrank" )
2994+ 3
29952995
2996- To establish that the rank is in fact 0 in this case, we would
2997- need to carry out a higher descent::
2996+ This curve has rank 1, and 4 elements in Sha[2].
2997+ Yet the order of Sha is 16, so that group is the product
2998+ of two cyclic groups of order 4::
29982999
2999- sage: E.three_selmer_rank() # optional - magma
3000- 0
3000+ sage: E = EllipticCurve([1, 0, 0, -150752, -22541610])
3001+ sage: E.selmer_rank()
3002+ 4
30013003
3002- Or use the L-function to compute the analytic rank ::
3004+ Instead in this last example of rank 0, Sha is a product of four cyclic groups of order 2 ::
30033005
3004- sage: E.rank(only_use_mwrank=False)
3006+ sage: E = EllipticCurve([1, 0, 0, -49280, -4214808])
3007+ sage: E.selmer_rank()
3008+ 5
3009+ sage: E.rank()
30053010 0
30063011 """
30073012 try :
30083013 return self .__selmer_rank
30093014 except AttributeError :
3010- C = self .mwrank_curve ()
3011- self .__selmer_rank = C .selmer_rank ()
3012- return self .__selmer_rank
3015+ if algorithm == "pari" :
3016+ ep = self .pari_curve ()
3017+ lower , upper , s , pts = ep .ellrank ()
3018+ T = self .torsion_subgroup ().invariants ()
3019+ tor = sum (x % 2 == 0 for x in T )
3020+ return upper + tor + s
3021+ elif algorithm == "mwrank" :
3022+ C = self .mwrank_curve ()
3023+ self .__selmer_rank = C .selmer_rank ()
3024+ return self .__selmer_rank
3025+ else :
3026+ raise ValueError (f"unknown { algorithm = } " )
30133027
3014- def rank_bound (self ):
3028+ def rank_bound (self , algorithm = "pari" ):
30153029 r"""
3016- Upper bound on the rank of the curve, computed using
3017- 2-descent.
3030+ Return the upper bound on the rank of the curve,
3031+ computed using a 2-descent.
3032+
3033+ INPUT:
3034+
3035+ - ``algorithm`` -- (default:``'pari'``)
3036+ either ``'pari'`` or ``'mwrank'``
30183037
30193038 In many cases, this is the actual rank of the
3020- curve. If the curve has no 2-torsion it is the same as the
3021- 2-selmer rank.
3039+ curve.
3040+
3041+ EXAMPLES::
30223042
3023- EXAMPLES: The following is the curve 960D1, which has rank 0, but
3024- Sha of order 4.
3043+ sage: E = EllipticCurve("389a1")
3044+ sage: E.rank_bound()
3045+ 2
30253046
3026- ::
3047+ The following is the curve 571a1, which has
3048+ rank 0, but Sha of order 4, yet pari, using the Cassels
3049+ pairing is able to show that the rank is 0.
3050+ The 2-descent in mwrank only determines a weaker upper bound::
30273051
3028- sage: E = EllipticCurve([0, -1, 0 , -900 , -10098 ])
3052+ sage: E = EllipticCurve([0, -1, 1 , -929 , -10595 ])
30293053 sage: E.rank_bound()
30303054 0
3055+ sage: E.rank_bound(algorithm="mwrank")
3056+ 2
30313057
3032- It gives 0 instead of 2, because it knows Sha is nontrivial. In
3033- contrast, for the curve 571A, also with rank 0 and Sha of order 4,
3034- we get a worse bound::
3058+ In the following last example, both algorithm only determine a rank bound larger than the actual rank::
30353059
3036- sage: E = EllipticCurve([0, - 1, 1, -929 , -10595 ])
3060+ sage: E = EllipticCurve([1, 1, 1, -896670 , -327184905 ])
30373061 sage: E.rank_bound()
30383062 2
3039- sage: E.rank(only_use_mwrank=False) # uses L-function
3063+ sage: E.rank_bound(algorithm="mwrank")
3064+ 2
3065+ sage: E.rank(only_use_mwrank=False) # uses L-function
30403066 0
30413067 """
30423068 try :
30433069 return self .__rank_bound
30443070 except AttributeError :
3045- C = self .mwrank_curve ()
3046- self .__rank_bound = C .rank_bound ()
3047- return self .__rank_bound
3071+ if algorithm == "pari" :
3072+ ep = self .pari_curve ()
3073+ lower , upper , s , pts = ep .ellrank ()
3074+ return upper
3075+ elif algorithm == "mwrank" :
3076+ C = self .mwrank_curve ()
3077+ self .__rank_bound = C .rank_bound ()
3078+ return self .__rank_bound
3079+ else :
3080+ raise ValueError (f"unknown { algorithm = } " )
30483081
30493082 def an (self , n ):
30503083 r"""
0 commit comments