Esempio n. 1
0
 def _load(self, path, filename):
     print filename
     i = 0
     while filename[i].isalpha():
         i += 1
     j = len(filename) - 1
     while filename[j].isalpha() or filename[j] in [".", "_"]:
         j -= 1
     S = [eval(z) for z in filename[i:j + 1].split("-")]
     S.sort()
     data = open(path + "/" + filename).read()
     data = data.replace("^", "**")
     x = PolynomialRing(RationalField(), 'x').gen()
     v = eval(data)
     s = tuple(S)
     if self.root.has_key(s):
         self.root[s] += v
         self.root[s].sort()
     else:
         self.root[s] = v
Esempio n. 2
0
 def _load(self, path, filename):
     print(filename)
     i = 0
     while filename[i].isalpha():
         i += 1
     j = len(filename) - 1
     while filename[j].isalpha() or filename[j] in [".", "_"]:
         j -= 1
     S = sorted([eval(z) for z in filename[i:j + 1].split("-")])
     with open(path + "/" + filename) as f:
         data = f.read()
     data = data.replace("^", "**")
     x = PolynomialRing(RationalField(), 'x').gen()  # used next line
     v = eval(data)
     s = tuple(S)
     if s in self.root:
         self.root[s] += v
         self.root[s].sort()
     else:
         self.root[s] = v
Esempio n. 3
0
    def _init(self, path):
        """
        Create the database from scratch from the PARI files on John Jones's
        web page, downloaded (e.g., via wget) to a local directory, which
        is specified as path above.

        INPUT:


        -  ``path`` - (default works on William Stein install.)
           path must be the path to Jones's Number_Fields directory
           http://hobbes.la.asu.edu/Number_Fields These files should have
           been downloaded using wget.


        EXAMPLES: This is how to create the database from scratch, assuming
        that the number fields are in the default directory above: From a
        cold start of Sage::

                sage: J = JonesDatabase()
                sage: J._init()   # not tested
                ...

        This takes about 5 seconds.
        """
        from sage.misc.misc import sage_makedirs
        n = 0
        x = PolynomialRing(RationalField(), 'x').gen()
        self.root = {}
        self.root[tuple([])] = [x - 1]
        if not os.path.exists(path):
            raise IOError("Path %s does not exist." % path)
        for X in os.listdir(path):
            if X[-4:] == "solo":
                Z = path + "/" + X
                print(X)
                for Y in os.listdir(Z):
                    if Y[-3:] == ".gp":
                        self._load(Z, Y)
        sage_makedirs(JONESDATA)
        save(self.root, JONESDATA + "/jones.sobj")
Esempio n. 4
0
def ExponentialCycleIndexSeries(R=RationalField()):
    r"""
    Return the cycle index series of the species `E` of sets.

    This cycle index satisfies

    .. MATH::

        Z_{E} = \sum_{n \geq 0} \sum_{\lambda \vdash n}
        \frac{p_{\lambda}}{z_{\lambda}}.

    EXAMPLES::

        sage: from sage.combinat.species.generating_series import ExponentialCycleIndexSeries
        sage: ExponentialCycleIndexSeries().coefficients(5)
        [p[], p[1], 1/2*p[1, 1] + 1/2*p[2], 1/6*p[1, 1, 1] + 1/2*p[2, 1]
         + 1/3*p[3], 1/24*p[1, 1, 1, 1] + 1/4*p[2, 1, 1] + 1/8*p[2, 2]
         + 1/3*p[3, 1] + 1/4*p[4]]
    """
    CIS = CycleIndexSeriesRing(R)
    return CIS(_exp_gen(R))
Esempio n. 5
0
    def __init__(self,
                 g,
                 weights=None,
                 field=None,
                 phantom_edge=None,
                 no_symmetry=False):

        if g.oriented and g.is_degenerate:
            raise NotImplementedError(
                "degenerate oriented graphs not supported.")

        self._graph = copy(g)
        self._flag_cls = type(g)

        if weights is None:
            self._weights = None
        else:
            if len(weights) != g.n:
                raise ValueError
            self._weights = weights

        if field is None:
            self._field = RationalField()
        else:
            self._field = field

        if not phantom_edge is None:
            # check edge is valid; will get an Exception if not.
            h = copy(g)
            h.add_edge(phantom_edge)
            self._phantom_edge = phantom_edge

        # Only make use of symmetry when all the conditions are right...

        self._use_symmetry = False
        if field is None and weights is None and phantom_edge is None:
            if g.n > 4 and not no_symmetry:
                # Should probably allow OrientedGraphFlag
                if type(g) is GraphFlag or type(g) is OrientedGraphFlag:
                    self._use_symmetry = True
Esempio n. 6
0
    def twist_values(self, s, dmin, dmax):
        r"""
        Return values of `L(E, s, \chi_d)` for each quadratic
        character `\chi_d` for `d_{\min} \leq d \leq d_{\max}`.

        .. note::

            The L-series is normalized so that the center of the
            critical strip is 1.

        INPUT:

        - ``s`` -- complex numbers

        - ``dmin`` -- integer

        - ``dmax`` -- integer

        OUTPUT:

        - list of pairs `(d, L(E, s, \chi_d))`

        EXAMPLES::

            sage: E = EllipticCurve('37a')
            sage: vals = E.lseries().twist_values(1, -12, -4)
            sage: vals  # abs tol 1e-17
            [(-11, 1.47824342), (-8, 8.9590946e-18), (-7, 1.85307619), (-4, 2.45138938)]
            sage: F = E.quadratic_twist(-8)
            sage: F.rank()
            1
            sage: F = E.quadratic_twist(-7)
            sage: F.rank()
            0
        """
        from sage.lfunctions.lcalc import lcalc
        return lcalc.twist_values(s - RationalField()('1/2'),
                                  dmin,
                                  dmax,
                                  L=self.__E)
Esempio n. 7
0
def _cl_term(n, R = RationalField()):
    r"""
    Compute the order-n term of the cycle index series of the virtual species `\Omega`,
    the compositional inverse of the species `E^{+}` of nonempty sets.

    EXAMPLES::

        sage: from sage.combinat.species.generating_series import _cl_term
        sage: [_cl_term(i) for i in range(4)]
        [0, p[1], -1/2*p[1, 1] - 1/2*p[2], 1/3*p[1, 1, 1] - 1/3*p[3]]
    """
    n = Integer(n)  # check that n is an integer

    p = SymmetricFunctions(R).power()

    res = p.zero()
    if n == 1:
        res = p([1])
    elif n > 1:
        res = 1/n * ((-1)**(n-1) * p([1])**n - sum(d * p([n // d]).plethysm(_cl_term(d, R)) for d in divisors(n)[:-1]))

    return res
Esempio n. 8
0
 def _change_basis(self,x):
     v = x.parts()
     tmp = self._changebasismatrix * Matrix(RationalField(),2,1,v)
     return tmp[0,0],tmp[1,0]
Esempio n. 9
0
    def L_ratio(self):
        r"""
        Returns the ratio `L(E,1)/\Omega` as an exact rational
        number. The result is \emph{provably} correct if the Manin
        constant of the associated optimal quotient is `\leq 2`.  This
        hypothesis on the Manin constant is true for all semistable
        curves (i.e., squarefree conductor), by a theorem of Mazur
        from his \emph{Rational Isogenies of Prime Degree} paper.

        EXAMPLES::

            sage: E = EllipticCurve([0, -1, 1, -10, -20])   # 11A  = X_0(11)
            sage: E.lseries().L_ratio()
            1/5
            sage: E = EllipticCurve([0, -1, 1, 0, 0])       # X_1(11)
            sage: E.lseries().L_ratio()
            1/25
            sage: E = EllipticCurve([0, 0, 1, -1, 0])       # 37A  (rank 1)
            sage: E.lseries().L_ratio()
            0
            sage: E = EllipticCurve([0, 1, 1, -2, 0])       # 389A (rank 2)
            sage: E.lseries().L_ratio()
            0
            sage: E = EllipticCurve([0, 0, 1, -38, 90])     # 361A (CM curve))
            sage: E.lseries().L_ratio()
            0
            sage: E = EllipticCurve([0,-1,1,-2,-1])         # 141C (13-isogeny)
            sage: E.lseries().L_ratio()
            1
            sage: E = EllipticCurve(RationalField(), [1, 0, 0, 1/24624, 1/886464])
            sage: E.lseries().L_ratio()
            2

        See :trac:`3651` and :trac:`15299`::

            sage: EllipticCurve([0,0,0,-193^2,0]).sha().an()
            4
            sage: EllipticCurve([1, 0, 1, -131, 558]).sha().an()  # long time
            1.00000000000000

        ALGORITHM: Compute the root number.  If it is -1 then L(E,s)
        vanishes to odd order at 1, hence vanishes.  If it is +1, use
        a result about modular symbols and Mazur's "Rational Isogenies"
        paper to determine a provably correct bound (assuming Manin
        constant is <= 2) so that we can determine whether L(E,1) = 0.

        AUTHOR: William Stein, 2005-04-20.
        """
        try:
            return self.__lratio
        except AttributeError:
            pass

        if not self.__E.is_minimal():
            self.__lratio = self.__E.minimal_model().lseries().L_ratio()
            return self.__lratio

        QQ = RationalField()
        if self.__E.root_number() == -1:
            self.__lratio = QQ.zero()
            return self.__lratio

        # Even root number.  Decide if L(E,1) = 0.  If E is a modular
        # *OPTIMAL* quotient of J_0(N) elliptic curve, we know that T *
        # L(E,1)/omega is an integer n, where T is the order of the
        # image of the rational torsion point (0)-(oo) in E(Q), and
        # omega is the least real Neron period.  (This is proved in my
        # Ph.D. thesis, but is probably well known.)  We can easily
        # compute omega to very high precision using AGM.  So to prove
        # that L(E,1) = 0 we compute T/omega * L(E,1) to sufficient
        # precision to determine it as an integer.  If eps is the
        # error in computation of L(E,1), then the error in computing
        # the product is (2T/Omega_E) * eps, and we need this to be
        # less than 0.5, i.e.,
        #          (2T/Omega_E) * eps < 0.5,
        # so
        #          eps < 0.5 * Omega_E / (2T) = Omega_E / (4*T).
        #
        # Since in general E need not be optimal, we have to choose
        # eps = Omega_E/(8*t*B), where t is the exponent of E(Q)_tor,
        # and is a multiple of the degree of an isogeny between E
        # and the optimal curve.
        #
        # NOTES: We *do* have to worry about the Manin constant, since
        # we are using the Neron model to compute omega, not the
        # newform.  My theorem replaces the omega above by omega/c,
        # where c is the Manin constant, and the bound must be
        # correspondingly smaller.  If the level is square free, then
        # the Manin constant is 1 or 2, so there's no problem (since
        # we took 8 instead of 4 in the denominator).  If the level
        # is divisible by a square, then the Manin constant could
        # be a divisible by an arbitrary power of that prime, except
        # that Edixhoven claims the primes that appear are <= 7.

        t = self.__E.torsion_subgroup().order()
        omega = self.__E.period_lattice().basis()[0]
        d = self.__E._multiple_of_degree_of_isogeny_to_optimal_curve()
        C = 8*d*t
        eps = omega / C

        sqrtN = 2*int(sqrt(self.__E.conductor()))
        k = sqrtN + 10
        while True:
            L1, error_bound = self.at1(k)
            if error_bound < eps:
                n = int(round(L1*C/omega))
                quo = QQ((n,C))
                self.__lratio = quo / self.__E.real_components()
                return self.__lratio
            k += sqrtN
            misc.verbose("Increasing precision to %s terms."%k)
Esempio n. 10
0
 def sage(self, var="x", base_field=RationalField()):
     from sage.rings.all import PolynomialRing, QQ, Integer
     PP = PolynomialRing(QQ, var)
     return PP([Integer(val) for val in self])
Esempio n. 11
0
 def sage(self, var="x", base_field=RationalField()):
     from sage.rings.all import PolynomialRing, QQ
     PP = PolynomialRing(QQ, var)
     return PP(self)
Esempio n. 12
0
 def __init__(self):
     self._field = RationalField()
     self._flag_cls = None
Esempio n. 13
0
 def __init__(self, variant=False):
     self._variant = variant
     self._field = RationalField()
     self._flag_cls = ThreeGraphFlag
    def coleman_integrals_on_basis(self, P, Q, algorithm=None):
        r"""
        Computes the Coleman integrals `\{\int_P^Q x^i dx/2y \}_{i=0}^{2g-1}`

        INPUT:

        - P point on self
        - Q point on self
        - algorithm (optional) = None (uses Frobenius) or teichmuller (uses Teichmuller points)

        OUTPUT:

        the Coleman integrals `\{\int_P^Q x^i dx/2y \}_{i=0}^{2g-1}`

        EXAMPLES::

            sage: K = pAdicField(11, 5)
            sage: x = polygen(K)
            sage: C = HyperellipticCurve(x^5 + 33/16*x^4 + 3/4*x^3 + 3/8*x^2 - 1/4*x + 1/16)
            sage: P = C.lift_x(2)
            sage: Q = C.lift_x(3)
            sage: C.coleman_integrals_on_basis(P, Q)
            (10*11 + 6*11^3 + 2*11^4 + O(11^5), 11 + 9*11^2 + 7*11^3 + 9*11^4 + O(11^5), 3 + 10*11 + 5*11^2 + 9*11^3 + 4*11^4 + O(11^5), 3 + 11 + 5*11^2 + 4*11^4 + O(11^5))
            sage: C.coleman_integrals_on_basis(P, Q, algorithm='teichmuller')
            (10*11 + 6*11^3 + 2*11^4 + O(11^5), 11 + 9*11^2 + 7*11^3 + 9*11^4 + O(11^5), 3 + 10*11 + 5*11^2 + 9*11^3 + 4*11^4 + O(11^5), 3 + 11 + 5*11^2 + 4*11^4 + O(11^5))

        ::

            sage: K = pAdicField(11,5)
            sage: x = polygen(K)
            sage: C = HyperellipticCurve(x^5 + 33/16*x^4 + 3/4*x^3 + 3/8*x^2 - 1/4*x + 1/16)
            sage: P = C.lift_x(11^(-2))
            sage: Q = C.lift_x(3*11^(-2))
            sage: C.coleman_integrals_on_basis(P, Q)
            (3*11^3 + 7*11^4 + 4*11^5 + 7*11^6 + 5*11^7 + O(11^8), 3*11 + 10*11^2 + 8*11^3 + 9*11^4 + 7*11^5 + O(11^6), 4*11^-1 + 2 + 6*11 + 6*11^2 + 7*11^3 + O(11^4), 11^-3 + 6*11^-2 + 2*11^-1 + 2 + O(11^2))

        ::

            sage: R = C(0,1/4)
            sage: a = C.coleman_integrals_on_basis(P,R)  # long time (7s on sage.math, 2011)
            sage: b = C.coleman_integrals_on_basis(R,Q)  # long time (9s on sage.math, 2011)
            sage: c = C.coleman_integrals_on_basis(P,Q)  # long time
            sage: a+b == c  # long time
            True

        ::

            sage: R.<x> = QQ['x']
            sage: H = HyperellipticCurve(x^3-10*x+9)
            sage: K = Qp(5,8)
            sage: HK = H.change_ring(K)
            sage: S = HK(1,0)
            sage: P = HK(0,3)
            sage: T = HK(0,1,0)
            sage: Q = HK.lift_x(5^-2)
            sage: R = HK.lift_x(4*5^-2)
            sage: HK.coleman_integrals_on_basis(S,P)
            (2*5^2 + 5^4 + 5^5 + 3*5^6 + 3*5^7 + 2*5^8 + O(5^9), 5 + 2*5^2 + 4*5^3 + 2*5^4 + 3*5^6 + 4*5^7 + 2*5^8 + O(5^9))
            sage: HK.coleman_integrals_on_basis(T,P)
            (2*5^2 + 5^4 + 5^5 + 3*5^6 + 3*5^7 + 2*5^8 + O(5^9), 5 + 2*5^2 + 4*5^3 + 2*5^4 + 3*5^6 + 4*5^7 + 2*5^8 + O(5^9))
            sage: HK.coleman_integrals_on_basis(P,S) == -HK.coleman_integrals_on_basis(S,P)
            True
            sage: HK.coleman_integrals_on_basis(S,Q)
            (4*5 + 4*5^2 + 4*5^3 + O(5^4), 5^-1 + O(5^3))
            sage: HK.coleman_integrals_on_basis(Q,R)
            (4*5 + 2*5^2 + 2*5^3 + 2*5^4 + 5^5 + 5^6 + 5^7 + 3*5^8 + O(5^9), 2*5^-1 + 4 + 4*5 + 4*5^2 + 4*5^3 + 2*5^4 + 3*5^5 + 2*5^6 + O(5^7))
            sage: HK.coleman_integrals_on_basis(S,R) == HK.coleman_integrals_on_basis(S,Q) + HK.coleman_integrals_on_basis(Q,R)
            True
            sage: HK.coleman_integrals_on_basis(T,T)
            (0, 0)
            sage: HK.coleman_integrals_on_basis(S,T)
            (0, 0)

        AUTHORS:

        - Robert Bradshaw (2007-03): non-Weierstrass points
        - Jennifer Balakrishnan and Robert Bradshaw (2010-02): Weierstrass points
        """
        import sage.schemes.hyperelliptic_curves.monsky_washnitzer as monsky_washnitzer
        from sage.misc.profiler import Profiler
        prof = Profiler()
        prof("setup")
        K = self.base_ring()
        p = K.prime()
        prec = K.precision_cap()
        g = self.genus()
        dim = 2 * g
        V = VectorSpace(K, dim)
        #if P or Q is Weierstrass, use the Frobenius algorithm
        if self.is_weierstrass(P):
            if self.is_weierstrass(Q):
                return V(0)
            else:
                PP = None
                QQ = Q
                TP = None
                TQ = self.frobenius(Q)
        elif self.is_weierstrass(Q):
            PP = P
            QQ = None
            TQ = None
            TP = self.frobenius(P)
        elif self.is_same_disc(P, Q):
            return self.tiny_integrals_on_basis(P, Q)
        elif algorithm == 'teichmuller':
            prof("teichmuller")
            PP = TP = self.teichmuller(P)
            QQ = TQ = self.teichmuller(Q)
            evalP, evalQ = TP, TQ
        else:
            prof("frobPQ")
            TP = self.frobenius(P)
            TQ = self.frobenius(Q)
            PP, QQ = P, Q
        prof("tiny integrals")
        if TP is None:
            P_to_TP = V(0)
        else:
            if TP is not None:
                TPv = (TP[0]**g / TP[1]).valuation()
                xTPv = TP[0].valuation()
            else:
                xTPv = TPv = +Infinity
            if TQ is not None:
                TQv = (TQ[0]**g / TQ[1]).valuation()
                xTQv = TQ[0].valuation()
            else:
                xTQv = TQv = +Infinity
            offset = (2 * g - 1) * max(TPv, TQv)
            if offset == +Infinity:
                offset = (2 * g - 1) * min(TPv, TQv)
            if (offset > prec and (xTPv < 0 or xTQv < 0) and
                (self.residue_disc(P) == self.change_ring(GF(p))(0, 1, 0)
                 or self.residue_disc(Q) == self.change_ring(GF(p))(0, 1, 0))):
                newprec = offset + prec
                K = pAdicField(p, newprec)
                A = PolynomialRing(RationalField(), 'x')
                f = A(self.hyperelliptic_polynomials()[0])
                from sage.schemes.hyperelliptic_curves.constructor import HyperellipticCurve
                self = HyperellipticCurve(f).change_ring(K)
                xP = P[0]
                xPv = xP.valuation()
                xPnew = K(
                    sum(c * p**(xPv + i)
                        for i, c in enumerate(xP.expansion())))
                PP = P = self.lift_x(xPnew)
                TP = self.frobenius(P)
                xQ = Q[0]
                xQv = xQ.valuation()
                xQnew = K(
                    sum(c * p**(xQv + i)
                        for i, c in enumerate(xQ.expansion())))
                QQ = Q = self.lift_x(xQnew)
                TQ = self.frobenius(Q)
                V = VectorSpace(K, dim)
            P_to_TP = V(self.tiny_integrals_on_basis(P, TP))
        if TQ is None:
            TQ_to_Q = V(0)
        else:
            TQ_to_Q = V(self.tiny_integrals_on_basis(TQ, Q))
        prof("mw calc")
        try:
            M_frob, forms = self._frob_calc
        except AttributeError:
            M_frob, forms = self._frob_calc = monsky_washnitzer.matrix_of_frobenius_hyperelliptic(
                self)
        prof("eval f")
        R = forms[0].base_ring()
        try:
            prof("eval f %s" % R)
            if PP is None:
                L = [-f(R(QQ[0]), R(QQ[1])) for f in forms]  ##changed
            elif QQ is None:
                L = [f(R(PP[0]), R(PP[1])) for f in forms]
            else:
                L = [
                    f(R(PP[0]), R(PP[1])) - f(R(QQ[0]), R(QQ[1]))
                    for f in forms
                ]
        except ValueError:
            prof("changing rings")
            forms = [f.change_ring(self.base_ring()) for f in forms]
            prof("eval f %s" % self.base_ring())
            if PP is None:
                L = [-f(QQ[0], QQ[1]) for f in forms]  ##changed
            elif QQ is None:
                L = [f(PP[0], PP[1]) for f in forms]
            else:
                L = [f(PP[0], PP[1]) - f(QQ[0], QQ[1]) for f in forms]
        b = V(L)
        if PP is None:
            b -= TQ_to_Q
        elif QQ is None:
            b -= P_to_TP
        elif algorithm != 'teichmuller':
            b -= P_to_TP + TQ_to_Q
        prof("lin alg")
        M_sys = matrix(K, M_frob).transpose() - 1
        TP_to_TQ = M_sys**(-1) * b
        prof("done")
        #        print prof
        if algorithm == 'teichmuller':
            return P_to_TP + TP_to_TQ + TQ_to_Q
        else:
            return TP_to_TQ
Esempio n. 15
0
    def __init__(self, E, algorithm=None):
        r"""
        Initialization function for EllipticCurveTorsionSubgroup class

        INPUT:

        - ``E`` - An elliptic curve defined over a number field (including `\Q`)

        - ``algorithm`` - (string, default None): If not None, must be one
                     of 'PARI', 'doud', 'lutz_nagell'.  For curves
                     defined over `\QQ`, PARI is then used with the
                     appropriate flag passed to PARI's ``elltors()``
                     function; this parameter is ignored for curves
                     whose base field is not `\QQ`.

        EXAMPLES::

            sage: from sage.schemes.elliptic_curves.ell_torsion import EllipticCurveTorsionSubgroup
            sage: E=EllipticCurve('11a1')
            sage: K.<i>=NumberField(x^2+1)
            sage: EK=E.change_ring(K)
            sage: EllipticCurveTorsionSubgroup(EK)
            Torsion Subgroup isomorphic to Z/5 associated to the Elliptic Curve defined by y^2 + y = x^3 + (-1)*x^2 + (-10)*x + (-20) over Number Field in i with defining polynomial x^2 + 1

        Note: this class is normally constructed indirectly as follows::

            sage: T = EK.torsion_subgroup(); T
            Torsion Subgroup isomorphic to Z/5 associated to the Elliptic Curve defined by y^2 + y = x^3 + (-1)*x^2 + (-10)*x + (-20) over Number Field in i with defining polynomial x^2 + 1
            sage: type(T)
            <class 'sage.schemes.elliptic_curves.ell_torsion.EllipticCurveTorsionSubgroup_with_category'>

            sage: T == loads(dumps(T))  # optional - pickling http://trac.sagemath.org/sage_trac/ticket/11599
            True

        """
        self.__E = E
        self.__K = E.base_field()

        pari_torsion_algorithms = ["pari", "doud", "lutz_nagell"]

        if self.__K is RationalField(
        ) and algorithm in pari_torsion_algorithms:
            flag = pari_torsion_algorithms.index(algorithm)

            G = None
            loop = 0
            while G is None and loop < 3:
                loop += 1
                try:
                    G = self.__E.pari_curve(prec=400).elltors(
                        flag
                    )  # pari_curve will return the curve of maximum known precision
                except RuntimeError:
                    self.__E.pari_curve(
                        factor=2)  # caches a curve of twice the precision
            if G is not None:
                order = G[0].python()
                structure = G[1].python()
                gens = G[2].python()

                self.__torsion_gens = [self.__E(P) for P in gens]
                from sage.groups.additive_abelian.additive_abelian_group import cover_and_relations_from_invariants
                groups.AdditiveAbelianGroupWrapper.__init__(
                    self,
                    self.__E(0).parent(), self.__torsion_gens, structure)
                return

        T1 = E(0)  # these will be the two generators
        T2 = E(0)
        k1 = 1  # with their order
        k2 = 1

        # find a multiple of the order of the torsion group
        bound = E._torsion_bound(number_of_places=20)

        # now do prime by prime
        for p, e in bound.factor():
            ptor = E._p_primary_torsion_basis(p, e)
            # print p,'-primary part is ',ptor
            if len(ptor) > 0:
                T1 += ptor[0][0]
                k1 *= p**(ptor[0][1])
            if len(ptor) > 1:
                T2 += ptor[1][0]
                k2 *= p**(ptor[1][1])

        order = k1 * k2
        if k1 == 1:
            structure = []
            gens = []
        elif k2 == 1:
            structure = [k1]
            gens = [T1]
        else:
            structure = [k1, k2]
            gens = [T1, T2]

        #self.__torsion_gens = gens
        self._structure = structure
        groups.AdditiveAbelianGroupWrapper.__init__(self, T1.parent(),
                                                    [T1, T2], structure)
Esempio n. 16
0
    def L_ratio(self):
        r"""
        Returns the ratio `L(E,1)/\Omega` as an exact rational
        number. The result is *provably* correct if the Manin
        constant of the associated optimal quotient is `\leq 2`.  This
        hypothesis on the Manin constant is true for all semistable
        curves (i.e., squarefree conductor), by a theorem of Mazur
        from his *Rational Isogenies of Prime Degree* paper.

        EXAMPLES::

            sage: E = EllipticCurve([0, -1, 1, -10, -20])   # 11A  = X_0(11)
            sage: E.lseries().L_ratio()
            1/5
            sage: E = EllipticCurve([0, -1, 1, 0, 0])       # X_1(11)
            sage: E.lseries().L_ratio()
            1/25
            sage: E = EllipticCurve([0, 0, 1, -1, 0])       # 37A  (rank 1)
            sage: E.lseries().L_ratio()
            0
            sage: E = EllipticCurve([0, 1, 1, -2, 0])       # 389A (rank 2)
            sage: E.lseries().L_ratio()
            0
            sage: E = EllipticCurve([0, 0, 1, -38, 90])     # 361A (CM curve))
            sage: E.lseries().L_ratio()
            0
            sage: E = EllipticCurve([0,-1,1,-2,-1])         # 141C (13-isogeny)
            sage: E.lseries().L_ratio()
            1
            sage: E = EllipticCurve(RationalField(), [1, 0, 0, 1/24624, 1/886464])
            sage: E.lseries().L_ratio()
            2

        See :trac:`3651` and :trac:`15299`::

            sage: EllipticCurve([0,0,0,-193^2,0]).sha().an()
            4
            sage: EllipticCurve([1, 0, 1, -131, 558]).sha().an()  # long time
            1.00000000000000

        ALGORITHM: Compute the root number.  If it is -1 then `L(E,s)`
        vanishes to odd order at 1, hence vanishes.  If it is +1, use
        a result about modular symbols and Mazur's *Rational Isogenies*
        paper to determine a provably correct bound (assuming Manin
        constant is <= 2) so that we can determine whether `L(E,1) = 0`.

        AUTHOR: William Stein, 2005-04-20.
        """
        try:
            return self.__lratio
        except AttributeError:
            pass

        if not self.__E.is_minimal():
            self.__lratio = self.__E.minimal_model().lseries().L_ratio()
            return self.__lratio

        QQ = RationalField()
        if self.__E.root_number() == -1:
            self.__lratio = QQ.zero()
            return self.__lratio

        # Even root number.  Decide if L(E,1) = 0.  If E is a modular
        # *OPTIMAL* quotient of J_0(N) elliptic curve, we know that T *
        # L(E,1)/omega is an integer n, where T is the order of the
        # image of the rational torsion point (0)-(oo) in E(Q), and
        # omega is the least real Neron period.  (This is proved in my
        # Ph.D. thesis, but is probably well known.)  We can easily
        # compute omega to very high precision using AGM.  So to prove
        # that L(E,1) = 0 we compute T/omega * L(E,1) to sufficient
        # precision to determine it as an integer.  If eps is the
        # error in computation of L(E,1), then the error in computing
        # the product is (2T/Omega_E) * eps, and we need this to be
        # less than 0.5, i.e.,
        #          (2T/Omega_E) * eps < 0.5,
        # so
        #          eps < 0.5 * Omega_E / (2T) = Omega_E / (4*T).
        #
        # Since in general E need not be optimal, we have to choose
        # eps = Omega_E/(8*t*B), where t is the exponent of E(Q)_tor,
        # and is a multiple of the degree of an isogeny between E
        # and the optimal curve.
        #
        # NOTES: We *do* have to worry about the Manin constant, since
        # we are using the Neron model to compute omega, not the
        # newform.  My theorem replaces the omega above by omega/c,
        # where c is the Manin constant, and the bound must be
        # correspondingly smaller.  If the level is square free, then
        # the Manin constant is 1 or 2, so there's no problem (since
        # we took 8 instead of 4 in the denominator).  If the level
        # is divisible by a square, then the Manin constant could
        # be a divisible by an arbitrary power of that prime, except
        # that Edixhoven claims the primes that appear are <= 7.

        t = self.__E.torsion_subgroup().order()
        omega = self.__E.period_lattice().basis()[0]
        d = self.__E._multiple_of_degree_of_isogeny_to_optimal_curve()
        C = 8 * d * t
        eps = omega / C

        sqrtN = 2 * int(sqrt(self.__E.conductor()))
        k = sqrtN + 10
        while True:
            L1, error_bound = self.at1(k)
            if error_bound < eps:
                n = int(round(L1 * C / omega))
                quo = QQ((n, C))
                self.__lratio = quo / self.__E.real_components()
                return self.__lratio
            k += sqrtN
            misc.verbose("Increasing precision to %s terms." % k)
Esempio n. 17
0
    def __init__(self):

        self._field = RationalField()
        self._flag_cls = ThreeGraphFlag
Esempio n. 18
0
from sage.structure.sage_object import SageObject
from sage.rings.all import (
    Integer,
    RealField,
    RationalField,
    RIF,
    ZZ)
from sage.misc.functional import log
from math import sqrt
from sage.misc.all import verbose
import sage.rings.arith as arith
from sage.rings.padics.factory import Qp

factor = arith.factor
valuation = arith.valuation
Q = RationalField()

class Sha(SageObject):
    r"""
    The Tate-Shafarevich group associated to an elliptic curve.

    If `E` is an elliptic curve over a global field `K`, the Tate-Shafarevich group
    is the subgroup of elements in `H^1(K,E)` which map to zero under every global-to-local
    restriction map `H^1(K,E) \to H^1(K_v,E)`, one for each place `v`
    of `K`.

    EXAMPLES::

        sage: E = EllipticCurve('571a1')
        sage: E._set_gens([])
        sage: S = E.sha()
Esempio n. 19
0
    def __init__(self, E):
        r"""
        Initialization function for EllipticCurveTorsionSubgroup class

        INPUT:

        - ``E`` - An elliptic curve defined over a number field (including `\Q`)

        EXAMPLES::

            sage: from sage.schemes.elliptic_curves.ell_torsion import EllipticCurveTorsionSubgroup
            sage: E = EllipticCurve('11a1')
            sage: K.<i> = NumberField(x^2+1)
            sage: EK = E.change_ring(K)
            sage: EllipticCurveTorsionSubgroup(EK)
            Torsion Subgroup isomorphic to Z/5 associated to the Elliptic Curve defined by y^2 + y = x^3 + (-1)*x^2 + (-10)*x + (-20) over Number Field in i with defining polynomial x^2 + 1

        Note: this class is normally constructed indirectly as follows::

            sage: T = EK.torsion_subgroup(); T
            Torsion Subgroup isomorphic to Z/5 associated to the Elliptic Curve defined by y^2 + y = x^3 + (-1)*x^2 + (-10)*x + (-20) over Number Field in i with defining polynomial x^2 + 1
            sage: type(T)
            <class 'sage.schemes.elliptic_curves.ell_torsion.EllipticCurveTorsionSubgroup_with_category'>

            sage: T == loads(dumps(T))  # known bug, see http://trac.sagemath.org/sage_trac/ticket/11599#comment:7
            True
        """
        self.__E = E
        self.__K = E.base_field()

        if self.__K is RationalField():
            G = self.__E.pari_curve().elltors()
            structure = G[1].sage()
            gens = G[2].sage()

            self.__torsion_gens = [self.__E(P) for P in gens]
            groups.AdditiveAbelianGroupWrapper.__init__(
                self,
                self.__E(0).parent(), self.__torsion_gens, structure)
            return

        T1 = E(0)  # these will be the two generators
        T2 = E(0)
        k1 = 1  # with their order
        k2 = 1

        # find a multiple of the order of the torsion group
        bound = torsion_bound(E, number_of_places=20)

        # now do prime by prime
        for p, e in bound.factor():
            ptor = E._p_primary_torsion_basis(p, e)
            if ptor:
                T1 += ptor[0][0]
                k1 *= p**(ptor[0][1])
            if len(ptor) > 1:
                T2 += ptor[1][0]
                k2 *= p**(ptor[1][1])

        if k1 == 1:
            structure = []
            gens = []
        elif k2 == 1:
            structure = [k1]
            gens = [T1]
        else:
            structure = [k1, k2]
            gens = [T1, T2]

        #self.__torsion_gens = gens
        self._structure = structure
        groups.AdditiveAbelianGroupWrapper.__init__(self, T1.parent(),
                                                    [T1, T2], structure)
Esempio n. 20
0
def torsion_bound(E, number_of_places=20):
    r"""
    Return an upper bound on the order of the torsion subgroup.

    INPUT:

    - ``E`` -- an elliptic curve over `\QQ` or a number field

    - ``number_of_places`` (positive integer, default = 20) -- the
        number of places that will be used to find the bound

    OUTPUT:

    (integer) An upper bound on the torsion order.

    ALGORITHM:

    An upper bound on the order of the torsion group of the elliptic
    curve is obtained by counting points modulo several primes of good
    reduction. Note that the upper bound returned by this function is
    a multiple of the order of the torsion group, and in general will
    be greater than the order.

    To avoid nontrivial arithmetic in the base field (in particular,
    to avoid having to compute the maximal order) we only use prime
    `P` above rational primes `p` which do not divide the discriminant
    of the equation order.

    EXAMPLES::

        sage: CDB = CremonaDatabase()
        sage: from sage.schemes.elliptic_curves.ell_torsion import torsion_bound
        sage: [torsion_bound(E) for E in CDB.iter([14])]
        [6, 6, 6, 6, 6, 6]
        sage: [E.torsion_order() for E in CDB.iter([14])]
        [6, 6, 2, 6, 2, 6]

    An example over a relative number field (see :trac:`16011`)::

        sage: R.<x> = QQ[]
        sage: F.<a> = QuadraticField(5)
        sage: K.<b> = F.extension(x^2-3)
        sage: E = EllipticCurve(K,[0,0,0,b,1])
        sage: E.torsion_subgroup().order()
        1

    An example of a base-change curve from `\QQ` to a degree 16 field::

        sage: from sage.schemes.elliptic_curves.ell_torsion import torsion_bound
        sage: f = PolynomialRing(QQ,'x')([5643417737593488384,0,
        ....:     -11114515801179776,0,-455989850911004,0,379781901872,
        ....:     0,14339154953,0,-1564048,0,-194542,0,-32,0,1])
        sage: K = NumberField(f,'a')
        sage: E = EllipticCurve(K, [1, -1, 1, 824579, 245512517])
        sage: torsion_bound(E)
        16
        sage: E.torsion_subgroup().invariants()
        (4, 4)
    """
    from sage.rings.all import ZZ, GF
    from sage.schemes.elliptic_curves.constructor import EllipticCurve

    K = E.base_field()

    # Special case K = QQ

    if K is RationalField():
        bound = ZZ.zero()
        k = 0
        p = ZZ(2)  # so we start with 3
        E = E.integral_model()
        disc_E = E.discriminant()

        while k < number_of_places:
            p = p.next_prime()
            if p.divides(disc_E):
                continue
            k += 1
            Fp = GF(p)
            new_bound = E.reduction(p).cardinality()
            bound = bound.gcd(new_bound)
            if bound == 1:
                return bound
        return bound

    # In case K is a relative extension we absolutize:

    absK = K.absolute_field('a_')
    f = absK.defining_polynomial()
    abs_map = absK.structure()[1]

    # Ensure f is monic and in ZZ[x]

    f = f.monic()
    den = f.denominator()
    if den != 1:
        x = f.parent().gen()
        n = f.degree()
        f = den**n * f(x / den)
    disc_f = f.discriminant()
    d = K.absolute_degree()

    # Now f is monic in ZZ[x] of degree d and defines the extension K = Q(a)

    # Make sure that we have a model for E with coefficients in ZZ[a]

    E = E.integral_model()
    disc_E = E.discriminant().norm()
    ainvs = [abs_map(c) for c in E.a_invariants()]

    bound = ZZ.zero()
    k = 0
    p = ZZ(2)  # so we start with 3

    try:  # special case, useful for base-changes from QQ
        ainvs = [ZZ(ai) for ai in ainvs]
        while k < number_of_places:
            p = p.next_prime()
            if p.divides(disc_E) or p.divides(disc_f):
                continue
            k += 1
            for fi, ei in f.factor_mod(p):
                di = fi.degree()
                Fp = GF(p)
                new_bound = EllipticCurve(
                    Fp, ainvs).cardinality(extension_degree=di)
                bound = bound.gcd(new_bound)
                if bound == 1:
                    return bound
        return bound
    except (ValueError, TypeError):
        pass

    # General case

    while k < number_of_places:
        p = p.next_prime()
        if p.divides(disc_E) or p.divides(disc_f):
            continue
        k += 1
        for fi, ei in f.factor_mod(p):
            di = fi.degree()
            Fq = GF(p**di)
            ai = fi.roots(Fq, multiplicities=False)[0]

            def red(c):
                return Fq.sum(Fq(c[j]) * ai**j for j in range(d))

            new_bound = EllipticCurve([red(c) for c in ainvs]).cardinality()
            bound = bound.gcd(new_bound)
            if bound == 1:
                return bound
    return bound
Esempio n. 21
0
 def _change_basis(self,x):
     v=x.parts()
     tmp=self._changebasismatrix*Matrix(RationalField(),_sage_const_2 ,_sage_const_1 ,v)
     return tmp[_sage_const_0 ,_sage_const_0 ],tmp[_sage_const_1 ,_sage_const_0 ]