def fit_gauss(x, y): """ fitting a normal distribution on a given data Input: x --- a list of the bin y --- a list of the count Output: amp --- amp of the a normal distribution cent--- center of the normal distribution width--- width of the normal distribution """ nx = numpy.array(x) ny = numpy.array(y) ne = numpy.ones(len(ny)) # #--- we need to give an initial guess # ymax = numpy.max(ny) cest = find_center(x, y) p0 = [ymax, cest, 10, 0] fitobj = kmpfit.Fitter(residuals=residualsG, data=(nx,ny,ne)) fitobj.fit(params0=p0) [amp, cent, width, floor] = fitobj.params return [cent, width, amp]
def setUp(self): # Pearson's data retrieved from http://www.astro.rug.nl/software/kapteyn/kmpfittutorial.html#fitting-data-when-both-variables-have-uncertainties x = np.array([0.0, 0.9, 1.8, 2.6, 3.3, 4.4, 5.2, 6.1, 6.5, 7.4]) y = np.array([5.9, 5.4, 4.4, 4.6, 3.5, 3.7, 2.8, 2.8, 2.4, 1.5]) wy = np.array([1, 1.8, 4, 8, 20, 20, 70, 70, 100, 500]) erry = 1 / np.sqrt(wy) N = len(x) # weights in x are ignored in linearfit # wx = np.array([1000.0,1000,500,800,200,80,60,20,1.8,1.0]) # errx = 1/np.sqrt(wx) # dependent variables M = np.mat(y) # diagonal covariance matrix of dependent variables S = np.mat(np.diag(wy)) # matrix of independent variables, here only ones C = np.mat(np.vstack((np.ones(len(x)), x))) # initialise object res = linearfit.LinearFit(M, S, C) # do the fit res.fit() print("\n\n======== Results linearfit =========") res.display_results(precision=10) res.display_correlations() self.result = res # optional comparison with kapteyn (nonlinear fitting) package if 0: from kapteyn import kmpfit def model(p, x): a, b = p return a + b * x def residuals2(p, data): # Residuals function for data with errors in y only a, b = p x, y, ey = data wi = np.where(ey == 0.0, 0.0, 1.0 / ey) d = wi * (y - model(p, x)) return d # Prepare fit routine beta0 = [5.0, 1.0] # Initial estimates # Prepare fit routine fitobj2 = kmpfit.Fitter(residuals=residuals2, data=(x, y, erry)) fitobj2.fit(params0=beta0) print("\n\n======== Results kmpfit =========") print("Fitted parameters: ", fitobj2.params) print("Covariance errors: ", fitobj2.xerror) print("Standard errors ", fitobj2.stderr) print("Reduced Chi^2: ", fitobj2.rchi2_min)
def fit_pmodel(hist, ymax, xpos, hwidth): """ for a given histgram data, fit a gaussian distribution input: hist --- hist data ymax --- initial guess height of the profile xpos --- initial guess center postion hwidth --- initial guess sigma Output: amp --- estimated height of the profile cent --- estimated center postion width --- estimated sigma floor --- estimated floor level """ start = int(xpos) - hwidth stop = int(xpos) + hwidth ybin = hist[start:stop] xbin = [x for x in range(start, stop)] err = numpy.ones(2 * hwidth) p0 = [ymax, xpos, 10, 0] fitobj = kmpfit.Fitter(residuals=residualsG, data=(xbin, ybin, err)) fitobj.fit(params0=p0) [amp, cent, width, floor] = fitobj.params return [amp, cent, width, floor]
def fit_poly(x, y, nterms): """ estimate polynomial fitting coefficients Input: x --- independent variable (array) y --- dependent variable (array) nterms --- degree of polynomial fit Output: fitobj.params --- array of polynomial fit coefficient Note: for the detail on kmpfit, read: http://www.astro.rug.nl/software/kapteyn/kmpfittutorial.html#a-basic-example """ # #--- make sure that the arrays are numpyed # d = numpy.array(x) v = numpy.array(y) # #--- set the initial estimate of the coefficients, all "0" is fine # paraminitial = [0.0 for i in range(0, nterms)] # #--- call kmfit # fitobj = kmpfit.Fitter(residuals=residuals, data=(d, v)) try: fitobj.fit(params0=paraminitial) except: print "Something wrong with kmpfit fit" raise SystemExit return fitobj.params
def getHistory(sDay,nAhead,x0,hWeek): nLin = sDay.shape[0] + nAhead nFit = sDay.shape[0] if int(x0['obs_time']) <= 14 else int(x0['obs_time']) sDay['hist'] = sp.interpolate.interp1d(hWeek.t,hWeek.y,kind="cubic")(sDay['t']) histNorm = sDay['hist'].mean() sDay['hist'] = ( (sDay['hist']-sDay['hist'].min())/(sDay['hist'].max()-sDay['hist'].min()) + .5)*x0['hist_adj'] fitD = np.array([sDay.t.tail(nFit),sDay.y.tail(nFit)]) fitobj = kmpfit.Fitter(residuals=ser_residuals,data=fitD) fitobj.fit(params0=x0['poly']) x0['poly'] = fitobj.params sDay['stat'] = (sDay['y']-ser_poly(x0['poly'],sDay.t)) sDay['stat'].ix[0:(sDay.shape[0]-nFit)] = sDay['stat'][sDay.shape[0]-nFit] t_test = np.linspace(sDay['t'][0],sDay['t'][sDay.shape[0]-1]+sDay.t[nAhead]-sDay.t[0],nLin) predS = pd.DataFrame({'t':t_test},index=[sDay.index[0]+datetime.timedelta(days=x) for x in range(nLin)]) predS['y'] = sDay.y predS['hist'] = sp.interpolate.interp1d(hWeek.t,hWeek.y,kind="cubic")(predS['t']) predS['hist'] = ( (predS['hist']-predS['hist'].min())/(predS['hist'].max()-predS['hist'].min())*x0['hist_adj'] + .5) predS['trend'] = ser_poly(x0['poly'],predS['t']) predS['trend'].ix[0:(sDay.shape[0]-nFit)] = predS['trend'][sDay.shape[0]-nFit] predS['pred'] = 0 predS['lsq'] = 0 # plt.plot(sDay.t,sDay.y,'-',label='series') # plt.plot(sDay.t,sDay['hist'],'-',label='hist') # plt.plot(hWeek.t,hWeek.y,label='week') # plt.plot(sDay.t,sDay['stat'],'-',label='stat') # plt.plot(predS.t,predS['trend'],'-',label='fit') # plt.legend() # plt.show() return predS, x0
def FocusRunResults(): data = np.loadtxt(directory_prefix + 'bahtinov_results/Focusrun/' + today_utc_date + '/Results/FocusResults.txt') image = data[:, 0] defocus = data[:, 1] focus = data[:, 2] focuserr = data[:, 3] xp = np.linspace(min(defocus), max(defocus), 100) z = np.polyfit(defocus, focus, 1) fitobj = kmpfit.Fitter(residuals=functions.linfitresiduals, data=(defocus, focus, focuserr), xtol=1e-12, gtol=1e-12) fitobj.fit(params0=z) print "\n=================== Results linear fit best defocus M2 ===================" print "Fitted parameters: ", fitobj.params print "Covariance errors: ", fitobj.xerror print "Standard errors: ", fitobj.stderr print "Chi^2 min: ", round(fitobj.chi2_min, 2) print "Reduced Chi^2: ", round(fitobj.rchi2_min, 2) print "Iterations: ", fitobj.niter print "Number of free pars.: ", fitobj.nfree print "Degrees of freedom ", fitobj.dof print "Status Message: ", fitobj.message dfdp = [1, xp] confprob = 95.0 ydummy, upperband, lowerband = functions.confidence_band( xp, dfdp, confprob, fitobj, functions.linfit) verts = zip(xp, lowerband) + zip(xp[::-1], upperband[::-1]) bestfocus = -fitobj.params[0] / fitobj.params[1] bestfocusvar = bestfocus**2 * ( (fitobj.stderr[0] / fitobj.params[0])**2 + (fitobj.stderr[1] / fitobj.params[1])**2 - 2 * (fitobj.covar[0, 1] / (fitobj.params[0] * fitobj.params[1]))) fig, axis = plt.subplots() axis.xaxis.set_minor_locator(AutoMinorLocator()) axis.yaxis.set_minor_locator(AutoMinorLocator()) axis.errorbar(defocus, focus, yerr=focuserr, fmt='ko') axis.annotate('Best offset M2 = %.2f $\pm$ %.3f $\\mu m$' % (bestfocus, bestfocusvar**.5), xy=(0, 1), xycoords='axes fraction', fontsize=12, horizontalalignment='left', verticalalignment='top') axis.plot(xp, functions.linfit(fitobj.params, xp), color='r', ls='--', lw=2) axis.set_title('Focus run M2 vs calculated axial defocus', fontsize=14) axis.set_xlabel('Piston M2 [$\mu m$]') axis.set_ylabel('Calculated axial defocus [$\mu m$]') axis.set_xlim(-5, 205) axis.grid(True) #axis.legend(loc=4,fancybox=True, shadow=True, ncol=4, borderpad=1.01) fig.tight_layout() fig.savefig(directory_prefix + 'bahtinov_results/Focusrun/' + today_utc_date + '/Results/Focusrun_defocus.png')
def fit_model(x, y, err, p0, detail='no'): """ fitting a model to a given data Input: data --- input data list of lists [xdata, ydata, error] p0 --- initial guess of the parameters in a list detail --- if you want to print out a detail fitting profile, set "yes'. Default: 'no' Output: fitting parameter [noarmalization, center, sigma, zero level] """ # #--- convert the data to numpy array # d = numpy.array(x) v = numpy.array(y) err = numpy.array(err) # #--- fitting routine starts # fitobj = kmpfit.Fitter(residuals=my_residuals, deriv=my_derivs, data=(d, v, err)) try: fitobj.fit(params0=p0) except Exception, mes: print "Something wrong with fit:", mes raise SystemExit
def gamma_fit(x, y, a0, b0, m0): """ fitting gammaf profile to the data Input: x --- independent var y --- dependent var Output: [a, b] """ N = len(y) x = numpy.array(x) y = numpy.array(y) err = numpy.ones(N) # #--- initial guess # p0 = [a0, b0, m0] # #--- fit the model # try: fitter = kmpfit.Fitter(residuals=residualsG, data=(x, y, err)) #fitter.parinfo = [{}, {}, {'fixed':True}] # Take zero level fixed in fit fitter.fit(params0=p0) a, b, h = fitter.params except: a, b, h = p0 return [a, b, h]
def voigt_fit(x, y): """ fitting voigt profile to the data Input: x --- independent var y --- dependent var Output: [nu_0, hwhm, amp, alphaD, alphaL, nu_0, I, a_back, b_back] nu_0 --- central postion hwhm --- HWHM amp --- amp alphaD --- doppler alpha alphaL --- lorntz alpha I --- area under profile a_back --- base line intercept b_back --- base line slope """ N = len(y) x = numpy.array(x) y = numpy.array(y) err = numpy.ones(N) # #--- initial guess # A = max(y) alphaD = 0.5 alphaL = 0.5 a = 0 b = 0 nu_0 = find_center(x, y) p0 = [alphaD, alphaL, nu_0, A, a, b] # #--- fit the model # fitter = kmpfit.Fitter(residuals=residualsV, data=(x, y, err)) fitter.parinfo = [{}, {}, {}, {}, {}, { 'fixed': True }] # Take zero level fixed in fit fitter.fit(params0=p0) alphaD, alphaL, nu_0, I, a_back, b_back = fitter.params # #--- compute width: HWHM # c1 = 1.0692 c2 = 0.86639 hwhm = 0.5 * (c1 * alphaL + numpy.sqrt(c2 * alphaL**2 + 4 * alphaD**2)) hwhm = 2.0 * hwhm # #--- compute amp # f = numpy.sqrt(ln2) Y = alphaL / alphaD * f amp = I / alphaD * numpy.sqrt(ln2 / numpy.pi) * voigt(0, Y) return [nu_0, hwhm, amp, alphaD, alphaL, I, a_back, b_back]
def fit_line(paramsinit, x, y, err, type): """ kmpfit calling function to fit the lines on data input: paramsinit --- initial guess for the parameters x --- a list of x data y --- a list of y data err --- a list of y error type --- linear or exp: output: two parameters (a, b) are returned """ sx = [] sy = [] se = [] avg = mean(y) stdp = std(y) bot = avg - 3.0 * stdp top = avg + 3.0 * stdp i = 0 for val in y: if (val >= bot) and (val <= top): sx.append(x[i]) sy.append(y[i]) se.append(err[i]) i += 1 # #--- make sure that the arrays are numpyed # d = numpy.array(sx) v = numpy.array(sy) e = numpy.array(se) if type == 'linear': # #--- linear fit # fitobj = kmpfit.Fitter(residuals=linear_res, data=(d, v, e)) fitobj.fit(params0 = paramsinit) else: # #--- exp fit # fitobj = kmpfit.Fitter(residuals=exp_res, data=(d, v, e)) fitobj.fit(params0 = paramsinit) return fitobj.params
def fit_polinom_to_center(fdata, start, stop, action, grating, catg): """ fitting a 5th degree polinomial to the data and find differences input: fdata --- a list of arrays of time and data start --- starting time in seconds from 1998.1.1 stop --- stopping time in seconds from 1998.1.1 action --- movement grating --- grating cag --- catogry (roll/pitch/yaw) output: estimates --- a list of model fitted data diff_data --- a list of difference between themodel and the data f_time --- a list of time for the selected data period sec1,sec2,sec3 --- list of [avg, std] of three sections """ # #--- set fitting range # tdiff = stop - start dstart = -1.5 * tdiff dstop = 1.5 * tdiff # #--- limit data to the fitting range # t_array = fdata[0] v_array = fdata[1] index = [(t_array > dstart) & (t_array < dstop)] f_time = t_array[index] f_data = v_array[index] # #--- fit the data # paraminitial = [0.0 for i in range(0, 5)] fitobj = kmpfit.Fitter(residuals=residuals, data=(f_time, f_data)) try: fitobj.fit(params0=paraminitial) except: print "Something wrong with kmpfit fit" return False # #--- create lists of data of estimated fitting and deviations # [estimates, diff_data] = compute_difference(f_time, f_data, fitobj) # #--- find avg and std of three sections # [sec1, sec2, sec3] = compute_avg_of_three_sections(f_time, diff_data, start, stop) # #--- write out the polinomial fitting result # write_poli_fitting_result(fitobj, start, stop, action, grating, catg) return [estimates, diff_data, f_time, sec1, sec2, sec3]
def fit_model(x, y, err, p0, detail='no'): """ fitting a model to a given data Input: data --- input data list of lists [xdata, ydata, error] p0 --- initial guess of the parameters in a list detail --- if you want to print out a detail fitting profile, set "yes'. Default: 'no' Output: fitting parameter [noarmalization, center, sigma, zero level] """ # #--- convert the data to numpy array # d = numpy.array(x) v = numpy.array(y) err = numpy.array(err) # #--- fitting routine starts # fitobj = kmpfit.Fitter(residuals=my_residuals, deriv=my_derivs, data=(d, v, err)) try: fitobj.fit(params0=p0) except Exception as mes: print("Something wrong with fit:", mes) raise SystemExit # #--- if detail fitting profile is asked, print it out # if detail == 'yes': line = "\n\n======== Results kmpfit with explicit partial derivatives =========" + "\n" line = line + "Params: " + str(fitobj.params) + "\n" line = line + "Errors from covariance matrix : " + str( fitobj.xerror) + "\n" line = line + "Uncertainties assuming reduced Chi^2=1: " + str( fitobj.stderr) + "\n" line = line + "Chi^2 min: " + str(fitobj.chi2_min) + "\n" line = line + "Reduced Chi^2: " + str(fitobj.rchi2_min) + "\n" line = line + "Iterations: " + str(fitobj.niter) + "\n" line = line + "Function ev: " + str(fitobj.nfev) + "\n" line = line + "Status: " + str(fitobj.status) + "\n" line = line + "Status Message:" + str(fitobj.message) + "\n" line = line + "Covariance:\n" + str(fitobj.covar) + "\n" f = open('./kmpfit_info', 'w') f.write(line) f.close() return fitobj.params
def kmp_wrap(center, max_cnt, drange, xdata, ydata, dcnt): """ a wrapper function to use kmpfit input: center --- gaussian center position max_cnt --- gaussinan peak count drange --- width of the data collecting area center +/- drange xdata --- a list of the full sim position data ydata --- a list of the full sim count data dcnt --- a number of data points output: [center position, count rate, width of the peak] """ freturn = [-999, -999, -999, -999, -999, -999] xval = [] yval = [] chk = 0 rmin = int(center - drange) rmax = int(center + drange) for i in range(0, dcnt): if xdata[i] >= rmin and xdata[i] <= rmax: xval.append(xdata[i]) yval.append(ydata[i]) chk += 1 # #--- kmpfit, least squares fitting from kapteyn package # if chk > 0 and max_cnt > 0: try: paramsinitial = (center, max_cnt, 10) fitobj = kmpfit.Fitter(residuals=residuals, data=(xval, yval)) fitobj.fit(params0=paramsinitial) [pos, count, width] = fitobj.params [perr, cerr, werr] = fitobj.xerror return [pos, count, width, perr, cerr, werr] except: return freturn else: return freturn
def kmp_wrap(center, max_cnt, drange, xdata, ydata, dcnt): ''' a wrapper function to use kmpfit input: center: gaussian center position max_cnt: gaussinan peak count drange: width of the data collecting area center +/- drange xdata: full sim position data ydata: full sim count data dcnt: number of data points output: [center position, count rate, width of the peak] ''' xval = [] yval = [] chk = 0 rmin = int(center - drange) rmax = int(center + drange) for i in range(0, dcnt): if xdata[i] >= rmin and xdata[i] <= rmax: xval.append(xdata[i]) yval.append(ydata[i]) chk += 1 # #--- kmpfit, least squares fitting from kapteyn package # if chk > 0 and max_cnt > 0: paramsinitial = (center, max_cnt, 10) fitobj = kmpfit.Fitter(residuals=residuals, data=(xval, yval)) fitobj.fit(params0=paramsinitial) [pos, count, width] = fitobj.params else: pos = -999 count = -999 width = -999 return [pos, count, width]
def fitZshape(x,y,err) : A = 0.5 alphaD = 1.4 alphaL = 2.5/2 a = 0.001 b = 0 nu_0 = 91.2 p0 = [alphaD, alphaL, nu_0, A, a, b] # Do the fit fitter = kmpfit.Fitter(residuals=residualsV, data=(x,y,err)) # fitter.parinfo = [{}, {}, {}, {}, {}, {'fixed':True}] # Take zero level fixed in fit fitter.parinfo = [{}, {'fixed':True}, {}, {}, {}, {}] fitter.fit(params0=p0) print "\n========= Fit results Voigt profile ==========" print "Initial params:", fitter.params0 print "Params: ", fitter.params print "Iterations: ", fitter.niter print "Function ev: ", fitter.nfev print "Uncertainties: ", fitter.xerror print "dof: ", fitter.dof print "chi^2, rchi2: ", fitter.chi2_min, fitter.rchi2_min print "stderr: ", fitter.stderr print "Status: ", fitter.status alphaD, alphaL, nu_0, I, a_back, b_back = fitter.params c1 = 1.0692 c2 = 0.86639 hwhm = 0.5*(c1*alphaL+np.sqrt(c2*alphaL**2+4*alphaD**2)) print "\nFWHM Voigt profile: ", 2*hwhm f = np.sqrt(ln2) Y = alphaL/alphaD * f amp = I/alphaD*np.sqrt(ln2/np.pi)*voigt(0,Y) print "Amplitude Voigt profile:", amp print "Area under profile: ", I return fitter.params
# Here one can experiment with errors on the measured values err0 = numpy.zeros(N0) + normal(190.0, 1.0, N0) # Mean 200, sigma 1 # Hubble space telescope 2009: H0 = 74.2 +- 3.6 (km/s)/Mpc. H0_last = 74.2 # Filter possible outliers based on Chauvenet's criterion # Use the current literature value of the Hubble constant # to create a line which is used as a base to calculate # deviations. These offsets are distributed normally and we can # apply Chauvenet's criterion to filter outliers. print("\nPre filtering:") print("=================") paramsinitial = [70.0] fitobj = kmpfit.Fitter(residuals=residuals, data=(d0, v0, err0)) fitobj.fit(params0=paramsinitial) H0_fit0 = fitobj.params[0] H0_fit0_delta = fitobj.stderr print("H0 with unfiltered data: ", H0_fit0) # If you want to know which data would have been excluded if # you had a perfect fit with H0 = Ho_last, then use: mean = H0_last*d mean = H0_fit0 * d0 # Use expression below for unit weighting. Otherwise use # the errors in the data as standard deviations. # stdv = numpy.sqrt(((v0-mean)**2).sum()/(N0)) stdv = err0 filter = chauvenet(d0, v0, mean=mean, stdv=stdv) print("Excluded data based on Chauvenet's criterion:", list(zip(d0[~filter], v0[~filter])))
def vertprofile(datafnme=(u'', ), work_dir=(u'', ), header=(1, ), struct=([1, 2, 3, 4], ), labelx=u'to be completed', labely=u'to be completed', labeldata=(u'Data', ), rangex=None, rangey=None, statstypes=[0, 1, 2, 3], confprob=95.0, fontsz=10, fontleg=9, output='graph'): """ This code is to compute regressions for points with their error using different regression methods USAGE >>>from vertprof import vertprofile >>>vertprofile(datafnme = u'', work_dir = u'', header = 1, struct = [1,2,3,4], labelx = 'to be completed', labely = 'to be completed', rangex = None, rangey = None, statstypes = [0,1,2,3], confprob = 95.0, fontsz = 10, fontleg = 9, output = 'graph') INPUTS To use options or inputs, you need to set them as vertprof(option_name = option_value, [...]) 1. work_dir: tuple (i.e. (u'data1 workdir',u'data2 workdir',...) of the Working directory(-ies) (local path) for each dataset ex: work_dir = (u'Purgatorio3/',) (note the (,) structure if there is only one dataset to plot Default None 2. datafnme: tuple (i.e. (u'data1 name ',u'data2 name',...) of the name(s) of text data file should be in the form : Alt - Age - Age_Error ex: datafnme = 'Purgatorio3.txt' 3. header: tuple of the number of lines of the header in the data for each dataset ex: header = (1,) (Default) 4. struct: tuple of the structure of the data for each dataset Struct = ([Xdata, Xerr, Ydata, Yerr],) where Xdata, Xerr, Ydata, Yerr give their respective columns in the data file If one of the data type do not exist, set the corresponding column to NONE ex : struct = ([1,2,3,4],) (Default) 5. output: name of output ex: output = 'graph' (Default) 6. labelx/labely: label x-axis/y-axis ex: labelx = 'Exposure age (ka)' labely ='Distance to the top of the scarp (m)' 7. labeldata: tuple (i.e. (u'data1 label',u'data2 label',...) with the name of the type of data for each dataset plotted default = (u'Data',) 8. rangex/rangey: Set the x- and y-range Depends on type of data ex: rangex = [0,8] rangey = [10,4] (in that case, the axis is inverted) 9. statstypes: Type(s) of the stats to plot 0 = kmpfit effective variance 1 = kmpfit unweighted 2 = Williamson 3 = Cl relative weighting in X &/or Y ex: statstype = [0,1,2,3] (Default) statstype = [1,3] 10. fontsz: labels fontsize ex: fontsz = 10 (Default) 11. fontleg: legend fontsize ex: fontleg = 9 (Default) 12. confprob: the confidence interval probabilty (in %) ex: confprob = 95.0 (Default) OUTPUTS For each dataset, the module outputs a pdf graph, and a text file with the stats outputs for each method asked CONTACT If needed, do not hesitate to contact the author. Please, use https://isterre.fr/spip.php?page=contact&id_auteur=303 LICENCE This package is licenced with `CCby-nc-sa` (https://creativecommons.org/licenses/by-nc-sa/2.0/) """ # set colors # For the moment, only for 6 datasets, it should be enough colors = ['b', 'darkorange', 'peru', 'black', 'darkviolet', 'green'] # initiate variables erry = errx = a_will = b_will = verts = fitobj = fitobj2 = fitobj3 = None # Tuples to lists datafnme = list(datafnme) work_dir = list(work_dir) header = list(header) struct = list(struct) labeldata = list(labeldata) # Initiate the plotting plt.rc(u'font', size=fontsz) #plt.rc(u'title', size = fontsz) plt.rc(u'legend', fontsize=fontleg) # Open figure plt.figure(1).clear #plt.add_subplot(1,1,1, aspect=1, adjustable=u'datalim') # If the minima input data are not given print the help file if not datafnme: help(vertprofile) raise TypeError(color.RED + u'ERROR : ' + color.END + u'Name of Input file not given...') # check if the length of work_dir, struct and labeldata are equal to the length of datafnme # If not, copy the first record to the others, with a warning for item in [work_dir, header, struct, labeldata]: if len(datafnme) != len(item): warnings.warn( color.YELLOW + u"\nWARNING : " + color.END + u"work_dir, header, struct and/or labeldata may be the same for all dataset" ) #item = (item[0]) for i_data in range(1, len(datafnme)): item = item.append(item[0]) #item[i_data] = item[0] # do a loop on the number of dataset to plot for i_data in range(0, len(datafnme)): # check if the working directory exists, if not, create it if work_dir[i_data].strip(): if work_dir[i_data][-1:] != u'/': work_dir[i_data] = work_dir[i_data] + u'/' if path.exists(work_dir[i_data]) == False: os.mkdir(work_dir[i_data]) else: warnings.warn( color.YELLOW + u"\nWARNING : " + color.END + u"Working directory already exists and will be erased\n") # Check if the file exists in the main folder # if not, ckeck in the working folder # if only in the working folder, copy it to the main folder if not path.isfile(datafnme[i_data]): if not path.isfile(work_dir[i_data] + datafnme[i_data]): #sys.exit(color.RED + u"ERROR : " + color.END + u"Input file %s does not exist..." % datafnme) raise NameError(color.RED + u"ERROR : " + color.END + u"Input file %s does not exist..." % datafnme[i_data]) else: copyfile(work_dir[i_data] + datafnme[i_data], datafnme[i_data]) if not path.isfile(work_dir[i_data] + datafnme[i_data]): copyfile(datafnme[i_data], work_dir[i_data] + datafnme[i_data]) datapath = work_dir[i_data] + datafnme[i_data] else: if not path.isfile(work_dir[i_data] + datafnme[i_data]): #sys.exit(color.RED + u"ERROR : " + color.END + u"Input file %s does not exist..." % datafnme) raise NameError(color.RED + u"ERROR : " + color.END + u"Input file %s does not exist..." % datafnme[i_data]) else: datapath = datafnme[i_data] work_dir[i_data] = u'' # read data data = np.loadtxt(datapath, skiprows=header[i_data]) y = data[:, struct[i_data][0] - 1] if struct[i_data][1] != 0 and struct[i_data][1] != None: erry = data[:, struct[i_data][1] - 1] else: erry = 0 x = data[:, struct[i_data][2] - 1] if struct[i_data][3] != 0 and struct[i_data][3] != None: errx = data[:, struct[i_data][3] - 1] else: errx = 0 N = len(x) # Open new file to print the results f1w = open(work_dir[i_data] + u'results_' + datafnme[i_data], 'w') string = ' ' print(string) f1w.write(string + u"\n") string = ' ' print(string) f1w.write(string + u"\n") string = ' ' print(string) f1w.write(string + u"\n") string = u' Dataset ' + labeldata[i_data] print(color.RED + color.BOLD + string + color.END) f1w.write(string + u"\n") string = u"Results of weigthed least square from file " + datafnme[ i_data] + u"\n" print(color.RED + color.BOLD + string + color.END) f1w.write(string + u"\n") string = u"xmax/min = " + str(x.max()) + u", " + str(x.min()) print(string) f1w.write(string + u"\n") string = u"ymax/min = " + str(y.max()) + u", " + str(y.min()) print(string) f1w.write(string + u"\n") string = u"x/y mean = " + str(x.mean()) + u", " + str(y.mean()) print(string) f1w.write(string + u"\n") string = ( u"\nMethods used are: \n" + u" - kmpfit: kapteyn method, from " + u"https://www.astro.rug.nl/software/kapteyn/kmpfittutorial.html \n" + u" with error on X and Y or Y only or none \n" + u" - ODR: Orthogonal Distance Regression \n" + u" - Williamson: least square fitting with errors in X and Y " + u"according to \n" + u" Williamson (Canadian Journal of Physics, 46, 1845-1847, 1968) \n" ) print(color.CYAN + string + color.END) f1w.write(string) beta0 = [5.0, 1.0] # Initial estimates if struct[i_data][3] != 0 and struct[i_data][3] != None: if struct[i_data][1] != 0 or struct[i_data][1] != None: # Prepare fit routine fitobj = kmpfit.Fitter(residuals=residuals, data=(x, y, errx, erry)) fitobj.fit(params0=beta0) string = ( u"\n\n======== Results kmpfit: weights for both coordinates =========" ) print(color.BLUE + color.BOLD + string + color.END) f1w.write(string + "\n") string = ( u"Fitted parameters: " + str(fitobj.params) + u"\n" u"Covariance errors: " + str(fitobj.xerror) + u"\n" u"Standard errors " + str(fitobj.stderr) + u"\n" u"Chi^2 min: " + str(fitobj.chi2_min) + u"\n" u"Reduced Chi^2: " + str(fitobj.rchi2_min) + u"\n" u"Iterations: " + str(fitobj.niter)) print(string) f1w.write(string + u"\n") else: # Prepare fit routine fitobj2 = kmpfit.Fitter(residuals=residuals2, data=(x, y, erry)) fitobj2.fit(params0=beta0) string = ( u"\n\n======== Results kmpfit errors in Y only =========") print(color.BLUE + color.BOLD + string + color.END) f1w.write(string + u"\n") string = ( u"Fitted parameters: " + str(fitobj2.params) + u"\n" u"Covariance errors: " + str(fitobj2.xerror) + u"\n" u"Standard errors " + str(fitobj2.stderr) + u"\n" u"Chi^2 min: " + str(fitobj2.chi2_min) + u"\n" u"Reduced Chi^2: " + str(fitobj2.rchi2_min)) print(string) f1w.write(string) # Unweighted (unit weighting) fitobj3 = kmpfit.Fitter(residuals=residuals2, data=(x, y, np.ones(N))) fitobj3.fit(params0=beta0) string = (u"\n\n======== Results kmpfit unit weighting =========") print(color.BLUE + color.BOLD + string + color.END) f1w.write(string + "\n") string = (u"Fitted parameters: " + str(fitobj3.params) + u"\n" u"Covariance errors: " + str(fitobj3.xerror) + u"\n" u"Standard errors " + str(fitobj3.stderr) + u"\n" u"Chi^2 min: " + str(fitobj3.chi2_min) + u"\n" u"Reduced Chi^2: " + str(fitobj3.rchi2_min)) print(string) f1w.write(string) # Compare result with ODR # Create the linear model from statsfuncs linear = Model(model) if struct[i_data][3] != 0 and struct[i_data][3] != None: if struct[i_data][1] != 0 and struct[i_data][1] != None: mydata = RealData(x, y, sx=errx, sy=erry) else: mydata = RealData(x, y, sy=erry) else: mydata = RealData(x, y) myodr = ODR(mydata, linear, beta0=beta0, maxit=5000, sstol=1e-14) myoutput = myodr.run() string = (u"\n\n======== Results ODR =========") print(color.BLUE + color.BOLD + string + color.END) f1w.write(string + u"\n") string = (u"Fitted parameters: " + str(myoutput.beta) + u"\n" u"Covariance errors: " + str(np.sqrt(myoutput.cov_beta.diagonal())) + u"\n" u"Standard errors: " + str(myoutput.sd_beta) + u"\n" u"Minimum chi^2: " + str(myoutput.sum_square) + u"\n" u"Minimum (reduced)chi^2: " + str(myoutput.res_var)) print(string) f1w.write(string) # Compute Williamson regression a_will, b_will, siga, sigb, beta, x_av, x__mean = williamson( x, y, errx, erry, struct[i_data], myoutput) if struct[i_data][3] != 0 and struct[i_data][3] != None: if struct[i_data][1] != 0 and struct[i_data][1] != None: chi2 = (residuals(fitobj.params, (x, y, errx, erry))**2).sum() else: chi2 = (residuals2(fitobj2.params, (x, y, erry))**2).sum() else: chi2 = (residuals2(fitobj3.params, (x, y, np.ones(N)))**2).sum() string = (u"\n\n======== Results Williamson =========") print(color.BLUE + color.BOLD + string + color.END) f1w.write(string + u"\n") string = (u"Average x weighted: " + str(x_av) + u"\n" u"Average x unweighted: " + str(x__mean) + u"\n" u"Fitted parameters: " + u"[" + str(a_will) + u"," + str(b_will) + u"]\n" u"Covariance errors: " + u"[" + str(siga) + u"," + str(sigb) + u"]\n" u"Minimum chi^2: " + str(chi2)) print(string) f1w.write(string) string = ( u"\n=====================================" u"\nPractical results: a + b * x" ) print(color.BLUE + color.BOLD + string + color.END) f1w.write(u"\n" + string + u"\n") string = (u"kmpfit unweighted: %13.4f %13.4f" % (fitobj3.params[0], fitobj3.params[1])) print(string) f1w.write(string + u"\n") string = (u" Exhumation Rate: %13.4f" % (1 / fitobj3.params[1])) print(string) f1w.write(string + u"\n") string = (u" Min. Exh. Rate: %13.4f" % (1 / (fitobj3.params[1] - np.sqrt(fitobj3.stderr[1])))) print(string) f1w.write(string + u"\n") string = (u" Max. Exh. Rate: %13.4f" % (1 / (fitobj3.params[1] + np.sqrt(fitobj3.stderr[1])))) print(string) f1w.write(string + "\n") if struct[i_data][3] != 0 and struct[i_data][3] != None: if struct[i_data][1] != 0 and struct[i_data][1] != None: string = u"kmpfit effective variance: %13.4f %13.4f" % ( fitobj.params[0], fitobj.params[1]) print(string) f1w.write(string + u"\n") string = (u" Exhumation Rate: %13.4f" % (1 / fitobj.params[1])) print(string) f1w.write(string + u"\n") string = (u" Min. Exh. Rate: %13.4f" % (1 / (fitobj.params[1] - np.sqrt(fitobj.stderr[1])))) print(string) f1w.write(string + u"\n") string = (u" Max. Exh. Rate: %13.4f" % (1 / (fitobj.params[1] + np.sqrt(fitobj.stderr[1])))) print(string) f1w.write(string + u"\n") else: string = u"kmpfit weights in Y only: %13.4f %13.4f" % ( fitobj2.params[0], fitobj2.params[1]) print(string) f1w.write(string + u"\n") string = (u" Exhumation Rate: %13.4f" % (1 / fitobj2.params[1])) print(string) f1w.write(string + u"\n") string = (u" Min. Exh. Rate: %13.4f" % (1 / (fitobj2.params[1] - np.sqrt(fitobj2.stderr[1])))) print(string) f1w.write(string + u"\n") string = (u" Max. Exh. Rate: %13.4f" % (1 / (fitobj2.params[1] + np.sqrt(fitobj2.stderr[1])))) print(string) f1w.write(string + u"\n") string = u"ODR: %13.4f %13.4f" % (beta[0], beta[1]) print(string) f1w.write(string + u"\n") string = (u" Exhumation Rate: %13.4f" % (1 / beta[1])) print(string) f1w.write(string + u"\n") string = (u" Min. Exh. Rate: %13.4f" % (1 / (beta[1] - np.sqrt(myoutput.sd_beta[1])))) print(string) f1w.write(string + u"\n") string = (u" Max. Exh. Rate: %13.4f" % (1 / (beta[1] + np.sqrt(myoutput.sd_beta[1])))) print(string) f1w.write(string + u"\n") string = u"Williamson: %13.4f %13.4f" % (a_will, b_will) print(string) f1w.write(string + u"\n") string = (u" Exhumation Rate: %13.4f" % (1 / b_will)) print(string) f1w.write(string + u"\n") # For the next lines, not sure that we have to use the chi2 as error... string = (u" Min. Exh. Rate: %13.4f" % (1 / (b_will - chi2))) print(string) f1w.write(string + u"\n") string = (u" Max. Exh. Rate: %13.4f" % (1 / (b_will + chi2))) print(string) f1w.write(string + u"\n") print(u"\n") # calcul of confidence intervals dfdp = [1, x, x**2] if struct[i_data][3] != 0 and struct[i_data][3] != None: if struct[i_data][1] != 0 and struct[i_data][1] != None: ydummy, upperband, lowerband = confidence_band( x, dfdp, confprob, fitobj, model) labelconf = u"CI (" + str( confprob) + u"%) relative weighting in X & Y" if i_data == 0: #string = (u"y = a + b * x with a = %6.4f +/- %6.4f and b = %6.4f +/- %6.4f " #stringl = (u"y_" + labeldata[i_data] + u" = a + b * x with a = %.2f +/- %.2f and b = %.2f +/- %.2f " #stringl = (u" y_" + labeldata[i_data] + u" = a + b * x with a = %.2f +/- %.2f and b = %.2f +/- %.2f " # %(fitobj.params[0], np.sqrt(fitobj.stderr[0]), # fitobj.params[1], np.sqrt(fitobj.stderr[1]))) stringl = ( r" $\mathbf{Y_{%s}} = \mathbf{a} + \mathbf{b} \times \mathbf{X}$ with $\mathbf{a} = %.2f \pm %.2f$ and $\mathbf{b} = %.2f \pm %.2f$ " % (labeldata[i_data], fitobj.params[0], np.sqrt(fitobj.stderr[0]), fitobj.params[1], np.sqrt(fitobj.stderr[1]))) else: #string = (u"y = a + b * x with a = %6.4f +/- %6.4f and b = %6.4f +/- %6.4f " stringl = stringl + "\n" + ( r"$\mathbf{Y_{%s}} = \mathbf{a} + \mathbf{b} \times \mathbf{X}$ with $\mathbf{a} = %.2f \pm %.2f$ and $\mathbf{b} = %.2f \pm %.2f$ " % (labeldata[i_data], fitobj.params[0], np.sqrt(fitobj.stderr[0]), fitobj.params[1], np.sqrt(fitobj.stderr[1]))) else: ydummy, upperband, lowerband = confidence_band( x, dfdp, confprob, fitobj2, model) labelconf = u"CI (" + str( confprob) + u"%) relative weighting in Y" if i_data == 0: #string = (u"y = a + b * x with a = %6.4f +/- %6.4f and b = %6.4f +/- %6.4f " stringl = ( r"$\mathbf{Y_{%s}} = \mathbf{a} + \mathbf{b} \times \mathbf{X}$ with $\mathbf{a} = %.2f \pm %.2f$ and $\mathbf{b} = %.2f \pm %.2f$ " % (labeldata[i_data], fitobj2.params[0], np.sqrt(fitobj2.stderr[0]), fitobj2.params[1], np.sqrt(fitobj2.stderr[1]))) else: #string = (u"y = a + b * x with a = %6.4f +/- %6.4f and b = %6.4f +/- %6.4f " stringl = stringl + "\n" + ( r"$\mathbf{Y_{%s}} = \mathbf{a} + \mathbf{b} \times \mathbf{X}$ with $\mathbf{a} = %.2f \pm %.2f$ and $\mathbf{b} = %.2f \pm %.2f$ " % (labeldata[i_data], fitobj2.params[0], np.sqrt(fitobj2.stderr[0]), fitobj2.params[1], np.sqrt(fitobj2.stderr[1]))) else: ydummy, upperband, lowerband = confidence_band( x, dfdp, confprob, fitobj3, model) labelconf = u"CI (" + str(confprob) + u"%) with no weighting" if i_data == 0: #string = (u"y = a + b * x with a = %6.4f +/- %6.4f and b = %6.4f +/- %6.4f " stringl = ( r"$\mathbf{y_{%s}} = \mathbf{a} + \mathbf{b} \times x$ with $\mathbf{a} = %.2f \pm %.2f$ and $\mathbf{b} = %.2f \pm %.2f$ " % (labeldata[i_data], fitobj3.params[0], np.sqrt(fitobj3.stderr[0]), fitobj3.params[1], np.sqrt(fitobj3.stderr[1]))) else: #string = (u"y = a + b * x with a = %6.4f +/- %6.4f and b = %6.4f +/- %6.4f " stringl = stringl + "\n" + ( r"$\mathbf{Y_{%s}} = \mathbf{a} + \mathbf{b} \times \mathbf{X}$ with $\mathbf{a} = %.2f \pm %.2f$ and $\mathbf{b} = %.2f \pm %.2f$ " % (labeldata[i_data], fitobj3.params[0], np.sqrt(fitobj3.stderr[0]), fitobj3.params[1], np.sqrt(fitobj3.stderr[1]))) #verts = zip(x, lowerband) + zip(x[::-1], upperband[::-1]) # Because we need to invert X and Y for the graph verts = list(zip(lowerband, x)) + list(zip(upperband[::-1], x[::-1])) # Close output file f1w.close() #if rangex: # X = np.linspace(rangex[0], rangex[1], 50) #else: # d = (x.max() - x.min())/10 # X = np.linspace(x.min()-d, x.max()+d, 50) #if rangey: # Y = np.linspace(rangey[0], rangey[1], 50) #else: # d = (y.max() - y.min())/10 # Y = np.linspace(y.min()-d, y.max()+d, 50) # Call the plotting function #axes = plotgraphreg(struct[i_data], x, y, errx, erry, X, Y, axes = plotgraphreg(struct[i_data], x, y, errx, erry, colors[i_data], labeldata[i_data], statstypes, a_will, b_will, verts, confprob, fitobj, fitobj2, fitobj3) # Set graph characteristics/attributes plt.xlabel(labelx) plt.ylabel(labely) plt.grid(True) plt.title(stringl, size=fontsz) # clean the legend from duplicates handles, labels = plt.gca().get_legend_handles_labels() by_label = OrderedDict(zip(labels, handles)) plt.legend(by_label.values(), by_label.keys(), loc="best") # set the X and Y limits if rangex: axes.set_xlim([rangex[0], rangex[1]]) if rangey: axes.set_ylim(bottom=rangey[0], top=rangey[1]) plt.savefig(work_dir[0] + output + u'.pdf') plt.close()
fr = len(dat2[dat2 <= yy]) / float(n) cdfnew.append(fr) return numpy.asarray(cdfnew) # Create data N = 30 x = numpy.linspace(-5, 10, N) # Parameters: A, mu, sigma, zerolev truepars = [10.0, 4.0, 2.5, 0.0] p0 = [10, 4.5, 0.8, 0] y = func(truepars, x) + numpy.random.normal(0, 0.8, N) err = numpy.random.normal(0.0, 0.6, N) # Do the fit fitter = kmpfit.Fitter(residuals=residuals, data=(x, y, err)) #fitter.parinfo = [{}, {}, {}, {'fixed':True}] # Take zero level fixed in fit fitter.fit(params0=p0) if (fitter.status <= 0): print("Status: ", fitter.status) print('error message = ', fitter.errmsg) raise SystemExit print("\n========= Fit results ==========") print("Initial params:", fitter.params0) print("Params: ", fitter.params) print("Iterations: ", fitter.niter) print("Function ev: ", fitter.nfev) print("Uncertainties: ", fitter.xerror) print("dof: ", fitter.dof)
def gauss_hermite_fit(data, p0, plot_op='no', xname='X', yname='Cnts', tname='Voigt Fit', xmin='na', xmax='na', ymin='na', ymax='na', detail='no'): """ control function of Gauss-Hermite fitting Input: data --- data list of lists [x, y, err] p0 = --- parameter list: [A1, X1, S1, h31, h41, z01] A1: area covered X1: center position S1: h31: h41: zo1: plot_op --- if yes, the script will plot. default: no xname --- the name of x axis yname --- the name of y axis tname --- title of the plot xmin --- lower boundary in x of the plot xmax --- upper boundray in x of the plot ymin --- lower boundary in y of the plot ymax --- upper boundray in y of the plot detail --- if yes, it will print fitting profiles. default: no Output: param: [A1, X1, S1, h31, h41, z01, height, center, width, floor] if plot is asked: out.png if proflie is asked: gh_fitting_profile """ x, y, err = data # #--- convert the list ot numpy array # x = numpy.array(x) y = numpy.array(y) err = numpy.array(err) # #---- Fit the Gaussian model # [A1, X1, S1, h31, h41, z01] = p0 pg = [A1, X1, S1, z01] #--- approximate the initial values using GH initial estimates fitterG = kmpfit.Fitter(residuals=residualsG, data=(x, y, err)) fitterG.fit(params0=pg) if detail == 'yes': line = "\n========= Fit results Gaussian profile ==========\n\n" line = line + "Initial params:" + str(fitterG.params0) + "\n" line = line + "Params: " + str(fitterG.params) + "\n" line = line + "Iterations: " + str(fitterG.niter) + "\n" line = line + "Function ev: " + str(fitterG.nfev) + "\n" line = line + "Uncertainties: " + str(fitterG.xerror) + "\n" line = line + "dof: " + str(fitterG.dof) + "\n" line = line + "chi^2, rchi2: " + str(fitterG.chi2_min) + ' ' + str( fitterG.rchi2_min) + "\n" line = line + "stderr: " + str(fitterG.stderr) + "\n" line = line + "Status: " + str(fitterG.status) + "\n" fwhmG = 2 * numpy.sqrt(2 * numpy.log(2)) * fitterG.params[2] line = line + "FWHM Gaussian: " + str(fwhmG) + "\n" z0G = fitterG.params0[-1] # Store background # #--- Fit the Gauss-Hermite model # #--- Initial estimates for A, xo, s, h3, h4, z0 # fitterGH = kmpfit.Fitter(residuals=residualsGH, data=(x, y, err)) # fitterGH.parinfo = [{}, {}, {}, {}, {}] # Take zero level fixed in fit fitterGH.fit(params0=p0) if detail == 'yes': line = line + "\n\n========= Fit results Gaussian-Hermite profile ==========\n\n" line = line + "Initial params:" + str(fitterGH.params0) + "\n" line = line + "Params: " + str(fitterGH.params) + "\n" line = line + "Iterations: " + str(fitterGH.niter) + "\n" line = line + "Function ev: " + str(fitterGH.nfev) + "\n" line = line + "Uncertainties: " + str(fitterGH.xerror) + "\n" line = line + "dof: " + str(fitterGH.dof) + "\n" line = line + "chi^2, rchi2: " + str(fitterGH.chi2_min) + ' ' + str( fitterGH.rchi2_min) + "\n" line = line + "stderr: " + str(fitterGH.stderr) + "\n" line = line + "Status: " + str(fitterGH.status) + "\n" A, x0, s, h3, h4, z0GH = fitterGH.params # #--- xm, ampmax, area, mean, dispersion, skewness, kurtosis # res = hermite2gauss(fitterGH.params[:-1], fitterGH.stderr[:-1]) line = line + "Gauss-Hermite max=%g at x=%g\n" % (res['amplitude'], res['xmax']) line = line + "Area :" + str( res['area']) + ' ' + str('+-') + ' ' + str(res['d_area']) + "\n" line = line + "Mean (X0) :" + str( res['mean']) + ' ' + str('+-') + ' ' + str(res['d_mean']) + "\n" line = line + "Dispersion:" + str( res['dispersion']) + ' ' + str('+-') + ' ' + str( res['d_dispersion']) + "\n" line = line + "Skewness :" + str( res['skewness']) + ' ' + str('+-') + ' ' + str( res['d_skewness']) + "\n" line = line + "Kurtosis :" + str( res['kurtosis']) + ' ' + str('+-') + ' ' + str( res['d_kurtosis']) + "\n" f = open('gh_fitting_profile', 'w') f.write(line) f.close() # #--- Plot the result # if plot_op == 'yes': rc('legend', fontsize=6) fig = figure() frame1 = fig.add_subplot(1, 1, 1) if xmax != 'na': frame1.set_xlim(xmin=xmin, xmax=xmax, auto=False) frame1.set_ylim(ymin=ymin, ymax=ymax, auto=False) xd = numpy.linspace(x.min(), x.max(), 500) frame1.plot(x, y, 'bo', label="data") label = "Model with Gaussian function" frame1.plot(xd, funcG(fitterG.params, xd), 'm', ls='--', label=label) label = "Model with Gauss-Hermite function" frame1.plot(xd, funcGH(fitterGH.params, xd), 'b', label=label) frame1.plot(xd, [z0G] * len(xd), "y", ls="-.", label='Background G') frame1.plot(xd, [z0GH] * len(xd), "y", ls="--", label='Background G-H') frame1.set_xlabel(xname) frame1.set_ylabel(yname) t = (res['area'], res['mean'], res['dispersion'], res['skewness'], res['kurtosis']) title = tname + " GH: $\gamma_{gh}$=%.1f $\mu_{gh}$=%.1f $\sigma_{gh}$ = %.2f $\\xi_1$=%.2f $\\xi_f$=%.2f" % t frame1.set_title(title, fontsize=9) frame1.grid(True) leg = frame1.legend(loc=1) # #--- set the size of the plotting area in inch (width: 10.0in, height 5.0in) # fig = mpl.pyplot.gcf() fig.set_size_inches(10.0, 5.0) # #--- save the plot in png format # fig.savefig('out.png', format='png', dpi=100) # #--- returning parameters # [A1, X1, S1, h31, h41, z01] = fitterGH.params [height, center, width, floor] = fitterG.params return [A1, X1, S1, h31, h41, z01, height, center, width, floor]
Before fitting we will sample the chisquare plane to make a first guess of 'p0'. This will be the sample for which χ2 is minimal. """ Ns = 200 def chi2(p, *data): return np.sum(residuals(p, data)**2) prange = ((-np.pi, np.pi), (0, np.pi)) p0, fval, ϕθ, χ2 = brute(chi2, ranges=prange, args=data, Ns=200, full_output=True, workers=-1) fitobj = kmpfit.Fitter(residuals) fitobj.data = data fitobj.params0 = p0 #we don't impose any limits on the parameter space as that would cause branch cuts fitobj.fit() #Below we phase shift the results such that -π < ϕ < π and 0 < θ < π. #phase shift ϕ if fitobj.params[0] < 0: N = fitobj.params[0] // -np.pi fitobj.params = np.array( [fitobj.params[0] + 2 * np.pi * N, fitobj.params[1]]) elif fitobj.params[0] > 0: N = fitobj.params[0] // np.pi fitobj.params = np.array( [fitobj.params[0] - 2 * np.pi * N, fitobj.params[1]])
a_pearson = y_av - b_pearson*x_av print("Best fit parameters: a=%.10f b=%.10f"%(a_pearson,b_pearson)) rxy = Sxy/numpy.sqrt(Sxx*Syy) print("Pearson's Corr. coef: ", rxy) tan2theta = 2*rxy*numpy.sqrt(Sxx*Syy)/(Sxx-Syy) twotheta = numpy.arctan(tan2theta) print("Pearson's best tan2theta, theta, slope: ", \ tan2theta, 0.5*twotheta, numpy.tan(0.5*twotheta)) b1 = rxy*numpy.sqrt(Syy)/numpy.sqrt(Sxx) print("b1 (Y on X), slope: ", b1, b1) b2 = rxy*numpy.sqrt(Sxx)/numpy.sqrt(Syy) print("b2 (X on Y), slope", b2, 1/b2) # Prepare fit routine fitobj = kmpfit.Fitter(residuals=residuals, data=(x, y)) fitobj.fit(params0=beta0) print("\n======== Results kmpfit: effective variance =========") print("Params: ", fitobj.params[0], numpy.tan(fitobj.params[1])) print("Covariance errors: ", fitobj.xerror) print("Standard errors ", fitobj.stderr) print("Chi^2 min: ", fitobj.chi2_min) print("Reduced Chi^2: ", fitobj.rchi2_min) # Prepare fit routine fitobj2 = kmpfit.Fitter(residuals=residuals2, data=(x, y)) fitobj2.fit(params0=beta0) print("\n======== Results kmpfit Y on X =========") print("Params: ", fitobj2.params) print("Covariance errors: ", fitobj2.xerror) print("Standard errors ", fitobj2.stderr)
print("\nODR:") print("==========") from scipy.odr import Data, Model, ODR, RealData, odr_stop linear = Model(model) mydata = RealData(x, y, sx=errx, sy=erry) myodr = ODR(mydata, linear, beta0=beta0, maxit=5000) myoutput = myodr.run() print("Fitted parameters: ", myoutput.beta) print("Covariance errors: ", numpy.sqrt(myoutput.cov_beta.diagonal())) print("Standard errors: ", myoutput.sd_beta) print("Minimum chi^2: ", myoutput.sum_square) print("Minimum (reduced)chi^2: ", myoutput.res_var) beta = myoutput.beta # Prepare fit routine fitobj = kmpfit.Fitter(residuals=residuals, data=(x, y, errx, erry)) fitobj.fit(params0=beta0) print("\n\n======== Results kmpfit with effective variance =========") print("Fitted parameters: ", fitobj.params) print("Covariance errors: ", fitobj.xerror) print("Standard errors: ", fitobj.stderr) print("Chi^2 min: ", fitobj.chi2_min) print("Reduced Chi^2: ", fitobj.rchi2_min) print("Status Message:", fitobj.message) # Compare to a fit with weights for y only fitobj2 = kmpfit.Fitter(residuals=residuals2, data=(x, y, erry)) fitobj2.fit(params0=beta0) print("\n\n======== Results kmpfit errors in Y only =========") print("Fitted parameters: ", fitobj2.params) print("Covariance errors: ", fitobj2.xerror)
elif i == 3: pderiv[3] = 1.0 pderiv /= -err return pderiv # Artificial data N = 100 x = numpy.linspace(-5, 10, N) truepars = [10.0, 5.0, 1.0, 0.0] p0 = [9, 4.5, 0.8, 0] y = my_model(truepars, x) + 0.3*numpy.random.randn(len(x)) err = 0.3*numpy.random.randn(N) # The fit fitobj = kmpfit.Fitter(residuals=my_residuals, deriv=my_derivs, data=(x, y, err)) try: fitobj.fit(params0=p0) except Exception as mes: print("Something wrong with fit: ", mes) raise SystemExit print("\n\n======== Results kmpfit with explicit partial derivatives =========") print("Params: ", fitobj.params) print("Errors from covariance matrix : ", fitobj.xerror) print("Uncertainties assuming reduced Chi^2=1: ", fitobj.stderr) print("Chi^2 min: ", fitobj.chi2_min) print("Reduced Chi^2: ", fitobj.rchi2_min) print("Iterations: ", fitobj.niter) print("Function ev: ", fitobj.nfev) print("Status: ", fitobj.status)
def residuals(p, my_arrays): x, y, err = my_arrays a, b = p return (y - model(p, x)) / err x = numpy.array([1.0, 2, 3, 4, 5, 6, 7]) y = numpy.array([6.9, 11.95, 16.8, 22.5, 26.2, 33.5, 41.0]) N = len(y) err = numpy.ones(N) errw = numpy.array([0.05, 0.1, 0.2, 0.5, 0.8, 1.5, 4.0]) print("Data x:", x) print("Data y:", y) print("Errors:", errw) fitobj = kmpfit.Fitter(residuals=residuals, data=(x, y, err)) fitobj.fit(params0=[1, 1]) print("\n-- Results kmpfit unit weighting wi=1.0:") print("Best-fit parameters: ", fitobj.params) print("Parameter errors using measurement uncertainties: ", fitobj.xerror) print("Parameter errors unit-/relative weighted fit: ", fitobj.stderr) print("Minimum chi^2: ", fitobj.chi2_min) print("Covariance matrix:") print(fitobj.covar) fitobj = kmpfit.Fitter(residuals=residuals, data=(x, y, 10 * err)) fitobj.fit(params0=[1, 1]) print("\n-- Results kmpfit with (scaled) equal weights wi=10*1.0:") print("Best-fit parameters: ", fitobj.params) print("Parameter errors using measurement uncertainties: ", fitobj.xerror) print("Parameter errors unit-/relative weighted fit: ", fitobj.stderr)
def linefitting(x, y, xerr=None, yerr=None, xrange=[-5, 5], color='b', prob=.95, yoffset=0): # Initial guess from simple linear regression sorted = np.argsort(x) b, a, rval, pval, std_err = stats.linregress(x[sorted], y[sorted]) print("\nLineregress parameters: ", a, b) # Run the fit fitobj = kmpfit.Fitter(residuals=residuals, data=(x, y, xerr, yerr)) fitobj.fit(params0=[a, b]) print("\n======== Results kmpfit with effective variance =========") print("Fitted parameters: ", fitobj.params) print("Covariance errors: ", fitobj.xerror) print("Standard errors: ", fitobj.stderr) print("Chi^2 min: ", fitobj.chi2_min) print("Reduced Chi^2: ", fitobj.rchi2_min) print("Status Message:", fitobj.message) c, d = fitobj.params e, f = fitobj.stderr # Alternative method using Orthogonal Distance Regression linear = odr.Model(model) mydata = odr.RealData(x, y, sx=xerr, sy=yerr) myodr = odr.ODR(mydata, linear, beta0=[a, b]) myoutput = myodr.run() myoutput.pprint() # Plot the results xmod = np.linspace(xrange[0], xrange[1], 50) #ymod0 = model([a, b], xmod) ymod = model([c, d], xmod) plt.plot(xmod, ymod, linestyle='--', color=color, zorder=1) axes = plt.gca() dfdp = [1, xmod] ydummy, upperband, lowerband = fitobj.confidence_band( xmod, dfdp, prob, model) verts = list(zip(xmod, lowerband)) + list(zip(xmod[::-1], upperband[::-1])) poly = Polygon(verts, closed=True, fc='c', ec='c', alpha=0.3, label="{:g}% conf.".format(prob * 100)) axes.add_patch(poly) # The slope axes.text(0.03, 0.95 - yoffset, 'a = $%4.2f$ ' % d + u'\u00B1' + ' $%4.2f$' % f, size=10, transform=axes.transAxes, color=color) # The intercept axes.text(0.03, 0.90 - yoffset, 'b = $%4.2f$ ' % c + u'\u00B1' + ' $%4.2f$' % e, size=10, transform=axes.transAxes, color=color) return
# Artificial data #================ N = 50 # Number of data points mean = 0.0 sigma = 0.6 # Characteristics of the noise we add xstart = 2.0 xend = 10.0 x = numpy.linspace(3.0, 10.0, N) paramsreal = [1.0, 1.0] noise = numpy.random.normal(mean, sigma, N) y = model(paramsreal, x) + noise # Prepare a 'Fitter' object' #=========================== arrays = (x, y) fitobj = kmpfit.Fitter(residuals, data=arrays) paramsinitial = (0.0, 0.0) fitobj.fit(params0=paramsinitial) if (fitobj.status <= 0): print('Error message = ', fitobj.errmsg) else: print("Optimal parameters: ", fitobj.params) # Plot the result #================ rc('legend', fontsize=8) fig = figure() xp = numpy.linspace(xstart - 1, xend + 1, 200) frame = fig.add_subplot(1, 1, 1, aspect=1.0) frame.plot(x, y, 'ro', label="Data")
# Artificial data x = numpy.array([2, 4, 6, 8, 10, 12]) y = numpy.array([3.5, 7.2, 9.5, 17.1, 20.0, 25.5]) err = numpy.array([0.55, 0.65, 0.74, 0.5, 0.85, 0.6]) # Prepare plot fig = figure() rc('legend', fontsize=8) frame = fig.add_subplot(1, 1, 1) frame.plot(x, y, 'go', label="data") frame.set_xlabel("x") frame.set_ylabel("y") frame.set_title("Exclude poor data with criterion of Chauvenet") params0 = (1, 1) fitter = kmpfit.Fitter(residuals=residuals, data=(x, y, err)) fitter.fit(params0=params0) print("======== Fit results all data included ==========") print("Params: ", fitter.params) print("Uncertainties: ", fitter.xerror) print("Errors assuming red.chi^2=1: ", fitter.stderr) print("Iterations: ", fitter.niter) print("Function ev: ", fitter.nfev) print("dof: ", fitter.dof) print("chi^2, rchi2: ", fitter.chi2_min, fitter.rchi2_min) print("Status: ", fitter.status) from scipy.stats import chi2 rv = chi2(fitter.dof) print("If H0 was correct, then")
m, n, r_value, p_value, std_err = stats.linregress(x_i, y_i) m_vector[k], n_vector[k] = m, n #Lmfit result_lmfit = lmod.fit(y_i, x=x_i, m=0.005, n=0.24709) lmfit_matrix[:, k] = array(result_lmfit.params.valuesdict().values()) lmfit_error[:, k] = array( [result_lmfit.params['m'].stderr, result_lmfit.params['n'].stderr]) #Curvefit best_vals, covar = curve_fit(linear_model, x_i, y_i, p0=p0) curvefit_matrix[:, k] = best_vals #kapteyn fitobj = kmpfit.Fitter(residuals=residuals_lin, data=(x_i, y_i)) fitobj.fit(params0=p0) kapteyn_matrix[:, k] = fitobj.params #Get fit mean values n_Median, n_16th, n_84th = median(n_vector), percentile(n_vector, 16), percentile( n_vector, 84) m_Median, m_16th, m_84th = median(m_vector), percentile(m_vector, 16), percentile( m_vector, 84) m_Median_lm, m_16th_lm, m_84th_lm = median(lmfit_matrix[0, :]), percentile( lmfit_matrix[0, :], 16), percentile(lmfit_matrix[0, :], 84) n_Median_lm, n_16th_lm, n_84th_lm = median(lmfit_matrix[1, :]), percentile( lmfit_matrix[1, :], 16), percentile(lmfit_matrix[1, :], 84) m_Median_lm_error, n_Median_lm_error = median(lmfit_error[0, :]), median(
pv = Plots_Manager() dz = Fitting_Gaussians() mu, sigma = 0, 1 A = (1 / ((2 * 3.1415)**0.5) * sigma) x_true = linspace(-2, 2, 100) y = A * exp(-(x_true - mu)**2 / (2 * sigma**2)) zerolev = zeros(len(x_true)) p_1, conv = leastsq(Residuals_Gaussian, [A, mu, sigma], [x_true, y, zerolev]) print 'predictions initial', p_1 L = exp(-y / 2) p0 = [-0.2, 0, 1, max(L)] fitterG = kmpfit.Fitter(residuals=residualsG, data=(x_true, L)) fitterG.fit(params0=p0) print fitterG.params gaus_inv = funcG(fitterG.params, x_true) y_frac = y / 3 p_2, conv = leastsq(Residuals_Gaussian, [A / 5, mu, sigma], [x_true, y_frac, zerolev]) print 'predictions by3', p_2 gaus_inv = SingleGaussian_Cont([x_true, zerolev], p_2[0], p_2[1], p_2[2]) # dz.SingleGaussian_Cont(Ind_Variables, A, mu, sigma) plt.plot(x_true, y, '-', color='black') plt.plot(x_true, gaus_inv, '-', color='red') # plt.plot(x_true, y_frac, '-', color = 'orange')
import numpy as np import pandas as pd from matplotlib.pyplot import figure, show from kapteyn import kmpfit def model(p, v, x, w): a, b, c, d, e, f, g, h, i, j, k = p #coefficients to the polynomials return a * v**2 + b * x**2 + c * w**2 + d * v * x + e * v * w + f * x * w + g * v + h * x + i * y + k def residuals(p, data): # Function needed by fit routine v, x, w, z = data # The values for v, x, w and the measured hypersurface z a, b, c, d, e, f, g, h, i, j, k = p #coefficients to the polynomials return (z - model(p, v, x, w)) # Returns an array of residuals. #This should (z-model(p,v,x,w))/err if # there are error bars on the measured z values #initial guess at parameters. Avoid using 0.0 as initial guess par0 = [1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0] #create a fitting object. data should be in the form #that the functions above are looking for, i.e. a Nx4 #list of lists/tuples like (v,x,w,z) data = pd.read_csv("data.csv") print(data) fitobj = kmpfit.Fitter(residuals=residuals, data=data) # call the fitter fitobj.fit(params0=par0)