From e186645877ba864762021563bb4b98fc0d3fe870 Mon Sep 17 00:00:00 2001 From: Matt Graham Date: Tue, 25 Feb 2025 07:19:38 -0800 Subject: [PATCH 1/2] add classes for skimming recon events --- .../recon/filtering/ThreeProngECalFilter.java | 83 ++++++++++ .../java/org/hps/recon/skims/FEESkimmer.java | 31 ++++ .../org/hps/recon/skims/MollerSkimmer.java | 31 ++++ .../org/hps/recon/skims/MultiSkimDriver.java | 146 ++++++++++++++++++ .../java/org/hps/recon/skims/Skimmer.java | 119 ++++++++++++++ .../org/hps/recon/skims/ThreeBodySkimmer.java | 30 ++++ .../java/org/hps/recon/skims/V0Skimmer.java | 117 ++++++++++++++ .../hps/steering/production/StreamSkims.lcsim | 42 +++++ 8 files changed, 599 insertions(+) create mode 100644 recon/src/main/java/org/hps/recon/filtering/ThreeProngECalFilter.java create mode 100644 recon/src/main/java/org/hps/recon/skims/FEESkimmer.java create mode 100644 recon/src/main/java/org/hps/recon/skims/MollerSkimmer.java create mode 100644 recon/src/main/java/org/hps/recon/skims/MultiSkimDriver.java create mode 100644 recon/src/main/java/org/hps/recon/skims/Skimmer.java create mode 100644 recon/src/main/java/org/hps/recon/skims/ThreeBodySkimmer.java create mode 100644 recon/src/main/java/org/hps/recon/skims/V0Skimmer.java create mode 100644 steering-files/src/main/resources/org/hps/steering/production/StreamSkims.lcsim diff --git a/recon/src/main/java/org/hps/recon/filtering/ThreeProngECalFilter.java b/recon/src/main/java/org/hps/recon/filtering/ThreeProngECalFilter.java new file mode 100644 index 0000000000..e65964bf0e --- /dev/null +++ b/recon/src/main/java/org/hps/recon/filtering/ThreeProngECalFilter.java @@ -0,0 +1,83 @@ +package org.hps.recon.filtering; + +import static java.lang.Math.abs; +import java.util.List; +import java.util.ArrayList; +import org.lcsim.event.Cluster; +import org.lcsim.event.base.BaseCluster; +import org.hps.recon.ecal.cluster.ClusterUtilities; +import org.lcsim.event.EventHeader; +import org.lcsim.geometry.Detector; + +/** + * Class to strip off 3-prong trident candidates, using only the ECal cluster energy sum, + * requires exactly 3 in-time clusters, with at least 1 top and 1 bottom and + * the 3-cluster energy sum be within eMin<3-Esum clusters = event.get(Cluster.class, _ECalClusterCollectionName); + if(clusters.size()<3) //have to have three clusters for this + skipEvent(); + + + boolean hasTop=false; + boolean hasBottom=false; + List inTimeClusters=new ArrayList(); + for (Cluster clu : clusters){ + double clTime= ClusterUtilities.getSeedHitTime(clu); + if( clTime>(_triggerTimeOffset-_triggerWindowSize) + && clTime<(_triggerTimeOffset+_triggerWindowSize)){ + if(clu.getPosition()[1]>0) + hasTop=true; + else + hasBottom=true; + inTimeClusters.add(clu); + } + } + // System.out.println("Found "+inTimeClusters.size()+" in time clusters"); + if(inTimeClusters.size()!=3) //have to have exactly three in time clusters for this + skipEvent(); + + if(! (hasTop && hasBottom)) + skipEvent(); + + double t0= ClusterUtilities.getSeedHitTime(inTimeClusters.get(0)); + double t1= ClusterUtilities.getSeedHitTime(inTimeClusters.get(1)); + double t2= ClusterUtilities.getSeedHitTime(inTimeClusters.get(2)); + + // require that all 3 clusters are within _clusterRelativeTimingCut + if(abs(t0-t1)>_clusterRelativeTimingCut) + skipEvent(); + if(abs(t1-t2)>_clusterRelativeTimingCut) + skipEvent(); + if(abs(t2-t0)>_clusterRelativeTimingCut) + skipEvent(); + // forget to add energy cut! + double clEneSum=inTimeClusters.get(0).getEnergy() + +inTimeClusters.get(1).getEnergy() + +inTimeClusters.get(2).getEnergy(); + if(clEneSum<_eMin || clEneSum>_eMax) + skipEvent(); + + incrementEventPassed(); + } + + protected void detectorChanged(Detector detector) { + super.detectorChanged(detector); + } +} diff --git a/recon/src/main/java/org/hps/recon/skims/FEESkimmer.java b/recon/src/main/java/org/hps/recon/skims/FEESkimmer.java new file mode 100644 index 0000000000..4c6eeac1cb --- /dev/null +++ b/recon/src/main/java/org/hps/recon/skims/FEESkimmer.java @@ -0,0 +1,31 @@ +package org.hps.recon.skims; + +import org.lcsim.event.EventHeader; + + +public class FEESkimmer extends Skimmer { + private String _FEECandidateCollectionName = "UnconstrainedFEECandidates"; + private double _clusterTimingCut = 20.0; // only used if _tight is true + private double _v0Chi2Cut = 100.0; + private double _trackChi2Cut = 80.0; + private double _trackDtCut = 20.0; + private double _trackPMax = 0.9; + private double _v0PMax = 1.4; + private int _nHitsMin=10; + + @Override + public boolean passSelection(EventHeader event){ + System.out.println(this.getClass().getName()+":: in pass selection"); + boolean pass=true; + + + return pass; + } + + + public FEESkimmer(String file) { + super(file, null); + // this(super.addFileExtension(file), null); + } + +} diff --git a/recon/src/main/java/org/hps/recon/skims/MollerSkimmer.java b/recon/src/main/java/org/hps/recon/skims/MollerSkimmer.java new file mode 100644 index 0000000000..ca6979f8df --- /dev/null +++ b/recon/src/main/java/org/hps/recon/skims/MollerSkimmer.java @@ -0,0 +1,31 @@ +package org.hps.recon.skims; + +import org.lcsim.event.EventHeader; + + +public class MollerSkimmer extends Skimmer { + private String _MollerCandidateCollectionName = "UnconstrainedMollerCandidates"; + private double _clusterTimingCut = 20.0; // only used if _tight is true + private double _v0Chi2Cut = 100.0; + private double _trackChi2Cut = 80.0; + private double _trackDtCut = 20.0; + private double _trackPMax = 0.9; + private double _v0PMax = 1.4; + private int _nHitsMin=10; + + @Override + public boolean passSelection(EventHeader event){ + System.out.println(this.getClass().getName()+":: in pass selection"); + boolean pass=true; + + + return pass; + } + + + public MollerSkimmer(String file) { + super(file, null); + // this(super.addFileExtension(file), null); + } + +} diff --git a/recon/src/main/java/org/hps/recon/skims/MultiSkimDriver.java b/recon/src/main/java/org/hps/recon/skims/MultiSkimDriver.java new file mode 100644 index 0000000000..b4a11f88af --- /dev/null +++ b/recon/src/main/java/org/hps/recon/skims/MultiSkimDriver.java @@ -0,0 +1,146 @@ +package org.hps.recon.skims; + +import java.util.logging.Level; +import java.util.logging.Logger; +import java.util.List; +import java.util.ArrayList; + +import org.hps.conditions.beam.BeamEnergy.BeamEnergyCollection; + +import org.lcsim.util.Driver; +import org.lcsim.event.EventHeader; +import org.lcsim.geometry.Detector; + +public class MultiSkimDriver extends Driver { + + private static final Logger LOGGER = Logger.getLogger(MultiSkimDriver.class.getPackage().getName()); + + //if this is true, an event will be written to each stream that it passes + //if false, it will only go into the first stream it passes... so the ordering of the skim list matters. + private boolean allowEventsInMultipleStreams=false; + // this is not super smart...just hard-coding the possible skims + private boolean skimV0=false; + private boolean skimThreeBody=false; + private boolean skimFEE=false; + private boolean skimMoller=false; + + private String ouputDir="skimData"; + + private String v0OutputFile="v0Skim"; + private String threeBodyOutputFile="threeBodySkim"; + private String FEEOutputFile="FEESkim"; + private String mollerOutputFile="mollerSkim"; + + private Skimmer v0Skimmer; + private Skimmer threeBodySkimmer; + private Skimmer FEESkimmer; + private Skimmer mollerSkimmer; + + protected Double beamEnergy; + + private int nprocessed = 0; + private int npassed = 0; + List writeSkimList=new ArrayList(); + + + public void endOfData() { + System.out.println(this.getClass().getSimpleName() + " Summary: "); + System.out.println("events processed = " + nprocessed); + System.out.println("events passed = " + npassed); + System.out.println(" rejection = " + ((double) npassed) / nprocessed); + + } + + @Override + protected void process(EventHeader event) { + writeSkimList.clear(); + // check each skim and see if event passes + if(skimV0 && + v0Skimmer.passSelection(event)) + writeSkimList.add(v0Skimmer); + + if(skimThreeBody && + threeBodySkimmer.passSelection(event)) + writeSkimList.add(threeBodySkimmer); + + if(skimFEE && + FEESkimmer.passSelection(event)) + writeSkimList.add(FEESkimmer); + if(skimMoller && + mollerSkimmer.passSelection(event)) + writeSkimList.add(mollerSkimmer); + + + if(writeSkimList.size()>0) + writeEventToStreams(event,writeSkimList); + } + + + public void writeEventToStreams(EventHeader event, List skimsToWrite){ + for(Skimmer skim: skimsToWrite) + skim.writeEvent(event); + } + + + public void incrementEventProcessed() { + nprocessed++; + } + + public void incrementEventPassed() { + npassed++; + } + + public void skipEvent() { + throw new Driver.NextEventException(); + } + + public void setBeamEnergy(double e) { + this.beamEnergy = e; + } + + public double getBeamEnergy() { + return this.beamEnergy; + } + + public void setV0OutputFile(String outputFile){ + this.v0OutputFile=outputFile; + } + + @Override + protected void detectorChanged(Detector detector) { + BeamEnergyCollection beamEnergyCollection = this.getConditionsManager() + .getCachedConditions(BeamEnergyCollection.class, "beam_energies").getCachedData(); + if (beamEnergy == null && beamEnergyCollection != null && beamEnergyCollection.size() != 0) + beamEnergy = beamEnergyCollection.get(0).getBeamEnergy(); + else { + LOGGER.log(Level.WARNING, "warning: beam energy not found. Using 3.74 GeV as the default energy"); + beamEnergy = 3.74; + } + + //set up skims + if(skimV0) + v0Skimmer=new V0Skimmer(ouputDir+"/"+v0OutputFile); + if(skimThreeBody) + threeBodySkimmer=new ThreeBodySkimmer(ouputDir+"/"+threeBodyOutputFile); + if(skimFEE) + FEESkimmer=new FEESkimmer(ouputDir+"/"+FEEOutputFile); + if(skimMoller) + mollerSkimmer=new MollerSkimmer(ouputDir+"/"+mollerOutputFile); + + } + + public void setSkimV0(boolean doSkim){ + this.skimV0=doSkim; + } + + public void setSkimThreeBody(boolean doSkim){ + this.skimThreeBody=doSkim; + } + public void setSkimFEE(boolean doSkim){ + this.skimFEE=doSkim; + } + public void setSkimMoller(boolean doSkim){ + this.skimMoller=doSkim; + } + +} diff --git a/recon/src/main/java/org/hps/recon/skims/Skimmer.java b/recon/src/main/java/org/hps/recon/skims/Skimmer.java new file mode 100644 index 0000000000..8e9008fcb7 --- /dev/null +++ b/recon/src/main/java/org/hps/recon/skims/Skimmer.java @@ -0,0 +1,119 @@ +package org.hps.recon.skims; + +import java.io.File; +import java.io.IOException; +import java.util.Arrays; +import java.util.Collection; +import java.util.HashSet; +import java.util.Set; + +import org.lcsim.event.EventHeader; +import org.lcsim.util.Driver; +import org.lcsim.lcio.LCIOWriter; + +/* **************************************** + + */ +abstract class Skimmer{ + private LCIOWriter writer; + private Set listIgnore = new HashSet(); + private Set listKeep = new HashSet(); + private File outputFile; + private int nprocessed = 0; + private int npassed = 0; + abstract boolean passSelection(EventHeader event); + + public Skimmer(String file) { + this(addFileExtension(file), null); + } + //methods below are taken from lcsim LCIODriver and shouldn't need to be touched + void writeEvent(EventHeader event){ + try { + writer.write(event); + } catch (IOException x) { + throw new RuntimeException("Error writing LCIO file", x); + } + } + + //this is taken from lcsim LCIODriver + public Skimmer(String file, Collection listIgnore) { + this(new File(addFileExtension(file)), listIgnore); + } + + //this is taken from lcsim LCIODriver + public Skimmer(File file, Collection listIgnore) { + this.outputFile = file; + if (listIgnore != null) { + this.listIgnore.addAll(listIgnore); + } + setupWriter(); + } + + public Skimmer(){ + } + + public void setOutputFilePath(String filePath) { + outputFile = new File(addFileExtension(filePath)); + } + + public void setIgnoreCollections(String[] ignoreCollections) { + listIgnore.addAll(Arrays.asList(ignoreCollections)); + } + + public void setWriteOnlyCollections(String[] keepCollections) { + listKeep.addAll(Arrays.asList(keepCollections)); + } + + public void setIgnoreCollection(String ignoreCollection) { + listIgnore.add(ignoreCollection); + } + + public void setWriteOnlyCollection(String writeOnlyCollection) { + listKeep.add(writeOnlyCollection); + } + + + //this is taken from lcsim LCIODriver + private void setupWriter() { + // Cleanup existing writer. + if (writer != null) { + try { + writer.flush(); + writer.close(); + writer = null; + } catch (IOException x) { + System.err.println(x.getMessage()); + } + } + + // Setup new writer. + try { + writer = new LCIOWriter(outputFile); + } catch (IOException x) { + throw new RuntimeException("Error creating writer", x); + } + writer.addAllIgnore(listIgnore); + writer.addAllWriteOnly(listKeep); + + try { + writer.reOpen(); + } catch (IOException x) { + throw new RuntimeException("Error rewinding LCIO file", x); + } + } + + private static String addFileExtension(String filePath) { + if (!filePath.endsWith(".slcio")) { + return filePath + ".slcio"; + } else + return filePath; + } + /////////////// done stealing from LCIODriver ///////////// + public void incrementEventProcessed() { + nprocessed++; + } + + public void incrementEventPassed() { + npassed++; + } +} diff --git a/recon/src/main/java/org/hps/recon/skims/ThreeBodySkimmer.java b/recon/src/main/java/org/hps/recon/skims/ThreeBodySkimmer.java new file mode 100644 index 0000000000..88bad9c0ae --- /dev/null +++ b/recon/src/main/java/org/hps/recon/skims/ThreeBodySkimmer.java @@ -0,0 +1,30 @@ +package org.hps.recon.skims; + +import org.lcsim.event.EventHeader; + + +public class ThreeBodySkimmer extends Skimmer { + private String _ThreeBodyCandidateCollectionName = "UnconstrainedThreeBodyCandidates"; + private double _clusterTimingCut = 20.0; // only used if _tight is true + private double _v0Chi2Cut = 100.0; + private double _trackChi2Cut = 80.0; + private double _trackDtCut = 20.0; + private double _trackPMax = 0.9; + private double _v0PMax = 1.4; + private int _nHitsMin=10; + + @Override + public boolean passSelection(EventHeader event){ + System.out.println(this.getClass().getName()+":: in pass selection"); + boolean pass=true; + + + return pass; + } + + + public ThreeBodySkimmer(String file) { + super(file, null); + } + +} diff --git a/recon/src/main/java/org/hps/recon/skims/V0Skimmer.java b/recon/src/main/java/org/hps/recon/skims/V0Skimmer.java new file mode 100644 index 0000000000..02e29f05f3 --- /dev/null +++ b/recon/src/main/java/org/hps/recon/skims/V0Skimmer.java @@ -0,0 +1,117 @@ +package org.hps.recon.skims; +import static java.lang.Math.abs; +import java.util.List; +import org.lcsim.event.EventHeader; +import org.hps.recon.ecal.cluster.ClusterUtilities; +import org.hps.recon.particle.ReconParticleDriver; +import org.hps.recon.tracking.TrackData; +import org.hps.recon.tracking.TrackType; +import org.hps.record.epics.EpicsData; +import org.hps.record.scalers.ScalerData; +import org.lcsim.event.EventHeader; +import org.lcsim.event.ReconstructedParticle; + +public class V0Skimmer extends Skimmer { + private String _V0CandidateCollectionName = "UnconstrainedV0Candidates"; + private double _clusterTimingCut = 20.0; // only used if _tight is true + private double _v0Chi2Cut = 100.0; + private double _trackChi2Cut = 80.0; + private double _trackDtCut = 20.0; // the 2-track time difference + private double _trackPMax = 3.4; //GeV + private double _v0PMax = 4.5; //GeV + private int _nHitsMin=10; + private boolean _reqClusterMatch=false; + private boolean _debug=false; + + @Override + public boolean passSelection(EventHeader event){ + if(_debug) + System.out.println(this.getClass().getName()+":: in pass selection"); + incrementEventProcessed(); + + if (!event.hasCollection(ReconstructedParticle.class, _V0CandidateCollectionName)) { + return false; + } + List V0Candidates = event.get(ReconstructedParticle.class, _V0CandidateCollectionName); + int nV0 = 0; // number of good V0 + for (ReconstructedParticle v0 : V0Candidates) { + ReconstructedParticle electron = v0.getParticles().get(ReconParticleDriver.ELECTRON); + ReconstructedParticle positron = v0.getParticles().get(ReconParticleDriver.POSITRON); + + // if (!TrackType.isGBL(v0.getType())) { // we only care about GBL vertices + // continue; + //} + + if (v0.getStartVertex().getChi2() > _v0Chi2Cut) { + continue; + } + + if(electron.getTracks().get(0).getTrackerHits().size()<_nHitsMin + || positron.getTracks().get(0).getTrackerHits().size()<_nHitsMin){ + continue; + } + if (electron.getTracks().get(0).getChi2() > _trackChi2Cut + || positron.getTracks().get(0).getChi2() > _trackChi2Cut) { + continue; + } + if (electron.getMomentum().magnitude() > _trackPMax || positron.getMomentum().magnitude() > _trackPMax) { + continue; + } + if (v0.getMomentum().magnitude() > _v0PMax) { + continue; + } + double eleTime = TrackData.getTrackTime(TrackData.getTrackData(event, electron.getTracks().get(0))); + double posTime = TrackData.getTrackTime(TrackData.getTrackData(event, positron.getTracks().get(0))); + if (Math.abs(eleTime - posTime) > _trackDtCut) { + continue; + } + if (_reqClusterMatch) { // requires cluster matches and cluster time cut + if (electron.getClusters().isEmpty() || positron.getClusters().isEmpty()) { + continue; + } + // calorimeter cluster timing cut + // first CalorimeterHit in the list is the seed crystal + double t1 = ClusterUtilities.getSeedHitTime(electron.getClusters().get(0)); + double t2 = ClusterUtilities.getSeedHitTime(positron.getClusters().get(0)); + + if (abs(t1 - t2) > _clusterTimingCut) { + continue; + } + } + nV0++; + } + + if (nV0>0){ + incrementEventPassed(); + return true; + } else + return false; + + } + + public V0Skimmer(String file) { + super(file, null); + } + + public void setClusterTimeCut(double cutVal){ + this._clusterTimingCut=cutVal; + } + public void setV0Chi2Cut(double cutVal){ + this._v0Chi2Cut=cutVal; + } + public void setTrackChi2Cut(double cutVal){ + this._trackChi2Cut=cutVal; + } + public void setTrackDtCut(double cutVal){ + this._trackDtCut=cutVal; + } + public void setTrackPMax(double cutVal){ + this._trackPMax=cutVal; + } + public void setV0PMax(double cutVal){ + this._v0PMax=cutVal; + } + public void setNHitsMin(int cutVal){ + this._nHitsMin=cutVal; + } +} diff --git a/steering-files/src/main/resources/org/hps/steering/production/StreamSkims.lcsim b/steering-files/src/main/resources/org/hps/steering/production/StreamSkims.lcsim new file mode 100644 index 0000000000..5f2d23beee --- /dev/null +++ b/steering-files/src/main/resources/org/hps/steering/production/StreamSkims.lcsim @@ -0,0 +1,42 @@ + + + + true + + + + + + + + + + + + + true + true + true + true + + + + + + ${outputFile}.slcio + + + From eb581ff5a632e5d03de2b13cfedd44216b1ff42a Mon Sep 17 00:00:00 2001 From: Matt Graham Date: Mon, 3 Mar 2025 07:29:49 -0800 Subject: [PATCH 2/2] impliments v0 skim plus read in cut parameters via resource --- .../recon/filtering/V0CandidateFilter.java | 25 ++++-- .../java/org/hps/recon/skims/FEESkimmer.java | 4 + .../org/hps/recon/skims/MollerSkimmer.java | 5 ++ .../org/hps/recon/skims/MultiSkimDriver.java | 65 +++++++++++++-- .../java/org/hps/recon/skims/Skimmer.java | 39 +++++---- .../org/hps/recon/skims/ThreeBodySkimmer.java | 4 + .../java/org/hps/recon/skims/V0Skimmer.java | 79 ++++++++++++++++--- .../recon/skims/v0skim_parameters_ver0.txt | 8 ++ .../org/hps/recon/tracking/TrackData.java | 4 +- 9 files changed, 192 insertions(+), 41 deletions(-) create mode 100644 recon/src/main/resources/org/hps/recon/skims/v0skim_parameters_ver0.txt diff --git a/recon/src/main/java/org/hps/recon/filtering/V0CandidateFilter.java b/recon/src/main/java/org/hps/recon/filtering/V0CandidateFilter.java index 129ec64352..d440594eb8 100644 --- a/recon/src/main/java/org/hps/recon/filtering/V0CandidateFilter.java +++ b/recon/src/main/java/org/hps/recon/filtering/V0CandidateFilter.java @@ -21,12 +21,13 @@ public class V0CandidateFilter extends EventReconFilter { private String _V0CandidateCollectionName = "UnconstrainedV0Candidates"; - private double _clusterTimingCut = 20.0; + private double _clusterTimingCut = 20.0; // only used if _tight is true private double v0Chi2Cut = 100.0; private double trackChi2Cut = 80.0; private double trackDtCut = 20.0; private double trackPMax = 0.9; private double v0PMax = 1.4; + private int nHitsMin=10; private boolean _tight = false; private boolean _keepEpicsDataEvents = false; @@ -57,13 +58,19 @@ protected void process(EventHeader event) { ReconstructedParticle electron = v0.getParticles().get(ReconParticleDriver.ELECTRON); ReconstructedParticle positron = v0.getParticles().get(ReconParticleDriver.POSITRON); - if (!TrackType.isGBL(v0.getType())) { // we only care about GBL vertices + // if (!TrackType.isGBL(v0.getType())) { // we only care about GBL vertices + // continue; + //} + + if (v0.getStartVertex().getChi2() > v0Chi2Cut) { continue; } - if (v0.getStartVertex().getChi2() > v0Chi2Cut) { - continue; - } - if (electron.getTracks().get(0).getChi2() > trackChi2Cut + + if(electron.getTracks().get(0).getTrackerHits().size() trackChi2Cut || positron.getTracks().get(0).getChi2() > trackChi2Cut) { continue; } @@ -180,7 +187,11 @@ public void setTightConstraint(boolean b) { public void setKeepEpicsDataEvents(boolean b) { _keepEpicsDataEvents = b; } - + + public void setNHitsMin(int m){ + nHitsMin=m; + } + protected void detectorChanged(Detector detector) { super.detectorChanged(detector); } diff --git a/recon/src/main/java/org/hps/recon/skims/FEESkimmer.java b/recon/src/main/java/org/hps/recon/skims/FEESkimmer.java index 4c6eeac1cb..5cf00e83ff 100644 --- a/recon/src/main/java/org/hps/recon/skims/FEESkimmer.java +++ b/recon/src/main/java/org/hps/recon/skims/FEESkimmer.java @@ -21,6 +21,10 @@ public boolean passSelection(EventHeader event){ return pass; } + @Override + public void setParameters(String parsFileName){ + return; + } public FEESkimmer(String file) { diff --git a/recon/src/main/java/org/hps/recon/skims/MollerSkimmer.java b/recon/src/main/java/org/hps/recon/skims/MollerSkimmer.java index ca6979f8df..a7d487684b 100644 --- a/recon/src/main/java/org/hps/recon/skims/MollerSkimmer.java +++ b/recon/src/main/java/org/hps/recon/skims/MollerSkimmer.java @@ -23,6 +23,11 @@ public boolean passSelection(EventHeader event){ } + @Override + public void setParameters(String parsFileName){ + return; + } + public MollerSkimmer(String file) { super(file, null); // this(super.addFileExtension(file), null); diff --git a/recon/src/main/java/org/hps/recon/skims/MultiSkimDriver.java b/recon/src/main/java/org/hps/recon/skims/MultiSkimDriver.java index b4a11f88af..8526a440fc 100644 --- a/recon/src/main/java/org/hps/recon/skims/MultiSkimDriver.java +++ b/recon/src/main/java/org/hps/recon/skims/MultiSkimDriver.java @@ -30,6 +30,11 @@ public class MultiSkimDriver extends Driver { private String threeBodyOutputFile="threeBodySkim"; private String FEEOutputFile="FEESkim"; private String mollerOutputFile="mollerSkim"; + + private String v0ParamFile="default"; + private String threeBodyParamFile="default"; + private String FEEParamFile="default"; + private String mollerParamFile="default"; private Skimmer v0Skimmer; private Skimmer threeBodySkimmer; @@ -45,9 +50,9 @@ public class MultiSkimDriver extends Driver { public void endOfData() { System.out.println(this.getClass().getSimpleName() + " Summary: "); - System.out.println("events processed = " + nprocessed); - System.out.println("events passed = " + npassed); - System.out.println(" rejection = " + ((double) npassed) / nprocessed); + System.out.println("V0 skim events processed = " + v0Skimmer.getNProcessed()); + System.out.println("events passed = " + v0Skimmer.getNPassed()); + System.out.println(" pass efficiency = " + v0Skimmer.getPassFraction()); } @@ -105,6 +110,16 @@ public double getBeamEnergy() { public void setV0OutputFile(String outputFile){ this.v0OutputFile=outputFile; } + public void setThreeBodyOutputFile(String outputFile){ + this.threeBodyOutputFile=outputFile; + } + + public void setFEEOutputFile(String outputFile){ + this.FEEOutputFile=outputFile; + } + public void setMollerOutputFile(String outputFile){ + this.mollerOutputFile=outputFile; + } @Override protected void detectorChanged(Detector detector) { @@ -119,16 +134,52 @@ protected void detectorChanged(Detector detector) { //set up skims if(skimV0) - v0Skimmer=new V0Skimmer(ouputDir+"/"+v0OutputFile); + v0Skimmer=setupSkimmer("v0",v0OutputFile, v0ParamFile); if(skimThreeBody) - threeBodySkimmer=new ThreeBodySkimmer(ouputDir+"/"+threeBodyOutputFile); + threeBodySkimmer=setupSkimmer("ThreeBody",threeBodyOutputFile, threeBodyParamFile); if(skimFEE) - FEESkimmer=new FEESkimmer(ouputDir+"/"+FEEOutputFile); + FEESkimmer=setupSkimmer("FEE",FEEOutputFile, FEEParamFile); if(skimMoller) - mollerSkimmer=new MollerSkimmer(ouputDir+"/"+mollerOutputFile); + mollerSkimmer=setupSkimmer("Moller",mollerOutputFile, mollerParamFile); + } + + + private Skimmer setupSkimmer(String evtType, String outputFile, String paramFile){ + Skimmer skm; + if(evtType.equals("v0")) + skm=new V0Skimmer(ouputDir+"/"+outputFile); + else if(evtType.equals("ThreeBody")) + skm=new ThreeBodySkimmer(ouputDir+"/"+outputFile); + else if(evtType.equals("FEE")) + skm=new FEESkimmer(ouputDir+"/"+outputFile); + else if(evtType.equals("Moller")) + skm=new MollerSkimmer(ouputDir+"/"+outputFile); + else{ + System.out.println(this.getClass().getName()+":: in setupSkimmer: invalid evtTrype = "+evtType); + return null; + } + if(!paramFile.equals("default")) + skm.setParameters(paramFile); + return skm; + + } + + public void setV0ParamFile(String pFile){ + this.v0ParamFile=pFile; + } + public void setThreeBodyParamFile(String pFile){ + this.threeBodyParamFile=pFile; } + public void setFEEParamFile(String pFile){ + this.FEEParamFile=pFile; + } + + public void setMollerParamFile(String pFile){ + this.mollerParamFile=pFile; + } + public void setSkimV0(boolean doSkim){ this.skimV0=doSkim; } diff --git a/recon/src/main/java/org/hps/recon/skims/Skimmer.java b/recon/src/main/java/org/hps/recon/skims/Skimmer.java index 8e9008fcb7..ba57925652 100644 --- a/recon/src/main/java/org/hps/recon/skims/Skimmer.java +++ b/recon/src/main/java/org/hps/recon/skims/Skimmer.java @@ -21,26 +21,19 @@ abstract class Skimmer{ private File outputFile; private int nprocessed = 0; private int npassed = 0; + abstract boolean passSelection(EventHeader event); + abstract void setParameters(String parsFileName); + //methods below are taken from lcsim LCIODriver and shouldn't need to be touched public Skimmer(String file) { this(addFileExtension(file), null); } - //methods below are taken from lcsim LCIODriver and shouldn't need to be touched - void writeEvent(EventHeader event){ - try { - writer.write(event); - } catch (IOException x) { - throw new RuntimeException("Error writing LCIO file", x); - } - } - - //this is taken from lcsim LCIODriver + public Skimmer(String file, Collection listIgnore) { this(new File(addFileExtension(file)), listIgnore); } - //this is taken from lcsim LCIODriver public Skimmer(File file, Collection listIgnore) { this.outputFile = file; if (listIgnore != null) { @@ -51,7 +44,15 @@ public Skimmer(File file, Collection listIgnore) { public Skimmer(){ } - + + void writeEvent(EventHeader event){ + try { + writer.write(event); + } catch (IOException x) { + throw new RuntimeException("Error writing LCIO file", x); + } + } + public void setOutputFilePath(String filePath) { outputFile = new File(addFileExtension(filePath)); } @@ -72,8 +73,6 @@ public void setWriteOnlyCollection(String writeOnlyCollection) { listKeep.add(writeOnlyCollection); } - - //this is taken from lcsim LCIODriver private void setupWriter() { // Cleanup existing writer. if (writer != null) { @@ -116,4 +115,16 @@ public void incrementEventProcessed() { public void incrementEventPassed() { npassed++; } + + public int getNProcessed(){ + return nprocessed; + } + + public int getNPassed(){ + return npassed; + } + + public double getPassFraction(){ + return ((double)npassed)/nprocessed; + } } diff --git a/recon/src/main/java/org/hps/recon/skims/ThreeBodySkimmer.java b/recon/src/main/java/org/hps/recon/skims/ThreeBodySkimmer.java index 88bad9c0ae..5ec125ff5c 100644 --- a/recon/src/main/java/org/hps/recon/skims/ThreeBodySkimmer.java +++ b/recon/src/main/java/org/hps/recon/skims/ThreeBodySkimmer.java @@ -22,6 +22,10 @@ public boolean passSelection(EventHeader event){ return pass; } + @Override + public void setParameters(String parsFileName){ + return; + } public ThreeBodySkimmer(String file) { super(file, null); diff --git a/recon/src/main/java/org/hps/recon/skims/V0Skimmer.java b/recon/src/main/java/org/hps/recon/skims/V0Skimmer.java index 02e29f05f3..897b7841c6 100644 --- a/recon/src/main/java/org/hps/recon/skims/V0Skimmer.java +++ b/recon/src/main/java/org/hps/recon/skims/V0Skimmer.java @@ -1,6 +1,12 @@ package org.hps.recon.skims; import static java.lang.Math.abs; + import java.util.List; +import java.io.BufferedReader; +import java.io.IOException; +import java.io.InputStream; +import java.io.InputStreamReader; + import org.lcsim.event.EventHeader; import org.hps.recon.ecal.cluster.ClusterUtilities; import org.hps.recon.particle.ReconParticleDriver; @@ -12,57 +18,61 @@ import org.lcsim.event.ReconstructedParticle; public class V0Skimmer extends Skimmer { - private String _V0CandidateCollectionName = "UnconstrainedV0Candidates"; + //default parameters...ok for 2021 run + private String _V0CandidateCollectionName = "UnconstrainedV0Candidates_KF"; private double _clusterTimingCut = 20.0; // only used if _tight is true private double _v0Chi2Cut = 100.0; private double _trackChi2Cut = 80.0; private double _trackDtCut = 20.0; // the 2-track time difference - private double _trackPMax = 3.4; //GeV + private double _trackPMax = 4.5; //GeV private double _v0PMax = 4.5; //GeV private int _nHitsMin=10; private boolean _reqClusterMatch=false; - private boolean _debug=false; - + private boolean _debug=false; @Override public boolean passSelection(EventHeader event){ if(_debug) System.out.println(this.getClass().getName()+":: in pass selection"); incrementEventProcessed(); - if (!event.hasCollection(ReconstructedParticle.class, _V0CandidateCollectionName)) { + if (!event.hasCollection(ReconstructedParticle.class, _V0CandidateCollectionName)) { return false; } + List V0Candidates = event.get(ReconstructedParticle.class, _V0CandidateCollectionName); int nV0 = 0; // number of good V0 for (ReconstructedParticle v0 : V0Candidates) { ReconstructedParticle electron = v0.getParticles().get(ReconParticleDriver.ELECTRON); ReconstructedParticle positron = v0.getParticles().get(ReconParticleDriver.POSITRON); - - // if (!TrackType.isGBL(v0.getType())) { // we only care about GBL vertices - // continue; - //} - + if (v0.getStartVertex().getChi2() > _v0Chi2Cut) { + if(_debug)System.out.println(this.getClass().getName()+":: failed vertex chi2"); continue; } - if(electron.getTracks().get(0).getTrackerHits().size()<_nHitsMin + if(electron.getTracks().get(0).getTrackerHits().size()<_nHitsMin || positron.getTracks().get(0).getTrackerHits().size()<_nHitsMin){ + // printParameters(); + if(_debug)System.out.println(this.getClass().getName()+":: failed nHitsMin "+electron.getTracks().get(0).getTrackerHits().size()+" "+positron.getTracks().get(0).getTrackerHits().size()+" nHitsMin = "+_nHitsMin); continue; } if (electron.getTracks().get(0).getChi2() > _trackChi2Cut || positron.getTracks().get(0).getChi2() > _trackChi2Cut) { + System.out.println(this.getClass().getName()+":: failed track chi2"); continue; } if (electron.getMomentum().magnitude() > _trackPMax || positron.getMomentum().magnitude() > _trackPMax) { + System.out.println(this.getClass().getName()+":: failed track momentum"); continue; } if (v0.getMomentum().magnitude() > _v0PMax) { + System.out.println(this.getClass().getName()+":: failed v0 momentum"); continue; } double eleTime = TrackData.getTrackTime(TrackData.getTrackData(event, electron.getTracks().get(0))); double posTime = TrackData.getTrackTime(TrackData.getTrackData(event, positron.getTracks().get(0))); if (Math.abs(eleTime - posTime) > _trackDtCut) { + System.out.println(this.getClass().getName()+":: failed track dt"); continue; } if (_reqClusterMatch) { // requires cluster matches and cluster time cut @@ -92,6 +102,53 @@ public boolean passSelection(EventHeader event){ public V0Skimmer(String file) { super(file, null); } + + @Override + public void setParameters(String parsFileName){ + String infilePreResDir = "/org/hps/recon/skims/"; + String infile=infilePreResDir+parsFileName; + InputStream inParamStream = this.getClass().getResourceAsStream(infile); + System.out.println(this.getClass().getName()+":: reading in per-sensor per-phase calibs from "+infile); + BufferedReader reader = new BufferedReader(new InputStreamReader(inParamStream)); + String line; + String delims = "[ ]+";// this will split strings between one or more spaces + try { + while ((line = reader.readLine()) != null) { + String[] tokens = line.split(delims); + String parName=tokens[0].replaceAll("\\s+",""); + System.out.println(this.getClass().getName()+":: parameter name = " + parName + "; value = " + tokens[1]); + putParam(parName,tokens[1]); + + } + } catch (IOException ex) { + System.out.println(this.getClass().getName()+":: died while reading parameters"); + return; + } + return; + } + + + private void putParam(String parName, String var){ + if(parName.equals("V0CandidateCollectionName")) + _V0CandidateCollectionName=var; + else if(parName.equals("clusterTimingCut")) + _clusterTimingCut=Double.parseDouble(var); + else if(parName.equals("v0Chi2Cut")) + _v0Chi2Cut=Double.parseDouble(var); + else if(parName.equals("trackChi2Cut")) + _trackChi2Cut=Double.parseDouble(var); + else if(parName.equals("trackDtCut")) + _trackDtCut=Double.parseDouble(var); + else if(parName.equals("trackPMax")) + _trackPMax=Double.parseDouble(var); + else if(parName.equals("v0PMax")) + _v0PMax=Double.parseDouble(var); + else if(parName.equals("nHitsMin")) + _nHitsMin=Integer.parseInt(var); + else if(parName.equals("reqClusterMatch")) + _reqClusterMatch=Boolean.parseBoolean(var); + } + public void setClusterTimeCut(double cutVal){ this._clusterTimingCut=cutVal; diff --git a/recon/src/main/resources/org/hps/recon/skims/v0skim_parameters_ver0.txt b/recon/src/main/resources/org/hps/recon/skims/v0skim_parameters_ver0.txt new file mode 100644 index 0000000000..8772c05b66 --- /dev/null +++ b/recon/src/main/resources/org/hps/recon/skims/v0skim_parameters_ver0.txt @@ -0,0 +1,8 @@ +V0CandidateCollectionName UnconstrainedV0Candidates_KF +trackChi2Cut 80.0 +nHitsMin 9 +v0Chi2Cut 100.0 +trackDtCut 20.0 +v0PMax 4.5 +reqClusterMatch false +clusterTimingCut 20.0 diff --git a/tracking/src/main/java/org/hps/recon/tracking/TrackData.java b/tracking/src/main/java/org/hps/recon/tracking/TrackData.java index 5ac9bc7408..b41e3a1be5 100644 --- a/tracking/src/main/java/org/hps/recon/tracking/TrackData.java +++ b/tracking/src/main/java/org/hps/recon/tracking/TrackData.java @@ -28,8 +28,8 @@ public class TrackData implements GenericObject { public static final int ECAL_BFY_INDEX = 6; //BFieldY at ECal TrackState public static final int SVTCENTER_BFY_INDEX = 7; //BFieldY at SVT Center public static final int TRACK_VOLUME_INDEX = 0; - public static final String TRACK_DATA_COLLECTION = "TrackData"; - public static final String TRACK_DATA_RELATION_COLLECTION = "TrackDataRelations"; + public static final String TRACK_DATA_COLLECTION = "KFTrackData"; + public static final String TRACK_DATA_RELATION_COLLECTION = "KFTrackDataRelations"; private final double[] doubles; private final float[] floats;