Descent on elliptic curves over \(\QQ\) with a 2-isogeny - Elliptic curves

Skip to content
Back to top
View this page
Edit this page

# Descent on elliptic curves over \(\QQ\) with a 2-isogeny

sage.schemes.elliptic_curves.descent_two_isogeny.test_els(a, b, c, d, e)

  Doctest function for cdef int everywhere_locally_soluble(mpz_t, mpz_t, mpz_t, mpz_t, mpz_t).

  EXAMPLES:

  Sage

      sage: from sage.schemes.elliptic_curves.descent_two_isogeny import test_els
      sage: for _ in range(1000):
      ....:     a,b,c,d,e = randint(1,1000), randint(1,1000), randint(1,1000), randint(1,1000), randint(1,1000)
      ....:     if pari.Pol([a,b,c,d,e]).hyperellratpoints(1000, 1):
      ....:         try:
      ....:             if not test_els(a,b,c,d,e):
      ....:                 print("This never happened", a, b, c, d, e)
      ....:         except ValueError:
      ....:             continue

  Python

      >>> from sage.all import *
      >>> from sage.schemes.elliptic_curves.descent_two_isogeny import test_els
      >>> for _ in range(Integer(1000)):
      ...     a,b,c,d,e = randint(Integer(1),Integer(1000)), randint(Integer(1),Integer(1000)), randint(Integer(1),Integer(1000)), randint(Integer(1),Integer(1000)), randint(Integer(1),Integer(1000))
      ...     if pari.Pol([a,b,c,d,e]).hyperellratpoints(Integer(1000), Integer(1)):
      ...         try:
      ...             if not test_els(a,b,c,d,e):
      ...                 print("This never happened", a, b, c, d, e)
      ...         except ValueError:
      ...             continue

sage.schemes.elliptic_curves.descent_two_isogeny.test_padic_square(a, p)

  Doctest function for cdef int padic_square(mpz_t, unsigned long).

  EXAMPLES:

  Sage

      sage: from sage.schemes.elliptic_curves.descent_two_isogeny import test_padic_square as ps
      sage: for i in [1..300]:
      ....:     for p in prime_range(100):
      ....:          if Qp(p)(i).is_square() != bool(ps(i,p)):
      ....:              print(i, p)

  Python

      >>> from sage.all import *
      >>> from sage.schemes.elliptic_curves.descent_two_isogeny import test_padic_square as ps
      >>> for i in (ellipsis_range(Integer(1),Ellipsis,Integer(300))):
      ...     for p in prime_range(Integer(100)):
      ...          if Qp(p)(i).is_square() != bool(ps(i,p)):
      ...              print(i, p)

sage.schemes.elliptic_curves.descent_two_isogeny.test_qpls(a, b, c, d, e, p)

  Testing function for Qp_soluble.

  EXAMPLES:

  Sage

      sage: from sage.schemes.elliptic_curves.descent_two_isogeny import test_qpls as tq
      sage: tq(1,2,3,4,5,7)
      1

  Python

      >>> from sage.all import *
      >>> from sage.schemes.elliptic_curves.descent_two_isogeny import test_qpls as tq
      >>> tq(Integer(1),Integer(2),Integer(3),Integer(4),Integer(5),Integer(7))
      1

sage.schemes.elliptic_curves.descent_two_isogeny.test_valuation(a, p)

  Doctest function for cdef long valuation(mpz_t, mpz_t).

  EXAMPLES:

  Sage

      sage: from sage.schemes.elliptic_curves.descent_two_isogeny import test_valuation as tv
      sage: for i in [1..20]:
      ....:     print('{:>10} {} {} {}'.format(str(factor(i)), tv(i,2), tv(i,3), tv(i,5)))
               1 0 0 0
               2 1 0 0
               3 0 1 0
             2^2 2 0 0
               5 0 0 1
           2 * 3 1 1 0
               7 0 0 0
             2^3 3 0 0
             3^2 0 2 0
           2 * 5 1 0 1
              11 0 0 0
         2^2 * 3 2 1 0
              13 0 0 0
           2 * 7 1 0 0
           3 * 5 0 1 1
             2^4 4 0 0
              17 0 0 0
         2 * 3^2 1 2 0
              19 0 0 0
         2^2 * 5 2 0 1

  Python

      >>> from sage.all import *
      >>> from sage.schemes.elliptic_curves.descent_two_isogeny import test_valuation as tv
      >>> for i in (ellipsis_range(Integer(1),Ellipsis,Integer(20))):
      ...     print('{:>10} {} {} {}'.format(str(factor(i)), tv(i,Integer(2)), tv(i,Integer(3)), tv(i,Integer(5))))
               1 0 0 0
               2 1 0 0
               3 0 1 0
             2^2 2 0 0
               5 0 0 1
           2 * 3 1 1 0
               7 0 0 0
             2^3 3 0 0
             3^2 0 2 0
           2 * 5 1 0 1
              11 0 0 0
         2^2 * 3 2 1 0
              13 0 0 0
           2 * 7 1 0 0
           3 * 5 0 1 1
             2^4 4 0 0
              17 0 0 0
         2 * 3^2 1 2 0
              19 0 0 0
         2^2 * 5 2 0 1

sage.schemes.elliptic_curves.descent_two_isogeny.two_descent_by_two_isogeny(E, global_limit_small=10, global_limit_large=10000, verbosity=0, selmer_only=0, proof=1)

  Given an elliptic curve E with a two-isogeny phi : E –> E’ and dual isogeny phi’, runs a two-isogeny descent on E, returning n1, n2, n1’ and n2’. Here n1 is the number of quartic covers found with a rational point, and n2 is the number which are ELS.

  EXAMPLES:

  Sage

      sage: from sage.schemes.elliptic_curves.descent_two_isogeny import two_descent_by_two_isogeny
      sage: E = EllipticCurve('14a')
      sage: n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny(E)
      sage: log(n1,2) + log(n1_prime,2) - 2 # the rank
      0
      sage: E = EllipticCurve('65a')
      sage: n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny(E)
      sage: log(n1,2) + log(n1_prime,2) - 2 # the rank
      1

      sage: # needs sage.symbolic
      sage: x,y = var('x,y')
      sage: E = EllipticCurve(y^2 == x^3 + x^2 - 25*x + 39)
      sage: n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny(E)
      sage: log(n1,2) + log(n1_prime,2) - 2  # the rank
      2
      sage: E = EllipticCurve(y^2 + x*y + y == x^3 - 131*x + 558)
      sage: n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny(E)
      sage: log(n1,2) + log(n1_prime,2) - 2  # the rank
      3

  Python

      >>> from sage.all import *
      >>> from sage.schemes.elliptic_curves.descent_two_isogeny import two_descent_by_two_isogeny
      >>> E = EllipticCurve('14a')
      >>> n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny(E)
      >>> log(n1,Integer(2)) + log(n1_prime,Integer(2)) - Integer(2) # the rank
      0
      >>> E = EllipticCurve('65a')
      >>> n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny(E)
      >>> log(n1,Integer(2)) + log(n1_prime,Integer(2)) - Integer(2) # the rank
      1

      >>> # needs sage.symbolic
      >>> x,y = var('x,y')
      >>> E = EllipticCurve(y**Integer(2) == x**Integer(3) + x**Integer(2) - Integer(25)*x + Integer(39))
      >>> n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny(E)
      >>> log(n1,Integer(2)) + log(n1_prime,Integer(2)) - Integer(2)  # the rank
      2
      >>> E = EllipticCurve(y**Integer(2) + x*y + y == x**Integer(3) - Integer(131)*x + Integer(558))
      >>> n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny(E)
      >>> log(n1,Integer(2)) + log(n1_prime,Integer(2)) - Integer(2)  # the rank
      3

  Using the verbosity option:

  Sage

      sage: E = EllipticCurve('14a')
      sage: two_descent_by_two_isogeny(E, verbosity=1)
      2-isogeny
      Results:
      2 <= #E(Q)/phi'(E'(Q)) <= 2
      2 <= #E'(Q)/phi(E(Q)) <= 2
      #Sel^(phi')(E'/Q) = 2
      #Sel^(phi)(E/Q) = 2
      1 <= #Sha(E'/Q)[phi'] <= 1
      1 <= #Sha(E/Q)[phi] <= 1
      1 <= #Sha(E/Q)[2], #Sha(E'/Q)[2] <= 1
      0 <= rank of E(Q) = rank of E'(Q) <= 0
      (2, 2, 2, 2)

  [Python]

      >>> from sage.all import *
      >>> E = EllipticCurve('14a')
      >>> two_descent_by_two_isogeny(E, verbosity=Integer(1))
      2-isogeny
      Results:
      2 <= #E(Q)/phi'(E'(Q)) <= 2
      2 <= #E'(Q)/phi(E(Q)) <= 2
      #Sel^(phi')(E'/Q) = 2
      #Sel^(phi)(E/Q) = 2
      1 <= #Sha(E'/Q)[phi'] <= 1
      1 <= #Sha(E/Q)[phi] <= 1
      1 <= #Sha(E/Q)[2], #Sha(E'/Q)[2] <= 1
      0 <= rank of E(Q) = rank of E'(Q) <= 0
      (2, 2, 2, 2)

  Handling curves whose discriminants involve larger than wordsize primes:

  Sage

      sage: E = EllipticCurve('14a')
      sage: E = E.quadratic_twist(next_prime(10^20))
      sage: E
      Elliptic Curve defined by y^2 = x^3 + x^2 + 716666666666666667225666666666666666775672*x - 391925925925925926384240370370370370549019837037037037060249356 over Rational Field
      sage: E.discriminant().factor()
      -1 * 2^18 * 7^3 * 100000000000000000039^6
      sage: log(100000000000000000039.0, 2.0)
      66.438...
      sage: n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny(E)
      sage: log(n1,2) + log(n1_prime,2) - 2 # the rank
      0

  Python

      >>> from sage.all import *
      >>> E = EllipticCurve('14a')
      >>> E = E.quadratic_twist(next_prime(Integer(10)**Integer(20)))
      >>> E
      Elliptic Curve defined by y^2 = x^3 + x^2 + 716666666666666667225666666666666666775672*x - 391925925925925926384240370370370370549019837037037037060249356 over Rational Field
      >>> E.discriminant().factor()
      -1 * 2^18 * 7^3 * 100000000000000000039^6
      >>> log(RealNumber('100000000000000000039.0'), RealNumber('2.0'))
      66.438...
      >>> n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny(E)
      >>> log(n1,Integer(2)) + log(n1_prime,Integer(2)) - Integer(2) # the rank
      0

sage.schemes.elliptic_curves.descent_two_isogeny.two_descent_by_two_isogeny_work(c, d, global_limit_small=10, global_limit_large=10000, verbosity=0, selmer_only=0, proof=1)

  Do all the work in doing a two-isogeny descent.

  EXAMPLES:

  Sage

      sage: from sage.schemes.elliptic_curves.descent_two_isogeny import two_descent_by_two_isogeny_work
      sage: n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny_work(13,128)
      sage: log(n1,2) + log(n1_prime,2) - 2 # the rank
      0
      sage: n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny_work(1,-16)
      sage: log(n1,2) + log(n1_prime,2) - 2 # the rank
      1
      sage: n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny_work(10,8)
      sage: log(n1,2) + log(n1_prime,2) - 2 # the rank
      2
      sage: n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny_work(85,320)
      sage: log(n1,2) + log(n1_prime,2) - 2 # the rank
      3

  Python

      >>> from sage.all import *
      >>> from sage.schemes.elliptic_curves.descent_two_isogeny import two_descent_by_two_isogeny_work
      >>> n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny_work(Integer(13),Integer(128))
      >>> log(n1,Integer(2)) + log(n1_prime,Integer(2)) - Integer(2) # the rank
      0
      >>> n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny_work(Integer(1),-Integer(16))
      >>> log(n1,Integer(2)) + log(n1_prime,Integer(2)) - Integer(2) # the rank
      1
      >>> n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny_work(Integer(10),Integer(8))
      >>> log(n1,Integer(2)) + log(n1_prime,Integer(2)) - Integer(2) # the rank
      2
      >>> n1, n2, n1_prime, n2_prime = two_descent_by_two_isogeny_work(Integer(85),Integer(320))
      >>> log(n1,Integer(2)) + log(n1_prime,Integer(2)) - Integer(2) # the rank
      3