示例#1
0
def _prec_for_solve_diff_eqn_families(M, p):
    #UPDATE THIS with valuation of K[0]-1 and K[1]
    r"""
        A helper function for determining the (relative) precision of the input
        to solve_diff_eqn required in order obtain an answer with (relative)
        precision ``M``. The parameter ``p`` is the prime and ``k`` is the weight.

        Given input precision `M_\text{in}`, the output has precision

        .. MATH::

            M = M_\text{in} - \lceil\log_p(M_\text{in}) - 3.

    """
    # Do we need the weight?
    # A good guess to begin:
    if M < 1:
        raise ValueError("Desired precision M(=%s) must be at least 1."%(M))
    cp = (p - 2) / (p - 1)
    Min = ZZ(3 + M + ceil(ZZ(M).log(p)))
    # It looks like usually there are no iterations
    # For low M, there can be 1 or 2
    while M > Min*cp - ceil(log((Min * cp),p)) - 3: #THINK ABOUT THIS MORE
        Min += 1
        #print("An iteration in _prec_solve_diff_eqn")
    return Min
示例#2
0
    def lifts_basis(self, k, prec, cusp_forms=True):
        r"""
        Compute a basis of the Maass Spezialschar of weight ``k`` up to precision ``prec``.

        This computes the theta lifts of a basis of cusp forms (or a basis of modular forms, if ``cusp_forms`` is set to False).

        INPUT:
        - ``k`` -- the weight
        - ``prec`` -- the precision of the output
        - ``cusp_forms`` -- boolean (default True). If True then we output only cusp forms.

        OUTPUT: list of OrthogonalModularForm's

        EXAMPLES::

            sage: from weilrep import *
            sage: ParamodularForms(N = 1).spezialschar(10, 5)
            [(r^-1 - 2 + r)*q*s + (-2*r^-2 - 16*r^-1 + 36 - 16*r - 2*r^2)*q^2*s + (-2*r^-2 - 16*r^-1 + 36 - 16*r - 2*r^2)*q*s^2 + (r^-3 + 36*r^-2 + 99*r^-1 - 272 + 99*r + 36*r^2 + r^3)*q^3*s + (-16*r^-3 + 240*r^-2 - 240*r^-1 + 32 - 240*r + 240*r^2 - 16*r^3)*q^2*s^2 + (r^-3 + 36*r^-2 + 99*r^-1 - 272 + 99*r + 36*r^2 + r^3)*q*s^3 + O(q, s)^5]
        """
        S = self.gram_matrix()
        w = self.weilrep()
        if cusp_forms:
            X = w.cusp_forms_basis(k + self.input_wt(),
                                   ceil(prec * prec / 4) + 1)
        else:
            X = w.modular_forms_basis(k + self.input_wt(),
                                      ceil(prec * prec / 4) + 1)
        try:
            return X[0].theta_lift(prec, _L=X)
        except TypeError:
            return [x.theta_lift(prec) for x in X]
示例#3
0
文件: lwe.py 项目: bopopescu/sage-5
    def __init__(self, n, instance='key', m=None):
        """
        Construct LWE instance parameterised by security parameter ``n`` where
        all other parameters are chosen as in [CGW13]_.

        INPUT:

        - ``n`` - security parameter (integer >= 89)
        - ``instance`` - one of

          - "key" - the LWE-instance that hides the secret key is generated
          - "encrypt" - the LWE-instance that hides the message is generated
            (default: ``key``)

        - ``m`` - number of allowed samples or ``None`` in which case ``m`` is
          chosen as in [CGW13_].  (default: ``None``)

        EXAMPLES::

            sage: from sage.crypto.lwe import UniformNoiseLWE
            sage: UniformNoiseLWE(89)
            LWE(89, 154262477, UniformSampler(0, 351), 'noise', 131)

            sage: UniformNoiseLWE(89, instance='encrypt')
            LWE(131, 154262477, UniformSampler(0, 497), 'noise', 181)
        """

        if n < 89:
            raise TypeError("Parameter too small")

        n2 = n
        C = 4 / sqrt(2 * pi)
        kk = floor((n2 - 2 * log(n2, 2)**2) / 5)
        n1 = floor((3 * n2 - 5 * kk) / 2)
        ke = floor((n1 - 2 * log(n1, 2)**2) / 5)
        l = floor((3 * n1 - 5 * ke) / 2) - n2
        sk = ceil((C * (n1 + n2))**(3 / 2))
        se = ceil((C * (n1 + n2 + l))**(3 / 2))
        q = next_prime(
            max(ceil((4 * sk)**((n1 + n2) / n1)),
                ceil((4 * se)**((n1 + n2 + l) / (n2 + l))),
                ceil(4 * (n1 + n2) * se * sk + 4 * se + 1)))

        if kk <= 0:
            raise TypeError("Parameter too small")

        if instance == 'key':
            D = UniformSampler(0, sk - 1)
            if m is None:
                m = n1
            LWE.__init__(self, n=n2, q=q, D=D, secret_dist='noise', m=m)
        elif instance == 'encrypt':
            D = UniformSampler(0, se - 1)
            if m is None:
                m = n2 + l
            LWE.__init__(self, n=n1, q=q, D=D, secret_dist='noise', m=m)
        else:
            raise TypeError("Parameter instance=%s not understood." %
                            (instance))
示例#4
0
文件: lwe.py 项目: sagemath/sage
    def __init__(self, n, instance='key', m=None):
        """
        Construct LWE instance parameterised by security parameter ``n`` where
        all other parameters are chosen as in [CGW2013]_.

        INPUT:

        - ``n`` - security parameter (integer >= 89)
        - ``instance`` - one of

          - "key" - the LWE-instance that hides the secret key is generated
          - "encrypt" - the LWE-instance that hides the message is generated
            (default: ``key``)

        - ``m`` - number of allowed samples or ``None`` in which case ``m`` is
          chosen as in [CGW2013]_.  (default: ``None``)

        EXAMPLES::

            sage: from sage.crypto.lwe import UniformNoiseLWE
            sage: UniformNoiseLWE(89)
            LWE(89, 154262477, UniformSampler(0, 351), 'noise', 131)

            sage: UniformNoiseLWE(89, instance='encrypt')
            LWE(131, 154262477, UniformSampler(0, 497), 'noise', 181)
        """

        if n<89:
            raise TypeError("Parameter too small")

        n2 = n
        C  = 4/sqrt(2*pi)
        kk = floor((n2-2*log(n2, 2)**2)/5)
        n1 = floor((3*n2-5*kk)/2)
        ke = floor((n1-2*log(n1, 2)**2)/5)
        l  = floor((3*n1-5*ke)/2)-n2
        sk = ceil((C*(n1+n2))**(3/2))
        se = ceil((C*(n1+n2+l))**(3/2))
        q = next_prime(max(ceil((4*sk)**((n1+n2)/n1)), ceil((4*se)**((n1+n2+l)/(n2+l))), ceil(4*(n1+n2)*se*sk+4*se+1)))

        if kk<=0:
            raise TypeError("Parameter too small")

        if instance == 'key':
            D  = UniformSampler(0, sk-1)
            if m is None:
                m = n1
            LWE.__init__(self, n=n2, q=q, D=D, secret_dist='noise', m=m)
        elif instance == 'encrypt':
            D   = UniformSampler(0, se-1)
            if m is None:
                m = n2+l
            LWE.__init__(self, n=n1, q=q, D=D, secret_dist='noise', m=m)
        else:
            raise TypeError("Parameter instance=%s not understood."%(instance))
    def _normalisation_factor_zz(self, tau=3):
        r"""
        This function returns an approximation of `∑_{x ∈ \ZZ^n}
        \exp(-|x|_2^2/(2σ²))`, i.e. the normalisation factor such that the sum
        over all probabilities is 1 for `\ZZⁿ`.

        If this ``self.B`` is not an identity matrix over `\ZZ` a
        ``NotImplementedError`` is raised.

        INPUT:

        - ``tau`` -- all vectors `v` with `|v|_∞ ≤ τ·σ` are enumerated
                     (default: ``3``).

        EXAMPLES::

            sage: from sage.stats.distributions.discrete_gaussian_lattice import DiscreteGaussianDistributionLatticeSampler
            sage: n = 3; sigma = 1.0
            sage: D = DiscreteGaussianDistributionLatticeSampler(ZZ^n, sigma)
            sage: f = D.f
            sage: c = D._normalisation_factor_zz(); c
            15.528...

            sage: from collections import defaultdict
            sage: counter = defaultdict(Integer)
            sage: m = 0
            sage: def add_samples(i):
            ....:     global counter, m
            ....:     for _ in range(i):
            ....:         counter[D()] += 1
            ....:         m += 1

            sage: v = vector(ZZ, n, (0, 0, 0))
            sage: v.set_immutable()
            sage: while v not in counter: add_samples(1000)

            sage: while abs(m*f(v)*1.0/c/counter[v] - 1.0) >= 0.1: add_samples(1000)

            sage: v = vector(ZZ, n, (-1, 2, 3))
            sage: v.set_immutable()
            sage: while v not in counter: add_samples(1000)

            sage: while abs(m*f(v)*1.0/c/counter[v] - 1.0) >= 0.2: add_samples(1000)  # long time
        """
        if self.B != identity_matrix(ZZ, self.B.nrows()):
            raise NotImplementedError(
                "This function is only implemented when B is an identity matrix."
            )

        f = self.f
        n = self.B.ncols()
        sigma = self._sigma
        return sum(
            f(x)
            for x in _iter_vectors(n, -ceil(tau * sigma), ceil(tau * sigma)))
    def __init__(self, bleachermark, runs):
        from sage.parallel.decorate import parallel
        from sage.functions.other import ceil, floor
        self._benchmarks = bleachermark._benchmarks
        # profiling we run each benchmark once
        self._totaltime = reduce(
            lambda a, b: a + b,
            [r[0] for bm in self._benchmarks for r in bm.run(runs[0])[1:]])
        #divide the runs in chunks
        self._chunksize = ceil(2.0 / self._totaltime)
        self._nchunks = floor(len(runs) / self._chunksize)
        self._chunks = [
            runs[i * self._chunksize:(i + 1) * self._chunksize]
            for i in range(self._nchunks)
        ]
        if (self._nchunks) * self._chunksize < len(runs):
            self._chunks.append(runs[(self._nchunks) * self._chunksize:])
        # we define the parallel function
        @parallel
        def f(indices):
            results = []
            for frun in indices:
                for i in range(len(self._benchmarks)):
                    bm = self._benchmarks[i]
                    res = bm.run(frun)
                    results.append((i, res))
            return results

        self._getchunks = f(self._chunks)
        self._currentchunk = []
        def _base(j, k, c):

            assert k - j == 1
            aajk = subbasis(j, k)
            assert all(a.order() in (1, p) for a in aajk)
            idxs = [i for i, a in enumerate(aajk) if a.order() == p]

            rs = [([0], [0]) for i in range(len(aajk))]
            for i in range(len(idxs)):
                rs[idxs[i]] = (range(p), [0]) if i % 2 else ([0], range(p))
            if len(idxs) % 2:
                m = ceil(sqrt(p))
                rs[idxs[-1]] = range(0, p, m), range(m)

            tab = {}
            for x in iproduct(*(r for r, _ in rs)):
                key = dotprod(x, aajk)
                if hasattr(key, 'set_immutable'):
                    key.set_immutable()
                tab[key] = vector(x)
            for y in iproduct(*(r for _, r in rs)):
                key = c - dotprod(y, aajk)
                if hasattr(key, 'set_immutable'):
                    key.set_immutable()
                if key in tab:
                    return tab[key] + vector(y)

            raise TypeError('Not in group')
示例#8
0
    def get_contents_bound_for_semi_definite_forms(self):
        r"""
        Return the bound for the contents of a semi positive definite
        form falling within this precision.

        EXAMPLES::

            sage: from sage.modular.siegel.siegel_modular_form_prec import SiegelModularFormPrecision
            sage: prec = SiegelModularFormPrecision(7)
            sage: prec.get_contents_bound_for_semi_definite_forms()
            2
            sage: prec = SiegelModularFormPrecision(101)
            sage: prec.get_contents_bound_for_semi_definite_forms()
            26


        NOTE
            If (a,b,c) is semi positive definite, then it is GL(2,Z)-equivalent
            to a the form (0,0,g) where g is the contents (gcd) of a,b,c.
   
            I don't know what this does.  It seems to only do it for singular forms-- NR
        """
        if self.__type == 'infinity':
            return infinity
        elif self.__type == 'disc':
            return ceil((self.__prec+1)/4)
        elif self.__type == 'box':
            return self.__prec[2]
        else:
            raise RuntimeError("Unexpected value of self.__type")        
    def get_contents_bound_for_semi_definite_forms(self):
        r"""
        Return the bound for the contents of a semi positive definite
        form falling within this precision.

        EXAMPLES::

            sage: from sage.modular.siegel.siegel_modular_form_prec import SiegelModularFormPrecision
            sage: prec = SiegelModularFormPrecision(7)
            sage: prec.get_contents_bound_for_semi_definite_forms()
            2
            sage: prec = SiegelModularFormPrecision(101)
            sage: prec.get_contents_bound_for_semi_definite_forms()
            26


        NOTE
            If (a,b,c) is semi positive definite, then it is GL(2,Z)-equivalent
            to a the form (0,0,g) where g is the contents (gcd) of a,b,c.
   
            I don't know what this does.  It seems to only do it for singular forms-- NR
        """
        if self.__type == 'infinity':
            return infinity
        elif self.__type == 'disc':
            return ceil((self.__prec+1)/4)
        elif self.__type == 'box':
            return self.__prec[2]
        else:
            raise RuntimeError, "Unexpected value of self.__type"        
示例#10
0
    def eisenstein_series(self, k, prec):
        r"""
        Compute the Hilbert Eisenstein series E_k(tau1, tau2).

        This is a simple algorithm based on the theta lift. We do not use a closed formula for Eisenstein series coefficients.

        INPUT:
        - ``k`` -- the weight (an even integer >= 2)
        - ``prec`` -- the precision of the output

        OUTPUT: HilbertModularForm

        EXAMPLES::

            sage: from weilrep import *
            sage: x = var('x')
            sage: K.<sqrt5> = NumberField(x^2 - 5)
            sage: HMF(K).eisenstein_series(2, 6)
            1 + 120*q1^(-1/10*sqrt5 + 1/2)*q2^(1/10*sqrt5 + 1/2) + 120*q1^(1/10*sqrt5 + 1/2)*q2^(-1/10*sqrt5 + 1/2) + 120*q1^(-2/5*sqrt5 + 1)*q2^(2/5*sqrt5 + 1) + 600*q1^(-1/5*sqrt5 + 1)*q2^(1/5*sqrt5 + 1) + 720*q1*q2 + 600*q1^(1/5*sqrt5 + 1)*q2^(-1/5*sqrt5 + 1) + 120*q1^(2/5*sqrt5 + 1)*q2^(-2/5*sqrt5 + 1) + 720*q1^(-1/2*sqrt5 + 3/2)*q2^(1/2*sqrt5 + 3/2) + 1200*q1^(-3/10*sqrt5 + 3/2)*q2^(3/10*sqrt5 + 3/2) + 1440*q1^(-1/10*sqrt5 + 3/2)*q2^(1/10*sqrt5 + 3/2) + 1440*q1^(1/10*sqrt5 + 3/2)*q2^(-1/10*sqrt5 + 3/2) + 1200*q1^(3/10*sqrt5 + 3/2)*q2^(-3/10*sqrt5 + 3/2) + 720*q1^(1/2*sqrt5 + 3/2)*q2^(-1/2*sqrt5 + 3/2) + 600*q1^(-4/5*sqrt5 + 2)*q2^(4/5*sqrt5 + 2) + 1440*q1^(-3/5*sqrt5 + 2)*q2^(3/5*sqrt5 + 2) + 2520*q1^(-2/5*sqrt5 + 2)*q2^(2/5*sqrt5 + 2) + 2400*q1^(-1/5*sqrt5 + 2)*q2^(1/5*sqrt5 + 2) + 3600*q1^2*q2^2 + 2400*q1^(1/5*sqrt5 + 2)*q2^(-1/5*sqrt5 + 2) + 2520*q1^(2/5*sqrt5 + 2)*q2^(-2/5*sqrt5 + 2) + 1440*q1^(3/5*sqrt5 + 2)*q2^(-3/5*sqrt5 + 2) + 600*q1^(4/5*sqrt5 + 2)*q2^(-4/5*sqrt5 + 2) + 120*q1^(-11/10*sqrt5 + 5/2)*q2^(11/10*sqrt5 + 5/2) + 1440*q1^(-9/10*sqrt5 + 5/2)*q2^(9/10*sqrt5 + 5/2) + 2400*q1^(-7/10*sqrt5 + 5/2)*q2^(7/10*sqrt5 + 5/2) + 3720*q1^(-1/2*sqrt5 + 5/2)*q2^(1/2*sqrt5 + 5/2) + 3600*q1^(-3/10*sqrt5 + 5/2)*q2^(3/10*sqrt5 + 5/2) + 3840*q1^(-1/10*sqrt5 + 5/2)*q2^(1/10*sqrt5 + 5/2) + 3840*q1^(1/10*sqrt5 + 5/2)*q2^(-1/10*sqrt5 + 5/2) + 3600*q1^(3/10*sqrt5 + 5/2)*q2^(-3/10*sqrt5 + 5/2) + 3720*q1^(1/2*sqrt5 + 5/2)*q2^(-1/2*sqrt5 + 5/2) + 2400*q1^(7/10*sqrt5 + 5/2)*q2^(-7/10*sqrt5 + 5/2) + 1440*q1^(9/10*sqrt5 + 5/2)*q2^(-9/10*sqrt5 + 5/2) + 120*q1^(11/10*sqrt5 + 5/2)*q2^(-11/10*sqrt5 + 5/2) + O(q1, q2)^6
        """
        w = self.weilrep()
        try:
            return (-((k + k) / bernoulli(k)) * w.eisenstein_series(
                k,
                ceil(prec * prec / 4) + 1)).theta_lift(prec)
        except (TypeError, ValueError, ZeroDivisionError):
            raise ValueError('Invalid weight')
示例#11
0
def native_two_isogeny_descent_work(E, two_tor_rk):
    """
    Prepares the output from two-descent by two-isogeny.

    INPUT:

        - ``E`` - an elliptic curve

        - ``two_tor_rk`` - its two-torsion rank

    OUTPUT:

        - a lower bound on the rank

        - an upper bound on the rank

        - a lower bound on the rank of Sha[2]

        - an upper bound on the rank of Sha[2]

        - a list of the generators found (currently None, since we don't store them)

    EXAMPLES::

        sage: from sage.schemes.elliptic_curves.BSD import native_two_isogeny_descent_work
        sage: E = EllipticCurve('14a')
        sage: native_two_isogeny_descent_work(E, E.two_torsion_rank())
        (0, 0, 0, 0, None)
        sage: E = EllipticCurve('65a')
        sage: native_two_isogeny_descent_work(E, E.two_torsion_rank())
        (1, 1, 0, 0, None)

    """
    from sage.schemes.elliptic_curves.descent_two_isogeny import two_descent_by_two_isogeny
    n1, n2, n1p, n2p = two_descent_by_two_isogeny(E)
    # bring n1 and n1p up to the nearest power of two
    two = ZZ(2)  # otherwise "log" is symbolic >.<
    e1 = ceil(ZZ(n1).log(two))
    e1p = ceil(ZZ(n1p).log(two))
    e2 = ZZ(n2).log(two)
    e2p = ZZ(n2p).log(two)
    rank_lower_bd = e1 + e1p - 2
    rank_upper_bd = e2 + e2p - 2
    sha_upper_bd = e2 + e2p - e1 - e1p
    gens = None  # right now, we are not keeping track of them
    return rank_lower_bd, rank_upper_bd, 0, sha_upper_bd, gens
示例#12
0
    def _getitem_by_num(self, i):
        from sage.functions.other import ceil

        val = self._polygon(i)
        if val is Infinity:
            return self._base_exactprec
        else:
            return self._baseprec(ceil(val))
示例#13
0
    def schmidt_t5_eigenvalue_numerical(self, t):
        (tau1, z, tau2) = t
        from sage.libs.mpmath import mp
        from sage.libs.mpmath.mp import exp, pi
        from sage.libs.mpmath.mp import j as i

        if not Integer(self.__level()).is_prime():
            raise ValueError("T_5 is only unique if the level is a prime")

        precision = ParamodularFormD2Filter_trace(self.precision())

        s = Sequence([tau1, z, tau2])
        if not is_ComplexField(s):
            mp_precision = 30
        else:
            mp_precision = ceil(3.33 * s.universe().precision())
        mp.dps = mp_precision

        p1list = P1List(self.level())

        ## Prepare the operation for d_1(N)
        ## We have to invert the lifts since we will later use apply_GL_to_form
        d1_matrices = [p1list.lift_to_sl2z(i) for i in range(len(p1list))]
        d1_matrices = [(a_b_c_d[3], -a_b_c_d[1], -a_b_c_d[2], a_b_c_d[0])
                       for a_b_c_d in d1_matrices]

        ## Prepare the evaluation points corresponding to d_02(N)
        d2_points = list()
        for i in range(len(p1list())):
            (a, b, c, d) = p1list.lift_to_sl2z(i)
            tau1p = (a * tau1 + b) / (c * tau1 + d)
            zp = z / (c * tau1 + d)
            tau2p = tau2 - c * z**2 / (c * tau1 + d)

            (e_tau1p, e_zp, e_tau2p) = (exp(2 * pi * i * tau1p),
                                        exp(2 * pi * i * zp),
                                        exp(2 * pi * i * tau2p))
            d2_points.append((e_tau1p, e_zp, e_tau2p))

        (e_tau1, e_z, e_tau2) = (exp(2 * pi * i * tau1), exp(2 * pi * i * z),
                                 exp(2 * pi * i * tau2))

        self_value = s.universe().zero()
        trans_value = s.universe().zero()

        for k in precision:
            (a, b, c) = apply_GL_to_form(self._P1List()(k[1]), k[0])

            self_value = self_value + self[k] * e_tau1**a * e_z**b * e_tau2**c
            for m in d1_matrices:
                (ap, bp, cp) = apply_GL_to_form(m, (a, b, c))

                for (e_tau1p, e_zp, e_tau2p) in d2_points:
                    trans_value = trans_value + self[((
                        ap, bp, cp), 0)] * e_tau1p**ap * e_zp**bp * e_tau2p**cp

        return trans_value / self_value
def eis_F(cv, dv, N, k, Q=None, prec=10, t=1):
    """
    Computes the coefficient of the Eisenstein series for $\Gamma(N)$.
    Not indented to be called by user.
    INPUT:
    - cv - int, the first coordinate of the vector determining the \Gamma(N)
      Eisenstein series
    - dv - int, the second coordinate of the vector determining the \Gamma(N)
      Eisenstein series
    - N - int, the level of the Eisenstein series to be computed
    - k - int, the weight of the Eisenstein seriess to be computed
    - Q - power series ring, the ring containing the q-expansion to be computed
    - param_level - int, the parameter of the returned series will be
      q_{param_level}
    - prec - int, the precision.  The series in q_{param_level} will be truncated
      after prec coefficients
    OUTPUT:
    - an element of the ring Q, which is the Fourier expansion of the Eisenstein
      series
    """
    if Q == None:
        Q = PowerSeriesRing(CyclotomicField(N), 'q{}'.format(N))
    R = Q.base_ring()
    zetaN = R.zeta(N)
    q = Q.gen()
    s = 0
    if k == 1:
        if cv % N == 0 and dv % N != 0:
            s = QQ(1) / QQ(2) * (1 + zetaN**dv) / (1 - zetaN**dv)
        elif cv % N != 0:
            s = QQ(1) / QQ(2) - QQ(cv) / QQ(N) + floor(QQ(cv) / QQ(N))
    elif k > 1:
        s = -ber_pol(QQ(cv) / QQ(N) - floor(QQ(cv) / QQ(N)), k) / QQ(k)
    for n1 in xrange(1, ceil(prec / QQ(t))):  # this is n/m in DS
        for n2 in xrange(1,
                         ceil(prec / QQ(t) / QQ(n1)) + 1):  # this is m in DS
            if Mod(n1, N) == Mod(cv, N):
                s += N**(1 - k) * n1**(k - 1) * zetaN**(dv * n2) * q**(t * n1 *
                                                                       n2)
            if Mod(n1, N) == Mod(-cv, N):
                s += (-1)**k * N**(1 - k) * n1**(k - 1) * zetaN**(
                    -dv * n2) * q**(t * n1 * n2)
    return s + O(q**floor(prec))
示例#15
0
def griesmer_upper_bound(n,q,d,algorithm=None):
    r"""
    Returns the Griesmer upper bound.

    Returns the Griesmer upper bound for the number of elements in a
    largest linear code of minimum distance `d` in `\GF{q}^n`, cf. [HP2003]_.
    If the method is "gap", it wraps GAP's ``UpperBoundGriesmer``. 

    The bound states:

    .. MATH::

        `n\geq \sum_{i=0}^{k-1} \lceil d/q^i \rceil.`


    EXAMPLES:

    The bound is reached for the ternary Golay codes::

        sage: codes.bounds.griesmer_upper_bound(12,3,6)
        729
        sage: codes.bounds.griesmer_upper_bound(11,3,5)
        729

    ::

        sage: codes.bounds.griesmer_upper_bound(10,2,3)
        128
        sage: codes.bounds.griesmer_upper_bound(10,2,3,algorithm="gap")  # optional - gap_packages (Guava package)
        128

    TESTS::

        sage: codes.bounds.griesmer_upper_bound(11,3,6)
        243
        sage: codes.bounds.griesmer_upper_bound(11,3,6)
        243
    """
    _check_n_q_d(n, q, d)
    if algorithm=="gap":
        gap.load_package("guava")
        ans=gap.eval("UpperBoundGriesmer(%s,%s,%s)"%(n,d,q))
        return QQ(ans)
    else:
        #To compute the bound, we keep summing up the terms on the RHS
        #until we start violating the inequality.
        from sage.functions.other import ceil
        den = 1
        s = 0
        k = 0
        while s <= n:
            s += ceil(d/den)
            den *= q
            k = k + 1
        return q**(k-1)
示例#16
0
    def _an_element_3d(self, x=0, y=0):
        r"""
        Returns an element in self.

        EXAMPLES::

            sage: from slabbe import DiscreteHyperplane
            sage: p = DiscreteHyperplane([1,pi,7], 1+pi+7, mu=10)
            sage: p._an_element_3d()
            (0, 0, 0)
        """
        a, b, c = self._v
        x_sqrt3 = ceil(x / sqrt(3))
        left = ((a + b) * y + (a - b) * x_sqrt3 - self._mu) / (a + b + c)
        right = ((a + b) * y +
                 (a - b) * x_sqrt3 - self._mu + self._omega) / (a + b + c)
        #print "left, right = ", left, right
        #print "left, right = ", ceil(left), ceil(right)-1
        # left <= z <= right
        znew = ceil(left)
        xnew = znew - y - x_sqrt3
        ynew = znew - y + x_sqrt3
        znew = ceil(right) - 1
        #print xnew, ynew, znew
        #print vector((xnew, ynew, znew)) in self
        #print vector((x,y,ceil(right)-1)) in self
        v = vector((xnew, ynew, znew))
        if v in self:
            v.set_immutable()
            return v
        else:
            print "%s not in the plane" % v
            print "trying similar points"
            v = vector((xnew, ynew, znew - 1))
            if v in self:
                v.set_immutable()
                return v
            v = vector((xnew, ynew, znew + 1))
            if v in self:
                v.set_immutable()
                return v
        raise ValueError("%s not in the plane" % v)
示例#17
0
def gegenbauer_polynomial(N, s):
    r"""
    Compute two-variable Gegenbauer polynomials.
    """
    x, y = PolynomialRing(QQ, ['x', 'y']).gens()
    f = 0
    for k in range(N // 2 + 1):
        j = N - (k + k)
        f += (-1)**k * QQ(gamma(s + k + j) / gamma(s + ceil(N / 2))) / (
            factorial(k) * factorial(j)) * (x**j) * (y**k)
    return f * factorial(N)
def _compute_eigenvector(s, l, m, gam, verbose=False, min_nmax=8):
    r"""
    Compute the eigenvector and the eigenvalue corresponding to (s, l, m, gam)

    INPUT:

    - ``s`` -- integer; the spin weight
    - ``l`` -- non-negative integer; the harmonic degree
    - ``m`` -- integer within the range ``[-l, l]``; the azimuthal number
    - ``gam`` -- spheroidicity parameter
    - ``verbose`` -- (default: ``False``) determines whether some details of the
      computation are printed out
    - ``min_nmax`` -- (default: 8) integer; floor for the evaluation of the
      parameter ``nmax``, which sets the highest degree of the spherical
      harmonic expansion as ``l+nmax``.

    """
    nmax = ceil(abs(3 * gam / 2 - gam * gam /
                    250)) + min_nmax  # FIXME : improve the estimate of nmax
    if nmax % 2 == 0:
        nmax += 1
    lmin = max(abs(s), abs(m))
    nmin = min(l - lmin, nmax)
    size = nmax + nmin + 1
    mat = matrix(RDF, size, size)
    for i in range(1, size + 1):
        mat[i - 1, i - 1] = -kHat(s, l - nmin - 1 + i, m, gam)
        if i > 2:
            mat[i - 1, i - 3] = -k2(s, l - nmin - 3 + i, m, gam)
        if i > 1:
            mat[i - 1, i - 2] = -kTilde2(s, l - nmin + i - 2, m, gam)
        if (i < size):
            mat[i - 1, i] = -kTilde2(s, l - nmin + i - 1, m, gam)
        if (i < size - 1):
            mat[i - 1, i + 1] = -k2(s, l - nmin + i + -1, m, gam)
    if verbose:
        print("nmax: {}".format(nmax))
        print("lmin: {}".format(lmin))
        print("nmin: {}".format(nmin))
        print("size: {}".format(size))
        # show(mat)
    # Computation of the eigenvalues and eigenvectors:
    evlist = mat.eigenvectors_right()  # list of triples, each triple being
    # (eigenvalue, [eigenvector], 1)
    sevlist = sorted(evlist, key=lambda x: x[0], reverse=True)
    egval, egvec, mult = sevlist[-(nmin + 1)]
    egvec = egvec[0]  # since egvec is the single-element list [eigenvector]
    if verbose:
        print("eigenvalue: {}".format(egval))
        print("eigenvector: {}".format(egvec))
        check = mat * egvec - egval * egvec
        print("check: {}".format(check))
    lamb = egval - s * (s + 1) - 2 * m * gam + gam * gam
    return lamb, egvec, nmin, nmax, lmin
示例#19
0
    def _an_element_3d(self, x=0, y=0):
        r"""
        Returns an element in self.

        EXAMPLES::

            sage: from slabbe import DiscreteHyperplane
            sage: p = DiscreteHyperplane([1,pi,7], 1+pi+7, mu=10)
            sage: p._an_element_3d()
            (0, 0, 0)
        """
        a,b,c = self._v
        x_sqrt3 = ceil(x / sqrt(3))
        left  = ((a+b) * y + (a-b) * x_sqrt3 - self._mu) / (a+b+c)
        right = ((a+b) * y + (a-b) * x_sqrt3 - self._mu + self._omega) / (a+b+c)
        #print("left, right = ", left, right)
        #print("left, right = ", ceil(left), ceil(right)-1)
        # left <= z <= right
        znew = ceil(left)
        xnew = znew - y - x_sqrt3
        ynew = znew - y + x_sqrt3
        znew = ceil(right)-1
        #print(xnew, ynew, znew)
        #print(vector((xnew, ynew, znew)) in self)
        #print(vector((x,y,ceil(right)-1)) in self)
        v = vector((xnew, ynew, znew))
        if v in self:
            v.set_immutable()
            return v
        else:
            print("%s not in the plane" % v)
            print("trying similar points")
            v = vector((xnew, ynew, znew-1))
            if v in self:
                v.set_immutable()
                return v
            v = vector((xnew, ynew, znew+1))
            if v in self:
                v.set_immutable()
                return v
        raise ValueError("%s not in the plane" % v)
示例#20
0
def _sympysage_ceiling(self):
    """
    EXAMPLES::

        sage: from sympy import Symbol, ceiling
        sage: assert ceil(x)._sympy_() == ceiling(Symbol('x'))
        sage: assert ceil(x) == ceiling(Symbol('x'))._sage_()
        sage: integrate(ceil(x), x, 0, infinity, algorithm='sympy')
        integrate(ceil(x), x, 0, +Infinity)
    """
    from sage.functions.other import ceil
    return ceil(self.args[0]._sage_())
示例#21
0
def _sympysage_ceiling(self):
    """
    EXAMPLES::

        sage: from sympy import Symbol, ceiling
        sage: assert ceil(x)._sympy_() == ceiling(Symbol('x'))
        sage: assert ceil(x) == ceiling(Symbol('x'))._sage_()
        sage: integrate(ceil(x), x, 0, infinity, algorithm='sympy')
        integrate(ceil(x), x, 0, +Infinity)
    """
    from sage.functions.other import ceil
    return ceil(self.args[0]._sage_())
示例#22
0
    def _normalisation_factor_zz(self, tau=3):
        r"""
        This function returns an approximation of `∑_{x ∈ \ZZ^n}
        \exp(-|x|_2^2/(2σ²))`, i.e. the normalisation factor such that the sum
        over all probabilities is 1 for `\ZZⁿ`.

        If this ``self.B`` is not an identity matrix over `\ZZ` a
        ``NotImplementedError`` is raised.

        INPUT:

        - ``tau`` -- all vectors `v` with `|v|_∞ ≤ τ·σ` are enumerated
                     (default: ``3``).

        EXAMPLE::

            sage: from sage.stats.distributions.discrete_gaussian_lattice import DiscreteGaussianDistributionLatticeSampler
            sage: n = 3; sigma = 1.0; m = 1000
            sage: D = DiscreteGaussianDistributionLatticeSampler(ZZ^n, sigma)
            sage: f = D.f
            sage: c = D._normalisation_factor_zz(); c
            15.528...

            sage: l = [D() for _ in xrange(m)]
            sage: v = vector(ZZ, n, (0, 0, 0))
            sage: l.count(v), ZZ(round(m*f(v)/c))
            (57, 64)

        """
        if self.B != identity_matrix(ZZ, self.B.nrows()):
            raise NotImplementedError(
                "This function is only implemented when B is an identity matrix."
            )

        f = self.f
        n = self.B.ncols()
        sigma = self._sigma
        return sum(
            f(x)
            for x in _iter_vectors(n, -ceil(tau * sigma), ceil(tau * sigma)))
示例#23
0
def bench(p, start=2, stop=200, routine=test_irred):
    l = []
    i = ZZ(start)
    while i < stop:
	print i,
        try:
            l.append((i, routine(p, i, i+1)))
        except:
            print "failed"
	else:
	    print sum(l[-1][1])
        i += ceil(i/10)
    return l
示例#24
0
def automorphy_factor_vector(p, a, c, k, chi, p_prec, var_prec, R):
    """
    EXAMPLES::
        
        sage: from sage.modular.pollack_stevens.families_util import automorphy_factor_vector
        sage: automorphy_factor_vector(3, 1, 3, 0, None, 4, 3, PowerSeriesRing(ZpCA(3), 'w'))
        [1 + O(3^20), O(3^21) + (3 + 3^2 + 2*3^3 + O(3^21))*w + (3^2 + 2*3^3 + O(3^22))*w^2, O(3^22) + (3^2 + 2*3^3 + O(3^22))*w + (2*3^2 + O(3^22))*w^2, O(3^22) + (3^2 + 3^3 + O(3^22))*w + (2*3^3 + O(3^23))*w^2]
        sage: automorphy_factor_vector(3, 1, 3, 2, None, 4, 3, PowerSeriesRing(ZpCA(3), 'w'))
        [1 + O(3^20),
         O(3^21) + (3 + 3^2 + 2*3^3 + O(3^21))*w + (3^2 + 2*3^3 + O(3^22))*w^2,
         O(3^22) + (3^2 + 2*3^3 + O(3^22))*w + (2*3^2 + O(3^22))*w^2,
         O(3^22) + (3^2 + 3^3 + O(3^22))*w + (2*3^3 + O(3^23))*w^2]
        sage: p, a, c, k, chi, p_prec, var_prec, R = 11, -3, 11, 0, None, 6, 4, PowerSeriesRing(ZpCA(11, 6), 'w')
        sage: automorphy_factor_vector(p, a, c, k, chi, p_prec, var_prec, R)
        [1 + O(11^6) + (7*11^2 + 4*11^3 + 11^4 + 9*11^5 + 3*11^6 + 10*11^7 + O(11^8))*w + (2*11^3 + 2*11^5 + 2*11^6 + 6*11^7 + 8*11^8 + O(11^9))*w^2 + (6*11^4 + 4*11^5 + 5*11^6 + 6*11^7 + 4*11^9 + O(11^10))*w^3,
         O(11^7) + (7*11 + 11^2 + 2*11^3 + 3*11^4 + 4*11^5 + 3*11^6 + O(11^7))*w + (2*11^2 + 4*11^3 + 5*11^4 + 10*11^5 + 10*11^6 + 2*11^7 + O(11^8))*w^2 + (6*11^3 + 6*11^4 + 2*11^5 + 9*11^6 + 9*11^7 + 2*11^8 + O(11^9))*w^3,
         O(11^8) + (3*11^2 + 4*11^4 + 2*11^5 + 6*11^6 + 10*11^7 + O(11^8))*w + (8*11^2 + 7*11^3 + 8*11^4 + 8*11^5 + 11^6 + O(11^8))*w^2 + (3*11^3 + 9*11^4 + 10*11^5 + 5*11^6 + 10*11^7 + 11^8 + O(11^9))*w^3,
         O(11^9) + (8*11^3 + 3*11^4 + 3*11^5 + 7*11^6 + 2*11^7 + 6*11^8 + O(11^9))*w + (10*11^3 + 6*11^5 + 7*11^6 + O(11^9))*w^2 + (4*11^3 + 11^4 + 8*11^8 + O(11^9))*w^3,
         O(11^10) + (2*11^4 + 9*11^5 + 8*11^6 + 5*11^7 + 4*11^8 + 6*11^9 + O(11^10))*w + (6*11^5 + 3*11^6 + 5*11^7 + 7*11^8 + 4*11^9 + O(11^10))*w^2 + (2*11^4 + 8*11^6 + 2*11^7 + 9*11^8 + 7*11^9 + O(11^10))*w^3,
         O(11^11) + (2*11^5 + 10*11^6 + 10*11^7 + 10*11^8 + 10*11^9 + 10*11^10 + O(11^11))*w + (5*11^5 + 10*11^6 + 10*11^7 + 10*11^8 + 10*11^9 + 10*11^10 + O(11^11))*w^2 + (2*11^5 + 10*11^6 + 10*11^7 + 10*11^8 + 10*11^9 + 10*11^10 + O(11^11))*w^3]
        sage: k = 2
        sage: automorphy_factor_vector(p, a, c, k, chi, p_prec, var_prec, R)
        [9 + 6*11^2 + 11^3 + 9*11^4 + 8*11^5 + O(11^6) + (8*11^2 + 8*11^3 + 10*11^4 + 6*11^5 + 5*11^7 + O(11^8))*w + (7*11^3 + 11^4 + 8*11^5 + 9*11^7 + 10*11^8 + O(11^9))*w^2 + (10*11^4 + 7*11^5 + 7*11^6 + 3*11^7 + 8*11^8 + 4*11^9 + O(11^10))*w^3,
         O(11^7) + (8*11 + 3*11^2 + 6*11^3 + 11^4 + 6*11^5 + 11^6 + O(11^7))*w + (7*11^2 + 4*11^3 + 5*11^4 + 10*11^6 + 5*11^7 + O(11^8))*w^2 + (10*11^3 + 3*11^4 + 4*11^5 + 7*11^6 + 10*11^7 + 3*11^8 + O(11^9))*w^3,
         O(11^8) + (5*11^2 + 2*11^3 + 10*11^4 + 3*11^5 + 8*11^6 + 7*11^7 + O(11^8))*w + (6*11^2 + 3*11^3 + 5*11^4 + 11^5 + 5*11^6 + 9*11^7 + O(11^8))*w^2 + (5*11^3 + 6*11^4 + 5*11^5 + 2*11^6 + 9*11^7 + 6*11^8 + O(11^9))*w^3,
         O(11^9) + (6*11^3 + 11^5 + 8*11^6 + 9*11^7 + 2*11^8 + O(11^9))*w + (2*11^3 + 8*11^4 + 4*11^5 + 6*11^6 + 11^7 + 8*11^8 + O(11^9))*w^2 + (3*11^3 + 11^4 + 3*11^5 + 11^6 + 5*11^7 + 6*11^8 + O(11^9))*w^3,
         O(11^10) + (7*11^4 + 5*11^5 + 3*11^6 + 10*11^7 + 10*11^8 + 11^9 + O(11^10))*w + (10*11^5 + 9*11^6 + 6*11^7 + 6*11^8 + 10*11^9 + O(11^10))*w^2 + (7*11^4 + 11^5 + 7*11^6 + 5*11^7 + 6*11^8 + 2*11^9 + O(11^10))*w^3,
         O(11^11) + (7*11^5 + 3*11^6 + 8*11^8 + 5*11^9 + 8*11^10 + O(11^11))*w + (11^5 + 6*11^6 + 7*11^7 + 11^8 + 2*11^10 + O(11^11))*w^2 + (7*11^5 + 3*11^6 + 8*11^8 + 5*11^9 + 8*11^10 + O(11^11))*w^3]
    """
    S = PolynomialRing(R, 'z')
    z = S.gens()[0]
    w = R.gen()
    aut = S(1)
    for n in range(1, var_prec):
        ## RP: I doubled the precision in "z" here to account for the loss of precision from plugging in arg in below
        ## This should be done better.
        LB = logpp_binom(n, p, ceil(p_prec * (p - 1) / (p - 2)))
        ta = ZZ(Qp(p, 2 * max(p_prec, var_prec)).teichmuller(a))
        arg = (a / ta - 1) / p + c / (p * ta) * z
        aut += LB(arg).truncate(p_prec) * (w**n)
    aut *= (ta**k)
    #if not (chi is None):
    #    aut *= chi(a)
    aut = aut.list()
    len_aut = len(aut)
    if len_aut == p_prec:
        return aut
    elif len_aut > p_prec:
        return aut[:p_prec]
    return aut + [R.zero_element()] * (p_prec - len_aut)
示例#25
0
    def next_height(self, N):
        """
        Return the next permissable height greater than or equal to N for
         curves in self's family.
        
        WARNING: This function my return a height for which only singular
                  curves exist. For example, in the short Weierstrass case
                  height 0 is permissable, as the curve Y^2 = X^3 (uniquely)
                  has height zero.

        INPUT:

            - ``N`` -- A non-negative integer

        OUTPUT:

            - A tuple consisting of three elements of the form
              (H, C, I) such that 
              H: The smallest height >= N
              C: A list of coefficients for curves of this height
              I: A list of indices indicating which of the above coefficients
              achieve this height. The remaining values in C  indicate the 
              max absolute value those coefficients are allowed to obtain
              without altering the height.

              For example, the tuple (4, [1, 2], [1]) for the short Weierstrass
              case denotes set of curves with height 4; these are all of the
              form Y^2 = X^3 + A*X + B, where B=2 and A ranges between -1 and 1.

        EXAMPLES::

            sage: from sage.schemes.elliptic_curves.curve_enumerator import *
            sage: C = CurveEnumerator(family="short_weierstrass")
            sage: C.next_height(4) 
            (4, [1, 2], [1])
            sage: C.next_height(60)
            (64, [4, 8], [0, 1])

            sage: C.next_height(-100)
            Traceback (most recent call last):
            ...
            AssertionError: Input must be non-negative integer.
        """

        assert N >= 0, "Input must be non-negative integer."

        coeffs = [ceil(N**(1 / n)) - 1 for n in self._pows]
        height = max(
            [coeffs[i]**(self._pows[i]) for i in range(self._num_coeffs)])
        return self._height_increment(coeffs)
示例#26
0
def automorphy_factor_vector(p, a, c, k, chi, p_prec, var_prec, R):
    """
    EXAMPLES::
        
        sage: from sage.modular.pollack_stevens.families_util import automorphy_factor_vector
        sage: automorphy_factor_vector(3, 1, 3, 0, None, 4, 3, PowerSeriesRing(ZpCA(3), 'w'))
        [1 + O(3^20), O(3^21) + (3 + 3^2 + 2*3^3 + O(3^21))*w + (3^2 + 2*3^3 + O(3^22))*w^2, O(3^22) + (3^2 + 2*3^3 + O(3^22))*w + (2*3^2 + O(3^22))*w^2, O(3^22) + (3^2 + 3^3 + O(3^22))*w + (2*3^3 + O(3^23))*w^2]
        sage: automorphy_factor_vector(3, 1, 3, 2, None, 4, 3, PowerSeriesRing(ZpCA(3), 'w'))
        [1 + O(3^20),
         O(3^21) + (3 + 3^2 + 2*3^3 + O(3^21))*w + (3^2 + 2*3^3 + O(3^22))*w^2,
         O(3^22) + (3^2 + 2*3^3 + O(3^22))*w + (2*3^2 + O(3^22))*w^2,
         O(3^22) + (3^2 + 3^3 + O(3^22))*w + (2*3^3 + O(3^23))*w^2]
        sage: p, a, c, k, chi, p_prec, var_prec, R = 11, -3, 11, 0, None, 6, 4, PowerSeriesRing(ZpCA(11, 6), 'w')
        sage: automorphy_factor_vector(p, a, c, k, chi, p_prec, var_prec, R)
        [1 + O(11^6) + (7*11^2 + 4*11^3 + 11^4 + 9*11^5 + 3*11^6 + 10*11^7 + O(11^8))*w + (2*11^3 + 2*11^5 + 2*11^6 + 6*11^7 + 8*11^8 + O(11^9))*w^2 + (6*11^4 + 4*11^5 + 5*11^6 + 6*11^7 + 4*11^9 + O(11^10))*w^3,
         O(11^7) + (7*11 + 11^2 + 2*11^3 + 3*11^4 + 4*11^5 + 3*11^6 + O(11^7))*w + (2*11^2 + 4*11^3 + 5*11^4 + 10*11^5 + 10*11^6 + 2*11^7 + O(11^8))*w^2 + (6*11^3 + 6*11^4 + 2*11^5 + 9*11^6 + 9*11^7 + 2*11^8 + O(11^9))*w^3,
         O(11^8) + (3*11^2 + 4*11^4 + 2*11^5 + 6*11^6 + 10*11^7 + O(11^8))*w + (8*11^2 + 7*11^3 + 8*11^4 + 8*11^5 + 11^6 + O(11^8))*w^2 + (3*11^3 + 9*11^4 + 10*11^5 + 5*11^6 + 10*11^7 + 11^8 + O(11^9))*w^3,
         O(11^9) + (8*11^3 + 3*11^4 + 3*11^5 + 7*11^6 + 2*11^7 + 6*11^8 + O(11^9))*w + (10*11^3 + 6*11^5 + 7*11^6 + O(11^9))*w^2 + (4*11^3 + 11^4 + 8*11^8 + O(11^9))*w^3,
         O(11^10) + (2*11^4 + 9*11^5 + 8*11^6 + 5*11^7 + 4*11^8 + 6*11^9 + O(11^10))*w + (6*11^5 + 3*11^6 + 5*11^7 + 7*11^8 + 4*11^9 + O(11^10))*w^2 + (2*11^4 + 8*11^6 + 2*11^7 + 9*11^8 + 7*11^9 + O(11^10))*w^3,
         O(11^11) + (2*11^5 + 10*11^6 + 10*11^7 + 10*11^8 + 10*11^9 + 10*11^10 + O(11^11))*w + (5*11^5 + 10*11^6 + 10*11^7 + 10*11^8 + 10*11^9 + 10*11^10 + O(11^11))*w^2 + (2*11^5 + 10*11^6 + 10*11^7 + 10*11^8 + 10*11^9 + 10*11^10 + O(11^11))*w^3]
        sage: k = 2
        sage: automorphy_factor_vector(p, a, c, k, chi, p_prec, var_prec, R)
        [9 + 6*11^2 + 11^3 + 9*11^4 + 8*11^5 + O(11^6) + (8*11^2 + 8*11^3 + 10*11^4 + 6*11^5 + 5*11^7 + O(11^8))*w + (7*11^3 + 11^4 + 8*11^5 + 9*11^7 + 10*11^8 + O(11^9))*w^2 + (10*11^4 + 7*11^5 + 7*11^6 + 3*11^7 + 8*11^8 + 4*11^9 + O(11^10))*w^3,
         O(11^7) + (8*11 + 3*11^2 + 6*11^3 + 11^4 + 6*11^5 + 11^6 + O(11^7))*w + (7*11^2 + 4*11^3 + 5*11^4 + 10*11^6 + 5*11^7 + O(11^8))*w^2 + (10*11^3 + 3*11^4 + 4*11^5 + 7*11^6 + 10*11^7 + 3*11^8 + O(11^9))*w^3,
         O(11^8) + (5*11^2 + 2*11^3 + 10*11^4 + 3*11^5 + 8*11^6 + 7*11^7 + O(11^8))*w + (6*11^2 + 3*11^3 + 5*11^4 + 11^5 + 5*11^6 + 9*11^7 + O(11^8))*w^2 + (5*11^3 + 6*11^4 + 5*11^5 + 2*11^6 + 9*11^7 + 6*11^8 + O(11^9))*w^3,
         O(11^9) + (6*11^3 + 11^5 + 8*11^6 + 9*11^7 + 2*11^8 + O(11^9))*w + (2*11^3 + 8*11^4 + 4*11^5 + 6*11^6 + 11^7 + 8*11^8 + O(11^9))*w^2 + (3*11^3 + 11^4 + 3*11^5 + 11^6 + 5*11^7 + 6*11^8 + O(11^9))*w^3,
         O(11^10) + (7*11^4 + 5*11^5 + 3*11^6 + 10*11^7 + 10*11^8 + 11^9 + O(11^10))*w + (10*11^5 + 9*11^6 + 6*11^7 + 6*11^8 + 10*11^9 + O(11^10))*w^2 + (7*11^4 + 11^5 + 7*11^6 + 5*11^7 + 6*11^8 + 2*11^9 + O(11^10))*w^3,
         O(11^11) + (7*11^5 + 3*11^6 + 8*11^8 + 5*11^9 + 8*11^10 + O(11^11))*w + (11^5 + 6*11^6 + 7*11^7 + 11^8 + 2*11^10 + O(11^11))*w^2 + (7*11^5 + 3*11^6 + 8*11^8 + 5*11^9 + 8*11^10 + O(11^11))*w^3]
    """
    S = PolynomialRing(R, 'z')
    z = S.gens()[0]
    w = R.gen()
    aut = S(1)
    for n in range(1, var_prec):
        ## RP: I doubled the precision in "z" here to account for the loss of precision from plugging in arg in below
        ## This should be done better.
        LB = logpp_binom(n, p, ceil(p_prec * (p-1)/(p-2)))
        ta = ZZ(Qp(p, 2 * max(p_prec, var_prec)).teichmuller(a))
        arg = (a / ta - 1) / p + c / (p * ta) * z
        aut += LB(arg).truncate(p_prec) * (w ** n)
    aut *= (ta ** k)
    #if not (chi is None):
    #    aut *= chi(a)
    aut = aut.list()
    len_aut = len(aut)
    if len_aut == p_prec:
        return aut
    elif len_aut > p_prec:
        return aut[:p_prec]
    return aut + [R.zero_element()] * (p_prec - len_aut)
示例#27
0
    def e_string_to_ground_state(self):
        r"""
        Returns a string of integers in the index set `(i_1,\ldots,i_k)` such that `e_{i_k} \cdots e_{i_1} self` is
        the ground state.

        INPUT:

        - ``self`` -- an element of a tensor product of Kirillov-Reshetikhin crystals.

        OUTPUT: a tuple of integers `(i_1,\ldots,i_k)`

        This method is only defined when ``self`` is an element of a tensor product of affine Kirillov-Reshetikhin crystals.
        It calculates a path from ``self`` to a ground state path using Demazure arrows as defined in 
        Lemma 7.3 in [SchillingTingley2011]_.

        EXAMPLES::

            sage: K = KirillovReshetikhinCrystal(['A',2,1],1,1)
            sage: T = TensorProductOfCrystals(K,K)
            sage: t = T.module_generators[0]
            sage: t.e_string_to_ground_state()
            (0, 2)

            sage: K = KirillovReshetikhinCrystal(['C',2,1],1,1)
            sage: T = TensorProductOfCrystals(K,K)
            sage: t = T.module_generators[0]; t
            [[[1]], [[1]]]
            sage: t.e_string_to_ground_state()
            (0,)
            sage: x=t.e(0)
            sage: x.e_string_to_ground_state()
            ()
            sage: y=t.f_string([1,2,1,1,0]); y
            [[[2]], [[1]]]
            sage: y.e_string_to_ground_state()
            ()
        """
        assert self.parent().crystals[0].__module__ == 'sage.combinat.crystals.kirillov_reshetikhin', \
            "All crystals in the tensor product need to be Kirillov-Reshetikhin crystals"
        I = self.index_set()
        I.remove(0)
        ell = max(
            ceil(K.s() / K.cartan_type().c()[K.r()])
            for K in self.parent().crystals)
        for i in I:
            if self.epsilon(i) > 0:
                return (i, ) + (self.e(i)).e_string_to_ground_state()
        if self.epsilon(0) > ell:
            return (0, ) + (self.e(0)).e_string_to_ground_state()
        return ()
示例#28
0
 def exp(self,workprec=Infinity):
     from sage.functions.other import ceil
     if workprec is Infinity:
         raise ApproximationError("unable to compute exp to infinite precision")
     parent = self.parent()
     pow = parent(1)
     res = parent(1)
     val = self.valuation()
     iter = ceil(workprec / (val - 1/(parent._p-1))) + 1
     for i in range(1,iter):
         pow *= self / parent(i)
         res += pow
         res = res.truncate(workprec)
     return res
示例#29
0
    def _normalisation_factor_zz(self, tau=3):
        r"""
        This function returns an approximation of `∑_{x ∈ \ZZ^n}
        \exp(-|x|_2^2/(2σ²))`, i.e. the normalisation factor such that the sum
        over all probabilities is 1 for `\ZZⁿ`.

        If this ``self.B`` is not an identity matrix over `\ZZ` a
        ``NotImplementedError`` is raised.

        INPUT:

        - ``tau`` -- all vectors `v` with `|v|_∞ ≤ τ·σ` are enumerated
                     (default: ``3``).

        EXAMPLES::

            sage: from sage.stats.distributions.discrete_gaussian_lattice import DiscreteGaussianDistributionLatticeSampler
            sage: n = 3; sigma = 1.0; m = 1000
            sage: D = DiscreteGaussianDistributionLatticeSampler(ZZ^n, sigma)
            sage: f = D.f
            sage: c = D._normalisation_factor_zz(); c
            15.528...

            sage: l = [D() for _ in range(m)]
            sage: v = vector(ZZ, n, (0, 0, 0))
            sage: l.count(v), ZZ(round(m*f(v)/c))
            (57, 64)

        """
        if self.B != identity_matrix(ZZ, self.B.nrows()):
            raise NotImplementedError("This function is only implemented when B is an identity matrix.")

        f = self.f
        n = self.B.ncols()
        sigma = self._sigma
        return sum(f(x) for x in _iter_vectors(n, -ceil(tau * sigma),
                                               ceil(tau * sigma)))
示例#30
0
    def next_height(self,N):
        """
        Return the next permissable height greater than or equal to N for
         curves in self's family.
        
        WARNING: This function my return a height for which only singular
                  curves exist. For example, in the short Weierstrass case
                  height 0 is permissable, as the curve Y^2 = X^3 (uniquely)
                  has height zero.

        INPUT:

            - ``N`` -- A non-negative integer

        OUTPUT:

            - A tuple consisting of three elements of the form
              (H, C, I) such that 
              H: The smallest height >= N
              C: A list of coefficients for curves of this height
              I: A list of indices indicating which of the above coefficients
              achieve this height. The remaining values in C  indicate the 
              max absolute value those coefficients are allowed to obtain
              without altering the height.

              For example, the tuple (4, [1, 2], [1]) for the short Weierstrass
              case denotes set of curves with height 4; these are all of the
              form Y^2 = X^3 + A*X + B, where B=2 and A ranges between -1 and 1.

        EXAMPLES::

            sage: from sage.schemes.elliptic_curves.curve_enumerator import *
            sage: C = CurveEnumerator(family="short_weierstrass")
            sage: C.next_height(4) 
            (4, [1, 2], [1])
            sage: C.next_height(60)
            (64, [4, 8], [0, 1])

            sage: C.next_height(-100)
            Traceback (most recent call last):
            ...
            AssertionError: Input must be non-negative integer.
        """

        assert N>=0, "Input must be non-negative integer."

        coeffs = [ceil(N**(1/n))-1 for n in self._pows]
        height = max([coeffs[i]**(self._pows[i]) for i in range(self._num_coeffs)])
        return self._height_increment(coeffs)
示例#31
0
    def e_string_to_ground_state(self):
        r"""
        Returns a string of integers in the index set `(i_1,\ldots,i_k)` such that `e_{i_k} \cdots e_{i_1} self` is
        the ground state.

        INPUT:

        - ``self`` -- an element of a tensor product of Kirillov-Reshetikhin crystals.

        OUTPUT: a tuple of integers `(i_1,\ldots,i_k)`

        This method is only defined when ``self`` is an element of a tensor product of affine Kirillov-Reshetikhin crystals.
        It calculates a path from ``self`` to a ground state path using Demazure arrows as defined in
        Lemma 7.3 in [SchillingTingley2011]_.

        EXAMPLES::

            sage: K = KirillovReshetikhinCrystal(['A',2,1],1,1)
            sage: T = TensorProductOfCrystals(K,K)
            sage: t = T.module_generators[0]
            sage: t.e_string_to_ground_state()
            (0, 2)

            sage: K = KirillovReshetikhinCrystal(['C',2,1],1,1)
            sage: T = TensorProductOfCrystals(K,K)
            sage: t = T.module_generators[0]; t
            [[[1]], [[1]]]
            sage: t.e_string_to_ground_state()
            (0,)
            sage: x=t.e(0)
            sage: x.e_string_to_ground_state()
            ()
            sage: y=t.f_string([1,2,1,1,0]); y
            [[[2]], [[1]]]
            sage: y.e_string_to_ground_state()
            ()
        """
        assert self.parent().crystals[0].__module__ == 'sage.combinat.crystals.kirillov_reshetikhin', \
            "All crystals in the tensor product need to be Kirillov-Reshetikhin crystals"
        I = self.index_set()
        I.remove(0)
        ell = max(ceil(K.s()/K.cartan_type().c()[K.r()]) for K in self.parent().crystals)
        for i in I:
            if self.epsilon(i) > 0:
                return (i,) + (self.e(i)).e_string_to_ground_state()
        if self.epsilon(0) > ell:
            return (0,) + (self.e(0)).e_string_to_ground_state()
        return ()
示例#32
0
def trunc(i):
    """
    Truncates to the integer closer to zero

    EXAMPLES::

        sage: from sage.combinat.crystals.tensor_product import trunc
        sage: trunc(-3/2), trunc(-1), trunc(-1/2), trunc(0), trunc(1/2), trunc(1), trunc(3/2)
        (-1, -1, 0, 0, 0, 1, 1)
        sage: isinstance(trunc(3/2), Integer)
        True
    """
    if i >= 0:
        return floor(i)
    else:
        return ceil(i)
示例#33
0
    def calc_prec(self):
        if self.prec != None:
            return self.prec

        mp0 = MatrixPowerSexp(self.bsym,self.N-1,iprec=self.iprec,x0=self.x0sym)

        sexp_precision=RR(1)*log(abs(self.sexp_1(0.5)-mp0.sexp_1(0.5)),2.0)
        self.prec = (-sexp_precision).floor()
        print "sexp precision: " , self.prec

        cprec = self.prec+ceil(log(self.N)/log(2.0))

        #self.eigenvalues = [ ev.n(cprec) for ev in self.eigenvalues ]
        #self.IM = self.IM.n(cprec)
        #self.b = self.bsym.n(cprec)
        return self
示例#34
0
def trunc(i):
    """
    Truncates to the integer closer to zero

    EXAMPLES::

        sage: from sage.combinat.crystals.tensor_product import trunc
        sage: trunc(-3/2), trunc(-1), trunc(-1/2), trunc(0), trunc(1/2), trunc(1), trunc(3/2)
        (-1, -1, 0, 0, 0, 1, 1)
        sage: isinstance(trunc(3/2), Integer)
        True
    """
    if i>= 0:
        return floor(i)
    else:
        return ceil(i)
示例#35
0
    def __iter__(self):
        r"""
        Iterate over all GL(2,Z)-reduced  semi positive forms
        which are within the bounds of this precision.

        EXAMPLES::

            sage: from sage.modular.siegel.siegel_modular_form_prec import SiegelModularFormPrecision
            sage: prec = SiegelModularFormPrecision(11)
            sage: for k in prec.__iter__(): print k
            (0, 0, 0)
            (0, 0, 1)
            (0, 0, 2)
            (1, 0, 1)
            (1, 0, 2)
            (1, 1, 1)
            (1, 1, 2)


        NOTE
            The forms are enumerated in lexicographic order.
        """
        if self.__type == 'disc':
            bound = self.get_contents_bound_for_semi_definite_forms()
            for c in range(0, bound):
                yield (0,0,c)

            atop = isqrt(self.__prec // 3)
            if 3*atop*atop == self.__prec: atop -= 1
            for a in range(1,atop + 1):
                for b in range(a+1):
                    for c in range(a, ceil((b**2 + self.__prec)/(4*a))):
                        yield (a,b,c)

        elif 'box' == self.__type:
            (am, bm, cm) = self.__prec
            for a in range(am):
                for b in range(min(bm,a+1)):
                    for c in range(a, cm):
                        yield (a,b,c)

        else:
            raise RuntimeError("Unexpected value of self.__type")
            
        raise StopIteration
    def __iter__(self):
        r"""
        Iterate over all GL(2,Z)-reduced  semi positive forms
        which are within the bounds of this precision.

        EXAMPLES::

            sage: from sage.modular.siegel.siegel_modular_form_prec import SiegelModularFormPrecision
            sage: prec = SiegelModularFormPrecision(11)
            sage: for k in prec.__iter__(): print k
            (0, 0, 0)
            (0, 0, 1)
            (0, 0, 2)
            (1, 0, 1)
            (1, 0, 2)
            (1, 1, 1)
            (1, 1, 2)


        NOTE
            The forms are enumerated in lexicographic order.
        """
        if self.__type == 'disc':
            bound = self.get_contents_bound_for_semi_definite_forms()
            for c in xrange(0, bound):
                yield (0,0,c)

            atop = isqrt(self.__prec // 3)
            if 3*atop*atop == self.__prec: atop -= 1
            for a in xrange(1,atop + 1):
                for b in xrange(a+1):
                    for c in xrange(a, ceil((b**2 + self.__prec)/(4*a))):
                        yield (a,b,c)

        elif 'box' == self.__type:
            (am, bm, cm) = self.__prec
            for a in xrange(am):
                for b in xrange( min(bm,a+1)):
                    for c in xrange(a, cm):
                        yield (a,b,c)

        else:
            raise RuntimeError, "Unexpected value of self.__type"
            
        raise StopIteration
示例#37
0
def newton_iteration(G, n):
    r"""Returns a truncated series `y = y(x)` satisfying

    .. math::

        G(x,y(x)) \equiv 0 \bmod{x^r}

    where $r = \ceil{\log_2{n}}$. Based on the algorithm in [XXX].

    Parameters
    ----------
    G, x, y : polynomial
        A polynomial in `x` and `y`.
    n : int
        Requested degree of the series expansion.

    Notes
    -----
    This algorithm returns the series up to order :math:`2^r > n`. Any
    choice of order below :math:`2^r` will return the same series.

    """
    R = G.parent()
    x,y = R.gens()
    if n < 0:
        raise ValueError('Number of terms must be positive. (n=%d'%n)
    elif n == 0:
        return R(0)

    phi = G
    phiprime = phi.derivative(y)
    try:
        pi = R(x).polynomial(x)
        gi = R(0)
        si = R(phiprime(x,gi)).polynomial(x).inverse_mod(pi)
    except NotImplementedError:
        raise ValueError('Newton iteration for computing regular part of '
                         'Puiseux expansion failed. Curve is most likely '
                         'not regular at center.')

    r = ceil(log(n,2))
    for i in range(r):
        gi,si,pi = newton_iteration_step(phi,phiprime,gi,si,pi)
    return R(gi)
示例#38
0
def newton_iteration(G, n):
    r"""Returns a truncated series `y = y(x)` satisfying

    .. math::

        G(x,y(x)) \equiv 0 \bmod{x^r}

    where $r = \ceil{\log_2{n}}$. Based on the algorithm in [XXX].

    Parameters
    ----------
    G, x, y : polynomial
        A polynomial in `x` and `y`.
    n : int
        Requested degree of the series expansion.

    Notes
    -----
    This algorithm returns the series up to order :math:`2^r > n`. Any
    choice of order below :math:`2^r` will return the same series.

    """
    R = G.parent()
    x, y = R.gens()
    if n < 0:
        raise ValueError('Number of terms must be positive. (n=%d' % n)
    elif n == 0:
        return R(0)

    phi = G
    phiprime = phi.derivative(y)
    try:
        pi = R(x).polynomial(x)
        gi = R(0)
        si = R(phiprime(x, gi)).polynomial(x).inverse_mod(pi)
    except NotImplementedError:
        raise ValueError('Newton iteration for computing regular part of '
                         'Puiseux expansion failed. Curve is most likely '
                         'not regular at center.')

    r = ceil(log(n, 2))
    for i in range(r):
        gi, si, pi = newton_iteration_step(phi, phiprime, gi, si, pi)
    return R(gi)
示例#39
0
    def atkin_lehner_eigenvalue_numerical(self, t):
        (tau1, z, tau2) = t
        from sage.libs.mpmath import mp
        from sage.libs.mpmath.mp import exp, pi
        from sage.libs.mpmath.mp import j as i

        if not Integer(self.__level()).is_prime():
            raise ValueError(
                "The Atkin Lehner involution is only unique if the level is a prime"
            )

        precision = ParamodularFormD2Filter_trace(self.precision())

        s = Sequence([tau1, z, tau2])
        if not is_ComplexField(s):
            mp_precision = 30
        else:
            mp_precision = ceil(3.33 * s.universe().precision())
        mp.dps = mp_precision

        (tau1, z, tau2) = tuple(s)
        (tau1p, zp, tau2p) = (self.level() * tau1, self.level() * z,
                              self.level() * tau2)

        (e_tau1, e_z, e_tau2) = (exp(2 * pi * i * tau1), exp(2 * pi * i * z),
                                 exp(2 * pi * i * tau2))
        (e_tau1p, e_zp, e_tau2p) = (exp(2 * pi * i * tau1p),
                                    exp(2 * pi * i * zp),
                                    exp(2 * pi * i * tau2p))

        self_value = s.universe().zero()
        trans_value = s.universe().zero()

        for k in precision:
            (a, b, c) = apply_GL_to_form(self._P1List()(k[1]), k[0])

            self_value = self_value + self[k] * (e_tau1**a * e_z**b *
                                                 e_tau2**c)
            trans_value = trans_value + self[k] * (e_tau1p**a * e_zp**b *
                                                   e_tau2p**c)

        return trans_value / self_value
示例#40
0
    def split_xor(self, monomial_list, equal_zero):
        """
        Split XOR chains into subchains.

        INPUT:

        - ``monomial_list`` - a list of monomials
        - ``equal_zero`` - is the constant coefficient zero?

        EXAMPLES::

            sage: from sage.sat.converters.polybori import CNFEncoder
            sage: from sage.sat.solvers.dimacs import DIMACS
            sage: B.<a,b,c,d,e,f> = BooleanPolynomialRing()
            sage: ce = CNFEncoder(DIMACS(), B, cutting_number=3)
            sage: ce.split_xor([1,2,3,4,5,6], False)
            [[[1, 7], False], [[7, 2, 8], True], [[8, 3, 9], True], [[9, 4, 10], True], [[10, 5, 11], True], [[11, 6], True]]

            sage: ce = CNFEncoder(DIMACS(), B, cutting_number=4)
            sage: ce.split_xor([1,2,3,4,5,6], False)
            [[[1, 2, 7], False], [[7, 3, 4, 8], True], [[8, 5, 6], True]]

            sage: ce = CNFEncoder(DIMACS(), B, cutting_number=5)
            sage: ce.split_xor([1,2,3,4,5,6], False)
            [[[1, 2, 3, 7], False], [[7, 4, 5, 6], True]]
        """
        c = self.cutting_number

        nm = len(monomial_list)
        step = ceil((c - 2) / ZZ(nm) * nm)
        M = []

        new_variables = []
        for j in range(0, nm, step):
            m = new_variables + monomial_list[j:j + step]
            if (j + step) < nm:
                new_variables = [self.var(None)]
                m += new_variables
            M.append([m, equal_zero])
            equal_zero = True
        return M
示例#41
0
文件: polybori.py 项目: DrXyzzy/sage
    def split_xor(self, monomial_list, equal_zero):
        """
        Split XOR chains into subchains.

        INPUT:

        - ``monomial_list`` - a list of monomials
        - ``equal_zero`` - is the constant coefficient zero?

        EXAMPLE::

            sage: from sage.sat.converters.polybori import CNFEncoder
            sage: from sage.sat.solvers.dimacs import DIMACS
            sage: B.<a,b,c,d,e,f> = BooleanPolynomialRing()
            sage: ce = CNFEncoder(DIMACS(), B, cutting_number=3)
            sage: ce.split_xor([1,2,3,4,5,6], False)
            [[[1, 7], False], [[7, 2, 8], True], [[8, 3, 9], True], [[9, 4, 10], True], [[10, 5, 11], True], [[11, 6], True]]

            sage: ce = CNFEncoder(DIMACS(), B, cutting_number=4)
            sage: ce.split_xor([1,2,3,4,5,6], False)
            [[[1, 2, 7], False], [[7, 3, 4, 8], True], [[8, 5, 6], True]]

            sage: ce = CNFEncoder(DIMACS(), B, cutting_number=5)
            sage: ce.split_xor([1,2,3,4,5,6], False)
            [[[1, 2, 3, 7], False], [[7, 4, 5, 6], True]]
        """
        c = self.cutting_number

        nm = len(monomial_list)
        step = ceil((c-2)/ZZ(nm) * nm)
        M = []

        new_variables = []
        for j in range(0, nm, step):
            m =  new_variables + monomial_list[j:j+step]
            if (j + step) < nm:
                new_variables = [self.var(None)]
                m += new_variables
            M.append([m, equal_zero])
            equal_zero = True
        return M
def compute_series_truncations(f, alpha):
    r"""Computes Puiseux series at :math:`x=\alpha` with necessary terms.

    The Puiseux series expansions of :math:`f = f(x,y)` centered at
    :math:`\alpha` are computed up to the number of terms needed for the
    integral basis algorithm to be successful. The expansion degree bounds are
    determined by :func:`compute_expansion_bounds`.

    Parameters
    ----------
    f : polynomial
    alpha : complex

    Returns
    -------
    list : PuiseuxXSeries
        A list of Puiseux series expansions centered at :math:`x = \alpha` with
        enough terms to compute integral bases as SymPy expressions.

    """
    # compute the parametric Puiseix series with the minimal number of terms
    # needed to distinguish them.
    pt = puiseux(f,alpha)
    px = [p for P in pt for p in P.xseries()]

    # compute the orders necessary for the integral basis algorithm. the orders
    # are on the Puiseux x-series (non-parametric) so scale by the ramification
    # index of each series
    N = compute_expansion_bounds(px)
    for i in range(len(N)):
        e = px[i].ramification_index
        N[i] = ceil(N[i]*e)

    order = max(N) + 1
    for pti in pt:
        pti.extend(order=order)

    # recompute the corresponding x-series with the extened terms
    px = [p for P in pt for p in P.xseries()]
    return px
示例#43
0
def compute_series_truncations(f, alpha):
    r"""Computes Puiseux series at :math:`x=\alpha` with necessary terms.

    The Puiseux series expansions of :math:`f = f(x,y)` centered at
    :math:`\alpha` are computed up to the number of terms needed for the
    integral basis algorithm to be successful. The expansion degree bounds are
    determined by :func:`compute_expansion_bounds`.

    Parameters
    ----------
    f : polynomial
    alpha : complex

    Returns
    -------
    list : PuiseuxXSeries
        A list of Puiseux series expansions centered at :math:`x = \alpha` with
        enough terms to compute integral bases as SymPy expressions.

    """
    # compute the parametric Puiseix series with the minimal number of terms
    # needed to distinguish them.
    pt = puiseux(f, alpha)
    px = [p for P in pt for p in P.xseries()]

    # compute the orders necessary for the integral basis algorithm. the orders
    # are on the Puiseux x-series (non-parametric) so scale by the ramification
    # index of each series
    N = compute_expansion_bounds(px)
    for i in range(len(N)):
        e = px[i].ramification_index
        N[i] = ceil(N[i] * e)

    order = max(N) + 1
    for pti in pt:
        pti.extend(order=order)

    # recompute the corresponding x-series with the extened terms
    px = [p for P in pt for p in P.xseries()]
    return px
示例#44
0
def _N0_nodenominators(p, g, n):
    """
    Return the necessary p-adic precision for the Frobenius matrix to deduce
    the characteristic polynomial of Frobenius using the Newton identities,
    using  :meth:`charpoly_frobenius`, which assumes that the Frobenius matrix
    is integral, i.e., has no denominators.


    INPUT:

    - `p` - prime
    - `g` - genus
    - `n` - degree of residue field

    TESTS::

        sage: sage.schemes.cyclic_covers.cycliccover_finite_field._N0_nodenominators(4999, 4, 5)
        11
    """
    return max(
        ceil(log(2 * (2 * g) / ZZ(i), p) + (n * i) / ZZ(2))
        for i in range(1, g + 1))
示例#45
0
def numeric_converter(value, cur=None):
    """
    Used for converting numeric values from Postgres to Python.

    INPUT:

    - ``value`` -- a string representing a decimal number.
    - ``cur`` -- a cursor, unused

    OUTPUT:

    - either a sage integer (if there is no decimal point) or a real number whose precision depends on the number of digits in value.
    """
    if value is None:
        return None
    if '.' in value:
        # The following is a good guess for the bit-precision,
        # but we use LmfdbRealLiterals to ensure that our number
        # prints the same as we got it.
        prec = ceil(len(value)*3.322)
        return LmfdbRealLiteral(RealField(prec), value)
    else:
        return Integer(value)
示例#46
0
def numeric_converter(value, cur=None):
    """
    Used for converting numeric values from Postgres to Python.

    INPUT:

    - ``value`` -- a string representing a decimal number.
    - ``cur`` -- a cursor, unused

    OUTPUT:

    - either a sage integer (if there is no decimal point) or a real number whose precision depends on the number of digits in value.
    """
    if value is None:
        return None
    if '.' in value:
        # The following is a good guess for the bit-precision,
        # but we use LmfdbRealLiterals to ensure that our number
        # prints the same as we got it.
        prec = ceil(len(value) * 3.322)
        return LmfdbRealLiteral(RealField(prec), value)
    else:
        return Integer(value)
示例#47
0
    def eisenstein_series(self, k, prec, allow_small_weight=False):
        r"""
        Compute the Eisenstein series. (i.e. the theta lift of a vector-valued Eisenstein series)

        INPUT:
        - ``k`` -- the weight (an even integer)
        - ``prec`` -- the output precision

        OUTPUT: OrthogonalModularFormLorentzian

        EXAMPLES::

            sage: from weilrep import *
            sage: OrthogonalModularForms(diagonal_matrix([-2, 2, 2])).eisenstein_series(4, 5)
            1 + 480*t + (240*x^-2 + (2880*r_0^-1 + 7680 + 2880*r_0)*x^-1 + (240*r_0^-2 + 7680*r_0^-1 + 18720 + 7680*r_0 + 240*r_0^2) + (2880*r_0^-1 + 7680 + 2880*r_0)*x + 240*x^2)*t^2 + ((480*r_0^-2 + 15360*r_0^-1 + 28800 + 15360*r_0 + 480*r_0^2)*x^-2 + (15360*r_0^-2 + 76800*r_0^-1 + 92160 + 76800*r_0 + 15360*r_0^2)*x^-1 + (28800*r_0^-2 + 92160*r_0^-1 + 134400 + 92160*r_0 + 28800*r_0^2) + (15360*r_0^-2 + 76800*r_0^-1 + 92160 + 76800*r_0 + 15360*r_0^2)*x + (480*r_0^-2 + 15360*r_0^-1 + 28800 + 15360*r_0 + 480*r_0^2)*x^2)*t^3 + (2160*x^-4 + (7680*r_0^-2 + 44160*r_0^-1 + 61440 + 44160*r_0 + 7680*r_0^2)*x^-3 + (7680*r_0^-3 + 112320*r_0^-2 + 207360*r_0^-1 + 312960 + 207360*r_0 + 112320*r_0^2 + 7680*r_0^3)*x^-2 + (44160*r_0^-3 + 207360*r_0^-2 + 380160*r_0^-1 + 430080 + 380160*r_0 + 207360*r_0^2 + 44160*r_0^3)*x^-1 + (2160*r_0^-4 + 61440*r_0^-3 + 312960*r_0^-2 + 430080*r_0^-1 + 656160 + 430080*r_0 + 312960*r_0^2 + 61440*r_0^3 + 2160*r_0^4) + (44160*r_0^-3 + 207360*r_0^-2 + 380160*r_0^-1 + 430080 + 380160*r_0 + 207360*r_0^2 + 44160*r_0^3)*x + (7680*r_0^-3 + 112320*r_0^-2 + 207360*r_0^-1 + 312960 + 207360*r_0 + 112320*r_0^2 + 7680*r_0^3)*x^2 + (7680*r_0^-2 + 44160*r_0^-1 + 61440 + 44160*r_0 + 7680*r_0^2)*x^3 + 2160*x^4)*t^4 + O(t^5)
        """
        w = self.__weilrep
        try:
            return (-((k + k) / bernoulli(k)) * w.eisenstein_series(
                k + self.input_wt(),
                ceil(prec * prec / 4) + 1,
                allow_small_weight=allow_small_weight)).theta_lift(prec)
        except (TypeError, ValueError, ZeroDivisionError):
            raise ValueError('Invalid weight') from None
示例#48
0
def _monomial_list(maxdeg, l, wy):
    r"""
    Returns a list of all non-negative integer pairs `(i,j)` such that ``i + wy
    * j < maxdeg`` and ``j \geq l``.

    INPUT:

    - ``maxdeg``, ``l``, ``wy`` -- integers.

    OUTPUT:

    - a list of pairs of integers.

    EXAMPLES::

        sage: from sage.coding.guruswami_sudan.interpolation import _monomial_list
        sage: _monomial_list(8, 1, 3)
        [(0, 0),
         (1, 0),
         (2, 0),
         (3, 0),
         (4, 0),
         (5, 0),
         (6, 0),
         (7, 0),
         (0, 1),
         (1, 1),
         (2, 1),
         (3, 1),
         (4, 1)]
    """
    monomials = []
    for y in range(0, l+1):
        for x in range(0,  ceil(maxdeg - y*wy)):
            monomials.append((x, y))
    return monomials
示例#49
0
def _monomial_list(maxdeg, l, wy):
    r"""
    Returns a list of all non-negative integer pairs `(i,j)` such that ``i + wy
    * j < maxdeg`` and ``j \geq l``.

    INPUT:

    - ``maxdeg``, ``l``, ``wy`` -- integers.

    OUTPUT:

    - a list of pairs of integers.

    EXAMPLES::

        sage: from sage.coding.guruswami_sudan.interpolation import _monomial_list
        sage: _monomial_list(8, 1, 3)
        [(0, 0),
         (1, 0),
         (2, 0),
         (3, 0),
         (4, 0),
         (5, 0),
         (6, 0),
         (7, 0),
         (0, 1),
         (1, 1),
         (2, 1),
         (3, 1),
         (4, 1)]
    """
    monomials = []
    for y in range(0, l + 1):
        for x in range(0, ceil(maxdeg - y * wy)):
            monomials.append((x, y))
    return monomials
示例#50
0
def binpacking(items,maximum=1,k=None):
    r"""
    Solves the bin packing problem.

    The Bin Packing problem is the following :

    Given a list of items of weights `p_i` and a real value `K`, what is
    the least number of bins such that all the items can be put in the
    bins, while keeping sure that each bin contains a weight of at most `K` ?

    For more informations : http://en.wikipedia.org/wiki/Bin_packing_problem

    Two version of this problem are solved by this algorithm :
         * Is it possible to put the given items in `L` bins ?
         * What is the assignment of items using the
           least number of bins with the given list of items ?

    INPUT:

    - ``items`` -- A list of real values (the items' weight)

    - ``maximum``   -- The maximal size of a bin

    - ``k``     -- Number of bins

      - When set to an integer value, the function returns a partition
        of the items into `k` bins if possible, and raises an
        exception otherwise.

      - When set to ``None``, the function returns a partition of the items
        using the least number possible of bins.

    OUTPUT:

    A list of lists, each member corresponding to a box and containing
    the list of the weights inside it. If there is no solution, an
    exception is raised (this can only happen when ``k`` is specified
    or if ``maximum`` is less that the size of one item).

    EXAMPLES:

    Trying to find the minimum amount of boxes for 5 items of weights
    `1/5, 1/4, 2/3, 3/4, 5/7`::

        sage: from sage.numerical.optimize import binpacking
        sage: values = [1/5, 1/3, 2/3, 3/4, 5/7]
        sage: bins = binpacking(values)
        sage: len(bins)
        3

    Checking the bins are of correct size ::

        sage: all([ sum(b)<= 1 for b in bins ])
        True

    Checking every item is in a bin ::

        sage: b1, b2, b3 = bins
        sage: all([ (v in b1 or v in b2 or v in b3) for v in values ])
        True

    One way to use only three boxes (which is best possible) is to put
    `1/5 + 3/4` together in a box, `1/3+2/3` in another, and `5/7`
    by itself in the third one.

    Of course, we can also check that there is no solution using only two boxes ::

        sage: from sage.numerical.optimize import binpacking
        sage: binpacking([0.2,0.3,0.8,0.9], k=2)
        Traceback (most recent call last):
        ...
        ValueError: This problem has no solution !
    """

    if max(items) > maximum:
        raise ValueError("This problem has no solution !")

    if k==None:
        from sage.functions.other import ceil
        k=ceil(sum(items)/maximum)
        while True:
            from sage.numerical.mip import MIPSolverException
            try:
                return binpacking(items,k=k,maximum=maximum)
            except MIPSolverException:
                k = k + 1

    from sage.numerical.mip import MixedIntegerLinearProgram, MIPSolverException
    p=MixedIntegerLinearProgram()

    # Boolean variable indicating whether
    # the i th element belongs to box b
    box=p.new_variable(dim=2)

    # Each bin contains at most max
    for b in range(k):
        p.add_constraint(p.sum([items[i]*box[i][b] for i in range(len(items))]),max=maximum)

    # Each item is assigned exactly one bin
    for i in range(len(items)):
        p.add_constraint(p.sum([box[i][b] for b in range(k)]),min=1,max=1)

    p.set_objective(None)
    p.set_binary(box)

    try:
        p.solve()
    except MIPSolverException:
        raise ValueError("This problem has no solution !")

    box=p.get_values(box)

    boxes=[[] for i in range(k)]

    for b in range(k):
        boxes[b].extend([items[i] for i in range(len(items)) if round(box[i][b])==1])

    return boxes
示例#51
0
 def f(x):
     if x == Infinity: return Infinity
     else: return max(x - workprec_shift, ceil(x/exp))
示例#52
0
 def sqrt(self,exp=2):
     from sage.functions.other import ceil
     precision = ceil(self._precision / exp)
     return ValuationBigOh(self.parent(), precision)
示例#53
0
    def heights(self,lowerbound,upperbound):
        """
        Return a list of permissable curve heights in the specified range
         (bounds inclusive), and for each height the equation coefficients
         that produce curves of that height.

        WARNING: This function my return heights for which only singular
                  curves exist. For example, in the short Weierstrass case
                  height 0 is permissable, as the curve Y^2 = X^3 (uniquely)
                  has height zero. 

        INPUT:

            - ``lowerbound`` -- Lower bound for the height range;
            - ``upperbound`` -- Upper bound for the height range. Heights
              returned are up to and including both bounds.

        OUTPUT:

            - A list of tuples, each consisting of three elements of the form
              (H, C, I) such that 
              H: The smallest height >= N
              C: A list of coefficients for curves of this height
              I: A list of indices indicating which of the above coefficients
              achieve this height. The remaining values in C  indicate the 
              max absolute value those coefficients are allowed to obtain
              without altering the height.

              For example, the tuple (4, [1, 2], [1]) for the short Weierstrass
              case denotes set of curves with height 4; these are all of the
              form Y^2 = X^3 + A*X + B, where B=2 and A ranges between -1 and 1.

        EXAMPLES::

            sage: from sage.schemes.elliptic_curves.curve_enumerator import *
            sage: C = CurveEnumerator(family="short_weierstrass")
            sage: C.heights(100,150) 
            [(100, [4, 10], [1]), (121, [4, 11], [1]), (125, [5, 11], [0]), (144, [5, 12], [1])]

            sage: C.heights(150,100)
            Traceback (most recent call last):
            ...
            AssertionError: Height upper bound must be greater than or equal to lower bound.
            sage: C.heights(-100,100)
            Traceback (most recent call last):
            ...
            AssertionError: Height lower bound must be non-negative.
        """

        assert lowerbound>=0, "Height lower bound must be non-negative."
        assert upperbound>=lowerbound, "Height upper bound must be greater "\
                   +"than or equal to lower bound." 

        coeffs = [ceil(lowerbound**(1/n))-1 for n in self._pows]
        height = max([coeffs[i]**(self._pows[i]) for i in range(self._num_coeffs)])

        L = []
        while height <= upperbound:
            C = self._height_increment(coeffs)
            if C[0]>upperbound:
                break
            else:
                height = C[0]
                coeffs = C[1]
                L.append(C)
        return L
示例#54
0
def binpacking(items, maximum=1, k=None, solver=None, verbose=0):
    r"""
    Solve the bin packing problem.

    The Bin Packing problem is the following :

    Given a list of items of weights `p_i` and a real value `k`, what is the
    least number of bins such that all the items can be packed in the bins,
    while ensuring that the sum of the weights of the items packed in each bin
    is at most `k` ?

    For more informations, see :wikipedia:`Bin_packing_problem`.

    Two versions of this problem are solved by this algorithm :

    - Is it possible to put the given items in `k` bins ?
    - What is the assignment of items using the least number of bins with
      the given list of items ?

    INPUT:

    - ``items`` -- list or dict; either a list of real values (the items'
      weight), or a dictionary associating to each item its weight.

    - ``maximum`` -- (default: 1); the maximal size of a bin

    - ``k`` -- integer (default: ``None``); Number of bins

      - When set to an integer value, the function returns a partition of the
        items into `k` bins if possible, and raises an exception otherwise.

      - When set to ``None``, the function returns a partition of the items
        using the least possible number of bins.

    - ``solver`` -- (default: ``None``); Specify a Linear Program (LP) solver to
      be used. If set to ``None``, the default one is used. For more information
      on LP solvers and which default solver is used, see the method
      :meth:`~sage.numerical.mip.MixedIntegerLinearProgram.solve` of the class
      :class:`~sage.numerical.mip.MixedIntegerLinearProgram`.

    - ``verbose`` -- integer (default: ``0``); sets the level of verbosity. Set
      to 0 by default, which means quiet.

    OUTPUT:

    A list of lists, each member corresponding to a bin and containing either
    the list of the weights inside it when ``items`` is a list of items' weight,
    or the list of items inside it when ``items`` is a dictionary. If there is
    no solution, an exception is raised (this can only happen when ``k`` is
    specified or if ``maximum`` is less than the weight of one item).

    EXAMPLES:

    Trying to find the minimum amount of boxes for 5 items of weights
    `1/5, 1/4, 2/3, 3/4, 5/7`::

        sage: from sage.numerical.optimize import binpacking
        sage: values = [1/5, 1/3, 2/3, 3/4, 5/7]
        sage: bins = binpacking(values)
        sage: len(bins)
        3

    Checking the bins are of correct size ::

        sage: all(sum(b) <= 1 for b in bins)
        True

    Checking every item is in a bin ::

        sage: b1, b2, b3 = bins
        sage: all((v in b1 or v in b2 or v in b3) for v in values)
        True

    And only in one bin ::

        sage: sum(len(b) for b in bins) == len(values)
        True

    One way to use only three boxes (which is best possible) is to put
    `1/5 + 3/4` together in a box, `1/3+2/3` in another, and `5/7`
    by itself in the third one.

    Of course, we can also check that there is no solution using only two boxes ::

        sage: from sage.numerical.optimize import binpacking
        sage: binpacking([0.2,0.3,0.8,0.9], k=2)
        Traceback (most recent call last):
        ...
        ValueError: this problem has no solution !

    We can also provide a dictionary keyed by items and associating to each item
    its weight. Then, the bins contain the name of the items inside it ::

        sage: values = {'a':1/5, 'b':1/3, 'c':2/3, 'd':3/4, 'e':5/7}
        sage: bins = binpacking(values)
        sage: set(flatten(bins)) == set(values.keys())
        True

    TESTS:

    Wrong type for parameter items::

        sage: binpacking(set())
        Traceback (most recent call last):
        ...
        TypeError: parameter items must be a list or a dictionary.
    """
    if isinstance(items, list):
        weight = {i:w for i,w in enumerate(items)}
    elif isinstance(items, dict):
        weight = items
    else:
        raise TypeError("parameter items must be a list or a dictionary.")

    if max(weight.values()) > maximum:
        raise ValueError("this problem has no solution !")

    if k is None:
        from sage.functions.other import ceil
        k = ceil(sum(weight.values())/maximum)
        while True:
            from sage.numerical.mip import MIPSolverException
            try:
                return binpacking(items, k=k, maximum=maximum, solver=solver, verbose=verbose)
            except MIPSolverException:
                k = k + 1

    from sage.numerical.mip import MixedIntegerLinearProgram, MIPSolverException
    p = MixedIntegerLinearProgram(solver=solver)

    # Boolean variable indicating whether the ith element belongs to box b
    box = p.new_variable(binary=True)

    # Capacity constraint of each bin
    for b in range(k):
        p.add_constraint(p.sum(weight[i]*box[i,b] for i in weight) <= maximum)

    # Each item is assigned exactly one bin
    for i in weight:
        p.add_constraint(p.sum(box[i,b] for b in range(k)) == 1)

    try:
        p.solve(log=verbose)
    except MIPSolverException:
        raise ValueError("this problem has no solution !")

    box = p.get_values(box)

    boxes = [[] for i in range(k)]

    for i,b in box:
        if box[i,b] == 1:
            boxes[b].append(weight[i] if isinstance(items, list) else i)

    return boxes
示例#55
0
文件: tides.py 项目: Findstat/sage
def genfiles_mpfr(integrator, driver, f, ics, initial, final, delta,
                  parameters = None , parameter_values = None, dig = 20, tolrel=1e-16,
                  tolabs=1e-16, output = ''):
    r"""
        Generate the needed files for the mpfr module of the tides library.

    INPUT:

    - ``integrator`` -- the name of the integrator file.

    - ``driver`` -- the name of the driver file.

    - ``f`` -- the function that determines the differential equation.

    - ``ics`` -- a list or tuple with the initial conditions.

    - ``initial`` -- the initial time for the integration.

    - ``final`` -- the final time for the integration.

    - ``delta`` -- the step of the output.

    - ``parameters`` -- the variables inside the function that should be treated
       as parameters.

    - ``parameter_values`` -- the values of the parameters for the particular
       initial value problem.

    - ``dig`` -- the number of digits of precission that will be used in the integration

    - ``tolrel`` -- the relative tolerance.

    - ``tolabs`` -- the absolute tolerance.

    -  ``output`` -- the name of the file that the compiled integrator will write to

    This function creates two files, integrator and driver, that can be used
    later with the tides library ([TI]_).


    TESTS::

        sage: from tempfile import mkdtemp
        sage: from sage.interfaces.tides import genfiles_mpfr
        sage: import os
        sage: import shutil
        sage: from sage.misc.temporary_file import tmp_dir
        sage: tempdir = tmp_dir()
        sage: intfile = os.path.join(tempdir, 'integrator.c')
        sage: drfile = os.path.join(tempdir ,'driver.c')
        sage: var('t,x,y,X,Y')
        (t, x, y, X, Y)
        sage: f(t,x,y,X,Y)=[X, Y, -x/(x^2+y^2)^(3/2), -y/(x^2+y^2)^(3/2)]
        sage: genfiles_mpfr(intfile, drfile, f, [1,0, 0, 0.2], 0, 10, 0.1, output = 'out', dig = 50)
        sage: fileint = open(intfile)
        sage: l = fileint.readlines()
        sage: fileint.close()
        sage: l[5]
        '    #include "mp_tides.h"\n'
        sage: l[15]
        '\tstatic int PARAMETERS = 0;\n'
        sage: l[25]
        '\t\tmpfrts_var_t(itd, link[5], var[3], i);\n'
        sage: l[30]
        '\t\tmpfrts_pow_t_c(itd, link[2], "-1.500000000000000000000000000000000000000000000000000", link[3], i);\n'
        sage: l[35]
        '\n'
        sage: l[36]
        '    }\n'
        sage: l[37]
        '    write_mp_solution();\n'
        sage: filedr = open(drfile)
        sage: l = filedr.readlines()
        sage: filedr.close()
        sage: l[6]
        '    #include "mpfr.h"\n'
        sage: l[16]
        '    int nfun = 0;\n'
        sage: l[26]
        '\tmpfr_set_str(v[2], "0.0000000000000000000000000000000000000000000000000000", 10, TIDES_RND);\n'
        sage: l[30]
        '\tmpfr_init2(tolabs, TIDES_PREC); \n'
        sage: l[34]
        '\tmpfr_init2(tini, TIDES_PREC); \n'
        sage: l[40]
        '\tmp_tides_delta(function_iteration, NULL, nvar, npar, nfun, v, p, tini, dt, nipt, tolrel, tolabs, NULL, fd);\n'
        sage: shutil.rmtree(tempdir)

    Check that ticket :trac:`17179` is fixed (handle expressions like `\\pi`)::

        sage: from sage.interfaces.tides import genfiles_mpfr
        sage: import os
        sage: import shutil
        sage: from sage.misc.temporary_file import tmp_dir
        sage: tempdir = tmp_dir()
        sage: intfile = os.path.join(tempdir, 'integrator.c')
        sage: drfile = os.path.join(tempdir ,'driver.c')
        sage: var('t,x,y,X,Y')
        (t, x, y, X, Y)
        sage: f(t,x,y,X,Y)=[X, Y, -x/(x^2+y^2)^(3/2), -y/(x^2+y^2)^(3/2)]
        sage: genfiles_mpfr(intfile, drfile, f, [pi, 0, 0, 0.2], 0, 10, 0.1, output = 'out', dig = 50)
        sage: fileint = open(intfile)
        sage: l = fileint.readlines()
        sage: fileint.close()
        sage: l[30]
        '\t\tmpfrts_pow_t_c(itd, link[2], "-1.500000000000000000000000000000000000000000000000000", link[3], i);\n'
        sage: filedr = open(drfile)
        sage: l = filedr.readlines()
        sage: filedr.close()
        sage: l[24]
        '\tmpfr_set_str(v[0], "3.141592653589793238462643383279502884197169399375101", 10, TIDES_RND);\n'
        sage: shutil.rmtree(tempdir)

    """
    if parameters == None:
        parameters = []
    if parameter_values == None:
        parameter_values = []
    RR = RealField(ceil(dig * 3.3219))
    l1, l2 = subexpressions_list(f, parameters)
    remove_repeated(l1, l2)
    remove_constants(l1, l2)
    l3=[]
    var = f[0].arguments()
    l0 = map(str, l1)
    lv = map(str, var)
    lp = map(str, parameters)
    for i in l2:
        oper = i[0]
        if oper in ["log", "exp", "sin", "cos", "atan", "asin", "acos"]:
            a = i[1]
            if str(a) in lv:
                l3.append((oper, 'var[{}]'.format(lv.index(str(a)))))
            elif str(a) in lp:
                l3.append((oper, 'par[{}]'.format(lp.index(str(a)))))
            else:
                l3.append((oper, 'link[{}]'.format(l0.index(str(a)))))

        else:
            a=i[1]
            b=i[2]
            sa = str(a)
            sb = str(b)
            consta=False
            constb=False

            if sa in lv:
                aa = 'var[{}]'.format(lv.index(sa))
            elif sa in l0:
                aa = 'link[{}]'.format(l0.index(sa))
            elif sa in lp:
                aa = 'par[{}]'.format(lp.index(sa))
            else:
                consta=True
                aa = RR(a).str(truncate=False)
            if sb in lv:
                bb = 'var[{}]'.format(lv.index(sb))
            elif sb in l0:
                bb = 'link[{}]'.format(l0.index(sb))
            elif sb in lp:
                bb = 'par[{}]'.format(lp.index(sb))
            else:
                constb=True
                bb = RR(b).str(truncate=False)
            if consta:
                oper += '_c'
                if not oper=='div':
                    bb, aa = aa,bb
            elif constb:
                oper += '_c'
            l3.append((oper, aa, bb))


    n = len(var)
    code = []


    l0 = lv + l0
    indices = [l0.index(str(i(*var)))+n for i in f]
    for i in range (1, n):
        aux = indices[i-1]-n
        if aux < n:
            code.append('mpfrts_var_t(itd, var[{}], var[{}], i);'.format(aux, i))
        else:
            code.append('mpfrts_var_t(itd, link[{}], var[{}], i);'.format(aux-n, i))

    for i in range(len(l3)):
        el = l3[i]
        string = "mpfrts_"
        if el[0] == 'add':
            string += 'add_t(itd, ' + el[1] + ', ' + el[2] + ', link[{}], i);'.format(i)
        elif el[0] == 'add_c':
            string += 'add_t_c(itd, "' + el[2] + '", ' + el[1] + ', link[{}], i);'.format(i)
        elif el[0] == 'mul':
            string += 'mul_t(itd, ' + el[1] + ', ' + el[2] + ', link[{}], i);'.format(i)
        elif el[0] == 'mul_c':
            string += 'mul_t_c(itd, "' + el[2] + '", ' + el[1] + ', link[{}], i);'.format(i)
        elif el[0] == 'pow_c':
            string += 'pow_t_c(itd, ' + el[1] + ', "' + el[2] + '", link[{}], i);'.format(i)
        elif el[0] == 'div':
            string += 'div_t(itd, ' + el[2] + ', ' + el[1] + ', link[{}], i);'.format(i)
        elif el[0] == 'div_c':
            string += 'div_t_cv(itd, "' + el[2] + '", ' + el[1] + ', link[{}], i);'.format(i)
        elif el[0] == 'log':
            string += 'log_t(itd, ' + el[1]  + ', link[{}], i);'.format(i)
        elif el[0] == 'exp':
            string += 'exp_t(itd, ' + el[1]  + ', link[{}], i);'.format(i)
        elif el[0] == 'sin':
            string += 'sin_t(itd, ' + el[1]  + ', link[{}], link[{}], i);'.format(i+1, i)
        elif el[0] == 'cos':
            string += 'cos_t(itd, ' + el[1]  + ', link[{}], link[{}], i);'.format(i-1, i)
        elif el[0] == 'atan':
            indarg = l0.index(str(1+l2[i][1]**2))-n
            string += 'atan_t(itd, ' + el[1] + ', link[{}], link[{}], i);'.format(indarg, i)
        elif el[0] == 'asin':
            indarg = l0.index(str(sqrt(1-l2[i][1]**2)))-n
            string += 'asin_t(itd, ' + el[1] + ', link[{}], link[{}], i);'.format(indarg, i)
        elif el[0] == 'acos':
            indarg = l0.index(str(-sqrt(1-l2[i][1]**2)))-n
            string += 'acos_t(itd, ' + el[1] + ', link[{}], link[{}], i);'.format(indarg, i)
        code.append(string)

    VAR = n-1
    PAR = len(parameters)
    TT =  len(code)+1-VAR

    outfile = open(integrator, 'a')

    auxstring = """
    /****************************************************************************
    This file has been created by Sage for its use with TIDES
    *****************************************************************************/

    #include "mp_tides.h"

    long  function_iteration(iteration_data *itd, mpfr_t t, mpfr_t v[], mpfr_t p[], int ORDER, mpfr_t *cvfd)
    {

    int i;
    int NCONST = 0;
    mpfr_t ct[0];
    """

    outfile.write(auxstring)

    outfile.write("\n\tstatic int VARIABLES = {};\n".format(VAR))
    outfile.write("\tstatic int PARAMETERS = {};\n".format(PAR))
    outfile.write("\tstatic int LINKS = {};\n".format(TT))
    outfile.write('\tstatic int   FUNCTIONS        = 0;\n')
    outfile.write('\tstatic int   POS_FUNCTIONS[1] = {0};\n')
    outfile.write('\n\tinitialize_mp_case();\n')
    outfile.write('\n\tfor(i=0;  i<=ORDER; i++) {\n')
    for i in code:
        outfile.write('\t\t'+i+'\n')

    auxstring = """
    }
    write_mp_solution();
    clear_vpl();
    clear_cts();
    return NUM_COLUMNS;
}
    """
    outfile.write(auxstring)
    outfile.close()


    npar = len(parameter_values)
    outfile = open(driver, 'a')

    auxstring = """
    /****************************************************************************
    Driver file of the mp_tides program
    This file has been created automatically by Sage
    *****************************************************************************/

    #include "mpfr.h"
    #include "mp_tides.h"
    long  function_iteration(iteration_data *itd, mpfr_t t, mpfr_t v[], mpfr_t p[], int ORDER, mpfr_t *cvfd);

    int main() {

        int i;



    int nfun = 0;
    """
    outfile.write(auxstring)
    outfile.write('\tset_precision_digits({});'.format(dig))
    outfile.write('\n\tint npar = {};\n'.format(npar))
    outfile.write('\tmpfr_t p[npar];\n')
    outfile.write('\tfor(i=0; i<npar; i++) mpfr_init2(p[i], TIDES_PREC);\n')

    for i in range(npar):
        outfile.write('\tmpfr_set_str(p[{}], "{}", 10, TIDES_RND);\n'.format(i,RR(parameter_values[i]).str(truncate=False)))
    outfile.write('\tint nvar = {};\n\tmpfr_t v[nvar];\n'.format(VAR))
    outfile.write('\tfor(i=0; i<nvar; i++) mpfr_init2(v[i], TIDES_PREC);\n')
    for i in range(len(ics)):
        outfile.write('\tmpfr_set_str(v[{}], "{}", 10, TIDES_RND);\n'.format(i,RR(ics[i]).str(truncate=False)))
    outfile.write('\tmpfr_t tolrel, tolabs;\n')
    outfile.write('\tmpfr_init2(tolrel, TIDES_PREC); \n')
    outfile.write('\tmpfr_init2(tolabs, TIDES_PREC); \n')
    outfile.write('\tmpfr_set_str(tolrel, "{}", 10, TIDES_RND);\n'.format(RR(tolrel).str(truncate=False)))
    outfile.write('\tmpfr_set_str(tolabs, "{}", 10, TIDES_RND);\n'.format(RR(tolabs).str(truncate=False)))

    outfile.write('\tmpfr_t tini, dt; \n')
    outfile.write('\tmpfr_init2(tini, TIDES_PREC); \n')
    outfile.write('\tmpfr_init2(dt, TIDES_PREC); \n')


    outfile.write('\tmpfr_set_str(tini, "{}", 10, TIDES_RND);;\n'.format(RR(initial).str(truncate=False)))
    outfile.write('\tmpfr_set_str(dt, "{}", 10, TIDES_RND);\n'.format(RR(delta).str(truncate=False)))
    outfile.write('\tint nipt = {};\n'.format(floor((final-initial)/delta)))
    outfile.write('\tFILE* fd = fopen("' + output + '", "w");\n')
    outfile.write('\tmp_tides_delta(function_iteration, NULL, nvar, npar, nfun, v, p, tini, dt, nipt, tolrel, tolabs, NULL, fd);\n')
    outfile.write('\tfclose(fd);\n\treturn 0;\n}')
    outfile.close()
示例#56
0
    def plot(self, **kwds):
        r"""
        Plot the initial triangulation associated to ``self``.

        INPUT:

        - ``radius`` - the radius of the disk; by default the length of
          the circle is the number of vertices
        - ``points_color`` - the color of the vertices; default 'black'
        - ``points_size`` - the size of the vertices; default 7
        - ``triangulation_color`` - the color of the arcs; default 'black'
        - ``triangulation_thickness`` - the thickness of the arcs; default 0.5
        - ``shading_color`` - the color of the shading used on neuter
          intervals; default 'lightgray'
        - ``reflections_color`` - the color of the reflection axes; default
          'blue'
        - ``reflections_thickness`` - the thickness of the reflection axes;
          default 1

        EXAMPLES::

            sage: Y = SineGordonYsystem('A',(6,4,3))
            sage: Y.plot()  # long time 2s
            Graphics object consisting of 219 graphics primitives
        """
        # Set up plotting options
        if 'radius' in kwds:
            radius = kwds['radius']
        else:
            radius = ceil(self.r() / (2 * pi))
        points_opts = {}
        if 'points_color' in kwds:
            points_opts['color'] = kwds['points_color']
        else:
            points_opts['color'] = 'black'
        if 'points_size' in kwds:
            points_opts['size'] = kwds['points_size']
        else:
            points_opts['size'] = 7
        triangulation_opts = {}
        if 'triangulation_color' in kwds:
            triangulation_opts['color'] = kwds['triangulation_color']
        else:
            triangulation_opts['color'] = 'black'
        if 'triangulation_thickness' in kwds:
            triangulation_opts['thickness'] = kwds['triangulation_thickness']
        else:
            triangulation_opts['thickness'] = 0.5
        shading_opts = {}
        if 'shading_color' in kwds:
            shading_opts['color'] = kwds['shading_color']
        else:
            shading_opts['color'] = 'lightgray'
        reflections_opts = {}
        if 'reflections_color' in kwds:
            reflections_opts['color'] = kwds['reflections_color']
        else:
            reflections_opts['color'] = 'blue'
        if 'reflections_thickness' in kwds:
            reflections_opts['thickness'] = kwds['reflections_thickness']
        else:
            reflections_opts['thickness'] = 1
        # Helper functions

        def triangle(x):
            (a, b) = sorted(x[:2])
            for p in self.vertices():
                if (p, a) in self.triangulation() or (a, p) in self.triangulation():
                    if (p, b) in self.triangulation() or (b, p) in self.triangulation():
                        if p < a or p > b:
                            return sorted((a, b, p))

        def plot_arc(radius, p, q, **opts):
            # TODO: THIS SHOULD USE THE EXISTING PLOT OF ARCS!
            # plot the arc from p to q differently depending on the type of self
            p = ZZ(p)
            q = ZZ(q)
            t = var('t')
            if p - q in [1, -1]:
                def f(t):
                    return (radius * cos(t), radius * sin(t))
                (p, q) = sorted([p, q])
                angle_p = vertex_to_angle(p)
                angle_q = vertex_to_angle(q)
                return parametric_plot(f(t), (t, angle_q, angle_p), **opts)
            if self.type() == 'A':
                angle_p = vertex_to_angle(p)
                angle_q = vertex_to_angle(q)
                if angle_p < angle_q:
                    angle_p += 2 * pi
                internal_angle = angle_p - angle_q
                if internal_angle > pi:
                    (angle_p, angle_q) = (angle_q + 2 * pi, angle_p)
                    internal_angle = angle_p - angle_q
                angle_center = (angle_p+angle_q) / 2
                hypotenuse = radius / cos(internal_angle / 2)
                radius_arc = hypotenuse * sin(internal_angle / 2)
                center = (hypotenuse * cos(angle_center),
                          hypotenuse * sin(angle_center))
                center_angle_p = angle_p + pi / 2
                center_angle_q = angle_q + 3 * pi / 2

                def f(t):
                    return (radius_arc * cos(t) + center[0],
                            radius_arc * sin(t) + center[1])
                return parametric_plot(f(t), (t, center_angle_p,
                                              center_angle_q), **opts)
            elif self.type() == 'D':
                if p >= q:
                    q += self.r()
                px = -2 * pi * p / self.r() + pi / 2
                qx = -2 * pi * q / self.r() + pi / 2
                arc_radius = (px - qx) / 2
                arc_center = qx + arc_radius

                def f(t):
                    return exp(I * ((cos(t) + I * sin(t)) *
                                    arc_radius + arc_center)) * radius
                return parametric_plot((real_part(f(t)), imag_part(f(t))),
                                       (t, 0, pi), **opts)

        def vertex_to_angle(v):
            # v==0 corresponds to pi/2
            return -2 * pi * RR(v) / self.r() + 5 * pi / 2

        # Begin plotting
        P = Graphics()
        # Shade neuter intervals
        neuter_intervals = [x for x in flatten(self.intervals()[:-1],
                                               max_level=1)
                            if x[2] in ["NR", "NL"]]
        shaded_triangles = map(triangle, neuter_intervals)
        for (p, q, r) in shaded_triangles:
            points = list(plot_arc(radius, p, q)[0])
            points += list(plot_arc(radius, q, r)[0])
            points += list(reversed(plot_arc(radius, p, r)[0]))
            P += polygon2d(points, **shading_opts)
        # Disk boundary
        P += circle((0, 0), radius, **triangulation_opts)
        # Triangulation
        for (p, q) in self.triangulation():
            P += plot_arc(radius, p, q, **triangulation_opts)
        if self.type() == 'D':
            s = radius / 50.0
            P += polygon2d([(s, 5 * s), (s, 7 * s),
                            (3 * s, 5 * s), (3 * s, 7 * s)],
                           color=triangulation_opts['color'])
            P += bezier_path([[(0, 0), (2 * s, 1 * s), (2 * s, 6 * s)],
                              [(2 * s, 10 * s), (s, 20 * s)],
                              [(0, 30 * s), (0, radius)]],
                             **triangulation_opts)
            P += bezier_path([[(0, 0), (-2 * s, 1 * s), (-2 * s, 6 * s)],
                              [(-2 * s, 10 * s), (-s, 20 * s)],
                              [(0, 30 * s), (0, radius)]],
                             **triangulation_opts)
            P += point((0, 0), zorder=len(P), **points_opts)
        # Vertices
        v_points = {x: (radius * cos(vertex_to_angle(x)),
                        radius * sin(vertex_to_angle(x)))
                    for x in self.vertices()}
        for v in v_points:
            P += point(v_points[v], zorder=len(P), **points_opts)
        # Reflection axes
        P += line([(0, 1.1 * radius), (0, -1.1 * radius)],
                  zorder=len(P), **reflections_opts)
        axis_angle = vertex_to_angle(-0.5 * (self.rk() + (1, 1))[1])
        (a, b) = (1.1 * radius * cos(axis_angle),
                  1.1 * radius * sin(axis_angle))
        P += line([(a, b), (-a, -b)], zorder=len(P), **reflections_opts)
        # Wrap up
        P.set_aspect_ratio(1)
        P.axes(False)
        return P
示例#57
0
    def energy_function(self):
        r"""
        Returns the energy function of `self`.

        INPUT:

        - ``self`` -- an element of a tensor product of perfect Kirillov-Reshetkhin crystals of the same level.

        OUTPUT: an integer

        The energy is only defined when ``self`` is an element of a tensor product of affine Kirillov-Reshetikhin crystals.
        In this implementation, it is assumed that ``self`` is an element of a tensor product of perfect crystals of the
        same level, see Theorem 7.5 in [SchillingTingley2011]_.

        REFERENCES:

            .. [SchillingTingley2011] A. Schilling, P. Tingley.
               Demazure crystals, Kirillov-Reshetikhin crystals, and the energy function.
               preprint arXiv:1104.2359

        EXAMPLES::

            sage: K = KirillovReshetikhinCrystal(['A',2,1],1,1)
            sage: T = TensorProductOfCrystals(K,K,K)
            sage: hw = [b for b in T if all(b.epsilon(i)==0 for i in [1,2])]
            sage: for b in hw:
            ...      print b, b.energy_function()
            ...
            [[[1]], [[1]], [[1]]] 0
            [[[1]], [[2]], [[1]]] 2
            [[[2]], [[1]], [[1]]] 1
            [[[3]], [[2]], [[1]]] 3

            sage: K = KirillovReshetikhinCrystal(['C',2,1],1,2)
            sage: T = TensorProductOfCrystals(K,K)
            sage: hw = [b for b in T if all(b.epsilon(i)==0 for i in [1,2])]
            sage: for b in hw:  # long time (5s on sage.math, 2011)
            ...       print b, b.energy_function()
            ...
            [[], []] 4
            [[], [[1, 1]]] 1
            [[[1, 1]], []] 3
            [[[1, 1]], [[1, 1]]] 0
            [[[1, 2]], [[1, 1]]] 1
            [[[2, 2]], [[1, 1]]] 2
            [[[-1, -1]], [[1, 1]]] 2
            [[[1, -1]], [[1, 1]]] 2
            [[[2, -1]], [[1, 1]]] 2

            sage: K = KirillovReshetikhinCrystal(['C',2,1],1,1)
            sage: T = TensorProductOfCrystals(K)
            sage: t = T.module_generators[0]
            sage: t.energy_function()
            Traceback (most recent call last):
            ...
            AssertionError: All crystals in the tensor product need to be perfect of the same level
        """
        C = self.parent().crystals[0]
        ell = ceil(C.s()/C.cartan_type().c()[C.r()])
        assert all(ell == K.s()/K.cartan_type().c()[K.r()] for K in self.parent().crystals), \
            "All crystals in the tensor product need to be perfect of the same level"
        t = self.parent()(*[K.module_generator() for K in self.parent().crystals])
        d = t.affine_grading()
        return d - self.affine_grading()
示例#58
0
    def guess(self, sequence, algorithm="sage"):
        """
        Return the minimal CFiniteSequence that generates the sequence.

        Assume the first value has index 0.

        INPUT:

        - ``sequence`` -- list of integers
        - ``algorithm`` -- string
            - 'sage' - the default is to use Sage's matrix kernel function
            - 'pari' - use Pari's implementation of LLL
            - 'bm' - use Sage's Berlekamp-Massey algorithm

        OUTPUT:

        - a CFiniteSequence, or 0 if none could be found

        With the default kernel method, trailing zeroes are chopped
        off before a guessing attempt. This may reduce the data
        below the accepted length of six values.

        EXAMPLES::

            sage: C.<x> = CFiniteSequences(QQ)
            sage: C.guess([1,2,4,8,16,32])
            C-finite sequence, generated by 1/(-2*x + 1)
            sage: r = C.guess([1,2,3,4,5])
            Traceback (most recent call last):
            ...
            ValueError: Sequence too short for guessing.

        With Berlekamp-Massey, if an odd number of values is given, the last one is dropped.
        So with an odd number of values the result may not generate the last value::

            sage: r = C.guess([1,2,4,8,9], algorithm='bm'); r
            C-finite sequence, generated by 1/(-2*x + 1)
            sage: r[0:5]
            [1, 2, 4, 8, 16]
        """
        S = self.polynomial_ring()
        if algorithm == "bm":
            from sage.matrix.berlekamp_massey import berlekamp_massey

            if len(sequence) < 2:
                raise ValueError("Sequence too short for guessing.")
            R = PowerSeriesRing(QQ, "x")
            if len(sequence) % 2 == 1:
                sequence = sequence[:-1]
            l = len(sequence) - 1
            denominator = S(berlekamp_massey(sequence).list()[::-1])
            numerator = R(S(sequence) * denominator, prec=l).truncate()

            return CFiniteSequence(numerator / denominator)
        elif algorithm == "pari":
            global _gp
            if len(sequence) < 6:
                raise ValueError("Sequence too short for guessing.")
            if _gp is None:
                _gp = Gp()
                _gp(
                    "ggf(v)=local(l,m,p,q,B);l=length(v);B=floor(l/2);\
                if(B<3,return(0));m=matrix(B,B,x,y,v[x-y+B+1]);\
                q=qflll(m,4)[1];if(length(q)==0,return(0));\
                p=sum(k=1,B,x^(k-1)*q[k,1]);\
                q=Pol(Pol(vector(l,n,v[l-n+1]))*p+O(x^(B+1)));\
                if(polcoeff(p,0)<0,q=-q;p=-p);q=q/p;p=Ser(q+O(x^(l+1)));\
                for(m=1,l,if(polcoeff(p,m-1)!=v[m],return(0)));q"
                )
            _gp.set("gf", sequence)
            _gp("gf=ggf(gf)")
            num = S(sage_eval(_gp.eval("Vec(numerator(gf))"))[::-1])
            den = S(sage_eval(_gp.eval("Vec(denominator(gf))"))[::-1])
            if num == 0:
                return 0
            else:
                return CFiniteSequence(num / den)
        else:
            from sage.matrix.constructor import matrix
            from sage.functions.other import floor, ceil
            from numpy import trim_zeros

            l = len(sequence)
            while l > 0 and sequence[l - 1] == 0:
                l -= 1
            sequence = sequence[:l]
            if l == 0:
                return 0
            if l < 6:
                raise ValueError("Sequence too short for guessing.")

            hl = ceil(ZZ(l) / 2)
            A = matrix([sequence[k : k + hl] for k in range(hl)])
            K = A.kernel()
            if K.dimension() == 0:
                return 0
            R = PolynomialRing(QQ, "x")
            den = R(trim_zeros(K.basis()[-1].list()[::-1]))
            if den == 1:
                return 0
            offset = next((i for i, x in enumerate(sequence) if x != 0), None)
            S = PowerSeriesRing(QQ, "x", default_prec=l - offset)
            num = S(R(sequence) * den).add_bigoh(floor(ZZ(l) / 2 + 1)).truncate()
            if num == 0 or sequence != S(num / den).list():
                return 0
            else:
                return CFiniteSequence(num / den)