'Compute a definite integral over a piecewise polynomial.
Parameters
a : float
Lower integration bound
b : float
Upper integration bound
extrapolate : {bool, \'periodic\', None}, optional
Whether to extrapolate to out-of-bounds points based on first
and last intervals, or to return NaNs. If \'periodic\', periodic
extrapolation is used. If None (default), use `self.extrapolate`.
Returns
array_like
Definite integral of the piecewise polynomial over [a, b]'

def integrate(self, a, b, extrapolate=None):

    ib = self.antiderivative()
    if (extrapolate is None):
        extrapolate = self.extrapolate
    if (extrapolate != 'periodic'):
        ib.extrapolate = extrapolate
    if (extrapolate == 'periodic'):
        if (a <= b):
            sign = 1
        else:
            (a, b) = (b, a)
            sign = (-1)
        (xs, xe) = (self.x[0], self.x[(-1)])
        period = (xe - xs)
        interval = (b - a)
        (n_periods, left) = divmod(interval, period)
        res = (n_periods * (ib(xe) - ib(xs)))
        a = (xs + ((a - xs) % period))
        b = (a + left)
        if (b <= xe):
            res += (ib(b) - ib(a))
        else:
            res += (((ib(xe) - ib(a)) + ib((((xs + left) + a) - xe))) - ib(xs))
        return (sign * res)
    else:
        return (ib(b) - ib(a))
