Card |
---|
| Code Block |
---|
|
#include <TROOT.h>
#include <TH1F.h>
#include <TProfile.h>
#include <time.h>
#include "myana.hh"
#include "main.hh"
static int numChannelsITof;
static int numSamplesITof;
static double sampleIntervalITof;
static const int maxITofBin = 50;
static TProfile* profWf[maxITofBin];
static TProfile* profWfAll;
static TH1F* histEnrg;
static TH1I* histBin;
static unsigned int shotCountITof = 0;
float e1,e2;
int nenergy;
static int bin;
//double* weights;
clock_t start_time;
clock_t finish_time;
const char* ParameterFileName = "ParameterFileName";
FILE *LaserParamOut;
FILE *ShotsOut;
char ShotsName[200];
using namespace Pds;
// This function is called once at the beginning of the analysis job,
// You can ask for detector "configuration" information here.
void beginjob() {
// get ITof parameters from myana.inp
const char inpname[20]="myana.inp";
FILE *inpfile;
inpfile=fopen(inpname,"r");
fscanf(inpfile,"%d\n",&nenergy); // nbins of histogram
fscanf(inpfile,"%f\n",&e1); // xmin of histogram
fscanf(inpfile,"%f\n",&e2); // xmax of histogram
printf("%d %e %e\n",nenergy,e1,e2);
fclose(inpfile);
printf("calling beginjob()\n"); fflush(stdout);
int i;
int fail = 0;
/*
* Processing ITof Config Data
*/
fail = getAcqConfig( AmoITof, numChannelsITof, numSamplesITof, sampleIntervalITof);
// // this is needed for TProfile::FillN routine
// double weightsarray[numSamplesITof];
// for (int i=0;i<numSamplesITof;i++){
// weightsarray[i] = 1.000000;
// }
// weights = &weightsarray[0];
// create an "averaging" histogram (called "profile")
profWfAll = new TProfile("profWfAll","Average Waveform;Seconds;Volts"
, numSamplesITof
, 0.0,sampleIntervalITof,"");
char name[32];
char title[232];
for (i=0;i<nenergy;i=i+1) {
sprintf(name,"profWf%d",i);
sprintf(title,"Average Waveform in Energy bin %d",i);
profWf[i] = new TProfile(name,title,numSamplesITof,
0.0,sampleIntervalITof,"");
profWf[i]->SetYTitle("Volts"); //optional
profWf[i]->SetXTitle("Seconds"); //optional
}
// create a histogram to display the energy bins
histEnrg = new TH1F("histEnrg","Energy bins;Energy; Event Count",nenergy,e1,e2);
histBin = new TH1I("histBin","Energy bins;Bin; Event Count",nenergy,0.0,nenergy);
histEnrg->SetMarkerStyle(4); histEnrg->SetMarkerColor(4); // blue circles
histBin->SetMarkerStyle(4); histBin->SetMarkerColor(4); // blue circles
}
// This function is called once for each run. You should check to see
// if detector configuration information has changed.
void beginrun()
{
printf("beginrun is done, starting timer...");
start_time = clock();
}
void begincalib()
{
}
// This is called once every shot. You can ask for
// the individual detector shot data here.
void event()
{
int fail;
/*
* Processing FeeGasDet Value
*/
double shotEnergy[4];
fail = getFeeGasDet( shotEnergy );
double energy = (shotEnergy[2]+shotEnergy[3])/2;
if ( energy < e1 ) {
histEnrg->Fill(e1);
} else if ( energy > e2 ) {
histEnrg->Fill(e2);
} else {
histEnrg->Fill(energy);
}
/*
* Processing ITof waveform
*/
double* timeITof;
double* voltageITof;
int channel = 0;
fail = getAcqValue( AmoITof, channel, timeITof, voltageITof);
if ( fail != 0 )
printf( "event(): getAcqValue() failed, code = %d\n", fail );
else
{
bin = int(( (energy-e1)/(e2-e1) )*nenergy+0.5);
if (bin<1) bin=0;
if (bin>nenergy-1) bin=int(nenergy-1);
for (int i=0;i<numSamplesITof;i=i+1)
{
double t = timeITof[i];
double v = voltageITof[i];
profWf[bin]->Fill(t,v);
profWfAll->Fill(t,v);
}
//profWfAllhistBin->FillN( int(numSamplesITof), timeITof, voltageITof, weights, 1);
histBin->Fill(bin);
shotCountITof>Fill(bin);
shotCountITof++;
}
}
void endcalib()
{
}
void endrun()
{
printf("User analysis endrun() routine called.\n");
}
void endjob()
{
printf("User analysis endjob() routine called.\n");
finish_time = clock();
double duration = (finish_time - start_time)/CLOCKS_PER_SEC;
printf("Time elapsed: %.2f s \n",(duration));
printf("Number of events processed: %d \n", shotCountITof);
printf("%d \n",profWfAll->GetNbinsX());
for (int bin=20;bin<40;bin++){
printf("%.10f +- %.10f \n",profWfAll->GetBinContent(bin+1),profWfAll->GetBinError(bin+1));
}
}
|
|
Card |
---|
label | pyana psana with ROOT |
---|
| Code Block |
---|
title | "pyanapsana_esort_hmgr.pycpp" |
---|
|
import sys
import logging
import time
#------//-----------------------
#// ImportsThis for other modulesClass's Header --
#//-----------------------------
import numpy as np
import matplotlib.pyplot as plt
#-
#include "speed/psana_esort.h"
//--------------------
# Class definition// C/C++ Headers --
#//-----------------
#include <time.h>
//---------------
class pyana_esort_hmgr (object) :
"""Class whose instance will be used as a user analysis module. """
#----------------
// Collaborating Class #Headers Constructor --
#//-------------------------------
def __init__ ( self, nenergy, e1, e2, source = "AmoITof-0|Acqiris-0"):
"""Class constructor. The parameters to the constructor are passed
from pyana configuration file. If parameters do not have default
values here then the must be defined in pyana.cfg. All parameters
are passed as strings, convert to correct type before use.
"""
self.source = source
self.nebins = int(nenergy)
#include "MsgLogger/MsgLogger.h"
//--------------------------------------------------
// to work with detector data include corresponding
// header from psddl_psana package
//--------------------------------------------------
#include "psddl_psana/acqiris.ddl.h"
#include "psddl_psana/bld.ddl.h"
//-----------------------------------------------------------------------
// Local Macros, Typedefs, Structures, Unions and Forward Declarations --
//-----------------------------------------------------------------------
// This declares this class as psana module
using namespace speed;
PSANA_MODULE_FACTORY(psana_esort)
// ----------------------------------------
// self.emin = float(e1)
-- Public Function Member self.emax = float(e2)
Definitions --
// self.nev = 0
#-------------------
# Public methods --
#-------------------
namespace def beginjob( self, evt, env ) :
"""This method is called once at the beginning of the job.
It will also be called in any Xtc Configure transition, if
configurations have changed since last it was run.
@param evt event data object
@param env environment object
"""
# Preferred way to log information is via logging package
logging.info( "pyana_esort_hmgr.beginjob() called " )
cfg = env.getAcqConfig(self.source)
#numChannels = cfg.nbrChannels()
self.numSamplesITof = cfg.horiz().nbrSamples()
sampleIntervalITof = cfg.horiz().sampInterval()
print self.numSamplesITof
print sampleIntervalITof
speed {
//----------------
// Constructors --
//----------------
psana_esort::psana_esort (const std::string& name)
: Module(name)
, m_acqSrc()
, m_feeSrc()
, m_maxEvents()
, m_filter()
, m_nenergy()
, m_e1()
, m_e2()
{
// get the values from configuration or use defaults
m_acqSrc = configStr("acqSource", "DetInfo(:Acqiris)");
m_feeSrc = configStr("feeSource", "BldInfo(FEEGasDetEnergy)");
m_maxEvents = config("events", 32U);
m_filter = config("filter", false);
m_nenergy = config("nenergy",20);
m_e1 = config("e1",0.0);
m_e2 = config("e2",4.0);
}
//--------------
// Destructor --
//--------------
psana_esort::~psana_esort ()
{
}
/// Method which is called once at the beginning of the job
void
psana_esort::beginJob(Env& env)
{
m_count = 0;
RootHistoManager::RootHMgr& rhmgr = env.rhmgr();
shared_ptr<Psana::Acqiris::ConfigV1> acqConfig = env.configStore().get(m_acqSrc);
if (acqConfig.get()) {
int channel = 0;
m_nSamples = acqConfig->horiz().nbrSamples();
m_sampleInterval = acqConfig->horiz().sampInterval();
m_slope hmgr = env.hmgracqConfig->vert(channel).slope()
;
m_offset self.histEnrg = hmgr.h1f("histEnrg",";Energy",self.nebins,self.emin,self.emax)acqConfig->vert(channel).offset();
m_timevector = self.histBin = hmgr.h1i("histBin",";Bin",self.nebins,0.0, self.nebins)new double[m_nSamples];
m_wfvector = self.histEnrg.SetMarkerStyle(4)new double[m_nSamples];
m_wgvector = self.histEnrg.SetMarkerColor(4)new double[m_nSamples];
for self.histBin.SetMarkerStyle(4)(int i(0);i<m_nSamples;i++){
m_timevector[i]= self.histBin.SetMarkerColor(4)
i * m_sampleInterval;
m_wfvector[i]=0.0;
name = "profWfAll"m_wgvector[i]=1.0;
}
titlem_profWfAll = rhmgr.profile("profWfAll","Average Waveform;time [s];voltage [V]",
self.prof_wfAll = hmgr.prof(name,title,self.numSamplesITof,
AxisDef(0.0, m_nSamples*m_sampleInterval,m_nSamples)
0.0,
);
char name[32];
char title[232];
self.numSamplesITof*sampleIntervalITof,
for (int i=0; i<m_nenergy;i++){
sprintf(name,"profWf%d",i);
sprintf(title,"Average Waveform in Energy bin %d; time [s]; voltage [V]",i);
m_profWf[i] = rhmgr.profile(name, "")
title,
self.prof_wf = []
for bin in range (0,self.nebins):
name = "profWf%d"%binAxisDef(0.0,m_nSamples*m_sampleInterval,m_nSamples)
title = "Average Waveform in Energy Bin %d;time [s];voltage [V]" % bin
self.prof_wf.append( hmgr.prof(name,title,self.numSamplesITof,);
}
}
// create a histogram to display the energy bins
m_histEnrg 0.0,
self.numSamplesITof*sampleIntervalITof,
""))
# prof.FillN requires a weight array...
self.wg = np.ones(self.numSamplesITof,dtype=float)
self.ts = None
def beginrun( self, evt, env ) :
"""This optional method is called if present at the beginning
of the new run.
@param evt event data object
@param env environment object
"""
logging.info( "pyana_esort_hmgr.beginrun() called ")
print "beginrun is done, starting timer..."
self.start = time.clock()
def begincalibcycle( self, evt, env ) :
"""This optional method is called if present at the beginning
of the new calibration cycle.= rhmgr.h1f("histEnrg","Energy bins;Energy; Event Count",AxisDef(m_e1,m_e2,m_nenergy));
m_histBin = rhmgr.h1i("histBin","Energy bins;Bin; Event count",AxisDef(0.0,m_nenergy,m_nenergy));
m_histEnrg->SetMarkerStyle(4); m_histEnrg->SetMarkerColor(4); // blue circles
m_histBin->SetMarkerStyle(4); m_histBin->SetMarkerColor(4); // blue circles
}
/// Method which is called at the beginning of the run
void
psana_esort::beginRun(Env& env)
{
printf("beginRun is done, starting timer...");
m_start_time = clock();
}
/// Method which is called at the beginning of the calibration cycle
void
psana_esort::beginCalibCycle(Env& env)
{
}
/// Method which is called with event data, this is the only required
/// method, all other methods are optional
void
psana_esort::event(Event& evt, Env& env)
{
//MsgLog(name(),info,"Event:" << m_count);
/*
* Processing FeeGasDet Value
*/
shared_ptr<Psana::Bld::BldDataFEEGasDetEnergy> fee = evt.get(m_feeSrc);
double shotEnergy[4] = {0.,0.,0.,0.};
if (fee.get()) {
shotEnergy[0] = fee->f_11_ENRC();
shotEnergy[1] = fee->f_12_ENRC();
shotEnergy[2] = fee->f_21_ENRC();
shotEnergy[3] = fee->f_22_ENRC();
}
double energy = (shotEnergy[2]+shotEnergy[3])/2;
if ( energy < m_e1 ) {
m_histEnrg->Fill(m_e1);
} else if ( energy > m_e2 ) {
m_histEnrg->Fill(m_e2);
} else {
m_histEnrg->Fill(energy);
}
/*
* Processing ITof waveform
*/
shared_ptr<Psana::Acqiris::DataDescV1> acqData = evt.get(m_acqSrc);
if (acqData.get()) {
m_count++;
int channel = 0;
const Psana::Acqiris::DataDescV1Elem& data = acqData->data(channel);
// copy myana main.cc getAcqValue()
const int16_t* wfdata = data.waveforms();
wfdata += data.indexFirstPoint();
shared_ptr<Psana::Acqiris::ConfigV1> acqConfig = env.configStore().get(m_acqSrc);
if (acqConfig.get()) {
for @param evt(int j=0;j<m_nSamples;j++){
event data object
@param env m_wfvector[j] = wfdata[j] * m_slope - m_offset;
environment object
"""}
int numSamples logging.info( "pyana_esort_hmgr.begincalibcycle= data.nbrSegments() called ")
* data.nbrSamplesInSeg();
def event( self, evt, env ) :
"""This method is called for every L1Accept transition.if (numSamples != m_nSamples) std::cout << "nSamples mismatch" << std::endl;
int bin @param= evt event data objectint(( (energy-m_e1)/(m_e2-m_e1) )*m_nenergy+0.5);
if @param env(bin<1) bin=0;
environment object
if (bin>m_nenergy-1) bin=int(m_nenergy-1);
"""m_histBin->Fill(bin);
logging.info( "pyana_esort_hmgr.event() called ")m_profWf[bin]->FillN(numSamples,m_timevector,m_wfvector,m_wgvector,1);
self.nev+=1
m_profWfAll->FillN(numSamples,m_timevector,m_wfvector,m_wgvector,1);
}
}
}
/// Method shotEnergywhich is called at the end of the calibration cycle
void
psana_esort::endCalibCycle(Env& env)
{
delete[] m_timevector;
}
/// Method which is called at the end of the run
void
psana_esort::endRun(Env& env)
{
}
/// Method which is called once at the end of the job
void
psana_esort::endJob(Env& env)
{
clock_t finish_time = clock();
double duration = (finish_time - m_start_time)/CLOCKS_PER_SEC;
printf("Time elapsed: %.2f s \n",(duration));
printf("Number of events processed: %d \n", m_count);
std::cout << m_profWfAll->GetNbinsX() << std::endl;
for (int bin = 20; bin<40; bin++) {
std::cout << m_profWfAll->GetBinContent(bin+1) << " +- " << m_profWfAll->GetBinError(bin+1) << std::endl;
}
}
} // namespace speed
|
|
Card |
---|
| Code Block |
---|
title | "pyana_esort_hmgr.py" |
---|
|
import sys
import logging
import time
#-----------------------------
# Imports for other modules --
#-----------------------------
import numpy as np
import matplotlib.pyplot as plt
#---------------------
# Class definition --
#---------------------
class pyana_esort_hmgr (object) :
"""Class whose instance will be used as a user analysis module. """
#----------------
# Constructor --
#----------------
def __init__ ( self, nenergy, e1, e2, source = "AmoITof-0|Acqiris-0"):= evt.getFeeGasDet()
energy = 0.0
bin = 0
if shotEnergy is None :
print "No Gas Detector"
else :
energy = (shotEnergy[2]+shotEnergy[3])/2
self.histEnrg.Fill(energy);
acqData = evt.getAcqValue(self.source, 0, env)
if acqData :
wf = acqData.waveform()
if self.ts is None :
self.ts = acqData.timestamps()
self.prof_wfAll.FillN(self.numSamplesITof,self.ts,wf,self.wg,1)
bin = int( ((energy-self.emin)/(self.emax-self.emin))*self.nebins+0.5)
if bin < 1 : bin = 0
"""Class constructor. The parameters ifto binthe >constructor self.nebins : bin = self.nebins-1
are passed
from pyana configuration file. If parameters self.histBin.Fill(bin)
do not have default
self.prof_wf[bin].FillN(self.numSamplesITof,self.ts,wf,self.wg,1)
def endcalibcycle( self, env ) :values here then the must be defined in pyana.cfg. All parameters
"""This optional method is called if present at the end of theare passed as strings, convert to correct type before use.
calibration cycle.
"""
@paramself.source env= source
environment object
self.nebins """
= int(nenergy)
logging.info( "pyana_esort_hmgr.endcalibcycle() called" )
self.emin = float(e1)
def endrun( self,.emax env= float(e2) :
"""This optional method is called if present at the end of the run.self.nev = 0
@param env environment object#-------------------
# Public methods """--
logging.info( "pyana_esort_hmgr.endrun() called" )#-------------------
def endjobbeginjob( self, evt, env ) :
"""This method is called once at the endbeginning of the job.
It should do It will also be called in any Xtc Configure transition, if
configurations finalhave cleanup, e.g. close all open fileschanged since last it was run.
@param evt event data object
@param env environment object
"""
# Preferred way to log information is via logging package
logging.info( "pyana_esort_hmgr.endjobbeginjob() called " )
durationcfg = timeenv.clockgetAcqConfig() - self.startsource)
print#numChannels "duration in seconds : ", duration
= cfg.nbrChannels()
self.numSamplesITof = cfg.horiz().nbrSamples()
print "Number of events processed:sampleIntervalITof ", self.nev
= cfg.horiz().sampInterval()
print self.prof_wfAll.GetNbinsX()numSamplesITof
for bin in range (20,40):
print sampleIntervalITof
hmgr = env.hmgr()
print self.prof_wfAll.GetBinContent(bin+1), " +- ", self.prof_wfAll.GetBinError(bin+1)
|
| Card |
---|
label | pyana with MatPlotLib |
---|
| Code Block |
---|
title | "pyana_esort_mpl.py" |
---|
|
import sys
import logging
import time
#-----------------------------
# Imports for other modules --
#-----------------------------
import numpy as np
import matplotlib.pyplot as plt
import h5py
#---------------------
# Class definition --
#---------------------
class pyana_esort_mpl (object) :
"""Class whose instance will be used as a user analysis module. """
#----------------
# Constructor --
#----------------
def __init__ ( self, nenergy, e1, e2, source = "AmoITof-0|Acqiris-0"):
histEnrg = hmgr.h1f("histEnrg",";Energy",self.nebins,self.emin,self.emax)
self.histBin = hmgr.h1i("histBin",";Bin",self.nebins,0.0, self.nebins)
self.histEnrg.SetMarkerStyle(4)
self.histEnrg.SetMarkerColor(4)
self.histBin.SetMarkerStyle(4)
self.histBin.SetMarkerColor(4)
name = "profWfAll"
title = "Average Waveform;time [s];voltage [V]"
self.prof_wfAll = hmgr.prof(name,title,self.numSamplesITof,
"""Class constructor. The parameters to the constructor are passed0.0,
from pyana configuration file. If parameters do not have default
values here then the must be defined in pyana.cfg. All parameters self.numSamplesITof*sampleIntervalITof,
are passed as strings, convert to correct type before use.
"""
self.source = source
"")
self.nebinsprof_wf = int(nenergy)
[]
for bin self.eminin =range float(e10,self.nebins):
self.emaxname = float(e2)"profWf%d"%bin
self.bwidth = (self.emax-self.emin)/self.nebins
title = "Average Waveform in Energy self.nev = 0
#-------------------Bin %d;time [s];voltage [V]" % bin
# Public methods --
#-------------------
self.prof_wf.append( hmgr.prof(name,title,self.numSamplesITof,
def beginjob( self, evt, env ) :
"""This method is called once at the beginning of the job.
It will also be called in any Xtc Configure transition0.0, if
configurations have changed since last it was run.
@param evt event data object
@param env environment objectself.numSamplesITof*sampleIntervalITof,
"""
# Preferred way to log information is via logging package
logging.info( "pyana_esort_mpl.beginjob() called " )
""))
cfg = env.getAcqConfig(self.source)
# prof.FillN requires a #numChannels = cfg.nbrChannels()weight array...
self.numSamplesITofwg = cfgnp.horizones().nbrSamples(self.numSamplesITof,dtype=float)
sampleIntervalITofself.ts = cfg.horiz().sampInterval()None
def beginrun( self, evt, #env for) matplotlib,:
we store the array till the end instead of a histogram...
""" energy / bin histogram """
"""This optional method is called if present at the beginning
of the new run.
self.axisEnrg = np.arange(self.emin,self.emax,self.bwidth, dtype=float)
@param evt event data object
self.arrayEnrg = np.zeros(self.nebins, dtype=float)
@param env """ time wave"""environment object
self.ts = None
"""
logging.info( """ voltage wave"""
pyana_esort_hmgr.beginrun() called ")
print self.wf = None"beginrun is done, starting timer..."
self.wf2start = Nonetime.clock()
def begincalibcycle( self, """ voltage wave in bins of energyevt, env ) :
"""
This optional method is called if present at self.bwf = []the beginning
self.bwf2of =the []
new calibration cycle.
for bin in@param rangeevt (0, self.nebins):
event data object
@param env self.bwf.append( None )
environment object
"""
self.bwf2.append( None ) logging.info( "pyana_esort_hmgr.begincalibcycle() called ")
def beginrunevent( self, evt, env ) :
"""This optional method is called iffor presentevery at the beginning
of the new runL1Accept transition.
@param evt event data object
@param env environment object
"""
logging.info( "pyana_esort_mplhmgr.beginrunevent() called ")
print "beginrun is done, starting timer..."self.nev+=1
self.startshotEnergy = timeevt.clockgetFeeGasDet()
def begincalibcycle( self, evt, env ) :
energy = 0.0
bin """This optional method is called if present at the beginning
= 0
if shotEnergy is None :
of the new calibration cycle.
print "No Gas Detector"
@param evt event dataelse object:
@param env energy environment object= (shotEnergy[2]+shotEnergy[3])/2
"""
logging.info( "pyana_esort_mpl.begincalibcycle() called ")
self.histEnrg.Fill(energy);
def event( self, evt, envacqData ) :
= evt.getAcqValue(self.source, 0, env)
"""This method isif called for every L1Accept transition.
acqData :
@param evt wf event data object
= acqData.waveform()
@param env if self.ts is environmentNone object:
"""
logging.info( "pyana_esort_mpl.event() called ")
self.ts = acqData.timestamps()
self.nev+=1
prof_wfAll.FillN(self.numSamplesITof,self.ts,wf,self.wg,1)
shotEnergy = evt.getFeeGasDet( bin = int( ((energy-self.emin)/(self.emax-self.emin))*self.nebins+0.5)
energy = 0.0
if bin < 1 : bin = 0
if shotEnergybin is> Noneself.nebins :
bin = self.nebins-1
print "No Gas Detector" self.histBin.Fill(bin)
else :
self.prof_wf[bin].FillN(self.numSamplesITof,self.ts,wf,self.wg,1)
def endcalibcycle( self, env energy = (shotEnergy[2]+shotEnergy[3])/2
) :
acqData = evt.getAcqValue(self.source, 0, env)
if acqData :"""This optional method is called if present at the end of the
awf = acqData.waveform()calibration cycle.
@param env if self.ts is None :environment object
"""
selflogging.ts = acqData.timestamps()info( "pyana_esort_hmgr.endcalibcycle() called" )
def endrun( self, env ) :
# average waveform
"""This optional method is called if present at the ifend self.wfof is None:the run.
@param env self.wf = awfenvironment object
"""
selflogging.wf2 = (awf*awf)
info( "pyana_esort_hmgr.endrun() called" )
def endjob( self, env else) :
"""This method is called at the end of self.wf += awfthe job. It should do
final cleanup, e.g. close all open files.
self.wf2 += (awf*awf)
@param env environment object
# binned waveform
"""
bin = int( ((energy-self.emin)/(self.emax-self.emin))*self.nebins+0.5)logging.info( "pyana_esort_hmgr.endjob() called" )
duration = time.clock() - self.start
if bin < 1 : binprint ="duration 0
in seconds : ", duration
ifprint bin"Number >of self.nebinsevents processed: bin", = self.nebins-1nev
print self.arrayEnrg[bin] += 1
self.prof_wfAll.GetNbinsX()
if self.bwf[bin] is None for bin in range (20,40):
print self.prof_wfAll.GetBinContent(bin+1), " +- ", self.prof_wfAll.GetBinError(bin+1)
|
|
Card |
---|
label | pyana with MatPlotLib |
---|
| Code Block |
---|
title | "pyana_esort_mpl.py" |
---|
|
import sys
import logging
import time
#-----------------------------
# Imports for other modules --
#-----------------------------
import numpy as np
import matplotlib.pyplot as plt
import h5py
#---------------------
# Class definition --
#---------------------
class pyana_esort_mpl (object) :
"""Class whose instance will be used as a user analysis module. """
#----------------
# Constructor --
#----------------
def __init__ ( self, nenergy, e1, e2, source = "AmoITof-0|Acqiris-0"):
"""Class constructor. The parameters to the constructor are passed
.bwf[bin]=awf
self.bwf2[bin]=(awf*awf)
else :
self.bwf[bin]+=awf
self.bwf2[bin]+=(awf*awf)
def endcalibcycle( self, env ) :
"""This optional method is called if present at the end of the
calibration cycle.
@param env environment object
"""
logging.info(from "pyana_esort_mpl.endcalibcycle() called" )
def endrun( self, env ) :
"""This optional method is called if present at the end of the run.
@param env environment objectpyana configuration file. If parameters do not have default
values here then the must be defined in pyana.cfg. All parameters
are passed as strings, convert to correct type before use.
"""
logging.info( "pyana_esort_mpl.endrun() called" )
self.source = source
def endjob( self,.nebins env= int(nenergy) :
"""This method is called at the end of the job. It should doself.emin = float(e1)
self.emax = float(e2)
final cleanup, e.g. close all open files.self.bwidth = (self.emax-self.emin)/self.nebins
@paramself.nev env= 0
environment object #-------------------
# Public methods """--
logging.info( "pyana_esort_mpl.endjob() called" )#-------------------
def beginjob( self, evt, #env have) collected:
the sum so far, but we
"""This method is called once at #the wantbeginning toof display the average
job.
It will also be called in self.wfany =Xtc self.wf / self.nev
Configure transition, if
self.wf2 = self.wf2 / self.nevconfigurations have changed since last it was run.
self.wf_rms = np.sqrt( self.wf2 - self.wf*self.wf ) / np.sqrt(self.nev)
@param evt event data object
self.bwf_rms = []
@param env environment object
for bin in range (0, self.nebins): """
# Preferred way to if self.bwf[bin]log information is None:
via logging package
self.bwf_rms.append(None)
logging.info( "pyana_esort_mpl.beginjob() called " )
cfg continue
= env.getAcqConfig(self.source)
self.bwf[bin]#numChannels = self.bwf[bin] / self.arrayEnrg[bin]
cfg.nbrChannels()
self.bwf2[bin]numSamplesITof = self.bwf2[bin] / self.arrayEnrg[bin]cfg.horiz().nbrSamples()
sampleIntervalITof = self.bwf_rms.append(np.sqrt( self.bwf2[bin] \cfg.horiz().sampInterval()
# for matplotlib, we store the array till the end instead of a histogram...
""" energy / bin histogram """
- self.bwf[bin]*self.bwf[bin] ) \self.axisEnrg = np.arange(self.emin,self.emax,self.bwidth, dtype=float)
self.arrayEnrg = np.zeros(self.nebins, dtype=float)
""" time wave"""
self.ts / np.sqrt(self.arrayEnrg[bin]))= None
duration = time.clock() - self.start
""" voltage wave"""
self.wf = None
print "duration in seconds : ", duration self.wf2 = None
print "nevents processed: ", self.nev
""" voltage wave in bins of energy """
duration = time.clock() - self.start
bwf = []
print "duration inself.bwf2 seconds= :[]
", duration
for bin printin "nevents processed: "range (0, self.nev
nebins):
# save "histograms" to an hdf5 file self.bwf.append( None )
ofile = h5pyself.bwf2.File("outputfile.hdf5", 'w') # open for writing (overwrites existing file)append( None )
def beginrun( self, evt, env ) :
group = ofile.create_group("HistogramArrays")
group.create_dataset("wf_time",data=self.ts)"""This optional method is called if present at the beginning
group.create_dataset("wf_avg",data=self.wf)of the new run.
group.create_dataset("wf_avg_rms",data=self.wf_rms)
@param evt event data group.create_dataset("bin_enrg",data=self.arrayEnrg)
object
group.create_dataset("bin_axis",data=self.axisEnrg)
@param env environment object
for bin in range (0, self.nebins):
"""
logging.info( "pyana_esort_mpl.beginrun() called ")
if self.bwf[bin] is not None:
print "beginrun is done, starting timer..."
self.start = grouptime.create_dataset("wf_bin%d"%bin,data=self.bwf[bin])clock()
def begincalibcycle( self, evt, env ) :
group.create_dataset("wf_bin%d_rms"%bin,data=self.bwf_rms[bin])
ofile.close()
"""This optional method is called if present at the beginning
durationof = time.clock() - self.startthe new calibration cycle.
print "duration till after save hdf5, in seconds : ", duration
@param evt event data object
@param env #environment plotobject
fig = plt.figure(num=100, figsize=(7.5,5))"""
ax = fig.add_subplot(111)
logging.info( "pyana_esort_mpl.begincalibcycle() called ")
def event( plt.plot(self.axisEnrg, self.arrayEnrgevt, env 'bo') :
plt.errorbar(self.axisEnrg, self.arrayEnrg, xerr=self.bwidth, yerr=np.sqrt(self.arrayEnrg),fmt=None)
plt.title("Energy Bins")
"""This method is called for every L1Accept transition.
@param evt plt.xlabel("Energy")
event data object
plt.ylabel("Event count")
@param env environment plt.draw()object
print "energy histogram plotted"""
figlogging.savefiginfo( "pyana_esort_mpl_histEnrg.png.event() called ")
print "energy histogram saved"self.nev+=1
figshotEnergy = pltevt.figure(num=200, figsize=(7.5,5)getFeeGasDet()
axenergy = fig.add_subplot(111)0.0
plt.clf()
bin = 0
plt.errorbar(self.ts, self.wf,yerr=self.wf_rms, mew=0.0)
if shotEnergy is None :
print plt.title("Average Waveform")"No Gas Detector"
plt.xlabel("timeelse :
[s]")
plt.ylabel("voltage energy = [V]")
(shotEnergy[2]+shotEnergy[3])/2
acqData plt= evt.draw(getAcqValue(self.source, 0, env)
printif "wf avg histogram plotted"
acqData :
awf = figacqData.savefig("pyana_mpl_profWfAll.png")
waveform()
print "wf avg histogram saved"
if self.ts is None :
for bin in range (0, self.nebins):ts = acqData.timestamps()
if self.bwf[bin] is not None:# average waveform
if self.wf # plotis None:
figself.wf = plt.figure(num=300+bin, figsize=(7.5,5))awf
axself.wf2 = fig.add_subplot(111(awf*awf)
plt.clf()else :
plt.errorbar(self.ts, self.bwf[bin], yerr=self.bwf_rms[bin],mew=0.0)wf += awf
plt.title("Waveform bin %d (%.2f<E<%.2f)"\self.wf2 += (awf*awf)
# binned waveform
bin %= int(bin, ((energy-self.emin+bin*)/(self.bwidth, emax-self.emin+(bin+1))*self.nebins+0.bwidth5))
if bin < 1 : plt.xlabel("time bin = 0
[s]")
if bin > self.nebins : bin = plt.ylabel("voltageself.nebins-1
self.arrayEnrg[V]")bin] += 1
if self.bwf[bin] is None plt.draw():
print "wf bin %d histogram plotted"%binself.bwf[bin]=awf
fig.savefig("pyana_mpl_profWf%d.png"%binself.bwf2[bin]=(awf*awf)
else :
print "wf bin %d histogram saved"%bin
duration = time.clock() - self.start
self.bwf[bin]+=awf
print "duration3 in seconds : ", duration self.bwf2[bin]+=(awf*awf)
def endcalibcycle( self, env #) test:
print self.wf.size
for bin in range (20,40):
"""This optional method is called if present at the end of the
calibration cycle.
print self.wf[bin], " +-- ", self.wf_rms[bin]
|
| Card |
---|
| Code Block |
---|
|
//-----------------------
// This Class's Header --
//-----------------------
#include "speed/psana_esort.h"
//-----------------
// C/C++ Headers --
//-----------------
#include <time.h>
//-------------------------------
// Collaborating Class Headers --
//-------------------------------
#include "MsgLogger/MsgLogger.h"
//--------------------------------------------------
// to work with detector data include corresponding
// header from psddl_psana package
//--------------------------------------------------
#include "psddl_psana/acqiris.ddl.h"
#include "psddl_psana/bld.ddl.h"
//-----------------------------------------------------------------------
// Local Macros, Typedefs, Structures, Unions and Forward Declarations --
//-----------------------------------------------------------------------
// This declares this class as psana module
using namespace speed;
PSANA_MODULE_FACTORY(psana_esort)
// ----------------------------------------
// -- Public Function Member Definitions --
// @param env environment object
"""
logging.info( "pyana_esort_mpl.endcalibcycle() called" )
def endrun( self, env ) :
"""This optional method is called if present at the end of the run.
@param env environment object
"""
logging.info( "pyana_esort_mpl.endrun() called" )
def endjob( self, env ) :
"""This method is called at the end of the job. It should do
final cleanup, e.g. close all ----------------------------------------
namespace speed {
//----------------
// Constructors --
//----------------
psana_esort::psana_esort (const std::string& name)
: Module(name)
, m_acqSrc()
, m_feeSrc()
, m_maxEvents()
, m_filter()
, m_nenergy()
, m_e1()
, m_e2()
{
// get the values from configuration or use defaults
m_acqSrc = configStr("acqSource", "DetInfo(:Acqiris)");
m_feeSrc = configStr("feeSource", "BldInfo(FEEGasDetEnergy)");
m_maxEvents = config("events", 32U);
m_filter = config("filter", false);
m_nenergy = config("nenergy",20);
m_e1 = config("e1",0.0);
m_e2 = config("e2",4.0);
}
//--------------
// Destructor --
//--------------
psana_esort::~psana_esort ()
{
}
/// Method which is called once at the beginning of the job
void
psana_esort::beginJob(Env& env)
{
m_count = 0;
RootHistoManager::RootHMgr& rhmgr = env.rhmgr();
shared_ptr<Psana::Acqiris::ConfigV1> acqConfig = env.configStore().get(m_acqSrc);
if (acqConfig.get()) {
int channel = 0;
m_nSamples = acqConfig->horiz().nbrSamples();
m_sampleInterval = acqConfig->horiz().sampInterval();
m_slopeopen files.
@param env environment object
"""
logging.info( "pyana_esort_mpl.endjob() called" )
# have collected the sum so far, but we
# want to display the average
self.wf = self.wf / self.nev
self.wf2 = self.wf2 / self.nev
self.wf_rms = np.sqrt( self.wf2 - self.wf*self.wf ) / np.sqrt(self.nev)
self.bwf_rms = []
for bin in range (0, self.nebins):
if self.bwf[bin] is None:
self.bwf_rms.append(None)
continue
self.bwf[bin] = self.bwf[bin] / self.arrayEnrg[bin]
self.bwf2[bin] = self.bwf2[bin] / self.arrayEnrg[bin]
= acqConfig->vert(channel).slope();
self.bwf_rms.append(np.sqrt( self.bwf2[bin] \
m_offset = acqConfig->vert(channel).offset();
m_timevector = new double[m_nSamples];
m_wfvector = new double[m_nSamples];
m_wgvector = new double[m_nSamples];
for (int i(0);i<m_nSamples;i++){- self.bwf[bin]*self.bwf[bin] ) \
m_timevector[i]= i * m_sampleInterval;
m_wfvector[i]=0.0;
m_wgvector[i]=1.0;
}
m_profWfAll = rhmgr.profile("profWfAll","Average Waveform;time [s];voltage [V]", / np.sqrt(self.arrayEnrg[bin]))
duration = time.clock() - self.start
print "duration in seconds : ", duration
AxisDef(0.0, m_nSamples*m_sampleInterval,m_nSamples)
print "nevents processed: ", self.nev
duration = time.clock() - self.start
print "duration in seconds : ", );duration
char name[32];
print char title[232];
for (int i=0; i<m_nenergy;i++){
"nevents processed: ", self.nev
# save sprintf(name,"profWf%dhistograms",i);
to an hdf5 file
sprintf(title,"Average Waveform in Energy bin %d; time [s]; voltage [V]",i);
m_profWf[i] = rhmgr.profile(name, title,ofile = h5py.File("outputfile.hdf5", 'w') # open for writing (overwrites existing file)
group = ofile.create_group("HistogramArrays")
group.create_dataset("wf_time",data=self.ts)
group.create_dataset("wf_avg",data=self.wf)
AxisDef(0.0,m_nSamples*m_sampleInterval,m_nSamplesgroup.create_dataset("wf_avg_rms",data=self.wf_rms)
group.create_dataset("bin_enrg",data=self.arrayEnrg)
group.create_dataset("bin_axis",data=self.axisEnrg)
for bin in range );
}
}
// create a histogram to display the energy bins
m_histEnrg = rhmgr.h1f("histEnrg","Energy bins;Energy; Event Count",AxisDef(m_e1,m_e2,m_nenergy));
m_histBin = rhmgr.h1i("histBin","Energy bins;Bin; Event count",AxisDef(0.0,m_nenergy,m_nenergy));
m_histEnrg->SetMarkerStyle(4); m_histEnrg->SetMarkerColor(4); // blue circles
m_histBin->SetMarkerStyle(4); m_histBin->SetMarkerColor(4); // blue circles
//m_histEnrg = new TH1F("histEnrg",";Energy",m_nenergy,m_e1,m_e2);
//m_histBin = new TH1I("histBin",";Bin",m_nenergy,0.0,m_nenergy);
}
/// Method which is called at the beginning of the run
void
psana_esort::beginRun(Env& env)
{
printf("beginRun is done, starting timer...");
m_start_time = clock();
}
/// Method which is called at the beginning of the calibration cycle
void
psana_esort::beginCalibCycle(Env& env)
{
}
/// Method which is called with event data, this is the only required
/// method, all other methods are optional
void
psana_esort::event(Event& evt, Env& env)
{
// // this is how to skip event (all downstream modules will not be called)
// if (m_filter && m_count % 10 == 0) skip();
// // this is how to gracefully stop analysis job
// if (m_count >= m_maxEvents) stop();
//MsgLog(name(),info,"Event:" << m_count);
/*
* Processing FeeGasDet Value
*/
shared_ptr<Psana::Bld::BldDataFEEGasDetEnergy> fee = evt.get(m_feeSrc);
double shotEnergy[4] = {0.,0.,0.,0.};
if (fee.get()) {
shotEnergy[0] = fee->f_11_ENRC();
shotEnergy[1] = fee->f_12_ENRC();
shotEnergy[2] = fee->f_21_ENRC();
shotEnergy[3] = fee->f_22_ENRC();
}
double energy = (shotEnergy[2]+shotEnergy[3])/2;
if ( energy < m_e1 ) {
m_histEnrg->Fill(m_e1);
} else if ( energy > m_e2 ) {
m_histEnrg->Fill(m_e2);
} else {
m_histEnrg->Fill(energy);
}
/*
* Processing ITof waveform
*/
shared_ptr<Psana::Acqiris::DataDescV1> acqData = evt.get(m_acqSrc);
if (acqData.get()) {
m_count++;
int channel = 0;
const Psana::Acqiris::DataDescV1Elem& data = acqData->data(channel);
// copy myana main.cc getAcqValue()
const int16_t* wfdata = data.waveforms();
wfdata += data.indexFirstPoint();
shared_ptr<Psana::Acqiris::ConfigV1> acqConfig = env.configStore().get(m_acqSrc);
if (acqConfig.get()) {
// const Psana::Acqiris::HorizV1& hcfg = acqConfig->horiz();
// const Psana::Acqiris::VertV1& vcfg = acqConfig->vert(channel);
// float slope = vcfg.slope();
// float offset = vcfg.offset();
// int nbrSamples = hcfg.nbrSamples();
// for (int j=0;j<nbrSamples;j++){
// int16_t swap = (wfdata[j]&0xff<<8) | (wfdata[j]&0xff00>>8);
// m_wfvector[j] = swap*slope-offset;
for (int j=0;j<m_nSamples;j++){
int16_t swap = (wfdata[j]&0xff<<8) | (wfdata[j]&0xff00>>8);
m_wfvector[j] = swap* m_slope - m_offset;
}
int numSamples = data.nbrSegments() * data.nbrSamplesInSeg();
if (numSamples != m_nSamples) std::cout << "nSamples mismatch" << std::endl;
int bin = int(( (energy-m_e1)/(m_e2-m_e1) )*m_nenergy+0.5);
if (bin<1) bin=0;
if (bin>m_nenergy-1) bin=int(m_nenergy-1);
m_histBin->Fill(bin);
m_profWf[bin]->FillN(numSamples,m_timevector,m_wfvector,m_wgvector,1);
m_profWfAll->FillN(numSamples,m_timevector,m_wfvector,m_wgvector,1);
}
}
}
/// Method which is called at the end of the calibration cycle
void
psana_esort::endCalibCycle(Env& env)
{
delete[] m_timevector;
}
/// Method which is called at the end of the run
void
psana_esort::endRun(Env& env)
{
}
/// Method which is called once at the end of the job
void
psana_esort::endJob(Env& env)
{
clock_t finish_time = clock();
double duration = (finish_time - m_start_time)/CLOCKS_PER_SEC;
printf("Time elapsed: %.2f s \n",(duration));
printf("Number of events processed: %d \n", m_count);
std::cout << m_profWfAll->GetNbinsX() << std::endl;
for (int bin = 20; bin<40; bin++) {
std::cout << m_profWfAll->GetBinContent(bin+1) << " +- " << m_profWfAll->GetBinError(bin+1) << std::endl;
}
}
} // namespace speed(0, self.nebins):
if self.bwf[bin] is not None:
group.create_dataset("wf_bin%d"%bin,data=self.bwf[bin])
group.create_dataset("wf_bin%d_rms"%bin,data=self.bwf_rms[bin])
ofile.close()
duration = time.clock() - self.start
print "duration till after save hdf5, in seconds : ", duration
# plot
fig = plt.figure(num=100, figsize=(7.5,5))
ax = fig.add_subplot(111)
plt.plot(self.axisEnrg, self.arrayEnrg, 'bo')
plt.errorbar(self.axisEnrg, self.arrayEnrg, xerr=self.bwidth, yerr=np.sqrt(self.arrayEnrg),fmt=None)
plt.title("Energy Bins")
plt.xlabel("Energy")
plt.ylabel("Event count")
plt.draw()
print "energy histogram plotted"
fig.savefig("pyana_mpl_histEnrg.png")
print "energy histogram saved"
fig = plt.figure(num=200, figsize=(7.5,5))
ax = fig.add_subplot(111)
plt.clf()
plt.errorbar(self.ts, self.wf,yerr=self.wf_rms, mew=0.0)
plt.title("Average Waveform")
plt.xlabel("time [s]")
plt.ylabel("voltage [V]")
plt.draw()
print "wf avg histogram plotted"
fig.savefig("pyana_mpl_profWfAll.png")
print "wf avg histogram saved"
for bin in range (0, self.nebins):
if self.bwf[bin] is not None:
# plot
fig = plt.figure(num=300+bin, figsize=(7.5,5))
ax = fig.add_subplot(111)
plt.clf()
plt.errorbar(self.ts, self.bwf[bin], yerr=self.bwf_rms[bin],mew=0.0)
plt.title("Waveform bin %d (%.2f<E<%.2f)"\
% (bin, self.emin+bin*self.bwidth, self.emin+(bin+1)*self.bwidth))
plt.xlabel("time [s]")
plt.ylabel("voltage [V]")
plt.draw()
print "wf bin %d histogram plotted"%bin
fig.savefig("pyana_mpl_profWf%d.png"%bin)
print "wf bin %d histogram saved"%bin
duration = time.clock() - self.start
print "duration3 in seconds : ", duration
# test
print self.wf.size
for bin in range (20,40):
print self.wf[bin], " +-- ", self.wf_rms[bin]
|
|
|