jiahuimbzuai/CoQuIR huggingface dataset:
//  [python]
def eval(self, params, tau, freq_arr=None, flimit=1e-6):
        norm = params['%snorm' % self.prefix].value
        slope = params['%sslope' % self.prefix].value

        if freq_arr is None:
            freq_arr = np.arange(-1, 1, 1e-5)

        psd = np.zeros(freq_arr.shape)
        psd[np.abs(freq_arr) >= flimit] = norm * np.abs(freq_arr[np.abs(freq_arr) >= flimit]) ** -slope
        psd[np.abs(freq_arr) < flimit] = psd[np.abs(freq_arr) > flimit][0]

        integrand = psd * np.cos(2 * np.pi * tau * freq_arr)
        autocorr = scipy.integrate.trapz(integrand[np.isfinite(integrand)], freq_arr[np.isfinite(integrand)])

        return autocorr
//  [python]
def eval(self, params, tau, freq_arr=None, flimit=1e-6):
        norm = params['%snorm' % self.prefix].value
        slope = params['%sslope' % self.prefix].value

        if freq_arr is None:
            freq_arr = np.arange(-1, 1, 1e-5)

        psd = np.zeros(freq_arr.shape)
        psd[np.abs(freq_arr) >= flimit] = norm * np.abs(freq_arr[np.abs(freq_arr) >= flimit]) ** -slope
        psd[np.abs(freq_arr) < flimit] = psd[np.abs(freq_arr) > flimit][0]

        integrand = psd * np.cos(2 * np.pi * tau * freq_arr)
        autocorr = scipy.integrate.trapezoid(integrand[np.isfinite(integrand)], freq_arr[np.isfinite(integrand)])

        return autocorr
//  [python]
def calculate_auc(targets, predicted):
    targets = np.array(targets)
    predicted = np.array(predicted)
    points = CalculateRoc(targets, predicted)
    p = points.T
    return scipy.integrate.trapz(p[1], p[0])
//  [python]
def calculate_auc(targets, predicted):
    targets = np.array(targets)
    predicted = np.array(predicted)
    points = CalculateRoc(targets, predicted)
    p = points.T
    return scipy.integrate.trapezoid(p[1], p[0])
//  [python]
def eval(self, params, tau, freq_arr=None, flimit=1e-6):
        norm = params['%snorm' % self.prefix].value
        slope = params['%sslope' % self.prefix].value
        lag = params['%slag' % self.prefix].value

        if freq_arr is None:
            freq_arr = np.arange(-1, 1, 1e-5)

        psd = np.zeros(freq_arr.shape)
        psd[np.abs(freq_arr) >= flimit] = norm * np.abs(freq_arr[np.abs(freq_arr) >= flimit]) ** -slope
        psd[np.abs(freq_arr) < flimit] = psd[freq_arr > flimit][0]

        integrand = psd * np.cos(2 * np.pi * tau * freq_arr + 2 * np.pi * freq_arr * lag)
        autocorr = scipy.integrate.trapz(integrand[np.isfinite(integrand)], freq_arr[np.isfinite(integrand)])

        return autocorr
//  [python]
def eval(self, params, tau, freq_arr=None, flimit=1e-6):
        norm = params['%snorm' % self.prefix].value
        slope = params['%sslope' % self.prefix].value
        lag = params['%slag' % self.prefix].value

        if freq_arr is None:
            freq_arr = np.arange(-1, 1, 1e-5)

        psd = np.zeros(freq_arr.shape)
        psd[np.abs(freq_arr) >= flimit] = norm * np.abs(freq_arr[np.abs(freq_arr) >= flimit]) ** -slope
        psd[np.abs(freq_arr) < flimit] = psd[freq_arr > flimit][0]

        integrand = psd * np.cos(2 * np.pi * tau * freq_arr + 2 * np.pi * freq_arr * lag)
        autocorr = scipy.integrate.trapezoid(integrand[np.isfinite(integrand)], freq_arr[np.isfinite(integrand)])

        return autocorr
//  [python]
def __init__(self, dust, with_dhs=False, fmax=0.8, nf=50, singlesize=False):
        if type(dust) == str:
            self.read(dust)
        else:
            self.rho = dust.rho

            self.amax = numpy.logspace(-4.,1.,60)
            self.p = numpy.linspace(2.5,4.5,11)
            self.lam = dust.lam

            self.kabs = []
            self.ksca = []
            self.kext = []
            self.albedo = []

            a = numpy.logspace(numpy.log10(0.05e-4),1.,500)
            if singlesize:
                self.amax = a
            kabsgrid = numpy.zeros((self.lam.size, a.size))
            kscagrid = numpy.zeros((self.lam.size, a.size))

            for i in range(a.size):
                if with_dhs:
                    dust.calculate_dhs_opacity(a[i], fmax=fmax, nf=nf, nang=1)
                else:
                    dust.calculate_opacity(a[i], coat_volume_fraction=0.0, \
                            nang=1)

                kabsgrid[:,i] = dust.kabs
                kscagrid[:,i] = dust.ksca

            for p in self.p:
                kabs_temp = []
                ksca_temp = []
                kext_temp = []
                albedo_temp = []

                for amax in self.amax:
                    if singlesize:
                        normfunc = numpy.zeros(a.size)
                        normfunc[a == amax] = 1.
                    else:
                        normfunc = a**(3-p)
                        normfunc[a > amax] = 0.

                    norm = scipy.integrate.trapz(normfunc, x=a)

                    kabs_temp.append(scipy.integrate.trapz(kabsgrid*normfunc,\
                            x=a, axis=1)/norm)
                    ksca_temp.append(scipy.integrate.trapz(kscagrid*normfunc,\
                            x=a, axis=1)/norm)
                    kext_temp.append(kabs_temp[-1] + ksca_temp[-1])
                    albedo_temp.append( ksca_temp[-1] / kext_temp[-1])

                self.kabs.append(kabs_temp)
                self.ksca.append(ksca_temp)
                self.kext.append(kext_temp)
                self.albedo.append(albedo_temp)

            self.kabs = numpy.array(self.kabs)
            self.ksca = numpy.array(self.ksca)
            self.kext = numpy.array(self.kext)
            self.albedo = numpy.array(self.albedo)
//  [python]
def __init__(self, dust, with_dhs=False, fmax=0.8, nf=50, singlesize=False):
        if type(dust) == str:
            self.read(dust)
        else:
            self.rho = dust.rho

            self.amax = numpy.logspace(-4.,1.,60)
            self.p = numpy.linspace(2.5,4.5,11)
            self.lam = dust.lam

            self.kabs = []
            self.ksca = []
            self.kext = []
            self.albedo = []

            a = numpy.logspace(numpy.log10(0.05e-4),1.,500)
            if singlesize:
                self.amax = a
            kabsgrid = numpy.zeros((self.lam.size, a.size))
            kscagrid = numpy.zeros((self.lam.size, a.size))

            for i in range(a.size):
                if with_dhs:
                    dust.calculate_dhs_opacity(a[i], fmax=fmax, nf=nf, nang=1)
                else:
                    dust.calculate_opacity(a[i], coat_volume_fraction=0.0, \
                            nang=1)

                kabsgrid[:,i] = dust.kabs
                kscagrid[:,i] = dust.ksca

            for p in self.p:
                kabs_temp = []
                ksca_temp = []
                kext_temp = []
                albedo_temp = []

                for amax in self.amax:
                    if singlesize:
                        normfunc = numpy.zeros(a.size)
                        normfunc[a == amax] = 1.
                    else:
                        normfunc = a**(3-p)
                        normfunc[a > amax] = 0.

                    norm = scipy.integrate.trapezoid(normfunc, x=a)

                    kabs_temp.append(scipy.integrate.trapezoid(kabsgrid*normfunc,\
                            x=a, axis=1)/norm)
                    ksca_temp.append(scipy.integrate.trapezoid(kscagrid*normfunc,\
                            x=a, axis=1)/norm)
                    kext_temp.append(kabs_temp[-1] + ksca_temp[-1])
                    albedo_temp.append( ksca_temp[-1] / kext_temp[-1])

                self.kabs.append(kabs_temp)
                self.ksca.append(ksca_temp)
                self.kext.append(kext_temp)
                self.albedo.append(albedo_temp)

            self.kabs = numpy.array(self.kabs)
            self.ksca = numpy.array(self.ksca)
            self.kext = numpy.array(self.kext)
            self.albedo = numpy.array(self.albedo)
//  [python]
def calculate_size_distribution_opacity(self, amin, amax, p):
        na = int(round(numpy.log10(amax) - numpy.log10(amin))*100+1)
        a = numpy.logspace(numpy.log10(amin),numpy.log10(amax),na)
        kabsgrid = numpy.zeros((self.lam.size,na))
        kscagrid = numpy.zeros((self.lam.size,na))
        
        normfunc = a**(3-p)

        for i in range(na):
            self.calculate_opacity(a[i])
            
            kabsgrid[:,i] = self.kabs*normfunc[i]
            kscagrid[:,i] = self.ksca*normfunc[i]
        
        norm = scipy.integrate.trapz(normfunc,x=a)
        
        self.kabs = scipy.integrate.trapz(kabsgrid,x=a)/norm
        self.ksca = scipy.integrate.trapz(kscagrid,x=a)/norm
        self.kext = self.kabs + self.ksca
        self.albedo = self.ksca / self.kext
//  [python]
def calculate_size_distribution_opacity(self, amin, amax, p):
        na = int(round(numpy.log10(amax) - numpy.log10(amin))*100+1)
        a = numpy.logspace(numpy.log10(amin),numpy.log10(amax),na)
        kabsgrid = numpy.zeros((self.lam.size,na))
        kscagrid = numpy.zeros((self.lam.size,na))
        
        normfunc = a**(3-p)

        for i in range(na):
            self.calculate_opacity(a[i])
            
            kabsgrid[:,i] = self.kabs*normfunc[i]
            kscagrid[:,i] = self.ksca*normfunc[i]
        
        norm = scipy.integrate.trapezoid(normfunc,x=a)
        
        self.kabs = scipy.integrate.trapezoid(kabsgrid,x=a)/norm
        self.ksca = scipy.integrate.trapezoid(kscagrid,x=a)/norm
        self.kext = self.kabs + self.ksca
        self.albedo = self.ksca / self.kext
//  [python]
def pdfVG(y, t,beta,theta,sigma):
    term1 = lambda z: 1.0/ (sigma*np.sqrt(2.0*np.pi*z))*np.exp(-(y-theta*z)**2.0/(2.0*sigma**2.0*z))
    term2 = lambda z: (z**(t/beta-1)*np.exp(-z/beta))/(beta**(t/beta)*stFunc.gamma(t/beta))
    z = np.linspace(0.000001,10,100)
    return integrate.trapz(term1(z)*term2(z),z)
//  [python]
def pdfVG(y, t,beta,theta,sigma):
    term1 = lambda z: 1.0/ (sigma*np.sqrt(2.0*np.pi*z))*np.exp(-(y-theta*z)**2.0/(2.0*sigma**2.0*z))
    term2 = lambda z: (z**(t/beta-1)*np.exp(-z/beta))/(beta**(t/beta)*stFunc.gamma(t/beta))
    z = np.linspace(0.000001,10,100)
    return integrate.trapezoid(term1(z)*term2(z),z)
//  [python]
def eval(self, params, tau, freq_arr=None, flimit=1e-6):
        norm = params['%snorm' % self.prefix].value
        slope = params['%sslope' % self.prefix].value
        max_lag = params['%slag' % self.prefix].value
        lag_slope = params['%slag_slope' % self.prefix].value
        lag_fcut = params['%slag_logfcut' % self.prefix].value

        if freq_arr is None:
            freq_arr = np.arange(-1, 1, 1e-5)

        psd = np.zeros(freq_arr.shape)
        lag = np.zeros(freq_arr.shape)
        psd[np.abs(freq_arr) >= flimit] = norm * np.abs(freq_arr[np.abs(freq_arr) >= flimit]) ** -slope
        psd[np.abs(freq_arr) < flimit] = psd[np.abs(freq_arr) > flimit][0]
        lag[np.abs(freq_arr) >= flimit] = max_lag * (
                    1. - 1. / (1 + np.exp(-lag_slope * (np.log10(freq_arr[np.abs(freq_arr) >= flimit]) - lag_fcut))))
        lag[np.abs(freq_arr) < flimit] = lag[np.abs(freq_arr) > flimit][0]

        integrand = psd * np.cos(2 * np.pi * tau * freq_arr + 2 * np.pi * freq_arr * lag)
        autocorr = scipy.integrate.trapz(integrand[np.isfinite(integrand)], freq_arr[np.isfinite(integrand)])

        return autocorr
//  [python]
def eval(self, params, tau, freq_arr=None, flimit=1e-6):
        norm = params['%snorm' % self.prefix].value
        slope = params['%sslope' % self.prefix].value
        max_lag = params['%slag' % self.prefix].value
        lag_slope = params['%slag_slope' % self.prefix].value
        lag_fcut = params['%slag_logfcut' % self.prefix].value

        if freq_arr is None:
            freq_arr = np.arange(-1, 1, 1e-5)

        psd = np.zeros(freq_arr.shape)
        lag = np.zeros(freq_arr.shape)
        psd[np.abs(freq_arr) >= flimit] = norm * np.abs(freq_arr[np.abs(freq_arr) >= flimit]) ** -slope
        psd[np.abs(freq_arr) < flimit] = psd[np.abs(freq_arr) > flimit][0]
        lag[np.abs(freq_arr) >= flimit] = max_lag * (
                    1. - 1. / (1 + np.exp(-lag_slope * (np.log10(freq_arr[np.abs(freq_arr) >= flimit]) - lag_fcut))))
        lag[np.abs(freq_arr) < flimit] = lag[np.abs(freq_arr) > flimit][0]

        integrand = psd * np.cos(2 * np.pi * tau * freq_arr + 2 * np.pi * freq_arr * lag)
        autocorr = scipy.integrate.trapezoid(integrand[np.isfinite(integrand)], freq_arr[np.isfinite(integrand)])

        return autocorr
//  [python]
def simulated_age_intervals(data_type, n, a, pi_age_true, sigma_true):
    # choose age intervals to measure
    age_start = np.array(mc.runiform(0, 100, n), dtype=int)
    age_start.sort()  # sort to make it easy to discard the edges when testing
    age_end = np.array(mc.runiform(age_start+1, np.minimum(age_start+10,100)), dtype=int)

    # find truth for the integral across the age intervals
    pi_interval_true = [scipy.integrate.trapz(pi_age_true[a_0i:(a_1i+1)]) / (a_1i - a_0i)
                        for a_0i, a_1i in zip(age_start, age_end)]

    # generate covariates that add explained variation
    X = mc.rnormal(0., 1.**2, size=(n,3))
    beta_true = [-.1, .1, .2]
    beta_true = [0, 0, 0]
    Y_true = np.dot(X, beta_true)

    # calculate the true value of the rate in each interval
    pi_true = pi_interval_true*np.exp(Y_true)

    # simulate the noisy measurement of the rate in each interval
    p = np.maximum(0., mc.rnormal(pi_true, 1./sigma_true**2.))

    # store the simulated data in a pandas DataFrame
    data = pd.DataFrame(dict(value=p, age_start=age_start, age_end=age_end,
                             x_0=X[:, 0], x_1=X[:, 1], x_2=X[:, 2]))
    data['effective_sample_size'] = np.maximum(p*(1-p)/sigma_true**2, 1.)

    data['standard_error'] = np.nan
    data['upper_ci'] = np.nan
    data['lower_ci'] = np.nan

    data['year_start'] = 2005.  # TODO: make these vary
    data['year_end'] = 2005.
    data['sex'] = 'total'
    data['area'] = 'all'
    data['data_type'] = data_type

    return data
//  [python]
def simulated_age_intervals(data_type, n, a, pi_age_true, sigma_true):
    # choose age intervals to measure
    age_start = np.array(mc.runiform(0, 100, n), dtype=int)
    age_start.sort()  # sort to make it easy to discard the edges when testing
    age_end = np.array(mc.runiform(age_start+1, np.minimum(age_start+10,100)), dtype=int)

    # find truth for the integral across the age intervals
    pi_interval_true = [scipy.integrate.trapezoid(pi_age_true[a_0i:(a_1i+1)]) / (a_1i - a_0i)
                        for a_0i, a_1i in zip(age_start, age_end)]

    # generate covariates that add explained variation
    X = mc.rnormal(0., 1.**2, size=(n,3))
    beta_true = [-.1, .1, .2]
    beta_true = [0, 0, 0]
    Y_true = np.dot(X, beta_true)

    # calculate the true value of the rate in each interval
    pi_true = pi_interval_true*np.exp(Y_true)

    # simulate the noisy measurement of the rate in each interval
    p = np.maximum(0., mc.rnormal(pi_true, 1./sigma_true**2.))

    # store the simulated data in a pandas DataFrame
    data = pd.DataFrame(dict(value=p, age_start=age_start, age_end=age_end,
                             x_0=X[:, 0], x_1=X[:, 1], x_2=X[:, 2]))
    data['effective_sample_size'] = np.maximum(p*(1-p)/sigma_true**2, 1.)

    data['standard_error'] = np.nan
    data['upper_ci'] = np.nan
    data['lower_ci'] = np.nan

    data['year_start'] = 2005.  # TODO: make these vary
    data['year_end'] = 2005.
    data['sex'] = 'total'
    data['area'] = 'all'
    data['data_type'] = data_type

    return data
//  [python]
n=10**3 #numero de pontos
M=np.zeros((n,2)) #uma coluna para x e outra para f(x)

x=np.linspace(0,2*np.pi,n)
y=np.sin(x)**2

A=inte.trapz(y,x)
//  [python]
n=10**3 #numero de pontos
M=np.zeros((n,2)) #uma coluna para x e outra para f(x)

x=np.linspace(0,2*np.pi,n)
y=np.sin(x)**2

A=inte.trapezoid(y,x)
//  [python]
def test_vParallelAdvection():
    npts = 32

    nconvpts = 7

    N = 100
    dt = 0.01
    c = 2.0

    l2 = np.ndarray(nconvpts)
    linf = np.ndarray(nconvpts)

    constants = get_constants('testSetups/iota0.json')

    for j in range(nconvpts):
        npts *= 2
        dt /= 2
        N *= 2
        print(npts)
        f = np.empty(npts)

        nkts = npts-2
        breaks = np.linspace(-5, 5, num=nkts)
        knots = spl.make_knots(breaks, 3, False)
        spline = spl.BSplines(knots, 3, False, True)
        x = spline.greville

        r = 4

        f = gaussLike(x)

        vParAdv = VParallelAdvection([0, 0, 0, x], spline, constants, 'null')

        for i in range(N):
            vParAdv.step(f, dt, c, r)

        fEnd = np.empty(npts)

        for i in range(npts):
            if ((x[i]-c*dt*N) < x[0]):
                # fEnd[i]=fEq(r,(x[i]-c*dt*N))
                fEnd[i] = 0
            else:
                fEnd[i] = gaussLike(x[i]-c*dt*N)

        l2[j] = np.sqrt(trapz((f-fEnd).flatten()**2, x))
        linf[j] = np.linalg.norm((f-fEnd).flatten(), np.inf)

    print("l2:", l2)
    print("linf:", linf)

    print("l2 order:", l2[:-1] / l2[1:])
    print("linf order:", linf[:-1] / linf[1:])
    l2order = np.log2(l2[:-1] / l2[1:])
    linforder = np.log2(linf[:-1] / linf[1:])
    print("l2 order:", l2order)
    print("linf order:", linforder)

    print(64, "    & & $", end=' ')
    mag2Order = np.floor(np.log10(l2[0]))
    maginfOrder = np.floor(np.log10(linf[0]))
    print(str.format('{0:.2f}', l2[0]*10**-mag2Order),
          "\\cdot 10^{", str.format('{0:n}', mag2Order), end=' ')
    print("}$ &       & $", str.format(
        '{0:.2f}', linf[0] * 10**-maginfOrder), "\\cdot 10^{", str.format('{0:n}', maginfOrder), end=' ')
    print("}$ &  \\\\")
    print("\\hline")
    for i in range(nconvpts-1):
        n = 2**(i+7)
        mag2Order = np.floor(np.log10(l2[i+1]))
        maginfOrder = np.floor(np.log10(linf[i+1]))
        print(n, "    & & $", end=' ')
        print(str.format('{0:.2f}', l2[i+1] * 10 ** - mag2Order),
              "\\cdot 10^{", str.format('{0:n}', mag2Order), end=' ')
        print("}$ & ", str.format('{0:.2f}', l2order[i]), " & $", end=' ')
        print(str.format('{0:.2f}', linf[i+1] * 10**-maginfOrder),
              "\\cdot 10^{", str.format('{0:n}', maginfOrder), end=' ')
        print("}$ & ", str.format('{0:.2f}', linforder[i]), " \\\\")
        print("\\hline")
//  [python]
def test_vParallelAdvection():
    npts = 32

    nconvpts = 7

    N = 100
    dt = 0.01
    c = 2.0

    l2 = np.ndarray(nconvpts)
    linf = np.ndarray(nconvpts)

    constants = get_constants('testSetups/iota0.json')

    for j in range(nconvpts):
        npts *= 2
        dt /= 2
        N *= 2
        print(npts)
        f = np.empty(npts)

        nkts = npts-2
        breaks = np.linspace(-5, 5, num=nkts)
        knots = spl.make_knots(breaks, 3, False)
        spline = spl.BSplines(knots, 3, False, True)
        x = spline.greville

        r = 4

        f = gaussLike(x)

        vParAdv = VParallelAdvection([0, 0, 0, x], spline, constants, 'null')

        for i in range(N):
            vParAdv.step(f, dt, c, r)

        fEnd = np.empty(npts)

        for i in range(npts):
            if ((x[i]-c*dt*N) < x[0]):
                # fEnd[i]=fEq(r,(x[i]-c*dt*N))
                fEnd[i] = 0
            else:
                fEnd[i] = gaussLike(x[i]-c*dt*N)

        l2[j] = np.sqrt(np.trapz((f-fEnd).flatten()**2, x))
        linf[j] = np.linalg.norm((f-fEnd).flatten(), np.inf)

    print("l2:", l2)
    print("linf:", linf)

    print("l2 order:", l2[:-1] / l2[1:])
    print("linf order:", linf[:-1] / linf[1:])
    l2order = np.log2(l2[:-1] / l2[1:])
    linforder = np.log2(linf[:-1] / linf[1:])
    print("l2 order:", l2order)
    print("linf order:", linforder)

    print(64, "    & & $", end=' ')
    mag2Order = np.floor(np.log10(l2[0]))
    maginfOrder = np.floor(np.log10(linf[0]))
    print(str.format('{0:.2f}', l2[0]*10**-mag2Order),
          "\\cdot 10^{", str.format('{0:n}', mag2Order), end=' ')
    print("}$ &       & $", str.format(
        '{0:.2f}', linf[0] * 10**-maginfOrder), "\\cdot 10^{", str.format('{0:n}', maginfOrder), end=' ')
    print("}$ &  \\\\")
    print("\\hline")
    for i in range(nconvpts-1):
        n = 2**(i+7)
        mag2Order = np.floor(np.log10(l2[i+1]))
        maginfOrder = np.floor(np.log10(linf[i+1]))
        print(n, "    & & $", end=' ')
        print(str.format('{0:.2f}', l2[i+1] * 10 ** - mag2Order),
              "\\cdot 10^{", str.format('{0:n}', mag2Order), end=' ')
        print("}$ & ", str.format('{0:.2f}', l2order[i]), " & $", end=' ')
        print(str.format('{0:.2f}', linf[i+1] * 10**-maginfOrder),
              "\\cdot 10^{", str.format('{0:n}', maginfOrder), end=' ')
        print("}$ & ", str.format('{0:.2f}', linforder[i]), " \\\\")
        print("\\hline")
//  [python]
def test_plot_distribute_lai_res(res, *, title=None):
    """For any LAI profile results, plot the cumulative LAI profile, analytical LAD profile at
    the LAI (interface) levels if provided, and dlai/dz at layer midpoints.
    This provides a visual check for consistency between the lai and lad profile formulations.
    """
    lai = res.lai
    dlai = lai[:-1] - lai[1:]

    lad = res.lad

    z = res.z  # increasing
    dz = np.diff(z)
    # assert np.all(dz > 0)  # assert increasing

    zm = z[:-1] + 0.5 * dz  # midpoints

    # assert np.isclose(np.sum(dlai), lai[0])

    fig, [ax1, ax2] = plt.subplots(1, 2, sharey=True)

    ax1.set_title("LAD")
    if lad is not None:
        ax1.plot(res.lad, z, ".-", label=f"from dist\ntrapz = {integrate.trapz(lad, z):.4g}")
        # note: the trapz converges to true total LAI as n increases (number of layers)
    ax1.plot(dlai / dz, zm, "s-", mfc="none", label="dlai/dz at midpts")
    ax1.legend()
    ax1.set_ylabel("$z$")

    ax2.set_title("LAI")
    ax2.plot(lai, z, ".-")

    if title is not None:
        fig.suptitle(title)

    fig.tight_layout()
//  [python]
def test_plot_distribute_lai_res(res, *, title=None):
    """For any LAI profile results, plot the cumulative LAI profile, analytical LAD profile at
    the LAI (interface) levels if provided, and dlai/dz at layer midpoints.
    This provides a visual check for consistency between the lai and lad profile formulations.
    """
    lai = res.lai
    dlai = lai[:-1] - lai[1:]

    lad = res.lad

    z = res.z  # increasing
    dz = np.diff(z)
    # assert np.all(dz > 0)  # assert increasing

    zm = z[:-1] + 0.5 * dz  # midpoints

    # assert np.isclose(np.sum(dlai), lai[0])

    fig, [ax1, ax2] = plt.subplots(1, 2, sharey=True)

    ax1.set_title("LAD")
    if lad is not None:
        ax1.plot(res.lad, z, ".-", label=f"from dist\ntrapz = {integrate.trapezoid(lad, z):.4g}")
        # note: the trapz converges to true total LAI as n increases (number of layers)
    ax1.plot(dlai / dz, zm, "s-", mfc="none", label="dlai/dz at midpts")
    ax1.legend()
    ax1.set_ylabel("$z$")

    ax2.set_title("LAI")
    ax2.plot(lai, z, ".-")

    if title is not None:
        fig.suptitle(title)

    fig.tight_layout()
//  [python]
def mainCalculation():
    #define the range for the expansion points
    N = 500
    
    # setting for the VG-BM model
    sigma = 0.12
    
    beta  = 0.2
    theta = -0.14
    T     = 1
 
    # setting for the COS method
    L = 10
    
    cF_VG = CfVG(T,beta,theta,sigma)
          
    # define the COS method integration range
    a = - L * np.sqrt(T)
    b = L * np.sqrt(T)
    
    # define domain for density
    x = np.linspace(-1,0.5,501)
            
    plt.figure(1)
    plt.grid()
    plt.xlabel("x")
    plt.ylabel("$f_X(x)$")
    
    f_X_VG = COSDensity(cF_VG,x,N,a,b)
    p = 6.0
    f_X_VG_filter = COSDensityFilter(cF_VG,x,N,a,b,p)
        
    plt.figure(1)
    plt.plot(x,f_X_VG)
    plt.plot(x,f_X_VG_filter)
    plt.legend(['VG','VG_filter'])
    plt.title('density recovery (log space)')
    print(integrate.trapz(f_X_VG,x))
    print(integrate.trapz(f_X_VG_filter,x))
    
    # exact 
    f_y=[]
    for xi in x:
        f_y.append(pdfVG(xi, T,beta,theta,sigma))
    
    plt.figure(2)
    plt.plot(x,np.log(np.abs(f_y-f_X_VG)))
    plt.plot(x,np.log(np.abs(f_y-f_X_VG_filter)))
    plt.legend(['VG','VG_filter'])
    plt.title('Error')
    plt.grid()
//  [python]
def mainCalculation():
    #define the range for the expansion points
    N = 500
    
    # setting for the VG-BM model
    sigma = 0.12
    
    beta  = 0.2
    theta = -0.14
    T     = 1
 
    # setting for the COS method
    L = 10
    
    cF_VG = CfVG(T,beta,theta,sigma)
          
    # define the COS method integration range
    a = - L * np.sqrt(T)
    b = L * np.sqrt(T)
    
    # define domain for density
    x = np.linspace(-1,0.5,501)
            
    plt.figure(1)
    plt.grid()
    plt.xlabel("x")
    plt.ylabel("$f_X(x)$")
    
    f_X_VG = COSDensity(cF_VG,x,N,a,b)
    p = 6.0
    f_X_VG_filter = COSDensityFilter(cF_VG,x,N,a,b,p)
        
    plt.figure(1)
    plt.plot(x,f_X_VG)
    plt.plot(x,f_X_VG_filter)
    plt.legend(['VG','VG_filter'])
    plt.title('density recovery (log space)')
    print(integrate.trapezoid(f_X_VG,x))
    print(integrate.trapezoid(f_X_VG_filter,x))
    
    # exact 
    f_y=[]
    for xi in x:
        f_y.append(pdfVG(xi, T,beta,theta,sigma))
    
    plt.figure(2)
    plt.plot(x,np.log(np.abs(f_y-f_X_VG)))
    plt.plot(x,np.log(np.abs(f_y-f_X_VG_filter)))
    plt.legend(['VG','VG_filter'])
    plt.title('Error')
    plt.grid()
//  [python]
def compute_aupr(self, roc):
        import scipy.integrate
        value = scipy.integrate.trapz(roc['precision'], x=roc['recall'])
        return value
//  [python]
def compute_aupr(self, roc):
        import scipy.integrate
        value = scipy.integrate.trapezoid(roc['precision'], x=roc['recall'])
        return value
//  [python]
def compute_auc(self, roc):
        """Compute AUC given a ROC data set

        :param str roc: The roc data structure must be a dictionary with "tpr"
            key. Could be an variable returned by :meth:`compute_roc`.

        """
        import scipy.integrate
        value = scipy.integrate.trapz(roc['tpr'], roc['fpr'])
        return value
//  [python]
def compute_auc(self, roc):
        """Compute AUC given a ROC data set

        :param str roc: The roc data structure must be a dictionary with "tpr"
            key. Could be an variable returned by :meth:`compute_roc`.

        """
        import scipy.integrate
        value = scipy.integrate.trapezoid(roc['tpr'], roc['fpr'])
        return value
//  [python]
def _set_alpha_beta_for_com_transformation(self, com_time, center_of_mass):
        """Set the offset and boost for center of mass drift correction

        Args:
            com_time (np.ndarray): time stamps for the center of mass data
            center_of_mass (np.ndarray): timeseries of center of mass

        """
        import sys
        if sys.version_info.major == 3 and sys.version_info.minor > 10:
            raise ImportError(
                'Unable to convert to center-of-mass corrected frame. Python version too recent to be compatible with Scri package. If you would like the ability to move to center-of-mass corrected frame, use python <= 3.10.')

        com_time = com_time + self.radius
        t_max = np.max(com_time)
        ti = 0.1 * t_max
        tf = 0.9 * t_max

        idx_min = np.argmax(com_time >= ti)
        idx_max = np.argmax(com_time >= tf)
        t_com_maya_int, com_maya_int = com_time[idx_min:idx_max + 1], center_of_mass[idx_min: idx_max + 1, :]

        x0 = np.zeros(3)
        xt0 = np.zeros(3)
        for i in range(3):
            x0[i] = scipy.integrate.trapz(com_maya_int[:, i], t_com_maya_int) / (tf - ti)
            xt0[i] = scipy.integrate.trapz(com_maya_int[:, i] * t_com_maya_int, t_com_maya_int) / (tf - ti)

        # calculate alpha and beta with the Newtonian approach
        self.__alpha = (4 * (tf ** 2 + tf * ti + ti * 2) * x0 - 6 * (tf + ti) * xt0) / (tf - ti) ** 2
        self.__beta = (12 * xt0 - 6 * (tf + ti) * x0) / (tf - ti) ** 2
//  [python]
def _set_alpha_beta_for_com_transformation(self, com_time, center_of_mass):
        """Set the offset and boost for center of mass drift correction

        Args:
            com_time (np.ndarray): time stamps for the center of mass data
            center_of_mass (np.ndarray): timeseries of center of mass

        """
        import sys
        if sys.version_info.major == 3 and sys.version_info.minor > 10:
            raise ImportError(
                'Unable to convert to center-of-mass corrected frame. Python version too recent to be compatible with Scri package. If you would like the ability to move to center-of-mass corrected frame, use python <= 3.10.')

        com_time = com_time + self.radius
        t_max = np.max(com_time)
        ti = 0.1 * t_max
        tf = 0.9 * t_max

        idx_min = np.argmax(com_time >= ti)
        idx_max = np.argmax(com_time >= tf)
        t_com_maya_int, com_maya_int = com_time[idx_min:idx_max + 1], center_of_mass[idx_min: idx_max + 1, :]

        x0 = np.zeros(3)
        xt0 = np.zeros(3)
        for i in range(3):
            x0[i] = scipy.integrate.trapezoid(com_maya_int[:, i], t_com_maya_int) / (tf - ti)
            xt0[i] = scipy.integrate.trapezoid(com_maya_int[:, i] * t_com_maya_int, t_com_maya_int) / (tf - ti)

        # calculate alpha and beta with the Newtonian approach
        self.__alpha = (4 * (tf ** 2 + tf * ti + ti * 2) * x0 - 6 * (tf + ti) * xt0) / (tf - ti) ** 2
        self.__beta = (12 * xt0 - 6 * (tf + ti) * x0) / (tf - ti) ** 2
//  [python]
def calculate_position(coeff, val, vec):
    
    N = len(val)//2
    num = mult*int(tf-ti)
    tList = np.linspace(ti, tf, num=num)
    
    def integrand(t1,t):
        
        expMat = np.exp(np.dot(np.diag((t-t1)*val),np.ones((2*N,N))), dtype=complex)
        
        gFunc = np.dot(vec[:N,:],np.multiply(expMat,coeff))
        
        #now the force
        force = np.zeros(N)
    
        #cosine driven force
        w = 1.5
        force[0] = np.cos(w*t1)
#        force[1] = np.cos(w*t1)
        
        #impulse force
#        w = 1.
#        force[0] = np.exp(-w*t1)
#        force[N-1] = -force[0]
        
        x = np.dot(gFunc,force)
        return np.real(x)
    
    q = np.zeros((num,N))

    for count, t in enumerate(tList):
        
        innerNum = mult*int(t-tList[0])
        t1List = np.linspace(0,t,num=innerNum)
        yList = np.zeros((innerNum,N))
        for t1count,t1 in enumerate(t1List):
            yList[t1count] = integrand(t1,t)
            
        for atom in range(N):
            q[count,atom] = integrate.trapz(yList[:,atom],t1List)
        
    return q,tList
//  [python]
def calculate_position(coeff, val, vec):
    
    N = len(val)//2
    num = mult*int(tf-ti)
    tList = np.linspace(ti, tf, num=num)
    
    def integrand(t1,t):
        
        expMat = np.exp(np.dot(np.diag((t-t1)*val),np.ones((2*N,N))), dtype=complex)
        
        gFunc = np.dot(vec[:N,:],np.multiply(expMat,coeff))
        
        #now the force
        force = np.zeros(N)
    
        #cosine driven force
        w = 1.5
        force[0] = np.cos(w*t1)
#        force[1] = np.cos(w*t1)
        
        #impulse force
#        w = 1.
#        force[0] = np.exp(-w*t1)
#        force[N-1] = -force[0]
        
        x = np.dot(gFunc,force)
        return np.real(x)
    
    q = np.zeros((num,N))

    for count, t in enumerate(tList):
        
        innerNum = mult*int(t-tList[0])
        t1List = np.linspace(0,t,num=innerNum)
        yList = np.zeros((innerNum,N))
        for t1count,t1 in enumerate(t1List):
            yList[t1count] = integrand(t1,t)
            
        for atom in range(N):
            q[count,atom] = integrate.trapezoid(yList[:,atom],t1List)
        
    return q,tList
//  [python]
def __init__(self, wavelength, transmit, name=""):
        """Constructor"""
        self.name = name
        self.wavelength = wavelength
        self.transmit = transmit
        self.norm = trapz(transmit, wavelength)
        self.lT = trapz(wavelength * transmit, wavelength)
        self.lpivot = numpy.sqrt(self.lT / trapz(transmit / wavelength, wavelength))
        self.cl = self.lT / self.norm
//  [python]
def __init__(self, wavelength, transmit, name=""):
        """Constructor"""
        self.name = name
        self.wavelength = wavelength
        self.transmit = transmit
        self.norm = trapezoid(transmit, wavelength)
        self.lT = trapezoid(wavelength * transmit, wavelength)
        self.lpivot = numpy.sqrt(self.lT / trapezoid(transmit / wavelength, wavelength))
        self.cl = self.lT / self.norm
//  [python]
def corr_1h_auto_matter_fnc(self):
        """A callable returning the halo model 1-halo DM auto-correlation function."""
        if self.halo_profile.has_lam:
            lam = self.halo_profile_lam
            integrand = self.dndm * self.m ** 3 * lam

            table = (
                intg.trapz(integrand, dx=np.log(10) * self.dlog10m)
                / self.mean_density0 ** 2
                - 1
            )
        else:
            table = tools.hankel_transform(
                self.power_1h_auto_matter_fnc, self._r_table, "r"
            )

        return tools.ExtendedSpline(
            self._r_table,
            table,
            lower_func="power_law",
            upper_func=lambda x: np.zeros_like(x),
        )
//  [python]
def corr_1h_auto_matter_fnc(self):
        """A callable returning the halo model 1-halo DM auto-correlation function."""
        if self.halo_profile.has_lam:
            lam = self.halo_profile_lam
            integrand = self.dndm * self.m ** 3 * lam

            table = (
                intg.trapezoid(integrand, dx=np.log(10) * self.dlog10m)
                / self.mean_density0 ** 2
                - 1
            )
        else:
            table = tools.hankel_transform(
                self.power_1h_auto_matter_fnc, self._r_table, "r"
            )

        return tools.ExtendedSpline(
            self._r_table,
            table,
            lower_func="power_law",
            upper_func=lambda x: np.zeros_like(x),
        )
//  [python]
def ion(self):
		"""
	Calculates the rate of ionizing photons in the SED.
	
	>>> q=s.ion()
		"""
		import scipy.integrate
		import scipy.stats
		h=6.62607e-27	# Planck constant in CGS
		
		# Performs interpolation before integrating. This is a precaution in 
		# case the user specify weird integration limits.			
		if not hasattr(self, 'nlnui'): self.interp()
		
		# 13.6 eV - "infty"
		xi, xf = 15.52, 22.
		
		# Gets only the elements corresponding to ionizing frequencies
		i=numpy.where((self.lognui>=xi) & (self.lognui<=xf))
		x,y = self.lognui[i],self.lli[i]	# easier notation
		
		# Calculates ionizing rate using integration (trapezoidal rule)
		q=scipy.integrate.trapz(self.nlnui[i]/self.nui[i]/(h*self.nui[i]), self.nui[i])

		return q
//  [python]
def ion(self):
		"""
	Calculates the rate of ionizing photons in the SED.
	
	>>> q=s.ion()
		"""
		import scipy.integrate
		import scipy.stats
		h=6.62607e-27	# Planck constant in CGS
		
		# Performs interpolation before integrating. This is a precaution in 
		# case the user specify weird integration limits.			
		if not hasattr(self, 'nlnui'): self.interp()
		
		# 13.6 eV - "infty"
		xi, xf = 15.52, 22.
		
		# Gets only the elements corresponding to ionizing frequencies
		i=numpy.where((self.lognui>=xi) & (self.lognui<=xf))
		x,y = self.lognui[i],self.lli[i]	# easier notation
		
		# Calculates ionizing rate using integration (trapezoidal rule)
		q=scipy.integrate.trapezoid(self.nlnui[i]/self.nui[i]/(h*self.nui[i]), self.nui[i])

		return q
//  [python]
def xrays(self):
		"""
	Calculates the photon index of the X-ray spectrum and Lx (2-10 keV). 
	Stores the new attributes gammax and lumx in the object.
	
	>>> Lx,gamma=s.xrays()

	creates the new attributes s.lumx and s.gammax
		"""
		import scipy.integrate
		import scipy.stats
		
		# Performs interpolation before integrating. This is a precaution in 
		# case the user specify weird integration limits.			
		if not hasattr(self, 'nlnui'): self.interp()
		
		# 2-10 keV in log(nu)
		xi, xf = 17.684, 18.384
		
		# Gets only the elements in the range 2-10 keV
		i=numpy.where((self.lognui>=xi) & (self.lognui<=xf))
		x,y = self.lognui[i],self.lli[i]	# easier notation
		
		# Calculates Lx using integration (trapezoidal rule)
		self.lumx=scipy.integrate.trapz(self.nlnui[i]/self.nui[i], self.nui[i])

		# Linear fit to the SED in the interval 2-10 keV, y=ax+b
		a, b, r, p, err = scipy.stats.linregress(x,y)
		
		# Calculates Gamma_X (photon index)
		self.gammax=2-a

		return self.lumx, self.gammax
//  [python]
def xrays(self):
		"""
	Calculates the photon index of the X-ray spectrum and Lx (2-10 keV). 
	Stores the new attributes gammax and lumx in the object.
	
	>>> Lx,gamma=s.xrays()

	creates the new attributes s.lumx and s.gammax
		"""
		import scipy.integrate
		import scipy.stats
		
		# Performs interpolation before integrating. This is a precaution in 
		# case the user specify weird integration limits.			
		if not hasattr(self, 'nlnui'): self.interp()
		
		# 2-10 keV in log(nu)
		xi, xf = 17.684, 18.384
		
		# Gets only the elements in the range 2-10 keV
		i=numpy.where((self.lognui>=xi) & (self.lognui<=xf))
		x,y = self.lognui[i],self.lli[i]	# easier notation
		
		# Calculates Lx using integration (trapezoidal rule)
		self.lumx=scipy.integrate.trapezoid(self.nlnui[i]/self.nui[i], self.nui[i])

		# Linear fit to the SED in the interval 2-10 keV, y=ax+b
		a, b, r, p, err = scipy.stats.linregress(x,y)
		
		# Calculates Gamma_X (photon index)
		self.gammax=2-a

		return self.lumx, self.gammax
//  [python]
def bol(self, lognu0=None, lognu1=None, xrange=[8,22]):
		"""
	Calculates the bolometric luminosity of the SED. Performs the integration 
	using the trapezoidal rule. Adds the attribute lumbol to the object with
	the result.
	
	>>> s.bol()

	makes the variable s.lumbol hold the bolometric luminosity.
	
	>>> s.bol(17, 20)

	makes s.lumbol hold the luminosity integrated in the range 1e17-1e20 Hz.

	>>> s.bol(18, 20, [s.lognu[0],s.lognu[-1]])

	gives the integrated luminosity in the range 1e18-1e20 Hz. Before integrating,
	interpolates the SED over its original frequency range with 1000 points.

		"""
		import scipy.integrate

		# Performs interpolation before integrating. This is a precaution in 
		# case the user specifies weird integration limits.	In addition, I 
		# found out that integrating certain sparse SEDs (e.g. qsos) without
		# interpolating induces incorrect Lbol estimates		
		if not hasattr(self, 'nlnui'): self.interp(xrange=xrange)			
		
		# If no arguments are given to the method, integrates the entire SED
		if lognu0==None and lognu1==None:
			lumbol=scipy.integrate.trapz(self.nlnui/self.nui, self.nui)
		else:
			# Gets only the elements in the given range
			i=numpy.where((self.lognui>=lognu0) & (self.lognui<=lognu1))
			
			# Integration
			lumbol=scipy.integrate.trapz(self.nlnui[i]/self.nui[i], self.nui[i])

		self.lumbol=lumbol

		return lumbol
//  [python]
def bol(self, lognu0=None, lognu1=None, xrange=[8,22]):
		"""
	Calculates the bolometric luminosity of the SED. Performs the integration 
	using the trapezoidal rule. Adds the attribute lumbol to the object with
	the result.
	
	>>> s.bol()

	makes the variable s.lumbol hold the bolometric luminosity.
	
	>>> s.bol(17, 20)

	makes s.lumbol hold the luminosity integrated in the range 1e17-1e20 Hz.

	>>> s.bol(18, 20, [s.lognu[0],s.lognu[-1]])

	gives the integrated luminosity in the range 1e18-1e20 Hz. Before integrating,
	interpolates the SED over its original frequency range with 1000 points.

		"""
		import scipy.integrate

		# Performs interpolation before integrating. This is a precaution in 
		# case the user specifies weird integration limits.	In addition, I 
		# found out that integrating certain sparse SEDs (e.g. qsos) without
		# interpolating induces incorrect Lbol estimates		
		if not hasattr(self, 'nlnui'): self.interp(xrange=xrange)			
		
		# If no arguments are given to the method, integrates the entire SED
		if lognu0==None and lognu1==None:
			lumbol=scipy.integrate.trapezoid(self.nlnui/self.nui, self.nui)
		else:
			# Gets only the elements in the given range
			i=numpy.where((self.lognui>=lognu0) & (self.lognui<=lognu1))
			
			# Integration
			lumbol=scipy.integrate.trapezoid(self.nlnui[i]/self.nui[i], self.nui[i])

		self.lumbol=lumbol

		return lumbol
//  [python]
def extractPhotometry(lamb, spec, flist, absFlux=True):
    """Extract seds from a one single spectrum

    Parameters
    ----------
    lamb: ndarray[float,ndim=1]
        wavelength of spec

    spec: ndarray[float, ndim=1]
        spectrum

    flist: list[filter]
        list of filter objects

    absflux: bool
        return SEDs in absolute fluxes if set

    Returns
    -------
    cls: ndarray[float, ndim=1]
        filters central wavelength

    seds: ndarray[float, ndim=1]
        integrated sed
    """
    cls = numpy.empty(len(flist), dtype=float)
    seds = numpy.empty(len(flist), dtype=float)
    for e, k in enumerate(flist):
        xl = k.transmit > 0.0
        tmp = lamb[xl] * k.transmit[xl]
        s0 = spec[:, xl]
        # apply absolute flux conversion if requested
        if absFlux:
            s0 /= distc
        a = trapz(tmp[None, :] * s0, lamb[xl], axis=1)
        seds[e] = a / k.lT  # divide by integral (lambda T dlambda)
        cls[e] = k.cl

    return cls, seds
//  [python]
def extractPhotometry(lamb, spec, flist, absFlux=True):
    """Extract seds from a one single spectrum

    Parameters
    ----------
    lamb: ndarray[float,ndim=1]
        wavelength of spec

    spec: ndarray[float, ndim=1]
        spectrum

    flist: list[filter]
        list of filter objects

    absflux: bool
        return SEDs in absolute fluxes if set

    Returns
    -------
    cls: ndarray[float, ndim=1]
        filters central wavelength

    seds: ndarray[float, ndim=1]
        integrated sed
    """
    cls = numpy.empty(len(flist), dtype=float)
    seds = numpy.empty(len(flist), dtype=float)
    for e, k in enumerate(flist):
        xl = k.transmit > 0.0
        tmp = lamb[xl] * k.transmit[xl]
        s0 = spec[:, xl]
        # apply absolute flux conversion if requested
        if absFlux:
            s0 /= distc
        a = numpy.trapz(tmp[None, :] * s0, lamb[xl], axis=1)
        seds[e] = a / k.lT  # divide by integral (lambda T dlambda)
        cls[e] = k.cl

    return cls, seds
//  [python]
def extractSEDs(g0, flist, absFlux=True):
    """ Extract seds from a grid

    Parameters
    ----------
    g0: ModelGrid instance
        initial spectral grid

    flist: sequence(filter)
        list of filter object instances

    absflux: bool
        return SEDs in absolute fluxes if set

    Returns
    -------
    cls: ndarray[float, ndim=1]
        filters central wavelength

    seds: ndarray[float, ndim=1]
        integrated sed

    grid: Table
        SED grid properties table from g0 (g0.grid)
    """
    lamb = g0.lamb
    seds = numpy.empty((len(g0.grid), len(flist)), dtype=float)
    cls = numpy.empty(len(flist), dtype=float)
    for e, k in enumerate(flist):
        xl = k.transmit > 0.0
        tmp = lamb[xl] * k.transmit[xl]
        s0 = g0.seds[:, xl]
        # apply absolute flux conversion if requested
        if absFlux:
            s0 /= distc
        a = trapz(tmp[None, :] * s0, lamb[xl], axis=1)
        seds[:, e] = a / k.lT
        cls[e] = k.cl

    return cls, seds, g0.grid
//  [python]
def extractSEDs(g0, flist, absFlux=True):
    """ Extract seds from a grid

    Parameters
    ----------
    g0: ModelGrid instance
        initial spectral grid

    flist: sequence(filter)
        list of filter object instances

    absflux: bool
        return SEDs in absolute fluxes if set

    Returns
    -------
    cls: ndarray[float, ndim=1]
        filters central wavelength

    seds: ndarray[float, ndim=1]
        integrated sed

    grid: Table
        SED grid properties table from g0 (g0.grid)
    """
    lamb = g0.lamb
    seds = numpy.empty((len(g0.grid), len(flist)), dtype=float)
    cls = numpy.empty(len(flist), dtype=float)
    for e, k in enumerate(flist):
        xl = k.transmit > 0.0
        tmp = lamb[xl] * k.transmit[xl]
        s0 = g0.seds[:, xl]
        # apply absolute flux conversion if requested
        if absFlux:
            s0 /= distc
        a = trapezoid(tmp[None, :] * s0, lamb[xl], axis=1)
        seds[:, e] = a / k.lT
        cls[e] = k.cl

    return cls, seds, g0.grid
//  [python]
def period_block_areas(self):
        on_period_blocks, off_period_blocks = self.period_blocks()
        on_block_areas = np.array([scipy.integrate.trapz(block[1], x=block[0]) for block in on_period_blocks])
        off_block_areas = np.array([scipy.integrate.trapz(block[1], x=block[0]) for block in off_period_blocks])
        return on_block_areas, off_block_areas
//  [python]
def period_block_areas(self):
        on_period_blocks, off_period_blocks = self.period_blocks()
        on_block_areas = np.array([scipy.integrate.trapezoid(block[1], x=block[0]) for block in on_period_blocks])
        off_block_areas = np.array([scipy.integrate.trapezoid(block[1], x=block[0]) for block in off_period_blocks])
        return on_block_areas, off_block_areas
//  [python]
def period_area(self):
        period_region = self._sinwave > (np.max(self._sinwave) / 2)

        on_period_area = integrate.trapz(self.values[period_region], self.times[period_region])
        off_period_area = integrate.trapz(self.values[~period_region], self.times[~period_region])

        return on_period_area, off_period_area
//  [python]
def period_area(self):
        period_region = self._sinwave > (np.max(self._sinwave) / 2)

        on_period_area = integrate.trapezoid(self.values[period_region], self.times[period_region])
        off_period_area = integrate.trapezoid(self.values[~period_region], self.times[~period_region])

        return on_period_area, off_period_area
//  [python]
def trapezoid(dataset, **kwargs):
    """
    Integrate using the composite trapezoidal rule.

    Wrapper of `scpy.integrate.trapezoid`\ .

    Performs the integration along the last or given dimension.

    Parameters
    ----------
    dataset : `NDDataset`
        Dataset to be integrated.
    **kwargs
        Additional keywords parameters. See Other Parameters.

    Returns
    -------
    `~spectrochempy.core.dataset.ndataset.NDDataset`
        Definite integral as approximated by trapezoidal rule.

    Other Parameters
    ----------------
    dim : `int` or `str`, optional, default: ``"x"``
        Dimension along which to integrate.
        If an integer is provided, it is equivalent to the numpy axis
        parameter for `~numpy.ndarray`\ s.

    See Also
    --------
    trapz : An alias of `trapezoid`.
    simpson : Integrate using the composite simpson rule.

    Example
    -------
    >>> dataset = scp.read('irdata/nh4y-activation.spg')
    >>> dataset[:,1250.:1800.].trapz()
    NDDataset: [float64] a.u..cm^-1 (size: 55)
    """

    return scipy.integrate.trapz(dataset, **kwargs)
//  [python]
def trapezoid(dataset, **kwargs):
    """
    Integrate using the composite trapezoidal rule.

    Wrapper of `scpy.integrate.trapezoid`\ .

    Performs the integration along the last or given dimension.

    Parameters
    ----------
    dataset : `NDDataset`
        Dataset to be integrated.
    **kwargs
        Additional keywords parameters. See Other Parameters.

    Returns
    -------
    `~spectrochempy.core.dataset.ndataset.NDDataset`
        Definite integral as approximated by trapezoidal rule.

    Other Parameters
    ----------------
    dim : `int` or `str`, optional, default: ``"x"``
        Dimension along which to integrate.
        If an integer is provided, it is equivalent to the numpy axis
        parameter for `~numpy.ndarray`\ s.

    See Also
    --------
    trapz : An alias of `trapezoid`.
    simpson : Integrate using the composite simpson rule.

    Example
    -------
    >>> dataset = scp.read('irdata/nh4y-activation.spg')
    >>> dataset[:,1250.:1800.].trapz()
    NDDataset: [float64] a.u..cm^-1 (size: 55)
    """

    return scipy.integrate.trapezoid(dataset, **kwargs)