Ejemplo n.º 1
0
def implicitize_3d(x_fn, y_fn, z_fn, s, t):
    """Implicitize a 3D parametric triangle.

    Args:
        x_fn (sympy.Expr): Function :math:`x(s)` in the triangle.
        y_fn (sympy.Expr): Function :math:`y(s)` in the triangle.
        z_fn (sympy.Expr): Function :math:`z(s)` in the triangle.
        s (sympy.Symbol): The first symbol used to define ``x_fn``, ``y_fn``
            and ``z_fn``.
        t (sympy.Symbol): The second symbol used to define ``x_fn``, ``y_fn``
            and ``z_fn``.

    Returns:
        sympy.Expr: The implicitized function :math:`f(x, y, z)` such that the
        triangle satisfies :math:`f(x(s, t), y(s, t), z(s, t)) = 0`.
    """
    # NOTE: We import SymPy at runtime to avoid the import-time cost for users
    #       that don't want to do symbolic computation. The ``sympy`` import is
    #       a tad expensive.
    import sympy  # pylint: disable=import-outside-toplevel

    x_sym, y_sym, z_sym = sympy.symbols("x, y, z")

    f_xy = sympy.resultant(x_fn - x_sym, y_fn - y_sym, s)
    f_yz = sympy.resultant(y_fn - x_sym, z_fn - z_sym, s)
    return sympy.resultant(f_xy, f_yz, t).factor()
Ejemplo n.º 2
0
def implicit_quadratic():
    x, y, t = map(Symbol, ['x', 'y', 't'])
    a2, a1, a0 = map(Symbol, ['a2', 'a1', 'a0'])
    b2, b1, b0 = map(Symbol, ['b2', 'b1', 'b0'])
    P1 = Poly(a2 * t**2 + a1 * t + a0 - x, t)
    P2 = Poly(b2 * t**2 + b1 * t + b0 - y, t)
    P = Poly(resultant(P1, P2), x, y)

    print(P)
    return P
Ejemplo n.º 3
0
def implicit_linear():
    x, y, t = map(Symbol, ['x', 'y', 't'])
    a1, a0 = map(Symbol, ['a1', 'a0'])
    b1, b0 = map(Symbol, ['b1', 'b0'])
    P1 = Poly(a1 * t + a0 - x, t)
    P2 = Poly(b1 * t + b0 - y, t)
    P = Poly(resultant(P1, P2), x, y)

    print(P)
    return P
Ejemplo n.º 4
0
def implicit_cubic():
    x, y, t = map(Symbol, ['x', 'y', 't'])
    a3, a2, a1, a0 = map(Symbol, ['a3', 'a2', 'a1', 'a0'])
    b3, b2, b1, b0 = map(Symbol, ['b3', 'b2', 'b1', 'b0'])
    P1 = Poly(a3 * t**3 + a2 * t**2 + a1 * t + a0 - x, t)
    P2 = Poly(b3 * t**3 + b2 * t**2 + b1 * t + b0 - y, t)
    P = Poly(resultant(P1, P2), x, y)

    #print(P)
    return P
Ejemplo n.º 5
0
    def discriminant_points(self):
        """Returns the ordered discriminant points of the curve.

        The discriminant points are ordered by increasing argument with
        the base point.

        """
        if not self._discriminant_points is None:
            return self._discriminant_points

        f = self.RS.f
        x = self.RS.x
        y = self.RS.y
        p = sympy.Poly(f, [x,y])
        res = sympy.Poly(sympy.resultant(p, p.diff(y), y), x)

        # Compute the numerical roots. Since Sympy has issues balancing
        # between precision and speed we compute the roots of each
        # factor of the resultant.
        dps = sympy.mpmath.mp.dps
        rts = []
        for factor,degree in res.factor_list_include():
            rts.extend(factor.nroots(n=dps+3))
        rts = map(lambda z: z.as_real_imag(), rts)
        disc_pts = map(lambda z: sympy.mpmath.mpc(*z), rts)

        # Pop any roots that appear to be equal up to the set
        # multiprecision. Geometrically, this may cause two roots to be
        # interpreted as one thus reducing the genus of the curve.
        N = len(disc_pts)
        i = 0
        while i < N:
            k = 0
            while k < N:
                eq = sympy.mpmath.almosteq(disc_pts[i], disc_pts[k])
                if (k != i) and eq:
                    disc_pts.remove(disc_pts[k])
                    N -= 1
                else:
                    k += 1
            i += 1

        # sort the discriminant points first by argument with the base
        # point and then by distance from the base point.
        def cmp(z, a=None):
            return (sympy.mpmath.arg(z - a), sympy.mpmath.absmax(z - a))

        # determine the base point
        if self._base_point is None:
            a = min([numpy.complex(bi).real - 1 for bi in disc_pts])
            self._base_point = a

        disc_pts = sorted(disc_pts, key=lambda z: cmp(z, a=self._base_point))
        self._discriminant_points = numpy.array(disc_pts, dtype=numpy.complex)
        return self._discriminant_points
Ejemplo n.º 6
0
def implicitize_3d(x_fn, y_fn, z_fn, s, t):
    """Implicitize a 3D parametric triangle.

    Args:
        x_fn (sympy.Expr): Function :math:`x(s)` in the triangle.
        y_fn (sympy.Expr): Function :math:`y(s)` in the triangle.
        z_fn (sympy.Expr): Function :math:`z(s)` in the triangle.
        s (sympy.Symbol): The first symbol used to define ``x_fn``, ``y_fn``
            and ``z_fn``.
        t (sympy.Symbol): The second symbol used to define ``x_fn``, ``y_fn``
            and ``z_fn``.

    Returns:
        sympy.Expr: The implicitized function :math:`f(x, y, z)` such that the
        triangle satisfies :math:`f(x(s, t), y(s, t), z(s, t)) = 0`.
    """
    x_sym, y_sym, z_sym = sympy.symbols("x, y, z")

    f_xy = sympy.resultant(x_fn - x_sym, y_fn - y_sym, s)
    f_yz = sympy.resultant(y_fn - x_sym, z_fn - z_sym, s)
    return sympy.resultant(f_xy, f_yz, t).factor()
Ejemplo n.º 7
0
def implicitize_2d(x_fn, y_fn, s):
    """Implicitize a 2D parametric curve.

    Args:
        x_fn (sympy.Expr): Function :math:`x(s)` in the curve.
        y_fn (sympy.Expr): Function :math:`y(s)` in the curve.
        s (sympy.Symbol): The symbol used to define ``x_fn`` and ``y_fn``.

    Returns:
        sympy.Expr: The implicitized function :math:`f(x, y)` such that the
        curve satisfies :math:`f(x(s), y(s)) = 0`.
    """
    x_sym, y_sym = sympy.symbols("x, y")
    return sympy.resultant(x_fn - x_sym, y_fn - y_sym, s).factor()
Ejemplo n.º 8
0
def implicitize_2d(x_fn, y_fn, s):
    """Implicitize a 2D parametric curve.

    Args:
        x_fn (sympy.Expr): Function :math:`x(s)` in the curve.
        y_fn (sympy.Expr): Function :math:`y(s)` in the curve.
        s (sympy.Symbol): The symbol used to define ``x_fn`` and ``y_fn``.

    Returns:
        sympy.Expr: The implicitized function :math:`f(x, y)` such that the
        curve satisfies :math:`f(x(s), y(s)) = 0`.
    """
    # NOTE: We import SymPy at runtime to avoid the import-time cost for users
    #       that don't want to do symbolic computation. The ``sympy`` import is
    #       a tad expensive.
    import sympy  # pylint: disable=import-outside-toplevel

    x_sym, y_sym = sympy.symbols("x, y")
    return sympy.resultant(x_fn - x_sym, y_fn - y_sym, s).factor()
Ejemplo n.º 9
0
def _singular_points_finite(f,x,y):
    """
    Returns the finite singular points of f.
    """
    S = []

    # compute the finite singularities: use the resultant
    p  = sympy.Poly(f,[x,y])
    n  = p.degree(y)
    res = sympy.Poly(sympy.resultant(p,p.diff(y),y),x)
    for xk,deg in res.all_roots(multiple=False,radicals=False):
        if deg > 1:
            fxk = sympy.Poly(f.subs({x:xk,y:_Z}), _Z)
            for ykj,_ in fxk.all_roots(multiple=False,radicals=False):
                fx = f.diff(x)
                fy = f.diff(y)
                subs = {x:xk,y:ykj}
                if (fx.subs(subs) == 0) and (fy.subs(subs) == 0):
                    S.append((xk,ykj,1))

    return S
Ejemplo n.º 10
0
    def discriminant_points(self):
        """
        Returns the list of discriminant points of a plane algebraic
        curve `f = f(x,y)` in order.
        """
        # self.monodromy_graph requires that we compute the discriminant
        # points, unordered, first. However, once we order the points
        # we set the result as self._discriminant_points
        if self._discriminant_points:
            return self._discriminant_points

        x, y = self.x, self.y
        p    = sympy.Poly(self.f,[x,y])
        res  = sympy.Poly(sympy.resultant(p,p.diff(y),y),x)
        
        # compute the numerical roots
        dps = sympy.mpmath.mp.dps
        rts = [rt for rt,ord in res.all_roots(multiple=False, radicals=False)]
        rts = map(lambda z: sympy.N(z,n=dps).as_real_imag(), rts)
        disc_pts = map(lambda z: sympy.mpmath.mpc(*z), rts)

        return disc_pts
Ejemplo n.º 11
0
def ratint_logpart(f, g, x, t=None):
    """Lazard-Rioboo-Trager algorithm.

       Given a field K and polynomials f and g in K[x], such that f and g
       are coprime, deg(f) < deg(g) and g is square-free, returns a list
       of tuples (s_i, q_i) of polynomials, for i = 1..n, such that s_i
       in K[t, x] and q_i in K[t], and:
                               ___    ___
                     d  f   d  \  `   \  `
                     -- - = --  )      )   a log(s_i(a, x))
                     dx g   dx /__,   /__,
                              i=1..n a | q_i(a) = 0

    """
    f, g = Poly(f, x), Poly(g, x)

    t = t or Dummy('t')
    a, b = g, f - g.diff()*Poly(t, x)

    R = subresultants(a, b)
    res = Poly(resultant(a, b), t)

    R_map, H = {}, []

    for r in R:
        R_map[r.degree()] = r

    def _include_sign(c, sqf):
        if c < 0:
            h, k = sqf[0]
            sqf[0] = h*c, k

    C, res_sqf = res.sqf_list()
    _include_sign(C, res_sqf)

    for q, i in res_sqf:
        _, q = q.primitive()

        if g.degree() == i:
            H.append((g, q))
        else:
            h = R_map[i]
            h_lc = Poly(h.LC(), t, field=True)

            c, h_lc_sqf = h_lc.sqf_list(all=True)
            _include_sign(c, h_lc_sqf)

            for a, j in h_lc_sqf:
                h = h.exquo(Poly(a.gcd(q)**j, x))

            inv, coeffs = h_lc.invert(q), [S(1)]

            for coeff in h.coeffs()[1:]:
                T = (inv*coeff).rem(q)
                coeffs.append(T.as_basic())

            h = Poly(dict(zip(h.monoms(), coeffs)), x)

            H.append((h, q))

    return H
Ejemplo n.º 12
0
def log_to_real(h, q, x, t):
    """Convert complex logarithms to real functions.

       Given real field K and polynomials h in K[t,x] and q in K[t],
       returns real function f such that:
                              ___
                      df   d  \  `
                      -- = --  )  a log(h(a, x))
                      dx   dx /__,
                             a | q(a) = 0

    """
    u, v = symbols('u v')

    H = h.as_basic().subs({t: u + I * v}).expand()
    Q = q.as_basic().subs({t: u + I * v}).expand()

    H_map = collect(H, I, evaluate=False)
    Q_map = collect(Q, I, evaluate=False)

    a, b = H_map.get(S(1), S(0)), H_map.get(I, S(0))
    c, d = Q_map.get(S(1), S(0)), Q_map.get(I, S(0))

    R = Poly(resultant(c, d, v), u)

    R_u = roots(R, filter='R')

    if len(R_u) != number_of_real_roots(R):
        return None

    result = S(0)

    for r_u in R_u.iterkeys():
        C = Poly(c.subs({u: r_u}), v)
        R_v = roots(C, filter='R')

        if len(R_v) != number_of_real_roots(C):
            return None

        for r_v in R_v:
            if not r_v.is_positive:
                continue

            D = d.subs({u: r_u, v: r_v})

            if D.evalf(chop=True) != 0:
                continue

            A = Poly(a.subs({u: r_u, v: r_v}), x)
            B = Poly(b.subs({u: r_u, v: r_v}), x)

            AB = (A**2 + B**2).as_basic()

            result += r_u * log(AB) + r_v * log_to_atan(A, B)

    R_q = roots(q, filter='R')

    if len(R_q) != number_of_real_roots(q):
        return None

    for r in R_q.iterkeys():
        result += r * log(h.as_basic().subs(t, r))

    return result
Ejemplo n.º 13
0
def ratint_logpart(f, g, x, t=None):
    """Lazard-Rioboo-Trager algorithm.

       Given a field K and polynomials f and g in K[x], such that f and g
       are coprime, deg(f) < deg(g) and g is square-free, returns a list
       of tuples (s_i, q_i) of polynomials, for i = 1..n, such that s_i
       in K[t, x] and q_i in K[t], and:
                               ___    ___
                     d  f   d  \  `   \  `
                     -- - = --  )      )   a log(s_i(a, x))
                     dx g   dx /__,   /__,
                              i=1..n a | q_i(a) = 0

    """
    f, g = Poly(f, x), Poly(g, x)

    t = t or Dummy('t')
    a, b = g, f - g.diff() * Poly(t, x)

    R = subresultants(a, b)
    res = Poly(resultant(a, b), t)

    R_map, H = {}, []

    for r in R:
        R_map[r.degree()] = r

    def _include_sign(c, sqf):
        if c < 0:
            h, k = sqf[0]
            sqf[0] = h * c, k

    C, res_sqf = res.sqf_list()
    _include_sign(C, res_sqf)

    for q, i in res_sqf:
        _, q = q.primitive()

        if g.degree() == i:
            H.append((g, q))
        else:
            h = R_map[i]
            h_lc = Poly(h.LC(), t, field=True)

            c, h_lc_sqf = h_lc.sqf_list(all=True)
            _include_sign(c, h_lc_sqf)

            for a, j in h_lc_sqf:
                h = h.exquo(Poly(a.gcd(q)**j, x))

            inv, coeffs = h_lc.invert(q), [S(1)]

            for coeff in h.coeffs()[1:]:
                T = (inv * coeff).rem(q)
                coeffs.append(T.as_basic())

            h = Poly(dict(zip(h.monoms(), coeffs)), x)

            H.append((h, q))

    return H
Ejemplo n.º 14
0
def test_H11():
    skip('takes too much time')
    assert resultant(p1 * q, p2 * q, x) == 0
Ejemplo n.º 15
0
def test_H11():
    assert resultant(p1 * q, p2 * q, x) == 0
Ejemplo n.º 16
0
def test_H10():
    p1 = 3*x**4 + 3*x**3 + x**2 - x - 2
    p2 = x**3 - 3*x**2 + x + 5
    assert resultant(p1, p2, x) == 0
Ejemplo n.º 17
0
def integral_basis(f,x,y):
    """
    Compute the integral basis {b1, ..., bg} of the algebraic function
    field C[x,y] / (f).
    """
    # If the curve is not monic then map y |-> y/lc(x) where lc(x)
    # is the leading coefficient of f
    T  = sympy.Dummy('T')
    d  = sympy.degree(f,y)
    lc = sympy.LC(f,y)
    if x in lc:
        f = sympy.ratsimp( f.subs(y,y/lc)*lc**(d-1) )
    else:
        f = f/lc
        lc = 1

    #
    # Compute df
    #
    p = sympy.Poly(f,[x,y])
    n = p.degree(y)
    res = sympy.resultant(p,p.diff(y),y)
    factors = sympy.factor_list(res)[1]
    df = [k for k,deg in factors if (deg > 1) and (sympy.LC(k) == 1)]

    #
    # Compute series truncations at appropriate x points
    #
    alpha = []
    r = []
    for l in range(len(df)):
        k = df[l]
        alphak = sympy.roots(k).keys()[0]
        rk = compute_series_truncations(f,x,y,alphak,T)
        alpha.append(alphak)
        r.append(rk)

        
    #
    # Main Loop
    #
    a = [sympy.Dummy('a%d'%k) for k in xrange(n)]
    b = [1]
    for d in range(1,n):
        bd = y*b[-1]

        for l in range(len(df)):
            k = df[l]
            alphak = alpha[l]
            rk = r[l]

            found_something = True            
            while found_something:
                # construct system of equations consisting of the coefficients
                # of negative powers of (x-alphak) in the substitutions
                # A(r_{k,1}),...,A(r_{k,n})
                A  = (sum(ak*bk for ak,bk in zip(a,b)) + bd) / (x - alphak)

                coeffs = []
                for rki in rk:
                    # substitute and extract coefficients
                    A_rki  = A.subs(y,rki)
                    coeffs.extend(_negative_power_coeffs(A_rki, x, alphak))
               
                # solve the coefficient equations for a0,...,a_{d-1}
                coeffs = [coeff.as_numer_denom()[0] for coeff in coeffs]
                sols = sympy.solve_poly_system(coeffs, a[:d])
                if sols is None or sols == []:
                    found_something = False
                else:
                    sol  = sols[0]
                    bdm1 = sum( sol[i]*bk for i,bk in zip(range(d),b) )
                    bd   = (bdm1 + bd) / k
                        
        # bd found. Append to list of basis elements
        b.append( bd )

    # finally, convert back to singularized curve if necessary
    for i in xrange(1,len(b)):
        b[i] = b[i].subs(y,y*lc).ratsimp()

    return b
Ejemplo n.º 18
0
def test_H10():
    p1 = 3 * x**4 + 3 * x**3 + x**2 - x - 2
    p2 = x**3 - 3 * x**2 + x + 5
    assert resultant(p1, p2, x) == 0
def calc_g33335():
    # solid2sorted_C_Ks:
    ## (3, 3, 3, 3, 5): ((1/2, 1/2 + sqrt(5)/2), (2, 1)),
    # 0.463856880645439
    solid = (3, 3, 3, 3, 5)
    f = solid2zero_poly_GG(solid)
    ggs = solve(f)
##    print(ggs)
##    print(list(map(N, ggs)))
    gg, = ggs
    g33335 = nsimplify(sqrt(gg))
    _g33335 = sqrt(-(-(-188 + 12*sqrt(5))**3/(27*(-29 + sqrt(5))**3)
                     - (-192 + 64*sqrt(5))/(2*(-29 + sqrt(5)))
                     + sqrt((-(-188 + 12*sqrt(5))**2/(9*(-29 + sqrt(5))**2)
                             + (-368 + 48*sqrt(5))/(3*(-29 + sqrt(5))))**3
                            + (-2*(-188 + 12*sqrt(5))**3/(27*(-29 + sqrt(5))**3)
                               - (-192 + 64*sqrt(5))/(-29 + sqrt(5))
                               + (-368 + 48*sqrt(5))*(-188 + 12*sqrt(5))
                               /(3*(-29 + sqrt(5))**2))**2/4)
                     + (-368 + 48*sqrt(5))*(-188 + 12*sqrt(5))
                     /(6*(-29 + sqrt(5))**2))**(1/3)
                   + (-(-188 + 12*sqrt(5))**2/(9*(-29 + sqrt(5))**2)
                      + (-368 + 48*sqrt(5))/(3*(-29 + sqrt(5))))
                   /(-(-188 + 12*sqrt(5))**3/(27*(-29 + sqrt(5))**3)
                     - (-192 + 64*sqrt(5))/(2*(-29 + sqrt(5)))
                     + sqrt((-(-188 + 12*sqrt(5))**2/(9*(-29 + sqrt(5))**2)
                             + (-368 + 48*sqrt(5))/(3*(-29 + sqrt(5))))**3
                            + (-2*(-188 + 12*sqrt(5))**3/(27*(-29 + sqrt(5))**3)
                               - (-192 + 64*sqrt(5))/(-29 + sqrt(5))
                               + (-368 + 48*sqrt(5))*(-188 + 12*sqrt(5))
                               /(3*(-29 + sqrt(5))**2))**2/4)
                     + (-368 + 48*sqrt(5))*(-188 + 12*sqrt(5))
                     /(6*(-29 + sqrt(5))**2))**(1/3)
                   + (-188 + 12*sqrt(5))/(3*(-29 + sqrt(5))))
    assert verify_G(solid, g33335)


    # new form of g33335
    h = expand(f*(sqrt(5) + 29)/2)
    h = collect(h, GG)
    assert h == 209*GG**3 + GG**2*(-1348 + 40*sqrt(5)) + GG*(-256*sqrt(5) + 2608) - 1312 + 416*sqrt(5)

    fr_one = Fraction(1) # Fraction(1)
    sr_one = GG/GG # Rational(1) 
    A = 1881*sqrt(2)*sqrt(5760573 + 2813807*sqrt(5))
    B = (A + 2563547*sqrt(15) + 6192143*sqrt(3))
    D = 4**(sr_one/3)*3**(sr_one/6)/B**(sr_one/3)
    fr_D = 4**(fr_one/3)*3**(fr_one/6)/B**(fr_one/3) # NOTE: 4**Fraction(1,3) -> float
    #assert not 0 == nsimplify(D-fr_D)
    
    _GG = 2*(-6/D - 71208*D + sqrt(5)*(-19752*D - 60) + 2022)/1881
    _g33335 = sqrt(_GG)
    assert verify_G(solid, _g33335)
    assert 0 == nsimplify(g33335 - _g33335)


    # factor the below 'f' into h over QQ[sqrt(5)]
    # see below 'f'
    u = (209*GG**6 - 2696*GG**5 + 13872*GG**4 - 35776*GG**3 + 47104*GG**2 - 27648*GG + 4096)
    #assert factor(u,extension={sqrt(5)}) == 209*(GG**3 + GG**2*(-1348/209 - 40*sqrt(5)/209) + GG*(256*sqrt(5)/209 + 2608/209) - 1312/209 - 416*sqrt(5)/209)*(GG**3 + GG**2*(-1348/209 + 40*sqrt(5)/209) + GG*(-256*sqrt(5)/209 + 2608/209) - 1312/209 + 416*sqrt(5)/209)
    assert resultant(u,h) == 0 # so, they have a same root that is GG
    assert 0 == expand(gcd(u,h,extension=True)*209 - h)
    return _g33335

    
    _g = 0.463856880645439
    _gg = _g**2
    ef = lambda f, gg=_gg: N(f.subs(GG, gg))
    tf = lambda f: bool(abs(ef(f)) < 1e-7)
    assert tf(f)

    P = sqrt(5)
    f = expand(2*f)
    f = collect(f, P)
    A, B = seperate_term(f, P)
    assert f == A+B
    f = expand(A**2 - B**2)
    assert tf(f)
    
    print(f)
    f /= 4
    assert f == (209*GG**6 - 2696*GG**5 + 13872*GG**4 - 35776*GG**3 + 47104*GG**2 - 27648*GG + 4096)


    assert tf(f)
    ggs = solve(f)
    # sympy bug1:
    #   solve(f) ==>> [1.50152930508540, 2.97263618194513, 2.40355087229957, 2.97263618194513]
    #   NOTE: 2.97263618194513 appear twice but miss 0.21516320572211706
    # sympy bug2:
    #   root of f == 4*(root of h)?? since solve(f)=[4*RootOf(h)...]
    #   where h = 209*GG**6 - 674*GG**5 + 867*GG**4 - 559*GG**3 + 184*GG**2 - 27*GG + 1
    #   but solve(h) == [] !!!
    #   while GG:positive=True
    #   but var('x'), solve(h)==[6 roots (4 reals)] and two real roots be the same
    print('gg', [N((gg)) for gg in ggs])
    print('g', [N(sqrt(gg)) for gg in ggs])
    ggs = [gg for gg in ggs if (0 < N(gg) < 4)]
    print([ef(f,gg) for gg in ggs])
    ggs = [gg for gg in ggs if verify_G(solid, sqrt(gg))]
    print(ggs)
    raise
    g33335 = sqrt(gg)
    g33335 = nsimplify(g33335)
    #assert 0 == nsimplify(g33335 - _g33335)

    assert verify_G(solid, g33335)
    return g33335
Ejemplo n.º 20
0
def test_H11():
    assert resultant(p1 * q, p2 * q, x) == 0
Ejemplo n.º 21
0
def log_to_real(h, q, x, t):
    """Convert complex logarithms to real functions.

       Given real field K and polynomials h in K[t,x] and q in K[t],
       returns real function f such that:
                              ___
                      df   d  \  `
                      -- = --  )  a log(h(a, x))
                      dx   dx /__,
                             a | q(a) = 0

    """
    u, v = symbols('u v')

    H = h.subs({t:u+I*v}).as_basic().expand()
    Q = q.subs({t:u+I*v}).as_basic().expand()

    H_map = collect(H, I, evaluate=False)
    Q_map = collect(Q, I, evaluate=False)

    a, b = H_map.get(S(1), S(0)), H_map.get(I, S(0))
    c, d = Q_map.get(S(1), S(0)), Q_map.get(I, S(0))

    R = Poly(resultant(c, d, v), u)

    R_u = roots(R, domain='R')

    if len(R_u) != number_of_real_roots(R):
        return None

    result = S(0)

    for r_u in R_u.iterkeys():
        C = Poly(c.subs({u:r_u}), v)
        R_v = roots(C, domain='R')

        if len(R_v) != number_of_real_roots(C):
            return None

        for r_v in R_v:
            if not r_v.is_positive:
                continue

            D = d.subs({u:r_u, v:r_v})

            if D.evalf(chop=True) != 0:
                continue

            A = Poly(a.subs({u:r_u, v:r_v}), x)
            B = Poly(b.subs({u:r_u, v:r_v}), x)

            AB = (A**2 + B**2).as_basic()

            result += r_u*log(AB) + r_v*log_to_atan(A, B)

    R_q = roots(q, domain='R')

    if len(R_q) != number_of_real_roots(q):
        return None

    for r in R_q.iterkeys():
        result += r*log(h.subs(t, r).as_basic())

    return result
Ejemplo n.º 22
0
def test_H11():
    skip('takes too much time')
    assert resultant(p1 * q, p2 * q, x) == 0