import logging import unittest import astropy.units as u import numpy as np from exorad.log import setLogLevel from exorad.models.noise import Noise from exorad.models.signal import Signal, CountsPerSeconds, Sed setLogLevel(logging.DEBUG) class SignalTest(unittest.TestCase): def test_quantity_check(self): try: wl = np.linspace(0.1, 1, 10) * u.um data = np.random.random_sample((10, 10)) time_grid = np.linspace(1, 5, 10) * u.hr Signal(wl_grid=wl, data=data, time_grid=time_grid) CountsPerSeconds(wl_grid=wl, data=data * u.Unit('ct/s'), time_grid=time_grid) Noise(wl_grid=wl, data=data * u.hr**0.5, time_grid=time_grid) Sed(wl_grid=wl, data=data * u.W / u.m**2 / u.um, time_grid=time_grid) wl = np.linspace(0.1, 1, 10) * u.m time_grid = np.linspace(1, 5, 10) * u.s Signal(wl_grid=wl, data=data, time_grid=time_grid)
def test_table(self): setLogLevel(logging.DEBUG) for target in self.targets: plotter = Plotter(input_table=self.targets[target].table) plotter.plot_table() plt.show()
def test_efficiency_catcher(self): setLogLevel(logging.DEBUG) plotter = Plotter(input_table=self.table) plotter.plot_efficiency() plotter.save_fig('test.png', efficiency=True)
def test_efficiency(self): setLogLevel(logging.DEBUG) plotter = Plotter(channels=self.channels, input_table=self.table) plotter.plot_efficiency() plt.show()
def main(): import argparse from exorad.__version__ import __version__ from exorad.utils.util import parse_range parser = argparse.ArgumentParser( description='ExoRad {}'.format(__version__)) parser.add_argument("-i", "--input", dest='input', type=str, required=True, help="Input h5 file to pass") parser.add_argument("-o", "--out", dest='out', type=str, default='None', required=True, help="Output directory") parser.add_argument("-n", "--target-number", dest='target_number', type=str, default='all', required=False, help="A list or range of targets to run") parser.add_argument("-t", "--target-name", dest='target_name', type=str, default='None', required=False, help="name of the target to plot") parser.add_argument("-d", "--debug", dest='debug', default=False, required=False, help="log output on screen", action='store_true') args = parser.parse_args() logger = logging.getLogger('exorad') from exorad.utils.ascii_art import ascii_plot logger.info(ascii_plot) logger.info('code version {}'.format(__version__)) if args.debug: setLogLevel(logging.DEBUG) if not os.path.exists(args.out): os.makedirs(args.out) logger.info('output directory created') logger.info('reading {}'.format(args.input)) file = h5py.File(args.input) if args.target_number != 'all' and args.target_name != 'None': logger.error('you cannot use both target number and target name') raise ValueError targets_dir = file['targets'] targets_to_run_id = parse_range(args.target_number, len(targets_dir.keys())) targets_to_run = [list(targets_dir.keys())[n] for n in targets_to_run_id] if args.target_name != 'None': targets_to_run = [ target for target in targets_to_run if target == args.target_name ] for target in targets_to_run: target_dir = targets_dir[target] table_dir = target_dir['table'] table = read_table_hdf5(table_dir, path='table') plotter = Plotter(input_table=table) plotter.plot_table() plotter.save_fig(os.path.join(args.out, '{}.png'.format(target))) plt.close()
def test_values(self): # set constant qe options['channel']['Spec']['detector']['qe'] = {'value': 0.7} # prepare channel setLogLevel(logging.INFO) wl_grid = np.logspace( np.log10(options['channel']['Spec']['detector']['wl_min'] ['value'].value), np.log10(options['channel']['Spec']['detector']['cut_off'] ['value'].value), 6000) * u.um spectrometer = Spectrometer('Spec', options['channel']['Spec'], options) spectrometer.build() spec = OpticalPath(wl=wl_grid, description=options['channel']['Spec']) spec.build_transmission_table() spec.chain() spec.compute_signal(spectrometer.table, spectrometer.built_instr) setLogLevel(logging.DEBUG) # prepare elements to compute D1 = options['channel']['Spec']['optics']['opticalElement']['D1'] M5 = options['channel']['Spec']['optics']['opticalElement']['M5'] M6 = options['channel']['Spec']['optics']['opticalElement']['M6'] optics = options['channel']['Spec']['optics']['opticalElement'][ 'optics'] detector = options['channel']['Spec']['optics']['opticalElement'][ 'detector'] qe = 0.7 D = (options['channel']['Spec']['detector']['delta_pix']['value']) Windows = spectrometer.built_instr['window_size_px'] Windows_spatial = spectrometer.built_instr['window_spatial_width'] from exorad.utils.exolib import planck import astropy.constants as const from astropy.table import Table check_table = Table() # check detector: pi acceptance angle detector_radiance = planck(wl=wl_grid, T=detector['temperature']['value']).to( u.W / (u.m**2 * u.micron * u.sr)) detector_radiance *= D**2 * np.pi * u.sr * qe * ( wl_grid / const.c / const.h).to(1. / u.W / u.s) * u.count detector_signal = (np.trapz(detector_radiance, x=wl_grid)).to(u.count / u.s) check_table['detector signal'] = detector_signal * Windows # check optic box: pi-omega_pix acceptance angle from exorad.utils.exolib import OmegaPix omega_pix = OmegaPix( options['channel']['Spec']['Fnum_x']['value'].value, options['channel']['Spec']['Fnum_x']['value'].value) optics_radiance = planck(wl=wl_grid, T=optics['temperature']['value']).to( u.W / (u.m**2 * u.micron * u.sr)) optics_radiance *= D**2 * (np.pi * u.sr - omega_pix) * qe * ( wl_grid / const.c / const.h).to(1. / u.W / u.s) * u.count optics_signal = (np.trapz(optics_radiance, x=wl_grid)).to(u.count / u.s) check_table['optics signal'] = optics_signal * Windows # check M6: omega_pix acceptance angle M6_radiance = planck(wl=wl_grid, T=M6['temperature']['value']).to( u.W / (u.m**2 * u.micron * u.sr)) M6_radiance *= M6['emissivity']['value'] M6_radiance *= D**2 * omega_pix * qe * ( wl_grid / const.c / const.h).to(1. / u.W / u.s) * u.count M6_signal = (np.trapz(M6_radiance, x=wl_grid)).to(u.count / u.s) check_table['M6 signal'] = M6_signal * Windows # check M5: omega_pix acceptance angle, transmission applied (also D1) and slit slit_width = spectrometer.built_instr['slit_width'] wl_pix = spectrometer.built_instr['wl_pix_center'] dwl_pic = spectrometer.built_instr['pixel_bandwidth'] ch_table = spectrometer.table slit_kernel = np.ones(int(slit_width / D.to(u.um))) M5_radiance = planck(wl=wl_grid, T=M5['temperature']['value']).to( u.W / (u.m**2 * u.micron * u.sr)) M5_radiance *= M5['emissivity']['value'] * M6['transmission'][ 'value'] * D1['transmission']['value'] wl_min, wl_max = D1['wl_min']['value'], D1['wl_max']['value'] idx = np.where(wl_grid < wl_min) M5_radiance[idx] = 0.0 idx = np.where(wl_grid > wl_max) M5_radiance[idx] = 0.0 M5_radiance *= D**2 * omega_pix * qe * ( wl_grid / const.c / const.h).to(1. / u.W / u.s) * u.count from exorad.utils.exolib import rebin _, M5_radiance = rebin(wl_pix, wl_grid, M5_radiance) M5_signal_tmp = (np.convolve(M5_radiance * dwl_pic, slit_kernel, 'same')).to(u.count / u.s) idx = [ np.logical_and(wl_pix > wlow, wl_pix <= whigh) for wlow, whigh in zip(ch_table['LeftBinEdge'], ch_table['RightBinEdge']) ] M5_signal = [ M5_signal_tmp[idx[k]].value.sum() for k in range(len(idx)) ] check_table['M5 signal'] = M5_signal * u.ct / u.s * Windows_spatial spec.signal_table.remove_column('D1 signal') import matplotlib.pyplot as plt fig, ax = plt.subplots(1, 1) wl = spectrometer.table['Wavelength'] for col in spec.signal_table.keys(): ax.plot(wl, spec.signal_table[col], alpha=0.5, lw=1, label=col) ax.plot(wl, check_table[col], alpha=0.5, ls=':', lw=3, label='{} check'.format(col)) ax.set_yscale('log') fig.suptitle('test_optical.test_values 1') ax.legend() plt.show() import matplotlib.pyplot as plt fig, ax = plt.subplots(1, 1) wl = spectrometer.table['Wavelength'] for col in spec.signal_table.keys(): ax.plot(wl, spec.signal_table[col] / check_table[col], alpha=0.5, label=col) ax.set_yscale('log') fig.suptitle('test_optical.test_values 2') ax.legend() plt.show() for col in spec.signal_table.keys(): # check absolute equality up to 1e-40 np.testing.assert_almost_equal(spec.signal_table[col].value, check_table[col], decimal=40, err_msg='', verbose=True) for col in spec.signal_table.keys(): # check relative equality up to 1% np.testing.assert_almost_equal(spec.signal_table[col].value / check_table[col], np.ones(len(check_table[col])), decimal=2, err_msg='', verbose=True)