Esempio n. 1
0
    def convert_points_mev(self, energies_mev, dnde_mev):

        # (a) convert to acutal units. gtlike spectra take energy in MeV, return flux in ph/cm^2/s/MeV
        return self.convert_points(
            units.tosympy(energies_mev, units.MeV),
            units.tosympy(dnde_mev,
                          units.ph / units.cm**2 / units.s / units.MeV))
Esempio n. 2
0
 def get_dnde_error(spectrum, covariance_matrix, energies):
     """ assume energies has energy units and return flux in flux units. """
     energies = units.tonumpy(energies, units.MeV)
     dnde_error = SpectrumPlotter.get_dnde_error_mev(
         spectrum, covariance_matrix, energies)
     return units.tosympy(dnde_error,
                          units.ph / units.cm**2 / units.s / units.MeV)
Esempio n. 3
0
    def plot(self, filename=None, axes=None, title=None,
             fignum=None, figsize=(4,4), **kwargs):
        """ Plot the upper limit. """

        spectral_kwargs=dict(color='red',zorder=1.9)
        spectral_kwargs.update(kwargs)

        file_energy_units = units.fromstring(self.results['energy_units'])
        emin = self.results['emin']*file_energy_units
        emax = self.results['emax']*file_energy_units
        if axes is None:
            fig = P.figure(fignum,figsize)
            axes = SpectralAxes(fig=fig, 
                                rect=(0.22,0.15,0.75,0.8),
                                flux_units=self.flux_units,
                                energy_units=self.energy_units)
            fig.add_axes(axes)
            axes.set_xlim_units(emin,emax)

        # plot the spectral model
        spectrum = self.results['spectrum']
        sp=SpectrumPlotter(axes=axes)
        sp.plot(spectrum, emin=emin, emax=emax, **spectral_kwargs)

        # plot in the middle an arrow pointing down
        e_middle = units.tosympy([np.sqrt(self.results['emin']*self.results['emax'])],file_energy_units)
        dnde = sp.get_dnde(spectrum, e_middle)
        energies, e2_dnde = axes.convert_points(e_middle, dnde)
        if 'autoscale' in spectral_kwargs: spectral_kwargs.pop('autoscale')
        if 'label' in spectral_kwargs: spectral_kwargs.pop('label')
        plot_points(x=energies, y=e2_dnde,
                    xlo=None, xhi=None,
                    y_lower_err=None, y_upper_err=None,
                    y_ul=e2_dnde,
                    significant=False,
                    axes=axes, **spectral_kwargs)

        if title is not None: axes.set_title(title)
        if filename is not None: 
            P.savefig(expandvars(filename))
        return axes
Esempio n. 4
0
 def get_dnde_error(spectrum,covariance_matrix,energies):
     """ assume energies has energy units and return flux in flux units. """
     energies=units.tonumpy(energies,units.MeV)
     dnde_error=SpectrumPlotter.get_dnde_error_mev(spectrum,covariance_matrix,energies)
     return units.tosympy(dnde_error,units.ph/units.cm**2/units.s/units.MeV)
Esempio n. 5
0
 def get_dnde(spectrum,energies):
     """ assume energies has energy units and return flux in flux units. """
     energies=units.tonumpy(energies,units.MeV)
     dnde=SpectrumPlotter.get_dnde_mev(spectrum,energies)
     return units.tosympy(dnde,units.ph/units.cm**2/units.s/units.MeV)
Esempio n. 6
0
    def convert_points_mev(self, energies_mev, dnde_mev):

        # (a) convert to acutal units. gtlike spectra take energy in MeV, return flux in ph/cm^2/s/MeV
        return self.convert_points(units.tosympy(energies_mev,units.MeV),
                                   units.tosympy(dnde_mev,units.ph/units.cm**2/units.s/units.MeV))
Esempio n. 7
0
    def __load__(self, sed_file):
        """ Parse a HESS-style plain text SED file.
            Note, there is no real consistency to
            these files, so just try many
            examples. """

        lines = open(expandvars(sed_file)).readlines()

        # strip whitespace + newline characters
        lines = [line.strip() for line in lines]

        # remove blank lines + comments
        lines = [line for line in lines if line is not '' and line[0] != '#' ]

        # easier to parse '/TeV/cm^2/s' than '/TeV cm^2 s'
        lines = [line.replace('[/TeV cm^2 s]','[/TeV/cm^2/s]') for line in lines]

        # split on empty spaces
        lines = [ line.split() for line in lines ]

        energy_units='[TeV]'
        flux_units='[/TeV/cm^2/s]'

        header = lines[0]
        units_line = lines[1]

        for u in units_line:
            if u not in [energy_units, flux_units]:
                raise Exception("%s is an unrecognized unit" % u)

        # get all the data lines
        data = lines[2:]
        
        # convert to float + transpose rows + convert to numpy
        data = [ map(float,i) for i in data]
        data = zip(*data)
        data = [np.asarray(i,dtype=float) for i in data]

        if header == ['Energy','Flux','Flux','Error_low','Flux','Error_high']:
            # This is like SEDs from the galactic plane survey
            #  * http://www.mpi-hd.mpg.de/hfm/HESS/pages/publications/auxiliary/ApJ_636.html

            self.energy, self.dnde, dnde_lower, dnde_upper = data
            self.dnde_err = (dnde_lower + dnde_upper)/2

            # lines are energy, flux, flux_lower, flux_upper

        elif header == ['Energy','interval','Mean','energy','Flux','Flux','Error']:
            # This is like the SED for HESS J1303-631
            #  * http://www.mpi-hd.mpg.de/hfm/HESS/pages/publications/auxiliary/AA439_1013.html
            print 'data',data

            self.lower_energy, self.upper_energy, self.energy, self.dnde, self.dnde_err = data

        elif header == ['Mean','energy','Flux','Flux','Error']:
            # This is like the SED for Vela X
            #  * http://www.mpi-hd.mpg.de/hfm/HESS/pages/publications/auxiliary/VelaX_auxinfo.html

            self.energy, self.dnde, self.dnde_err = data

        elif header == ['Energy','interval','Mean','energy','Flux','Flux','Error']:
            # This is like the SED for MSH 15-52
            #  * http://www.mpi-hd.mpg.de/hfm/HESS/pages/publications/auxiliary/AA435_L17.html
            self.lower_energy, self.upper_energy, self.dnde, self.dnde_err = data

        elif header == ['Mean','energy','Flux','Flux','Error','(','-','/','+',')']:
            # This is like the SED for the Kookaburra
            #  * http://www.mpi-hd.mpg.de/hfm/HESS/pages/publications/auxiliary/kookaburra_auxinfo.html
            raise Exception("not implemented")

        if self.energy is None:
            self.energy = np.sqrt(self.lower_energy*self.upper_energy)
        if self.lower_energy is None or self.upper_energy is None:
            # if only energy is given, assume no range in energy
            self.lower_energy = self.energy
            self.upper_energy = self.energy

        self.significant = np.ones_like(self.energy).astype(bool)

        def estimate_flux(dnde,energy,emin,emax, e_weight):
            """ estimate the emin to emax flux for a source with prefactor
                dnde at the given energy. assuming the source has a
                spectral index of 2. 
                
                Note, for our situation dnde has units [ph/cm^2/s/TeV]
                and energy has units [TeV], but the ouptut of the
                i_flux function is correct. If e_weight=0,
                the return has units [ph/cm^2/s]. If e_weight=1,
                the return has units [TeV/cm^2/s]. """
            model = PowerLaw(index=2, norm=dnde, e0=energy)
            return model.i_flux(emin=emin, emax=emax, e_weight=e_weight)

        estimate_flux = np.vectorize(estimate_flux)

        self.flux = estimate_flux(self.dnde, self.energy, self.lower_energy, self.upper_energy, 0)
        self.eflux = estimate_flux(self.dnde, self.energy, self.lower_energy, self.upper_energy, 1)

        # Note, we can use this shortcut to comptue the errors,
        # But ONLY because the function flux(dnde) is linear in dnde and dnde is the only
        # parameter with an error: flux=dnde*f(gamma,e0) so flux_err=dnde_err*f(gamma,e0)
        self.flux_err = estimate_flux(self.dnde_err, self.energy, self.lower_energy, self.upper_energy, 0)
        self.eflux_err = estimate_flux(self.dnde_err, self.energy, self.lower_energy, self.upper_energy, 1)


        # no upper limits
        self.dnde_ul=np.nan*self.dnde
        self.flux_ul=np.nan*self.flux
        self.eflux_ul=np.nan*self.eflux

        for values, u in [
            [['lower_energy', 'upper_energy', 'energy'], units.TeV],
            [['dnde', 'dnde_err', 'dnde_ul'], units.ph/units.cm**2/units.s/units.TeV],
            [['flux', 'flux_err', 'flux_ul'], units.ph/units.cm**2/units.s],
            [['eflux','eflux_err', 'eflux_ul'], units.TeV/units.cm**2/units.s]]:

            for v in values:
                self.__dict__[v] = units.tosympy(self.__dict__[v], u)

        # all hess points are significant (as far as I can tell)
        self.significant = np.ones(len(self.energy),dtype=bool)
        print 'en',self.energy
        print 'sig',self.significant 
Esempio n. 8
0
 def get_dnde(spectrum, energies):
     """ assume energies has energy units and return flux in flux units. """
     energies = units.tonumpy(energies, units.MeV)
     dnde = SpectrumPlotter.get_dnde_mev(spectrum, energies)
     return units.tosympy(dnde,
                          units.ph / units.cm**2 / units.s / units.MeV)
Esempio n. 9
0
    def __load__(self, sed_file):
        """ Parse a HESS-style plain text SED file.
            Note, there is no real consistency to
            these files, so just try many
            examples. """

        lines = open(expandvars(sed_file)).readlines()

        # strip whitespace + newline characters
        lines = [line.strip() for line in lines]

        # remove blank lines + comments
        lines = [line for line in lines if line is not '' and line[0] != '#']

        # easier to parse '/TeV/cm^2/s' than '/TeV cm^2 s'
        lines = [
            line.replace('[/TeV cm^2 s]', '[/TeV/cm^2/s]') for line in lines
        ]

        # split on empty spaces
        lines = [line.split() for line in lines]

        energy_units = '[TeV]'
        flux_units = '[/TeV/cm^2/s]'

        header = lines[0]
        units_line = lines[1]

        for u in units_line:
            if u not in [energy_units, flux_units]:
                raise Exception("%s is an unrecognized unit" % u)

        # get all the data lines
        data = lines[2:]

        # convert to float + transpose rows + convert to numpy
        data = [map(float, i) for i in data]
        data = zip(*data)
        data = [np.asarray(i, dtype=float) for i in data]

        if header == [
                'Energy', 'Flux', 'Flux', 'Error_low', 'Flux', 'Error_high'
        ]:
            # This is like SEDs from the galactic plane survey
            #  * http://www.mpi-hd.mpg.de/hfm/HESS/pages/publications/auxiliary/ApJ_636.html

            self.energy, self.dnde, dnde_lower, dnde_upper = data
            self.dnde_err = (dnde_lower + dnde_upper) / 2

            # lines are energy, flux, flux_lower, flux_upper

        elif header == [
                'Energy', 'interval', 'Mean', 'energy', 'Flux', 'Flux', 'Error'
        ]:
            # This is like the SED for HESS J1303-631
            #  * http://www.mpi-hd.mpg.de/hfm/HESS/pages/publications/auxiliary/AA439_1013.html
            print 'data', data

            self.lower_energy, self.upper_energy, self.energy, self.dnde, self.dnde_err = data

        elif header == ['Mean', 'energy', 'Flux', 'Flux', 'Error']:
            # This is like the SED for Vela X
            #  * http://www.mpi-hd.mpg.de/hfm/HESS/pages/publications/auxiliary/VelaX_auxinfo.html

            self.energy, self.dnde, self.dnde_err = data

        elif header == [
                'Energy', 'interval', 'Mean', 'energy', 'Flux', 'Flux', 'Error'
        ]:
            # This is like the SED for MSH 15-52
            #  * http://www.mpi-hd.mpg.de/hfm/HESS/pages/publications/auxiliary/AA435_L17.html
            self.lower_energy, self.upper_energy, self.dnde, self.dnde_err = data

        elif header == [
                'Mean', 'energy', 'Flux', 'Flux', 'Error', '(', '-', '/', '+',
                ')'
        ]:
            # This is like the SED for the Kookaburra
            #  * http://www.mpi-hd.mpg.de/hfm/HESS/pages/publications/auxiliary/kookaburra_auxinfo.html
            raise Exception("not implemented")

        if self.energy is None:
            self.energy = np.sqrt(self.lower_energy * self.upper_energy)
        if self.lower_energy is None or self.upper_energy is None:
            # if only energy is given, assume no range in energy
            self.lower_energy = self.energy
            self.upper_energy = self.energy

        self.significant = np.ones_like(self.energy).astype(bool)

        def estimate_flux(dnde, energy, emin, emax, e_weight):
            """ estimate the emin to emax flux for a source with prefactor
                dnde at the given energy. assuming the source has a
                spectral index of 2. 
                
                Note, for our situation dnde has units [ph/cm^2/s/TeV]
                and energy has units [TeV], but the ouptut of the
                i_flux function is correct. If e_weight=0,
                the return has units [ph/cm^2/s]. If e_weight=1,
                the return has units [TeV/cm^2/s]. """
            model = PowerLaw(index=2, norm=dnde, e0=energy)
            return model.i_flux(emin=emin, emax=emax, e_weight=e_weight)

        estimate_flux = np.vectorize(estimate_flux)

        self.flux = estimate_flux(self.dnde, self.energy, self.lower_energy,
                                  self.upper_energy, 0)
        self.eflux = estimate_flux(self.dnde, self.energy, self.lower_energy,
                                   self.upper_energy, 1)

        # Note, we can use this shortcut to comptue the errors,
        # But ONLY because the function flux(dnde) is linear in dnde and dnde is the only
        # parameter with an error: flux=dnde*f(gamma,e0) so flux_err=dnde_err*f(gamma,e0)
        self.flux_err = estimate_flux(self.dnde_err, self.energy,
                                      self.lower_energy, self.upper_energy, 0)
        self.eflux_err = estimate_flux(self.dnde_err, self.energy,
                                       self.lower_energy, self.upper_energy, 1)

        # no upper limits
        self.dnde_ul = np.nan * self.dnde
        self.flux_ul = np.nan * self.flux
        self.eflux_ul = np.nan * self.eflux

        for values, u in [[['lower_energy', 'upper_energy', 'energy'],
                           units.TeV],
                          [['dnde', 'dnde_err', 'dnde_ul'],
                           units.ph / units.cm**2 / units.s / units.TeV],
                          [['flux', 'flux_err', 'flux_ul'],
                           units.ph / units.cm**2 / units.s],
                          [['eflux', 'eflux_err', 'eflux_ul'],
                           units.TeV / units.cm**2 / units.s]]:

            for v in values:
                self.__dict__[v] = units.tosympy(self.__dict__[v], u)

        # all hess points are significant (as far as I can tell)
        self.significant = np.ones(len(self.energy), dtype=bool)
        print 'en', self.energy
        print 'sig', self.significant