def voigt_fit(theta, x, y, yerr, sat_lim=0.05): peak1 = Voigt1D(x_0=theta[0], amplitude_L=theta[1], fwhm_L=theta[2], fwhm_G=theta[3])(x) peak2 = np.zeros(len(peak1)) if len(theta) > 5: peak2 = Voigt1D(x_0=theta[4], amplitude_L=theta[5], fwhm_L=theta[6], fwhm_G=theta[7])(x) model = 1.0 - (peak1 + peak2) sat = model < sat_lim model[sat] = np.mean(sat_lim) return model
def FitLine(self, params): ''' #Calulates the fitted line at given params and wavenumbers ''' upperFWavenumbers = np.zeros_like(self.relIntensities) for i, F in enumerate(self.listF[:, 0]): upperFWavenumbers[i] += dE(params[0], params[2], K(F, self.upperJ, self.I), F, self.upperJ, self.I) lowerFWavenumbers = np.zeros_like(self.relIntensities) for i, F in enumerate(self.listF[:, 1]): lowerFWavenumbers[i] += dE(params[1], params[3], K(F, self.lowerJ, self.I), F, self.lowerJ, self.I) self.hfsLines = upperFWavenumbers - lowerFWavenumbers + params[7] line_fit = np.zeros_like(self.w) self.components = [] for i, v in enumerate(self.relIntensities): voigt = Voigt1D(self.hfsLines[i], v, params[5], params[4]) line_fit += voigt(self.w) / (np.pi * params[5] / 2 ) #normalisation of area self.components.append(voigt(self.w) / (np.pi * params[5] / 2)) line_fit = line_fit * params[6] / np.sum(self.relIntensities) self.components = np.array(self.components) * params[6] / np.sum( self.relIntensities) line_fit = satFit(line_fit, params[8]) self.components = satFit(self.components, params[8]) self.noApoFit = cp.copy(line_fit) line_fit = self.ApoFit(line_fit) return line_fit
def __init__(self, center=0.0, intensity=1.0, fwhm_L=1.0, fwhm_G=1.0, x_min=-5.0, x_max=5.0, n_points=100, snr=30): super(FakeVoigt, self).__init__(center=center, intensity=intensity, x_min=x_min, x_max=x_max, n_points=n_points, snr=snr) self.fwhm_L = fwhm_L self.fwhm_G = fwhm_G v = Voigt1D( x_0=self.center, amplitude_L=self.intensity, fwhm_L=self.fwhm_L, fwhm_G=self.fwhm_G, ) self.voigt = v(self.x) self.noisy_voigt = self.voigt + self.noise
def model_from_frequencies(self, frequencies): v = Voigt1D( x_0=self.center, amplitude_L=self.intensity, fwhm_L=self.fwhm_L, fwhm_G=self.fwhm_G, ) return 1. - v(frequencies)
def VoigtFunction(x, centroid, amplitude, L_fwhm, G_fwhm): """ Return the Voigt line shape at x with Lorentzian component HWHM gamma and Gaussian component HWHM alpha. Source: http://scipython.com/book/chapter-8-scipy/examples/the-voigt-profile/ Args: x (numpy array): wavelength array centroid (float): center of profile alpha (float): Gaussian HWHM gamma (float): Lorentzian HWHM """ #sigma = alpha / np.sqrt(2 * np.log(2)) #return np.real(wofz((x - centroid + 1j*gamma)/sigma/np.sqrt(2))) / sigma / np.sqrt(2*np.pi) v = Voigt1D(x_0=centroid, amplitude_L=amplitude, fwhm_L=L_fwhm, fwhm_G=G_fwhm) return v(x)
#NH = NH_list[9] #NH = 1 * 10**12.5 * unit.cm**-2 b_list = np.linspace(10, 50, 5) * unit.km / unit.s #b = b_list[1] lam_0 = 1215.6701 * unit.Angstrom om_0 = 2 * np.pi * const.c / lam_0 f = 0.4164 gamma = 6.265 * 10**8 * unit.s**-1 #* np.pi for b in b_list: W = [] a = np.float((gamma / (4 * om_0) * const.c / b).decompose()) H2 = Voigt1D(x_0=0, amplitude_L=.57 / a, fwhm_L=2 * a, fwhm_G=2 * np.sqrt(np.log(2))) lam = np.linspace(1200., 1230, 4000) * unit.Angstrom om = 2 * np.pi * const.c / lam u = np.array(((om - om_0) / om_0 * const.c / b).decompose()) sigma = 2 * np.sqrt(np.pi) * lam * f * sigma_0 / b * H(a, u) for NH in NH_list: tau = sigma * NH flux = np.exp(-tau) # plt.plot(lam,flux,label="b={},N={:.3e}".format(b,NH))
import numpy as np from astropy.modeling.models import Voigt1D import matplotlib.pyplot as plt import pandas as pd plt.figure() df=pd.read_csv('7.csv') x=df.X*5.692082111+(656-9.705) y=df.Y v1 = Voigt1D(x_0=657.2, amplitude_L=100, fwhm_L=0.02, fwhm_G=0.02) plt.plot(x, v1(x),lw=0.7) #plt.plot(x,y-12) plt.show()
plt.errorbar(vel_2803, col_2803, yerr = sigma_tau2803, linewidth = 0.1, color = '#99ccff', label = '_nolegend_') ax.plot(vel_2796, col_2796, color = '#2CA14B', label = names[0]) ax.plot(vel_2803, col_2803, color = '#2C6EA1', label = names[1]) plt.title("Uncertainty of Column Density in %s" %(gal[h])) plt.xlabel("Velocity (km/s)") plt.ylabel("Column Density (Particle/cm^2)") ax.set_ylim(0, 5E12) ax.set_xlim(-3000,500) plt.legend(loc = 1) f = interp1d(vel_kms[0], flux) vel_new = np.linspace(-3000, 500, num = 3501, endpoint = True) flux_king = f(vel_new) voi = Voigt1D(amplitude_L=-0.5, x_0=0.0, fwhm_L=5.0, fwhm_G=5.0) #xarr = np.linspace(,5.0,num=40) #xarr = vel_kms[0] xarr = vel_new #yarr = voi(xarr) #yarr = flux[good] yarr = flux_king - 1. voi_init = Voigt1D(amplitude_L=-1.0, x_0=-1000, fwhm_L=200, fwhm_G=200) fitter = fitting.LevMarLSQFitter() voi_fit = fitter(voi_init, xarr, yarr) print(voi_fit) ax = fig.add_subplot(3,1,3) ax.plot(xarr,yarr+1, color='magenta') ax.plot(xarr,voi_fit(xarr)+1, color='red')
vel_median = np.median(vel_kms[0][test_2796]) vel_new = np.linspace(vel_median-1000, vel_median+1000, num=2001, endpoint=True) boom = len(vel_kms[0][test_2796]) one = vel_kms[0][test_2796][round(boom*0.2)] two = vel_kms[0][test_2796][round(boom*0.4)] thr = vel_kms[0][test_2796][round(boom*0.6)] fou = vel_kms[0][test_2796][round(boom*0.8)] flux_king = f(vel_new) xarr = vel_new yarr = flux_king - 1. voi_init = Voigt1D(amplitude_L=-1.0, x_0=one, fwhm_L=two-one, fwhm_G=two-one)+Voigt1D(amplitude_L=-1.0, x_0=two, fwhm_L=thr-two, fwhm_G=thr-two)+Voigt1D(amplitude_L=-1.0, x_0=thr, fwhm_L=fou-thr, fwhm_G=fou-thr)+Voigt1D(amplitude_L=-1.0, x_0=fou, fwhm_L=fou-thr, fwhm_G=fou-thr)+Voigt1D(amplitude_L=-1.0, x_0=vel_median, fwhm_L=200, fwhm_G=200) ## Write function that combines cover fraction code with Voigt profile code ??????????? ## ##Correlation between amplitude and cover frac could be key## fitter = fitting.LevMarLSQFitter() voi_fit = fitter(voi_init, xarr, yarr) ax.plot(xarr,voi_fit(xarr)+1, color='red') plt.title("Mg 2796 Voigt Profile for Galaxy %s" %(gal[h]), **title_font) plt.xlabel("Velocity(km/s)", **axis_font) plt.ylabel("C.N. Flux", **axis_font) plt.rc('xtick', labelsize=10) plt.rc('ytick', labelsize=10) ax.set_ylim (0,2) ax.set_xlim(-3000,500)
tied_RVa = {'x_0': tie_RVa } tied_RV = {'x_0': tie_RV } #need good guess #gg_init =( Voigt1D(x_0=lineB[0], amplitude_L=lineB[1], fwhm_L=lineB[2], fwhm_G=lineB[2] ) + # Voigt1D(x_0=0, amplitude_L=lineC[1], fwhm_L=lineC[2], fwhm_G=lineC[2], tied=tied_RV) + # Chebyshev1D(3, c0=C0, c1=C1, c2=C2, c3=C3, fixed={'c0': True, 'c1': True, 'c2': True, 'c3': True}) ) # 3 LINES MODEL CAT gg_init =( Voigt1D(x_0=lineB[0], amplitude_L=lineB[1], fwhm_L=lineB[2], fwhm_G=lineB[2] ,bounds={"amplitude_L": (-0.1, 50)} ) + Voigt1D(x_0=0, amplitude_L=lineC[1], fwhm_L=lineC[2], fwhm_G=lineC[2], tied=tied_RV, bounds={"amplitude_L": (-0.1, 50)}) + Chebyshev1D(3, c0=C0, c1=C1, c2=C2, c3=C3, fixed={'c0': True, 'c1': True, 'c2': True, 'c3': True}) + Voigt1D(x_0=lineA[0], amplitude_L=lineA[1], fwhm_L=lineA[2], fwhm_G=lineA[2], tied=tied_RVa, bounds={"amplitude_L": (-0.1, 50)} ) ) #Levenberg-Marquardt algorithm #SLSQPLSQFitter() does not work for strong lines sequential quadratic programming #fitter = fitting.SLSQPLSQFitter() fitter = fitting.LevMarLSQFitter() gg_fit = fitter(gg_init, x ,y) #gg_fit.mean.tied = tie_center
import numpy as np import os from astropy.modeling.models import Voigt1D import matplotlib.pyplot as plt from astropy.modeling import fitting from matplotlib.backends.backend_pdf import PdfPages filename = 'ad_voigt_test.pdf' with PdfPages(filename) as pdf: fig = plt.figure() ax = fig.add_subplot(1, 1, 1) x = np.arange(-3500, 500, 1) v1 = Voigt1D(x_0=-1000, amplitude_L=-1, fwhm_L=100, fwhm_G=100) ax.plot(x, v1(x) + 1.) plt.ylabel('Continuum-normalized Flux') plt.xlabel('Velocity [km/s]') pdf.savefig() plt.close() fig = plt.figure() ax = fig.add_subplot(1, 1, 1) voi = Voigt1D(amplitude_L=-0.5, x_0=0.0, fwhm_L=5.0, fwhm_G=5.0) xarr = np.linspace(-5.0, 5.0, num=40) yarr = voi(xarr)
def __voigtPeak__(self, spectrum, x0, amplitudeL, fwhmG, fwhmL): voigt_peak = Voigt1D(x_0=x0, amplitude_L=amplitudeL, fwhm_L=fwhmL, fwhm_G=fwhmG) return voigt_peak
def voigtfull(xs, mean, aL, sigmaL, sigmaG, offset): p = [mean, aL, sigmaL, sigmaG, offset] v = Voigt1D(x_0=p[0], amplitude_L=p[1], fwhm_L=p[2], fwhm_G=p[3]) full = p[4] + v(xs) return full
def voigt(xs, p0): '''Returns a gaussian function with inputs p0 over xs. p0 = [sigma, mean]''' v = Voigt1D(x_0=p0[0], amplitude_L=p0[1], fwhm_L=p0[2], fwhm_G=p0[3]) full = p0[4] + v(xs) return full
def voigt2(x, p): decay = (np.exp(-x / p[4])) v1 = Voigt1D(x_0=p[3], amplitude_L=0.18, fwhm_L=p[2], fwhm_G=p[5]) V = p[0] + decay * p[1] * v1(x) #voigt function return V
def voigt(x, x0, a_l, fwhm_l, fwhm_g, offset): v = Voigt1D(x_0=x0, amplitude_L=a_l, fwhm_L=fwhm_l, fwhm_G=fwhm_g) return v(x) + offset