ore_algebra.analytic.polynomial_approximation¶
Rigorous approximation of D-finite functions by polynomials
Functions
chebyshev_economization (pol, eps) |
Decrease the degree of pol in such a way that its value on the real segment [-1, 1] changes at most by eps . |
chebyshev_polynomials (ring, n) |
Return the list of the Chebyshev polynomials T[0], …, T[n -1] as elements of ring . |
combine_radii (pol) |
|
doit (dop, ini, path, rad, eps, derivatives, …) |
|
general_economization (…) |
Decrease the degree of pol by subtracting a linear combination of the polynomials produced by economization_polynomials . |
mixed_economization () |
|
on_disk (dop, ini, path, rad, eps) |
Compute a polynomial approximation of a solution of dop on a complex disk. |
on_interval (dop, ini, path, eps[, rad]) |
Compute a polynomial approximation of a solution of dop on a segment. |
taylor_economization (pol, eps) |
Economize a polynomial by removing monomials. |
-
ore_algebra.analytic.polynomial_approximation.
chebyshev_economization
(pol, eps)¶ Decrease the degree of
pol
in such a way that its value on the real segment [-1, 1] changes at most byeps
.EXAMPLES:
sage: from ore_algebra.analytic.polynomial_approximation import chebyshev_economization sage: pol = polygen(QQ, 'x')._exp_series(10).change_ring(RBF) sage: newpol = chebyshev_economization(pol, RBF(1e-3)); newpol [0.04379...]*x^4 + [0.17734...]*x^3 + [0.49919...]*x^2 + [0.9973...]*x + [1.000 +/- 6...e-4]
TESTS:
sage: from ore_algebra.analytic.polynomial_approximation import _test_fun_approx sage: _test_fun_approx(newpol, pol, interval_rad=1)
-
ore_algebra.analytic.polynomial_approximation.
chebyshev_polynomials
(ring, n)¶ Return the list of the Chebyshev polynomials T[0], …, T[
n
-1] as elements ofring
.EXAMPLES:
sage: from ore_algebra.analytic.polynomial_approximation import chebyshev_polynomials sage: chebyshev_polynomials(ZZ['x'], 3) [1, x, 2*x^2 - 1]
TESTS:
sage: chebyshev_polynomials(QQ['x'], 0) []
-
ore_algebra.analytic.polynomial_approximation.
general_economization
(economization_polynomials, pol, eps)¶ Decrease the degree of
pol
by subtracting a linear combination of the polynomials produced byeconomization_polynomials
.INPUT:
economization_polynomials(ring, n)
- function returning a list [E[0], …, E[n-1]] ofn
elements ofring
; it is assumed that E[k] is a polynomial of degree exactlyk
such that |E[k](x)| ≤ 1 when x lies in some domain of interest;pol
- polynomial with real or complex ball coefficients;eps
- real ball, maximum error that may be added to the polynomial (see below).
OUTPUT:
A polynomial with the same parent as
pol
. A bound on the linear combination of economization polynomials is added to the constant term. For real x in the domain where they are all bounded by 1, the value of the result at x contains that ofpol
. This also holds true for complex x whenpol
has complex coefficients, but not in general for the evaluation at complex points of polynomials with real coefficients.TESTS:
sage: from ore_algebra.analytic.polynomial_approximation import general_economization sage: def monomials(ring, n): ....: x = ring.gen() ....: return [x**k for k in range(n)] sage: Pols.<x> = RBF[] sage: general_economization(monomials, ....: x^5 + 10*x^4 + x^3 + 2*x + 10, RBF(3)) 10.00000000000000*x^4 + 2.000000000000000*x + [1e+1 +/- 2.01]
-
ore_algebra.analytic.polynomial_approximation.
on_disk
(dop, ini, path, rad, eps)¶ Compute a polynomial approximation of a solution of
dop
on a complex disk.EXAMPLES:
sage: from ore_algebra import * sage: from ore_algebra.analytic import polynomial_approximation as polapprox sage: QQi.<i> = QuadraticField(-1, 'I') sage: Dops, x, Dx = DifferentialOperators() sage: polapprox.on_disk(Dx - 1, [1], [0], 1, 1e-3) ([0.001...])*x^6 + ([0.008...])*x^5 + ([0.041...])*x^4 + ([0.16...])*x^3 + 0.50...*x^2 + x + [1.00...] + [+/- ...]*I
TESTS:
sage: from ore_algebra.analytic.polynomial_approximation import _test_fun_approx sage: pol = polapprox.on_disk(Dx - 1, [1], [0, i], 1, 1e-20) sage: _test_fun_approx(pol, lambda b: (i + b).exp(), disk_rad=1, prec=200)
sage: pol = polapprox.on_disk(Dx^2 + 2*x*Dx, [0, 2/sqrt(RBF(pi))], [0], 2, 1e-10) sage: _test_fun_approx(pol, lambda x: x.erf(), disk_rad=1) sage: pol[0].abs() < RBF(10)^-10 True
Ensure that the polynomial we computed correctly takes into account that x may be complex, even though the Taylor series it is based on has real coefficients:
sage: pol.parent() Univariate Polynomial Ring in x over Complex ball field with ... precision sage: pol[0].imag().is_zero() False
-
ore_algebra.analytic.polynomial_approximation.
on_interval
(dop, ini, path, eps, rad=None)¶ Compute a polynomial approximation of a solution of
dop
on a segment.EXAMPLES:
sage: from ore_algebra import * sage: from ore_algebra.analytic import polynomial_approximation as polapprox sage: Dops, x, Dx = DifferentialOperators() sage: pol1 = polapprox.on_interval(Dx - 1, [1], [0], 1e-3, rad=1); pol1 [0.008...]*x^5 + [0.04...]*x^4 + [0.166...]*x^3 + [0.499...]*x^2 + [1.0...]*x + [1.0...] sage: pol2 = polapprox.on_interval(Dx - 1, [1], [0, [1, 2]], 1e-3); pol2 [0.189...]*x^4 + [0.7...]*x^3 + [2.24...]*x^2 + [4.4...]*x + [4.4...]
TESTS:
sage: from ore_algebra.analytic.polynomial_approximation import _test_fun_approx sage: _test_fun_approx(pol1, lambda b: b.exp(), interval_rad=1) sage: _test_fun_approx(pol2, lambda b: (3/2 + b).exp(), interval_rad=.5) sage: polapprox.on_interval(Dx - 1, [1], [0, [1, 2]], 1e-3, rad=1) Traceback (most recent call last): ... TypeError: unexpected value for point: [1, 2] sage: polapprox.on_interval(Dx - 1, [1], [0], 1e-3) Traceback (most recent call last): ... TypeError: missing radius sage: pol = polapprox.on_interval(Dx^2 - x, ....: ini=[1/(gamma(2/3)*3^(2/3)), -1/(gamma(1/3)*3^(1/3))], ....: path=[0,[-1,1]], eps=1e-8) sage: _test_fun_approx(pol, lambda x: RBF(CBF(x).airy_ai()), interval_rad=1)
-
ore_algebra.analytic.polynomial_approximation.
taylor_economization
(pol, eps)¶ Economize a polynomial by removing monomials.
Remove terms from the polynomial
pol
, starting with the high-order terms, in such a way that its value on the disk |z| < 1 changes at most byeps
.A bound on the difference between the result and the input polynomial is added to the constant term, so that, for any complex number z with |z| < 1, the value of the result at z contains that of
pol
.EXAMPLES:
sage: from ore_algebra.analytic.polynomial_approximation import taylor_economization sage: pol = polygen(QQ, 'x')._exp_series(10).change_ring(RBF); pol [2.755...e-6 +/- 5.96e-22]*x^9 + [2.480...e-5 +/- 4.96e-21]*x^8 + [0.0001... +/- 3.97e-20]*x^7 + [0.0013... +/- 4.92e-19]*x^6 + ... + x + 1.000000000000000 sage: newpol = taylor_economization(pol, RBF(1e-3)); newpol ([0.0013... +/- 4.92e-19])*x^6 + ... + x + [1.000 +/- 2.26e-4] + [+/- 2.26e-4]*I
TESTS:
sage: from ore_algebra.analytic.polynomial_approximation import _test_fun_approx sage: _test_fun_approx(newpol, pol, disk_rad=1) sage: Pols.<x> = RBF[] sage: taylor_economization(x^5 + 10*x^4 + x^3 + 2*x + 10, RBF(3)) 10.0000...*x^4 + 2.0000...*x + [1e+1 +/- 2.01] + [+/- 2.01]*I