Ejemplo n.º 1
0
def test_spectra(noise, sim='lgal', lib='bc03', sample='mini_mocha'):
    print(noise)
    specs, meta = Data.Spectra(sim=sim, noise=noise, lib=lib, sample=sample)

    n_meta = len(meta['galid'])
    assert n_meta == len(meta['redshift'])

    n_spec = specs['flux'].shape[0]
    assert n_meta == n_spec
Ejemplo n.º 2
0
def test_iSpeculator(data_type):

    # initiate fitter
    iSpec = Fitters.iSpeculator(model_name='emulator')
    # default prior
    prior = iSpec._default_prior()

    specs, meta = Data.Spectra(sim='lgal',
                               noise='bgs0',
                               lib='bc03',
                               sample='mini_mocha')
    photo, _ = Data.Photometry(sim='lgal',
                               noise='legacy',
                               lib='bc03',
                               sample='mini_mocha')

    zred = meta['redshift'][0]
    w_obs = specs['wave']
    flux_obs = specs['flux'][0]
    photo_obs = photo['flux'][0, :3]

    if data_type == 'spec':
        output = iSpec.MCMC_spec(w_obs,
                                 flux_obs,
                                 np.ones(len(w_obs)),
                                 zred,
                                 prior=prior,
                                 nwalkers=20,
                                 burnin=10,
                                 niter=10,
                                 silent=False)
        assert 'theta_med' in output.keys()

    elif data_type == 'photo':
        output = iSpec.MCMC_photo(photo_obs,
                                  np.ones(len(photo_obs)),
                                  zred,
                                  bands='desi',
                                  prior=prior,
                                  nwalkers=20,
                                  burnin=10,
                                  niter=10,
                                  opt_maxiter=100,
                                  silent=False)
        assert 'theta_med' in output.keys()
Ejemplo n.º 3
0
def validate_sample(sim):
    ''' generate some plots to validate the mini Mock Challenge photometry
    and spectroscopy 
    '''
    # read photometry
    photo, _ = Data.Photometry(sim=sim, noise='legacy', sample='mini_mocha')
    photo_g = 22.5 - 2.5 * np.log10(photo['flux'][:, 0])
    photo_r = 22.5 - 2.5 * np.log10(photo['flux'][:, 1])
    photo_z = 22.5 - 2.5 * np.log10(photo['flux'][:, 2])

    flux_g = photo['flux'][:, 0] * 1e-9 * 1e17 * UT.c_light() / 4750.**2 * (
        3631. * UT.jansky_cgs())
    flux_r = photo['flux'][:, 1] * 1e-9 * 1e17 * UT.c_light() / 6350.**2 * (
        3631. * UT.jansky_cgs())
    flux_z = photo['flux'][:, 2] * 1e-9 * 1e17 * UT.c_light() / 9250.**2 * (
        3631. * UT.jansky_cgs())  # convert to 10^-17 ergs/s/cm^2/Ang
    ivar_g = photo['ivar'][:, 0] * (1e-9 * 1e17 * UT.c_light() / 4750.**2 *
                                    (3631. * UT.jansky_cgs()))**-2.
    ivar_r = photo['ivar'][:, 1] * (1e-9 * 1e17 * UT.c_light() / 6350.**2 *
                                    (3631. * UT.jansky_cgs()))**-2.
    ivar_z = photo['ivar'][:, 2] * (
        1e-9 * 1e17 * UT.c_light() / 9250.**2 *
        (3631. * UT.jansky_cgs()))**-2.  # convert to 10^-17 ergs/s/cm^2/Ang

    # read BGS targets from imaging
    bgs_targets = h5py.File(
        os.path.join(UT.dat_dir(), 'bgs.1400deg2.rlim21.0.hdf5'), 'r')
    n_targets = len(bgs_targets['ra'][...])

    bgs_g = 22.5 - 2.5 * np.log10(bgs_targets['flux_g'][...])[::10]
    bgs_r = 22.5 - 2.5 * np.log10(bgs_targets['flux_r'][...])[::10]
    bgs_z = 22.5 - 2.5 * np.log10(bgs_targets['flux_z'][...])[::10]

    # photometry validation
    fig = plt.figure(figsize=(6, 6))
    sub = fig.add_subplot(111)
    DFM.hist2d(bgs_g - bgs_r,
               bgs_r - bgs_z,
               color='k',
               levels=[0.68, 0.95],
               range=[[-1., 3.], [-1., 3.]],
               bins=40,
               smooth=0.5,
               plot_datapoints=True,
               fill_contours=False,
               plot_density=False,
               linewidth=0.5,
               ax=sub)
    sub.scatter([-100.], [-100], c='k', s=1, label='BGS targets')
    sub.scatter(photo_g - photo_r,
                photo_r - photo_z,
                c='C0',
                s=1,
                label='LGal photometry')
    sub.legend(loc='upper left', handletextpad=0, markerscale=10, fontsize=20)
    sub.set_xlabel('$g-r$', fontsize=25)
    sub.set_xlim(-1., 3.)
    sub.set_ylabel('$r-z$', fontsize=25)
    sub.set_ylim(-1., 3.)
    ffig = os.path.join(UT.dat_dir(), 'mini_mocha',
                        'mini_mocha.%s.photo.png' % sim)
    fig.savefig(ffig, bbox_inches='tight')
    fig.savefig(UT.fig_tex(ffig, pdf=True), bbox_inches='tight')

    # read spectra
    spec_s, _ = Data.Spectra(sim=sim, noise='none', sample='mini_mocha')
    spec_bgs0, _ = Data.Spectra(sim=sim, noise='bgs0', sample='mini_mocha')
    spec_bgs1, _ = Data.Spectra(sim=sim, noise='bgs1', sample='mini_mocha')
    spec_bgs2, _ = Data.Spectra(sim=sim, noise='bgs2', sample='mini_mocha')

    # read sky brightness
    _fsky = os.path.join(UT.dat_dir(), 'mini_mocha',
                         'bgs.exposure.surveysim.150s.v0p4.sample.hdf5')
    fsky = h5py.File(_fsky, 'r')
    wave_sky = fsky['wave'][...]  # sky wavelength
    sbright_sky = fsky['sky'][...]

    # spectra validationg
    fig = plt.figure(figsize=(10, 5))
    sub = fig.add_subplot(111)

    for i, spec_bgs in enumerate([spec_bgs2, spec_bgs0]):
        wsort = np.argsort(spec_bgs['wave'])
        if i == 0:
            _plt, = sub.plot(spec_bgs['wave'][wsort],
                             spec_bgs['flux'][0, wsort],
                             c='C%i' % i,
                             lw=0.25)
        else:
            sub.plot(spec_bgs['wave'][wsort],
                     spec_bgs['flux'][0, wsort],
                     c='C%i' % i,
                     lw=0.25)

    _plt_photo = sub.errorbar(
        [4750, 6350, 9250], [flux_g[0], flux_r[0], flux_z[0]],
        [ivar_g[0]**-0.5, ivar_r[0]**-0.5, ivar_z[0]**-0.5],
        fmt='.r')

    _plt_sim, = sub.plot(spec_s['wave'][0, :],
                         spec_s['flux'][0, :],
                         c='k',
                         ls='-',
                         lw=1)
    _plt_sim0, = sub.plot(spec_s['wave'][0, :],
                          spec_s['flux_unscaled'][0, :],
                          c='k',
                          ls=':',
                          lw=0.25)

    leg = sub.legend([_plt_sim0, _plt_photo, _plt_sim, _plt], [
        '%s spectrum' % sim.upper(),
        '%s photometry' % sim.upper(),
        '%s fiber spectrum' % sim.upper(),
        '%s BGS spectra' % sim.upper()
    ],
                     loc='upper right',
                     fontsize=17)
    for legobj in leg.legendHandles:
        legobj.set_linewidth(2.0)
    sub.set_xlabel('Wavelength [$A$]', fontsize=20)
    sub.set_xlim(3e3, 1e4)
    sub.set_ylabel('flux [$10^{-17} erg/s/cm^2/A$', fontsize=20)
    if sim == 'lgal': sub.set_ylim(-2., 8.)
    elif sim == 'tng': sub.set_ylim(0., None)

    ffig = os.path.join(UT.dat_dir(), 'mini_mocha',
                        'mini_mocha.%s.spectra.png' % sim)
    fig.savefig(ffig, bbox_inches='tight')
    fig.savefig(UT.fig_tex(ffig, pdf=True), bbox_inches='tight')

    return None
Ejemplo n.º 4
0
def fit_pFF_spectra(igal, noise='none', iter_max=10, overwrite=False):
    ''' Fit Lgal spectra. `noise` specifies whether to fit spectra without noise or 
    with BGS-like noise.  

    :param igal: 
        index of Lgal galaxy within the spectral_challenge 

    :param noise: 
        If 'none', fit noiseless spectra. 
        If 'bgs1'...'bgs8', fit BGS-like spectra. (default: 'none') 

    :param justplot: 
        If True, skip the fitting and plot the best-fit. This is mainly implemented 
        because I'm having issues plotting in NERSC. (default: False) 
    '''
    # read noiseless Lgal spectra of the spectral_challenge mocks
    specs, meta = Data.Spectra(sim='lgal',
                               noise=noise,
                               lib='bc03',
                               sample='mini_mocha')

    model = 'vanilla'
    w_obs = specs['wave']
    flux_obs = specs['flux'][igal]
    if noise != 'none': ivar_obs = specs['ivar'][igal]
    truths = [
        meta['logM_fiber'][igal],
        np.log10(meta['Z_MW'][igal]), meta['t_age_MW'][igal]
    ]
    labels = ['$\log M_*$', '$\log Z$', r'$t_{\rm age}$']

    if noise == 'none':  # no noise
        ivar_obs = np.ones(len(w_obs))

    print('--- input ---')
    print('z = %f' % meta['redshift'][igal])
    print('log M* total = %f' % meta['logM_total'][igal])
    print('log M* fiber = %f' % meta['logM_fiber'][igal])
    print('MW Z = %f' % meta['Z_MW'][igal])
    print('MW tage = %f' % meta['t_age_MW'][igal])

    f_bf = os.path.join(UT.dat_dir(), 'mini_mocha', 'pff',
                        'lgal.spec.noise_%s.%s.%i.hdf5' % (noise, model, igal))
    if os.path.isfile(f_bf):
        if not overwrite:
            print("** CAUTION: %s already exists **" % os.path.basename(f_bf))
    # initiating fit
    pff = Fitters.pseudoFirefly(model_name=model, prior=None)
    bestfit = pff.Fit_spec(w_obs,
                           flux_obs,
                           ivar_obs,
                           meta['redshift'][igal],
                           mask='emline',
                           fit_cap=1000,
                           iter_max=10,
                           writeout=f_bf,
                           silent=False)
    print('--- bestfit ---')
    print('written to %s' % f_bf)
    print('log M* = %f' % bestfit['theta_med'][0])
    print('log Z = %f' % bestfit['theta_med'][1])
    print('---------------')

    fig = plt.figure(figsize=(12, 4))
    sub = fig.add_subplot(111)
    sub.plot(bestfit['wavelength_data'],
             bestfit['flux_data'],
             c='k',
             zorder=1,
             lw=0.5)
    sub.plot(bestfit['wavelength_model'] * (1. + bestfit['redshift']),
             bestfit['flux_model'],
             c='C1')
    sub.set_xlabel('Wavelength', fontsize=20)
    sub.set_xlim(3500, 1e4)
    sub.set_ylabel('Flux', fontsize=20)
    sub.set_ylim(0., None)
    fig.savefig(f_bf.replace('.hdf5', '.png'), bbox_inches='tight')
    return None
Ejemplo n.º 5
0
def fit_spectrophotometry(igal,
                          sim='lgal',
                          noise='bgs0_legacy',
                          method='ifsps',
                          model='emulator',
                          nwalkers=100,
                          burnin=100,
                          niter='adaptive',
                          maxiter=200000,
                          opt_maxiter=100,
                          overwrite=False,
                          postprocess=False,
                          justplot=False):
    ''' Fit Lgal spectra. `noise` specifies whether to fit spectra without noise or 
    with BGS-like noise. Produces an MCMC chain and, if not on nersc, a corner plot of the posterior. 

    :param igal: 
        index of Lgal galaxy within the spectral_challenge 
    :param noise: 
        If 'bgs1'...'bgs8', fit BGS-like spectra. (default: 'none') 
    :param justplot: 
        If True, skip the fitting and plot the best-fit. This is mainly implemented 
        because I'm having issues plotting in NERSC. (default: False) 
    '''
    noise_spec = noise.split('_')[0]
    noise_photo = noise.split('_')[1]
    # read noiseless Lgal spectra of the spectral_challenge mocks
    specs, meta = Data.Spectra(sim=sim,
                               noise=noise_spec,
                               lib='bc03',
                               sample='mini_mocha')
    # read Lgal photometry of the mini_mocha mocks
    photo, _ = Data.Photometry(sim=sim,
                               noise=noise_photo,
                               lib='bc03',
                               sample='mini_mocha')

    if meta['redshift'][igal] < 0.101:
        # current Speculator wavelength doesn't extend far enough
        # current Speculator wavelength doesn't extend far enough
        # current Speculator wavelength doesn't extend far enough
        # current Speculator wavelength doesn't extend far enough
        # current Speculator wavelength doesn't extend far enough
        return None

    w_obs = specs['wave']
    flux_obs = specs['flux'][igal]
    ivar_obs = specs['ivar'][igal]
    if method == 'ispeculator':
        photo_obs = photo['flux'][igal, :3]
        photo_ivar_obs = photo['ivar'][igal, :3]
    else:
        photo_obs = photo['flux'][igal, :5]
        photo_ivar_obs = photo['ivar'][igal, :5]

    # get fiber flux factor prior range based on measured fiber flux
    f_fiber_true = (photo['fiberflux_r_true'][igal] /
                    photo['flux_r_true'][igal])
    prior_width = np.max([
        0.05,
        5. * photo['fiberflux_r_ivar'][igal]**-0.5 / photo['flux'][igal, 1]
    ])
    f_fiber_min = (
        photo['fiberflux_r_meas'][igal]) / photo['flux'][igal, 1] - prior_width
    f_fiber_max = (
        photo['fiberflux_r_meas'][igal]) / photo['flux'][igal, 1] + prior_width
    f_fiber_prior = [f_fiber_min, f_fiber_max]

    print('--- input ---')
    print('z = %f' % meta['redshift'][igal])
    print('log M* total = %f' % meta['logM_total'][igal])
    print('log M* fiber = %f' % meta['logM_fiber'][igal])
    print('f_fiber = %f' % f_fiber_true)
    print('log SFR 100myr = %f' % np.log10(meta['sfr_100myr'][igal]))
    print('log Z_MW = %f' % np.log10(meta['Z_MW'][igal]))

    f_mcmc = os.path.join(
        UT.dat_dir(), 'mini_mocha', method,
        '%s.specphoto.noise_%s.%s.%i.mcmc.hdf5' % (sim, noise, model, igal))

    if method == 'ifsps':
        ifitter = Fitters.iFSPS(model_name=model)
    elif method == 'ispeculator':
        ifitter = Fitters.iSpeculator(model_name=model)

    print('--- mcmc ---')
    if (justplot or not overwrite) and os.path.isfile(f_mcmc):
        print('     reading... %s' % os.path.basename(f_mcmc))
        # read in mcmc chain
        fmcmc = h5py.File(f_mcmc, 'r')
        mcmc = {}
        for k in fmcmc.keys():
            mcmc[k] = fmcmc[k][...]
        fmcmc.close()
    else:
        if os.path.isfile(f_mcmc) and not overwrite:
            print("** CAUTION: %s already exists **" %
                  os.path.basename(f_mcmc))
        print('     writing... %s' % os.path.basename(f_mcmc))
        # initiating fit
        prior = ifitter._default_prior(f_fiber_prior=f_fiber_prior)

        mcmc = ifitter.MCMC_spectrophoto(w_obs,
                                         flux_obs,
                                         ivar_obs,
                                         photo_obs,
                                         photo_ivar_obs,
                                         meta['redshift'][igal],
                                         mask='emline',
                                         prior=prior,
                                         nwalkers=nwalkers,
                                         burnin=burnin,
                                         niter=niter,
                                         maxiter=maxiter,
                                         opt_maxiter=opt_maxiter,
                                         writeout=f_mcmc,
                                         silent=False)

    if postprocess:
        print('--- postprocessing ---')
        f_post = f_mcmc.replace('.mcmc.hdf5', '.postproc.hdf5')
        mcmc = ifitter.postprocess(mcmc_output=mcmc, writeout=f_post)

    i_fib = list(mcmc['theta_names'].astype(str)).index('f_fiber')

    print('log M* total = %f' % mcmc['theta_med'][0])
    print('log M* fiber = %f' %
          (mcmc['theta_med'][0] + np.log10(mcmc['theta_med'][i_fib])))
    print('---------------')
    try:
        # plotting on nersc never works.
        if os.environ['NERSC_HOST'] == 'cori': return None
    except KeyError:

        labels = [lbl_dict[_t] for _t in mcmc['theta_names'].astype(str)]
        truths = [None for _ in labels]
        truths[0] = meta['logM_total'][igal]
        truths[i_fib] = f_fiber_true
        if postprocess:
            i_sfr = list(
                mcmc['theta_names'].astype(str)).index('logsfr.100myr')
            truths[i_sfr] = np.log10(meta['sfr_100myr'][igal])
            i_zw = list(mcmc['theta_names'].astype(str)).index('logz.mw')
            truths[i_zw] = np.log10(meta['Z_MW'][igal])
            print('log SFR 100myr = %f' %
                  np.median(mcmc['mcmc_chain'][:, i_sfr]))
            print('log Z_MW = %f' % np.median(mcmc['mcmc_chain'][:, i_zw]))

        # corner plot of the posteriors
        fig = DFM.corner(mcmc['mcmc_chain'],
                         range=mcmc['prior_range'],
                         quantiles=[0.16, 0.5, 0.84],
                         levels=[0.68, 0.95],
                         nbin=40,
                         smooth=True,
                         truths=truths,
                         labels=labels,
                         label_kwargs={'fontsize': 20})
        if postprocess:
            fig.savefig(f_post.replace('.hdf5', '.png'), bbox_inches='tight')
        else:
            fig.savefig(f_mcmc.replace('.hdf5', '.png'), bbox_inches='tight')
        plt.close()

        fig = plt.figure(figsize=(18, 5))
        gs = mpl.gridspec.GridSpec(1,
                                   2,
                                   figure=fig,
                                   width_ratios=[1, 3],
                                   wspace=0.2)
        sub = plt.subplot(gs[0])
        sub.errorbar(np.arange(len(photo_obs)),
                     photo_obs,
                     yerr=photo_ivar_obs**-0.5,
                     fmt='.k',
                     label='data')
        sub.scatter(np.arange(len(photo_obs)),
                    mcmc['flux_photo_model'],
                    c='C1',
                    label='model')
        sub.legend(loc='upper left',
                   markerscale=3,
                   handletextpad=0.2,
                   fontsize=15)
        sub.set_xticks([0, 1, 2, 3, 4])
        sub.set_xticklabels(['$g$', '$r$', '$z$', 'W1', 'W2'])
        sub.set_xlim(-0.5, len(photo_obs) - 0.5)

        sub = plt.subplot(gs[1])
        sub.plot(w_obs, flux_obs, c='k', lw=1, label='data')
        sub.plot(mcmc['wavelength_model'],
                 mcmc['flux_spec_model'],
                 c='C1',
                 ls='--',
                 lw=1,
                 label=method)
        sub.legend(loc='upper right', fontsize=15)
        sub.set_xlabel('wavelength [$A$]', fontsize=20)
        sub.set_xlim(3600., 9800.)
        sub.set_ylim(-1., 5.)

        if postprocess:
            fig.savefig(f_post.replace('.hdf5', '.bestfit.png'),
                        bbox_inches='tight')
        else:
            fig.savefig(f_mcmc.replace('.hdf5', '.bestfit.png'),
                        bbox_inches='tight')
        plt.close()
    return None
Ejemplo n.º 6
0
import numpy as np
import matplotlib.pyplot as plt
import h5py
import sys
import os
from gqp_mc import data as Data 
from gqp_mc import fitters as Fitters
import warnings
warnings.filterwarnings("ignore")

specs,meta = Data.Spectra(sim='lgal',noise = 'none', lib = 'bc03', sample = 'mini_mocha')
# photo, _ = Data.Photometry(sim='lgal', noise= 'none', lib='bc03', sample='mini_mocha') 
True_logM_total = meta['logM_total']
True_logsfr_100myr = np.log10(meta['sfr_100myr'])
True_logsfr_1gyr = np.log10(meta['sfr_1gyr'])
True_logz_mw = np.log10(meta['Z_MW'])
True_logM_fiber = meta['logM_fiber']

class Doctor():
    def __init__(self):
        pass

    def _diagnose(self,mcmc_data,tt_names,param,gal_idx):
        if param == 'logmstar':
            truth = True_logM_total[gal_idx]
        elif param == 'logsfr.100myr':
            truth = True_logsfr_100myr[gal_idx]
        elif param == 'logsfr.1gyr':
            truth = True_logsfr_1gyr[gal_idx]
        elif param == 'logz.mw':
            truth = True_logz_mw[gal_idx]
Ejemplo n.º 7
0
def mini_mocha_spec(noise='bgs0_legacy', sample='mini_mocha', method='ifsps'):
    ''' Compare properties inferred from forward modeled spectra to input properties
    '''
    if noise != 'none':
        noise_spec = noise.split('_')[0]
        noise_photo = noise.split('_')[1]
    else:
        noise_spec = 'none'
        noise_photo = 'none'
    # read noiseless Lgal spectra of the spectral_challenge mocks
    specs, meta = Data.Spectra(sim='lgal',
                               noise=noise_spec,
                               lib='bc03',
                               sample=sample)

    Mstar_input = meta['logM_total'][:97]  # total mass
    Z_MW_input = meta['Z_MW'][:97]  # mass-weighted metallicity
    tage_input = meta['t_age_MW'][:97]  # mass-weighted age
    #print(meta['redshift'])

    theta_inf = []
    for igal in range(97):
        # read best-fit file and get inferred parameters
        _fbf = Fbestfit_spec(igal, noise=noise, method=method)
        fbf = h5py.File(_fbf, 'r')
        #print(fbf['redshift'][...])

        theta_inf_i = np.array([
            fbf['theta_2sig_minus'][...], fbf['theta_1sig_minus'][...],
            fbf['theta_med'][...], fbf['theta_1sig_plus'][...],
            fbf['theta_2sig_plus'][...]
        ])
        theta_inf.append(theta_inf_i)
    theta_inf = np.array(theta_inf)

    # inferred properties
    Mstar_inf = theta_inf[:, :, 0]
    Z_MW_inf = 10**theta_inf[:, :, 1]
    tage_inf = theta_inf[:, :, 2]

    fig = plt.figure(figsize=(15, 4))
    # compare total stellar mass
    sub = fig.add_subplot(131)
    sub.errorbar(Mstar_input,
                 Mstar_inf[:, 2],
                 yerr=[
                     Mstar_inf[:, 2] - Mstar_inf[:, 1],
                     Mstar_inf[:, 3] - Mstar_inf[:, 2]
                 ],
                 fmt='.C0')
    sub.plot([9., 12.], [9., 12.], c='k', ls='--')
    sub.set_xlabel(r'input $\log~M_{\rm tot}$', fontsize=20)
    sub.set_xlim(9., 12.)
    sub.set_ylabel(r'inferred $\log~M_{\rm tot}$', fontsize=20)
    sub.set_ylim(9., 12.)

    # compare metallicity
    sub = fig.add_subplot(132)
    sub.errorbar(Z_MW_input,
                 Z_MW_inf[:, 2],
                 yerr=[
                     Z_MW_inf[:, 2] - Z_MW_inf[:, 1],
                     Z_MW_inf[:, 3] - Z_MW_inf[:, 2]
                 ],
                 fmt='.C0')
    sub.plot([1e-3, 1], [1e-3, 1.], c='k', ls='--')
    sub.set_xlabel(r'input MW $Z$', fontsize=20)
    sub.set_xscale('log')
    sub.set_xlim(1e-3, 5e-2)
    sub.set_ylabel(r'inferred MW $Z$', fontsize=20)
    sub.set_yscale('log')
    sub.set_ylim(1e-3, 5e-2)

    # compare age
    sub = fig.add_subplot(133)
    sub.errorbar(tage_input,
                 tage_inf[:, 2],
                 yerr=[
                     tage_inf[:, 2] - tage_inf[:, 1],
                     tage_inf[:, 3] - tage_inf[:, 2]
                 ],
                 fmt='.C0')
    sub.plot([0, 13], [0, 13.], c='k', ls='--')
    sub.set_xlabel(r'input MW $t_{\rm age}$', fontsize=20)
    sub.set_xlim(0, 13)
    sub.set_ylabel(r'inferred MW $t_{\rm age}$', fontsize=20)
    sub.set_ylim(0, 13)

    fig.subplots_adjust(wspace=0.4)
    _ffig = os.path.join(
        dir_fig,
        'mini_mocha.%s.specfit.vanilla.noise_%s.png' % (method, noise))
    fig.savefig(_ffig, bbox_inches='tight')
    fig.savefig(_ffig, bbox_inches='tight')
    fig.savefig(UT.fig_tex(_ffig, pdf=True), bbox_inches='tight')
    return None
Ejemplo n.º 8
0
def fit_spectrophotometry(igal, noise='none', nwalkers=100, burnin=100, niter=1000, overwrite=False, justplot=False): 
    ''' Fit Lgal spectra. `noise` specifies whether to fit spectra without noise or 
    with BGS-like noise. Produces an MCMC chain and, if not on nersc, a corner plot of the posterior. 

    :param igal: 
        index of Lgal galaxy within the spectral_challenge 

    :param noise: 
        If 'none', fit noiseless spectra. 
        If 'bgs1'...'bgs8', fit BGS-like spectra. (default: 'none') 

    :param justplot: 
        If True, skip the fitting and plot the best-fit. This is mainly implemented 
        because I'm having issues plotting in NERSC. (default: False) 
    '''
    if noise != 'none': 
        noise_spec = noise.split('_')[0]
        noise_photo = noise.split('_')[1]
    else: 
        noise_spec = 'none'
        noise_photo = 'none'
    # read noiseless Lgal spectra of the spectral_challenge mocks 
    specs, meta = Data.Spectra(sim='lgal', noise=noise_spec, lib='bc03', sample='mini_mocha') 
    
    # read Lgal photometry of the mini_mocha mocks 
    photo, _ = Data.Photometry(sim='lgal', noise=noise_photo, lib='bc03', sample='mini_mocha') 

    model       = 'vanilla'
    w_obs       = specs['wave']
    flux_obs    = specs['flux'][igal]
    if noise_spec != 'none': 
        ivar_obs = specs['ivar'][igal]
    else:  
        ivar_obs = np.ones(len(w_obs)) 
    photo_obs   = photo['flux'][igal,:5]
    if noise_photo != 'none': 
        photo_ivar_obs = photo['ivar'][igal,:5]
    else:  
        photo_ivar_obs = np.ones(photo_obs.shape[0]) 

    # get fiber flux factor prior range based on measured fiber flux 
    f_fiber_true = (photo['fiberflux_r_meas'][igal]/photo['flux_r_true'][igal]) 
    f_fiber_min = (photo['fiberflux_r_meas'][igal] - 3.*photo['fiberflux_r_ivar'][igal]**-0.5)/photo['flux'][igal,1]
    f_fiber_max = (photo['fiberflux_r_meas'][igal] + 3.*photo['fiberflux_r_ivar'][igal]**-0.5)/photo['flux'][igal,1]
    f_fiber_prior = [f_fiber_min, f_fiber_max]
    print(f_fiber_prior) 
    print(f_fiber_true) 
    print((photo['fiberflux_r_true'][igal]/photo['flux_r_true'][igal])) 

    truths      = [meta['logM_total'][igal], np.log10(meta['Z_MW'][igal]), meta['t_age_MW'][igal], None, None, f_fiber_true]
    labels      = ['$\log M_*$', '$\log Z$', r'$t_{\rm age}$', 'dust2', r'$\tau$', r'$f_{\rm fiber}$']

    print('--- input ---') 
    print('z = %f' % meta['redshift'][igal])
    print('log M* total = %f' % meta['logM_total'][igal])
    print('log M* fiber = %f' % meta['logM_fiber'][igal])
    print('MW Z = %f' % meta['Z_MW'][igal]) 
    print('MW tage = %f' % meta['t_age_MW'][igal]) 

    f_bf = os.path.join(UT.dat_dir(), 'mini_mocha', 'ifsps', 'lgal.specphoto.noise_%s.%s.%i.hdf5' % (noise, model, igal))
    if not justplot: 
        if os.path.isfile(f_bf): 
            if not overwrite: 
                print("** CAUTION: %s already exists **" % os.path.basename(f_bf)) 
        # initiating fit
        ifsps = Fitters.iFSPS(model_name=model, prior=None) 
        bestfit = ifsps.MCMC_spectrophoto(
                w_obs, 
                flux_obs, 
                ivar_obs, 
                photo_obs, 
                photo_ivar_obs, 
                meta['redshift'][igal], 
                f_fiber_prior=f_fiber_prior, 
                mask='emline', 
                nwalkers=nwalkers, 
                burnin=burnin, 
                niter=niter, 
                writeout=f_bf,
                silent=False)
    else: 
        # read in best-fit file with mcmc chain
        fbestfit = h5py.File(f_bf, 'r')  
        bestfit = {} 
        for k in fbestfit.keys(): 
            bestfit[k] = fbestfit[k][...]

    print('--- bestfit ---') 
    print('written to %s' % f_bf) 
    print('log M* total = %f' % bestfit['theta_med'][0])
    print('log M* fiber = %f' % (bestfit['theta_med'][0] + np.log10(bestfit['theta_med'][-1])))
    print('log Z = %f' % bestfit['theta_med'][1]) 
    print('---------------') 
    
    try: 
        # plotting on nersc never works.
        if os.environ['NERSC_HOST'] == 'cori': return None 
    except KeyError: 
        # corner plot of the posteriors 
        fig = DFM.corner(bestfit['mcmc_chain'], range=bestfit['priors'], quantiles=[0.16, 0.5, 0.84], 
                levels=[0.68, 0.95], nbin=40, smooth=True, 
                truths=truths, labels=labels, label_kwargs={'fontsize': 20}) 
        fig.savefig(f_bf.replace('.hdf5', '.png'), bbox_inches='tight') 
    return None