DAS  3.0
Das Analysis System
TPS.h
Go to the documentation of this file.
1 #pragma once
2 
5 
6 #include <algorithm>
7 #include <list>
8 #include <vector>
9 #include <numeric>
10 #include "Math/Vector2D.h"
11 
13 
14 #include <darwin.h>
15 
16 namespace DE = Darwin::Exceptions;
17 
18 namespace DAS::TPS {
19 
31 template<class Jet>
32 struct MultiJets {
33 
34  std::vector<Jet> jets;
36 
37  MultiJets(const std::vector<Jet>& inputJets, int minpt):
38  jets(PhaseSpaceSelection(inputJets, minpt))
39  {
40  if (jets.size() > 1){
41  dijet = jets.at(0) + jets.at(1);
42  }
43  }
44 
45  // At least 2 jets
46  explicit operator bool() const {
47  return jets.size() > 1;
48  }
49 
50  double jetswgt() const {
51  return accumulate(jets.begin(), jets.end(), 1.0,
52  [] (double w, const Jet& j) {
53  return w * j.weights.front();
54  });
55  }
56 
57  double Ht () const
58  {
59  return accumulate(jets.begin(), jets.end(), 0.0,
60  [](double sum, const auto& jet) {
61  return sum + jet.CorrPt();
62  });
63  }
64 
71  float SpT() const
72  {
73  using namespace std;
74  if (jets.size() < 6)
75  BOOST_THROW_EXCEPTION( invalid_argument("insufficient jetMultiplicity for SpT calculation") );
76 
77  float sumS = 0.0f;
78  for (const auto& triple : jetCombinations) {
79  float S2 = 0.0f;
80  // triple.size() == 3, each triple[i] is a pair<int,int>
81  for (auto& pr : triple) {
82  FourVector jet1 = jets[pr.first ].CorrP4();
83  FourVector jet2 = jets[pr.second].CorrP4();
84  ROOT::Math::XYVector pTsum(jet1.Px() + jet2.Px(), jet1.Py() + jet2.Py());
85  S2 += pow( pTsum.R() / (jets[pr.first].CorrPt() + jets[pr.second].CorrPt()), 2 );
86  }
87  sumS += sqrt(S2 / 3.0f);
88  }
89  return sumS / static_cast<float>(jetCombinations.size());
90  }
91 
98  float Sphi() const
99  {
100  using namespace std;
101  if (jets.size() < 6)
102  BOOST_THROW_EXCEPTION( invalid_argument("insufficient jetMultiplicity for Sphi calculation") );
103 
104  float sumS = 0.0f;
105  for (const auto& triple : jetCombinations) {
106  float S2 = 0.0f;
107  for (auto& pr : triple) {
108  FourVector jet1 = jets[pr.first ].CorrP4();
109  FourVector jet2 = jets[pr.second].CorrP4();
110  S2 += pow(DeltaPhi(jet1, jet2), 2);
111  }
112  sumS += sqrt(S2 / 3.0f);
113  }
114  return sumS / static_cast<float>(jetCombinations.size());
115  }
116 private:
117  // Generates all 15 unique pairings of 6 elements (labelled 0..5),
118  // Each result is a vector of 3 std::pairs<int,int>.
119  static const std::vector<std::vector<std::pair<int, int>>>& getJetPairings() {
120  static const auto jetPairs = []() {
121  std::vector<int> elements{0, 1, 2, 3, 4, 5};
122  std::vector<std::pair<int, int>> current;
123  std::vector<std::vector<std::pair<int, int>>> results;
124 
125  // Helper function that recursively generates all ways to partition 'elements'
126  // into pairs. Each unique partition is pushed into 'allPairs' as a list of
127  // (a,b) pairs, stored in current recursion via 'current'.
128  auto pairJetsIndices = [](const std::vector<int>& elements,
129  std::vector<std::pair<int, int>>& current,
130  std::vector<std::vector<std::pair<int, int>>>& results,
131  auto&& self) -> void {
132  // If no elements remain, we've formed all pairs for this arrangement
133  if (elements.empty()) {
134  results.push_back(current);
135  return;
136  }
137  // Take the first element
138  int first = elements.front();
139  // Remaining elements
140  std::vector<int> rest(elements.begin() + 1, elements.end());
141 
142  // Try pairing 'first' with each of the others
143  for (size_t i = 0; i < rest.size(); ++i) {
144  int partner = rest[i];
145  // Add this pair to 'current'
146  current.emplace_back(first, partner);
147 
148  // Build the list for the next recursion by removing 'partner'
149  std::vector<int> next;
150  next.reserve(rest.size() - 1);
151  for (size_t j = 0; j < rest.size(); ++j) {
152  if (j != i)
153  next.push_back(rest[j]);
154  }
155 
156  // Recurse with the remaining elements
157  self(next, current, results, self);
158  current.pop_back();
159  }
160  };
161  // Start the recursion
162  pairJetsIndices(elements, current, results, pairJetsIndices);
163  return results;
164  }();
165  return jetPairs;
166  }
167 
168  // `jetCombinations` stores all possible unique ways of dividing six elements into three pairs.
169  const std::vector<std::vector<std::pair<int, int>>>& jetCombinations = getJetPairings();
170 
171 };
172 
173 } // end of namespace DAS::TPS
DAS::TPS::MultiJets::MultiJets
MultiJets(const std::vector< Jet > &inputJets, int minpt)
Definition: TPS.h:37
DAS::TPS::MultiJets::Sphi
float Sphi() const
Definition: TPS.h:98
DAS::TPS::MultiJets::jetswgt
double jetswgt() const
Definition: TPS.h:50
DAS::TPS
Definition: applyEventMixing.cc:31
DAS::TPS::MultiJets::Ht
double Ht() const
Definition: TPS.h:57
Ntupliser_cfg.f
f
Definition: Ntupliser_cfg.py:309
DAS::JetEnergy::w
static const float w
Definition: common.h:53
Jet.h
DAS::MN::minpt
static const double minpt
Definition: getMNobservables.cc:39
Darwin::Exceptions
Handling of exceptions.
Definition: darwin.h:36
DAS::TPS::MultiJets::getJetPairings
static const std::vector< std::vector< std::pair< int, int > > > & getJetPairings()
Definition: TPS.h:119
DAS::TPS::MultiJets::dijet
Di< const Jet, const Jet > dijet
Definition: TPS.h:35
DAS::Di< const Jet, const Jet >
DAS::TPS::MultiJets::jetCombinations
const std::vector< std::vector< std::pair< int, int > > > & jetCombinations
Definition: TPS.h:169
DAS::TPS::MultiJets::SpT
float SpT() const
Definition: TPS.h:71
Di.h
DAS::TPS::PhaseSpaceSelection
std::vector< Jet > PhaseSpaceSelection(const std::vector< Jet > &jets, float minpt)
return Jets pass the phase space selection
Definition: common.h:18
DAS::TPS::MultiJets::jets
std::vector< Jet > jets
Definition: TPS.h:34
DAS::FourVector
ROOT::Math::LorentzVector< ROOT::Math::PtEtaPhiM4D< float > > FourVector
Definition: PhysicsObject.h:15
DAS::TPS::MultiJets
Definition: TPS.h:32
common.h