def _eval_product(self, term=None): k = self.index a = self.lower n = self.upper if term is None: term = self.term if not term.has(k): return term**(n - a + 1) elif term.is_polynomial(k): poly = term.as_poly(k) A = B = Q = S.One C_ = poly.LC all_roots = roots(poly, multiple=True) for r in all_roots: A *= C.RisingFactorial(a - r, n - a + 1) Q *= n - r if len(all_roots) < poly.degree: B = Product(quo(poly, Q.as_poly(k)), (k, a, n)) return poly.LC**(n - a + 1) * A * B elif term.is_Add: p, q = term.as_numer_denom() p = self._eval_product(p) q = self._eval_product(q) return p / q elif term.is_Mul: exclude, include = [], [] for t in term.args: p = self._eval_product(t) if p is not None: exclude.append(p) else: include.append(p) if not exclude: return None else: A, B = Mul(*exclude), Mul(*include) return A * Product(B, (k, a, n)) elif term.is_Pow: if not term.base.has(k): s = sum(term.exp, (k, a, n)) if not isinstance(s, Sum): return term.base**s elif not term.exp.has(k): p = self._eval_product(term.base) if p is not None: return p**term.exp
def _eval_product(self, a, n, term): from sympy import summation, Sum k = self.index if not term.has(k): return term**(n - a + 1) elif term.is_polynomial(k): poly = term.as_poly(k) A = B = Q = S.One C_ = poly.LC() all_roots = roots(poly, multiple=True) for r in all_roots: A *= C.RisingFactorial(a - r, n - a + 1) Q *= n - r if len(all_roots) < poly.degree(): B = Product(quo(poly, Q.as_poly(k)), (k, a, n)) return poly.LC()**(n - a + 1) * A * B elif term.is_Add: p, q = term.as_numer_denom() p = self._eval_product(a, n, p) q = self._eval_product(a, n, q) return p / q elif term.is_Mul: exclude, include = [], [] for t in term.args: p = self._eval_product(a, n, t) if p is not None: exclude.append(p) else: include.append(t) if not exclude: return None else: A, B = Mul(*exclude), term._new_rawargs(*include) return A * Product(B, (k, a, n)) elif term.is_Pow: if not term.base.has(k): s = summation(term.exp, (k, a, n)) if not isinstance(s, Sum): return term.base**s elif not term.exp.has(k): p = self._eval_product(a, n, term.base) if p is not None: return p**term.exp
def taylor_term(n, x, *previous_terms): if n < 0 or n % 2 == 0: return S.Zero else: x = sympify(x) if len(previous_terms) >= 2 and n > 2: p = previous_terms[-2] return -p * (n-2)**2/(n*(n-1)) * x**2 else: k = (n - 1) // 2 R = C.RisingFactorial(S.Half, k) F = C.factorial(k) return (-1)**k * R / F * x**n / n
def _eval_expand_func(self, deep=True, **hints): if deep: arg = self.args[0].expand(deep, **hints) else: arg = self.args[0] if arg.is_Add: coeff, tail = arg.as_coeff_add() if coeff and coeff.q != 1: tail = (C.Rational(1, coeff.q), ) + tail coeff = floor(coeff) tail = arg._new_rawargs(*tail, **dict(reeval=False)) return gamma(tail) * C.RisingFactorial(tail, coeff) return self.func(*self.args)
def taylor_term(n, x, *previous_terms): if n == 0: return S.Pi*S.ImaginaryUnit / 2 elif n < 0 or n % 2 == 0: return S.Zero else: x = sympify(x) if len(previous_terms) >= 2 and n > 2: p = previous_terms[-2] return p * (n-2)**2/(n*(n-1)) * x**2 else: k = (n - 1) // 2 R = C.RisingFactorial(S.Half, k) F = C.Factorial(k) return -R / F * S.ImaginaryUnit * x**n / n
def _eval_expand_func(self, *args): arg = self.args[0].expand() if arg.is_Add: for i, coeff in enumerate(arg.args[:]): if arg.args[i].is_Number: terms = C.Add(*(arg.args[:i] + arg.args[i + 1:])) if coeff.is_Rational: if coeff.q != 1: terms += C.Rational(1, coeff.q) coeff = C.Integer(int(coeff)) else: continue return gamma(terms) * C.RisingFactorial(terms, coeff) return self.func(*self.args)
def _eval_expand_func(self, **hints): arg = self.args[0] if arg.is_Rational: if abs(arg.p) > arg.q: x = Dummy('x') n = arg.p // arg.q p = arg.p - n*arg.q return gamma(x + n)._eval_expand_func().subs(x, Rational(p, arg.q)) if arg.is_Add: coeff, tail = arg.as_coeff_add() if coeff and coeff.q != 1: intpart = floor(coeff) tail = (coeff - intpart,) + tail coeff = intpart tail = arg._new_rawargs(*tail, reeval=False) return gamma(tail)*C.RisingFactorial(tail, coeff) return self.func(*self.args)
def _eval_product(self, term, limits): from sympy import summation (k, a, n) = limits if k not in term.free_symbols: return term**(n - a + 1) if a == n: return term.subs(k, a) dif = n - a if dif.is_Integer: return Mul(*[term.subs(k, a + i) for i in xrange(dif + 1)]) elif term.is_polynomial(k): poly = term.as_poly(k) A = B = Q = S.One all_roots = roots(poly, multiple=True) for r in all_roots: A *= C.RisingFactorial(a - r, n - a + 1) Q *= n - r if len(all_roots) < poly.degree(): arg = quo(poly, Q.as_poly(k)) B = Product(arg, (k, a, n)).doit() return poly.LC()**(n - a + 1) * A * B elif term.is_Add: p, q = term.as_numer_denom() p = self._eval_product(p, (k, a, n)) q = self._eval_product(q, (k, a, n)) return p / q elif term.is_Mul: exclude, include = [], [] for t in term.args: p = self._eval_product(t, (k, a, n)) if p is not None: exclude.append(p) else: include.append(t) if not exclude: return None else: arg = term._new_rawargs(*include) A = Mul(*exclude) B = Product(arg, (k, a, n)).doit() return A * B elif term.is_Pow: if not term.base.has(k): s = summation(term.exp, (k, a, n)) return term.base**s elif not term.exp.has(k): p = self._eval_product(term.base, (k, a, n)) if p is not None: return p**term.exp elif isinstance(term, Product): evaluated = term.doit() f = self._eval_product(evaluated, limits) if f is None: return Product(evaluated, limits) else: return f