def test_combine_inverse(): assert Mul._combine_inverse(x * I * y, x * I) == y assert Mul._combine_inverse(x * I * y, y * I) == x assert Mul._combine_inverse(oo * I * y, y * I) == oo assert Mul._combine_inverse(oo * I * y, oo * I) == y assert Add._combine_inverse(oo, oo) == Integer(0) assert Add._combine_inverse(oo * I, oo * I) == Integer(0)
def test_lookup_table(): table = defaultdict(list) _create_lookup_table(table) for _, l in sorted(table.items(), key=default_sort_key): for formula, terms, cond, hint in sorted(l, key=default_sort_key): subs = {} for a in list(formula.free_symbols) + [z_dummy]: if hasattr(a, 'properties') and a.properties: # these Wilds match positive integers subs[a] = randrange(1, 10) else: subs[a] = uniform(1.5, 2.0) if not isinstance(terms, list): terms = terms(subs) # First test that hyperexpand can do this. expanded = [hyperexpand(g) for (_, g) in terms] assert all(x.is_Piecewise or not x.has(meijerg) for x in expanded) # Now test that the meijer g-function is indeed as advertised. expanded = Add(*[f * x for (f, x) in terms]) a, b = formula.evalf(subs=subs, strict=False), expanded.evalf(subs=subs, strict=False) r = min(abs(a), abs(b)) if r < 1: assert abs(a - b).evalf(strict=False) <= 1e-10 else: assert (abs(a - b) / r).evalf(strict=False) <= 1e-10
def test_lookup_table(): table = defaultdict(list) _create_lookup_table(table) for _, l in sorted(table.items(), key=default_sort_key): for formula, terms, cond, hint in sorted(l, key=default_sort_key): subs = {} for a in list(formula.free_symbols) + [z_dummy]: if hasattr(a, 'properties') and a.properties: # these Wilds match positive integers subs[a] = randrange(1, 10) else: subs[a] = uniform(1.5, 2.0) if not isinstance(terms, list): terms = terms(subs) # First test that hyperexpand can do this. expanded = [hyperexpand(g) for (_, g) in terms] assert all(x.is_Piecewise or not x.has(meijerg) for x in expanded) # Now test that the meijer g-function is indeed as advertised. expanded = Add(*[f*x for (f, x) in terms]) a, b = formula.evalf(subs=subs, strict=False), expanded.evalf(subs=subs, strict=False) r = min(abs(a), abs(b)) if r < 1: assert abs(a - b).evalf(strict=False) <= 1e-10 else: assert (abs(a - b)/r).evalf(strict=False) <= 1e-10
def test_combine_inverse(): assert Mul._combine_inverse(x*I*y, x*I) == y assert Mul._combine_inverse(x*I*y, y*I) == x assert Mul._combine_inverse(oo*I*y, y*I) == oo assert Mul._combine_inverse(oo*I*y, oo*I) == y assert Add._combine_inverse(oo, oo) == Integer(0) assert Add._combine_inverse(oo*I, oo*I) == Integer(0)
def test_TR10i(): assert TR10i(cos(1) * cos(3) + sin(1) * sin(3)) == cos(2) assert TR10i(cos(1) * cos(3) - sin(1) * sin(3)) == cos(4) assert TR10i(cos(1) * sin(3) - sin(1) * cos(3)) == sin(2) assert TR10i(cos(1) * sin(3) + sin(1) * cos(3)) == sin(4) assert TR10i(cos(1) * sin(3) + sin(1) * cos(3) + 7) == sin(4) + 7 assert TR10i(cos(1) * sin(3) + sin(1) * cos(3) + cos(3)) == cos(3) + sin(4) assert TR10i(2*cos(1)*sin(3) + 2*sin(1)*cos(3) + cos(3)) == \ 2*sin(4) + cos(3) assert TR10i(cos(2)*cos(3) + sin(2)*(cos(1)*sin(2) + cos(2)*sin(1))) == \ cos(1) eq = (cos(2) * cos(3) + sin(2) * (cos(1) * sin(2) + cos(2) * sin(1))) * cos(5) + sin(1) * sin(5) assert TR10i(eq) == TR10i(eq.expand()) == cos(4) assert TR10i(sqrt(2)*cos(x)*x + sqrt(6)*sin(x)*x) == \ 2*sqrt(2)*x*sin(x + pi/6) assert TR10i( cos(x) / sqrt(6) + sin(x) / sqrt(2) + cos(x) / sqrt(6) / 3 + sin(x) / sqrt(2) / 3) == 4 * sqrt(6) * sin(x + pi / 6) / 9 assert TR10i(cos(x)/sqrt(6) + sin(x)/sqrt(2) + cos(y)/sqrt(6)/3 + sin(y)/sqrt(2)/3) == \ sqrt(6)*sin(x + pi/6)/3 + sqrt(6)*sin(y + pi/6)/9 assert TR10i(cos(x) + sqrt(3) * sin(x) + 2 * sqrt(3) * cos(x + pi / 6)) == 4 * cos(x) assert TR10i( cos(x) + sqrt(3) * sin(x) + 2 * sqrt(3) * cos(x + pi / 6) + 4 * sin(x)) == 4 * sqrt(2) * sin(x + pi / 4) assert TR10i(cos(2)*sin(3) + sin(2)*cos(4)) == \ sin(2)*cos(4) + sin(3)*cos(2) A = Symbol('A', commutative=False) assert TR10i(sqrt(2)*cos(x)*A + sqrt(6)*sin(x)*A) == \ 2*sqrt(2)*sin(x + pi/6)*A c = cos(x) s = sin(x) h = sin(y) r = cos(y) for si in ((1, 1), (1, -1), (-1, 1), (-1, -1)): for a in ((c * r, s * h), (c * h, s * r)): # explicit 2-args args = zip(si, a) ex = Add(*[Mul(*ai) for ai in args]) t = TR10i(ex) assert not (ex - t.expand(trig=True) or t.is_Add) c = cos(x) s = sin(x) h = sin(pi / 6) r = cos(pi / 6) for si in ((1, 1), (1, -1), (-1, 1), (-1, -1)): for a in ((c * r, s * h), (c * h, s * r)): # induced args = zip(si, a) ex = Add(*[Mul(*ai) for ai in args]) t = TR10i(ex) assert not (ex - t.expand(trig=True) or t.is_Add)
def test_evaluate_false(): cases = { '2 + 3': Add(2, 3, evaluate=False), '2**2 / 3': Mul(Pow(2, 2, evaluate=False), Pow(3, -1, evaluate=False), evaluate=False), '2 + 3 * 5': Add(2, Mul(3, 5, evaluate=False), evaluate=False), '2 - 3 * 5': Add(2, -Mul(3, 5, evaluate=False), evaluate=False), '1 / 3': Mul(1, Pow(3, -1, evaluate=False), evaluate=False), 'True | False': Or(True, False, evaluate=False), '1 + 2 + 3 + 5*3 + integrate(x)': Add(1, 2, 3, Mul(5, 3, evaluate=False), x**2/2, evaluate=False), '2 * 4 * 6 + 8': Add(Mul(2, 4, 6, evaluate=False), 8, evaluate=False), } for case, result in cases.items(): assert sympify(case, evaluate=False) == result
def test_gcd_terms(): f = 2*(x + 1)*(x + 4)/(5*x**2 + 5) + (2*x + 2)*(x + 5)/(x**2 + 1)/5 + \ (2*x + 2)*(x + 6)/(5*x**2 + 5) assert _gcd_terms(f) == (Rational(6, 5) * ((1 + x) / (1 + x**2)), 5 + x, 1) assert _gcd_terms(Add.make_args(f)) == \ (Rational(6, 5)*((1 + x)/(1 + x**2)), 5 + x, 1) newf = Rational(6, 5) * ((1 + x) * (5 + x) / (1 + x**2)) assert gcd_terms(f) == newf args = Add.make_args(f) # non-Basic sequences of terms treated as terms of Add assert gcd_terms(list(args)) == newf assert gcd_terms(tuple(args)) == newf assert gcd_terms(set(args)) == newf # but a Basic sequence is treated as a container assert gcd_terms(Tuple(*args)) != newf assert gcd_terms(Basic(Tuple(1, 3*y + 3*x*y), Tuple(1, 3))) == \ Basic((1, 3*y*(x + 1)), (1, 3)) # but we shouldn't change keys of a dictionary or some may be lost assert gcd_terms(Dict((x*(1 + y), 2), (x + x*y, y + x*y))) == \ Dict({x*(y + 1): 2, x + x*y: y*(1 + x)}) assert gcd_terms((2 * x + 2)**3 + (2 * x + 2)**2) == 4 * (x + 1)**2 * (2 * x + 3) assert gcd_terms(0) == 0 assert gcd_terms(1) == 1 assert gcd_terms(x) == x assert gcd_terms(2 + 2 * x) == Mul(2, 1 + x, evaluate=False) arg = x * (2 * x + 4 * y) garg = 2 * x * (x + 2 * y) assert gcd_terms(arg) == garg assert gcd_terms(sin(arg)) == sin(garg) # issue sympy/sympy#6139-like alpha, alpha1, alpha2, alpha3 = symbols('alpha:4') a = alpha**2 - alpha * x**2 + alpha + x**3 - x * (alpha + 1) rep = { alpha: (1 + sqrt(5)) / 2 + alpha1 * x + alpha2 * x**2 + alpha3 * x**3 } s = (a / (x - alpha)).subs(rep).series(x, 0, 1) assert simplify(collect(s, x)) == -sqrt(5) / 2 - Rational(3, 2) + O(x) # issue sympy/sympy#5917 assert _gcd_terms([Integer(0), Integer(0)]) == (0, 0, 1) assert _gcd_terms([2 * x + 4]) == (2, x + 2, 1) eq = x / (x + 1 / x) assert gcd_terms(eq, fraction=False) == eq
def _minpoly_cos(ex, x): """ Returns the minimal polynomial of ``cos(ex)`` see http://mathworld.wolfram.com/TrigonometryAngles.html """ from diofant import sqrt c, a = ex.args[0].as_coeff_Mul() if a is pi: if c.is_rational: if c.p == 1: if c.q == 7: return 8 * x**3 - 4 * x**2 - 4 * x + 1 if c.q == 9: return 8 * x**3 - 6 * x + 1 elif c.p == 2: q = sympify(c.q) if q.is_prime: s = _minpoly_sin(ex, x) return _mexpand(s.subs({x: sqrt((1 - x) / 2)})) # for a = pi*p/q, cos(q*a) =T_q(cos(a)) = (-1)**p n = int(c.q) a = dup_chebyshevt(n, ZZ) a = [x**(n - i) * a[i] for i in range(n + 1)] r = Add(*a) - (-1)**c.p _, factors = factor_list(r) res = _choose_factor(factors, x, ex) return res raise NotAlgebraic("%s doesn't seem to be an algebraic element" % ex)
def test_Add(): assert str(x + y) == "x + y" assert str(x + 1) == "x + 1" assert str(x + x**2) == "x**2 + x" assert str(5 + x + y + x*y + x**2 + y**2) == "x**2 + x*y + x + y**2 + y + 5" assert str(1 + x + x**2/2 + x**3/3) == "x**3/3 + x**2/2 + x + 1" assert str(2*x - 7*x**2 + 2 + 3*y) == "-7*x**2 + 2*x + 3*y + 2" assert str(x - y) == "x - y" assert str(2 - x) == "-x + 2" assert str(x - 2) == "x - 2" assert str(x - y - z - w) == "-w + x - y - z" assert str(x - z*y**2*z*w) == "-w*y**2*z**2 + x" assert str(x - 1*y*x*y) == "-x*y**2 + x" assert str(sin(x).series(x, 0, 15)) == "x - x**3/6 + x**5/120 - x**7/5040 + x**9/362880 - x**11/39916800 + x**13/6227020800 + O(x**15)" assert str(Add(0, 0, evaluate=False)) == "0 + 0" assert str(Add(And(x, y), z)) == 'z + (x & y)'
def test_diop_general_sum_of_squares_quick(): for i in range(3, 10): assert check_solutions(sum(i**2 for i in symbols(f':{i:d}')) - i) pytest.raises(ValueError, lambda: _diop_general_sum_of_squares((x, y), 2)) assert _diop_general_sum_of_squares((x, y, z), -2) == set() eq = x**2 + y**2 + z**2 - (1 + 4 + 9) assert diop_general_sum_of_squares(eq) == {(1, 2, 3)} eq = u**2 + v**2 + x**2 + y**2 + z**2 - 1313 assert len(diop_general_sum_of_squares(eq, 3)) == 3 # issue sympy/sympy#11016 var = symbols(':5') + (symbols('6', negative=True), ) eq = Add(*[i**2 for i in var]) - 112 assert diophantine(eq) == {(0, 1, 1, 5, 6, -7), (1, 1, 1, 3, 6, -8), (2, 3, 3, 4, 5, -7), (0, 1, 1, 1, 3, -10), (0, 0, 4, 4, 4, -8), (1, 2, 3, 3, 5, -8), (0, 1, 2, 3, 7, -7), (2, 2, 4, 4, 6, -6), (1, 1, 3, 4, 6, -7), (0, 2, 3, 3, 3, -9), (0, 0, 2, 2, 2, -10), (1, 1, 2, 3, 4, -9), (0, 1, 1, 2, 5, -9), (0, 0, 2, 6, 6, -6), (1, 3, 4, 5, 5, -6), (0, 2, 2, 2, 6, -8), (0, 3, 3, 3, 6, -7), (0, 2, 3, 5, 5, -7), (0, 1, 5, 5, 5, -6)} # handle negated squares with signsimp assert diophantine(12 - x**2 - y**2 - z**2) == {(2, 2, 2)} # diophantine handles simplification, so classify_diop should # not have to look for additional patterns that are removed # by diophantine eq = a**2 + b**2 + c**2 + d**2 - 4 pytest.raises(NotImplementedError, lambda: classify_diop(-eq))
def test_process_common_addends(): # this tests that the args are not evaluated as they are given to do # and that key2 works when key1 is False def do(x): return Add(*[i**(i % 2) for i in x.args]) process_common_addends(Add(*[1, 2, 3, 4], evaluate=False), do, key2=lambda x: x % 2, key1=False) == 1**1 + 3**1 + 2**0 + 4**0
def test_add(): assert (a**2 - b - c).subs({a**2 - b: d}) in [d - c, a**2 - b - c] assert (a**2 - c).subs({a**2 - c: d}) == d assert (a**2 - b - c).subs({a**2 - c: d}) in [d - b, a**2 - b - c] assert (a**2 - x - c).subs({a**2 - c: d}) in [d - x, a**2 - x - c] assert (a**2 - b - sqrt(a)).subs({a**2 - sqrt(a): c}) == c - b assert (a + b + exp(a + b)).subs({a + b: c}) == c + exp(c) assert (c + b + exp(c + b)).subs({c + b: a}) == a + exp(a) assert (a + b + c + d).subs({b + c: x}) == a + d + x assert (a + b + c + d).subs({-b - c: x}) == a + d - x assert ((x + 1) * y).subs({x + 1: t}) == t * y assert ((-x - 1) * y).subs({x + 1: t}) == -t * y assert ((x - 1) * y).subs({x + 1: t}) == y * (t - 2) assert ((-x + 1) * y).subs({x + 1: t}) == y * (-t + 2) # this should work everytime: e = a**2 - b - c assert e.subs({Add(*e.args[:2]): d}) == d + e.args[2] assert e.subs({a**2 - c: d}) == d - b # the fallback should recognize when a change has # been made; while .1 == Rational(1, 10) they are not the same # and the change should be made assert (0.1 + a).subs({0.1: Rational(1, 10)}) == Rational(1, 10) + a e = (-x * (-y + 1) - y * (y - 1)) ans = (-x * x - y * (-x)).expand() assert e.subs({-y + 1: x}) == ans
def test_add(): a, b, c, d, x, y, t = symbols('a b c d x y t') assert (a**2 - b - c).subs(a**2 - b, d) in [d - c, a**2 - b - c] assert (a**2 - c).subs(a**2 - c, d) == d assert (a**2 - b - c).subs(a**2 - c, d) in [d - b, a**2 - b - c] assert (a**2 - x - c).subs(a**2 - c, d) in [d - x, a**2 - x - c] assert (a**2 - b - sqrt(a)).subs(a**2 - sqrt(a), c) == c - b assert (a + b + exp(a + b)).subs(a + b, c) == c + exp(c) assert (c + b + exp(c + b)).subs(c + b, a) == a + exp(a) assert (a + b + c + d).subs(b + c, x) == a + d + x assert (a + b + c + d).subs(-b - c, x) == a + d - x assert ((x + 1) * y).subs(x + 1, t) == t * y assert ((-x - 1) * y).subs(x + 1, t) == -t * y assert ((x - 1) * y).subs(x + 1, t) == y * (t - 2) assert ((-x + 1) * y).subs(x + 1, t) == y * (-t + 2) # this should work everytime: e = a**2 - b - c assert e.subs(Add(*e.args[:2]), d) == d + e.args[2] assert e.subs(a**2 - c, d) == d - b # the fallback should recognize when a change has # been made; while .1 == Rational(1, 10) they are not the same # and the change should be made assert (0.1 + a).subs(0.1, Rational(1, 10)) == Rational(1, 10) + a e = (-x * (-y + 1) - y * (y - 1)) ans = (-x * (x) - y * (-x)).expand() assert e.subs(-y + 1, x) == ans
def test_as_content_primitive(): # although the _as_content_primitive methods do not alter the underlying structure, # the as_content_primitive function will touch up the expression and join # bases that would otherwise have not been joined. assert ((x*(2 + 2*x)*(3*x + 3)**2)).as_content_primitive() == \ (18, x*(x + 1)**3) assert (2 + 2*x + 2*y*(3 + 3*y)).as_content_primitive() == \ (2, x + 3*y*(y + 1) + 1) assert ((2 + 6*x)**2).as_content_primitive() == (4, (3*x + 1)**2) assert ((2 + 6*x)**(2*y)).as_content_primitive() == \ (1, (_keep_coeff(Integer(2), (3*x + 1)))**(2*y)) assert (5 + 10*x + 2*y*(3 + 3*y)).as_content_primitive() == \ (1, 10*x + 6*y*(y + 1) + 5) assert ((5*(x*(1 + y)) + 2*x*(3 + 3*y))).as_content_primitive() == \ (11, x*(y + 1)) assert ((5*(x*(1 + y)) + 2*x*(3 + 3*y))**2).as_content_primitive() == \ (121, x**2*(y + 1)**2) assert (y**2).as_content_primitive() == (1, y**2) assert oo.as_content_primitive() == (1, oo) eq = x**(2 + y) assert (eq).as_content_primitive() == (1, eq) assert (Rational(1, 2)**(2 + x)).as_content_primitive() == (Rational(1, 4), 2**-x) assert (Rational(-1, 2)**(2 + x)).as_content_primitive() == \ (Rational(1, 4), Rational(-1, 2)**x) assert (Rational(-1, 2)**(2 + x)).as_content_primitive() == \ (Rational(1, 4), Rational(-1, 2)**x) assert (4**((1 + y)/2)).as_content_primitive() == (2, 4**(y/2)) assert (3**((1 + y)/2)).as_content_primitive() == \ (1, 3**(Mul(Rational(1, 2), 1 + y, evaluate=False))) assert (5**Rational(3, 4)).as_content_primitive() == (1, 5**Rational(3, 4)) assert (5**Rational(7, 4)).as_content_primitive() == (5, 5**Rational(3, 4)) assert Add(5*z/7, 0.5*x, 3*y/2, evaluate=False).as_content_primitive() == \ (Rational(1, 14), 7.0*x + 21*y + 10*z) assert (2**Rational(3, 4) + root(2, 4)*sqrt(3)).as_content_primitive(radical=True) == \ (1, root(2, 4)*(sqrt(2) + sqrt(3)))
def test_TR9(): a = Rational(1, 2) b = 3 * a assert TR9(a) == a assert TR9(cos(1) + cos(2)) == 2 * cos(a) * cos(b) assert TR9(cos(1) - cos(2)) == 2 * sin(a) * sin(b) assert TR9(sin(1) - sin(2)) == -2 * sin(a) * cos(b) assert TR9(sin(1) + sin(2)) == 2 * sin(b) * cos(a) assert TR9(cos(1) + 2 * sin(1) + 2 * sin(2)) == cos(1) + 4 * sin(b) * cos(a) assert TR9(cos(4) + cos(2) + 2 * cos(1) * cos(3)) == 4 * cos(1) * cos(3) assert TR9((cos(4) + cos(2)) / cos(3) / 2 + cos(3)) == 2 * cos(1) * cos(2) assert TR9(cos(3) + cos(4) + cos(5) + cos(6)) == \ 4*cos(Rational(1, 2))*cos(1)*cos(Rational(9, 2)) assert TR9(cos(3) + cos(3) * cos(2)) == cos(3) + cos(2) * cos(3) assert TR9(-cos(y) + cos(x * y)) == -2 * sin(x * y / 2 - y / 2) * sin(x * y / 2 + y / 2) assert TR9(-sin(y) + sin(x * y)) == 2 * sin(x * y / 2 - y / 2) * cos(x * y / 2 + y / 2) c = cos(x) s = sin(x) for si in ((1, 1), (1, -1), (-1, 1), (-1, -1)): for a in ((c, s), (s, c), (cos(x), cos(x * y)), (sin(x), sin(x * y))): args = zip(si, a) ex = Add(*[Mul(*ai) for ai in args]) t = TR9(ex) assert not (a[0].func == a[1].func and (not verify_numerically(ex, t.expand(trig=True)) or t.is_Add) or a[1].func != a[0].func and ex != t)
def test_cse_single(): # Simple substitution. e = Add(Pow(x + y, 2), sqrt(x + y)) substs, reduced = cse([e]) assert substs == [(x0, x + y)] assert reduced == [sqrt(x0) + x0**2] assert cse([e], order='none') == cse([e])
def test_gcd_terms(): f = 2*(x + 1)*(x + 4)/(5*x**2 + 5) + (2*x + 2)*(x + 5)/(x**2 + 1)/5 + \ (2*x + 2)*(x + 6)/(5*x**2 + 5) assert _gcd_terms(f) == (Rational(6, 5)*((1 + x)/(1 + x**2)), 5 + x, 1) assert _gcd_terms(Add.make_args(f)) == \ (Rational(6, 5)*((1 + x)/(1 + x**2)), 5 + x, 1) newf = Rational(6, 5)*((1 + x)*(5 + x)/(1 + x**2)) assert gcd_terms(f) == newf args = Add.make_args(f) # non-Basic sequences of terms treated as terms of Add assert gcd_terms(list(args)) == newf assert gcd_terms(tuple(args)) == newf assert gcd_terms(set(args)) == newf # but a Basic sequence is treated as a container assert gcd_terms(Tuple(*args)) != newf assert gcd_terms(Basic(Tuple(1, 3*y + 3*x*y), Tuple(1, 3))) == \ Basic((1, 3*y*(x + 1)), (1, 3)) # but we shouldn't change keys of a dictionary or some may be lost assert gcd_terms(Dict((x*(1 + y), 2), (x + x*y, y + x*y))) == \ Dict({x*(y + 1): 2, x + x*y: y*(1 + x)}) assert gcd_terms((2*x + 2)**3 + (2*x + 2)**2) == 4*(x + 1)**2*(2*x + 3) assert gcd_terms(0) == 0 assert gcd_terms(1) == 1 assert gcd_terms(x) == x assert gcd_terms(2 + 2*x) == Mul(2, 1 + x, evaluate=False) arg = x*(2*x + 4*y) garg = 2*x*(x + 2*y) assert gcd_terms(arg) == garg assert gcd_terms(sin(arg)) == sin(garg) # issue sympy/sympy#6139-like alpha, alpha1, alpha2, alpha3 = symbols('alpha:4') a = alpha**2 - alpha*x**2 + alpha + x**3 - x*(alpha + 1) rep = {alpha: (1 + sqrt(5))/2 + alpha1*x + alpha2*x**2 + alpha3*x**3} s = (a/(x - alpha)).subs(rep).series(x, 0, 1) assert simplify(collect(s, x)) == -sqrt(5)/2 - Rational(3, 2) + O(x) # issue sympy/sympy#5917 assert _gcd_terms([Integer(0), Integer(0)]) == (0, 0, 1) assert _gcd_terms([2*x + 4]) == (2, x + 2, 1) eq = x/(x + 1/x) assert gcd_terms(eq, fraction=False) == eq
def test_cse_single2(): # Simple substitution, test for being able to pass the expression directly e = Add(Pow(x + y, 2), sqrt(x + y)) substs, reduced = cse(e) assert substs == [(x0, x + y)] assert reduced == [sqrt(x0) + x0**2] substs, reduced = cse(Matrix([[1]])) assert isinstance(reduced[0], Matrix)
def _muly(p, x, y): """ Returns ``_mexpand(y**deg*p.subs({x:x / y}))`` """ p1 = poly_from_expr(p, x)[0] n = degree(p1) a = [c * x**i * y**(n - i) for (i, ), c in p1.terms()] return Add(*a)
def _invertx(p, x): """ Returns ``expand_mul(x**degree(p, x)*p.subs(x, 1/x))`` """ p1 = poly_from_expr(p, x)[0] n = degree(p1) a = [c * x**(n - i) for (i, ), c in p1.terms()] return Add(*a)
def test_glom(): def key(x): return x.as_coeff_Mul()[1] def count(x): return x.as_coeff_Mul()[0] def newargs(cnt, arg): return cnt * arg rl = glom(key, count, newargs) result = rl(Add(x, -x, 3 * x, 2, 3, evaluate=False)) expected = Add(3 * x, 5) assert set(result.args) == set(expected.args) result = rl(Add(*expected.args, evaluate=False)) assert set(result.args) == set(expected.args)
def test_line_wrapping(): assert fcode(((x + y)**10).expand(), assign_to='var') == ( ' var = x**10 + 10*x**9*y + 45*x**8*y**2 + 120*x**7*y**3 + 210*x**6*\n' ' @ y**4 + 252*x**5*y**5 + 210*x**4*y**6 + 120*x**3*y**7 + 45*x**2*y\n' ' @ **8 + 10*x*y**9 + y**10') e = [x**i for i in range(11)] assert fcode(Add(*e)) == ( ' x**10 + x**9 + x**8 + x**7 + x**6 + x**5 + x**4 + x**3 + x**2 + x\n' ' @ + 1')
def test_collect_const(): # coverage not provided by above tests assert collect_const(2*sqrt(3) + 4*a*sqrt(5)) == \ 2*(2*sqrt(5)*a + sqrt(3)) # let the primitive reabsorb assert collect_const(2*sqrt(3) + 4*a*sqrt(5), sqrt(3)) == \ 2*sqrt(3) + 4*a*sqrt(5) assert collect_const(sqrt(2)*(1 + sqrt(2)) + sqrt(3) + x*sqrt(2)) == \ sqrt(2)*(x + 1 + sqrt(2)) + sqrt(3) # issue sympy/sympy#5290 assert collect_const(2*x + 2*y + 1, 2) == \ collect_const(2*x + 2*y + 1) == \ Add(Integer(1), Mul(2, x + y, evaluate=False), evaluate=False) assert collect_const(-y - z) == Mul(-1, y + z, evaluate=False) assert collect_const(2*x - 2*y - 2*z, 2) == \ Mul(2, x - y - z, evaluate=False) assert collect_const(2*x - 2*y - 2*z, -2) == \ Add(2*x, Mul(-2, y + z, evaluate=False), evaluate=False)
def test_cse_not_possible(): # No substitution possible. e = Add(x, y) substs, reduced = cse([e]) assert substs == [] assert reduced == [x + y] # issue sympy/sympy#6329 eq = (meijerg((1, 2), (y, 4), (5, ), [], x) + meijerg((1, 3), (y, 4), (5, ), [], x)) assert cse(eq) == ([], [eq])
def test_line_wrapping(): x, y = symbols('x,y') assert fcode(((x + y)**10).expand(), assign_to="var") == ( " var = x**10 + 10*x**9*y + 45*x**8*y**2 + 120*x**7*y**3 + 210*x**6*\n" " @ y**4 + 252*x**5*y**5 + 210*x**4*y**6 + 120*x**3*y**7 + 45*x**2*y\n" " @ **8 + 10*x*y**9 + y**10") e = [x**i for i in range(11)] assert fcode(Add(*e)) == ( " x**10 + x**9 + x**8 + x**7 + x**6 + x**5 + x**4 + x**3 + x**2 + x\n" " @ + 1")
def test_minimal_polynomial_sq(): p = expand_multinomial((1 + 5 * sqrt(2) + 2 * sqrt(3))**3) mp = minimal_polynomial(cbrt(p))(x) assert mp == x**4 - 4 * x**3 - 118 * x**2 + 244 * x + 1321 p = expand_multinomial((1 + sqrt(2) - 2 * sqrt(3) + sqrt(7))**3) mp = minimal_polynomial(cbrt(p))(x) assert mp == x**8 - 8 * x**7 - 56 * x**6 + 448 * x**5 + 480 * x**4 - 5056 * x**3 + 1984 * x**2 + 7424 * x - 3008 p = Add(*[sqrt(i) for i in range(1, 12)]) mp = minimal_polynomial(p)(x) assert mp.subs({x: 0}) == -71965773323122507776
def sampling_E(expr, given_condition=None, numsamples=1, evalf=True, **kwargs): """ Sampling version of E See Also ======== diofant.stats.P diofant.stats.rv.sampling_P diofant.stats.rv.sampling_density """ samples = sample_iter(expr, given_condition, numsamples=numsamples, **kwargs) result = Add(*list(samples)) / numsamples if evalf: return result.evalf() else: return result
def test_rewrite(): assert rewrite(Integer(1), x, m) == (1, None) e = exp(x) assert rewrite(e, x, m) == (1/m, -x) e = exp(x**2) assert rewrite(e, x, m) == (1/m, -x**2) e = exp(x + 1/x) assert rewrite(e, x, m) == (1/m, -x - 1/x) e = 1/exp(-x + exp(-x)) - exp(x) assert rewrite(e, x, m) == (Add(-1/m, 1/(m*exp(m)), evaluate=False), -x) e = exp(x)*log(log(exp(x))) assert mrv(e, x) == {exp(x)} assert rewrite(e, x, m) == (1/m*log(x), -x) e = exp(-x + 1/x**2) - exp(x + 1/x) assert rewrite(e, x, m) == (Add(m, Mul(-1, exp(1/x + x**(-2))/m, evaluate=False), evaluate=False), -x + 1/x**2)
def expectation(expr, condition=None, numsamples=None, evaluate=True, **kwargs): """ Returns the expected value of a random expression Parameters ========== expr : Expr containing RandomSymbols The expression of which you want to compute the expectation value given : Expr containing RandomSymbols A conditional expression. E(X, X>0) is expectation of X given X > 0 numsamples : int Enables sampling and approximates the expectation with this many samples evalf : Bool (defaults to True) If sampling return a number rather than a complex expression evaluate : Bool (defaults to True) In case of continuous systems return unevaluated integral Examples ======== >>> from diofant.stats import E, Die >>> X = Die('X', 6) >>> E(X) 7/2 >>> E(2*X + 1) 8 >>> E(X, X > 3) # Expectation of X given that it is above 3 5 """ if not random_symbols(expr): # expr isn't random? return expr if numsamples: # Computing by monte carlo sampling? return sampling_E(expr, condition, numsamples=numsamples) # Create new expr and recompute E if condition is not None: # If there is a condition return expectation(given(expr, condition), evaluate=evaluate) # A few known statements for efficiency if expr.is_Add: # We know that E is Linear return Add(*[expectation(arg, evaluate=evaluate) for arg in expr.args]) # Otherwise case is simple, pass work off to the ProbabilitySpace result = pspace(expr).integrate(expr) if evaluate and hasattr(result, 'doit'): return result.doit(**kwargs) else: return result
def _minpoly_sin(ex, x): """ Returns the minimal polynomial of ``sin(ex)`` see http://mathworld.wolfram.com/TrigonometryAngles.html """ c, a = ex.args[0].as_coeff_Mul() if a is pi: if c.is_rational: n = c.q q = sympify(n) if q.is_prime: # for a = pi*p/q with q odd prime, using chebyshevt # write sin(q*a) = mp(sin(a))*sin(a); # the roots of mp(x) are sin(pi*p/q) for p = 1,..., q - 1 a = dup_chebyshevt(n, ZZ) return Add(*[x**(n - i - 1) * a[i] for i in range(n)]) if c.p == 1: if q == 9: return 64 * x**6 - 96 * x**4 + 36 * x**2 - 3 if n % 2 == 1: # for a = pi*p/q with q odd, use # sin(q*a) = 0 to see that the minimal polynomial must be # a factor of dup_chebyshevt(n, ZZ) a = dup_chebyshevt(n, ZZ) a = [x**(n - i) * a[i] for i in range(n + 1)] r = Add(*a) _, factors = factor_list(r) res = _choose_factor(factors, x, ex) return res expr = ((1 - cos(2 * c * pi)) / 2)**S.Half res = _minpoly_compose(expr, x, QQ) return res raise NotAlgebraic("%s doesn't seem to be an algebraic element" % ex)
def bottom_up_scan(ex): if ex.is_Atom: if ex is S.ImaginaryUnit: if ex not in mapping: return update_mapping(ex, 2, 1) else: return symbols[ex] elif ex.is_Rational: return ex elif ex.is_Add: return Add(*[bottom_up_scan(g) for g in ex.args]) elif ex.is_Mul: return Mul(*[bottom_up_scan(g) for g in ex.args]) elif ex.is_Pow: if ex.exp.is_Rational: if ex.exp < 0 and ex.base.is_Add: coeff, terms = ex.base.as_coeff_add() elt, _ = primitive_element(terms, polys=True) alg = ex.base - coeff # XXX: turn this into eval() inverse = invert(elt.gen + coeff, elt).as_expr() base = inverse.subs(elt.gen, alg).expand() if ex.exp == -1: return bottom_up_scan(base) else: ex = base**(-ex.exp) if not ex.exp.is_Integer: base, exp = (ex.base**ex.exp.p).expand(), Rational( 1, ex.exp.q) else: base, exp = ex.base, ex.exp base = bottom_up_scan(base) expr = base**exp if expr not in mapping: return update_mapping(expr, 1 / exp, -base) else: return symbols[expr] elif ex.is_AlgebraicNumber: if ex.root not in mapping: return update_mapping(ex.root, ex.minpoly) else: return symbols[ex.root] raise NotAlgebraic("%s doesn't seem to be an algebraic number" % ex)
def _eval_aseries(self, n, args0, x, logx): from diofant import Order, Add, combsimp point = args0[0] if point is S.Infinity: z = self.args[0] l = [ gamma(k + Rational(5, 6)) * gamma(k + Rational(1, 6)) * Rational(3, 4)**k / (2 * S.Pi**2 * factorial(k) * z**Rational(3 * k + 1, 2)) for k in range(n) ] l = [combsimp(t) for t in l] o = Order(1 / z**Rational(3 * n + 1, 2), x) return (Add(*l))._eval_nseries(x, n, logx) + o # All other points are not handled return super(_airybis, self)._eval_aseries(n, args0, x, logx)
def field_isomorphism_factor(a, b): """Construct field isomorphism via factorization. """ _, factors = factor_list(a.minpoly, extension=b) for f, _ in factors: if f.degree() == 1: coeffs = f.rep.TC().to_diofant_list() d, terms = len(coeffs) - 1, [] for i, coeff in enumerate(coeffs): terms.append(coeff * b.root**(d - i)) root = Add(*terms) if (a.root - root).evalf(chop=True) == 0: return coeffs if (a.root + root).evalf(chop=True) == 0: return [-c for c in coeffs] else: return