def test_number_of_real_roots(): assert number_of_real_roots(0, x) == 0 assert number_of_real_roots(7, x) == 0 f = Poly(x - 1, x) assert number_of_real_roots(f) == 1 assert number_of_real_roots(f, sup=0) == 0 assert number_of_real_roots(f, inf=1) == 0 assert number_of_real_roots(f, sup=0, inf=1) == 1 assert number_of_real_roots(f, sup=1, inf=0) == 1 f = x**2 - 4 assert number_of_real_roots(f, x) == 2 assert number_of_real_roots(f, x, sup=0) == 1 assert number_of_real_roots(f, x, inf=-1, sup=1) == 0 raises(ValueError, "number_of_real_roots(f, x, inf=t)") raises(ValueError, "number_of_real_roots(f, x, sup=t)")
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