def _eval_evalf(self, prec): from mpmath import mp, workprec from diofant import Expr z = self.args[0]._to_mpmath(prec) with workprec(prec): res = mp.airybi(z, derivative=1) return Expr._from_mpmath(res, prec)
def _eval_evalf(self, prec): from mpmath import mp, workprec from diofant import Expr a = self.args[0]._to_mpmath(prec) z = self.args[1]._to_mpmath(prec) with workprec(prec): res = mp.gammainc(a, z, mp.inf) return Expr._from_mpmath(res, prec)
def _eval_evalf(self, prec): m = self.args[0] if m.is_Integer and m.is_nonnegative: from mpmath import mp from diofant import Expr m = m._to_mpmath(prec) with workprec(prec): res = mp.eulernum(m) return Expr._from_mpmath(res, prec)
def _eval_evalf(self, prec): # The default code is insufficient for polar arguments. # mpmath provides an optional argument "r", which evaluates # G(z**(1/r)). I am not sure what its intended use is, but we hijack it # here in the following way: to evaluate at a number z of |argument| # less than (say) n*pi, we put r=1/n, compute z' = root(z, n) # (carefully so as not to loose the branch information), and evaluate # G(z'**(1/r)) = G(z'**n) = G(z). from diofant.functions import exp_polar, ceiling from diofant import Expr import mpmath z = self.argument znum = self.argument._eval_evalf(prec) if znum.has(exp_polar): znum, branch = znum.as_coeff_mul(exp_polar) if len(branch) != 1: return branch = branch[0].args[0] / I else: branch = Integer(0) n = ceiling(abs(branch / S.Pi)) + 1 znum = znum**(Integer(1) / n) * exp(I * branch / n) # Convert all args to mpf or mpc try: [z, r, ap, bq] = [ arg._to_mpmath(prec) for arg in [znum, 1 / n, self.args[0], self.args[1]] ] except ValueError: return with mpmath.workprec(prec): v = mpmath.meijerg(ap, bq, z, r) return Expr._from_mpmath(v, prec)
def test_sympyissue_5486_bug(): assert abs(Expr._from_mpmath(I._to_mpmath(15), 15) - I) < 1.0e-15 pytest.raises(TypeError, lambda: Expr._from_mpmath(I, 15))
def test_issue_5486_bug(): from diofant import I, Expr assert abs(Expr._from_mpmath(I._to_mpmath(15), 15) - I) < 1.0e-15 pytest.raises(TypeError, lambda: Expr._from_mpmath(I, 15))
def test_from_mpmath(): # issue sympy/sympy#5486 pytest.raises(TypeError, lambda: Expr._from_mpmath(I, 15))
def test_sympyissue_5486(): assert not cos(sqrt(0.5 + I)).evalf(strict=False).is_Function assert abs(Expr._from_mpmath(I._to_mpmath(15), 15) - I) < 1.0e-15
def test_sympyissue_5486_bug(): assert abs(Expr._from_mpmath(I._to_mpmath(15), 15) - I) < 1.0e-15
def jn_zeros(n, k, method="diofant", dps=15): """ Zeros of the spherical Bessel function of the first kind. This returns an array of zeros of jn up to the k-th zero. * method = "diofant": uses mpmath's function ``besseljzero`` * method = "scipy": uses the `SciPy's sph_jn <http://docs.scipy.org/doc/scipy/reference/generated/scipy.special.jn_zeros.html>`_ and `newton <http://docs.scipy.org/doc/scipy/reference/generated/scipy.optimize.newton.html>`_ to find all roots, which is faster than computing the zeros using a general numerical solver, but it requires SciPy and only works with low precision floating point numbers. [The function used with method="diofant" is a recent addition to mpmath, before that a general solver was used.] Examples ======== >>> from diofant import jn_zeros >>> jn_zeros(2, 4, dps=5) [5.7635, 9.095, 12.323, 15.515] See Also ======== jn, yn, besselj, besselk, bessely """ from math import pi if method == "diofant": from mpmath import besseljzero from mpmath.libmp.libmpf import dps_to_prec from diofant import Expr prec = dps_to_prec(dps) return [ Expr._from_mpmath( besseljzero(sympify(n + 0.5)._to_mpmath(prec), int(l)), prec) for l in range(1, k + 1) ] elif method == "scipy": from scipy.special import sph_jn from scipy.optimize import newton def f(x): return sph_jn(n, x)[0][-1] else: raise NotImplementedError("Unknown method.") def solver(f, x): if method == "scipy": root = newton(f, x) else: raise NotImplementedError("Unknown method.") return root # we need to approximate the position of the first root: root = n + pi # determine the first root exactly: root = solver(f, root) roots = [root] for i in range(k - 1): # estimate the position of the next root using the last root + pi: root = solver(f, root + pi) roots.append(root) return roots