Belle II Software light-2509-fornax
restofevent.cc
1/**************************************************************************
2 * basf2 (Belle II Analysis Software Framework) *
3 * Author: The Belle II Collaboration *
4 * *
5 * See git log for contributors and copyright holders. *
6 * This file is licensed under LGPL-3.0, see LICENSE.md. *
7 **************************************************************************/
8#include <gtest/gtest.h>
9#include <framework/utilities/TestHelpers.h>
10#include "utilities/TestParticleFactory.h"
11#include <analysis/dataobjects/Particle.h>
12#include <analysis/VariableManager/Manager.h>
13#include <analysis/dataobjects/RestOfEvent.h>
14
15#include <analysis/VariableManager/Utility.h>
16#include <analysis/utility/PCmsLabTransform.h>
17#include <analysis/utility/ReferenceFrame.h>
18
19#include <framework/datastore/StoreArray.h>
20#include <framework/logging/Logger.h>
21#include <mdst/dataobjects/Track.h>
22#include <mdst/dataobjects/ECLCluster.h>
23#include <framework/gearbox/Gearbox.h>
24
25using namespace std;
26using namespace Belle2;
27using namespace Belle2::Variable;
28using namespace ROOT::Math;
29
30namespace {
31 class ROETest : public ::testing::Test {
32 protected:
34 void SetUp() override
35 {
36
38 StoreArray<ECLCluster> myECLClusters;
39 StoreArray<TrackFitResult> myTFRs;
40 StoreArray<Track> myTracks;
41 StoreArray<Particle> myParticles;
42 StoreArray<RestOfEvent> myROEs;
43 myECLClusters.registerInDataStore();
44 myTFRs.registerInDataStore();
45 myTracks.registerInDataStore();
46 myParticles.registerInDataStore();
47 myROEs.registerInDataStore();
48 myParticles.registerRelationTo(myROEs);
50
51 TestUtilities::TestParticleFactory factory;
52 ROOT::Math::XYZVector ipposition(0, 0, 0);
53 PxPyPzEVector ksmomentum(1, 0, 0, 3);
54 ROOT::Math::XYZVector ksposition(1.0, 0, 0);
55 //Creation of test particles:
56 //All daughters and mother particles have the same momenta within a decay
57 //In principle, this concept can be better developed if needed
58 auto* ksParticle = factory.produceParticle(string("^K_S0 -> ^pi+ ^pi-"), ksmomentum, ksposition);
59 PxPyPzEVector d0momentum(-2, 0, 0, 4);
60 auto* d0Particle = factory.produceParticle(string("^D0 -> ^K+ ^pi-"), d0momentum, ipposition);
61 PxPyPzEVector pi0momentum(-0.2, 0, 0, 1);
62 auto* pi0Particle = factory.produceParticle(string("^pi0 -> ^gamma ^gamma"), pi0momentum, ipposition);
63 PxPyPzEVector b0momentum(3, 0, 0, 5);
64 factory.produceParticle(string("^B0 -> [^K_S0 -> ^pi+ ^pi-] [^pi0 -> ^gamma ^gamma] ^gamma"), b0momentum, ipposition);
65
66 RestOfEvent roe;
67 vector<const Particle*> roeParticles;
68 roeParticles.push_back(ksParticle->getDaughter(0));
69 roeParticles.push_back(ksParticle->getDaughter(1));
70 roeParticles.push_back(d0Particle->getDaughter(0));
71 roeParticles.push_back(d0Particle->getDaughter(1));
72 roeParticles.push_back(pi0Particle->getDaughter(0));
73 roeParticles.push_back(pi0Particle->getDaughter(1));
74 roe.addParticles(roeParticles);
75 roe.initializeMask("cutMask", "TestModule");
76 //Exclude K_S0 pions
77 std::shared_ptr<Variable::Cut> trackSelection = std::shared_ptr<Variable::Cut>(Variable::Cut::compile("p > 1.5"));
78 //Exclude pi0 gammas
79 std::shared_ptr<Variable::Cut> eclSelection = std::shared_ptr<Variable::Cut>(Variable::Cut::compile("p > 1"));
80 roe.updateMaskWithCuts("cutMask", trackSelection, eclSelection);
81 roe.initializeMask("excludeMask", "TestModule");
82 vector<const Particle*> excludeParticles = {ksParticle->getDaughter(1), d0Particle->getDaughter(0)};
83 roe.excludeParticlesFromMask("excludeMask", excludeParticles, Particle::EParticleSourceObject::c_Track, true);
84 roe.initializeMask("keepMask", "TestModule");
85 roe.excludeParticlesFromMask("keepMask", excludeParticles, Particle::EParticleSourceObject::c_Track, false);
86 roe.initializeMask("V0Mask", "TestModule");
87 roe.updateMaskWithCuts("V0Mask"); // No selection
88 //Add V0 to ROE mask:
89 roe.updateMaskWithV0("V0Mask", ksParticle);
90 myROEs.appendNew(roe);
91 roe.print();
92 }
93
95 void TearDown() override
96 {
98 }
99 };
100
101 TEST_F(ROETest, hasParticle)
102 {
103 Gearbox& gearbox = Gearbox::getInstance();
104 gearbox.setBackends({std::string("file:")});
105 gearbox.close();
106 gearbox.open("geometry/Belle2.xml", false);
107 StoreArray<Particle> myParticles;
109 const RestOfEvent* roe = myROEs[0];
110 EXPECT_TRUE(roe->hasParticle(myParticles[0])); // K_S0_pi0
111 EXPECT_TRUE(roe->hasParticle(myParticles[1])); // K_S0_pi1
112 EXPECT_FALSE(roe->hasParticle(myParticles[2])); // K_S0
113 EXPECT_TRUE(roe->hasParticle(myParticles[3])); // D0_K
114 EXPECT_TRUE(roe->hasParticle(myParticles[4])); // D0_pi
115 EXPECT_FALSE(roe->hasParticle(myParticles[5])); // D0
116 EXPECT_TRUE(roe->hasParticle(myParticles[6])); // pi0_gamma0
117 EXPECT_TRUE(roe->hasParticle(myParticles[7])); // pi0_gamma1
118 EXPECT_FALSE(roe->hasParticle(myParticles[8])); // pi0
119 EXPECT_FALSE(roe->hasParticle(myParticles[9])); // B0_K_S0_pi0
120 EXPECT_FALSE(roe->hasParticle(myParticles[10])); // B0_K_S0_pi1
121 EXPECT_FALSE(roe->hasParticle(myParticles[11])); // B0_pi0_gamma0
122 }
123
124 TEST_F(ROETest, useROERecoilFrame)
125 {
126 Gearbox& gearbox = Gearbox::getInstance();
127 gearbox.setBackends({std::string("file:")});
128 gearbox.close();
129 gearbox.open("geometry/Belle2.xml", false);
130
131 StoreArray<Particle> myParticles;
133 StoreObjPtr<RestOfEvent> myROEObject;
137 myParticles[14]->addRelationTo(myROEs[0]); // Add relation to B0
138 myROEObject.assign(myROEs[0]);
139
141 // Recoil vector against all ROE particles
142 PxPyPzEVector pRecoil = T.getBeamFourMomentum() - myROEs[0]->get4Vector();
143 Particle tmp(pRecoil, 0);
144 RestFrame frame(&tmp);
145 //std::cout << "HER: " << T.getBeamParams().getHER()[0] << " LER: " << T.getBeamParams().getLER()[0] << std::endl;
146
147 const Manager::Var* var = Manager::Instance().getVariable("useROERecoilFrame(p)");
148 ASSERT_NE(var, nullptr);
149 EXPECT_FLOAT_EQ(std::get<double>(var->function(myParticles[5])),
150 frame.getMomentum(myParticles[5]->get4Vector()).P()); // test on D0 in ROE
151 EXPECT_FLOAT_EQ(std::get<double>(var->function(myParticles[14])),
152 frame.getMomentum(myParticles[14]->get4Vector()).P()); // test on B0 on signal side
153 var = Manager::Instance().getVariable("useROERecoilFrame(E)");
154 ASSERT_NE(var, nullptr);
155 EXPECT_FLOAT_EQ(std::get<double>(var->function(myParticles[5])),
156 frame.getMomentum(myParticles[5]->get4Vector()).E()); // test on D0 in ROE
157 EXPECT_FLOAT_EQ(std::get<double>(var->function(myParticles[14])),
158 frame.getMomentum(myParticles[14]->get4Vector()).E()); // test on B0 on signal side
159
161 DataStore::Instance().getEntry(myROEObject)->object = nullptr;
163 }
164
165 TEST_F(ROETest, getParticles)
166 {
168 const RestOfEvent* roe = myROEs[0];
169
170 EXPECT_TRUE(roe->getParticles().size() == 6);
171 EXPECT_TRUE(roe->getPhotons().size() == 2);
172 EXPECT_TRUE(roe->getHadrons().size() == 0);
173 EXPECT_TRUE(roe->getChargedParticles().size() == 4);
174 EXPECT_TRUE(roe->getChargedParticles("all", 321).size() == 1);
175 EXPECT_TRUE(roe->getChargedParticles("all", 211).size() == 3);
176 }
177
178 TEST_F(ROETest, updateMaskWithCuts)
179 {
180 StoreArray<Particle> myParticles;
182 const RestOfEvent* roe = myROEs[0];
183
184 EXPECT_FALSE(roe->hasParticle(myParticles[0], "cutMask")); // K_S0_pi0
185 EXPECT_FALSE(roe->hasParticle(myParticles[1], "cutMask")); // K_S0_pi0
186 EXPECT_TRUE(roe->hasParticle(myParticles[3], "cutMask")); // D0_K
187 EXPECT_TRUE(roe->hasParticle(myParticles[4], "cutMask")); // D0_pi
188 EXPECT_FALSE(roe->hasParticle(myParticles[6], "cutMask")); // pi0_gamma0
189 EXPECT_FALSE(roe->hasParticle(myParticles[7], "cutMask")); // pi0_gamma1
190 }
191 TEST_F(ROETest, excludeParticlesFromMask)
192 {
193 StoreArray<Particle> myParticles;
195 const RestOfEvent* roe = myROEs[0];
196
197 EXPECT_TRUE(roe->hasParticle(myParticles[0], "excludeMask")); // K_S0_pi0
198 EXPECT_FALSE(roe->hasParticle(myParticles[1], "excludeMask")); // K_S0_pi0
199 EXPECT_FALSE(roe->hasParticle(myParticles[3], "excludeMask")); // D0_K
200 EXPECT_TRUE(roe->hasParticle(myParticles[4], "excludeMask")); // D0_pi
201 EXPECT_TRUE(roe->hasParticle(myParticles[6], "excludeMask")); // pi0_gamma0
202 EXPECT_TRUE(roe->hasParticle(myParticles[7], "excludeMask")); // pi0_gamma1
203 // Inverted result with "!"
204 EXPECT_TRUE(!roe->hasParticle(myParticles[0], "keepMask")); // K_S0_pi0
205 EXPECT_FALSE(!roe->hasParticle(myParticles[1], "keepMask")); // K_S0_pi0
206 EXPECT_FALSE(!roe->hasParticle(myParticles[3], "keepMask")); // D0_K
207 EXPECT_TRUE(!roe->hasParticle(myParticles[4], "keepMask")); // D0_pi
208 // Photons not touched:
209 EXPECT_TRUE(roe->hasParticle(myParticles[6], "keepMask")); // pi0_gamma0
210 EXPECT_TRUE(roe->hasParticle(myParticles[7], "keepMask")); // pi0_gamma1
211 }
212 TEST_F(ROETest, updateMaskWithV0)
213 {
214 StoreArray<Particle> myParticles;
216 const RestOfEvent* roe = myROEs[0];
217 // Has particle checks for daughters
218 EXPECT_TRUE(roe->hasParticle(myParticles[0], "V0Mask")); // K_S0_pi0
219 EXPECT_TRUE(roe->hasParticle(myParticles[1], "V0Mask")); // K_S0_pi0
220 EXPECT_TRUE(roe->hasParticle(myParticles[3], "V0Mask")); // D0_K
221 EXPECT_TRUE(roe->hasParticle(myParticles[4], "V0Mask")); // D0_pi
222 EXPECT_TRUE(roe->hasParticle(myParticles[6], "V0Mask")); // pi0_gamma0
223 EXPECT_TRUE(roe->hasParticle(myParticles[7], "V0Mask")); // pi0_gamma1
224 //Get all particles, including the K_S0 in the mask:
225 auto v0maskParticles = roe->getParticles("V0Mask", false);
226 //Get all particles, but substitute K_S0 FS daughters:
227 auto v0maskParticlesUnpacked = roe->getParticles("V0Mask", true);
228 B2INFO("packed size is " << v0maskParticles.size());
229 for (auto* particle : v0maskParticles) {
230 B2INFO("My pdg: " << particle->getPDGCode());
231 }
232 B2INFO("unpacked size is " << v0maskParticlesUnpacked.size());
233 for (auto* particle : v0maskParticlesUnpacked) {
234 B2INFO("My pdg: " << particle->getPDGCode());
235 }
236 EXPECT_FLOAT_EQ(v0maskParticles.size(), 5);
237 EXPECT_FLOAT_EQ(v0maskParticlesUnpacked.size(), 6);
238 }
239
240 TEST_F(ROETest, maskNamingConventions)
241 {
242 RestOfEvent roe;
243
244 EXPECT_B2FATAL(roe.initializeMask("clean-mask", "maskNamingConventionTest"));
245 EXPECT_B2FATAL(roe.initializeMask("1mask", "maskNamingConventionTest"));
246 EXPECT_B2FATAL(roe.initializeMask("", "maskNamingConventionTest"));
247 EXPECT_B2FATAL(roe.initializeMask("all", "maskNamingConventionTest"));
248
249 roe.initializeMask("Clean_mask", "maskNamingConventionTest");
250 EXPECT_TRUE(roe.hasMask("Clean_mask"));
251
252 roe.initializeMask("cl3an_mask", "maskNamingConventionTest");
253 EXPECT_TRUE(roe.hasMask("cl3an_mask"));
254 }
255
256} //
@ c_DontWriteOut
Object/array should be NOT saved by output modules.
Definition DataStore.h:71
static DataStore & Instance()
Instance of singleton Store.
Definition DataStore.cc:53
void setInitializeActive(bool active)
Setter for m_initializeActive.
Definition DataStore.cc:93
void reset(EDurability durability)
Frees memory occupied by data store items and removes all objects from the map.
Definition DataStore.cc:85
StoreEntry * getEntry(const StoreAccessorBase &accessor)
Check whether an entry with the correct type is registered in the DataStore map and return it.
Definition DataStore.cc:293
Singleton class responsible for loading detector parameters from an XML file.
Definition Gearbox.h:34
static std::unique_ptr< GeneralCut > compile(const std::string &cut)
Definition GeneralCut.h:84
Class to hold Lorentz transformations from/to CMS and boost vector.
ROOT::Math::PxPyPzEVector getBeamFourMomentum() const
Returns LAB four-momentum of e+e-, i.e.
Class to store reconstructed particles.
Definition Particle.h:76
Rest frame of a particle.
This is a general purpose class for collecting reconstructed MDST data objects that are not used in r...
Definition RestOfEvent.h:55
std::vector< const Particle * > getParticles(const std::string &maskName=c_defaultMaskName, bool unpackComposite=true) const
Get all Particles from ROE mask.
std::vector< const Particle * > getChargedParticles(const std::string &maskName=c_defaultMaskName, unsigned int pdg=0, bool unpackComposite=true) const
Get charged particles from ROE mask.
void print(const std::string &maskName=c_defaultMaskName, bool unpackComposite=true) const
Prints the contents of a RestOfEvent object to screen.
void initializeMask(const std::string &name, const std::string &origin="unknown")
Initialize new mask.
void updateMaskWithCuts(const std::string &name, const std::shared_ptr< Variable::Cut > &trackCut=nullptr, const std::shared_ptr< Variable::Cut > &eclCut=nullptr, const std::shared_ptr< Variable::Cut > &klmCut=nullptr, bool updateExisting=false)
Update mask with cuts.
bool hasMask(const std::string &name) const
True if this ROE object has mask.
std::vector< const Particle * > getPhotons(const std::string &maskName=c_defaultMaskName, bool unpackComposite=true) const
Get photons from ROE mask.
bool hasParticle(const Particle *particle, const std::string &maskName=c_defaultMaskName) const
Check if ROE has StoreArray index of given to the list of unused tracks in the event.
void addParticles(const std::vector< const Particle * > &particle)
Add StoreArray indices of given Particles to the list of unused particles in the event.
void updateMaskWithV0(const std::string &name, const Particle *particleV0)
Update mask with composite particle.
std::vector< const Particle * > getHadrons(const std::string &maskName=c_defaultMaskName, bool unpackComposite=true) const
Get hadrons from ROE mask.
void excludeParticlesFromMask(const std::string &maskName, const std::vector< const Particle * > &particles, Particle::EParticleSourceObject listType, bool discard)
Update mask by keeping or excluding particles.
bool assign(TObject *object, bool replace=false)
Assign 'object' to this accessor.
bool registerInDataStore(DataStore::EStoreFlags storeFlags=DataStore::c_WriteOut)
Register the object/array in the DataStore.
Accessor to arrays stored in the data store.
Definition StoreArray.h:113
T * appendNew()
Construct a new T object at the end of the array.
Definition StoreArray.h:246
bool registerRelationTo(const StoreArray< TO > &toArray, DataStore::EDurability durability=DataStore::c_Event, DataStore::EStoreFlags storeFlags=DataStore::c_WriteOut, const std::string &namedRelation="") const
Register a relation to the given StoreArray.
Definition StoreArray.h:140
Type-safe access to single objects in the data store.
Definition StoreObjPtr.h:96
const Var * getVariable(std::string name)
Get the variable belonging to the given key.
Definition Manager.cc:58
static Manager & Instance()
get singleton instance.
Definition Manager.cc:26
const Belle2::Particle * produceParticle(const std::string &decayString, const ROOT::Math::PxPyPzEVector &momentum, const ROOT::Math::XYZVector &vertex)
Main method to produce particles.
static Gearbox & getInstance()
Return reference to the Gearbox instance.
Definition Gearbox.cc:81
Abstract base class for different kinds of events.
STL namespace.
TObject * object
The pointer to the actual object.
Definition StoreEntry.h:48
A variable returning a floating-point value for a given Particle.
Definition Manager.h:146