Iterative FitFunction parameters
Hammy
I'm fitting a lot of peaks in my data and am trying to write a somewhat efficient function to fit the peaks that I define and generate waves with the results of each fit (to include the coefficients, errors, and chi-squared information) so that I can display them in a table. My function also generates a tag which is anchored to each fitted peak containing information from the fit.
The issue that I'm running into as I continue to try and optimize it even more, is being able to define my coefficients and fit-parameters. What I would like to do is create a table which has my coefficient guesses and fit parameters for each peak I want to fit, as separate waves. By fit parameters, I simply mean Xstart and Xfinish for my Gaussian fit.
My code, which currently works with the values preset in the function, is below, followed by what I would like to try and impliment.
Function TestMultiFit2(coef,sigma,chisq,Npnts,n)
String coef
String sigma
String chisq
String Npnts
Variable n
Variable i
Variable V_chisq
Variable V_npnts
Wave W_Sigma
Wave W_Coef
Wave wave_0
String i_string
String CoefString
String SigmaString
String ChisqString
String NpntsString
For (i=0;i<n;i+=1)
//Convert i to a string
sprintf i_string, "%d", i
//Make n user-defined waves with sequential names_i
CoefString = coef + "_" + i_string
Make/D/N=5/O $CoefString
Wave coef_i = $CoefString
// Fit Peak i
coef_i[0] = {-10,10000,178000,250,1}
FuncFit/NTHR=0 SingleGauss coef_i watch_kev_Hist[573,623] /W=weight_kev_watch /I=1 /D
// Make Sigma Wave
SigmaString = sigma + "_" + i_string
Make/D/N=5/O $SigmaString
Wave sigma_i = $SigmaString
sigma_i = W_sigma
// Make Chi-Squared Wave
ChisqString = chisq + "_" + i_string
Make/D/N=1/O $ChisqString
Wave chisq_i = $ChisqString
chisq_i = V_chisq
// Make "Chi-Squared Number of Data Points" Wave
NpntsString = Npnts + "_" + i_string
Make/D/N=1/O $NpntsString
Wave Npnts_i = $NpntsString
Npnts_i = V_npnts
// Create a Tag with relevant information anchored on the Centroid Peak value
String Peak
sprintf Peak, "Peak " + i_string+"\rE=%g keV", Coef_i(3)
Tag/C/N=Fit1Results/X=10/Y=10 watch_kev_hist,Coef_i(3), Peak
EndFor
End
String coef
String sigma
String chisq
String Npnts
Variable n
Variable i
Variable V_chisq
Variable V_npnts
Wave W_Sigma
Wave W_Coef
Wave wave_0
String i_string
String CoefString
String SigmaString
String ChisqString
String NpntsString
For (i=0;i<n;i+=1)
//Convert i to a string
sprintf i_string, "%d", i
//Make n user-defined waves with sequential names_i
CoefString = coef + "_" + i_string
Make/D/N=5/O $CoefString
Wave coef_i = $CoefString
// Fit Peak i
coef_i[0] = {-10,10000,178000,250,1}
FuncFit/NTHR=0 SingleGauss coef_i watch_kev_Hist[573,623] /W=weight_kev_watch /I=1 /D
// Make Sigma Wave
SigmaString = sigma + "_" + i_string
Make/D/N=5/O $SigmaString
Wave sigma_i = $SigmaString
sigma_i = W_sigma
// Make Chi-Squared Wave
ChisqString = chisq + "_" + i_string
Make/D/N=1/O $ChisqString
Wave chisq_i = $ChisqString
chisq_i = V_chisq
// Make "Chi-Squared Number of Data Points" Wave
NpntsString = Npnts + "_" + i_string
Make/D/N=1/O $NpntsString
Wave Npnts_i = $NpntsString
Npnts_i = V_npnts
// Create a Tag with relevant information anchored on the Centroid Peak value
String Peak
sprintf Peak, "Peak " + i_string+"\rE=%g keV", Coef_i(3)
Tag/C/N=Fit1Results/X=10/Y=10 watch_kev_hist,Coef_i(3), Peak
EndFor
End
If I want to fit 3 specific peaks, I would have a wave for each peak in a table, ordered in such a manner as I can sift out whatever value I need for each coefficient guess and Xstart/Xfinish.
Peak_0
w_0
w_1
w_2
etc
Peak_1
w_0
w_1
w_2
etc
But when I try to incorporate such a method in my function, it messes up all of the following parts of the function which use the "i" value. Below is a similar idea to the modification I made to my function in an attempt to accomplish that:
// Fit Peak i
coef_i[0] = {Peak_i(0),Peak_i(1),Peak_i(2),Peak_i(3),Peak_i(4)}
FuncFit/NTHR=0 SingleGauss coef_i watch_kev_Hist[Peak_i(5),Peak_i(6)] /W=weight_kev_watch /I=1 /D
coef_i[0] = {Peak_i(0),Peak_i(1),Peak_i(2),Peak_i(3),Peak_i(4)}
FuncFit/NTHR=0 SingleGauss coef_i watch_kev_Hist[Peak_i(5),Peak_i(6)] /W=weight_kev_watch /I=1 /D
where Peak_i refers to waves I've created in a table which hold all those values.
To sum up, I'd like my function to fit Peak 1 with my defined guesses and Xstart/Xfinish, generate waves containing the results of the fit, and run back through to fit Peak 2 with the defined guesses for Peak 2, all the way through n peaks that I define. It currently does everything, except iterate the coefficient guesses and Xstart/Xfinish values.
I appreciate any input on the issue I'm running into with using an "i" value in the Fit Function parameters, and possible solutions. I'll be continuing to try to figure it out over the weekend.
Thanks.
Wave Peak_i = $name // Create reference to wave
For details execute:
March 10, 2013 at 10:48 am - Permalink
You're absolutely right. I was attempting to keep my post to a minimum to explain what I did with a simple example of what sort of edit to the fit function itself I was doing. I was creating a Peak_i wave reference (which I didn't show), but my problem was in how I defined my string name for it, which I see now from your example. I was defining the Wave Peak in a function parameter, and then using Wave Peak_i = Peak. As well as a few other attempts, which were all wrong. I'll be more explicit next time in the explanation of my full attempt(s).
Thanks for the clarification! The code now works just fine with an edit to the Fit Function section, as well as the Tag generator section so that it doesn't erase over the same tag with each iteration:
String name = "Peak_" + i_string
Wave Peak_i = $name
coef_i[0] = {Peak_i(0),Peak_i(1),Peak_i(2),Peak_i(3),Peak_i(4)}
FuncFit/NTHR=0 SingleGauss coef_i watch_kev_Hist[Peak_i(5),Peak_i(6)] /W=weight_kev_watch /I=1 /D
String Peak
sprintf Peak, "Peak " + i_string+"\rE=%g keV", Coef_i(3)
Tag/C/N=$name/X=10/Y=10 watch_kev_hist,Coef_i(3), Peak
I have a separate function to create the peak waves and generate the table with each one for parameter entry. Thanks for your help.
March 10, 2013 at 12:54 pm - Permalink