Example #1
0
    def __call__(self, s, a=0, b=np.inf):
        """transform f(r, *args) at s

        Parameters
        ----------
        s : scalar
            transform variable, i.e. coordinate to evaluate transform at
        a, b : float, optional
            limits of integration.  default a=0, b=np.inf.  A hankel transform
            is usually from 0 to infinity.  However, if you have a function
            that is defined on [a,b] and zero elsewhere then you can restrict
            integration to that interval (shanks_ind will be ignored if
            b!=np.inf).

        Returns
        -------
        F : float
            Transformed functin evaluated at s.
        err_est : float
            Error estimate.  For each interval (i.e. between bessel zeros
            and any specified points) sum up 200*abs(G-K)**1.5.  The error is
            calculated before any shanks extrapolation so the error is just a
            measure of the difference between the coarse Gauss quadrature and
            the finer Kronrod quadrature.


        """

        integrand = functools.partial(self._integrand, s)

        zeros = self.jn_0s / s

        if not self.points is None:
            #zeros becomes both zeros and interesting points/singularities
            zeros = np.unique(
                list(zeros) + list(self.points[(self.points < zeros[-1])
                                               & (self.points > 0)]))

        if (a != 0) or (b != np.inf):
            zeros = np.unique(zeros.clip(a, b))

        #1st segment
        igral0, err_est0 = gk_quad(integrand, zeros[0], zeros[1], self.args,
                                   self.ng0)
        #remaining segments
        if len(zeros) > 2:
            igralm, err_estm = gk_quad(integrand, zeros[1:-1], zeros[2:],
                                       self.args, self.ng)
        else:
            return igral0[0], err_est0[0]

        if (self.shanks_ind is None) or (b != np.inf):
            igral = igral0 + np.sum(igralm)
        else:
            igralm.cumsum(out=igralm)
            igral = igral0 + shanks(igralm, self.shanks_ind)

        err_est = (200 * np.abs(err_est0))**1.5 + np.sum(
            (200 * np.abs(err_estm))**1.5)
        return igral[0], err_est[0]
Example #2
0
def check_gk_quad_chunks_extra_dims2(n):
    """check that gk_quad integrates polynomial of degree 3*n+1 (even) and
    3*n+2 (odd)exactly, with multiple intervals with function that returns
    extra dims.

    This test is not rigorous because the polynomials formed can be fairly well
    approximated using lower order schemes
    """
    #a, b = (-0.9, 1.3)
    a = np.array([-0.9, -0.4, .5])
    b = np.array([-0.4, 0.5, 1.3])
    coeff = np.arange(1, 3 * n + 1 + (n % 2))
    coeff[::2] = coeff[::2] * -1.0
    f = np.poly1d(coeff)

    def g(x):
        out = f(x) * np.arange(1, 9)
        return out

    g_ = g  #np.vectorize(g)
    F = f.integ()
    exact = np.sum(F(b) - F(a)) * np.arange(1, 9)

    assert_allclose(gk_quad(g_, a, b, n=n, sum_intervals=True)[0],
                    exact,
                    rtol=1e-3,
                    atol=0)
Example #3
0
def check_gk_quad(n):
    """check that gk_quad integrates polynomial of degree 3*n+1 (even) and
    3*n+2 (odd)exactly

    This test is not rigorous because the ploynmials formed can be fairly well
    approximated using lower order schemes
    """
    a, b = (-0.9, 1.3)
    coeff = np.arange(1, 3*n + 1 + (n%2))
    coeff[::2]  =coeff[::2]*-1.0
    f = np.poly1d(coeff)
    F = f.integ()
    exact = F(b) - F(a)

    assert_allclose(gk_quad(f,a,b, n=n)[0], exact, rtol=1e-14,atol=0)
Example #4
0
def check_gk_quad(n):
    """check that gk_quad integrates polynomial of degree 3*n+1 (even) and
    3*n+2 (odd)exactly

    This test is not rigorous because the polynomials formed can be fairly well
    approximated using lower order schemes
    """
    a, b = (-0.9, 1.3)
    coeff = np.arange(1, 3 * n + 1 + (n % 2))
    coeff[::2] = coeff[::2] * -1.0
    f = np.poly1d(coeff)
    F = f.integ()
    exact = F(b) - F(a)

    assert_allclose(gk_quad(f, a, b, n=n)[0], exact, rtol=1e-14, atol=0)
Example #5
0
def check_gk_quad_chunks(n):
    """check that gk_quad integrates polynomial of degree 3*n+1 (even) and
    3*n+2 (odd)exactly, with multiple intervals

    This test is not rigorous because the polynomials formed can be fairly well
    approximated using lower order schemes
    """
    #a, b = (-0.9, 1.3)
    a = np.array([-0.9, -0.4, .5])
    b = np.array([-0.4, 0.5, 1.3])
    coeff = np.arange(1, 3*n + 1 + (n%2))
    coeff[::2]  =coeff[::2]*-1.0
    f = np.poly1d(coeff)
    F = f.integ()
    exact = np.sum(F(b) - F(a))

    assert_allclose(gk_quad(f,a,b, n=n, sum_intervals=True)[0], exact, rtol=1e-3,atol=0)
Example #6
0
def check_gk_quad_chunks(n):
    """check that gk_quad integrates polynomial of degree 3*n+1 (even) and
    3*n+2 (odd)exactly, with multiple intervals

    This test is not rigorous because the polynomials formed can be fairly well
    approximated using lower order schemes
    """
    #a, b = (-0.9, 1.3)
    a = np.array([-0.9, -0.4, .5])
    b = np.array([-0.4, 0.5, 1.3])
    coeff = np.arange(1, 3 * n + 1 + (n % 2))
    coeff[::2] = coeff[::2] * -1.0
    f = np.poly1d(coeff)
    F = f.integ()
    exact = np.sum(F(b) - F(a))

    assert_allclose(gk_quad(f, a, b, n=n, sum_intervals=True)[0],
                    exact,
                    rtol=1e-3,
                    atol=0)
Example #7
0
def check_gk_quad_chunks_extra_dims2(n):
    """check that gk_quad integrates polynomial of degree 3*n+1 (even) and
    3*n+2 (odd)exactly, with multiple intervals with function that returns
    extra dims.

    This test is not rigorous because the polynomials formed can be fairly well
    approximated using lower order schemes
    """
    #a, b = (-0.9, 1.3)
    a = np.array([-0.9, -0.4, .5])
    b = np.array([-0.4, 0.5, 1.3])
    coeff = np.arange(1, 3*n + 1 + (n%2))
    coeff[::2]  =coeff[::2]*-1.0
    f = np.poly1d(coeff)
    def g(x):
        out = f(x)*np.arange(1,9)
        return out
    g_ = g#np.vectorize(g)
    F = f.integ()
    exact = np.sum(F(b) - F(a)) * np.arange(1,9)

    assert_allclose(gk_quad(g_,a,b, n=n, sum_intervals=True)[0], exact, rtol=1e-3,atol=0)
Example #8
0
    def __call__(self, s, a=0, b=np.inf):
        """transform f(r, *args) at s

        Parameters
        ----------
        s : scalar
            transform variable, i.e. coordinate to evaluate transform at
        a, b : float, optional
            limits of integration.  default a=0, b=np.inf.  A hankel transform
            is usually from 0 to infinity.  However, if you have a function
            that is defined on [a,b] and zero elsewhere then you can restrict
            integration to that interval (shanks_ind will be ignored if
            b!=np.inf).

        Returns
        -------
        F : float
            Transformed functin evaluated at s.
        err_est : float
            Error estimate.  For each interval (i.e. between bessel zeros
            and any specified points) sum up 200*abs(G-K)**1.5.  The error is
            calculated before any shanks extrapolation so the error is just a
            measure of the difference between the coarse Gauss quadrature and
            the finer Kronrod quadrature.


        """


        integrand = functools.partial(self._integrand, s)

        zeros = self.jn_0s / s

        if not self.points is None:
            #zeros becomes both zeros and interesting points/singularities
            zeros = np.unique(list(zeros) +
                    list(self.points[(self.points < zeros[-1])
                                     & (self.points>0)]))

        if (a!=0) or (b!=np.inf):
            zeros = np.unique(zeros.clip(a, b))

        #1st segment
        igral0, err_est0 = gk_quad(integrand, zeros[0], zeros[1],
                                   self.args, self.ng0)
        #remaining segments
        if len(zeros)>2:
            igralm, err_estm = gk_quad(integrand, zeros[1:-1], zeros[2:],
                                       self.args, self.ng)
        else:
            return igral0[0], err_est0[0]


        if (self.shanks_ind is None) or (b!=np.inf):
            igral = igral0 + np.sum(igralm)
        else:
            igralm.cumsum(out=igralm)
            igral = igral0 + shanks(igralm, self.shanks_ind)

        err_est = (200*np.abs(err_est0))**1.5 + np.sum((200*np.abs(err_estm))**1.5)
        return igral[0], err_est[0]