def slice_spec(self, lam_rest, lam_min, lam_max, method='closest', linelist='LLS', use_vel=False): """ Slice the spectrum around a central wavelength and convert it to velocity space lam_rest : approximate rest wavelength of a transition lam_min : minimum wavelength/velocity to slice lam_max : maximum wavelength/velocity to slice Keywords: method = 'closest' [default] -> sets lam_rest to closest atomic transition method = 'Exact' -> uses given lam_rest value to look for transition linelist= Default LLS line linelist, otherwise uses the specified line list use_vel = True -> uses velocity space to slice. here inputs are lam_min = vel_min [in km/sec] lam_max =vel_max [km/s] """ ''' if kwargs.has_key('method'): method=kwargs['method'] else: method='closest' if kwargs.has_key('linelist'): linelist=kwargs['linelist'] else: linelist='LLS' ''' from IGM import rb_setline as s str = s.rb_setline(lam_rest, method, linelist=linelist) spl = 2.9979e5 #speed of light vel = (self.wrest - str['wave'] * (1.0 + 0.)) * spl / (str['wave'] * (1.0 + 0.)) # Now slice spectrum either velocity or wave space if use_vel == False: q = np.where((self.wrest >= lam_min) & (self.wrest <= lam_max)) else: vel_min = lam_min vel_max = lam_max q = np.where((vel >= vel_min) & (vel <= vel_max)) self.wave_slice = self.wrest[q] self.flux_slice = self.flux[q] self.error_slice = self.error[q] self.linelist = linelist self.velo = vel[q] return self.wave_slice, self.error_slice, self.flux_slice, self.velo, self.linelist
def compute_EW(self, lam_cen, vmin=-50., vmax=50., method='closest'): """ Computes rest frame equivalent width and column density for a desired atomic line. Around the species lam_cen and given vmin and vmax keyword values. """ from IGM import rb_setline as s str = s.rb_setline(lam_cen, method, linelist=self.linelist) from IGM import compute_EW as EW out = EW.compute_EW(self.wave_slice, self.fnorm, str['wave'], [vmin, vmax], self.enorm, f0=str['fval'], zabs=0.) self.trans = str['name'] self.fval = str['fval'] self.trans_wave = str['wave'] self.vmin = vmin self.vmax = vmax self.W = out['ew_tot'] self.W_e = out['err_ew_tot'] self.logN = out['col'] self.logN_e = out['colerr'] self.Tau = out['Tau_a'] return self.trans, self.fval, self.vmin, self.vmax, self.trans_wave, self.W, self.W_e, self.logN, self.logN_e, self.Tau
def plot_doublet(self, lam1, lam2, vmin=-600., vmax=600., method='closest'): """ Plot a given doublet defined by the lam1 and lam2 wavelength centers. """ from IGM import rb_setline as s str1 = s.rb_setline(lam1, method, linelist=self.linelist) str2 = s.rb_setline(lam2, method, linelist=self.linelist) spl = 2.9979e5 #speed of light vel1 = (self.wave_slice - str1['wave'] * (1.0 + 0.)) * spl / (str1['wave'] * (1.0 + 0.)) vel2 = (self.wave_slice - str2['wave'] * (1.0 + 0.)) * spl / (str2['wave'] * (1.0 + 0.)) import matplotlib.pyplot as plt fig = plt.figure() ax1 = fig.add_subplot(211) ax1.step(vel1, self.fnorm) ax1.step(vel1, self.enorm, color='r') ax1.set_xlim([vmin, vmax]) ax1.set_ylim([-0.02, 1.8]) ax1.plot([-2500, 2500], [0, 0], 'k:') ax1.plot([-2500, 2500], [1, 1], 'k:') ax1.set_xlabel('vel [km/s]') ax2 = fig.add_subplot(212) ax2.step(vel2, self.fnorm) ax2.step(vel2, self.enorm, color='r') ax2.set_xlim([vmin, vmax]) ax2.set_ylim([-0.02, 1.8]) ax2.plot([-2500, 2500], [0, 0], 'k:') ax2.plot([-2500, 2500], [1, 1], 'k:') ax2.set_xlabel('vel [km/s]') plt.show()
def __init__(self, z, wave, flux, error, lines=None, mask_init=[-200, 200], window_lim=[-1000, 1000], load_file=False, nofrills=False): mask = mask_init self.z = z self.ions = {} if lines: for line in lines: line_dat = rb_setline.rb_setline(line, method='closest') #if using Transition class uncomment below line. Also comment transition def, while uncommenting transition class, comment out lines 80-82 #self.ions[line_dat['name']] =Transition(line_dat,wave,flux,error,self.z,mask_init,window_lim) self.ions[line_dat['name']] = {} ion_dict = self.ions[line_dat['name']] self.Transition(ion_dict, line_dat, wave, flux, error, z, mask, window_lim, nofrills=nofrills) #last dictionary item for full spectra data self.ions['Target'] = {} self.ions['Target']['flux'] = flux self.ions['Target']['wave'] = wave self.ions['Target']['error'] = error self.ions['Target']['z'] = z else: print('Input Linelist and rerun')
def rb_interactive_vpfit_singlet(wave, flux, error, wrest, custom_guess=False, FWHM=15.): # Fix infinities sq = np.isnan(flux) flux[sq] = 0 sqq = flux <= 0 flux[sqq] = 0 q = flux <= 0 flux[q] = error[q] # Converting To velocities from IGM import rb_setline as s str = s.rb_setline(wrest, 'closest', 'atom') spl = 2.9979e5 #speed of light vel = (wave - str['wave'] * (1.0 + 0.)) * spl / (str['wave'] * (1.0 + 0.)) vel, nv = quick_nv_estimate(wave, flux, str['wave'], str['fval']) # Start guessing initial fit interactively if custom_guess == False: fig = plt.figure() ax = fig.add_subplot(111) ax.step(vel, flux) ax.step(vel, error, color='r') plt.xlim([np.min(vel), np.max(vel)]) plt.ylim([-0.02, 1.8]) ax.plot([-2500, 2500], [0, 0], 'k:') ax.plot([-2500, 2500], [1, 1], 'k:') ax.set_xlabel('vel [km/s]') ax.set_ylabel('Normalized Flux') ax.set_title('click to select line centers!') xx = plt.ginput(n=-1) print('Once you are done, press enter to continue!') n_clouds = len(xx) # Create the guesses for starting a fit bguess = np.zeros(n_clouds, ) vguess = np.zeros(n_clouds, ) nguess = np.zeros(n_clouds, ) plt.close() for i in range(0, n_clouds): vguess[i] = xx[i][0] qq = np.where((vel < vguess[i] + 80.) & (vel > vguess[i] - 80.)) nguess[i] = np.log10(sum(nv[qq])) #Now ask interactively for b values prompt = 'Guess b for line ' + np.str(i + 1) + '/' + np.str( n_clouds) + ', vel guess = ' + np.str( '%.1f' % vguess[i]) + ', col guess= ' + np.str( '%.1f' % nguess[i]) + ': ' tmp_b = input(prompt) bguess[i] = tmp_b # Now starting to set up the Voigt Profile model zabs = np.zeros((n_clouds)) lambda_rest = str['wave'] * np.ones((n_clouds)) s = m.create_voigt(zabs, lambda_rest) theta = np.concatenate((nguess, bguess, vguess)) outflux = s.model_flux(theta, wave) def test_fit(wave, *params): return s.model_flux(params, wave) #pdb.set_trace() popt, pcov = curve_fit(test_fit, wave, flux, p0=(theta)) print(popt) fig = plt.figure() ax = fig.add_subplot(111) ax.step(vel, flux) ax.step(vel, error, color='r') ax.plot(vel, outflux, color='k', lw=4) ax.plot(vel, s.model_flux(popt, wave), color='g', lw=6) plt.xlim([np.min(vel), np.max(vel)]) plt.ylim([-0.02, 1.8]) ax.plot([-2500, 2500], [0, 0], 'k:') ax.plot([-2500, 2500], [1, 1], 'k:') ax.set_xlabel('vel [km/s]') ax.set_ylabel('Normalized Flux') plt.show()