BuildInitialState.cc
1 /*
2  * MoMEMta: a modular implementation of the Matrix Element Method
3  * Copyright (C) 2016 Universite catholique de Louvain (UCL), Belgium
4  *
5  * This program is free software: you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation, either version 3 of the License, or
8  * (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program. If not, see <http://www.gnu.org/licenses/>.
17  */
18 
19 #include <functional>
20 
21 #include <Math/Vector3D.h>
22 #include <Math/Boost.h>
23 
24 #include <momemta/Module.h>
25 #include <momemta/ParameterSet.h>
26 #include <momemta/Types.h>
27 
70 class BuildInitialState: public Module {
71  public:
72 
73  BuildInitialState(PoolPtr pool, const ParameterSet& parameters): Module(pool, parameters.getModuleName()) {
74  if (parameters.get<bool>("do_transverse_boost", false)) {
75  do_compute_initials = compute_initials_boost;
76  } else {
77  do_compute_initials = compute_initials_trivial;
78  }
79 
80  halved_sqrt_s = parameters.globalParameters().get<double>("energy") / 2;
81 
82  std::vector<InputTag> input_particles_tags = parameters.get<std::vector<InputTag>>("particles");
83  for (auto& t: input_particles_tags)
84  input_particles.push_back(get<LorentzVector>(t));
85  };
86 
87  virtual Status work() override {
88 
89  partons->clear();
90 
91  LorentzVectorRefCollection particles;
92  for (auto& p: input_particles) {
93  particles.push_back(std::ref(*p));
94  }
95 
96  do_compute_initials(particles);
97 
98  // Check if solutions are physical
99  if ((*partons)[0].E() > halved_sqrt_s || (*partons)[1].E() > halved_sqrt_s )
100  return Status::NEXT;
101 
102  return Status::OK;
103  }
104 
105  private:
106  using compute_initials_signature = std::function<void(const LorentzVectorRefCollection&)>;
107 
108  compute_initials_signature do_compute_initials;
109 
110  compute_initials_signature compute_initials_trivial =
111  [&](const LorentzVectorRefCollection& particles) {
112  LorentzVector tot;
113  for (const auto& p: particles)
114  tot += p.get();
115 
116  double q1Pz = (tot.Pz() + tot.E()) / 2.;
117  double q2Pz = (tot.Pz() - tot.E()) / 2.;
118 
119  partons->push_back(LorentzVector(0., 0., q1Pz, std::abs(q1Pz)));
120  partons->push_back(LorentzVector(0., 0., q2Pz, std::abs(q2Pz)));
121  };
122 
123  compute_initials_signature compute_initials_boost =
124  [&](const LorentzVectorRefCollection& particles) {
125  LorentzVector tot;
126  for (const auto& p: particles)
127  tot += p.get();
128 
129  // Define boost that puts the transverse total momentum vector in its CoM frame
130  LorentzVector transverse_tot = tot;
131  transverse_tot.SetPz(0);
132  ROOT::Math::XYZVector isr_deBoost_vector( transverse_tot.BoostToCM() );
133 
134  // In the "transverse" CoM frame, use total Pz and E to define initial longitudinal quark momenta
135  const ROOT::Math::Boost isr_deBoost( isr_deBoost_vector );
136  const ROOT::Math::PxPyPzEVector new_tot( isr_deBoost * tot );
137 
138  double q1Pz = (new_tot.Pz() + new_tot.E()) / 2.;
139  double q2Pz = (new_tot.Pz() - new_tot.E()) / 2.;
140 
141  partons->push_back(LorentzVector(0., 0., q1Pz, std::abs(q1Pz)));
142  partons->push_back(LorentzVector(0., 0., q2Pz, std::abs(q2Pz)));
143 
144  // Boost initial parton momenta by the opposite of the transverse boost needed to put the whole system in its CoM
145  const ROOT::Math::Boost isr_boost( -isr_deBoost_vector );
146  (*partons)[0] = isr_boost * (*partons)[0];
147  (*partons)[1] = isr_boost * (*partons)[1];
148  };
149 
150  double halved_sqrt_s;
151 
152  std::vector<Value<LorentzVector>> input_particles;
153 
154  std::shared_ptr<std::vector<LorentzVector>> partons = produce<std::vector<LorentzVector>>("partons");
155 };
156 
157 REGISTER_MODULE(BuildInitialState)
158  .Inputs("particles")
159  .Output("partons")
160  .GlobalAttr("energy:double")
161  .Attr("do_transverse_boost:bool=false");
Build the initial partons given the whole final state.
Parent class for all the modules.
Definition: Module.h:37
A class encapsulating a lua table.
Definition: ParameterSet.h:82
virtual Status work() override
Main function.
Module(PoolPtr pool, const std::string &name)
Constructor.
Definition: Module.h:61