Beispiel #1
0
    def _print_Derivative(self, deriv):
        # XXX use U('PARTIAL DIFFERENTIAL') here ?
        syms = list(deriv.symbols)
        syms.reverse()
        x = None
        for sym in syms:
            S = self._print(sym)
            dS= prettyForm(*S.left('d'))

            if x is None:
                x = dS
            else:
                x = prettyForm(*x.right(' '))
                x = prettyForm(*x.right(dS))

        f = prettyForm(binding=prettyForm.FUNC, *self._print(deriv.expr).parens())

        pform = prettyForm('d')
        if len(syms) > 1:
            pform = pform ** prettyForm(str(len(deriv.symbols)))

        pform = prettyForm(*pform.below(stringPict.LINE, x))
        pform.baseline = pform.baseline + 1
        pform = prettyForm(*stringPict.next(pform, f))
        return pform
Beispiel #2
0
    def _print_seq(self, seq, left=None, right=None):
        S = None

        for item in seq:
            pform = self._print(item)

            if S is None:
                # first element
                S = pform
            else:
                S = prettyForm(*stringPict.next(S, ', '))
                S = prettyForm(*stringPict.next(S, pform))

        if S is None:
            S = stringPict('')

        S = prettyForm(*S.parens(left, right, ifascii_nougly=True))
        return S
Beispiel #3
0
def test_hidden_indices_for_matrix_multiplication():
    L = TensorIndexType('Lorentz')
    S = TensorIndexType('Matind')

    m0, m1, m2, m3, m4, m5 = tensor_indices('m0:6', L)
    s0, s1, s2 = tensor_indices('s0:3', S)

    A = tensorhead('A', [L, S, S], [[1], [1], [1]], matrix_behavior=True)
    B = tensorhead('B', [L, S], [[1], [1]], matrix_behavior=True)
    D = tensorhead('D', [L, L, S, S], [[1, 1], [1, 1]], matrix_behavior=True)
    E = tensorhead('E', [L, L, L, L], [[1], [1], [1], [1]], matrix_behavior=True)
    F = tensorhead('F', [L], [[1]], matrix_behavior=True)

    assert (A(m0)) == A(m0, S.auto_left, -S.auto_right)
    assert (B(-m1)) == B(-m1, S.auto_left)

    A0 = A(m0)
    B0 = B(-m0)
    B1 = B(m1)

    assert (B1*A0*B0) == B(m1, s0)*A(m0, -s0, s1)*B(-m0, -s1)
    assert (B0*A0) == B(-m0, s0)*A(m0, -s0, -S.auto_right)
    assert (A0*B0) == A(m0, S.auto_left, s0)*B(-m0, -s0)

    C = tensorhead('C', [L, L], [[1]*2])

    assert (C(True, True)) == C(L.auto_left, -L.auto_right)

    assert (A(m0)*C(m1, -m0)) == A(m2, S.auto_left, -S.auto_right)*C(m1, -m2)

    assert (C(True, True)*C(True, True)) == C(L.auto_left, m0)*C(-m0, -L.auto_right)

    assert A(m0) == A(m0)
    assert B(-m1) == B(-m1)

    assert A(m0) - A(m0) == 0
    ts1 = A(m0)*A(m1) + A(m1)*A(m0)
    ts2 = A(m1)*A(m0) + A(m0)*A(m1)
    assert ts1 == ts2
    assert A(m0)*A(m1) + A(m1)*A(m0) == A(m1)*A(m0) + A(m0)*A(m1)

    assert A(m0) == (2*A(m0))/2
    assert A(m0) == -(-A(m0))
    assert 2*A(m0) - 3*A(m0) == -A(m0)
    assert 2*D(m0, m1) - 5*D(m1, m0) == -3*D(m0, m1)

    D0 = D(True, True, True, True)
    Aa = A(True, True, True)

    assert D0 * Aa == D(L.auto_left, m0, S.auto_left, s0)*A(-m0, -s0, -S.auto_right)
    assert D(m0, m1) == D(m0, m1, S.auto_left, -S.auto_right)

    raises(ValueError, lambda: C(True))
    raises(ValueError, lambda: C())

    raises(ValueError, lambda: E(True, True, True, True))

    # test that a delta is automatically added on missing auto-matrix indices in TensAdd
    assert F(m2)*F(m3)*F(m4)*A(m1) + E(m1, m2, m3, m4) == \
        E(m1, m2, m3, m4)*S.delta(S.auto_left, -S.auto_right) +\
        F(m2)*F(m3)*F(m4)*A(m1, S.auto_left, -S.auto_right)
    assert E(m1, m2) + F(m1)*F(m2) == E(m1, m2) + F(m1)*F(m2)*L.delta(L.auto_left, -L.auto_right)
    assert E(m1, m2)*A(m3) + F(m1)*F(m2)*F(m3) == \
        E(m1, m2, L.auto_left, -L.auto_right)*A(m3, S.auto_left, -S.auto_right) +\
        F(m1)*F(m2)*F(m3)*L.delta(L.auto_left, -L.auto_right)*S.delta(S.auto_left, -S.auto_right)

    assert L.delta() == L.delta(L.auto_left, -L.auto_right)
    assert S.delta() == S.delta(S.auto_left, -S.auto_right)

    assert L.metric() == L.metric(L.auto_left, -L.auto_right)
    assert S.metric() == S.metric(S.auto_left, -S.auto_right)
Beispiel #4
0
 def _expr_big(cls, z, n):
     return S(-1)**n*((S(1)/2 - n)*pi/sqrt(z) + I*acosh(sqrt(z))/sqrt(z))
def test_del_operator():
    # Tests for curl

    assert delop ^ Vector.zero == Vector.zero
    assert ((delop ^ Vector.zero).doit() == Vector.zero == curl(Vector.zero))
    assert delop.cross(Vector.zero) == delop ^ Vector.zero
    assert (delop ^ i).doit() == Vector.zero
    assert delop.cross(2 * y**2 * j, doit=True) == Vector.zero
    assert delop.cross(2 * y**2 * j) == delop ^ 2 * y**2 * j
    v = x * y * z * (i + j + k)
    assert ((delop ^ v).doit() == (-x * y + x * z) * i + (x * y - y * z) * j +
            (-x * z + y * z) * k == curl(v))
    assert delop ^ v == delop.cross(v)
    assert (delop.cross(
        2 * x**2 *
        j) == (Derivative(0, C.y) - Derivative(2 * C.x**2, C.z)) * C.i +
            (-Derivative(0, C.x) + Derivative(0, C.z)) * C.j +
            (-Derivative(0, C.y) + Derivative(2 * C.x**2, C.x)) * C.k)
    assert (delop.cross(2 * x**2 * j, doit=True) == 4 * x * k == curl(
        2 * x**2 * j))

    #Tests for divergence
    assert delop & Vector.zero == S(0) == divergence(Vector.zero)
    assert (delop & Vector.zero).doit() == S(0)
    assert delop.dot(Vector.zero) == delop & Vector.zero
    assert (delop & i).doit() == S(0)
    assert (delop & x**2 * i).doit() == 2 * x == divergence(x**2 * i)
    assert (delop.dot(v, doit=True) == x * y + y * z + z * x == divergence(v))
    assert delop & v == delop.dot(v)
    assert delop.dot(1/(x*y*z) * (i + j + k), doit=True) == \
           - 1 / (x*y*z**2) - 1 / (x*y**2*z) - 1 / (x**2*y*z)
    v = x * i + y * j + z * k
    assert (delop & v == Derivative(C.x, C.x) + Derivative(C.y, C.y) +
            Derivative(C.z, C.z))
    assert delop.dot(v, doit=True) == 3 == divergence(v)
    assert delop & v == delop.dot(v)
    assert simplify((delop & v).doit()) == 3

    #Tests for gradient
    assert (delop.gradient(0, doit=True) == Vector.zero == gradient(0))
    assert delop.gradient(0) == delop(0)
    assert (delop(S(0))).doit() == Vector.zero
    assert (delop(x) == (Derivative(C.x, C.x)) * C.i +
            (Derivative(C.x, C.y)) * C.j + (Derivative(C.x, C.z)) * C.k)
    assert (delop(x)).doit() == i == gradient(x)
    assert (delop(x * y * z) == (Derivative(C.x * C.y * C.z, C.x)) * C.i +
            (Derivative(C.x * C.y * C.z, C.y)) * C.j +
            (Derivative(C.x * C.y * C.z, C.z)) * C.k)
    assert (delop.gradient(x * y * z, doit=True) ==
            y * z * i + z * x * j + x * y * k == gradient(x * y * z))
    assert delop(x * y * z) == delop.gradient(x * y * z)
    assert (delop(2 * x**2)).doit() == 4 * x * i
    assert ((delop(a * sin(y) / x)).doit() == -a * sin(y) / x**2 * i +
            a * cos(y) / x * j)

    #Tests for directional derivative
    assert (Vector.zero & delop)(a) == S(0)
    assert ((Vector.zero & delop)(a)).doit() == S(0)
    assert ((v & delop)(Vector.zero)).doit() == Vector.zero
    assert ((v & delop)(S(0))).doit() == S(0)
    assert ((i & delop)(x)).doit() == 1
    assert ((j & delop)(y)).doit() == 1
    assert ((k & delop)(z)).doit() == 1
    assert ((i & delop)(x * y * z)).doit() == y * z
    assert ((v & delop)(x)).doit() == x
    assert ((v & delop)(x * y * z)).doit() == 3 * x * y * z
    assert (v & delop)(x + y + z) == C.x + C.y + C.z
    assert ((v & delop)(x + y + z)).doit() == x + y + z
    assert ((v & delop)(v)).doit() == v
    assert ((i & delop)(v)).doit() == i
    assert ((j & delop)(v)).doit() == j
    assert ((k & delop)(v)).doit() == k
    assert ((v & delop)(Vector.zero)).doit() == Vector.zero

    # Tests for laplacian on scalar fields
    assert laplacian(x * y * z) == S.Zero
    assert laplacian(x**2) == S(2)
    assert laplacian(x**2*y**2*z**2) == \
                    2*y**2*z**2 + 2*x**2*z**2 + 2*x**2*y**2
    A = CoordSys3D('A',
                   transformation="spherical",
                   variable_names=["r", "theta", "phi"])
    B = CoordSys3D('B',
                   transformation='cylindrical',
                   variable_names=["r", "theta", "z"])
    assert laplacian(A.r + A.theta +
                     A.phi) == 2 / A.r + cos(A.theta) / (A.r**2 * sin(A.theta))
    assert laplacian(B.r + B.theta + B.z) == 1 / B.r

    # Tests for laplacian on vector fields
    assert laplacian(x * y * z * (i + j + k)) == Vector.zero
    assert laplacian(x*y**2*z*(i + j + k)) == \
                            2*x*z*i + 2*x*z*j + 2*x*z*k
Beispiel #6
0
 def as_real_imag(self):
     from sympy import I
     real = (S(1) / 2) * (self + self._eval_conjugate())
     im = (self - self._eval_conjugate()) / (2 * I)
     return (real, im)
Beispiel #7
0
def gauss_laguerre(n, n_digits):
    r"""
    Computes the Gauss-Laguerre quadrature [1]_ points and weights.

    The Gauss-Laguerre quadrature approximates the integral:

    .. math::
        \int_0^{\infty} e^{-x} f(x)\,dx \approx \sum_{i=1}^n w_i f(x_i)


    The nodes `x_i` of an order `n` quadrature rule are the roots of `L_n`
    and the weights `w_i` are given by:

    .. math::
        w_i = \frac{x_i}{(n+1)^2 \left(L_{n+1}(x_i)\right)^2}

    Parameters
    ==========

    n : the order of quadrature

    n_digits : number of significant digits of the points and weights to return

    Returns
    =======

    (x, w) : the ``x`` and ``w`` are lists of points and weights as Floats.
             The points `x_i` and weights `w_i` are returned as ``(x, w)``
             tuple of lists.

    Examples
    ========

    >>> from sympy.integrals.quadrature import gauss_laguerre
    >>> x, w = gauss_laguerre(3, 5)
    >>> x
    [0.41577, 2.2943, 6.2899]
    >>> w
    [0.71109, 0.27852, 0.010389]
    >>> x, w = gauss_laguerre(6, 5)
    >>> x
    [0.22285, 1.1889, 2.9927, 5.7751, 9.8375, 15.983]
    >>> w
    [0.45896, 0.417, 0.11337, 0.010399, 0.00026102, 8.9855e-7]

    See Also
    ========

    gauss_legendre, gauss_gen_laguerre, gauss_hermite, gauss_chebyshev_t, gauss_chebyshev_u, gauss_jacobi

    References
    ==========

    .. [1] http://en.wikipedia.org/wiki/Gauss%E2%80%93Laguerre_quadrature
    .. [2] http://people.sc.fsu.edu/~jburkardt/cpp_src/laguerre_rule/laguerre_rule.html
    """
    x = Dummy("x")
    p = laguerre_poly(n, x, polys=True)
    p1 = laguerre_poly(n + 1, x, polys=True)
    xi = []
    w = []
    for r in p.real_roots():
        if isinstance(r, RootOf):
            r = r.eval_rational(S(1) / 10**(n_digits + 2))
        xi.append(r.n(n_digits))
        w.append((r / ((n + 1)**2 * p1.subs(x, r)**2)).n(n_digits))
    return xi, w
Beispiel #8
0
def gauss_gen_laguerre(n, alpha, n_digits):
    r"""
    Computes the generalized Gauss-Laguerre quadrature [1]_ points and weights.

    The generalized Gauss-Laguerre quadrature approximates the integral:

    .. math::
        \int_{0}^\infty x^{\alpha} e^{-x} f(x)\,dx \approx \sum_{i=1}^n w_i f(x_i)

    The nodes `x_i` of an order `n` quadrature rule are the roots of `L^{\alpha}_n`
    and the weights `w_i` are given by:

    .. math::
        w_i = \frac{\Gamma(\alpha+n)}{n \Gamma(n) L^{\alpha}_{n-1}(x_i) L^{\alpha+1}_{n-1}(x_i)}

    Parameters
    ==========

    n : the order of quadrature

    alpha : the exponent of the singularity, `\alpha > -1`

    n_digits : number of significant digits of the points and weights to return

    Returns
    =======

    (x, w) : the ``x`` and ``w`` are lists of points and weights as Floats.
             The points `x_i` and weights `w_i` are returned as ``(x, w)``
             tuple of lists.

    Examples
    ========

    >>> from sympy import S
    >>> from sympy.integrals.quadrature import gauss_gen_laguerre
    >>> x, w = gauss_gen_laguerre(3, -S.Half, 5)
    >>> x
    [0.19016, 1.7845, 5.5253]
    >>> w
    [1.4493, 0.31413, 0.00906]

    >>> x, w = gauss_gen_laguerre(4, 3*S.Half, 5)
    >>> x
    [0.97851, 2.9904, 6.3193, 11.712]
    >>> w
    [0.53087, 0.67721, 0.11895, 0.0023152]

    See Also
    ========

    gauss_legendre, gauss_laguerre, gauss_hermite, gauss_chebyshev_t, gauss_chebyshev_u, gauss_jacobi

    References
    ==========

    .. [1] http://en.wikipedia.org/wiki/Gauss%E2%80%93Laguerre_quadrature
    .. [2] http://people.sc.fsu.edu/~jburkardt/cpp_src/gen_laguerre_rule/gen_laguerre_rule.html
    """
    x = Dummy("x")
    p = laguerre_poly(n, x, alpha=alpha, polys=True)
    p1 = laguerre_poly(n - 1, x, alpha=alpha, polys=True)
    p2 = laguerre_poly(n - 1, x, alpha=alpha + 1, polys=True)
    xi = []
    w = []
    for r in p.real_roots():
        if isinstance(r, RootOf):
            r = r.eval_rational(S(1) / 10**(n_digits + 2))
        xi.append(r.n(n_digits))
        w.append((gamma(alpha + n) /
                  (n * gamma(n) * p1.subs(x, r) * p2.subs(x, r))).n(n_digits))
    return xi, w
Beispiel #9
0
def test_imag():
    I = S('I')
    assert julia_code(I) == "im"
    assert julia_code(5*I) == "5im"
    assert julia_code((S(3)/2)*I) == "3*im/2"
    assert julia_code(3+4*I) == "3 + 4im"
Beispiel #10
0
 def _expr_big_minus(cls, z, n):
     return HyperRep_asin1._expr_big_minus(z, n) \
         /HyperRep_power1._expr_big_minus(S(1)/2, z, n)
Beispiel #11
0
 def _expr_small_minus(cls, z):
     return HyperRep_asin1._expr_small_minus(z) \
         /HyperRep_power1._expr_small_minus(S(1)/2, z)
Beispiel #12
0
 def _expr_big_minus(cls, z, n):
     if n.is_even:
         return pi * I * n + log(S(1) / 2 + sqrt(1 + z) / 2)
     else:
         return pi * I * n + log(sqrt(1 + z) / 2 - S(1) / 2)
Beispiel #13
0
def polytope_integrate(poly, expr, **kwargs):
    """Integrates homogeneous functions over polytopes.

    This function accepts the polytope in `poly` (currently only polygons are
    implemented) and the function in `expr` (currently only
    univariate/bivariate polynomials are implemented) and returns the exact
    integral of `expr` over `poly`.
    Parameters
    ==========
    poly : The input Polygon.
    expr : The input polynomial.

    Optional Parameters:
    clockwise : Binary value to sort input points of the polygon clockwise.
    max_degree : The maximum degree of any monomial of the input polynomial.
    Examples
    ========
    >>> from sympy.abc import x, y
    >>> from sympy.geometry.polygon import Polygon
    >>> from sympy.geometry.point import Point
    >>> from sympy.integrals.intpoly import polytope_integrate
    >>> polygon = Polygon(Point(0,0), Point(0,1), Point(1,1), Point(1,0))
    >>> polys = [1, x, y, x*y, x**2*y, x*y**2]
    >>> expr = x*y
    >>> polytope_integrate(polygon, expr)
    1/4
    >>> polytope_integrate(polygon, polys, max_degree=3)
    {1: 1, x: 1/2, y: 1/2, x*y: 1/4, x*y**2: 1/6, x**2*y: 1/6}
    """
    clockwise = kwargs.get('clockwise', False)
    max_degree = kwargs.get('max_degree', None)

    if clockwise is True and isinstance(poly, Polygon):
        poly = clockwise_sort(poly)

    expr = S(expr)

    if isinstance(poly, Polygon):
        # For Vertex Representation
        hp_params = hyperplane_parameters(poly)
        facets = poly.sides
    else:
        # For Hyperplane Representation
        plen = len(poly)
        intersections = [
            intersection(poly[(i - 1) % plen], poly[i])
            for i in range(0, plen)
        ]
        hp_params = poly
        lints = len(intersections)
        facets = [
            Segment2D(intersections[i], intersections[(i + 1) % lints])
            for i in range(0, lints)
        ]

    if max_degree is not None:
        result = {}
        if not isinstance(expr, list):
            raise TypeError('Input polynomials must be list of expressions')
        result_dict = main_integrate(0, facets, hp_params, max_degree)
        for polys in expr:
            if polys not in result:
                if polys is S.Zero:
                    result[S.Zero] = S.Zero
                    continue
                integral_value = S.Zero
                monoms = decompose(polys, separate=True)
                for monom in monoms:
                    if monom.is_number:
                        integral_value += result_dict[1] * monom
                    else:
                        coeff = LC(monom)
                        integral_value += result_dict[monom / coeff] * coeff
                result[polys] = integral_value
        return result

    return main_integrate(expr, facets, hp_params)
Beispiel #14
0
def equivalence_hypergeometric(A, B, func):
    # This method for finding the equivalence is only for 2F1 type.
    # We can extend it for 1F1 and 0F1 type also.
    x = func.args[0]

    # making given equation in normal form
    I1 = factor(cancel(A.diff(x) / 2 + A**2 / 4 - B))

    # computing shifted invariant(J1) of the equation
    J1 = factor(cancel(x**2 * I1 + S(1) / 4))
    num, dem = J1.as_numer_denom()
    num = powdenest(expand(num))
    dem = powdenest(expand(dem))

    # this function will compute the different powers of variable(x) in J1.
    # then it will help in finding value of k. k is power of x such that we can express
    # J1 = x**k * J0(x**k) then all the powers in J0 become integers.
    def _power_counting(num):
        _pow = {0}
        for val in num:
            if val.has(x):
                if isinstance(val, Pow) and val.as_base_exp()[0] == x:
                    _pow.add(val.as_base_exp()[1])
                elif val == x:
                    _pow.add(val.as_base_exp()[1])
                else:
                    _pow.update(_power_counting(val.args))
        return _pow

    pow_num = _power_counting((num, ))
    pow_dem = _power_counting((dem, ))
    pow_dem.update(pow_num)

    _pow = pow_dem
    k = gcd(_pow)

    # computing I0 of the given equation
    I0 = powdenest(simplify(factor(((J1 / k**2) - S(1) / 4) / ((x**k)**2))),
                   force=True)
    I0 = factor(cancel(powdenest(I0.subs(x, x**(S(1) / k)), force=True)))
    num, dem = I0.as_numer_denom()

    max_num_pow = max(_power_counting((num, )))
    dem_args = dem.args
    sing_point = []
    dem_pow = []
    # calculating singular point of I0.
    for arg in dem_args:
        if arg.has(x):
            if isinstance(arg, Pow):
                # (x-a)**n
                dem_pow.append(arg.as_base_exp()[1])
                sing_point.append(
                    list(roots(arg.as_base_exp()[0], x).keys())[0])
            else:
                # (x-a) type
                dem_pow.append(arg.as_base_exp()[1])
                sing_point.append(list(roots(arg, x).keys())[0])

    dem_pow.sort()
    # checking if equivalence is exists or not.

    if equivalence(max_num_pow, dem_pow) == "2F1":
        return {'I0': I0, 'k': k, 'sing_point': sing_point, 'type': "2F1"}
    else:
        return None
Beispiel #15
0
    def _eval_Mod(self, q):
        n, k = self.args

        if any(x.is_integer is False for x in (n, k, q)):
            raise ValueError("Integers expected for binomial Mod")

        if all(x.is_Integer for x in (n, k, q)):
            n, k = map(int, (n, k))
            aq, res = abs(q), 1

            # handle negative integers k or n
            if k < 0:
                return S.Zero
            if n < 0:
                n = -n + k - 1
                res = -1 if k % 2 else 1

            # non negative integers k and n
            if k > n:
                return S.Zero

            isprime = aq.is_prime
            aq = int(aq)
            if isprime:
                if aq < n:
                    # use Lucas Theorem
                    N, K = n, k
                    while N or K:
                        res = res * binomial(N % aq, K % aq) % aq
                        N, K = N // aq, K // aq

                else:
                    # use Factorial Modulo
                    d = n - k
                    if k > d:
                        k, d = d, k
                    kf = 1
                    for i in range(2, k + 1):
                        kf = kf * i % aq
                    df = kf
                    for i in range(k + 1, d + 1):
                        df = df * i % aq
                    res *= df
                    for i in range(d + 1, n + 1):
                        res = res * i % aq

                    res *= pow(kf * df % aq, aq - 2, aq)
                    res %= aq

            else:
                # Binomial Factorization is performed by calculating the
                # exponents of primes <= n in `n! /(k! (n - k)!)`,
                # for non-negative integers n and k. As the exponent of
                # prime in n! is e_p(n) = [n/p] + [n/p**2] + ...
                # the exponent of prime in binomial(n, k) would be
                # e_p(n) - e_p(k) - e_p(n - k)
                M = int(_sqrt(n))
                for prime in sieve.primerange(2, n + 1):
                    if prime > n - k:
                        res = res * prime % aq
                    elif prime > n // 2:
                        continue
                    elif prime > M:
                        if n % prime < k % prime:
                            res = res * prime % aq
                    else:
                        N, K = n, k
                        exp = a = 0

                        while N > 0:
                            a = int((N % prime) < (K % prime + a))
                            N, K = N // prime, K // prime
                            exp += a

                        if exp > 0:
                            res *= pow(prime, exp, aq)
                            res %= aq

            return S(res % q)
Beispiel #16
0
 def _expr_big(cls, z, n):
     if n.is_even:
         return (n - S(1)/2)*pi*I + log(sqrt(z)/2) + I*asin(1/sqrt(z))
     else:
         return (n - S(1)/2)*pi*I + log(sqrt(z)/2) - I*asin(1/sqrt(z))
Beispiel #17
0
def test_one_is_composite():
    assert S(1).is_composite is False
Beispiel #18
0
 def _expr_small(cls, z):
     return log(S(1) / 2 + sqrt(1 - z) / 2)
Beispiel #19
0
def gauss_hermite(n, n_digits):
    r"""
    Computes the Gauss-Hermite quadrature [1]_ points and weights.

    The Gauss-Hermite quadrature approximates the integral:

    .. math::
        \int_{-\infty}^{\infty} e^{-x^2} f(x)\,dx \approx \sum_{i=1}^n w_i f(x_i)

    The nodes `x_i` of an order `n` quadrature rule are the roots of `H_n`
    and the weights `w_i` are given by:

    .. math::
        w_i = \frac{2^{n-1} n! \sqrt{\pi}}{n^2 \left(H_{n-1}(x_i)\right)^2}

    Parameters
    ==========

    n : the order of quadrature

    n_digits : number of significant digits of the points and weights to return

    Returns
    =======

    (x, w) : the ``x`` and ``w`` are lists of points and weights as Floats.
             The points `x_i` and weights `w_i` are returned as ``(x, w)``
             tuple of lists.

    Examples
    ========

    >>> from sympy.integrals.quadrature import gauss_hermite
    >>> x, w = gauss_hermite(3, 5)
    >>> x
    [-1.2247, 0, 1.2247]
    >>> w
    [0.29541, 1.1816, 0.29541]

    >>> x, w = gauss_hermite(6, 5)
    >>> x
    [-2.3506, -1.3358, -0.43608, 0.43608, 1.3358, 2.3506]
    >>> w
    [0.00453, 0.15707, 0.72463, 0.72463, 0.15707, 0.00453]

    See Also
    ========

    gauss_legendre, gauss_laguerre, gauss_gen_laguerre, gauss_chebyshev_t, gauss_chebyshev_u, gauss_jacobi

    References
    ==========

    .. [1] http://en.wikipedia.org/wiki/Gauss-Hermite_Quadrature
    .. [2] http://people.sc.fsu.edu/~jburkardt/cpp_src/hermite_rule/hermite_rule.html
    .. [3] http://people.sc.fsu.edu/~jburkardt/cpp_src/gen_hermite_rule/gen_hermite_rule.html
    """
    x = Dummy("x")
    p = hermite_poly(n, x, polys=True)
    p1 = hermite_poly(n - 1, x, polys=True)
    xi = []
    w = []
    for r in p.real_roots():
        if isinstance(r, RootOf):
            r = r.eval_rational(S(1) / 10**(n_digits + 2))
        xi.append(r.n(n_digits))
        w.append(((2**(n - 1) * factorial(n) * sqrt(pi)) /
                  (n**2 * p1.subs(x, r)**2)).n(n_digits))
    return xi, w
Beispiel #20
0
 def _expr_small_minus(cls, z):
     return log(S(1) / 2 + sqrt(1 + z) / 2)
Beispiel #21
0
def gauss_jacobi(n, alpha, beta, n_digits):
    r"""
    Computes the Gauss-Jacobi quadrature [1]_ points and weights.

    The Gauss-Jacobi quadrature of the first kind approximates the integral:

    .. math::
        \int_{-1}^1 (1-x)^\alpha (1+x)^\beta f(x)\,dx \approx \sum_{i=1}^n w_i f(x_i)

    The nodes `x_i` of an order `n` quadrature rule are the roots of `P^{(\alpha,\beta)}_n`
    and the weights `w_i` are given by:

    .. math::
        w_i = -\frac{2n+\alpha+\beta+2}{n+\alpha+\beta+1}\frac{\Gamma(n+\alpha+1)\Gamma(n+\beta+1)}
              {\Gamma(n+\alpha+\beta+1)(n+1)!} \frac{2^{\alpha+\beta}}{P'_n(x_i)
              P^{(\alpha,\beta)}_{n+1}(x_i)}

    Parameters
    ==========

    n : the order of quadrature

    alpha : the first parameter of the Jacobi Polynomial, `\alpha > -1`

    beta : the second parameter of the Jacobi Polynomial, `\beta > -1`

    n_digits : number of significant digits of the points and weights to return

    Returns
    =======

    (x, w) : the ``x`` and ``w`` are lists of points and weights as Floats.
             The points `x_i` and weights `w_i` are returned as ``(x, w)``
             tuple of lists.

    Examples
    ========

    >>> from sympy import S
    >>> from sympy.integrals.quadrature import gauss_jacobi
    >>> x, w = gauss_jacobi(3, S.Half, -S.Half, 5)
    >>> x
    [-0.90097, -0.22252, 0.62349]
    >>> w
    [1.7063, 1.0973, 0.33795]

    >>> x, w = gauss_jacobi(6, 1, 1, 5)
    >>> x
    [-0.87174, -0.5917, -0.2093, 0.2093, 0.5917, 0.87174]
    >>> w
    [0.050584, 0.22169, 0.39439, 0.39439, 0.22169, 0.050584]

    See Also
    ========

    gauss_legendre, gauss_laguerre, gauss_hermite, gauss_gen_laguerre, gauss_chebyshev_t, gauss_chebyshev_u

    References
    ==========

    .. [1] http://en.wikipedia.org/wiki/Gauss%E2%80%93Jacobi_quadrature
    .. [2] http://people.sc.fsu.edu/~jburkardt/cpp_src/jacobi_rule/jacobi_rule.html
    .. [3] http://people.sc.fsu.edu/~jburkardt/cpp_src/gegenbauer_rule/gegenbauer_rule.html
    """
    x = Dummy("x")
    p = jacobi_poly(n, alpha, beta, x, polys=True)
    pd = p.diff(x)
    pn = jacobi_poly(n + 1, alpha, beta, x, polys=True)
    xi = []
    w = []
    for r in p.real_roots():
        if isinstance(r, RootOf):
            r = r.eval_rational(S(1) / 10**(n_digits + 2))
        xi.append(r.n(n_digits))
        w.append(
            (-(2 * n + alpha + beta + 2) / (n + alpha + beta + S.One) *
             (gamma(n + alpha + 1) * gamma(n + beta + 1)) /
             (gamma(n + alpha + beta + S.One) * gamma(n + 2)) *
             2**(alpha + beta) / (pd.subs(x, r) * pn.subs(x, r))).n(n_digits))
    return xi, w
Beispiel #22
0
def test_convolution_fft():
    assert all(convolution_fft([], x, dps=y) == [] for x in ([], [1]) for y in (None, 3))
    assert convolution_fft([1, 2, 3], [4, 5, 6]) == [4, 13, 28, 27, 18]
    assert convolution_fft([1], [5, 6, 7]) == [5, 6, 7]
    assert convolution_fft([1, 3], [5, 6, 7]) == [5, 21, 25, 21]

    assert convolution_fft([1 + 2*I], [2 + 3*I]) == [-4 + 7*I]
    assert convolution_fft([1 + 2*I, 3 + 4*I, 5 + S(3)/5*I], [S(2)/5 + S(4)/7*I]) == \
            [-S(26)/35 + 48*I/35, -S(38)/35 + 116*I/35, S(58)/35 + 542*I/175]

    assert convolution_fft([S(3)/4, S(5)/6], [S(7)/8, S(1)/3, S(2)/5]) == \
                                    [S(21)/32, S(47)/48, S(26)/45, S(1)/3]

    assert convolution_fft([S(1)/9, S(2)/3, S(3)/5], [S(2)/5, S(3)/7, S(4)/9]) == \
                                [S(2)/45, S(11)/35, S(8152)/14175, S(523)/945, S(4)/15]

    assert convolution_fft([pi, E, sqrt(2)], [sqrt(3), 1/pi, 1/E]) == \
                    [sqrt(3)*pi, 1 + sqrt(3)*E, E/pi + pi*exp(-1) + sqrt(6),
                                            sqrt(2)/pi + 1, sqrt(2)*exp(-1)]

    assert convolution_fft([2321, 33123], [5321, 6321, 71323]) == \
                        [12350041, 190918524, 374911166, 2362431729]

    assert convolution_fft([312313, 31278232], [32139631, 319631]) == \
                        [10037624576503, 1005370659728895, 9997492572392]

    raises(TypeError, lambda: convolution_fft(x, y))
    raises(ValueError, lambda: convolution_fft([x, y], [y, x]))
Beispiel #23
0
def gauss_legendre(n, n_digits):
    r"""
    Computes the Gauss-Legendre quadrature [1]_ points and weights.

    The Gauss-Legendre quadrature approximates the integral:

    .. math::
        \int_{-1}^1 f(x)\,dx \approx \sum_{i=1}^n w_i f(x_i)

    The nodes `x_i` of an order `n` quadrature rule are the roots of `P_n`
    and the weights `w_i` are given by:

    .. math::
        w_i = \frac{2}{\left(1-x_i^2\right) \left(P'_n(x_i)\right)^2}

    Parameters
    ==========

    n : the order of quadrature

    n_digits : number of significant digits of the points and weights to return

    Returns
    =======

    (x, w) : the ``x`` and ``w`` are lists of points and weights as Floats.
             The points `x_i` and weights `w_i` are returned as ``(x, w)``
             tuple of lists.

    Examples
    ========

    >>> from sympy.integrals.quadrature import gauss_legendre
    >>> x, w = gauss_legendre(3, 5)
    >>> x
    [-0.7746, 0, 0.7746]
    >>> w
    [0.55556, 0.88889, 0.55556]
    >>> x, w = gauss_legendre(4, 5)
    >>> x
    [-0.86114, -0.33998, 0.33998, 0.86114]
    >>> w
    [0.34786, 0.65215, 0.65215, 0.34786]

    See Also
    ========

    gauss_laguerre, gauss_gen_laguerre, gauss_hermite, gauss_chebyshev_t, gauss_chebyshev_u, gauss_jacobi

    References
    ==========

    .. [1] http://en.wikipedia.org/wiki/Gaussian_quadrature
    .. [2] http://people.sc.fsu.edu/~jburkardt/cpp_src/legendre_rule/legendre_rule.html
    """
    x = Dummy("x")
    p = legendre_poly(n, x, polys=True)
    pd = p.diff(x)
    xi = []
    w = []
    for r in p.real_roots():
        if isinstance(r, RootOf):
            r = r.eval_rational(S(1) / 10**(n_digits + 2))
        xi.append(r.n(n_digits))
        w.append((2 / ((1 - r**2) * pd.subs(x, r)**2)).n(n_digits))
    return xi, w
Beispiel #24
0
def test_convolution_fwht():
    assert convolution_fwht([], []) == []
    assert convolution_fwht([], [1]) == []
    assert convolution_fwht([1, 2, 3], [4, 5, 6]) == [32, 13, 18, 27]

    assert convolution_fwht([S(5)/7, S(6)/8, S(7)/3], [2, 4, S(6)/7]) == \
                                    [S(45)/7, S(61)/14, S(776)/147, S(419)/42]

    a = [1, S(5)/3, sqrt(3), S(7)/5, 4 + 5*I]
    b = [94, 51, 53, 45, 31, 27, 13]
    c = [3 + 4*I, 5 + 7*I, 3, S(7)/6, 8]

    assert convolution_fwht(a, b) == [53*sqrt(3) + 366 + 155*I,
                                    45*sqrt(3) + 5848/15 + 135*I,
                                    94*sqrt(3) + 1257/5 + 65*I,
                                    51*sqrt(3) + 3974/15,
                                    13*sqrt(3) + 452 + 470*I,
                                    4513/15 + 255*I,
                                    31*sqrt(3) + 1314/5 + 265*I,
                                    27*sqrt(3) + 3676/15 + 225*I]

    assert convolution_fwht(b, c) == [1993/S(2) + 733*I, 6215/S(6) + 862*I,
        1659/S(2) + 527*I, 1988/S(3) + 551*I, 1019 + 313*I, 3955/S(6) + 325*I,
        1175/S(2) + 52*I, 3253/S(6) + 91*I]

    assert convolution_fwht(a[3:], c) == [-54/5 + 293*I/5, -1 + 204*I/5,
            133/S(15) + 35*I/6, 409/S(30) + 15*I, 56/S(5), 32 + 40*I, 0, 0]

    u, v, w, x, y, z = symbols('u v w x y z')

    assert convolution_fwht([u, v], [x, y]) == [u*x + v*y, u*y + v*x]

    assert convolution_fwht([u, v, w], [x, y]) == \
        [u*x + v*y, u*y + v*x, w*x, w*y]

    assert convolution_fwht([u, v, w], [x, y, z]) == \
        [u*x + v*y + w*z, u*y + v*x, u*z + w*x, v*z + w*y]

    raises(TypeError, lambda: convolution_fwht(x, y))
    raises(TypeError, lambda: convolution_fwht(x*y, u + v))
Beispiel #25
0
def test_polytope_integrate():
    #  Convex 2-Polytopes
    #  Vertex representation
    assert polytope_integrate(Polygon(Point(0, 0), Point(0, 2), Point(4, 0)),
                              1,
                              dims=(x, y)) == 4
    assert polytope_integrate(Polygon(Point(0, 0), Point(0, 1),
                                      Point(1, 1), Point(1, 0)), x * y) ==\
                                      S(1)/4
    assert polytope_integrate(Polygon(Point(0, 3), Point(5, 3), Point(1, 1)),
                              6 * x**2 - 40 * y) == S(-935) / 3

    assert polytope_integrate(
        Polygon(Point(0, 0), Point(0, sqrt(3)), Point(sqrt(3), sqrt(3)),
                Point(sqrt(3), 0)), 1) == 3

    hexagon = Polygon(Point(0, 0), Point(-sqrt(3) / 2,
                                         S(1) / 2),
                      Point(-sqrt(3) / 2,
                            S(3) / 2), Point(0, 2),
                      Point(sqrt(3) / 2,
                            S(3) / 2), Point(sqrt(3) / 2,
                                             S(1) / 2))

    assert polytope_integrate(hexagon, 1) == S(3 * sqrt(3)) / 2

    #  Hyperplane representation
    assert polytope_integrate([((-1, 0), 0), ((1, 2), 4), ((0, -1), 0)],
                              1,
                              dims=(x, y)) == 4
    assert polytope_integrate([((-1, 0), 0), ((0, 1), 1), ((1, 0), 1),
                               ((0, -1), 0)], x * y) == S(1) / 4
    assert polytope_integrate([((0, 1), 3), ((1, -2), -1), ((-2, -1), -3)],
                              6 * x**2 - 40 * y) == S(-935) / 3
    assert polytope_integrate([((-1, 0), 0), ((0, sqrt(3)), 3),
                               ((sqrt(3), 0), 3), ((0, -1), 0)], 1) == 3

    hexagon = [((-S(1) / 2, -sqrt(3) / 2), 0), ((-1, 0), sqrt(3) / 2),
               ((-S(1) / 2, sqrt(3) / 2), sqrt(3)),
               ((S(1) / 2, sqrt(3) / 2), sqrt(3)), ((1, 0), sqrt(3) / 2),
               ((S(1) / 2, -sqrt(3) / 2), 0)]
    assert polytope_integrate(hexagon, 1) == S(3 * sqrt(3)) / 2

    #  Non-convex polytopes
    #  Vertex representation
    assert polytope_integrate(
        Polygon(Point(-1, -1), Point(-1, 1), Point(1, 1), Point(0, 0),
                Point(1, -1)), 1) == 3
    assert polytope_integrate(
        Polygon(Point(-1, -1), Point(-1, 1), Point(0, 0), Point(1, 1),
                Point(1, -1), Point(0, 0)), 1) == 2
    #  Hyperplane representation
    assert polytope_integrate([((-1, 0), 1), ((0, 1), 1), ((1, -1), 0),
                               ((1, 1), 0), ((0, -1), 1)], 1) == 3
    assert polytope_integrate([((-1, 0), 1), ((1, 1), 0), ((-1, 1), 0),
                               ((1, 0), 1), ((-1, -1), 0), ((1, -1), 0)],
                              1) == 2

    #  Tests for 2D polytopes mentioned in Chin et al(Page 10):
    #  http://dilbert.engr.ucdavis.edu/~suku/quadrature/cls-integration.pdf
    fig1 = Polygon(Point(1.220, -0.827), Point(-1.490, -4.503),
                   Point(-3.766, -1.622), Point(-4.240, -0.091),
                   Point(-3.160, 4), Point(-0.981, 4.447), Point(0.132, 4.027))
    assert polytope_integrate(fig1, x**2 + x*y + y**2) ==\
        S(2031627344735367)/(8*10**12)

    fig2 = Polygon(Point(4.561, 2.317), Point(1.491, -1.315),
                   Point(-3.310, -3.164), Point(-4.845, -3.110),
                   Point(-4.569, 1.867))
    assert polytope_integrate(fig2, x**2 + x*y + y**2) ==\
        S(517091313866043)/(16*10**11)

    fig3 = Polygon(Point(-2.740, -1.888), Point(-3.292, 4.233),
                   Point(-2.723, -0.697), Point(-0.643, -3.151))
    assert polytope_integrate(fig3, x**2 + x*y + y**2) ==\
        S(147449361647041)/(8*10**12)

    fig4 = Polygon(Point(0.211, -4.622), Point(-2.684, 3.851),
                   Point(0.468, 4.879), Point(4.630, -1.325),
                   Point(-0.411, -1.044))
    assert polytope_integrate(fig4, x**2 + x*y + y**2) ==\
        S(180742845225803)/(10**12)

    #  Tests for many polynomials with maximum degree given(2D case).
    tri = Polygon(Point(0, 3), Point(5, 3), Point(1, 1))
    polys = []
    expr1 = x**9 * y + x**7 * y**3 + 2 * x**2 * y**8
    expr2 = x**6 * y**4 + x**5 * y**5 + 2 * y**10
    expr3 = x**10 + x**9 * y + x**8 * y**2 + x**5 * y**5
    polys.extend((expr1, expr2, expr3))
    result_dict = polytope_integrate(tri, polys, max_degree=10)
    assert result_dict[expr1] == S(615780107) / 594
    assert result_dict[expr2] == S(13062161) / 27
    assert result_dict[expr3] == S(1946257153) / 924

    #  Tests when all integral of all monomials up to a max_degree is to be
    #  calculated.
    assert polytope_integrate(Polygon(Point(0, 0), Point(0, 1), Point(1, 1),
                                      Point(1, 0)),
                              max_degree=4) == {
                                  0: 0,
                                  1: 1,
                                  x: S(1) / 2,
                                  x**2 * y**2: S(1) / 9,
                                  x**4: S(1) / 5,
                                  y**4: S(1) / 5,
                                  y: S(1) / 2,
                                  x * y**2: S(1) / 6,
                                  y**2: S(1) / 3,
                                  x**3: S(1) / 4,
                                  x**2 * y: S(1) / 6,
                                  x**3 * y: S(1) / 8,
                                  x * y: S(1) / 4,
                                  y**3: S(1) / 4,
                                  x**2: S(1) / 3,
                                  x * y**3: S(1) / 8
                              }

    #  Tests for 3D polytopes
    cube1 = [[(0, 0, 0), (0, 6, 6), (6, 6, 6), (3, 6, 0), (0, 6, 0), (6, 0, 6),
              (3, 0, 0), (0, 0, 6)], [1, 2, 3, 4], [3, 2, 5, 6], [1, 7, 5, 2],
             [0, 6, 5, 7], [1, 4, 0, 7], [0, 4, 3, 6]]
    assert polytope_integrate(cube1, 1) == S(162)

    #  3D Test cases in Chin et al(2015)
    cube2 = [[(0, 0, 0), (0, 0, 5), (0, 5, 0), (0, 5, 5), (5, 0, 0), (5, 0, 5),
              (5, 5, 0), (5, 5, 5)], [3, 7, 6, 2], [1, 5, 7, 3], [5, 4, 6, 7],
             [0, 4, 5, 1], [2, 0, 1, 3], [2, 6, 4, 0]]

    cube3 = [[(0, 0, 0), (5, 0, 0), (5, 4, 0), (3, 2, 0), (3, 5, 0), (0, 5, 0),
              (0, 0, 5), (5, 0, 5), (5, 4, 5), (3, 2, 5), (3, 5, 5),
              (0, 5, 5)], [6, 11, 5, 0], [1, 7, 6, 0], [5, 4, 3, 2, 1, 0],
             [11, 10, 4, 5], [10, 9, 3, 4], [9, 8, 2, 3], [8, 7, 1, 2],
             [7, 8, 9, 10, 11, 6]]

    cube4 = [[(0, 0, 0), (1, 0, 0), (0, 1, 0), (0, 0, 1),
              (S(1) / 4, S(1) / 4, S(1) / 4)], [0, 2, 1], [1, 3, 0], [4, 2, 3],
             [4, 3, 1], [0, 1, 2], [2, 4, 1], [0, 3, 2]]

    assert polytope_integrate(cube2, x ** 2 + y ** 2 + x * y + z ** 2) ==\
           S(15625)/4
    assert polytope_integrate(cube3, x ** 2 + y ** 2 + x * y + z ** 2) ==\
           S(33835) / 12
    assert polytope_integrate(cube4, x ** 2 + y ** 2 + x * y + z ** 2) ==\
           S(37) / 960

    #  Test cases from Mathematica's PolyhedronData library
    octahedron = [[(S(-1) / sqrt(2), 0, 0), (0, S(1) / sqrt(2), 0),
                   (0, 0, S(-1) / sqrt(2)), (0, 0, S(1) / sqrt(2)),
                   (0, S(-1) / sqrt(2), 0), (S(1) / sqrt(2), 0, 0)], [3, 4, 5],
                  [3, 5, 1], [3, 1, 0], [3, 0, 4], [4, 0, 2], [4, 2, 5],
                  [2, 0, 1], [5, 2, 1]]

    assert polytope_integrate(octahedron, 1) == sqrt(2) / 3

    great_stellated_dodecahedron =\
        [[(-0.32491969623290634095, 0, 0.42532540417601993887),
          (0.32491969623290634095, 0, -0.42532540417601993887),
          (-0.52573111211913359231, 0, 0.10040570794311363956),
          (0.52573111211913359231, 0, -0.10040570794311363956),
          (-0.10040570794311363956, -0.3090169943749474241, 0.42532540417601993887),
          (-0.10040570794311363956, 0.30901699437494742410, 0.42532540417601993887),
          (0.10040570794311363956, -0.3090169943749474241, -0.42532540417601993887),
          (0.10040570794311363956, 0.30901699437494742410, -0.42532540417601993887),
          (-0.16245984811645317047, -0.5, 0.10040570794311363956),
          (-0.16245984811645317047,  0.5, 0.10040570794311363956),
          (0.16245984811645317047,  -0.5, -0.10040570794311363956),
          (0.16245984811645317047,   0.5, -0.10040570794311363956),
          (-0.42532540417601993887, -0.3090169943749474241, -0.10040570794311363956),
          (-0.42532540417601993887, 0.30901699437494742410, -0.10040570794311363956),
          (-0.26286555605956679615, 0.1909830056250525759, -0.42532540417601993887),
          (-0.26286555605956679615, -0.1909830056250525759, -0.42532540417601993887),
          (0.26286555605956679615, 0.1909830056250525759, 0.42532540417601993887),
          (0.26286555605956679615, -0.1909830056250525759, 0.42532540417601993887),
          (0.42532540417601993887, -0.3090169943749474241, 0.10040570794311363956),
          (0.42532540417601993887, 0.30901699437494742410, 0.10040570794311363956)],
         [12, 3, 0, 6, 16], [17, 7, 0, 3, 13],
         [9, 6, 0, 7, 8], [18, 2, 1, 4, 14],
         [15, 5, 1, 2, 19], [11, 4, 1, 5, 10],
         [8, 19, 2, 18, 9], [10, 13, 3, 12, 11],
         [16, 14, 4, 11, 12], [13, 10, 5, 15, 17],
         [14, 16, 6, 9, 18], [19, 8, 7, 17, 15]]
    #  Actual volume is : 0.163118960624632
    assert Abs(polytope_integrate(great_stellated_dodecahedron, 1) -\
        0.163118960624632) < 1e-12

    expr = x**2 + y**2 + z**2
    octahedron_five_compound = [[
        (0, -0.7071067811865475244, 0), (0, 0.70710678118654752440, 0),
        (0.1148764602736805918, -0.35355339059327376220,
         -0.60150095500754567366),
        (0.1148764602736805918, 0.35355339059327376220,
         -0.60150095500754567366),
        (0.18587401723009224507, -0.57206140281768429760,
         0.37174803446018449013),
        (0.18587401723009224507, 0.57206140281768429760,
         0.37174803446018449013),
        (0.30075047750377283683, -0.21850801222441053540,
         0.60150095500754567366),
        (0.30075047750377283683, 0.21850801222441053540,
         0.60150095500754567366),
        (0.48662449473386508189, -0.35355339059327376220,
         -0.37174803446018449013),
        (0.48662449473386508189, 0.35355339059327376220,
         -0.37174803446018449013),
        (-0.60150095500754567366, 0, -0.37174803446018449013),
        (-0.30075047750377283683, -0.21850801222441053540,
         -0.60150095500754567366),
        (-0.30075047750377283683, 0.21850801222441053540,
         -0.60150095500754567366),
        (0.60150095500754567366, 0, 0.37174803446018449013),
        (0.4156269377774534286, -0.57206140281768429760, 0),
        (0.4156269377774534286, 0.57206140281768429760, 0),
        (0.37174803446018449013, 0, -0.60150095500754567366),
        (-0.4156269377774534286, -0.57206140281768429760, 0),
        (-0.4156269377774534286, 0.57206140281768429760, 0),
        (-0.67249851196395732696, -0.21850801222441053540, 0),
        (-0.67249851196395732696, 0.21850801222441053540, 0),
        (0.67249851196395732696, -0.21850801222441053540, 0),
        (0.67249851196395732696, 0.21850801222441053540, 0),
        (-0.37174803446018449013, 0, 0.60150095500754567366),
        (-0.48662449473386508189, -0.35355339059327376220,
         0.37174803446018449013),
        (-0.48662449473386508189, 0.35355339059327376220,
         0.37174803446018449013),
        (-0.18587401723009224507, -0.57206140281768429760,
         -0.37174803446018449013),
        (-0.18587401723009224507, 0.57206140281768429760,
         -0.37174803446018449013),
        (-0.11487646027368059176, -0.35355339059327376220,
         0.60150095500754567366),
        (-0.11487646027368059176, 0.35355339059327376220,
         0.60150095500754567366)
    ], [0, 10, 16], [23, 10, 0], [16, 13, 0], [0, 13, 23], [16, 10, 1],
                                [1, 10, 23], [1, 13, 16], [23, 13, 1],
                                [2, 4, 19], [22, 4, 2], [2, 19,
                                                         27], [27, 22, 2],
                                [20, 5, 3], [3, 5, 21],
                                [26, 20, 3], [3, 21, 26], [29, 19, 4],
                                [4, 22, 29], [5, 20, 28], [28, 21, 5],
                                [6, 8, 15], [17, 8, 6], [6, 15,
                                                         25], [25, 17, 6],
                                [14, 9, 7], [7, 9, 18], [24, 14,
                                                         7], [7, 18, 24],
                                [8, 12, 15], [17, 12, 8], [14, 11, 9],
                                [9, 11, 18], [11, 14, 24], [24, 18, 11],
                                [25, 15, 12], [12, 17, 25], [29, 27, 19],
                                [20, 26, 28], [28, 26, 21], [22, 27, 29]]
    assert Abs(polytope_integrate(octahedron_five_compound, expr)) - 0.353553\
        < 1e-6

    cube_five_compound = [[
        (-0.1624598481164531631, -0.5, -0.6881909602355867691),
        (-0.1624598481164531631, 0.5, -0.6881909602355867691),
        (0.1624598481164531631, -0.5, 0.68819096023558676910),
        (0.1624598481164531631, 0.5, 0.68819096023558676910),
        (-0.52573111211913359231, 0, -0.6881909602355867691),
        (0.52573111211913359231, 0, 0.68819096023558676910),
        (-0.26286555605956679615, -0.8090169943749474241,
         -0.1624598481164531631),
        (-0.26286555605956679615, 0.8090169943749474241,
         -0.1624598481164531631),
        (0.26286555605956680301, -0.8090169943749474241,
         0.1624598481164531631),
        (0.26286555605956680301, 0.8090169943749474241, 0.1624598481164531631),
        (-0.42532540417601993887, -0.3090169943749474241,
         0.68819096023558676910),
        (-0.42532540417601993887, 0.30901699437494742410,
         0.68819096023558676910),
        (0.42532540417601996609, -0.3090169943749474241,
         -0.6881909602355867691),
        (0.42532540417601996609, 0.30901699437494742410,
         -0.6881909602355867691),
        (-0.6881909602355867691, -0.5, 0.1624598481164531631),
        (-0.6881909602355867691, 0.5, 0.1624598481164531631),
        (0.68819096023558676910, -0.5, -0.1624598481164531631),
        (0.68819096023558676910, 0.5, -0.1624598481164531631),
        (-0.85065080835203998877, 0, -0.1624598481164531631),
        (0.85065080835203993218, 0, 0.1624598481164531631)
    ], [18, 10, 3, 7], [13, 19, 8, 0], [18, 0, 8, 10], [3, 19, 13, 7],
                          [18, 7, 13, 0], [8, 19, 3, 10], [6, 2, 11, 18],
                          [1, 9, 19, 12], [11, 9, 1, 18], [6, 12, 19, 2],
                          [1, 12, 6, 18], [11, 2, 19, 9], [4, 14, 11, 7],
                          [17, 5, 8, 12], [4, 12, 8, 14], [11, 5, 17, 7],
                          [4, 7, 17, 12], [8, 5, 11, 14], [6, 10, 15, 4],
                          [13, 9, 5, 16], [15, 9, 13, 4], [6, 16, 5, 10],
                          [13, 16, 6, 4], [15, 10, 5, 9], [14, 15, 1, 0],
                          [16, 17, 3, 2], [14, 2, 3, 15], [1, 17, 16, 0],
                          [14, 0, 16, 2], [3, 17, 1, 15]]
    assert Abs(polytope_integrate(cube_five_compound, expr) - 1.25) < 1e-12

    echidnahedron = [[
        (0, 0, -2.4898982848827801995), (0, 0, 2.4898982848827802734),
        (0, -4.2360679774997896964, -2.4898982848827801995),
        (0, -4.2360679774997896964, 2.4898982848827802734),
        (0, 4.2360679774997896964, -2.4898982848827801995),
        (0, 4.2360679774997896964, 2.4898982848827802734),
        (-4.0287400534704067567, -1.3090169943749474241,
         -2.4898982848827801995),
        (-4.0287400534704067567, -1.3090169943749474241,
         2.4898982848827802734),
        (-4.0287400534704067567, 1.3090169943749474241,
         -2.4898982848827801995),
        (-4.0287400534704067567, 1.3090169943749474241, 2.4898982848827802734),
        (4.0287400534704069747, -1.3090169943749474241,
         -2.4898982848827801995),
        (4.0287400534704069747, -1.3090169943749474241, 2.4898982848827802734),
        (4.0287400534704069747, 1.3090169943749474241, -2.4898982848827801995),
        (4.0287400534704069747, 1.3090169943749474241, 2.4898982848827802734),
        (-2.4898982848827801995, -3.4270509831248422723,
         -2.4898982848827801995),
        (-2.4898982848827801995, -3.4270509831248422723,
         2.4898982848827802734),
        (-2.4898982848827801995, 3.4270509831248422723,
         -2.4898982848827801995),
        (-2.4898982848827801995, 3.4270509831248422723, 2.4898982848827802734),
        (2.4898982848827802734, -3.4270509831248422723,
         -2.4898982848827801995),
        (2.4898982848827802734, -3.4270509831248422723, 2.4898982848827802734),
        (2.4898982848827802734, 3.4270509831248422723, -2.4898982848827801995),
        (2.4898982848827802734, 3.4270509831248422723, 2.4898982848827802734),
        (-4.7169310137059934362, -0.8090169943749474241,
         -1.1135163644116066184),
        (-4.7169310137059934362, 0.8090169943749474241,
         -1.1135163644116066184),
        (4.7169310137059937438, -0.8090169943749474241,
         1.11351636441160673519),
        (4.7169310137059937438, 0.8090169943749474241, 1.11351636441160673519),
        (-4.2916056095299737777, -2.1180339887498948482,
         1.11351636441160673519),
        (-4.2916056095299737777, 2.1180339887498948482,
         1.11351636441160673519),
        (4.2916056095299737777, -2.1180339887498948482,
         -1.1135163644116066184),
        (4.2916056095299737777, 2.1180339887498948482, -1.1135163644116066184),
        (-3.6034146492943870399, 0, -3.3405490932348205213),
        (3.6034146492943870399, 0, 3.3405490932348202056),
        (-3.3405490932348205213, -3.4270509831248422723,
         1.11351636441160673519),
        (-3.3405490932348205213, 3.4270509831248422723,
         1.11351636441160673519),
        (3.3405490932348202056, -3.4270509831248422723,
         -1.1135163644116066184),
        (3.3405490932348202056, 3.4270509831248422723, -1.1135163644116066184),
        (-2.9152236890588002395, -2.1180339887498948482,
         3.3405490932348202056),
        (-2.9152236890588002395, 2.1180339887498948482, 3.3405490932348202056),
        (2.9152236890588002395, -2.1180339887498948482,
         -3.3405490932348205213),
        (2.9152236890588002395, 2.1180339887498948482, -3.3405490932348205213),
        (-2.2270327288232132368, 0, -1.1135163644116066184),
        (-2.2270327288232132368, -4.2360679774997896964,
         -1.1135163644116066184),
        (-2.2270327288232132368, 4.2360679774997896964,
         -1.1135163644116066184),
        (2.2270327288232134704, 0, 1.11351636441160673519),
        (2.2270327288232134704, -4.2360679774997896964,
         1.11351636441160673519),
        (2.2270327288232134704, 4.2360679774997896964, 1.11351636441160673519),
        (-1.8017073246471935200, -1.3090169943749474241,
         1.11351636441160673519),
        (-1.8017073246471935200, 1.3090169943749474241,
         1.11351636441160673519),
        (1.8017073246471935043, -1.3090169943749474241,
         -1.1135163644116066184),
        (1.8017073246471935043, 1.3090169943749474241, -1.1135163644116066184),
        (-1.3763819204711735382, 0, -4.7169310137059934362),
        (-1.3763819204711735382, 0, 0.26286555605956679615),
        (1.37638192047117353821, 0, 4.7169310137059937438),
        (1.37638192047117353821, 0, -0.26286555605956679615),
        (-1.1135163644116066184, -3.4270509831248422723,
         -3.3405490932348205213),
        (-1.1135163644116066184, -0.8090169943749474241,
         4.7169310137059937438),
        (-1.1135163644116066184, -0.8090169943749474241,
         -0.26286555605956679615),
        (-1.1135163644116066184, 0.8090169943749474241, 4.7169310137059937438),
        (-1.1135163644116066184, 0.8090169943749474241,
         -0.26286555605956679615),
        (-1.1135163644116066184, 3.4270509831248422723,
         -3.3405490932348205213),
        (1.11351636441160673519, -3.4270509831248422723,
         3.3405490932348202056),
        (1.11351636441160673519, -0.8090169943749474241,
         -4.7169310137059934362),
        (1.11351636441160673519, -0.8090169943749474241,
         0.26286555605956679615),
        (1.11351636441160673519, 0.8090169943749474241,
         -4.7169310137059934362),
        (1.11351636441160673519, 0.8090169943749474241,
         0.26286555605956679615),
        (1.11351636441160673519, 3.4270509831248422723, 3.3405490932348202056),
        (-0.85065080835203998877, 0, 1.11351636441160673519),
        (0.85065080835203993218, 0, -1.1135163644116066184),
        (-0.6881909602355867691, -0.5, -1.1135163644116066184),
        (-0.6881909602355867691, 0.5, -1.1135163644116066184),
        (-0.6881909602355867691, -4.7360679774997896964,
         -1.1135163644116066184),
        (-0.6881909602355867691, -2.1180339887498948482,
         -1.1135163644116066184),
        (-0.6881909602355867691, 2.1180339887498948482,
         -1.1135163644116066184),
        (-0.6881909602355867691, 4.7360679774997896964,
         -1.1135163644116066184),
        (0.68819096023558676910, -0.5, 1.11351636441160673519),
        (0.68819096023558676910, 0.5, 1.11351636441160673519),
        (0.68819096023558676910, -4.7360679774997896964,
         1.11351636441160673519),
        (0.68819096023558676910, -2.1180339887498948482,
         1.11351636441160673519),
        (0.68819096023558676910, 2.1180339887498948482,
         1.11351636441160673519),
        (0.68819096023558676910, 4.7360679774997896964,
         1.11351636441160673519),
        (-0.42532540417601993887, -1.3090169943749474241,
         -4.7169310137059934362),
        (-0.42532540417601993887, -1.3090169943749474241,
         0.26286555605956679615),
        (-0.42532540417601993887, 1.3090169943749474241,
         -4.7169310137059934362),
        (-0.42532540417601993887, 1.3090169943749474241,
         0.26286555605956679615),
        (-0.26286555605956679615, -0.8090169943749474241,
         1.11351636441160673519),
        (-0.26286555605956679615, 0.8090169943749474241,
         1.11351636441160673519),
        (0.26286555605956679615, -0.8090169943749474241,
         -1.1135163644116066184),
        (0.26286555605956679615, 0.8090169943749474241,
         -1.1135163644116066184),
        (0.42532540417601996609, -1.3090169943749474241,
         4.7169310137059937438),
        (0.42532540417601996609, -1.3090169943749474241,
         -0.26286555605956679615),
        (0.42532540417601996609, 1.3090169943749474241, 4.7169310137059937438),
        (0.42532540417601996609, 1.3090169943749474241,
         -0.26286555605956679615)
    ], [9, 66, 47], [44, 62, 77], [20, 91, 49], [33, 47, 83], [3, 77, 84],
                     [12, 49, 53], [36, 84, 66], [28, 53, 62], [73, 83, 91],
                     [15, 84, 46], [25, 64, 43], [16, 58, 72], [26, 46, 51],
                     [11, 43, 74], [4, 72, 91], [60, 74, 84], [35, 91, 64],
                     [23, 51, 58], [19, 74, 77], [79, 83, 78], [6, 56, 40],
                     [76, 77, 81], [21, 78, 75], [8, 40, 58], [31, 75, 74],
                     [42, 58, 83], [41, 81, 56], [13, 75, 43], [27, 51, 47],
                     [2, 89, 71], [24, 43, 62], [17, 47, 85], [14, 71, 56],
                     [65, 85, 75], [22, 56, 51], [34, 62, 89], [5, 85, 78],
                     [32, 81, 46], [10, 53, 48], [45, 78, 64], [7, 46, 66],
                     [18, 48, 89], [37, 66, 85], [70, 89, 81], [29, 64, 53],
                     [88, 74, 1], [38, 67, 48], [42, 83, 72], [57, 1, 85],
                     [34, 48, 62], [59, 72, 87], [19, 62, 74], [63, 87, 67],
                     [17, 85, 83], [52, 75, 1], [39, 87, 49], [22, 51, 40],
                     [55, 1, 66], [29, 49, 64], [30, 40, 69], [13, 64, 75],
                     [82, 69, 87], [7, 66, 51], [90, 85, 1], [59, 69, 72],
                     [70, 81, 71], [88, 1, 84], [73, 72, 83], [54, 71, 68],
                     [5, 83, 85], [50, 68, 69], [3, 84, 81], [57, 66, 1],
                     [30, 68, 40], [28, 62, 48], [52, 1, 74], [23, 40, 51],
                     [38, 48, 86], [9, 51, 66], [80, 86, 68], [11, 74, 62],
                     [55, 84, 1], [54, 86, 71], [35, 64, 49], [90, 1, 75],
                     [41, 71, 81], [39, 49, 67], [15, 81, 84], [61, 67, 86],
                     [21, 75, 64], [24, 53, 43], [50, 69, 0], [37, 85, 47],
                     [31, 43, 75], [61, 0, 67], [27, 47, 58], [10, 67, 53],
                     [8, 58, 69], [90, 75, 85], [45, 91, 78], [80, 68, 0],
                     [36, 66, 46], [65, 78, 85], [63, 0, 87], [32, 46, 56],
                     [20, 87, 91], [14, 56, 68], [57, 85, 66], [33, 58, 47],
                     [61, 86, 0], [60, 84, 77], [37, 47, 66], [82, 0, 69],
                     [44, 77, 89], [16, 69, 58], [18, 89, 86], [55, 66, 84],
                     [26, 56, 46], [63, 67, 0], [31, 74, 43], [36, 46, 84],
                     [50, 0, 68], [25, 43, 53], [6, 68, 56], [12, 53, 67],
                     [88, 84, 74], [76, 89, 77], [82, 87, 0], [65, 75, 78],
                     [60, 77, 74], [80, 0, 86], [79, 78, 91], [2, 86, 89],
                     [4, 91, 87], [52, 74, 75], [21, 64, 78], [18, 86, 48],
                     [23, 58, 40], [5, 78, 83], [28, 48, 53], [6, 40, 68],
                     [25, 53, 64], [54, 68, 86], [33, 83, 58], [17, 83, 47],
                     [12, 67, 49], [41, 56, 71], [9, 47, 51], [35, 49, 91],
                     [2, 71, 86], [79, 91, 83], [38, 86, 67], [26, 51, 56],
                     [7, 51, 46], [4, 87, 72], [34, 89, 48], [15, 46, 81],
                     [42, 72, 58], [10, 48, 67], [27, 58, 51], [39, 67, 87],
                     [76, 81, 89], [3, 81, 77], [8, 69, 40], [29, 53, 49],
                     [19, 77, 62], [22, 40, 56], [20, 49, 87], [32, 56, 81],
                     [59, 87, 69], [24, 62, 53], [11, 62, 43], [14, 68, 71],
                     [73, 91, 72], [13, 43, 64], [70, 71, 89], [16, 72, 69],
                     [44, 89, 62], [30, 69, 68], [45, 64, 91]]
    #  Actual volume is : 51.405764746872634
    assert Abs(polytope_integrate(echidnahedron, 1) - 51.4057647468726) < 1e-12
    assert Abs(polytope_integrate(echidnahedron, expr) - 253.569603474519) <\
    1e-12

    #  Tests for many polynomials with maximum degree given(2D case).
    assert polytope_integrate(cube2, [x**2, y*z], max_degree=2) == \
        {y * z: 3125 / S(4), x ** 2: 3125 / S(3)}

    assert polytope_integrate(cube2, max_degree=2) == \
        {1: 125, x: 625 / S(2), x * z: 3125 / S(4), y: 625 / S(2),
         y * z: 3125 / S(4), z ** 2: 3125 / S(3), y ** 2: 3125 / S(3),
         z: 625 / S(2), x * y: 3125 / S(4), x ** 2: 3125 / S(3)}
Beispiel #26
0
def test_cyclic_convolution():
    # fft
    a = [1, S(5)/3, sqrt(3), S(7)/5]
    b = [9, 5, 5, 4, 3, 2]

    assert convolution([1, 2, 3], [4, 5, 6], cycle=0) == \
            convolution([1, 2, 3], [4, 5, 6], cycle=5) == \
                convolution([1, 2, 3], [4, 5, 6])

    assert convolution([1, 2, 3], [4, 5, 6], cycle=3) == [31, 31, 28]

    a = [S(1)/3, S(7)/3, S(5)/9, S(2)/7, S(5)/8]
    b = [S(3)/5, S(4)/7, S(7)/8, S(8)/9]

    assert convolution(a, b, cycle=0) == \
            convolution(a, b, cycle=len(a) + len(b) - 1)

    assert convolution(a, b, cycle=4) == [S(87277)/26460, S(30521)/11340,
                            S(11125)/4032, S(3653)/1080]

    assert convolution(a, b, cycle=6) == [S(20177)/20160, S(676)/315, S(47)/24,
                            S(3053)/1080, S(16397)/5292, S(2497)/2268]

    assert convolution(a, b, cycle=9) == \
                convolution(a, b, cycle=0) + [S.Zero]

    # ntt
    a = [2313, 5323532, S(3232), 42142, 42242421]
    b = [S(33456), 56757, 45754, 432423]

    assert convolution(a, b, prime=19*2**10 + 1, cycle=0) == \
            convolution(a, b, prime=19*2**10 + 1, cycle=8) == \
                convolution(a, b, prime=19*2**10 + 1)

    assert convolution(a, b, prime=19*2**10 + 1, cycle=5) == [96, 17146, 2664,
                                                                    15534, 3517]

    assert convolution(a, b, prime=19*2**10 + 1, cycle=7) == [4643, 3458, 1260,
                                                        15534, 3517, 16314, 13688]

    assert convolution(a, b, prime=19*2**10 + 1, cycle=9) == \
            convolution(a, b, prime=19*2**10 + 1) + [0]

    # fwht
    u, v, w, x, y = symbols('u v w x y')
    p, q, r, s, t = symbols('p q r s t')
    c = [u, v, w, x, y]
    d = [p, q, r, s, t]

    assert convolution(a, b, dyadic=True, cycle=3) == \
                        [2499522285783, 19861417974796, 4702176579021]

    assert convolution(a, b, dyadic=True, cycle=5) == [2718149225143,
            2114320852171, 20571217906407, 246166418903, 1413262436976]

    assert convolution(c, d, dyadic=True, cycle=4) == \
            [p*u + p*y + q*v + r*w + s*x + t*u + t*y,
             p*v + q*u + q*y + r*x + s*w + t*v,
             p*w + q*x + r*u + r*y + s*v + t*w,
             p*x + q*w + r*v + s*u + s*y + t*x]

    assert convolution(c, d, dyadic=True, cycle=6) == \
            [p*u + q*v + r*w + r*y + s*x + t*w + t*y,
             p*v + q*u + r*x + s*w + s*y + t*x,
             p*w + q*x + r*u + s*v,
             p*x + q*w + r*v + s*u,
             p*y + t*u,
             q*y + t*v]

    # subset
    assert convolution(a, b, subset=True, cycle=7) == [18266671799811,
                    178235365533, 213958794, 246166418903, 1413262436976,
                    2397553088697, 1932759730434]

    assert convolution(a[1:], b, subset=True, cycle=4) == \
            [178104086592, 302255835516, 244982785880, 3717819845434]

    assert convolution(a, b[:-1], subset=True, cycle=6) == [1932837114162,
            178235365533, 213958794, 245166224504, 1413262436976, 2397553088697]

    assert convolution(c, d, subset=True, cycle=3) == \
            [p*u + p*x + q*w + r*v + r*y + s*u + t*w,
             p*v + p*y + q*u + s*y + t*u + t*x,
             p*w + q*y + r*u + t*v]

    assert convolution(c, d, subset=True, cycle=5) == \
            [p*u + q*y + t*v,
             p*v + q*u + r*y + t*w,
             p*w + r*u + s*y + t*x,
             p*x + q*w + r*v + s*u,
             p*y + t*u]
Beispiel #27
0
 def delta(self):
     """ A quantity related to the convergence region of the integral,
         c.f. references. """
     return len(self.bm) + len(self.an) - S(len(self.ap) + len(self.bq))/2
Beispiel #28
0
def roots(f, *gens, **flags):
    """
    Computes symbolic roots of a univariate polynomial.

    Given a univariate polynomial f with symbolic coefficients (or
    a list of the polynomial's coefficients), returns a dictionary
    with its roots and their multiplicities.

    Only roots expressible via radicals will be returned.  To get
    a complete set of roots use RootOf class or numerical methods
    instead. By default cubic and quartic formulas are used in
    the algorithm. To disable them because of unreadable output
    set `cubics=False` or `quartics=False` respectively.

    To get roots from a specific domain set the `filter` flag with
    one of the following specifiers: Z, Q, R, I, C. By default all
    roots are returned (this is equivalent to setting `filter='C'`).

    By default a dictionary is returned giving a compact result in
    case of multiple roots.  However to get a tuple containing all
    those roots set the `multiple` flag to True.

    **Examples**

    >>> from sympy import Poly, roots
    >>> from sympy.abc import x, y

    >>> roots(x**2 - 1, x)
    {-1: 1, 1: 1}

    >>> p = Poly(x**2-1, x)
    >>> roots(p)
    {-1: 1, 1: 1}

    >>> p = Poly(x**2-y, x, y)

    >>> roots(Poly(p, x))
    {y**(1/2): 1, -y**(1/2): 1}

    >>> roots(x**2 - y, x)
    {y**(1/2): 1, -y**(1/2): 1}

    >>> roots([1, 0, -1])
    {-1: 1, 1: 1}

    """
    flags = dict(flags)

    auto = flags.pop('auto', True)
    cubics = flags.pop('cubics', True)
    quartics = flags.pop('quartics', True)
    multiple = flags.pop('multiple', False)
    filter = flags.pop('filter', None)
    predicate = flags.pop('predicate', None)

    if isinstance(f, list):
        if gens:
            raise ValueError('redundant generators given')

        x = Dummy('x')

        poly, i = {}, len(f) - 1

        for coeff in f:
            poly[i], i = sympify(coeff), i - 1

        f = Poly(poly, x, field=True)
    else:
        try:
            f = Poly(f, *gens, **flags)
        except GeneratorsNeeded:
            if multiple:
                return []
            else:
                return {}

        if f.is_multivariate:
            raise PolynomialError('multivariate polynomials are not supported')

        if auto and f.get_domain().has_Ring:
            f = f.to_field()

    x = f.gen

    def _update_dict(result, root, k):
        if root in result:
            result[root] += k
        else:
            result[root] = k

    def _try_decompose(f):
        """Find roots using functional decomposition. """
        factors, roots = f.decompose(), []

        for root in _try_heuristics(factors[0]):
            roots.append(root)

        for factor in factors[1:]:
            previous, roots = list(roots), []

            for root in previous:
                g = factor - Poly(root, x)

                for root in _try_heuristics(g):
                    roots.append(root)

        return roots

    def _try_heuristics(f):
        """Find roots using formulas and some tricks. """
        if f.is_ground:
            return []
        if f.is_monomial:
            return [S(0)] * f.degree()

        if f.length() == 2:
            if f.degree() == 1:
                return map(cancel, roots_linear(f))
            else:
                return roots_binomial(f)

        result = []

        for i in [-1, 1]:
            if not f.eval(i):
                f = f.exquo(Poly(x - i, x))
                result.append(i)
                break

        n = f.degree()

        if n == 1:
            result += map(cancel, roots_linear(f))
        elif n == 2:
            result += map(cancel, roots_quadratic(f))
        elif f.is_cyclotomic:
            result += roots_cyclotomic(f)
        elif n == 3 and cubics:
            result += roots_cubic(f)
        elif n == 4 and quartics:
            result += roots_quartic(f)

        return result

    if f.is_monomial == 1:
        if f.is_ground:
            if multiple:
                return []
            else:
                return {}
        else:
            result = {S(0): f.degree()}
    else:
        (k, ), f = f.terms_gcd()

        if not k:
            zeros = {}
        else:
            zeros = {S(0): k}

        result = {}

        if not f.get_domain().is_Exact:
            for r in f.nroots():
                _update_dict(result, r, 1)
        elif f.degree() == 1:
            result[roots_linear(f)[0]] = 1
        elif f.degree() == 2:
            for r in roots_quadratic(f):
                _update_dict(result, r, 1)
        elif f.length() == 2:
            for r in roots_binomial(f):
                _update_dict(result, r, 1)
        else:
            _, factors = Poly(f.as_expr()).factor_list()

            if len(factors) == 1 and factors[0][1] == 1:
                for root in _try_decompose(f):
                    _update_dict(result, root, 1)
            else:
                for factor, k in factors:
                    for r in _try_heuristics(Poly(factor, x, field=True)):
                        _update_dict(result, r, k)

        result.update(zeros)

    if filter not in [None, 'C']:
        handlers = {
            'Z': lambda r: r.is_Integer,
            'Q': lambda r: r.is_Rational,
            'R': lambda r: r.is_real,
            'I': lambda r: r.is_imaginary,
        }

        try:
            query = handlers[filter]
        except KeyError:
            raise ValueError("Invalid filter: %s" % filter)

        for zero in dict(result).iterkeys():
            if not query(zero):
                del result[zero]

    if predicate is not None:
        for zero in dict(result).iterkeys():
            if not predicate(zero):
                del result[zero]

    if not multiple:
        return result
    else:
        zeros = []

        for zero, k in result.iteritems():
            zeros.extend([zero] * k)

        return zeros
Beispiel #29
0
 def _expr_big_minus(cls, z, n):
     return S(-1)**n*(asinh(sqrt(z))/sqrt(z) + n*pi*I/sqrt(z))
Beispiel #30
0
    def __new__(cls,
                name,
                transformation=None,
                parent=None,
                location=None,
                rotation_matrix=None,
                vector_names=None,
                variable_names=None):
        """
        The orientation/location parameters are necessary if this system
        is being defined at a certain orientation or location wrt another.

        Parameters
        ==========

        name : str
            The name of the new CoordSys3D instance.

        transformation : Lambda, Tuple, str
            Transformation defined by transformation equations or chosen
            from predefined ones.

        location : Vector
            The position vector of the new system's origin wrt the parent
            instance.

        rotation_matrix : SymPy ImmutableMatrix
            The rotation matrix of the new coordinate system with respect
            to the parent. In other words, the output of
            new_system.rotation_matrix(parent).

        parent : CoordSys3D
            The coordinate system wrt which the orientation/location
            (or both) is being defined.

        vector_names, variable_names : iterable(optional)
            Iterables of 3 strings each, with custom names for base
            vectors and base scalars of the new system respectively.
            Used for simple str printing.

        """

        name = str(name)
        Vector = sympy.vector.Vector
        BaseVector = sympy.vector.BaseVector
        Point = sympy.vector.Point

        if not isinstance(name, string_types):
            raise TypeError("name should be a string")

        if transformation is not None:
            if (location is not None) or (rotation_matrix is not None):
                raise ValueError("specify either `transformation` or "
                                 "`location`/`rotation_matrix`")
            if isinstance(transformation, (Tuple, tuple, list)):
                if isinstance(transformation[0], MatrixBase):
                    rotation_matrix = transformation[0]
                    location = transformation[1]
                else:
                    transformation = Lambda(transformation[0],
                                            transformation[1])
            elif isinstance(transformation, Callable):
                x1, x2, x3 = symbols('x1 x2 x3', cls=Dummy)
                transformation = Lambda((x1, x2, x3),
                                        transformation(x1, x2, x3))
            elif isinstance(transformation, string_types):
                transformation = Symbol(transformation)
            elif isinstance(transformation, (Symbol, Lambda)):
                pass
            else:
                raise TypeError("transformation: "
                                "wrong type {0}".format(type(transformation)))

        # If orientation information has been provided, store
        # the rotation matrix accordingly
        if rotation_matrix is None:
            rotation_matrix = ImmutableDenseMatrix(eye(3))
        else:
            if not isinstance(rotation_matrix, MatrixBase):
                raise TypeError("rotation_matrix should be an Immutable" +
                                "Matrix instance")
            rotation_matrix = rotation_matrix.as_immutable()

        # If location information is not given, adjust the default
        # location as Vector.zero
        if parent is not None:
            if not isinstance(parent, CoordSys3D):
                raise TypeError("parent should be a " + "CoordSys3D/None")
            if location is None:
                location = Vector.zero
            else:
                if not isinstance(location, Vector):
                    raise TypeError("location should be a Vector")
                # Check that location does not contain base
                # scalars
                for x in location.free_symbols:
                    if isinstance(x, BaseScalar):
                        raise ValueError("location should not contain" +
                                         " BaseScalars")
            origin = parent.origin.locate_new(name + '.origin', location)
        else:
            location = Vector.zero
            origin = Point(name + '.origin')

        if transformation is None:
            transformation = Tuple(rotation_matrix, location)

        if isinstance(transformation, Tuple):
            lambda_transformation = CoordSys3D._compose_rotation_and_translation(
                transformation[0], transformation[1], parent)
            r, l = transformation
            l = l._projections
            lambda_lame = CoordSys3D._get_lame_coeff('cartesian')
            lambda_inverse = lambda x, y, z: r.inv() * Matrix(
                [x - l[0], y - l[1], z - l[2]])
        elif isinstance(transformation, Symbol):
            trname = transformation.name
            lambda_transformation = CoordSys3D._get_transformation_lambdas(
                trname)
            if parent is not None:
                if parent.lame_coefficients() != (S(1), S(1), S(1)):
                    raise ValueError('Parent for pre-defined coordinate '
                                     'system should be Cartesian.')
            lambda_lame = CoordSys3D._get_lame_coeff(trname)
            lambda_inverse = CoordSys3D._set_inv_trans_equations(trname)
        elif isinstance(transformation, Lambda):
            if not CoordSys3D._check_orthogonality(transformation):
                raise ValueError("The transformation equation does not "
                                 "create orthogonal coordinate system")
            lambda_transformation = transformation
            lambda_lame = CoordSys3D._calculate_lame_coeff(
                lambda_transformation)
            lambda_inverse = None
        else:
            lambda_transformation = lambda x, y, z: transformation(x, y, z)
            lambda_lame = CoordSys3D._get_lame_coeff(transformation)
            lambda_inverse = None

        if variable_names is None:
            if isinstance(transformation, Lambda):
                variable_names = ["x1", "x2", "x3"]
            elif isinstance(transformation, Symbol):
                if transformation.name is 'spherical':
                    variable_names = ["r", "theta", "phi"]
                elif transformation.name is 'cylindrical':
                    variable_names = ["r", "theta", "z"]
                else:
                    variable_names = ["x", "y", "z"]
            else:
                variable_names = ["x", "y", "z"]
        if vector_names is None:
            vector_names = ["i", "j", "k"]

        # All systems that are defined as 'roots' are unequal, unless
        # they have the same name.
        # Systems defined at same orientation/position wrt the same
        # 'parent' are equal, irrespective of the name.
        # This is true even if the same orientation is provided via
        # different methods like Axis/Body/Space/Quaternion.
        # However, coincident systems may be seen as unequal if
        # positioned/oriented wrt different parents, even though
        # they may actually be 'coincident' wrt the root system.
        if parent is not None:
            obj = super(CoordSys3D, cls).__new__(cls, Symbol(name),
                                                 transformation, parent)
        else:
            obj = super(CoordSys3D, cls).__new__(cls, Symbol(name),
                                                 transformation)
        obj._name = name
        # Initialize the base vectors

        _check_strings('vector_names', vector_names)
        vector_names = list(vector_names)
        latex_vects = [(r'\mathbf{\hat{%s}_{%s}}' % (x, name))
                       for x in vector_names]
        pretty_vects = ['%s_%s' % (x, name) for x in vector_names]

        obj._vector_names = vector_names

        v1 = BaseVector(0, obj, pretty_vects[0], latex_vects[0])
        v2 = BaseVector(1, obj, pretty_vects[1], latex_vects[1])
        v3 = BaseVector(2, obj, pretty_vects[2], latex_vects[2])

        obj._base_vectors = (v1, v2, v3)

        # Initialize the base scalars

        _check_strings('variable_names', vector_names)
        variable_names = list(variable_names)
        latex_scalars = [(r"\mathbf{{%s}_{%s}}" % (x, name))
                         for x in variable_names]
        pretty_scalars = ['%s_%s' % (x, name) for x in variable_names]

        obj._variable_names = variable_names
        obj._vector_names = vector_names

        x1 = BaseScalar(0, obj, pretty_scalars[0], latex_scalars[0])
        x2 = BaseScalar(1, obj, pretty_scalars[1], latex_scalars[1])
        x3 = BaseScalar(2, obj, pretty_scalars[2], latex_scalars[2])

        obj._base_scalars = (x1, x2, x3)

        obj._transformation = transformation
        obj._transformation_lambda = lambda_transformation
        obj._lame_coefficients = lambda_lame(x1, x2, x3)
        obj._transformation_from_parent_lambda = lambda_inverse

        setattr(obj, variable_names[0], x1)
        setattr(obj, variable_names[1], x2)
        setattr(obj, variable_names[2], x3)

        setattr(obj, vector_names[0], v1)
        setattr(obj, vector_names[1], v2)
        setattr(obj, vector_names[2], v3)

        # Assign params
        obj._parent = parent
        if obj._parent is not None:
            obj._root = obj._parent._root
        else:
            obj._root = obj

        obj._parent_rotation_matrix = rotation_matrix
        obj._origin = origin

        # Return the instance
        return obj
Beispiel #31
0
    def _print_Integral(self, integral):
        f   = integral.function

        # Add parentheses if a sum and create pretty form for argument
        prettyF = self._print(f)
        # XXX generalize parents
        if f.is_Add:
            prettyF = prettyForm(*prettyF.parens())

        # dx dy dz ...
        arg = prettyF
        for x,ab in integral.limits:
            prettyArg = self._print(x)
            # XXX qparens   (parens if needs-parens)
            if prettyArg.width() > 1:
                prettyArg = prettyForm(*prettyArg.parens())

            arg = prettyForm(*arg.right(' d', prettyArg))


        # \int \int \int ...
        firstterm = True
        S = None
        for x,ab in integral.limits:
            # Create bar based on the height of the argument
            h = arg.height()
            H = h+2

            # XXX hack!
            ascii_mode = not pretty_use_unicode()
            if ascii_mode:
                H += 2

            vint= vobj('int', H)

            # Construct the pretty form with the integral sign and the argument
            pform = prettyForm(vint)
            #pform.baseline = pform.height()//2  # vcenter
            pform.baseline = arg.baseline + (H-h)//2    # covering the whole argument


            if ab is not None:
                # Create pretty forms for endpoints, if definite integral
                prettyA = self._print(ab[0])
                prettyB = self._print(ab[1])

                if ascii_mode:  # XXX hack
                    # Add spacing so that endpoint can more easily be
                    # identified with the correct integral sign
                    spc = max(1, 3 - prettyB.width())
                    prettyB = prettyForm(*prettyB.left(' ' * spc))

                    spc = max(1, 4 - prettyA.width())
                    prettyA = prettyForm(*prettyA.right(' ' * spc))

                pform = prettyForm(*pform.above(prettyB))
                pform = prettyForm(*pform.below(prettyA))

                #if ascii_mode:  # XXX hack
                #    # too much vspace beetween \int and argument
                #    # but I left it as is
                #    pform = prettyForm(*pform.right(' '))

            if not ascii_mode:  # XXX hack
                pform = prettyForm(*pform.right(' '))

            if firstterm:
                S = pform   # first term
                firstterm = False
            else:
                S = prettyForm(*S.left(pform))

        pform = prettyForm(*arg.left(S))
        return pform
def test_imag():
    I = S('I')
    assert mcode(I) == "1i"
    assert mcode(5 * I) == "5i"
    assert mcode((S(3) / 2) * I) == "3*1i/2"
    assert mcode(3 + 4 * I) == "3 + 4i"
Beispiel #33
0
def test_suitable_origin():
    assert Hyper_Function((S(1) / 2, ),
                          (S(3) / 2, ))._is_suitable_origin() is True
    assert Hyper_Function((S(1) / 2, ),
                          (S(1) / 2, ))._is_suitable_origin() is False
    assert Hyper_Function((S(1) / 2, ),
                          (-S(1) / 2, ))._is_suitable_origin() is False
    assert Hyper_Function((S(1) / 2, ), (0, ))._is_suitable_origin() is False
    assert Hyper_Function((S(1) / 2, ), (
        -1,
        1,
    ))._is_suitable_origin() is False
    assert Hyper_Function((S(1) / 2, 0), (1, ))._is_suitable_origin() is False
    assert Hyper_Function((S(1) / 2, 1),
                          (2, -S(2) / 3))._is_suitable_origin() is True
    assert Hyper_Function(
        (S(1) / 2, 1), (2, -S(2) / 3, S(3) / 2))._is_suitable_origin() is True
Beispiel #34
0
def point_sort(poly, normal=None, clockwise=True):
    """Returns the same polygon with points sorted in clockwise or
    anti-clockwise order.

    Note that it's necessary for input points to be sorted in some order
    (clockwise or anti-clockwise) for the integration algorithm to work.
    As a convention algorithm has been implemented keeping clockwise
    orientation in mind.

    Parameters
    ==========

    poly: 2D or 3D Polygon

    Optional Parameters:
    ---------------------

    normal : The normal of the plane which the 3-Polytope is a part of.
    clockwise : Returns points sorted in clockwise order if True and
    anti-clockwise if False.

    Examples
    ========

    >>> from sympy.integrals.intpoly import point_sort
    >>> from sympy.geometry.point import Point
    >>> point_sort([Point(0, 0), Point(1, 0), Point(1, 1)])
    [Point2D(1, 1), Point2D(1, 0), Point2D(0, 0)]
    """
    n = len(poly)
    if n < 2:
        return poly

    order = S(1) if clockwise else S(-1)
    dim = len(poly[0])
    if dim == 2:
        center = Point(
            sum(map(lambda vertex: vertex.x, poly)) / n,
            sum(map(lambda vertex: vertex.y, poly)) / n)
    else:
        center = Point(
            sum(map(lambda vertex: vertex.x, poly)) / n,
            sum(map(lambda vertex: vertex.y, poly)) / n,
            sum(map(lambda vertex: vertex.z, poly)) / n)

    def compare(a, b):
        if a.x - center.x >= S.Zero and b.x - center.x < S.Zero:
            return -order
        elif a.x - center.x < S.Zero and b.x - center.x >= S.Zero:
            return order
        elif a.x - center.x == S.Zero and b.x - center.x == S.Zero:
            if a.y - center.y >= S.Zero or b.y - center.y >= S.Zero:
                return -order if a.y > b.y else order
            return -order if b.y > a.y else order

        det = (a.x - center.x) * (b.y - center.y) -\
              (b.x - center.x) * (a.y - center.y)
        if det < S.Zero:
            return -order
        elif det > S.Zero:
            return order

        first = (a.x - center.x) * (a.x - center.x) +\
                (a.y - center.y) * (a.y - center.y)
        second = (b.x - center.x) * (b.x - center.x) +\
                 (b.y - center.y) * (b.y - center.y)
        return -order if first > second else order

    def compare3d(a, b):
        det = cross_product(center, a, b)
        dot_product = sum([det[i] * normal[i] for i in range(0, 3)])
        if dot_product < S.Zero:
            return -order
        elif dot_product > S.Zero:
            return order

    if dim == 2:
        return sorted(poly, key=cmp_to_key(compare))
    return sorted(poly, key=cmp_to_key(compare3d))