Performing a function on all traces on a graph
aakande
Hi everyone,
I recently started using Igor for mass spec research-related analysis and just getting familiar with it.
I am trying to get the average of different points in a graph. Using the Wavestats function, I can do this individually for each wave name (eg :PeakData:'CH3O2+) but I have tons of traces on a graph. How do I get the same function to automatically go through all the traces on the graph?
Is there also a way to get out only the V_avg of each of the traces and make them in a table? (I currently have to copy one after the other into an excel sheet. I now have tons of data and this isn't sustainable)
Thank you!
•WaveStats/R=[487,1943] :PeakData:'CH3O2+';
V_npnts= 1457; V_numNaNs= 0; V_numINFs= 0; V_avg= 34.5415;
V_Sum= 50327; V_sdev= 7.85227; V_sem= 0.205715; V_rms= 35.4222;
V_adev= 6.24775; V_skew= 0.328991; V_kurt= 0.140453;
V_minloc= 1934; V_maxloc= 836; V_min= 13.1429; V_max= 70.6547;
V_minRowLoc= 1934; V_maxRowLoc= 836; V_startRow= 487;
V_endRow= 1943;
V_npnts= 1457; V_numNaNs= 0; V_numINFs= 0; V_avg= 34.5415;
V_Sum= 50327; V_sdev= 7.85227; V_sem= 0.205715; V_rms= 35.4222;
V_adev= 6.24775; V_skew= 0.328991; V_kurt= 0.140453;
V_minloc= 1934; V_maxloc= 836; V_min= 13.1429; V_max= 70.6547;
V_minRowLoc= 1934; V_maxRowLoc= 836; V_startRow= 487;
V_endRow= 1943;
String outWaveName
Variable pstart,pend
String graphName=WinName(0,1)
if( strlen(graphName) == 0 )
DoAlert 0, "Expected graph"
return ""
endif
String traces= TraceNameList(graphName,";",1)
Variable i, n=ItemsInList(traces)
Make/O/D/N=(n) $outWaveName // overwrites any wave of the same name
WAVE wavgs= $outWaveName
for(i=0;i<n;i+=1)
String traceName= StringFromList(i,traces)
Wave wy = TraceNameToWaveRef(graphName,traceName)
WaveStats/M=1/Q/R=[pstart,pend] wy
wavgs[i] = V_Avg
SetDimLabel 0, i, $NameOfWave(wy), wavgs
endfor
return GetWavesDataFolder(wavgs,2) // full path
End
Macro AverageWavesInGraph(outWaveName,pstart,pend)
String outWaveName="averages" // you can (and should) change this
Variable pstart=0,pend=inf // defaults to entire wave
String avgWave= fAverageOfGraphWaves(outWaveName,pstart,pend)
if( strlen(avgWave) )
Edit $avgWave.ld
endif
End
November 21, 2021 at 09:37 pm - Permalink
Thank you, JimProuty! This worked great.
I have a quick follow up: I realized an issue I did not think about before now.
After using the function and using Edit to get my data in a table, they are registered as points instead of the name of a trace.
I am certain that the points correlate in the same order the waves are arranged (I crosschecked) but the names of the trace are also important because my plan is to create a category plot afterwards.
My question would be: Is there a way to make the table contain the wavenames rather than just points (0,1, ...)? or alternatively if I could create a list of the wavenames and make them in another table?
I tried simply copying and pasting but that did not work. I could only copy one at a time.
Thank you
November 22, 2021 at 02:22 pm - Permalink
Hi,
One suggestion is to use dimension labels.
for example you can add this line after waves[i] V_avg:
setdimlabel 0,i,,$traceName, wavgs
This sets the point label (0 dimension) at index, i, to the value of the tracename string. I am a big fan of dimension labels since it is a mechanism to have both string and numeric data in the same wave.
Andy
November 22, 2021 at 03:12 pm - Permalink
In reply to Thank you, JimProuty! This… by aakande
I've amended the code to use the dimension labels suggestion (good idea!)
If you want to make a category plot, though, you'll need a separate text wave, instead.
So...
String averagesWaveName,namesWaveName
Variable pstart,pend
String graphName=WinName(0,1)
if( strlen(graphName) == 0 )
DoAlert 0, "Expected graph"
return ""
endif
String traces= TraceNameList(graphName,";",1)
Variable i, n=ItemsInList(traces)
Make/O/D/N=(n) $averagesWaveName // overwrites any wave of the same name
WAVE wavgs= $averagesWaveName
Make/O/T/N=(n) $namesWaveName
WAVE/T wnames= $namesWaveName
for(i=0;i<n;i+=1)
String traceName= StringFromList(i,traces)
Wave wy = TraceNameToWaveRef(graphName,traceName)
WaveStats/M=1/Q/R=[pstart,pend] wy
wavgs[i] = V_Avg
wnames[i] = NameOfWave(wy)
endfor
String listOfWaves= GetWavesDataFolder(wavgs,2) + ";" + GetWavesDataFolder(wnames,2)
return listOfWaves // full paths to waves
End
Macro AverageWavesInGraph(averagesWaveName,namesWaveName,pstart,pend)
String averagesWaveName="averages" // you can (and should) change this
String namesWaveName="names" // you can (and should) change this
Variable pstart=0,pend=inf // defaults to entire wave
String listOfWaves= fAverageOfGraphWaves(averagesWaveName,namesWaveName,pstart,pend)
if( strlen(listOfWaves) )
String avgWave= StringFromList(0,listOfWaves)
String namesWave= StringFromList(1,listOfWaves)
Edit $namesWave, $avgWave
Display $avgWave vs $namesWave
endif
End
November 22, 2021 at 05:14 pm - Permalink
I would indeed need the text as a separate wave.
And this works! Thank you so much.
November 23, 2021 at 02:29 pm - Permalink
And in Igor 9, you *can* use the dimension labels for a category plot!
Simply use "Display $avgWave vs _labels_"
November 29, 2021 at 02:35 pm - Permalink