Example #1
0
    def evaluate(
        self,
        in_x,
        scale,
        alpha,
        sil1_amp,
        sil1_center,
        sil1_fwhm,
        sil1_asym,
        sil2_amp,
        sil2_center,
        sil2_fwhm,
        sil2_asym,
        csil_amp,
        csil_center,
        csil_fwhm,
        csil_asym,
    ):
        """
        G21 function

        Parameters
        ----------
        in_x: float
           expects either x in units of wavelengths or frequency
           or assumes wavelengths in wavenumbers [1/micron]

        Returns
        -------
        axav: np array (float)
            A(x)/A(V) extinction curve [mag]

        Raises
        ------
        ValueError
           Input x values outside of defined range
        """
        x = _get_x_in_wavenumbers(in_x)

        # check that the wavenumbers are within the defined range
        _test_valid_x_range(x, self.x_range, "G21")

        # powerlaw
        axav = scale * ((1.0 / x)**(-1.0 * alpha))

        # silicate feature drudes
        wave = 1 / x
        axav += drude_asym(wave, sil1_amp, sil1_center, sil1_fwhm, sil1_asym)
        axav += drude_asym(wave, sil2_amp, sil2_center, sil2_fwhm, sil2_asym)
        axav += drude_asym(wave, csil_amp, csil_center, csil_fwhm, csil_asym)

        return axav
Example #2
0
    def evaluate(self, in_x):
        """
        G03_SMCBar_WD01_extension function

        Parameters
        ----------
        in_x: float
           expects either x in units of wavelengths or frequency
           or assumes wavelengths in wavenumbers [1/micron]

           internally wavenumbers are used

        Returns
        -------
        axav: np array (float)
            A(x)/A(V) extinction curve [mag]

        Raises
        ------
        ValueError
           Input x values outside of defined range
        """
        # convert to wavenumbers (1/micron) if x input in units
        # otherwise, assume x in appropriate wavenumber units
        x = _get_x_in_wavenumbers(in_x)

        # check that the wavenumbers are within the defined range
        _test_valid_x_range(x, self.x_range, self.__class__.__name__)

        # compute the dust grain model
        dmodel = WD01(modelname="SMCBar")
        dmod = dmodel(in_x)

        # compute the F19 curve for the input Rv over the F19 defined wavelength range
        gvals_g03 = (x > super().x_range[0]) & (x < super().x_range[1])
        fmod = super().evaluate(in_x[gvals_g03])

        # now merge the two smoothly
        outmod = copy.copy(dmod)
        outmod[gvals_g03] = fmod

        merge_range = np.array([1.0 / 0.1675, super().x_range[1]])
        gvals_merge = (x > merge_range[0]) & (x < merge_range[1])
        # have weights be zero at the min merge and 1 at the max merge
        weights = (x[gvals_merge] - merge_range[0]) / (merge_range[1] - merge_range[0])
        outmod[gvals_merge] = (1.0 - weights) * outmod[gvals_merge] + weights * dmod[
            gvals_merge
        ]

        return outmod
Example #3
0
    def evaluate(self, in_x, Rv):
        """
        F19_D03_extension function

        Parameters
        ----------
        in_x: float
           expects either x in units of wavelengths or frequency
           or assumes wavelengths in wavenumbers [1/micron]

           internally wavenumbers are used

        Returns
        -------
        axav: np array (float)
            A(x)/A(V) extinction curve [mag]

        Raises
        ------
        ValueError
           Input x values outside of defined range
        """
        # convert to wavenumbers (1/micron) if x input in units
        # otherwise, assume x in appropriate wavenumber units
        x = _get_x_in_wavenumbers(in_x)

        # check that the wavenumbers are within the defined range
        _test_valid_x_range(x, self.x_range, self.__class__.__name__)

        # just in case someone calls evaluate explicitly
        Rv = np.atleast_1d(Rv)

        # ensure Rv is a single element, not numpy array
        Rv = Rv[0]

        # determine the dust grain models to use for the input Rv
        if Rv < 4.0:
            d1rv = 3.1
            d2rv = 4.0
            d1mod = D03(modelname="MWRV31")
            d2mod = D03(modelname="MWRV40")
        else:
            d1rv = 4.0
            d2rv = 5.5
            d1mod = D03(modelname="MWRV40")
            d2mod = D03(modelname="MWRV55")

        # interpolate to get the model extinction for the input Rv value
        dslope = (d2mod(in_x) - d1mod(in_x)) / (d2rv - d1rv)
        dmod = d1mod(in_x) + dslope * (Rv - d1rv)

        # compute the F19 curve for the input Rv over the F19 defined wavelength range
        gvals_f19 = (x > super().x_range[0]) & (x < super().x_range[1])
        fmod = super().evaluate(in_x[gvals_f19], Rv)

        # now merge the two smoothly
        outmod = copy.copy(dmod)
        outmod[gvals_f19] = fmod

        merge_range = np.array([1.0 / 0.1675, super().x_range[1]])
        gvals_merge = (x > merge_range[0]) & (x < merge_range[1])
        # have weights be zero at the min merge and 1 at the max merge
        weights = (x[gvals_merge] - merge_range[0]) / (merge_range[1] - merge_range[0])
        outmod[gvals_merge] = (1.0 - weights) * outmod[gvals_merge] + weights * dmod[
            gvals_merge
        ]

        return outmod
Example #4
0
    def evaluate(
        self,
        in_x,
        BKG_amp,
        BKG_lambda,
        BKG_width,
        FUV_amp,
        FUV_lambda,
        FUV_b,
        FUV_n,
        NUV_amp,
        NUV_lambda,
        NUV_width,
        SIL1_amp,
        SIL1_lambda,
        SIL1_width,
        SIL2_amp,
        SIL2_lambda,
        SIL2_width,
        FIR_amp,
        FIR_lambda,
        FIR_width,
    ):
        """
        P92 function

        Parameters
        ----------
        in_x: float
           expects either x in units of wavelengths or frequency
           or assumes wavelengths in wavenumbers [1/micron]

           internally wavenumbers are used

        Returns
        -------
        axav: np array (float)
            A(x)/A(V) extinction curve [mag]

        Raises
        ------
        ValueError
           Input x values outside of defined range
        """
        x = _get_x_in_wavenumbers(in_x)

        # check that the wavenumbers are within the defined range
        _test_valid_x_range(x, self.x_range, "P92_mod")

        # compute b from lambda and width
        BKG_b = np.power((BKG_width / BKG_lambda), 2.0) - 2.0
        NUV_b = np.power((NUV_width / NUV_lambda), 2.0) - 2.0
        SIL1_b = np.power((SIL1_width / SIL1_lambda), 2.0) - 2.0
        SIL2_b = np.power((SIL2_width / SIL2_lambda), 2.0) - 2.0
        FIR_b = np.power((FIR_width / FIR_lambda), 2.0) - 2.0

        # calculate the terms
        lam = 1.0 / x
        axav = (
            self._p92_single_term(lam, BKG_amp, BKG_lambda, BKG_b, 2.0) +
            self._p92_single_term(lam, FUV_amp, FUV_lambda, FUV_b, FUV_n) +
            self._p92_single_term(lam, NUV_amp, NUV_lambda, NUV_b, 2.0) +
            self._p92_single_term(lam, SIL1_amp, SIL1_lambda, SIL1_b, 2.0) +
            self._p92_single_term(lam, SIL2_amp, SIL2_lambda, SIL2_b, 2.0) +
            self._p92_single_term(lam, FIR_amp, FIR_lambda, FIR_b, 2.0))

        # return A(x)/A(V)
        return axav