Page MenuHomeHEPForge

No OneTemporary

This file is larger than 256 KB, so syntax highlighting was skipped.
diff --git a/MatrixElement/Hadron/MEDiffraction.cc b/MatrixElement/Hadron/MEDiffraction.cc
--- a/MatrixElement/Hadron/MEDiffraction.cc
+++ b/MatrixElement/Hadron/MEDiffraction.cc
@@ -1,873 +1,873 @@
// -*- C++ -*-
//
// This is the implementation of the non-inlined, non-templated member
// functions of the MEDiffraction class.
//
#include "MEDiffraction.h"
#include "ThePEG/Interface/ClassDocumentation.h"
#include "ThePEG/Utilities/SimplePhaseSpace.h"
#include "ThePEG/Repository/EventGenerator.h"
#include "ThePEG/Handlers/StandardXComb.h"
#include "ThePEG/Persistency/PersistentOStream.h"
#include "ThePEG/Persistency/PersistentIStream.h"
using namespace Herwig;
#include "ThePEG/PDT/EnumParticles.h"
#include "ThePEG/MatrixElement/Tree2toNDiagram.h"
#include "ThePEG/Interface/Parameter.h"
#include "ThePEG/Interface/Switch.h"
#include "Herwig/Utilities/Kinematics.h"
MEDiffraction::MEDiffraction()
: HwMEBase(),
- deltaOnly(false),
+ deltaOnly(false),
isInRunPhase(false),
theProtonMass(0.93827203*GeV)
{}
void MEDiffraction::getDiagrams() const {
//incoming particles
cPDPair incomingHardons = generator()->eventHandler()->incoming();
-
+
tcPDPtr pom = getParticleData(990);
//get incoming particles
tcPDPtr prt11 = getParticleData(incomingHardons.first->id());
tcPDPtr prt12 = getParticleData(incomingHardons.second->id());
//get sign of id
int sign1=0, sign2=0;
sign1 = (incomingHardons.first->id() > 0) ? 1 : -1;
sign2 = (incomingHardons.second->id() > 0) ? 1 : -1;
tcPDPtr prt21 = getParticleData(sign1*2214);//Delta+
tcPDPtr prt22 = getParticleData(sign2*2214);//Delta+
//for the left side
tcPDPtr q11 = getParticleData(sign1*2); //u
tcPDPtr q21 = getParticleData(sign1*1); //d
//for the right side
tcPDPtr q12 = getParticleData(sign2*2); //u
tcPDPtr q22 = getParticleData(sign2*1); //d
//for the left side
tcPDPtr dq11 = getParticleData(sign1*2101); //ud_0
tcPDPtr dq111 = getParticleData(sign1*2103); //ud_1
tcPDPtr dq21 = getParticleData(sign1*2203); //uu_1
//for the right side
tcPDPtr dq12 = getParticleData(sign2*2101); //ud_0
tcPDPtr dq112 = getParticleData(sign2*2103); //ud_1
tcPDPtr dq22 = getParticleData(sign2*2203); //uu_1
tcPDPtr gl = getParticleData(21);//gluon
//switch between dissociation decays to different
//number of clusters or dissociation into delta only
//(Maybe can be automated???)
//(Should be generalized to ppbar, for example!!!)
switch(dissociationDecay){
- case 0: //one cluster or only delta in the final state
- if(deltaOnly) //only delta in the final state
- {
-
- switch (diffDirection){
- case 0:
- add(new_ptr((Tree2toNDiagram(3), prt11, pom, prt12, 1, prt21, 2, prt12, -1)));
- break;
- case 1:
- add(new_ptr((Tree2toNDiagram(3), prt11, pom, prt12, 1, prt11, 2, prt22, -1)));
- break;
- case 2:
- add(new_ptr((Tree2toNDiagram(3), prt11, pom, prt12, 1, prt21, 2, prt22, -1)));
- break;
- }
-
-
- }else
- {
- //switch between direction of dissociated proton for single diffraction or
- //double diffraction
- switch (diffDirection){
- case 0: //left
- //u -- ud_0
- add(new_ptr((Tree2toNDiagram(4), prt11, q11, pom, prt12, 3, prt12, 1, dq11, 2, q11, -1)));
- //d -- uu_1
- add(new_ptr((Tree2toNDiagram(4), prt11, q21, pom, prt12, 3, prt12, 1, dq21, 2, q21, -2)));
- break;
- case 1: //right
- //u -- ud_0
- add(new_ptr((Tree2toNDiagram(4), prt11, pom, q12, prt12, 1, prt11, 3, dq12, 2, q12, -1)));
-
- //d -- uu_1
- add(new_ptr((Tree2toNDiagram(4), prt11, pom, q22, prt12, 1, prt11, 3, dq22, 2, q22, -2)));
- break;
- case 2: //double
- //u -- ud_0 left u -- ud_0 right
- add(new_ptr((Tree2toNDiagram(5), prt11, q11, pom, q12, prt12, 1, dq11, 2, q11, 3, q12, 4, dq12, -1)));
-
- //u -- ud_0 left d -- uu_1 right
- add(new_ptr((Tree2toNDiagram(5), prt11, q11, pom, q22, prt12, 1, dq11, 2, q11, 3, q22, 4, dq22, -2)));
-
- //d -- uu_1 left u -- ud_0 right
- add(new_ptr((Tree2toNDiagram(5), prt11, q21, pom, q12, prt12, 1,dq21, 2, q21, 3, q12, 4, dq12, -3)));
-
- //d -- uu_1 left d -- uu_1 right
- add(new_ptr((Tree2toNDiagram(5), prt11, q21, pom, q22, prt12, 1, dq21, 2, q21, 3, q22, 4, dq22, -4)));
- break;
- }
-
- }
- break;
- case 1: //two clusters (cases with ud_1 not included)
- switch (diffDirection){
- case 0: //left
- //u -- ud_0
- add(new_ptr((Tree2toNDiagram(5), prt11, q11, gl, pom, prt12, 1, dq11, 2, q11, 3, gl, 4, prt12, -1)));
- //d -- uu_1
- add(new_ptr((Tree2toNDiagram(5), prt11, q21, gl, pom, prt12, 1, dq21, 2, q21, 3, gl, 4, prt12, -2)));
- break;
- case 1: //right
- //u -- ud_0
- add(new_ptr((Tree2toNDiagram(5), prt11, pom, gl, q12, prt12, 1, prt11, 2, gl, 3, q12, 4, dq12, -1)));
- //d -- ud_1
- add(new_ptr((Tree2toNDiagram(5), prt11, pom, gl, q22, prt12, 1, prt11, 2, gl, 3, q22, 4, dq22, -2)));
- break;
- case 2: //double
- //u -- ud_0 left u -- ud_0 right
- add(new_ptr((Tree2toNDiagram(7), prt11, q11, gl, pom, gl, q12, prt12, 1, dq11, 2, q11, 3, gl, 4,
- gl, 5, q12, 6, dq12, -1)));
- //u -- ud_0 left d -- uu_1 right
- add(new_ptr((Tree2toNDiagram(7), prt11, q11, gl, pom, gl, q22, prt12, 1, dq11, 2, q11, 3, gl, 4,
- gl, 5, q22, 6, dq22, -2)));
- //d -- uu_1 left u -- ud_0 right
- add(new_ptr((Tree2toNDiagram(7), prt11, q21, gl, pom, gl, q12, prt12, 1, dq21, 2, q21, 3, gl, 4,
- gl, 5, q12, 6, dq12, -3)));
- //d -- uu_1 left d -- uu_1 right
- add(new_ptr((Tree2toNDiagram(7), prt11, q21, gl, pom, gl, q22, prt12, 1, dq21, 2, q21, 3, gl, 4,
- gl, 5, q22, 6, dq22, -4)));
- break;
- }
- break;
+ case 0: //one cluster or only delta in the final state
+ if(deltaOnly) //only delta in the final state
+ {
+
+ switch (diffDirection){
+ case 0:
+ add(new_ptr((Tree2toNDiagram(3), prt11, pom, prt12, 1, prt21, 2, prt12, -1)));
+ break;
+ case 1:
+ add(new_ptr((Tree2toNDiagram(3), prt11, pom, prt12, 1, prt11, 2, prt22, -1)));
+ break;
+ case 2:
+ add(new_ptr((Tree2toNDiagram(3), prt11, pom, prt12, 1, prt21, 2, prt22, -1)));
+ break;
+ }
+
+
+ }else
+ {
+ //switch between direction of dissociated proton for single diffraction or
+ //double diffraction
+ switch (diffDirection){
+ case 0: //left
+ //u -- ud_0
+ add(new_ptr((Tree2toNDiagram(4), prt11, q11, pom, prt12, 3, prt12, 1, dq11, 2, q11, -1)));
+ //d -- uu_1
+ add(new_ptr((Tree2toNDiagram(4), prt11, q21, pom, prt12, 3, prt12, 1, dq21, 2, q21, -2)));
+ break;
+ case 1: //right
+ //u -- ud_0
+ add(new_ptr((Tree2toNDiagram(4), prt11, pom, q12, prt12, 1, prt11, 3, dq12, 2, q12, -1)));
+
+ //d -- uu_1
+ add(new_ptr((Tree2toNDiagram(4), prt11, pom, q22, prt12, 1, prt11, 3, dq22, 2, q22, -2)));
+ break;
+ case 2: //double
+ //u -- ud_0 left u -- ud_0 right
+ add(new_ptr((Tree2toNDiagram(5), prt11, q11, pom, q12, prt12, 1, dq11, 2, q11, 3, q12, 4, dq12, -1)));
+
+ //u -- ud_0 left d -- uu_1 right
+ add(new_ptr((Tree2toNDiagram(5), prt11, q11, pom, q22, prt12, 1, dq11, 2, q11, 3, q22, 4, dq22, -2)));
+
+ //d -- uu_1 left u -- ud_0 right
+ add(new_ptr((Tree2toNDiagram(5), prt11, q21, pom, q12, prt12, 1,dq21, 2, q21, 3, q12, 4, dq12, -3)));
+
+ //d -- uu_1 left d -- uu_1 right
+ add(new_ptr((Tree2toNDiagram(5), prt11, q21, pom, q22, prt12, 1, dq21, 2, q21, 3, q22, 4, dq22, -4)));
+ break;
+ }
+
+ }
+ break;
+ case 1: //two clusters (cases with ud_1 not included)
+ switch (diffDirection){
+ case 0: //left
+ //u -- ud_0
+ add(new_ptr((Tree2toNDiagram(5), prt11, q11, gl, pom, prt12, 1, dq11, 2, q11, 3, gl, 4, prt12, -1)));
+ //d -- uu_1
+ add(new_ptr((Tree2toNDiagram(5), prt11, q21, gl, pom, prt12, 1, dq21, 2, q21, 3, gl, 4, prt12, -2)));
+ break;
+ case 1: //right
+ //u -- ud_0
+ add(new_ptr((Tree2toNDiagram(5), prt11, pom, gl, q12, prt12, 1, prt11, 2, gl, 3, q12, 4, dq12, -1)));
+ //d -- ud_1
+ add(new_ptr((Tree2toNDiagram(5), prt11, pom, gl, q22, prt12, 1, prt11, 2, gl, 3, q22, 4, dq22, -2)));
+ break;
+ case 2: //double
+ //u -- ud_0 left u -- ud_0 right
+ add(new_ptr((Tree2toNDiagram(7), prt11, q11, gl, pom, gl, q12, prt12, 1, dq11, 2, q11, 3, gl, 4,
+ gl, 5, q12, 6, dq12, -1)));
+ //u -- ud_0 left d -- uu_1 right
+ add(new_ptr((Tree2toNDiagram(7), prt11, q11, gl, pom, gl, q22, prt12, 1, dq11, 2, q11, 3, gl, 4,
+ gl, 5, q22, 6, dq22, -2)));
+ //d -- uu_1 left u -- ud_0 right
+ add(new_ptr((Tree2toNDiagram(7), prt11, q21, gl, pom, gl, q12, prt12, 1, dq21, 2, q21, 3, gl, 4,
+ gl, 5, q12, 6, dq12, -3)));
+ //d -- uu_1 left d -- uu_1 right
+ add(new_ptr((Tree2toNDiagram(7), prt11, q21, gl, pom, gl, q22, prt12, 1, dq21, 2, q21, 3, gl, 4,
+ gl, 5, q22, 6, dq22, -4)));
+ break;
+ }
+ break;
}
}
Energy2 MEDiffraction::scale() const {
return sqr(10*GeV);
}
int MEDiffraction::nDim() const {
return 0;
}
void MEDiffraction::setKinematics() {
HwMEBase::setKinematics(); // Always call the base class method first
}
bool MEDiffraction::generateKinematics(const double * ) {
// generate the masses of the particles
for (size_t i = 2; i < meMomenta().size(); ++i)
- meMomenta()[i] = Lorentz5Momentum(mePartonData()[i]->generateMass());
+ meMomenta()[i] = Lorentz5Momentum(mePartonData()[i]->generateMass());
/* sample M12, M22 and t, characterizing the diffractive final state */
const pair<pair<Energy2,Energy2>,Energy2> point = diffractiveMassAndMomentumTransfer();
const Energy2 M12 (point.first.first);
const Energy2 M22 (point.first.second);
const Energy2 t(point.second);
/* construct the hadronic momenta in the lab frame */
const double phi = UseRandom::rnd() * Constants::twopi;
const Energy cmEnergy = generator()->maximumCMEnergy();
const Energy2 s = sqr(cmEnergy);
//proton mass
const Energy2 m2 = sqr( theProtonMass );
const Energy E3 = (s - M22 + M12) / (2.*cmEnergy);
const Energy E4 = (s + M22 - M12) / (2.*cmEnergy);
//Momentum of outgoing proton and dissociated proton
const Energy pprime = sqrt(kallen(s, M12, M22)) / (2.*cmEnergy);
- //costheta of scattering angle
+ //costheta of scattering angle
double costheta = s*(s + 2*t - 2*m2 - M12 - M22)
/ sqrt( kallen(s, M12, M22)*kallen(s, m2, m2) );
assert(abs(costheta)<=1.);
const Energy pzprime = pprime*costheta;
const Energy pperp = pprime*sqrt(1 - sqr(costheta));
/* momenta in the lab frame */
const Lorentz5Momentum p3 = Lorentz5Momentum(pperp*cos(phi), pperp*sin(phi), pzprime, E3);
const Lorentz5Momentum p4 = Lorentz5Momentum(-pperp*cos(phi), -pperp*sin(phi), -pzprime, E4);
/* decay dissociated proton into quark-diquark */
//squares of constituent masses of quark and diquark
const Energy2 mqq2(sqr(mqq())), mq2(sqr(mq()));
Energy2 Mx2;
switch(diffDirection){
- case 0:
- Mx2=M12;
- break;
- case 1:
- Mx2=M22;
- break;
+ case 0:
+ Mx2=M12;
+ break;
+ case 1:
+ Mx2=M22;
+ break;
}
/* Select between left/right single diffraction and double diffraction */
//check if we want only delta for the excited state
//pair of momenta for double decay for a two cluster case
pair<Lorentz5Momentum,Lorentz5Momentum> momPair, momPair1;
//fraction of momenta
double frac = UseRandom::rnd();
switch(dissociationDecay){
- case 0:
- if(!deltaOnly)
- {
-
- pair<Lorentz5Momentum,Lorentz5Momentum> decayMomenta;
- pair<Lorentz5Momentum,Lorentz5Momentum> decayMomentaTwo;
- const double phiprime = UseRandom::rnd() * Constants::twopi;
-
- //aligned with outgoing dissociated proton
- const double costhetaprime = costheta;
-
- const double sinthetaprime=sqrt(1-sqr(costhetaprime));
- //axis along which diquark from associated proton is aligned
- Axis dir = Axis(sinthetaprime*cos(phiprime), sinthetaprime*sin(phiprime), costhetaprime);
-
- switch (diffDirection){
- case 0://Left single diffraction
- meMomenta()[4].setT(sqrt(mq2+sqr(meMomenta()[4].x())+sqr(meMomenta()[4].y())+sqr(meMomenta()[4].z())));
- ////////////////////////////////////////////////////
-
- do{}
- while(!Kinematics::twoBodyDecay(p3,mqq(),mq(),-dir,decayMomenta.first,decayMomenta.second));
- ///////////
-
- meMomenta()[2].setVect(p4.vect());
- meMomenta()[2].setT(p4.t());
-
- meMomenta()[3].setVect(decayMomenta.first.vect());
- meMomenta()[3].setT(decayMomenta.first.t());
- meMomenta()[4].setVect(decayMomenta.second.vect());
- meMomenta()[4].setT(decayMomenta.second.t());
-
- meMomenta()[2].rescaleEnergy();
- meMomenta()[3].rescaleEnergy();
- meMomenta()[4].rescaleEnergy();
- break;
- case 1://Right single diffraction
- meMomenta()[4].setT(sqrt(mq2+sqr(meMomenta()[4].x())+sqr(meMomenta()[4].y())+sqr(meMomenta()[4].z())));
- ////////////////////////////////////////////////////
-
- do{}
- while(!Kinematics::twoBodyDecay(p4,mqq(),mq(),dir,decayMomenta.first,decayMomenta.second));
-
- meMomenta()[2].setVect(p3.vect());
- meMomenta()[2].setT(p3.t());
-
- meMomenta()[3].setVect(decayMomenta.first.vect());
- meMomenta()[3].setT(decayMomenta.first.t());
- meMomenta()[4].setVect(decayMomenta.second.vect());
- meMomenta()[4].setT(decayMomenta.second.t());
-
- meMomenta()[2].rescaleEnergy();
- meMomenta()[3].rescaleEnergy();
- meMomenta()[4].rescaleEnergy();
- break;
- case 2://double diffraction
-
- do{}
- while(!Kinematics::twoBodyDecay(p3,mqq(),mq(),-dir,decayMomenta.first,decayMomenta.second));
-
- do{}
- while(!Kinematics::twoBodyDecay(p4,mqq(),mq(),dir,decayMomentaTwo.first,decayMomentaTwo.second));
-
- meMomenta()[2].setVect(decayMomenta.first.vect());
- meMomenta()[2].setT(decayMomenta.first.t());
- meMomenta()[3].setVect(decayMomenta.second.vect());
- meMomenta()[3].setT(decayMomenta.second.t());
-
- meMomenta()[4].setVect(decayMomentaTwo.second.vect());
- meMomenta()[4].setT(decayMomentaTwo.second.t());
- meMomenta()[5].setVect(decayMomentaTwo.first.vect());
- meMomenta()[5].setT(decayMomentaTwo.first.t());
-
-
- meMomenta()[2].rescaleEnergy();
- meMomenta()[3].rescaleEnergy();
- meMomenta()[4].rescaleEnergy();
-
- meMomenta()[5].rescaleEnergy();
-
- break;
- }
-
- }else
- {
- meMomenta()[2+diffDirection].setVect(p3.vect());
- meMomenta()[2+diffDirection].setT(p3.t());
- meMomenta()[3-diffDirection].setVect(p4.vect());
- meMomenta()[3-diffDirection].setT(p4.t());
-
- meMomenta()[2].rescaleEnergy();
- meMomenta()[3].rescaleEnergy();
+ case 0:
+ if(!deltaOnly)
+ {
+
+ pair<Lorentz5Momentum,Lorentz5Momentum> decayMomenta;
+ pair<Lorentz5Momentum,Lorentz5Momentum> decayMomentaTwo;
+ const double phiprime = UseRandom::rnd() * Constants::twopi;
+
+ //aligned with outgoing dissociated proton
+ const double costhetaprime = costheta;
+
+ const double sinthetaprime=sqrt(1-sqr(costhetaprime));
+ //axis along which diquark from associated proton is aligned
+ Axis dir = Axis(sinthetaprime*cos(phiprime), sinthetaprime*sin(phiprime), costhetaprime);
+
+ switch (diffDirection){
+ case 0://Left single diffraction
+ meMomenta()[4].setT(sqrt(mq2+sqr(meMomenta()[4].x())+sqr(meMomenta()[4].y())+sqr(meMomenta()[4].z())));
+ ////////////////////////////////////////////////////
+
+ do{}
+ while(!Kinematics::twoBodyDecay(p3,mqq(),mq(),-dir,decayMomenta.first,decayMomenta.second));
+ ///////////
+
+ meMomenta()[2].setVect(p4.vect());
+ meMomenta()[2].setT(p4.t());
+
+ meMomenta()[3].setVect(decayMomenta.first.vect());
+ meMomenta()[3].setT(decayMomenta.first.t());
+ meMomenta()[4].setVect(decayMomenta.second.vect());
+ meMomenta()[4].setT(decayMomenta.second.t());
+
+ meMomenta()[2].rescaleEnergy();
+ meMomenta()[3].rescaleEnergy();
+ meMomenta()[4].rescaleEnergy();
+ break;
+ case 1://Right single diffraction
+ meMomenta()[4].setT(sqrt(mq2+sqr(meMomenta()[4].x())+sqr(meMomenta()[4].y())+sqr(meMomenta()[4].z())));
+ ////////////////////////////////////////////////////
+
+ do{}
+ while(!Kinematics::twoBodyDecay(p4,mqq(),mq(),dir,decayMomenta.first,decayMomenta.second));
+
+ meMomenta()[2].setVect(p3.vect());
+ meMomenta()[2].setT(p3.t());
+
+ meMomenta()[3].setVect(decayMomenta.first.vect());
+ meMomenta()[3].setT(decayMomenta.first.t());
+ meMomenta()[4].setVect(decayMomenta.second.vect());
+ meMomenta()[4].setT(decayMomenta.second.t());
+
+ meMomenta()[2].rescaleEnergy();
+ meMomenta()[3].rescaleEnergy();
+ meMomenta()[4].rescaleEnergy();
+ break;
+ case 2://double diffraction
+
+ do{}
+ while(!Kinematics::twoBodyDecay(p3,mqq(),mq(),-dir,decayMomenta.first,decayMomenta.second));
+
+ do{}
+ while(!Kinematics::twoBodyDecay(p4,mqq(),mq(),dir,decayMomentaTwo.first,decayMomentaTwo.second));
+
+ meMomenta()[2].setVect(decayMomenta.first.vect());
+ meMomenta()[2].setT(decayMomenta.first.t());
+ meMomenta()[3].setVect(decayMomenta.second.vect());
+ meMomenta()[3].setT(decayMomenta.second.t());
+
+ meMomenta()[4].setVect(decayMomentaTwo.second.vect());
+ meMomenta()[4].setT(decayMomentaTwo.second.t());
+ meMomenta()[5].setVect(decayMomentaTwo.first.vect());
+ meMomenta()[5].setT(decayMomentaTwo.first.t());
+
+
+ meMomenta()[2].rescaleEnergy();
+ meMomenta()[3].rescaleEnergy();
+ meMomenta()[4].rescaleEnergy();
+
+ meMomenta()[5].rescaleEnergy();
+
+ break;
+ }
+
+ }else
+ {
+ meMomenta()[2+diffDirection].setVect(p3.vect());
+ meMomenta()[2+diffDirection].setT(p3.t());
+ meMomenta()[3-diffDirection].setVect(p4.vect());
+ meMomenta()[3-diffDirection].setT(p4.t());
+
+ meMomenta()[2].rescaleEnergy();
+ meMomenta()[3].rescaleEnergy();
- }
- break;
- case 1:
- switch(diffDirection){
- case 0:
- //quark and diquark masses
- meMomenta()[2].setMass(mqq());
- meMomenta()[3].setMass(mq());
-
- //gluon constituent mass
- meMomenta()[4].setMass(getParticleData(21)->constituentMass());
-
- //outgoing proton
- meMomenta()[5].setVect(p4.vect());
- meMomenta()[5].setT(p4.t());
-
- //two body decay of the outgoing dissociation proton
- do{}
- while(!Kinematics::twoBodyDecay(p3,mqq()+mq(),getParticleData(21)->constituentMass(),
- p3.vect().unit(),momPair.first,momPair.second));
- //put gluon back-to-back with quark-diquark
- //set momenta of quark and diquark
- frac = mqq()/(mqq()+mq());
- meMomenta()[2].setVect(frac*momPair.first.vect());
- meMomenta()[2].setT(sqrt(sqr(frac)*momPair.first.vect().mag2()+sqr(mqq())));
- meMomenta()[3].setVect((1-frac)*momPair.first.vect());
- meMomenta()[3].setT(sqrt(sqr(1-frac)*momPair.first.vect().mag2()+sqr(mq())));
- //set momentum of gluon
- meMomenta()[4].setVect(momPair.second.vect());
- meMomenta()[4].setT(momPair.second.t());
-
- break;
- case 1:
- //quark and diquark masses
- meMomenta()[5].setMass(mqq());
- meMomenta()[4].setMass(mq());
-
- //gluon constituent mass
- meMomenta()[3].setMass(getParticleData(21)->constituentMass());
-
- //outgoing proton
- meMomenta()[2].setVect(p3.vect());
- meMomenta()[2].setT(p3.t());
-
- //two body decay of the outgoing dissociation proton
- do{}
- while(!Kinematics::twoBodyDecay(p4,mqq()+mq(),getParticleData(21)->constituentMass(),
- p4.vect().unit(),momPair.first,momPair.second));
-
- //put gluon back-to-back with quark-diquark
- //set momenta of quark and diquark
- frac = mqq()/(mqq()+mq());
- meMomenta()[5].setVect(frac*momPair.first.vect());
- meMomenta()[5].setT(sqrt(sqr(frac)*momPair.first.vect().mag2()+sqr(mqq())));
- meMomenta()[4].setVect((1-frac)*momPair.first.vect());
- meMomenta()[4].setT(sqrt(sqr(1-frac)*momPair.first.vect().mag2()+sqr(mq())));
- //set momentum of gluon
- meMomenta()[3].setVect(momPair.second.vect());
- meMomenta()[3].setT(momPair.second.t());
-
-
-
- break;
- case 2:
- //first dissociated proton constituents
- meMomenta()[2].setMass(mqq());
- meMomenta()[3].setMass(mq());
- meMomenta()[4].setMass(getParticleData(21)->constituentMass());
- //second dissociated proton constituents
- meMomenta()[5].setMass(getParticleData(21)->constituentMass());
- meMomenta()[6].setMass(mq());
- meMomenta()[7].setMass(mqq());
-
-
- //two body decay of the outgoing dissociation proton
- do{}
- while(!Kinematics::twoBodyDecay(p3,mqq()+mq(),getParticleData(21)->constituentMass(),
- p3.vect().unit(),momPair.first,momPair.second));
-
- do{}
- while(!Kinematics::twoBodyDecay(p4,mqq()+mq(),getParticleData(21)->constituentMass(),
- p4.vect().unit(),momPair1.first,momPair1.second));
-
- //put gluon back-to-back with quark-diquark
- frac = mqq()/(mqq()+mq());
-
- //first dissociated proton
- //set momenta of quark and diquark
-
- meMomenta()[2].setVect(frac*momPair.first.vect());
- meMomenta()[2].setT(sqrt(sqr(frac)*momPair.first.vect().mag2()+sqr(mqq())));
- meMomenta()[3].setVect((1-frac)*momPair.first.vect());
- meMomenta()[3].setT(sqrt(sqr(1-frac)*momPair.first.vect().mag2()+sqr(mq())));
- //set momentum of gluon
- meMomenta()[4].setVect(momPair.second.vect());
- meMomenta()[4].setT(momPair.second.t());
-
- //first dissociated proton
- //set momenta of quark and diquark
-
- meMomenta()[7].setVect(frac*momPair1.first.vect());
- meMomenta()[7].setT(sqrt(sqr(frac)*momPair1.first.vect().mag2()+sqr(mqq())));
- meMomenta()[6].setVect((1-frac)*momPair1.first.vect());
- meMomenta()[6].setT(sqrt(sqr(1-frac)*momPair1.first.vect().mag2()+sqr(mq())));
- //set momentum of gluon
- meMomenta()[5].setVect(momPair1.second.vect());
- meMomenta()[5].setT(momPair1.second.t());
- break;
-
- }
- meMomenta()[2].rescaleEnergy();
- meMomenta()[3].rescaleEnergy();
- meMomenta()[4].rescaleEnergy();
- meMomenta()[5].rescaleEnergy();
- if(diffDirection==2){
- meMomenta()[6].rescaleEnergy();
- meMomenta()[7].rescaleEnergy();
- }
-
- break;
+ }
+ break;
+ case 1:
+ switch(diffDirection){
+ case 0:
+ //quark and diquark masses
+ meMomenta()[2].setMass(mqq());
+ meMomenta()[3].setMass(mq());
+
+ //gluon constituent mass
+ meMomenta()[4].setMass(getParticleData(21)->constituentMass());
+
+ //outgoing proton
+ meMomenta()[5].setVect(p4.vect());
+ meMomenta()[5].setT(p4.t());
+
+ //two body decay of the outgoing dissociation proton
+ do{}
+ while(!Kinematics::twoBodyDecay(p3,mqq()+mq(),getParticleData(21)->constituentMass(),
+ p3.vect().unit(),momPair.first,momPair.second));
+ //put gluon back-to-back with quark-diquark
+ //set momenta of quark and diquark
+ frac = mqq()/(mqq()+mq());
+ meMomenta()[2].setVect(frac*momPair.first.vect());
+ meMomenta()[2].setT(sqrt(sqr(frac)*momPair.first.vect().mag2()+sqr(mqq())));
+ meMomenta()[3].setVect((1-frac)*momPair.first.vect());
+ meMomenta()[3].setT(sqrt(sqr(1-frac)*momPair.first.vect().mag2()+sqr(mq())));
+ //set momentum of gluon
+ meMomenta()[4].setVect(momPair.second.vect());
+ meMomenta()[4].setT(momPair.second.t());
+
+ break;
+ case 1:
+ //quark and diquark masses
+ meMomenta()[5].setMass(mqq());
+ meMomenta()[4].setMass(mq());
+
+ //gluon constituent mass
+ meMomenta()[3].setMass(getParticleData(21)->constituentMass());
+
+ //outgoing proton
+ meMomenta()[2].setVect(p3.vect());
+ meMomenta()[2].setT(p3.t());
+
+ //two body decay of the outgoing dissociation proton
+ do{}
+ while(!Kinematics::twoBodyDecay(p4,mqq()+mq(),getParticleData(21)->constituentMass(),
+ p4.vect().unit(),momPair.first,momPair.second));
+
+ //put gluon back-to-back with quark-diquark
+ //set momenta of quark and diquark
+ frac = mqq()/(mqq()+mq());
+ meMomenta()[5].setVect(frac*momPair.first.vect());
+ meMomenta()[5].setT(sqrt(sqr(frac)*momPair.first.vect().mag2()+sqr(mqq())));
+ meMomenta()[4].setVect((1-frac)*momPair.first.vect());
+ meMomenta()[4].setT(sqrt(sqr(1-frac)*momPair.first.vect().mag2()+sqr(mq())));
+ //set momentum of gluon
+ meMomenta()[3].setVect(momPair.second.vect());
+ meMomenta()[3].setT(momPair.second.t());
+
+
+
+ break;
+ case 2:
+ //first dissociated proton constituents
+ meMomenta()[2].setMass(mqq());
+ meMomenta()[3].setMass(mq());
+ meMomenta()[4].setMass(getParticleData(21)->constituentMass());
+ //second dissociated proton constituents
+ meMomenta()[5].setMass(getParticleData(21)->constituentMass());
+ meMomenta()[6].setMass(mq());
+ meMomenta()[7].setMass(mqq());
+
+
+ //two body decay of the outgoing dissociation proton
+ do{}
+ while(!Kinematics::twoBodyDecay(p3,mqq()+mq(),getParticleData(21)->constituentMass(),
+ p3.vect().unit(),momPair.first,momPair.second));
+
+ do{}
+ while(!Kinematics::twoBodyDecay(p4,mqq()+mq(),getParticleData(21)->constituentMass(),
+ p4.vect().unit(),momPair1.first,momPair1.second));
+
+ //put gluon back-to-back with quark-diquark
+ frac = mqq()/(mqq()+mq());
+
+ //first dissociated proton
+ //set momenta of quark and diquark
+
+ meMomenta()[2].setVect(frac*momPair.first.vect());
+ meMomenta()[2].setT(sqrt(sqr(frac)*momPair.first.vect().mag2()+sqr(mqq())));
+ meMomenta()[3].setVect((1-frac)*momPair.first.vect());
+ meMomenta()[3].setT(sqrt(sqr(1-frac)*momPair.first.vect().mag2()+sqr(mq())));
+ //set momentum of gluon
+ meMomenta()[4].setVect(momPair.second.vect());
+ meMomenta()[4].setT(momPair.second.t());
+
+ //first dissociated proton
+ //set momenta of quark and diquark
+
+ meMomenta()[7].setVect(frac*momPair1.first.vect());
+ meMomenta()[7].setT(sqrt(sqr(frac)*momPair1.first.vect().mag2()+sqr(mqq())));
+ meMomenta()[6].setVect((1-frac)*momPair1.first.vect());
+ meMomenta()[6].setT(sqrt(sqr(1-frac)*momPair1.first.vect().mag2()+sqr(mq())));
+ //set momentum of gluon
+ meMomenta()[5].setVect(momPair1.second.vect());
+ meMomenta()[5].setT(momPair1.second.t());
+ break;
+
+ }
+ meMomenta()[2].rescaleEnergy();
+ meMomenta()[3].rescaleEnergy();
+ meMomenta()[4].rescaleEnergy();
+ meMomenta()[5].rescaleEnergy();
+ if(diffDirection==2){
+ meMomenta()[6].rescaleEnergy();
+ meMomenta()[7].rescaleEnergy();
+ }
+
+ break;
}
jacobian(sqr(cmEnergy)/GeV2);
return true;
}
//Generate masses of dissociated protons and momentum transfer from probability f(M2,t)
//(for single diffraction). Sample according to f(M2,t)=f(M2)f(t|M2).
pair<pair<Energy2,Energy2>,Energy2> MEDiffraction::diffractiveMassAndMomentumTransfer() const {
Energy2 theM12(ZERO),theM22(ZERO), thet(ZERO);
int count = 0;
//proton mass squared
const Energy2 m2 = sqr(theProtonMass);
//delta mass squared
const Energy2 md2 = sqr(getParticleData(2214)->mass());
Energy2 M2;
bool condition = true;
- do {
+ do {
//check if we want only delta
if(deltaOnly) {
- switch(diffDirection){
- case 0:
- theM12 = md2;
- theM22 = m2;
- M2 = md2;
- thet = randomt(md2);
- break;
- case 1:
- theM22 = md2;
- theM12 = m2;
- M2 = md2;
- thet = randomt(md2);
- break;
- case 2:
- theM12 = md2;
- theM22 = md2;
- M2 = md2;
- thet = doublediffrandomt(theM12,theM22);
- break;
- }
+ switch(diffDirection){
+ case 0:
+ theM12 = md2;
+ theM22 = m2;
+ M2 = md2;
+ thet = randomt(md2);
+ break;
+ case 1:
+ theM22 = md2;
+ theM12 = m2;
+ M2 = md2;
+ thet = randomt(md2);
+ break;
+ case 2:
+ theM12 = md2;
+ theM22 = md2;
+ M2 = md2;
+ thet = doublediffrandomt(theM12,theM22);
+ break;
+ }
}
else {
- switch (diffDirection){
- case 0:
- M2=randomM2();
- thet = randomt(M2);
- theM12=M2;
-
- theM22=m2;
-
- break;
- case 1:
-
- theM12=m2;
- M2=randomM2();
- thet = randomt(M2);
-
-
- theM22=M2;
- break;
- case 2:
- theM12=randomM2();
- theM22=randomM2();
- M2=(theM12>theM22) ? theM12: theM22;
-
- thet = doublediffrandomt(theM12,theM22);
-
- break;
- }
+ switch (diffDirection){
+ case 0:
+ M2=randomM2();
+ thet = randomt(M2);
+ theM12=M2;
+
+ theM22=m2;
+
+ break;
+ case 1:
+
+ theM12=m2;
+ M2=randomM2();
+ thet = randomt(M2);
+
+
+ theM22=M2;
+ break;
+ case 2:
+ theM12=randomM2();
+ theM22=randomM2();
+ M2=(theM12>theM22) ? theM12: theM22;
+
+ thet = doublediffrandomt(theM12,theM22);
+
+ break;
+ }
}
count++;
const Energy cmEnergy = generator()->maximumCMEnergy();
const Energy2 s = sqr(cmEnergy);
if(generator()->maximumCMEnergy()<sqrt(theM12)+sqrt(theM22)) {
condition = true;
}
else {
InvEnergy2 slope;
if(diffDirection==2){
- slope = 2*softPomeronSlope()*log(.1+(sqr(cmEnergy)/softPomeronSlope())/(theM12*theM22));
+ slope = 2*softPomeronSlope()*log(.1+(sqr(cmEnergy)/softPomeronSlope())/(theM12*theM22));
}else{
- slope = protonPomeronSlope()
+ slope = protonPomeronSlope()
+ 2*softPomeronSlope()*log(sqr(cmEnergy)/M2);
}
const double expmax = exp(slope*tmaxfun(s,m2,M2));
const double expmin = exp(slope*tminfun(s,m2,M2));
//without (1-M2/s) constraint
condition = (UseRandom::rnd()>(protonPomeronSlope()*GeV2)*(expmax-expmin)/(slope*GeV2))
- ||((theM12/GeV2)*(theM22/GeV2)>=(sqr(cmEnergy)/GeV2)/(softPomeronSlope()*GeV2));
+ ||((theM12/GeV2)*(theM22/GeV2)>=(sqr(cmEnergy)/GeV2)/(softPomeronSlope()*GeV2));
}
}
while(condition);
return make_pair (make_pair(theM12,theM22),thet);
}
//Decay of the excited proton to quark-diquark
pair<Lorentz5Momentum,Lorentz5Momentum> MEDiffraction::twoBodyDecayMomenta(Lorentz5Momentum pp) const{
- //Decay of the excited proton
- const Energy2 Mx2(sqr(pp.mass())),mq2(sqr(mq())),mqq2(sqr(mqq()));
-
- const Energy2 psq = ((Mx2-sqr(mq()+mqq()))*(Mx2-sqr(mq()-mqq())))/(4*Mx2);
+ //Decay of the excited proton
+ const Energy2 Mx2(sqr(pp.mass())),mq2(sqr(mq())),mqq2(sqr(mqq()));
+
+ const Energy2 psq = ((Mx2-sqr(mq()+mqq()))*(Mx2-sqr(mq()-mqq())))/(4*Mx2);
- assert(psq/GeV2>0);
- const Energy p(sqrt(psq));
-
- const double phi = UseRandom::rnd() * Constants::twopi;
- const double costheta =1-2*UseRandom::rnd();
- const double sintheta = sqrt(1-sqr(costheta));
-
- Lorentz5Momentum k1=Lorentz5Momentum(p*sintheta*cos(phi), p*sintheta*sin(phi), p*costheta, sqrt(mq2+psq));
- Lorentz5Momentum k2=Lorentz5Momentum(-p*sintheta*cos(phi), -p*sintheta*sin(phi), -p*costheta,sqrt(mqq2+psq));
-
- //find boost to pp center of mass
- const Boost betap3 = (pp).findBoostToCM();
-
- //k1 and k2 calculated at p3 center of mass, so boost back
- k1.boost(-betap3);
- k2.boost(-betap3);
-
- //first is quark, second diquark
- return make_pair(k1,k2);
+ assert(psq/GeV2>0);
+ const Energy p(sqrt(psq));
+
+ const double phi = UseRandom::rnd() * Constants::twopi;
+ const double costheta =1-2*UseRandom::rnd();
+ const double sintheta = sqrt(1-sqr(costheta));
+
+ Lorentz5Momentum k1=Lorentz5Momentum(p*sintheta*cos(phi), p*sintheta*sin(phi), p*costheta, sqrt(mq2+psq));
+ Lorentz5Momentum k2=Lorentz5Momentum(-p*sintheta*cos(phi), -p*sintheta*sin(phi), -p*costheta,sqrt(mqq2+psq));
+
+ //find boost to pp center of mass
+ const Boost betap3 = (pp).findBoostToCM();
+
+ //k1 and k2 calculated at p3 center of mass, so boost back
+ k1.boost(-betap3);
+ k2.boost(-betap3);
+
+ //first is quark, second diquark
+ return make_pair(k1,k2);
}
Energy2 MEDiffraction::randomt(Energy2 M2) const {
assert(protonPomeronSlope()*GeV2 > 0);
//proton mass
const Energy2 m2 = sqr( theProtonMass );
const Energy cmEnergy = generator()->maximumCMEnergy();
const Energy2 ttmin = tminfun(sqr(cmEnergy),m2,M2);
const Energy2 ttmax = tmaxfun(sqr(cmEnergy),m2,M2);
const InvEnergy2 slope = protonPomeronSlope()
+ 2*softPomeronSlope()*log(sqr(cmEnergy)/M2);
return log( exp(slope*ttmin) +
UseRandom::rnd()*(exp(slope*ttmax) - exp(slope*ttmin)) ) / slope;
}
Energy2 MEDiffraction::doublediffrandomt(Energy2 M12, Energy2 M22) const {
const Energy cmEnergy = generator()->maximumCMEnergy();
const double shift = 0.1;
const InvEnergy2 slope = 2*softPomeronSlope()*log(shift+(sqr(cmEnergy)/softPomeronSlope())/(M12*M22));
const Energy2 ttmin = tminfun(sqr(cmEnergy),M12,M22);
const Energy2 ttmax = tmaxfun(sqr(cmEnergy),M12,M22);
double r = UseRandom::rnd();
Energy2 newVal;
if(slope*ttmax>slope*ttmin) {
newVal = ttmax + log( r + (1.-r)*exp(slope*(ttmin-ttmax)) ) / slope;
}
else {
newVal = ttmin + log( 1. - r + r*exp(slope*(ttmax-ttmin))) / slope;
}
return newVal;
}
Energy2 MEDiffraction::randomM2() const {
const double tmp = 1 - softPomeronIntercept();
const Energy cmEnergy = generator()->maximumCMEnergy();
return sqr(cmEnergy) * pow( pow(M2min()/sqr(cmEnergy),tmp) +
UseRandom::rnd() * (pow(M2max()/sqr(cmEnergy),tmp) - pow(M2min()/sqr(cmEnergy),tmp)),
1.0/tmp );
}
Energy2 MEDiffraction::tminfun(Energy2 s, Energy2 M12, Energy2 M22) const {
const Energy2 m2 = sqr( theProtonMass );
return 0.5/s*(-sqrt(kallen(s, m2, m2)*kallen(s, M12, M22))-sqr(s)+2*s*m2+s*M12+s*M22);
}
Energy2 MEDiffraction::tmaxfun(Energy2 s, Energy2 M12, Energy2 M22) const {
const Energy2 m2 = sqr( theProtonMass );
-
+
return 0.5/s*(sqrt(kallen(s, m2, m2)*kallen(s, M12, M22))-sqr(s)+2*s*m2+s*M12+s*M22);
}
double MEDiffraction::me2() const{
return theme2;
}
CrossSection MEDiffraction::dSigHatDR() const {
return me2()*jacobian()/sHat()*sqr(hbarc);
}
unsigned int MEDiffraction::orderInAlphaS() const {
return 0;
}
unsigned int MEDiffraction::orderInAlphaEW() const {
return 0;
}
Selector<MEBase::DiagramIndex>
MEDiffraction::diagrams(const DiagramVector & diags) const {
Selector<DiagramIndex> sel;
if(!deltaOnly){
- if(diffDirection<2){
-
- for(unsigned int i = 0; i < diags.size(); i++){
- if(diags[0]->id()==-1)
- sel.insert(2./3.,i);
- else
- sel.insert(1./3.,i);
- }
-
- }else{
- for(unsigned int i = 0; i < diags.size(); i++){
- if(diags[0]->id()==-1)
- sel.insert(4./9.,i);
- else if(diags[0]->id()==-2)
- sel.insert(2./9.,i);
- else if(diags[0]->id()==-3)
- sel.insert(2./9.,i);
- else
- sel.insert(1./9.,i);
- }
- }
+ if(diffDirection<2){
+
+ for(unsigned int i = 0; i < diags.size(); i++){
+ if(diags[0]->id()==-1)
+ sel.insert(2./3.,i);
+ else
+ sel.insert(1./3.,i);
+ }
+
+ }else{
+ for(unsigned int i = 0; i < diags.size(); i++){
+ if(diags[0]->id()==-1)
+ sel.insert(4./9.,i);
+ else if(diags[0]->id()==-2)
+ sel.insert(2./9.,i);
+ else if(diags[0]->id()==-3)
+ sel.insert(2./9.,i);
+ else
+ sel.insert(1./9.,i);
+ }
+ }
}else{
- sel.insert(1.0,0);
- }
+ sel.insert(1.0,0);
+ }
return sel;
}
Selector<const ColourLines *>
MEDiffraction::colourGeometries(tcDiagPtr ) const {
Selector<const ColourLines *> sel;
int sign1=0, sign2=0;
sign1 = (generator()->eventHandler()->incoming().first->id() > 0) ? 1 : -1;
sign2 = (generator()->eventHandler()->incoming().second->id() > 0) ? 1 : -1;
switch(dissociationDecay){
- case 0:
- if(!deltaOnly)
- {
- if(diffDirection!=2){
-
- if (diffDirection == 0){
- if(sign1>0){
- static ColourLines dqq0=ColourLines("-6 2 7");
- sel.insert(1.0,&dqq0);
- }else{
- static ColourLines dqq0=ColourLines("6 -2 -7");
- sel.insert(1.0,&dqq0);
- }
-
-
- }
- else{
- if(sign2>0){
- static ColourLines dqq1=ColourLines("-6 3 7");
- sel.insert(1.0,&dqq1);
- }else{
- static ColourLines dqq1=ColourLines("6 -3 -7");
- sel.insert(1.0,&dqq1);
- }
- }
-
- }else{
-
- if(sign1>0 && sign2>0){
- static ColourLines ddqq0=ColourLines("-6 2 7, -9 4 8");
- sel.insert(1.0,&ddqq0);
- }else if(sign1<0 && sign2>0){
- static ColourLines ddqq0=ColourLines("6 -2 -7, -9 4 8");
- sel.insert(1.0,&ddqq0);
- }else if(sign1>0&& sign2<0){
- static ColourLines ddqq0=ColourLines("-6 2 7, 9 -4 -8");
- sel.insert(1.0,&ddqq0);
- }else{
- static ColourLines ddqq0=ColourLines("6 -2 -7, 9 -4 -8");
- sel.insert(1.0,&ddqq0);
- }
-
-
- }
-
- }else
- {
- static ColourLines cl("");
-
- sel.insert(1.0, &cl);
- }
- break;
- case 1:
- switch(diffDirection){
- case 0:
- static ColourLines clleft("-6 2 3 8, -8 -3 7");
- sel.insert(1.0, &clleft);
- break;
- case 1:
- static ColourLines clright("-9 4 3 7, -7 -3 8");
- sel.insert(1.0, &clright);
- break;
- case 2:
- static ColourLines cldouble("-8 2 3 10, -10 -3 9, -13 6 5 11, -11 -5 12");
- sel.insert(1.0, &cldouble);
- break;
- }
- break;
+ case 0:
+ if(!deltaOnly)
+ {
+ if(diffDirection!=2){
+
+ if (diffDirection == 0){
+ if(sign1>0){
+ static ColourLines dqq0=ColourLines("-6 2 7");
+ sel.insert(1.0,&dqq0);
+ }else{
+ static ColourLines dqq0=ColourLines("6 -2 -7");
+ sel.insert(1.0,&dqq0);
+ }
+
+
+ }
+ else{
+ if(sign2>0){
+ static ColourLines dqq1=ColourLines("-6 3 7");
+ sel.insert(1.0,&dqq1);
+ }else{
+ static ColourLines dqq1=ColourLines("6 -3 -7");
+ sel.insert(1.0,&dqq1);
+ }
+ }
+
+ }else{
+
+ if(sign1>0 && sign2>0){
+ static ColourLines ddqq0=ColourLines("-6 2 7, -9 4 8");
+ sel.insert(1.0,&ddqq0);
+ }else if(sign1<0 && sign2>0){
+ static ColourLines ddqq0=ColourLines("6 -2 -7, -9 4 8");
+ sel.insert(1.0,&ddqq0);
+ }else if(sign1>0&& sign2<0){
+ static ColourLines ddqq0=ColourLines("-6 2 7, 9 -4 -8");
+ sel.insert(1.0,&ddqq0);
+ }else{
+ static ColourLines ddqq0=ColourLines("6 -2 -7, 9 -4 -8");
+ sel.insert(1.0,&ddqq0);
+ }
+
+
+ }
+
+ }else
+ {
+ static ColourLines cl("");
+
+ sel.insert(1.0, &cl);
+ }
+ break;
+ case 1:
+ switch(diffDirection){
+ case 0:
+ static ColourLines clleft("-6 2 3 8, -8 -3 7");
+ sel.insert(1.0, &clleft);
+ break;
+ case 1:
+ static ColourLines clright("-9 4 3 7, -7 -3 8");
+ sel.insert(1.0, &clright);
+ break;
+ case 2:
+ static ColourLines cldouble("-8 2 3 10, -10 -3 9, -13 6 5 11, -11 -5 12");
+ sel.insert(1.0, &cldouble);
+ break;
+ }
+ break;
}
return sel;
}
void MEDiffraction::doinit() {
HwMEBase::doinit();
theProtonMass = getParticleData(2212)->mass();
}
void MEDiffraction::doinitrun() {
HwMEBase::doinitrun();
isInRunPhase = true;
}
IBPtr MEDiffraction::clone() const {
return new_ptr(*this);
}
IBPtr MEDiffraction::fullclone() const {
return new_ptr(*this);
}
ClassDescription<MEDiffraction> MEDiffraction::initMEDiffraction;
// Definition of the static class description member.
void MEDiffraction::persistentOutput(PersistentOStream & os) const {
os << theme2 << deltaOnly << diffDirection << theprotonPomeronSlope
<< thesoftPomeronIntercept << thesoftPomeronSlope << dissociationDecay
<< ounit(theProtonMass,GeV);
}
void MEDiffraction::persistentInput(PersistentIStream & is, int) {
is >> theme2 >> deltaOnly >> diffDirection >> theprotonPomeronSlope
>> thesoftPomeronIntercept >> thesoftPomeronSlope >> dissociationDecay
>> iunit(theProtonMass,GeV);
}
InvEnergy2 MEDiffraction::protonPomeronSlope() const{
- return theprotonPomeronSlope/GeV2;
+ return theprotonPomeronSlope/GeV2;
}
double MEDiffraction::softPomeronIntercept() const {
- return thesoftPomeronIntercept;
+ return thesoftPomeronIntercept;
}
InvEnergy2 MEDiffraction::softPomeronSlope() const {
- return thesoftPomeronSlope/GeV2;
+ return thesoftPomeronSlope/GeV2;
}
void MEDiffraction::Init() {
static ClassDocumentation<MEDiffraction> documentation
("There is no documentation for the MEDiffraction class");
static Parameter<MEDiffraction,double> interfaceme2
("DiffractionAmplitude",
"The square of the diffraction amplitude used to determine the "
"cross section.",
&MEDiffraction::theme2, 1.0, 0.00001, 100.0,
false, false, Interface::limited);
static Parameter<MEDiffraction,double> interfaceprotonPomeronSlope
("ProtonPomeronSlope",
"The proton-pomeron slope parameter.",
&MEDiffraction::theprotonPomeronSlope, 10.1, 0.00001, 100.0,
false, false, Interface::limited);
static Parameter<MEDiffraction,double> interfacesoftPomeronIntercept
("SoftPomeronIntercept",
"The soft pomeron intercept.",
&MEDiffraction::thesoftPomeronIntercept, 1.08, 0.00001, 100.0,
false, false, Interface::limited);
static Parameter<MEDiffraction,double> interfacesoftPomeronSlope
("SoftPomeronSlope",
"The soft pomeron slope parameter.",
&MEDiffraction::thesoftPomeronSlope, 0.25, 0.00001, 100.0,
false, false, Interface::limited);
static Switch<MEDiffraction, bool> interfaceDeltaOnly
("DeltaOnly",
"proton-proton to proton-delta only",
&MEDiffraction::deltaOnly, 0, false, false);
static SwitchOption interfaceDeltaOnly0
(interfaceDeltaOnly,"No","Final state with Delta only is OFF", 0);
static SwitchOption interfaceDeltaOnly1
(interfaceDeltaOnly,"Yes","Final state with Delta only is ON", 1);
//Select if the left, right or both protons are excited
static Switch<MEDiffraction, unsigned int> interfaceDiffDirection
("DiffDirection",
"Direction of the excited proton",
&MEDiffraction::diffDirection, 0, false, false);
static SwitchOption left
(interfaceDiffDirection,"Left","Proton moving in the positive z direction", 0);
static SwitchOption right
(interfaceDiffDirection,"Right","Proton moving in the negative z direction", 1);
static SwitchOption both
(interfaceDiffDirection,"Both","Both protons", 2);
//Select if two or three body decay
static Switch<MEDiffraction, unsigned int> interfaceDissociationDecay
("DissociationDecay",
"Number of clusters the dissociated proton decays",
&MEDiffraction::dissociationDecay, 0, false, false);
static SwitchOption one
(interfaceDissociationDecay,"One","Dissociated proton decays into one cluster", 0);
static SwitchOption two
(interfaceDissociationDecay,"Two","Dissociated proton decays into two clusters", 1);
}
diff --git a/MatrixElement/Hadron/MEDiffraction.h b/MatrixElement/Hadron/MEDiffraction.h
--- a/MatrixElement/Hadron/MEDiffraction.h
+++ b/MatrixElement/Hadron/MEDiffraction.h
@@ -1,344 +1,344 @@
// -*- C++ -*-
#ifndef HERWIG_MEDiffraction_H
#define HERWIG_MEDiffraction_H
//
// This is the declaration of the MEDiffraction class.
//
#include "Herwig/MatrixElement/HwMEBase.h"
namespace Herwig {
using namespace ThePEG;
/**
* The MEDiffraction class provides a simple colour singlet exchange matrix element
* to be used in the soft component of the multiple scattering model of the
* underlying event
*
* @see \ref MEDiffractionInterfaces "The interfaces"
* defined for MEDiffraction.
*/
class MEDiffraction: public HwMEBase {
public:
MEDiffraction();
/** @name Virtual functions required by the MEBase class. */
//@{
/**
* Return the order in \f$\alpha_S\f$ in which this matrix
* element is given.
*/
virtual unsigned int orderInAlphaS() const;
/**
* Return the order in \f$\alpha_{EW}\f$ in which this matrix
* element is given.
*/
virtual unsigned int orderInAlphaEW() const;
/**
* The matrix element for the kinematical configuration
* previously provided by the last call to setKinematics(), suitably
* scaled by sHat() to give a dimension-less number.
* @return the matrix element scaled with sHat() to give a
* dimensionless number.
*/
virtual double me2() const;
/**
* Return the scale associated with the last set phase space point.
*/
virtual Energy2 scale() const;
/**
* Set the typed and momenta of the incoming and outgoing partons to
* be used in subsequent calls to me() and colourGeometries()
* according to the associated XComb object. If the function is
* overridden in a sub class the new function must call the base
* class one first.
*/
virtual void setKinematics();
/**
* The number of internal degrees of freedom used in the matrix
* element.
*/
virtual int nDim() const;
/**
* Generate internal degrees of freedom given nDim() uniform
* random numbers in the interval \f$ ]0,1[ \f$. To help the phase space
* generator, the dSigHatDR should be a smooth function of these
* numbers, although this is not strictly necessary.
* @param r a pointer to the first of nDim() consecutive random numbers.
* @return true if the generation succeeded, otherwise false.
*/
virtual bool generateKinematics(const double * r);
/**
* Return the matrix element squared differential in the variables
* given by the last call to generateKinematics().
*/
virtual CrossSection dSigHatDR() const;
/**
* Add all possible diagrams with the add() function.
*/
virtual void getDiagrams() const;
/**
* Get diagram selector. With the information previously supplied with the
* setKinematics method, a derived class may optionally
* override this method to weight the given diagrams with their
* (although certainly not physical) relative probabilities.
* @param dv the diagrams to be weighted.
* @return a Selector relating the given diagrams to their weights.
*/
virtual Selector<DiagramIndex> diagrams(const DiagramVector & dv) const;
/**
* Return a Selector with possible colour geometries for the selected
* diagram weighted by their relative probabilities.
* @param diag the diagram chosen.
* @return the possible colour geometries weighted by their
* relative probabilities.
*/
virtual Selector<const ColourLines *>
colourGeometries(tcDiagPtr diag) const;
//@}
/**
* Expect the incoming partons in the laboratory frame
*/
/* virtual bool wantCMS() const { return false; } */
public:
/** @name Functions used by the persistent I/O system. */
//@{
/**
* Function used to write out object persistently.
* @param os the persistent output stream written to.
*/
void persistentOutput(PersistentOStream & os) const;
/**
* Function used to read in object persistently.
* @param is the persistent input stream read from.
* @param version the version number of the object when written.
*/
void persistentInput(PersistentIStream & is, int version);
//@}
/**
* The standard Init function used to initialize the interfaces.
* Called exactly once for each class by the class description system
* before the main function starts or
* when this class is dynamically loaded.
*/
static void Init();
protected:
/** @name Standard Interfaced functions. */
//@{
/**
* Initialize this object after the setup phase before saving an
* EventGenerator to disk.
* @throws InitException if object could not be initialized properly.
*/
virtual void doinit();
/**
* Initialize this object. Called in the run phase just before a run begins.
*/
virtual void doinitrun();
//@}
/** @name Clone Methods. */
//@{
/**
* Make a simple clone of this object.
* @return a pointer to the new object.
*/
virtual IBPtr clone() const;
/** Make a clone of this object, possibly modifying the cloned object
* to make it sane.
* @return a pointer to the new object.
*/
virtual IBPtr fullclone() const;
//@}
private:
/* The matrix element squared */
double theme2;
/* Use only delta as excited state */
bool deltaOnly;
/* Direction of the excited proton */
unsigned int diffDirection;
/* Number of clusters the dissociated proton decays into */
unsigned int dissociationDecay;
/* The mass of the consitutent quark */
Energy mq() const {return Energy(0.325*GeV);}
/* The mass of the constituent diquark */
Energy mqq() const {return Energy(0.650*GeV);}
/* The proton-pomeron slope */
double theprotonPomeronSlope;
/* The soft pomeron intercept */
double thesoftPomeronIntercept;
/* The soft pomeron slope */
double thesoftPomeronSlope;
/**
* Sample the diffractive mass squared M2 and the momentum transfer t
*/
pair<pair<Energy2,Energy2>,Energy2> diffractiveMassAndMomentumTransfer() const;
/**
* Random value for the diffractive mass squared M2 according to (M2/s0)^(-intercept)
*/
Energy2 randomM2() const;
/**
* Random value for t according to exp(diffSlope*t)
*/
Energy2 randomt(Energy2 M2) const;
/**
* Random value for t according to exp(diffSlope*t) for double diffraction
*/
Energy2 doublediffrandomt(Energy2 M12, Energy2 M22) const;
/**
* Returns the momenta of the two-body decay of momentum pp
*/
pair<Lorentz5Momentum,Lorentz5Momentum> twoBodyDecayMomenta(Lorentz5Momentum pp) const;
/**
* Returns the proton-pomeron slope
*/
InvEnergy2 protonPomeronSlope() const;
/**
* Returns the soft pomeron intercept
*/
double softPomeronIntercept() const;
//M12 and M22 are masses squared of
//outgoing particles
/**
* Returns the minimal possible value of momentum transfer t given the center
* of mass energy and diffractive masses
*/
Energy2 tminfun(Energy2 s, Energy2 M12, Energy2 M22) const;
/**
* Returns the maximal possible value of momentum transfer t given the center
* of mass energy and diffractive masses
*/
Energy2 tmaxfun(Energy2 s , Energy2 M12, Energy2 M22) const;
/**
* Returns the minimal possible value of diffractive mass
*/
//lowest possible mass given the constituent masses of quark and diquark
Energy2 M2min() const{return sqr(getParticleData(2212)->mass()+mq()+mqq());}
/**
* Returns the maximal possible value of diffractive mass
*/
Energy2 M2max() const{
- return sqr(generator()->maximumCMEnergy()-getParticleData(2212)->mass());
+ return sqr(generator()->maximumCMEnergy()-getParticleData(2212)->mass());
}//TODO:modify to get proper parameters
InvEnergy2 softPomeronSlope() const;
/* Kallen function */
template<int L, int E, int Q, int DL, int DE, int DQ>
Qty<2*L,2*E,2*Q,DL,DE,DQ> kallen(Qty<L,E,Q,DL,DE,DQ> a,
Qty<L,E,Q,DL,DE,DQ> b,
Qty<L,E,Q,DL,DE,DQ> c) const {
return a*a + b*b + c*c - 2.0*(a*b + b*c + c*a);
}
/**
* The static object used to initialize the description of this class.
* Indicates that this is a concrete class with persistent data.
*/
static ClassDescription<MEDiffraction> initMEDiffraction;
/**
* The assignment operator is private and must never be called.
* In fact, it should not even be implemented.
*/
MEDiffraction & operator=(const MEDiffraction &);
bool isInRunPhase;
/* The proton mass */
Energy theProtonMass;
};
}
#include "ThePEG/Utilities/ClassTraits.h"
namespace ThePEG {
/** @cond TRAITSPECIALIZATIONS */
/** This template specialization informs ThePEG about the
* base classes of MEDiffraction. */
template <>
struct BaseClassTrait<Herwig::MEDiffraction,1> {
/** Typedef of the first base class of MEDiffraction. */
typedef Herwig::HwMEBase NthBase;
};
/** This template specialization informs ThePEG about the name of
* the MEDiffraction class and the shared object where it is defined. */
template <>
struct ClassTraits<Herwig::MEDiffraction>
: public ClassTraitsBase<Herwig::MEDiffraction> {
/** Return a platform-independent class name */
static string className() { return "Herwig::MEDiffraction"; }
/**
* The name of a file containing the dynamic library where the class
* MEDiffraction is implemented. It may also include several, space-separated,
* libraries if the class MEDiffraction depends on other classes (base classes
* excepted). In this case the listed libraries will be dynamically
* linked in the order they are specified.
*/
static string library() {return "HwMEHadron.so";}
};
/** @endcond */
}
#endif /* HERWIG_MEDiffraction_H */
diff --git a/MatrixElement/Matchbox/Dipoles/SubtractionDipole.cc b/MatrixElement/Matchbox/Dipoles/SubtractionDipole.cc
--- a/MatrixElement/Matchbox/Dipoles/SubtractionDipole.cc
+++ b/MatrixElement/Matchbox/Dipoles/SubtractionDipole.cc
@@ -1,1330 +1,1331 @@
// -*- C++ -*-
//
// SubtractionDipole.cc is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
//
// This is the implementation of the non-inlined, non-templated member
// functions of the SubtractionDipole class.
//
#include "SubtractionDipole.h"
#include "ThePEG/Utilities/DescribeClass.h"
#include "ThePEG/Interface/ClassDocumentation.h"
#include "ThePEG/Interface/Reference.h"
#include "ThePEG/Interface/RefVector.h"
#include "ThePEG/Interface/Parameter.h"
#include "ThePEG/Repository/Repository.h"
#include "ThePEG/StandardModel/StandardModelBase.h"
#include "ThePEG/Utilities/Rebinder.h"
#include "ThePEG/Persistency/PersistentOStream.h"
#include "ThePEG/Persistency/PersistentIStream.h"
#include "ThePEG/PDF/PartonBin.h"
#include "ThePEG/PDF/PartonExtractor.h"
#include "Herwig/MatrixElement/Matchbox/Phasespace/TildeKinematics.h"
#include "Herwig/MatrixElement/Matchbox/Phasespace/InvertedTildeKinematics.h"
#include "Herwig/MatrixElement/Matchbox/MatchboxFactory.h"
#include "Herwig/MatrixElement/Matchbox/Utility/DiagramDrawer.h"
#include <iterator>
using std::ostream_iterator;
using namespace Herwig;
SubtractionDipole::SubtractionDipole()
: MEBase(), theSplitting(false), theApply(true), theSubtractionTest(false),
theIgnoreCuts(false),
theRealEmitter(-1), theRealEmission(-1), theRealSpectator(-1),
lastRealEmissionKey(realEmissionKey(cPDVector(),-1,-1,-1)),
lastUnderlyingBornKey(underlyingBornKey(cPDVector(),-1,-1)),
theBornEmitter(-1), theBornSpectator(-1),
theLastSubtractionScale(ZERO), theLastSplittingScale(ZERO),
theLastSubtractionPt(ZERO), theLastSplittingPt(ZERO),
theLastSubtractionZ(0.0), theLastSplittingZ(0.0),
theRealShowerSubtraction(false), theVirtualShowerSubtraction(false),
theLoopSimSubtraction(false), theRealEmissionScales(false),
theShowerHardScale(ZERO), theShowerScale(ZERO),
theIsInShowerPhasespace(false), theIsAboveCutoff(false) {}
SubtractionDipole::~SubtractionDipole() {}
double SubtractionDipole::alpha() const{
return factory()->alphaParameter();
}
void SubtractionDipole::clearBookkeeping() {
theRealEmitter = -1;
theRealEmission = -1;
theRealSpectator = -1;
theBornEmitter = -1;
theBornSpectator = -1;
theMergingMap.clear();
theSplittingMap.clear();
theIndexMap.clear();
theUnderlyingBornDiagrams.clear();
theRealEmissionDiagrams.clear();
theBornToRealDiagrams.clear();
theRealToBornDiagrams.clear();
}
void SubtractionDipole::setupBookkeeping(const map<Ptr<DiagramBase>::ptr,SubtractionDipole::MergeInfo>& mergeInfo,bool slim) {
theMergingMap.clear();
theSplittingMap.clear();
theUnderlyingBornDiagrams.clear();
theRealEmissionDiagrams.clear();
theBornToRealDiagrams.clear();
theRealToBornDiagrams.clear();
int xemitter = -1;
int xspectator = -1;
map<int,int> mergeLegs;
map<int,int> remapLegs;
map<int,int> realBornMap;
map<int,int> bornRealMap;
set<Ptr<DiagramBase>::cptr> usedDiagrams;
for ( map<Ptr<DiagramBase>::ptr,MergeInfo>::const_iterator mit = mergeInfo.begin();
mit != mergeInfo.end(); ++mit ) {
DiagramVector::const_iterator bd =
theUnderlyingBornME->diagrams().end();
// work out the most similar underlying Born diagram
map<int,int> xRemapLegs;
int nomapScore = 0;
for ( DiagramVector::const_iterator b =
theUnderlyingBornME->diagrams().begin();
b != theUnderlyingBornME->diagrams().end(); ++b ) {
map<int,int> theRemapLegs;
if ( mit->second.diagram->isSame(*b,theRemapLegs) &&
usedDiagrams.find(*b) == usedDiagrams.end() ) {
int theNomapScore = 0;
for ( map<int,int>::const_iterator m = theRemapLegs.begin();
m != theRemapLegs.end(); ++m )
if ( m->first == m->second )
theNomapScore += 1;
if ( theNomapScore >= nomapScore ) {
nomapScore = theNomapScore;
xRemapLegs = theRemapLegs;
bd = b;
}
}
}
// no underlying Born
if ( bd == theUnderlyingBornME->diagrams().end() )
continue;
// as we deal with one splitting only we now mark this diagram as used
// since we fixed the overall remapping of the process from the first
// occurence, see below. TODO: This confuses this code even more, and
// clearly calls for a cleanup. This is just grown historically and got
// messed up with experiencing different processes and setups.
usedDiagrams.insert(*bd);
if ( xemitter == -1 ) {
xemitter = mit->second.emitter;
mergeLegs = mit->second.mergeLegs;
remapLegs = xRemapLegs;
assert(remapLegs.find(xemitter) != remapLegs.end());
xemitter = remapLegs[xemitter];
// work out the leg remapping real -> born
for ( map<int,int>::const_iterator k = mergeLegs.begin();
k != mergeLegs.end(); ++k ) {
assert(remapLegs.find(k->second) != remapLegs.end());
realBornMap[k->first] = remapLegs[k->second];
}
// work out the leg remapping born -> real
for ( map<int,int>::const_iterator k = realBornMap.begin();
k != realBornMap.end(); ++k ) {
bornRealMap[k->second] = k->first;
}
// work out the spectator
assert(mergeLegs.find(realSpectator()) != mergeLegs.end());
assert(remapLegs.find(mergeLegs[realSpectator()]) != remapLegs.end());
xspectator = realBornMap[realSpectator()];
}
RealEmissionKey realKey = realEmissionKey((*mit->first).partons(),realEmitter(),realEmission(),realSpectator());
UnderlyingBornKey bornKey = underlyingBornKey((**bd).partons(),xemitter,xspectator);
if ( theMergingMap.find(realKey) == theMergingMap.end() )
theMergingMap.insert(make_pair(realKey,make_pair(bornKey,realBornMap)));
RealEmissionInfo realInfo = make_pair(realKey,bornRealMap);
bool gotit = false;
typedef multimap<UnderlyingBornKey,RealEmissionInfo>::const_iterator spIterator;
pair<spIterator,spIterator> range = theSplittingMap.equal_range(bornKey);
for ( ; range.first != range.second; ++range.first )
if ( range.first->second == realInfo ) {
gotit = true;
break;
}
if ( !gotit )
theSplittingMap.insert(make_pair(bornKey,realInfo));
theUnderlyingBornDiagrams[process(realKey)].push_back(*bd);
theRealEmissionDiagrams[process(bornKey)].push_back(mit->first);
theBornToRealDiagrams[*bd] = mit->first;
theRealToBornDiagrams[mit->first] = *bd;
}
if (slim) {
theIndexMap.clear();
theSplittingMap.clear();
theBornToRealDiagrams.clear();
theRealEmissionDiagrams.clear();
}
if ( theSplittingMap.empty() )
return;
theIndexMap.clear();
for ( multimap<UnderlyingBornKey,RealEmissionInfo>::const_iterator s =
theSplittingMap.begin(); s != theSplittingMap.end(); ++s ) {
theIndexMap[process(s->first)] = make_pair(emitter(s->first),spectator(s->first));
}
}
void SubtractionDipole::subtractionBookkeeping() {
/*
if ( theMergingMap.empty() )
setupBookkeeping();
*/
assert(!theMergingMap.empty());
lastRealEmissionKey =
realEmissionKey(lastHeadXComb().mePartonData(),realEmitter(),realEmission(),realSpectator());
map<RealEmissionKey,UnderlyingBornInfo>::const_iterator k =
theMergingMap.find(lastRealEmissionKey);
if ( k == theMergingMap.end() ) {
theApply = false;
return;
}
theApply = true;
lastUnderlyingBornKey = k->second.first;
bornEmitter(emitter(lastUnderlyingBornKey));
bornSpectator(spectator(lastUnderlyingBornKey));
}
void SubtractionDipole::splittingBookkeeping() {
/*
if ( theMergingMap.empty() )
setupBookkeeping();
*/
assert(!theMergingMap.empty());
map<cPDVector,pair<int,int> >::const_iterator esit =
theIndexMap.find(lastHeadXComb().mePartonData());
if ( esit == theIndexMap.end() ) {
theApply = false;
return;
}
theApply = true;
pair<int,int> es = esit->second;
bornEmitter(es.first);
bornSpectator(es.second);
lastUnderlyingBornKey = underlyingBornKey(lastHeadXComb().mePartonData(),bornEmitter(),bornSpectator());
typedef multimap<UnderlyingBornKey,RealEmissionInfo>::const_iterator spit;
pair<spit,spit> kr = theSplittingMap.equal_range(lastUnderlyingBornKey);
assert(kr.first != kr.second);
lastRealEmissionInfo = kr.first;
for ( ; lastRealEmissionInfo != kr.second; ++lastRealEmissionInfo )
if ( process(lastRealEmissionInfo->second.first) == lastXComb().mePartonData() )
break;
assert(lastRealEmissionInfo != kr.second);
lastRealEmissionKey = lastRealEmissionInfo->second.first;
realEmitter(emitter(lastRealEmissionKey));
realEmission(emission(lastRealEmissionKey));
realSpectator(spectator(lastRealEmissionKey));
}
StdXCombPtr SubtractionDipole::makeXComb(Energy newMaxEnergy, const cPDPair & inc,
tEHPtr newEventHandler,tSubHdlPtr newSubProcessHandler,
tPExtrPtr newExtractor, tCascHdlPtr newCKKW,
const PBPair & newPartonBins, tCutsPtr newCuts,
const DiagramVector & newDiagrams, bool mir,
const PartonPairVec& allBins,
tStdXCombPtr newHead,
tMEPtr newME) {
if ( !newME )
newME = this;
if ( !splitting() ) {
return
underlyingBornME()->makeXComb(newMaxEnergy, inc,
newEventHandler, newSubProcessHandler,
newExtractor, newCKKW,
newPartonBins, newCuts,
newDiagrams, mir, allBins,
newHead, newME);
}
return
realEmissionME()->makeXComb(newMaxEnergy, inc,
newEventHandler, newSubProcessHandler,
newExtractor, newCKKW,
newPartonBins, newCuts,
newDiagrams, mir, allBins,
newHead, newME);
}
StdXCombPtr SubtractionDipole::makeXComb(tStdXCombPtr newHead,
const PBPair & newPartonBins,
const DiagramVector & newDiagrams,
tMEPtr newME) {
if ( !newME )
newME = this;
if ( !splitting() ) {
return
underlyingBornME()->makeXComb(newHead, newPartonBins,
newDiagrams, newME);
}
return
realEmissionME()->makeXComb(newHead, newPartonBins,
newDiagrams, newME);
}
StdXCombPtr SubtractionDipole::makeBornXComb(tStdXCombPtr realXC) {
const cPDVector& proc = const_cast<const StandardXComb&>(*realXC).mePartonData();
lastRealEmissionKey =
realEmissionKey(proc,realEmitter(),realEmission(),realSpectator());
map<RealEmissionKey,UnderlyingBornInfo>::const_iterator k =
theMergingMap.find(lastRealEmissionKey);
if ( k == theMergingMap.end() )
return StdXCombPtr();
PartonPairVec pbs = realXC->pExtractor()->getPartons(realXC->maxEnergy(),
realXC->particles(),
*(realXC->cuts()));
DiagramVector bornDiags = underlyingBornDiagrams(proc);
assert(!bornDiags.empty());
PartonPairVec::iterator ppit = pbs.begin();
for ( ; ppit != pbs.end(); ++ppit ) {
if ( ppit->first->parton() == bornDiags.front()->partons()[0] &&
ppit->second->parton() == bornDiags.front()->partons()[1] )
break;
}
assert(ppit != pbs.end());
return
underlyingBornME()->makeXComb(realXC,*ppit,bornDiags,this);
}
vector<StdXCombPtr> SubtractionDipole::makeRealXCombs(tStdXCombPtr bornXC) {
const cPDVector& proc = const_cast<const StandardXComb&>(*bornXC).mePartonData();
map<cPDVector,pair<int,int> >::const_iterator esit = theIndexMap.find(proc);
if ( esit == theIndexMap.end() )
return vector<StdXCombPtr>();
pair<int,int> es = esit->second;
bornEmitter(es.first);
bornSpectator(es.second);
lastUnderlyingBornKey = underlyingBornKey(proc,bornEmitter(),bornSpectator());
if ( theSplittingMap.find(lastUnderlyingBornKey) == theSplittingMap.end() )
return vector<StdXCombPtr>();
PartonPairVec pbs = bornXC->pExtractor()->getPartons(bornXC->maxEnergy(),
bornXC->particles(),
*(bornXC->cuts()));
DiagramVector realDiags = realEmissionDiagrams(proc);
assert(!realDiags.empty());
vector<StdXCombPtr> res;
map<cPDVector,DiagramVector> realProcs;
for ( MEBase::DiagramVector::const_iterator d = realDiags.begin();
d != realDiags.end(); ++d ) {
realProcs[(**d).partons()].push_back(*d);
}
for ( map<cPDVector,DiagramVector>::const_iterator pr =
realProcs.begin(); pr != realProcs.end(); ++pr ) {
PartonPairVec::iterator ppit = pbs.begin();
for ( ; ppit != pbs.end(); ++ppit ) {
if ( ppit->first->parton() == pr->second.front()->partons()[0] &&
ppit->second->parton() == pr->second.front()->partons()[1] )
break;
}
assert(ppit != pbs.end());
StdXCombPtr rxc =
realEmissionME()->makeXComb(bornXC,*ppit,pr->second,this);
res.push_back(rxc);
}
return res;
}
const MEBase::DiagramVector& SubtractionDipole::underlyingBornDiagrams(const cPDVector& real) const {
static DiagramVector empty;
map<cPDVector,DiagramVector>::const_iterator k = theUnderlyingBornDiagrams.find(real);
if (k == theUnderlyingBornDiagrams.end() )
return empty;
return k->second;
}
tcDiagPtr SubtractionDipole::underlyingBornDiagram(tcDiagPtr realDiag) const {
map<tcDiagPtr,tcDiagPtr>::const_iterator it = theRealToBornDiagrams.find(realDiag);
assert(it != theRealToBornDiagrams.end());
return it->second;
}
const MEBase::DiagramVector& SubtractionDipole::realEmissionDiagrams(const cPDVector& born) const {
static DiagramVector empty;
map<cPDVector,DiagramVector>::const_iterator k = theRealEmissionDiagrams.find(born);
if ( k == theRealEmissionDiagrams.end() )
return empty;
return k->second;
}
tcDiagPtr SubtractionDipole::realEmissionDiagram(tcDiagPtr bornDiag) const {
map<tcDiagPtr,tcDiagPtr>::const_iterator it = theBornToRealDiagrams.find(bornDiag);
assert(it != theBornToRealDiagrams.end());
return it->second;
}
void SubtractionDipole::getDiagrams() const {
if ( splitting() ) {
realEmissionME()->diagrams();
useDiagrams(realEmissionME());
} else {
underlyingBornME()->diagrams();
useDiagrams(underlyingBornME());
}
}
Selector<MEBase::DiagramIndex> SubtractionDipole::diagrams(const DiagramVector & dv) const {
Ptr<MatchboxMEBase>::tcptr me =
splitting() ?
realEmissionME() :
underlyingBornME();
if ( me->phasespace() ) {
me->phasespace()->setXComb(lastXCombPtr());
+ me->phasespace()->clearDiagramWeights();
me->phasespace()->fillDiagramWeights();
}
return
me->diagrams(dv);
}
Selector<const ColourLines *>
SubtractionDipole::colourGeometries(tcDiagPtr diag) const {
return
splitting() ?
realEmissionME()->colourGeometries(diag) :
underlyingBornME()->colourGeometries(diag);
}
const ColourLines &
SubtractionDipole::selectColourGeometry(tcDiagPtr diag) const {
return
splitting() ?
realEmissionME()->selectColourGeometry(diag) :
underlyingBornME()->selectColourGeometry(diag);
}
void SubtractionDipole::flushCaches() {
theUnderlyingBornME->flushCaches();
theRealEmissionME->flushCaches();
for ( vector<Ptr<MatchboxReweightBase>::ptr>::iterator r =
reweights().begin(); r != reweights().end(); ++r ) {
(**r).flushCaches();
}
}
void SubtractionDipole::setXComb(tStdXCombPtr xc) {
if ( !xc ) {
theApply = false;
return;
} else {
theApply = true;
}
lastMatchboxXComb(xc);
MEBase::setXComb(xc);
if ( splitting() ) {
realEmissionME()->setXComb(xc);
underlyingBornME()->setXComb(xc->head());
splittingBookkeeping();
} else {
realEmissionME()->setXComb(xc->head());
underlyingBornME()->setXComb(xc);
subtractionBookkeeping();
}
if ( !apply() )
return;
}
void SubtractionDipole::setKinematics() {
MEBase::setKinematics();
if ( splitting() )
realEmissionME()->setKinematics();
else
underlyingBornME()->setKinematics();
}
bool SubtractionDipole::generateKinematics(const double * r) {
if ( lastXCombPtr()->kinematicsGenerated() )
return true;
if ( splitting() ) {
if ( !generateRadiationKinematics(r) )
return false;
if( ! realEmissionME()->lastXCombPtr()->setIncomingPartons())
return false;
realEmissionME()->setScale();
double jac = jacobian();
jac *= pow(underlyingBornME()->lastXComb().lastSHat() / realEmissionME()->lastXComb().lastSHat(),
realEmissionME()->lastXComb().mePartonData().size()-4.);
jacobian(jac);
assert(lastXCombPtr() == realEmissionME()->lastXCombPtr());
lastXCombPtr()->didGenerateKinematics();
return true;
}
if ( !generateTildeKinematics() ){ return false;}
if( ! underlyingBornME()->lastXCombPtr()->setIncomingPartons() )
return false;
underlyingBornME()->setScale();
assert(lastXCombPtr() == underlyingBornME()->lastXCombPtr());
if( ! underlyingBornME()->lastXCombPtr()->setIncomingPartons() )
return false;
// need to have the scale and x's available for checking shower phase space
if ( showerApproximation() &&
lastXCombPtr()->willPassCuts() )
showerApproximation()->getShowerVariables();
lastXCombPtr()->didGenerateKinematics();
return true;
}
int SubtractionDipole::nDim() const {
if ( !splitting() )
return underlyingBornME()->nDim();
return underlyingBornME()->nDim() + nDimRadiation();
}
void SubtractionDipole::clearKinematics() {
MEBase::clearKinematics();
if ( splitting() )
realEmissionME()->clearKinematics();
else
underlyingBornME()->clearKinematics();
}
void SubtractionDipole::tildeKinematics(Ptr<TildeKinematics>::tptr tk) {
theTildeKinematics = tk;
}
bool SubtractionDipole::generateTildeKinematics() {
assert(!splitting());
Ptr<TildeKinematics>::tptr kinematics = theTildeKinematics;
if ( showerApproximation() ) {
showerApproximation()->setBornXComb(lastXCombPtr());
showerApproximation()->setRealXComb(realEmissionME()->lastXCombPtr());
showerApproximation()->setDipole(this);
showerApproximation()->checkCutoff();
if ( showerApproximation()->showerTildeKinematics() &&
isAboveCutoff() &&
realShowerSubtraction() )
kinematics = showerApproximation()->showerTildeKinematics();
}
if ( !kinematics ) {
jacobian(0.0);
return false;
}
kinematics->prepare(lastHeadXCombPtr(),lastXCombPtr());
if ( !kinematics->doMap() ) {
jacobian(0.0);
return false;
}
theLastSubtractionScale = kinematics->lastScale();
theLastSubtractionPt = kinematics->lastPt();
theLastSubtractionZ = kinematics->lastZ();
meMomenta().resize(lastHeadXComb().meMomenta().size() - 1);
assert(mergingMap().find(lastRealEmissionKey) != mergingMap().end());
map<int,int>& trans = theMergingMap[lastRealEmissionKey].second;
int n = lastHeadXComb().meMomenta().size();
for ( int k = 0; k < n; ++k ) {
if ( k == realEmitter() || k == realEmission() || k == realSpectator() )
continue;
meMomenta()[trans[k]] = lastHeadXComb().meMomenta()[k];
if ( kinematics->doesTransform() && k > 1 )
meMomenta()[trans[k]] = kinematics->transform(meMomenta()[trans[k]]);
}
meMomenta()[bornEmitter()] =
const_cast<const TildeKinematics&>(*kinematics).bornEmitterMomentum();
meMomenta()[bornSpectator()] =
const_cast<const TildeKinematics&>(*kinematics).bornSpectatorMomentum();
cPDVector::const_iterator pd = mePartonData().begin();
vector<Lorentz5Momentum>::iterator p = meMomenta().begin();
for ( ; pd != mePartonData().end(); ++pd, ++p ) {
p->setMass((**pd).hardProcessMass());
p->rescaleRho();
}
jacobian(realEmissionME()->lastXComb().jacobian());
logGenerateTildeKinematics();
return true;
}
void SubtractionDipole::invertedTildeKinematics(Ptr<InvertedTildeKinematics>::tptr itk) {
theInvertedTildeKinematics = itk;
}
int SubtractionDipole::nDimRadiation() const {
return invertedTildeKinematics() ?
invertedTildeKinematics()->nDimRadiation() :
0;
}
bool SubtractionDipole::generateRadiationKinematics(const double * r) {
assert(splitting());
Ptr<InvertedTildeKinematics>::tptr kinematics = theInvertedTildeKinematics;
if ( showerApproximation() ) {
showerApproximation()->setBornXComb(lastHeadXCombPtr());
showerApproximation()->setRealXComb(lastXCombPtr());
showerApproximation()->setDipole(this);
if ( showerApproximation()->showerInvertedTildeKinematics() ) {
kinematics = showerApproximation()->showerInvertedTildeKinematics();
}
}
if ( !kinematics ) {
jacobian(0.0);
return false;
}
kinematics->prepare(lastXCombPtr(),lastHeadXCombPtr());
if ( !kinematics->doMap(r) ) {
jacobian(0.0);
return false;
}
theLastSplittingScale = kinematics->lastScale();
theLastSplittingPt = kinematics->lastPt();
theLastSplittingZ = kinematics->lastZ();
meMomenta().resize(lastHeadXComb().meMomenta().size() + 1);
assert(splittingMap().find(lastUnderlyingBornKey) != splittingMap().end());
map<int,int>& trans = const_cast<map<int,int>&>(lastRealEmissionInfo->second.second);
int n = lastHeadXComb().meMomenta().size();
for ( int k = 0; k < n; ++k ) {
if ( k == bornEmitter() || k == bornSpectator() )
continue;
meMomenta()[trans[k]] = lastHeadXComb().meMomenta()[k];
if ( kinematics->doesTransform() && k > 1 )
meMomenta()[trans[k]] = kinematics->transform(meMomenta()[trans[k]]);
}
meMomenta()[realEmitter()] =
const_cast<const InvertedTildeKinematics&>(*kinematics).realEmitterMomentum();
meMomenta()[realEmission()] =
const_cast<const InvertedTildeKinematics&>(*kinematics).realEmissionMomentum();
meMomenta()[realSpectator()] =
const_cast<const InvertedTildeKinematics&>(*kinematics).realSpectatorMomentum();
cPDVector::const_iterator pd = mePartonData().begin();
vector<Lorentz5Momentum>::iterator p = meMomenta().begin();
for ( ; pd != mePartonData().end(); ++pd, ++p ) {
p->setMass((**pd).hardProcessMass());
p->rescaleRho();
}
jacobian(underlyingBornME()->lastXComb().jacobian() *
kinematics->jacobian());
logGenerateRadiationKinematics(r);
return true;
}
void SubtractionDipole::ptCut(Energy cut) {
theInvertedTildeKinematics->ptCut(cut);
}
CrossSection SubtractionDipole::dSigHatDR(Energy2 factorizationScale) const {
double pdfweight = 1.;
double jac = jacobian();
if ( splitting() && jac == 0.0 ) {
lastMECrossSection(ZERO);
return ZERO;
}
if ( factorizationScale == ZERO ) {
factorizationScale = underlyingBornME()->lastScale();
}
if ( havePDFWeight1() ) {
pdfweight *= realEmissionME()->pdf1(factorizationScale);
}
if ( havePDFWeight2() ) {
pdfweight *= realEmissionME()->pdf2(factorizationScale);
}
lastMEPDFWeight(pdfweight);
bool needTheDipole = true;
CrossSection shower = ZERO;
double lastThetaMu = 1.0;
double showerFactor = 1.;
if ( showerApproximation() ) {
assert(!splitting());
showerApproximation()->setBornXComb(lastXCombPtr());
showerApproximation()->setRealXComb(realEmissionME()->lastXCombPtr());
showerApproximation()->setDipole(const_cast<SubtractionDipole*>(this));
if ( !isAboveCutoff() ) {
showerApproximation()->wasBelowCutoff();
lastThetaMu = 0.0;
} else {
lastThetaMu = 1.0;
}
if ( lastThetaMu > 0.0 && isInShowerPhasespace() ) {
if ( realShowerSubtraction() )
shower = showerApproximation()->dSigHatDR()*lastThetaMu;
if ( virtualShowerSubtraction() || loopSimSubtraction() )
shower = -showerApproximation()->dSigHatDR()*lastThetaMu;
if ( virtualShowerSubtraction() &&
isAboveCutoff() &&
showerApproximation()->showerTildeKinematics() ) {
// map shower to dipole kinematics; we are always above the
// cutoff in this case
showerFactor *=
showerApproximation()->showerTildeKinematics()->jacobianRatio();
}
shower *= showerFactor;
}
if ( realShowerSubtraction() && lastThetaMu == 1.0 )
needTheDipole = false;
if ( virtualShowerSubtraction() && lastThetaMu == 0.0 )
needTheDipole = false;
if ( factory()->loopSimCorrections() ||
factory()->meCorrectionsOnly() )
needTheDipole = false;
}
double xme2 = 0.0;
if ( needTheDipole )
xme2 = me2();
if ( factory()->loopSimCorrections() ||
factory()->meCorrectionsOnly() ) {
assert(showerApproximation());
xme2 = realEmissionME()->me2() * showerApproximation()->channelWeight();
double rws =
pow(underlyingBornME()->lastXComb().lastAlphaS()/
realEmissionME()->lastXComb().lastAlphaS(),
realEmissionME()->orderInAlphaS());
xme2 *= rws;
double rwe =
pow(underlyingBornME()->lastXComb().lastAlphaEM()/
realEmissionME()->lastXComb().lastAlphaEM(),
underlyingBornME()->orderInAlphaEW());
xme2 *= rwe;
}
if ( realShowerSubtraction() )
xme2 *= 1. - lastThetaMu;
if ( virtualShowerSubtraction() || loopSimSubtraction() )
xme2 *= lastThetaMu;
double coupl = lastMECouplings();
coupl *= underlyingBornME()->lastXComb().lastAlphaS();
lastMECouplings(coupl);
CrossSection res =
sqr(hbarc) * jac * pdfweight * xme2 /
(2. * realEmissionME()->lastXComb().lastSHat());
if ( !showerApproximation() && xme2 != 0.0 ) {
double weight = 0.0;
bool applied = false;
for ( vector<Ptr<MatchboxReweightBase>::ptr>::const_iterator rw =
theReweights.begin(); rw != theReweights.end(); ++rw ) {
(**rw).setXComb(theRealEmissionME->lastXCombPtr());
if ( !(**rw).apply() )
continue;
weight += (**rw).evaluate();
applied = true;
}
if ( applied )
res *= weight;
}
lastMECrossSection(-res-shower);
logDSigHatDR(jac);
return lastMECrossSection();
}
bool SubtractionDipole::aboveAlpha() const{return theTildeKinematics->aboveAlpha();}
CrossSection SubtractionDipole::prefactor(Energy2 factorizationScale)const{
const double jac = jacobian();
assert( factorizationScale != ZERO );
assert (! splitting());
double pdfweight = 1.;
if ( havePDFWeight1() ) pdfweight *= realEmissionME()->pdf1(factorizationScale);
if ( havePDFWeight2() ) pdfweight *= realEmissionME()->pdf2(factorizationScale);
return sqr(hbarc) * jac * pdfweight / (2. * realEmissionME()->lastXComb().lastSHat());
}
CrossSection SubtractionDipole::ps(Energy2 factorizationScale,Ptr<ColourBasis>::tptr largeNBasis) const {
double ccme2 =underlyingBornME()->me2()*
underlyingBornME()->
largeNColourCorrelatedME2(
make_pair(bornEmitter(),bornSpectator()),largeNBasis)/
underlyingBornME()->largeNME2(largeNBasis);
return prefactor(factorizationScale) * me2Avg(ccme2);
}
pair<CrossSection,CrossSection> SubtractionDipole::dipandPs(Energy2 factorizationScale,Ptr<ColourBasis>::tptr largeNBasis) const {
CrossSection factor= prefactor(factorizationScale);
double ccme2 =underlyingBornME()->me2()*
underlyingBornME()->
largeNColourCorrelatedME2(
make_pair(bornEmitter(),bornSpectator()),largeNBasis)/
underlyingBornME()->largeNME2(largeNBasis);
double ps = me2Avg(ccme2);
double dip = me2();
return make_pair(factor*dip,factor*ps);
}
CrossSection SubtractionDipole::dip(Energy2 factorizationScale) const {
CrossSection factor= prefactor(factorizationScale);
double dip = me2();
return factor*dip;
}
void SubtractionDipole::print(ostream& os) const {
os << "--- SubtractionDipole setup ----------------------------------------------------\n";
os << " subtraction '" << name() << "'\n for real emission '"
<< theRealEmissionME->name() << "'\n using underlying Born '"
<< theUnderlyingBornME->name() << "'\n";
os << " tilde kinematics are '"
<< (theTildeKinematics ? theTildeKinematics->name() : "")
<< " '\n inverted tilde kinematics are '"
<< (theInvertedTildeKinematics ? theInvertedTildeKinematics->name() : "") << "'\n";
os << " the following subtraction mappings have been found:\n";
for ( map<RealEmissionKey,UnderlyingBornInfo>::const_iterator m =
theMergingMap.begin(); m != theMergingMap.end(); ++m ) {
os << " " << process(m->second.first)[0]->PDGName() << " "
<< process(m->second.first)[1]->PDGName() << " -> ";
for ( cPDVector::const_iterator p = process(m->second.first).begin() + 2;
p != process(m->second.first).end(); ++p ) {
os << (**p).PDGName() << " ";
}
os << "[" << emitter(m->second.first) << "," << spectator(m->second.first) << "] <=> ";
os << process(m->first)[0]->PDGName() << " "
<< process(m->first)[1]->PDGName() << " -> ";
for ( cPDVector::const_iterator p = process(m->first).begin() + 2;
p != process(m->first).end(); ++p ) {
os << (**p).PDGName() << " ";
}
os << "[(" << emitter(m->first) << "," << emission(m->first) << ")," << spectator(m->first) << "]\n"
<< " non-dipole momenta ( ";
for ( map<int,int>::const_iterator k = m->second.second.begin();
k != m->second.second.end(); ++k ) {
if ( k->first == spectator(m->first) )
continue;
os << k->second << " ";
}
os << ") <=> ( ";
for ( map<int,int>::const_iterator k = m->second.second.begin();
k != m->second.second.end(); ++k ) {
if ( k->first == spectator(m->first) )
continue;
os << k->first << " ";
}
os << ")\n";
}
os << "--------------------------------------------------------------------------------\n";
os << flush;
}
void SubtractionDipole::printLastEvent(ostream& os) const {
os << "--- SubtractionDipole last event information -----------------------------------\n";
os << " for dipole '" << name() << "' applying ["
<< bornEmitter() << "," << bornSpectator() << "] <=> [("
<< realEmitter() << "," << realEmission() << ")," << realSpectator() << "]\n"
<< " evaluated the cross section/nb " << (lastMECrossSection()/nanobarn) << "\n"
<< " with subtraction parameters x[0] = " << subtractionParameters()[0]
<< " x[1] = " << subtractionParameters()[1] << "\n";
os << " the last real emission event was:\n";
realEmissionME()->printLastEvent(os);
os << " the last underlying Born event was:\n";
underlyingBornME()->printLastEvent(os);
os << "--- end SubtractionDipole last event information -------------------------------\n";
os << flush;
}
void SubtractionDipole::logME2() const {
if ( !realEmissionME()->verbose() &&
!underlyingBornME()->verbose() )
return;
tcStdXCombPtr bornxc = splitting() ? lastHeadXCombPtr() : lastXCombPtr();
tcStdXCombPtr realxc = splitting() ? lastXCombPtr() : lastHeadXCombPtr();
generator()->log() << "'" << name() << "' evaluated me2 using\n"
<< "Born XComb " << bornxc << " real XComb " << realxc << "\n";
generator()->log() << "subtraction parameters: ";
copy(subtractionParameters().begin(),subtractionParameters().end(),
ostream_iterator<double>(generator()->log()," "));
generator()->log() << "\n";
generator()->log() << "Born phase space point (in GeV):\n";
vector<Lorentz5Momentum>::const_iterator pit = bornxc->meMomenta().begin();
cPDVector::const_iterator dit = bornxc->mePartonData().begin();
for ( ; pit != bornxc->meMomenta().end() ; ++pit, ++dit )
generator()->log() << (**dit).PDGName() << " : "
<< (*pit/GeV) << "\n";
generator()->log() << "with x1 = " << bornxc->lastX1() << " x2 = " << bornxc->lastX2() << "\n"
<< "sHat/GeV2 = " << (bornxc->lastSHat()/GeV2) << "\n";
generator()->log() << "Real emission phase space point (in GeV):\n";
pit = realxc->meMomenta().begin();
dit = realxc->mePartonData().begin();
for ( ; pit != realxc->meMomenta().end() ; ++pit, ++dit )
generator()->log() << (**dit).PDGName() << " : "
<< (*pit/GeV) << "\n";
generator()->log() << "with x1 = " << realxc->lastX1() << " x2 = " << realxc->lastX2() << "\n"
<< "sHat/GeV2 = " << (realxc->lastSHat()/GeV2) << "\n";
}
void SubtractionDipole::logDSigHatDR(double effectiveJac) const {
if ( !realEmissionME()->verbose() &&
!underlyingBornME()->verbose() )
return;
tcStdXCombPtr bornxc = splitting() ? lastHeadXCombPtr() : lastXCombPtr();
tcStdXCombPtr realxc = splitting() ? lastXCombPtr() : lastHeadXCombPtr();
generator()->log() << "'" << name() << "' evaluated cross section using\n"
<< "Born XComb " << bornxc << " real XComb " << realxc << "\n"
<< "Jacobian = " << jacobian()
<< " effective Jacobian = " << effectiveJac << "\n"
<< "Born sHat/GeV2 = " << (bornxc->lastSHat()/GeV2)
<< " real sHat/GeV2 = " << (realxc->lastSHat()/GeV2)
<< " dsig/nb = "
<< (lastMECrossSection()/nanobarn) << "\n" << flush;
}
void SubtractionDipole::logGenerateTildeKinematics() const {
if ( !realEmissionME()->verbose() &&
!underlyingBornME()->verbose() )
return;
generator()->log() << "'" << name() << "' generating tilde kinematics.\n"
<< "configuration: [" << bornEmitter() << ","
<< bornSpectator() << "] => "
<< "[(" << realEmitter() << "," << realEmission() << "),"
<< realSpectator() << "]\n"
<< "with real xcomb " << lastHeadXCombPtr() << " born xcomb "
<< lastXCombPtr() << "\n"
<< "from real emission phase space point:\n";
Lorentz5Momentum rSum;
vector<Lorentz5Momentum>::const_iterator pr = lastHeadXComb().meMomenta().begin();
cPDVector::const_iterator dr = lastHeadXComb().mePartonData().begin();
size_t count = 0;
for ( ; pr != lastHeadXComb().meMomenta().end(); ++pr,++dr ) {
generator()->log() << (**dr).PDGName() << " : "
<< (*pr/GeV) << "\n";
if ( count < 2 ) {
rSum -= *pr;
} else {
rSum += *pr;
}
++count;
}
generator()->log() << "sum : " << (rSum/GeV) << "\n";
generator()->log() << "subtraction parameters: ";
copy(subtractionParameters().begin(),subtractionParameters().end(),
ostream_iterator<double>(generator()->log()," "));
generator()->log() << "\n"
<< "with scale/GeV = " << (theLastSubtractionScale/GeV)
<< "and pt/GeV = " << (theLastSubtractionPt/GeV) << "\n";
generator()->log() << "generated tilde kinematics:\n";
pr = lastXComb().meMomenta().begin();
dr = lastXComb().mePartonData().begin();
count = 0;
Lorentz5Momentum bSum;
for ( ; pr != lastXComb().meMomenta().end(); ++pr,++dr ) {
generator()->log() << (**dr).PDGName() << " : "
<< (*pr/GeV) << "\n";
if ( count < 2 ) {
bSum -= *pr;
} else {
bSum += *pr;
}
++count;
}
generator()->log() << "sum : " << (bSum/GeV) << "\n";
generator()->log() << "Jacobian = " << jacobian() << "\n" << flush;
}
void SubtractionDipole::logGenerateRadiationKinematics(const double * r) const {
if ( !realEmissionME()->verbose() &&
!underlyingBornME()->verbose() )
return;
generator()->log() << "'" << name() << "' generating radiation kinematics.\n"
<< "configuration: [" << bornEmitter() << ","
<< bornSpectator() << "] => "
<< "[(" << realEmitter() << "," << realEmission() << "),"
<< realSpectator() << "]\n"
<< "with born xcomb " << lastHeadXCombPtr() << " real xcomb "
<< lastXCombPtr() << "\n"
<< "from random numbers:\n";
copy(r,r+nDimRadiation(),ostream_iterator<double>(generator()->log()," "));
generator()->log() << "\n";
generator()->log() << "and born phase space point:\n";
vector<Lorentz5Momentum>::const_iterator pr = lastHeadXComb().meMomenta().begin();
cPDVector::const_iterator dr = lastHeadXComb().mePartonData().begin();
for ( ; pr != lastHeadXComb().meMomenta().end(); ++pr,++dr )
generator()->log() << (**dr).PDGName() << " : "
<< (*pr/GeV) << "\n";
generator()->log() << "subtraction parameters: ";
copy(subtractionParameters().begin(),subtractionParameters().end(),
ostream_iterator<double>(generator()->log()," "));
generator()->log() << "\n" << flush;
generator()->log() << "scales: scale/GeV = " << (theLastSplittingScale/GeV)
<< " pt/GeV = " << (theLastSplittingPt/GeV) << "\n" << flush;
generator()->log() << "generated real emission kinematics:\n";
pr = lastXComb().meMomenta().begin();
dr = lastXComb().mePartonData().begin();
for ( ; pr != lastXComb().meMomenta().end(); ++pr,++dr )
generator()->log() << (**dr).PDGName() << " : "
<< (*pr/GeV) << "\n";
generator()->log() << "Jacobian = "
<< jacobian() << " = "
<< underlyingBornME()->lastXComb().jacobian()
<< "|Born * "
<< invertedTildeKinematics()->jacobian()
<< "|Radiation\n" << flush;
}
void SubtractionDipole::doinit() {
MEBase::doinit();
if ( underlyingBornME() ) {
theUnderlyingBornME->init();
}
if ( realEmissionME() ) {
theRealEmissionME->init();
}
if ( tildeKinematics() ) {
theTildeKinematics->init();
}
if ( invertedTildeKinematics() ) {
theInvertedTildeKinematics->init();
}
if ( showerApproximation() ) {
theShowerApproximation->init();
}
for ( vector<Ptr<SubtractionDipole>::tptr>::iterator p = thePartners.begin();
p != thePartners.end(); ++p ) {
(**p).init();
}
for ( vector<Ptr<MatchboxReweightBase>::ptr>::iterator rw =
theReweights.begin(); rw != theReweights.end(); ++rw ) {
(**rw).init();
}
}
void SubtractionDipole::doinitrun() {
MEBase::doinitrun();
if ( underlyingBornME() ) {
theUnderlyingBornME->initrun();
}
if ( realEmissionME() ) {
theRealEmissionME->initrun();
}
if ( tildeKinematics() ) {
theTildeKinematics->initrun();
}
if ( invertedTildeKinematics() ) {
theInvertedTildeKinematics->initrun();
}
if ( showerApproximation() ) {
theShowerApproximation->initrun();
}
for ( vector<Ptr<SubtractionDipole>::tptr>::iterator p = thePartners.begin();
p != thePartners.end(); ++p ) {
(**p).initrun();
}
for ( vector<Ptr<MatchboxReweightBase>::ptr>::iterator rw =
theReweights.begin(); rw != theReweights.end(); ++rw ) {
(**rw).initrun();
}
}
void SubtractionDipole::cloneDependencies(const std::string& prefix,bool slim) {
if ( underlyingBornME() ) {
Ptr<MatchboxMEBase>::ptr myUnderlyingBornME = underlyingBornME()->cloneMe();
ostringstream pname;
pname << (prefix == "" ? fullName() : prefix) << "/" << myUnderlyingBornME->name();
if ( ! (generator()->preinitRegister(myUnderlyingBornME,pname.str()) ) )
throw Exception() << "SubtractionDipole::cloneDependencies(): Matrix element " << pname.str() << " already existing." << Exception::runerror;
myUnderlyingBornME->cloneDependencies(pname.str(),slim);
underlyingBornME(myUnderlyingBornME);
}
if ( realEmissionME()&& !slim ) {
Ptr<MatchboxMEBase>::ptr myRealEmissionME = realEmissionME()->cloneMe();
ostringstream pname;
pname << (prefix == "" ? fullName() : prefix) << "/" << myRealEmissionME->name();
if ( ! (generator()->preinitRegister(myRealEmissionME,pname.str()) ) )
throw Exception() << "SubtractionDipole::cloneDependencies(): Matrix element " << pname.str() << " already existing." << Exception::runerror;
myRealEmissionME->cloneDependencies(pname.str());
realEmissionME(myRealEmissionME);
}
if ( tildeKinematics() ) {
Ptr<TildeKinematics>::ptr myTildeKinematics = tildeKinematics()->cloneMe();
ostringstream pname;
pname << (prefix == "" ? fullName() : prefix) << "/" << myTildeKinematics->name();
if ( ! (generator()->preinitRegister(myTildeKinematics,pname.str()) ) )
throw Exception() << "SubtractionDipole::cloneDependencies(): Tilde kinematics " << pname.str() << " already existing." << Exception::runerror;
myTildeKinematics->dipole(this);
tildeKinematics(myTildeKinematics);
}
if ( invertedTildeKinematics()&& !slim ) {
Ptr<InvertedTildeKinematics>::ptr myInvertedTildeKinematics = invertedTildeKinematics()->cloneMe();
ostringstream pname;
pname << (prefix == "" ? fullName() : prefix) << "/" << myInvertedTildeKinematics->name();
if ( ! (generator()->preinitRegister(myInvertedTildeKinematics,pname.str()) ) )
throw Exception() << "SubtractionDipole::cloneDependencies(): Inverted tilde kinematics " << pname.str() << " already existing." << Exception::runerror;
myInvertedTildeKinematics->dipole(this);
invertedTildeKinematics(myInvertedTildeKinematics);
}
for ( vector<Ptr<MatchboxReweightBase>::ptr>::iterator rw =
theReweights.begin(); rw != theReweights.end(); ++rw ) {
Ptr<MatchboxReweightBase>::ptr myReweight = (**rw).cloneMe();
ostringstream pname;
pname << (prefix == "" ? fullName() : prefix) << "/" << (**rw).name();
if ( ! (generator()->preinitRegister(myReweight,pname.str()) ) )
throw Exception() << "SubtractionDipole::cloneDependencies(): Reweight " << pname.str() << " already existing." << Exception::runerror;
myReweight->cloneDependencies(pname.str());
*rw = myReweight;
}
}
void SubtractionDipole::constructVertex(tSubProPtr sub) {
if ( splitting() )
realEmissionME()->constructVertex(sub);
else
underlyingBornME()->constructVertex(sub);
}
void SubtractionDipole::constructVertex(tSubProPtr sub, const ColourLines* cl) {
if ( splitting() )
realEmissionME()->constructVertex(sub,cl);
else
underlyingBornME()->constructVertex(sub,cl);
}
void SubtractionDipole::generateSubCollision(SubProcess & sub) {
if ( splitting() )
realEmissionME()->generateSubCollision(sub);
else
underlyingBornME()->generateSubCollision(sub);
}
void SubtractionDipole::persistentOutput(PersistentOStream & os) const {
os << theLastXComb << theSplitting << theApply << theSubtractionTest
<< theIgnoreCuts << theRealEmissionME << theUnderlyingBornME
<< thePartners << theTildeKinematics << theInvertedTildeKinematics
<< theReweights << theRealEmitter << theRealEmission << theRealSpectator
<< theSubtractionParameters << theMergingMap << theSplittingMap
<< theIndexMap << theUnderlyingBornDiagrams << theRealEmissionDiagrams
<< theBornToRealDiagrams << theRealToBornDiagrams
<< lastRealEmissionKey << lastUnderlyingBornKey
<< theBornEmitter << theBornSpectator << ounit(theLastSubtractionScale,GeV)
<< ounit(theLastSplittingScale,GeV) << ounit(theLastSubtractionPt,GeV)
<< ounit(theLastSplittingPt,GeV) << theLastSubtractionZ
<< theLastSplittingZ << theShowerApproximation
<< theRealShowerSubtraction << theVirtualShowerSubtraction
<< theLoopSimSubtraction << theRealEmissionScales << theFactory
<< ounit(theShowerHardScale,GeV) << ounit(theShowerScale,GeV)
<< theShowerParameters << theIsInShowerPhasespace << theIsAboveCutoff;
}
void SubtractionDipole::persistentInput(PersistentIStream & is, int) {
is >> theLastXComb >> theSplitting >> theApply >> theSubtractionTest
>> theIgnoreCuts >> theRealEmissionME >> theUnderlyingBornME
>> thePartners >> theTildeKinematics >> theInvertedTildeKinematics
>> theReweights >> theRealEmitter >> theRealEmission >> theRealSpectator
>> theSubtractionParameters >> theMergingMap >> theSplittingMap
>> theIndexMap >> theUnderlyingBornDiagrams >> theRealEmissionDiagrams
>> theBornToRealDiagrams >> theRealToBornDiagrams
>> lastRealEmissionKey >> lastUnderlyingBornKey
>> theBornEmitter >> theBornSpectator >> iunit(theLastSubtractionScale,GeV)
>> iunit(theLastSplittingScale,GeV) >> iunit(theLastSubtractionPt,GeV)
>> iunit(theLastSplittingPt,GeV) >> theLastSubtractionZ
>> theLastSplittingZ >> theShowerApproximation
>> theRealShowerSubtraction >> theVirtualShowerSubtraction
>> theLoopSimSubtraction >> theRealEmissionScales >> theFactory
>> iunit(theShowerHardScale,GeV) >> iunit(theShowerScale,GeV)
>> theShowerParameters >> theIsInShowerPhasespace >> theIsAboveCutoff;
lastMatchboxXComb(theLastXComb);
typedef multimap<UnderlyingBornKey,RealEmissionInfo>::const_iterator spit;
pair<spit,spit> kr = theSplittingMap.equal_range(lastUnderlyingBornKey);
lastRealEmissionInfo = kr.first;
for ( ; lastRealEmissionInfo != kr.second; ++lastRealEmissionInfo )
if ( process(lastRealEmissionInfo->second.first) == lastXComb().mePartonData() )
break;
}
Ptr<MatchboxFactory>::tptr SubtractionDipole::factory() const {
return theFactory;
}
void SubtractionDipole::factory(Ptr<MatchboxFactory>::tptr f) {
theFactory = f;
}
void SubtractionDipole::Init() {
static ClassDocumentation<SubtractionDipole> documentation
("SubtractionDipole represents a dipole subtraction "
"term in the formalism of Catani and Seymour.");
}
// *** Attention *** The following static variable is needed for the type
// description system in ThePEG. Please check that the template arguments
// are correct (the class and its base class), and that the constructor
// arguments are correct (the class name and the name of the dynamically
// loadable library where the class implementation can be found).
DescribeAbstractClass<SubtractionDipole,MEBase>
describeSubtractionDipole("Herwig::SubtractionDipole", "Herwig.so");
diff --git a/MatrixElement/Matchbox/External/OpenLoops/OpenLoopsAmplitude.cc b/MatrixElement/Matchbox/External/OpenLoops/OpenLoopsAmplitude.cc
--- a/MatrixElement/Matchbox/External/OpenLoops/OpenLoopsAmplitude.cc
+++ b/MatrixElement/Matchbox/External/OpenLoops/OpenLoopsAmplitude.cc
@@ -1,488 +1,510 @@
// -*- C++ -*-
//
// OpenLoopsAmplitude.cc is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
//
// This is the implementation of the non-inlined, non-templated member
// functions of the OpenLoopsAmplitude class.
//
#include "OpenLoopsAmplitude.h"
#include "ThePEG/Interface/ClassDocumentation.h"
#include "ThePEG/EventRecord/Particle.h"
#include "ThePEG/Repository/UseRandom.h"
#include "ThePEG/Repository/EventGenerator.h"
#include "ThePEG/Utilities/DescribeClass.h"
#include "ThePEG/Interface/Reference.h"
#include "ThePEG/Interface/RefVector.h"
#include "ThePEG/Interface/Parameter.h"
#include "ThePEG/Interface/Switch.h"
#include "ThePEG/Persistency/PersistentOStream.h"
#include "ThePEG/Persistency/PersistentIStream.h"
#include "ThePEG/Utilities/DynamicLoader.h"
#include "Herwig/MatrixElement/Matchbox/MatchboxFactory.h"
#include <fstream>
#include <sstream>
#include <string>
#include <cstdlib>
using namespace Herwig;
#ifndef OPENLOOPSLIBS
#error Makefile.am needs to define OPENLOOPSLIBS
#endif
#ifndef OPENLOOPSPREFIX
#error Makefile.am needs to define OPENLOOPSPREFIX
#endif
OpenLoopsAmplitude::OpenLoopsAmplitude() :
theHiggsEff(false), use_cms(true), psp_tolerance(12){
}
OpenLoopsAmplitude::~OpenLoopsAmplitude() {
}
IBPtr OpenLoopsAmplitude::clone() const {
return new_ptr(*this);
}
IBPtr OpenLoopsAmplitude::fullclone() const {
return new_ptr(*this);
}
extern "C" void OLP_Start(const char*, int* i);
extern "C" void OLP_SetParameter(const char* ,double* ,double*,int*);
extern "C" void ol_setparameter_string(const char*, const char*);
extern "C" void OLP_PrintParameter(const char*);
extern "C" void OLP_EvalSubProcess(int*, double*, double*, double*, double*);
extern "C" void OLP_EvalSubProcess2(int*, double*, double*, double*, double*);
// id ps-point emitter polvec res
extern "C" void ol_evaluate_sc(int, double*, int, double*, double*);
extern "C" void OLP_Polvec(double*,double*,double*);
void OpenLoopsAmplitude::doinitrun() {
MatchboxOLPME::doinitrun();
}
vector<int> OpenLoopsAmplitude::idpair=vector<int>();
void OpenLoopsAmplitude::startOLP(const string& contract, int& status) {
string tempcontract=contract;
if ( ! (DynamicLoader::load(OpenLoopsLibs_+"/libopenloops.so") ||
DynamicLoader::load(OpenLoopsPrefix_+"/lib/libopenloops.so") ||
DynamicLoader::load("libopenloops.so") ||
DynamicLoader::load(OpenLoopsLibs_+"/libopenloops.dylib") ||
DynamicLoader::load("libopenloops.dylib")||
DynamicLoader::load(OpenLoopsPrefix_+"/lib/libopenloops.dylib") ) ) {
throw Exception() << "OpenLoopsAmplitude::startOLP(): Failed to load libopenloops.so/dylib\n"
<< DynamicLoader::lastErrorMessage
<< Exception::runerror;
}
string stabilityPrefix = factory()->runStorage() + "OpenLoops.StabilityLog";
assert(stabilityPrefix.size() < 256);
ol_setparameter_string("stability_logdir",stabilityPrefix.c_str());
ol_setparameter_string("install_path",OpenLoopsPrefix_.c_str());
int a=0;double null=0.0;double one=1.0;
int part[10]={1,2,3,4,5,6,15,23,24,25};string stri;
for (int i=0;i<10;i++){
map<long,Energy>::const_iterator it=reshuffleMasses().find(part[i]);
double mass;
if(it==reshuffleMasses().end())
mass = getParticleData(part[i])->hardProcessMass()/GeV;
else
mass = it->second/GeV;
double width=getParticleData(part[i])->hardProcessWidth()/GeV;
std::stringstream ss;
ss << part[i];
string str = ss.str();
stri="mass("+str+")";
OLP_SetParameter(stri.c_str(),&mass,&null,&a);
stri="width("+str+")";
OLP_SetParameter(stri.c_str(),&width,&null,&a);
}
stri="alphas";
one=SM().alphaS();
OLP_SetParameter( stri.c_str(),&one ,&null,&a);
stri="alpha";
one=SM().alphaEMMZ();
OLP_SetParameter(stri.c_str(),&one ,&null,&a);
OLP_Start(tempcontract.c_str(), &status);
didStartOLP() = true;
}
void OpenLoopsAmplitude::fillOrderFile(const map<pair<Process, int>, int>& procs) {
string orderFileName =
optionalContractFile().empty() ?
factory()->buildStorage() + name() + ".OLPContract.lh" :
optionalContractFile();
ofstream orderFile(orderFileName.c_str());
size_t asPower = 100;
size_t minlegs = 100;
size_t maxlegs = 0;
for ( map<pair<Process, int>, int>::const_iterator t = procs.begin() ; t != procs.end() ; ++t ) {
asPower = min(asPower, static_cast<size_t>(t->first.first.orderInAlphaS));
minlegs = min(minlegs, static_cast<size_t>(t->first.first.legs.size()));
maxlegs = max(maxlegs, static_cast<size_t>(t->first.first.legs.size()));
}
orderFile << "# OLP order file created by Herwig/Matchbox for OpenLoops\n\n";
orderFile << "CorrectionType QCD\n";
orderFile << "IRregularization " << (isDR() ? "DRED" : "CDR") << "\n";
orderFile << "extra answerfile " << (factory()->buildStorage() + name() + ".OLPAnswer.lh") << "\n";
orderFile << "extra psp_tolerance "<<psp_tolerance<<"\n";
orderFile << "extra use_cms "<<(use_cms?"1":"0")<< "\n";
- if (theHiggsEff)
+ if (theCollierLib) {
+ orderFile << "extra preset 2 "<<"\n";
+ if(theHiggsEff){
+ orderFile << "extra stability_mode 14\n";
+ orderFile << "extra redlib1 1\n";
+ }
+ }
+ if (theHiggsEff){
orderFile << "model heft\n";
+ }
orderFile << "\n";
- if (extraOpenLoopsPath!="")
- orderFile << "Extra OpenLoopsPath " << extraOpenLoopsPath << "\n";
for ( map<pair<Process, int>, int>::const_iterator p = procs.begin() ; p != procs.end() ; ++p ) {
std::stringstream Processstr;
std::stringstream Typestr;
Processstr << (*p).first.first.legs[0]->id() << " " << (*p).first.first.legs[1]->id() << " -> ";
for ( PDVector::const_iterator o = (*p).first.first.legs.begin() + 2 ; o != (*p).first.first.legs.end() ; ++o )
Processstr << (**o).id() << " ";
if ( (*p).first.second == ProcessType::treeME2 ) {
Typestr << "Tree";
} else if ( (*p).first.second == ProcessType::colourCorrelatedME2 ) {
Typestr << "ccTree";
} else if ( (*p).first.second == ProcessType::spinColourCorrelatedME2 ) {
Typestr << "sctree_polvect";
} else if ( (*p).first.second == ProcessType::oneLoopInterference ) {
Typestr << "Loop";
}
OpenLoopsProcInfo pro = OpenLoopsProcInfo((*p).second, -1, Processstr.str(), Typestr.str());
pro.setOAs(p->first.first.orderInAlphaS);
processmap[(*p).second] = pro;
}
vector < string > types;
types.push_back("Tree");
types.push_back("ccTree");
types.push_back("sctree_polvect");
types.push_back("Loop");
for ( size_t i = asPower ; i != asPower + maxlegs - minlegs + 1 ; i++ ) {
orderFile << "\n\nCouplingPower QCD " << i;
orderFile << "\n\n#AlphasPower " << i;
for ( vector<string>::iterator it = types.begin() ; it != types.end() ; it++ ) {
for ( map<int, OpenLoopsProcInfo>::iterator p = processmap.begin() ; p != processmap.end() ; ++p )
if ( (*p).second.Tstr() == *it && i == (unsigned int) (*p).second.orderAs() ) {
orderFile << "\nAmplitudeType " << *it << "\n";
break;
}
for ( map<int, OpenLoopsProcInfo>::iterator p = processmap.begin() ; p != processmap.end() ; ++p )
if ( (*p).second.Tstr() == *it && i == (unsigned int) (*p).second.orderAs() ) {
orderFile << (*p).second.Pstr() << "\n";
}
}
}
orderFile << flush;
}
bool OpenLoopsAmplitude::checkOLPContract() {
string contractFileName = factory()->buildStorage() + name() + ".OLPAnswer.lh";
ifstream infile(contractFileName.c_str());
string line;
vector < string > contractfile;
while (std::getline(infile, line)) {
contractfile.push_back(line);
}
for ( map<int, OpenLoopsProcInfo>::iterator p = processmap.begin() ; p != processmap.end() ; p++ ) {
bool righttype = false;
for ( vector<string>::iterator linex = contractfile.begin() ; linex != contractfile.end() ; ++linex ) {
if ( (*linex).find("AmplitudeType ")!= std::string::npos ) {
if ( (*linex).find(" " + (*p).second.Tstr() + " ")!= std::string::npos ) {
righttype = true;
} else {
righttype = false;
}
}
if ( righttype ) {
if ( (*linex).find((*p).second.Pstr()) != std::string::npos ){
if( (*p).second.Pstr().length() == (*linex).find("|") ) {
string sub = (*linex).substr((*linex).find("|") + 1, (*linex).find("#") - (*linex).find("|") - 1); // | 1 23 # buggy??
int subint;
int subint2;
istringstream(sub) >> subint >> subint2;
assert(subint==1);
(*p).second.setGID(subint2);
}
}
}
}
}
idpair.clear();
for (size_t i=0;i<processmap.size();i++)idpair.push_back(-1);
idpair.push_back(-1);
for ( map<int, OpenLoopsProcInfo>::iterator p = processmap.begin() ; p != processmap.end() ; p++ ) {
idpair[(*p).second.HID()]=(*p).second.GID();
if ( (*p).second.GID() == -1 ) return 0;
}
return 1;
}
bool OpenLoopsAmplitude::startOLP(const map<pair<Process, int>, int>& procs) {
string contractFileName = factory()->buildStorage() + name() + ".OLPAnswer.lh";
string orderFileName =
optionalContractFile().empty() ?
factory()->buildStorage() + name() + ".OLPContract.lh" :
optionalContractFile();
fillOrderFile(procs);
int status = -1;
startOLP(orderFileName, status);
if ( !checkOLPContract() ) {
return false;
}
if ( status != 1 ) return false;
return true;
}
void OpenLoopsAmplitude::evalSubProcess() const {
useMe();
double units = pow(lastSHat() / GeV2, mePartonData().size() - 4.);
fillOLPMomenta(lastXComb().meMomenta(),mePartonData(),reshuffleMasses());
double acc ;
double scale = sqrt(mu2() / GeV2);
if (hasRunningAlphaS()) {
int a=0;double null=0.0;double one=1.0;
string stri="alphas";
one=lastAlphaS();
OLP_SetParameter( stri.c_str(),&one ,&null,&a);
}
double out[7]={};
int id = olpId()[ProcessType::oneLoopInterference] ? olpId()[ProcessType::oneLoopInterference] : olpId()[ProcessType::treeME2];
assert ( idpair.size() != 0 );
OLP_EvalSubProcess2(&idpair[id], olpMomenta(), &scale, out,&acc );
if ( olpId()[ProcessType::oneLoopInterference] ) {
if(calculateTreeME2())lastTreeME2(out[3] * units);
lastOneLoopInterference((out[2])* units);
lastOneLoopPoles(pair<double, double>(out[0] * units, out[1] * units));
} else if ( olpId()[ProcessType::treeME2] ) {
lastTreeME2(out[0] * units);
}
}
void OpenLoopsAmplitude::evalColourCorrelator(pair<int, int> ) const {
double units = pow(lastSHat() / GeV2, mePartonData().size() - 4.);
fillOLPMomenta(lastXComb().meMomenta(),mePartonData(),reshuffleMasses());
double acc ;
double scale = sqrt(mu2() / GeV2);
if (hasRunningAlphaS()) {
int a=0;double null=0.0;double one=1.0;
string stri="alphas";
one=lastAlphaS();
OLP_SetParameter( stri.c_str(),&one ,&null,&a);
}
int n = lastXComb().meMomenta().size();
colourCorrelatorResults.resize(n * (n - 1) / 2);
assert ( idpair.size() != 0 );
int id = olpId()[ProcessType::colourCorrelatedME2];
OLP_EvalSubProcess2(&idpair[id], olpMomenta(), &scale, &colourCorrelatorResults[0],&acc );
for ( int i = 0 ; i < n ; ++i ){
for ( int j = i + 1 ; j < n ; ++j ) {
lastColourCorrelator(make_pair(i, j), colourCorrelatorResults[i+j*(j-1)/2] * units);
}
}
}
void OpenLoopsAmplitude::evalSpinColourCorrelator(pair<int , int > ) const {
assert(false);
}
double OpenLoopsAmplitude::spinColourCorrelatedME2(pair<int,int> ij,
const SpinCorrelationTensor& c) const{
double units = pow(lastSHat() / GeV2, mePartonData().size() - 4.);
fillOLPMomenta(lastXComb().meMomenta(),mePartonData(),reshuffleMasses());
if (hasRunningAlphaS()) {
int a=0;double null=0.0;double one=1.0;
string stri="alphas";
one=lastAlphaS();
OLP_SetParameter( stri.c_str(),&one ,&null,&a);
}
int emitter=ij.first+1;
int n = lastXComb().meMomenta().size();
assert ( idpair.size() != 0 ) ;
int id =idpair[olpId()[ProcessType::spinColourCorrelatedME2]];
//double * outx =new double[n];
spinColourCorrelatorResults.resize(n);
double polvec[4];
polvec[0]=c.momentum().e()/GeV;
polvec[1]=c.momentum().x()/GeV;
polvec[2]=c.momentum().y()/GeV;
polvec[3]=c.momentum().z()/GeV;
double avg= colourCorrelatedME2(ij)*(-c.diagonal());
ol_evaluate_sc(id, olpMomenta(),emitter,polvec,&spinColourCorrelatorResults[0]);
double corr =-1.*units * spinColourCorrelatorResults[ij.second]/c.scale()*c.momentum().dot(c.momentum());
double Nc = generator()->standardModel()->Nc();
double cfac = 1.;
if ( mePartonData()[ij.first]->iColour() == PDT::Colour8 ) {
cfac = Nc;
} else if ( mePartonData()[ij.first]->iColour() == PDT::Colour3 ||
mePartonData()[ij.first]->iColour() == PDT::Colour3bar ) {
cfac = (sqr(Nc)-1.)/(2.*Nc);
} else assert(false);
return
avg + corr/cfac;
}
string OpenLoopsAmplitude::OpenLoopsLibs_=OPENLOOPSLIBS;
string OpenLoopsAmplitude::OpenLoopsPrefix_=OPENLOOPSPREFIX;
void OpenLoopsAmplitude::setOpenLoopsLibs(string p){
OpenLoopsLibs_=p;
}
string OpenLoopsAmplitude::getOpenLoopsLibs() const{
return OpenLoopsLibs_;
}
void OpenLoopsAmplitude::setOpenLoopsPrefix(string p){
OpenLoopsPrefix_=p;
}
string OpenLoopsAmplitude::getOpenLoopsPrefix() const{
return OpenLoopsPrefix_;
}
// If needed, insert default implementations of virtual function defined
// in the InterfacedBase class here (using ThePEG-interfaced-impl in Emacs).
void OpenLoopsAmplitude::persistentOutput(PersistentOStream & os) const {
- os << idpair << OpenLoopsLibs_ << OpenLoopsPrefix_;
+ os << idpair << theHiggsEff << use_cms << theCollierLib << OpenLoopsLibs_ << OpenLoopsPrefix_;
}
void OpenLoopsAmplitude::persistentInput(PersistentIStream & is, int) {
- is >> idpair >> OpenLoopsLibs_ >> OpenLoopsPrefix_;
+ is >> idpair >> theHiggsEff >> use_cms >> theCollierLib >> OpenLoopsLibs_ >> OpenLoopsPrefix_;
}
// *** Attention *** The following static variable is needed for the type
// description system in ThePEG. Please check that the template arguments
// are correct (the class and its base class), and that the constructor
// arguments are correct (the class name and the name of the dynamically
// loadable library where the class implementation can be found).
DescribeClass<OpenLoopsAmplitude, MatchboxOLPME> describeHerwigOpenLoopsAmplitude("Herwig::OpenLoopsAmplitude", "HwMatchboxOpenLoops.so");
void OpenLoopsAmplitude::Init() {
static ClassDocumentation<OpenLoopsAmplitude>
documentation("OpenLoopsAmplitude implements an interface to OpenLoops.",
"Matrix elements have been calculated using OpenLoops \\cite{Cascioli:2011va}",
"%\\cite{Cascioli:2011va}\n"
"\\bibitem{Cascioli:2011va}\n"
"F.~Cascioli et al.,\n"
"``Scattering Amplitudes with Open Loops,''\n"
"arXiv:1111.5206 [hep-ph].\n"
"%%CITATION = ARXIV:1111.5206;%%");
static Switch<OpenLoopsAmplitude,bool> interfaceHiggsEff
("HiggsEff",
"Switch On/Off for effective higgs model.",
&OpenLoopsAmplitude::theHiggsEff, false, false, false);
static SwitchOption interfaceHiggsEffOn
(interfaceHiggsEff,
"On",
"On",
true);
static SwitchOption interfaceHiggsEffOff
(interfaceHiggsEff,
"Off",
"Off",
false);
static Switch<OpenLoopsAmplitude,bool> interfaceUseComplMass
("ComplexMassScheme",
"Switch on or off if Complex Masses.",
&OpenLoopsAmplitude::use_cms, true, false, false);
static SwitchOption interfaceUseComplMassOn
(interfaceUseComplMass,
"True",
"True for Complex Masses.",
true);
static SwitchOption interfaceUseComplMassOff
(interfaceUseComplMass,
"False",
"False for no Complex Masses.",
false);
-
+
+ static Switch<OpenLoopsAmplitude,bool> interfaceCollier
+ ("UseCollier",
+ "Switch On/Off for using the Collier Lib (arXiv:1604.06792).",
+ &OpenLoopsAmplitude::theCollierLib, true, false, false);
+ static SwitchOption interfaceCollierOn
+ (interfaceCollier,
+ "On",
+ "On",
+ true);
+ static SwitchOption interfaceCollierOff
+ (interfaceCollier,
+ "Off",
+ "Off",
+ false);
+
+
static Parameter<OpenLoopsAmplitude,int> interfacepsp_tolerance
("PSP_tolerance",
"(Debug)Phase Space Tolerance. Better use e.g.: set OpenLoops:Massless 13",
&OpenLoopsAmplitude::psp_tolerance, 12, 0, 0,
false, false, Interface::lowerlim);
static Parameter<OpenLoopsAmplitude,string> interfaceOpenLoopsLibs
("OpenLoopsLibs",
"The location of OpenLoops libraries",
0, string(OPENLOOPSLIBS),
false, false,
&OpenLoopsAmplitude::setOpenLoopsLibs,
&OpenLoopsAmplitude::getOpenLoopsLibs);
static Parameter<OpenLoopsAmplitude,string> interfaceOpenLoopsPrefix
("OpenLoopsPrefix",
"The location of OpenLoops libraries",
0, string(OPENLOOPSPREFIX),
false, false,
&OpenLoopsAmplitude::setOpenLoopsPrefix,
&OpenLoopsAmplitude::getOpenLoopsPrefix);
}
diff --git a/MatrixElement/Matchbox/External/OpenLoops/OpenLoopsAmplitude.h b/MatrixElement/Matchbox/External/OpenLoops/OpenLoopsAmplitude.h
--- a/MatrixElement/Matchbox/External/OpenLoops/OpenLoopsAmplitude.h
+++ b/MatrixElement/Matchbox/External/OpenLoops/OpenLoopsAmplitude.h
@@ -1,351 +1,350 @@
// -*- C++ -*-
//
// OpenLoopsAmplitude.h is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
#ifndef Herwig_OpenLoopsAmplitude_H
#define Herwig_OpenLoopsAmplitude_H
//
// This is the declaration of the OpenLoopsAmplitude class.
//
#include "Herwig/MatrixElement/Matchbox/Base/MatchboxOLPME.h"
namespace Herwig {
using namespace ThePEG;
/**
* \ingroup Matchbox
* \author Johannes Bellm, Simon Platzer
*
* \brief Process information for OpenLoops
*/
class OpenLoopsProcInfo{
public:
/**
* Default constructor
*/
OpenLoopsProcInfo() {}
/**
* Construct giving data
*/
OpenLoopsProcInfo(int HID,int GID, string procstr,string typestr)
: theHOlpId(HID), theGOlpId(GID), theProcstr(procstr), theTypestr(typestr) {}
/**
* Document me
*/
int HID() const { return theHOlpId; }
/**
* Document me
*/
int GID() const { return theGOlpId; }
/**
* Document me
*/
const string& Pstr() const { return theProcstr; }
/**
* Document me
*/
const string& Tstr() const { return theTypestr; }
/**
* Document me
*/
void setGID(int g) { theGOlpId=g; }
/**
* Document me
*/
void setOAs(int i) { orderAlphas=i; }
/**
* Document me
*/
int orderAs() { return orderAlphas; }
private:
/**
* Document me
*/
int theHOlpId;
/**
* Document me
*/
int theGOlpId;
/**
* Document me
*/
string theProcstr;
/**
* Document me
*/
string theTypestr;
/**
* Document me
*/
int orderAlphas;
public:
/**
* Write to persistent stream
*/
void persistentOutput(PersistentOStream & os) const{
os << theHOlpId << theGOlpId << theProcstr << theTypestr << orderAlphas;
}
/**
* Read from persistent stream
*/
void persistentInput(PersistentIStream &is) {
is >> theHOlpId >> theGOlpId >> theProcstr >> theTypestr >> orderAlphas;
}
};
/**
* \ingroup Matchbox
* \author Johannes Bellm, Simon Platzer
*
* \brief OpenLoopsAmplitude implements an interface to OpenLoops
*/
class OpenLoopsAmplitude: public MatchboxOLPME {
public:
/** @name Standard constructors and destructors. */
//@{
/**
* The default constructor.
*/
OpenLoopsAmplitude();
/**
* The destructor.
*/
virtual ~OpenLoopsAmplitude();
//@}
public:
virtual void fillOrderFile(const map<pair<Process,int>,int>& procs);
virtual bool isCS() const { return false; }
virtual bool isExpanded() const { return true; }
virtual bool isBDK() const { return false; }
//virtual bool isDR() const { return true; }
/**
* Start the one loop provider, if appropriate, giving order and
* contract files
*/
virtual bool checkOLPContract();
/**
* Start the one loop provider, if appropriate
*/
virtual void startOLP(const string&, int& status);
/**
* Return the value of the dimensional regularization
* parameter. Note that renormalization scale dependence is fully
* restored in DipoleIOperator.
*/
// virtual Energy2 mu2() const { return lastSHat(); }
/**
* Start the one loop provider, if appropriate. This default
* implementation writes an BLHA 2.0 order file and starts the OLP
*/
virtual bool startOLP(const map<pair<Process,int>,int>& procs);
/**
* Return true, if this amplitude already includes averaging over
* incoming parton's quantum numbers.
*/
virtual bool hasInitialAverage() const { return true; }
/**
* Return true, if this amplitude already includes symmetry factors
* for identical outgoing particles.
*/
virtual bool hasFinalStateSymmetry() const { return true; }
/**
* Call OLP_EvalSubProcess and fill in the results
*/
void evalSubProcess() const;
/**
* Fill in results for the given colour correlator
*/
virtual void evalColourCorrelator(pair<int,int> ij) const;
/**
* Fill in results for the given colour/spin correlator
*/
virtual void evalSpinColourCorrelator(pair<int,int> ij) const;
/**
* Return the colour and spin correlated matrix element.
*/
virtual double spinColourCorrelatedME2(pair<int,int> ij,
const SpinCorrelationTensor& c) const;
public:
/** @name Functions used by the persistent I/O system. */
//@{
/**
* Function used to write out object persistently.
* @param os the persistent output stream written to.
*/
void persistentOutput(PersistentOStream & os) const;
/**
* Function used to read in object persistently.
* @param is the persistent input stream read from.
* @param version the version number of the object when written.
*/
void persistentInput(PersistentIStream & is, int version);
//@}
/**
* The standard Init function used to initialize the interfaces.
* Called exactly once for each class by the class description system
* before the main function starts or
* when this class is dynamically loaded.
*/
static void Init();
protected:
/** @name Clone Methods. */
//@{
/**
* Make a simple clone of this object.
* @return a pointer to the new object.
*/
virtual IBPtr clone() const;
/** Make a clone of this object, possibly modifying the cloned object
* to make it sane.
* @return a pointer to the new object.
*/
virtual IBPtr fullclone() const;
//@}
virtual void doinitrun();
// If needed, insert declarations of virtual function defined in the
// InterfacedBase class here (using ThePEG-interfaced-decl in Emacs).
private:
/**
* The assignment operator is private and must never be called.
* In fact, it should not even be implemented.
*/
OpenLoopsAmplitude & operator=(const OpenLoopsAmplitude &);
/**
* Store colour correlator results
*/
mutable vector<double> colourCorrelatorResults;
/**
* Store spin colour correlator results
*/
mutable vector<double> spinColourCorrelatorResults;
/**
* first is the olp id from herwig, second the answer from openloops
*/
static vector< int > idpair;
/**
* Helper map to store information in different procs.
*/
map<int , OpenLoopsProcInfo > processmap;
/**
- * Extra argument of BLHA2 to tell the Amplitude which OpenLoops installation to use.
- */
-
- mutable string extraOpenLoopsPath;
-
- /**
* Interface for Higgs Effective
*/
bool theHiggsEff;
/**
* Complex Mass Scheme.
*/
bool use_cms;
-
+
+ /**
+ * Use of Collier Lib (arXiv:1604.06792), available since OpenLoops 1.3.0.
+ */
+ bool theCollierLib=true;
+
/**
* parameter to set Phase space tolerance for massiv particles.
* Should not be used. Better: set Openloops:Massless 11
*/
int psp_tolerance;
/**
* Location of the OpenLoops libraries
*/
static string OpenLoopsLibs_;
/**
* Location of the OpenLoops
*/
static string OpenLoopsPrefix_;
/**
* Helper functions to make long strings static
*/
void setOpenLoopsLibs(string p);
string getOpenLoopsLibs() const;
void setOpenLoopsPrefix(string p);
string getOpenLoopsPrefix() const;
};
}
#endif /* Herwig_OpenLoopsAmplitude_H */
diff --git a/MatrixElement/Matchbox/External/VBFNLO/VBFNLOPhasespace.cc b/MatrixElement/Matchbox/External/VBFNLO/VBFNLOPhasespace.cc
--- a/MatrixElement/Matchbox/External/VBFNLO/VBFNLOPhasespace.cc
+++ b/MatrixElement/Matchbox/External/VBFNLO/VBFNLOPhasespace.cc
@@ -1,277 +1,275 @@
// -*- C++ -*-
//
// VBFNLOPhasespace.cc is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
//
// This is the implementation of the non-inlined, non-templated member
// functions of the VBFNLOPhasespace class.
//
#include "VBFNLOPhasespace.h"
#include "ThePEG/Interface/ClassDocumentation.h"
#include "ThePEG/Interface/Parameter.h"
#include "ThePEG/Interface/Reference.h"
#include "ThePEG/Interface/Switch.h"
#include "ThePEG/EventRecord/Particle.h"
#include "ThePEG/Repository/UseRandom.h"
#include "ThePEG/Repository/EventGenerator.h"
#include "ThePEG/Utilities/DescribeClass.h"
#include "Herwig/Utilities/GSLBisection.h"
#include "ThePEG/Utilities/DynamicLoader.h"
#include "ThePEG/Persistency/PersistentOStream.h"
#include "ThePEG/Persistency/PersistentIStream.h"
#include "Herwig/MatrixElement/Matchbox/Base/MatchboxAmplitude.h"
#include "VBFNLO/utilities/BLHAinterface.h"
#define DEFSTR(s) CPPSTR(s)
#define CPPSTR(s) #s
using namespace Herwig;
VBFNLOPhasespace::VBFNLOPhasespace() :
lastSqrtS(0*GeV), needToReshuffle(false), VBFNLOlib_(DEFSTR(VBFNLOLIB))
{}
void VBFNLOPhasespace::loadVBFNLO() {
if ( ! DynamicLoader::load(VBFNLOlib_+"/libVBFNLO.so") ) {
string error1 = DynamicLoader::lastErrorMessage;
if ( ! DynamicLoader::load(VBFNLOlib_+"/libVBFNLO.dylib") ) {
string error2 = DynamicLoader::lastErrorMessage;
if ( ! DynamicLoader::load("libVBFNLO.so") ) {
string error3 = DynamicLoader::lastErrorMessage;
if ( ! DynamicLoader::load("libVBFNLO.dylib") ) {
string error4 = DynamicLoader::lastErrorMessage;
throw Exception() << "VBFNLOPhasespace: failed to load libVBFNLO.so/dylib\n"
<< "Error messages are:\n\n"
<< "* " << VBFNLOlib_ << "/libVBFNLO.so:\n"
<< error1 << "\n"
<< "* " << VBFNLOlib_ << "/libVBFNLO.dylib:\n"
<< error2 << "\n"
<< "* libVBFNLO.so:\n"
<< error3 << "\n"
<< "* libVBFNLO.dylib:\n"
<< error4 << "\n"
<< Exception::runerror;
}
}
}
}
}
VBFNLOPhasespace::~VBFNLOPhasespace() {}
IBPtr VBFNLOPhasespace::clone() const {
return new_ptr(*this);
}
IBPtr VBFNLOPhasespace::fullclone() const {
return new_ptr(*this);
}
void VBFNLOPhasespace::setXComb(tStdXCombPtr xco) {
MatchboxPhasespace::setXComb(xco);
// test for resuffling
needToReshuffle = false;
if ( xco ) {
for ( cPDVector::const_iterator d = mePartonData().begin();
d != mePartonData().end(); ++d ) {
// Higgs is massive -> does not need reshuffling
if ( ( (**d).id() != ParticleID::h0 ) && ( (**d).hardProcessMass() != ZERO ) ) {
needToReshuffle = true;
break;
}
}
}
// set CMS energy
int pStatus = 0;
double zero = 0.0;
double value = sqrt(lastXCombPtr()->lastS())/GeV;
if (value && (value != lastSqrtS/GeV)) {
lastSqrtS = value*GeV;
string name = "sqrtS";
OLP_SetParameter(const_cast<char*>(name.c_str()),&value,&zero,&pStatus);
if ( !pStatus )
throw Exception() << "VBFNLOPhasespace::setXComb(): VBFNLO failed to set parameter '"
<< name << "' to " << value << "\n"
<< Exception::runerror;
}
}
double VBFNLOPhasespace::generateTwoToNKinematics(const double* random,
vector<Lorentz5Momentum>& momenta) {
double weight;
int id =
olpId()[ProcessType::oneLoopInterference] ?
olpId()[ProcessType::oneLoopInterference] :
olpId()[ProcessType::treeME2];
double* p = new double[4*momenta.size()];
OLP_PhaseSpacePoint(&id, const_cast<double*>(random), const_cast<double*>(random+1), p, &weight);
if (weight < 0) {
throw Exception() << "VBFNLOPhasespace::generateTwoToNKinematics(): Negative weight in VBFNLOPhaseSpace\n"
<< Exception::runerror;
}
if (weight == 0) {
delete[] p;
return 0;
}
for ( size_t i = 0; i < momenta.size(); ++i ) {
momenta[i].setT(p[4*i] *GeV);
momenta[i].setX(p[4*i+1]*GeV);
momenta[i].setY(p[4*i+2]*GeV);
momenta[i].setZ(p[4*i+3]*GeV);
momenta[i].rescaleMass();
}
delete[] p;
Energy beamenergy = sqrt(lastXCombPtr()->lastS())/2.;
double x1 = momenta[0].e()/beamenergy;
double x2 = momenta[1].e()/beamenergy;
Energy2 thisSHat = (momenta[0] + momenta[1]).m2();
// reshuffle so that particles have correct mass
if ( needToReshuffle ) {
// boost final-state into partonic CMS
Boost toCMS = (momenta[0]+momenta[1]).findBoostToCM();
for ( size_t i = 2; i < momenta.size(); ++i ) {
momenta[i].boost(toCMS);
}
// copied from MatchboxRambo phasespace
double xi;
ReshuffleEquation solve(sqrt(thisSHat),mePartonData().begin()+2,mePartonData().end(),
momenta.begin()+2,momenta.end());
GSLBisection solver(1e-10,1e-8,10000);
try {
xi = solver.value(solve,0.0,1.1);
} catch (GSLBisection::GSLerror) {
return 0.;
} catch (GSLBisection::IntervalError) {
return 0.;
}
weight *= pow(xi,3.*(momenta.size()-3.));
Energy num = ZERO;
Energy den = ZERO;
cPDVector::const_iterator d = mePartonData().begin()+2;
for ( vector<Lorentz5Momentum>::iterator k = momenta.begin()+2;
k != momenta.end(); ++k, ++d ) {
num += (*k).vect().mag2()/(*k).t();
Energy q = (*k).t();
(*k).setT(sqrt(sqr((**d).hardProcessMass())+xi*xi*sqr((*k).t())));
(*k).setVect(xi*(*k).vect());
weight *= q/(*k).t();
den += (*k).vect().mag2()/(*k).t();
(*k).setMass((**d).hardProcessMass());
}
// unboost
for ( size_t i = 2; i < momenta.size(); ++i ) {
momenta[i].boost(-toCMS);
}
}
if ( !matchConstraints(momenta) )
return 0.;
lastXCombPtr()->lastX1X2(make_pair(x1,x2));
lastXCombPtr()->lastSHat(thisSHat);
weight /= pow(thisSHat/GeV2,momenta.size()-4);
weight /= x1*x2;
- fillDiagramWeights();
-
return weight;
}
int VBFNLOPhasespace::nDimPhasespace(int nFinal) const {
return 3*nFinal;
//get this from within VBFNLO
int pStatus = 0;
double value, zero;
string name = "PSdimension";
OLP_GetParameter(const_cast<char*>(name.c_str()),&value,&zero,&pStatus);
if ( pStatus != 1) {
throw Exception() << "VBFNLOPhasespace::nDimPhasespace(): Cannot get phasespace dimension in VBFNLOPhaseSpace\n"
<< "error code: " << pStatus << "\n"
<< Exception::runerror;
}
// one additional number (first) needed for channel selection
// one additional number (last) needed for global phi integration
return value+2;
}
Energy VBFNLOPhasespace::ReshuffleEquation::operator() (double xi) const {
cPDVector::const_iterator d = dataBegin;
vector<Lorentz5Momentum>::const_iterator p = momentaBegin;
Energy res = -w;
for ( ; d != dataEnd; ++d, ++p ) {
res += sqrt(sqr((**d).hardProcessMass()) +
xi*xi*sqr(p->t()));
}
return res;
}
void VBFNLOPhasespace::doinit() {
loadVBFNLO();
MatchboxPhasespace::doinit();
}
void VBFNLOPhasespace::doinitrun() {
loadVBFNLO();
MatchboxPhasespace::doinitrun();
}
void VBFNLOPhasespace::persistentOutput(PersistentOStream & os) const {
os << needToReshuffle << theLastXComb;
}
void VBFNLOPhasespace::persistentInput(PersistentIStream & is, int) {
is >> needToReshuffle >> theLastXComb;
}
// *** Attention *** The following static variable is needed for the type
// description system in ThePEG. Please check that the template arguments
// are correct (the class and its base class), and that the constructor
// arguments are correct (the class name and the name of the dynamically
// loadable library where the class implementation can be found).
DescribeClass<VBFNLOPhasespace,MatchboxPhasespace>
describeHerwigVBFNLOPhasespace("Herwig::VBFNLOPhasespace", "HwMatchboxVBFNLO.so");
void VBFNLOPhasespace::Init() {
static ClassDocumentation<VBFNLOPhasespace> documentation
("VBFNLOPhasespace is an interface to the internal phasespace generator "
"of VBFNLO. It uses the information passed via the BLHA interface to "
"obtain information on the required channels.");
}
diff --git a/MatrixElement/Matchbox/MatchboxFactory.h b/MatrixElement/Matchbox/MatchboxFactory.h
--- a/MatrixElement/Matchbox/MatchboxFactory.h
+++ b/MatrixElement/Matchbox/MatchboxFactory.h
@@ -1,1288 +1,1288 @@
// -*- C++ -*-
//
// MatchboxFactory.h is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
#ifndef HERWIG_MatchboxFactory_H
#define HERWIG_MatchboxFactory_H
//
// This is the declaration of the MatchboxFactory class.
//
#include "ThePEG/Handlers/SubProcessHandler.h"
#include "Herwig/MatrixElement/Matchbox/Base/MatchboxAmplitude.h"
#include "Herwig/MatrixElement/Matchbox/Utility/Tree2toNGenerator.h"
#include "Herwig/MatrixElement/Matchbox/Utility/ProcessData.h"
#include "Herwig/MatrixElement/Matchbox/Utility/MatchboxScaleChoice.h"
#include "Herwig/MatrixElement/Matchbox/Phasespace/MatchboxPhasespace.h"
#include "Herwig/MatrixElement/Matchbox/Base/MatchboxMEBase.h"
#include "Herwig/MatrixElement/Matchbox/Base/SubtractedME.h"
#include "Herwig/MatrixElement/Matchbox/MatchboxFactory.fh"
namespace Herwig {
using namespace ThePEG;
/**
* \ingroup Matchbox
* \author Simon Platzer
*
* \brief MatchboxFactory automatically sets up a NLO
* QCD calculation carried out in dipole subtraction.
*
* @see \ref MatchboxFactoryInterfaces "The interfaces"
* defined for MatchboxFactory.
*/
class MatchboxFactory: public SubProcessHandler {
public:
/** @name Standard constructors and destructors. */
//@{
/**
* The default constructor.
*/
MatchboxFactory();
/**
* The destructor.
*/
virtual ~MatchboxFactory();
//@}
public:
/**
* Flag to indicate that at least one MatchboxFactory object is in action
*/
static bool isMatchboxRun() {
return theIsMatchboxRun();
}
/** @name Process and diagram information */
//@{
/**
* Return the diagram generator.
*/
Ptr<Tree2toNGenerator>::tptr diagramGenerator() const { return theDiagramGenerator; }
/**
* Set the diagram generator.
*/
void diagramGenerator(Ptr<Tree2toNGenerator>::ptr dg) { theDiagramGenerator = dg; }
/**
* Return the process data.
*/
Ptr<ProcessData>::tptr processData() const { return theProcessData; }
/**
* Set the process data.
*/
void processData(Ptr<ProcessData>::ptr pd) { theProcessData = pd; }
/**
* Return the number of light flavours, this matrix
* element is calculated for.
*/
unsigned int nLight() const { return theNLight; }
/**
* Set the number of light flavours, this matrix
* element is calculated for.
*/
void nLight(unsigned int n) { theNLight = n; }
/**
* Return the vector that contains the PDG ids of
* the light flavours, which are contained in the
* jet particle group.
*/
vector<long> nLightJetVec() const { return theNLightJetVec; }
/**
* Set the elements of the vector that contains the PDG
* ids of the light flavours, which are contained in the
* jet particle group.
*/
void nLightJetVec(long n) { theNLightJetVec.push_back(n); }
/**
* Return the vector that contains the PDG ids of
* the heavy flavours, which are contained in the
* jet particle group.
*/
vector<long> nHeavyJetVec() const { return theNHeavyJetVec; }
/**
* Set the elements of the vector that contains the PDG
* ids of the heavy flavours, which are contained in the
* jet particle group.
*/
void nHeavyJetVec(long n) { theNHeavyJetVec.push_back(n); }
/**
* Return the vector that contains the PDG ids of
* the light flavours, which are contained in the
* proton particle group.
*/
vector<long> nLightProtonVec() const { return theNLightProtonVec; }
/**
* Set the elements of the vector that contains the PDG
* ids of the light flavours, which are contained in the
* proton particle group.
*/
void nLightProtonVec(long n) { theNLightProtonVec.push_back(n); }
/**
* Return the order in \f$\alpha_S\f$.
*/
unsigned int orderInAlphaS() const { return theOrderInAlphaS; }
/**
* Set the order in \f$\alpha_S\f$.
*/
void orderInAlphaS(unsigned int o) { theOrderInAlphaS = o; }
/**
* Return the order in \f$\alpha_{EM}\f$.
*/
unsigned int orderInAlphaEW() const { return theOrderInAlphaEW; }
/**
* Set the order in \f$\alpha_{EM}\f$.
*/
void orderInAlphaEW(unsigned int o) { theOrderInAlphaEW = o; }
/**
* The multiplicity of legs with virtual contributions.
*/
size_t highestVirt() const {return theHighestVirtualSize;}
/**
* Set the highest
**/
void setHighestVirt(size_t n){theHighestVirtualSize=n;}
/**
* Access the processes vector.
*/
const vector<vector<string> > getProcesses() const {return processes;}
/**
* Return true, if all processes up to a maximum order are considered
*/
bool allProcesses() const { return theAllProcesses; }
/**
* Switch on/off inclusino off all processes up to a maximum order
*/
void setAllProcesses(bool on = true) { theAllProcesses = on; }
/**
* Return true, if Born contributions should be included.
*/
bool bornContributions() const { return theBornContributions; }
/**
* Switch on or off Born contributions
*/
void setBornContributions(bool on = true) { theBornContributions = on; }
/**
* Return true, if virtual contributions should be included.
*/
bool virtualContributions() const { return theVirtualContributions; }
/**
* Switch on or off virtual contributions
*/
void setVirtualContributions(bool on = true) { theVirtualContributions = on; }
/**
* Produce matrix element corrections, but no NLO
*/
bool meCorrectionsOnly() const { return theMECorrectionsOnly; }
/**
* Switch to produce matrix element corrections, but no NLO
*/
void setMECorrectionsOnly(bool on = true) { theMECorrectionsOnly = on; }
/**
* Produce matrix element corrections, with LoopSim NLO
*/
bool loopSimCorrections() const { return theLoopSimCorrections; }
/**
* Switch to produce matrix element corrections, with LoopSim NLO
*/
void setLoopSimCorrections(bool on = true) { theLoopSimCorrections = on; }
/**
* Return true, if subtracted real emission contributions should be included.
*/
bool realContributions() const { return theRealContributions; }
/**
* Switch on or off subtracted real emission contributions
*/
void setRealContributions(bool on = true) { theRealContributions = on; }
/**
* Return true, if virtual contributions should be treated as independent subprocesses
*/
bool independentVirtuals() const { return theIndependentVirtuals; }
/**
* Switch on/off virtual contributions should be treated as independent subprocesses
*/
void setIndependentVirtuals(bool on = true) { theIndependentVirtuals = on; }
/**
* Return true, if PK operator contributions should be treated as independent subprocesses
*/
bool independentPKs() const { return theIndependentPKs; }
/**
* Switch on/off PK operator contributions should be treated as independent subprocesses
*/
void setIndependentPKs(bool on = true) { theIndependentPKs = on; }
/**
* Return true, if SubProcessGroups should be
* setup from this MEGroup. If not, a single SubProcess
* is constructed from the data provided by the
* head matrix element.
*/
virtual bool subProcessGroups() const { return !showerApproximation(); }
/**
* Return true, if subtraction scales should be caluclated from real emission kinematics
*/
bool realEmissionScales() const { return theRealEmissionScales; }
/**
* Switch on/off that subtraction scales should be caluclated from real emission kinematics
*/
void setRealEmissionScales(bool on = true) { theRealEmissionScales = on; }
/**
* Set the shower approximation.
*/
void showerApproximation(Ptr<ShowerApproximation>::tptr app) { theShowerApproximation = app; }
/**
* Return the shower approximation.
*/
Ptr<ShowerApproximation>::tptr showerApproximation() const { return theShowerApproximation; }
//@}
/** @name Phasespace generation and scale choice */
//@{
/**
* Return the phase space generator to be used.
*/
Ptr<MatchboxPhasespace>::tptr phasespace() const { return thePhasespace; }
/**
* Set the phase space generator to be used.
*/
void phasespace(Ptr<MatchboxPhasespace>::ptr ps) { thePhasespace = ps; }
/**
* Set the scale choice object
*/
void scaleChoice(Ptr<MatchboxScaleChoice>::ptr sc) { theScaleChoice = sc; }
/**
* Return the scale choice object
*/
Ptr<MatchboxScaleChoice>::tptr scaleChoice() const { return theScaleChoice; }
/**
* Get the factorization scale factor
*/
double factorizationScaleFactor() const { return theFactorizationScaleFactor; }
/**
* Set the factorization scale factor
*/
void factorizationScaleFactor(double f) { theFactorizationScaleFactor = f; }
/**
* Get the renormalization scale factor
*/
double renormalizationScaleFactor() const { return theRenormalizationScaleFactor; }
/**
* Set the renormalization scale factor
*/
void renormalizationScaleFactor(double f) { theRenormalizationScaleFactor = f; }
/**
* Return true, if fixed couplings are used.
*/
bool fixedCouplings() const { return theFixedCouplings; }
/**
* Switch on fixed couplings.
*/
void setFixedCouplings(bool on = true) { theFixedCouplings = on; }
/**
* Return true, if fixed couplings are used.
*/
bool fixedQEDCouplings() const { return theFixedQEDCouplings; }
/**
* Switch on fixed couplings.
*/
void setFixedQEDCouplings(bool on = true) { theFixedQEDCouplings = on; }
/**
* Return true, if veto scales should be set
* for the real emission
*/
bool vetoScales() const { return theVetoScales; }
/**
* Switch on setting veto scales
*/
void doVetoScales() { theVetoScales = true; }
/**
* Switch off setting veto scales
*/
void noVetoScales() { theVetoScales = true; }
//@}
/** @name Amplitudes and caching */
//@{
/**
* Return the amplitudes to be considered
*/
const vector<Ptr<MatchboxAmplitude>::ptr>& amplitudes() const { return theAmplitudes; }
/**
* Access the amplitudes to be considered
*/
vector<Ptr<MatchboxAmplitude>::ptr>& amplitudes() { return theAmplitudes; }
//@}
/** @name Matrix element objects. */
//@{
/**
* Return the Born matrix elements to be considered
*/
const vector<Ptr<MatchboxMEBase>::ptr>& bornMEs() const { return theBornMEs; }
/**
* Access the Born matrix elements to be considered
*/
vector<Ptr<MatchboxMEBase>::ptr>& bornMEs() { return theBornMEs; }
/**
* Return the loop induced matrix elements to be considered
*/
const vector<Ptr<MatchboxMEBase>::ptr>& loopInducedMEs() const { return theLoopInducedMEs; }
/**
* Access the loop induced matrix elements to be considered
*/
vector<Ptr<MatchboxMEBase>::ptr>& loopInducedMEs() { return theLoopInducedMEs; }
/**
* Return the processes to be ordered from an OLP
*/
const map<Ptr<MatchboxAmplitude>::tptr,
map<pair<Process,int>,int> >&
olpProcesses() const { return theOLPProcesses; }
/**
* Access the processes to be ordered from an OLP
*/
map<Ptr<MatchboxAmplitude>::tptr,
map<pair<Process,int>,int> >&
olpProcesses() { return theOLPProcesses; }
/**
* Order an OLP process and return its id
*/
int orderOLPProcess(const Process& p,
Ptr<MatchboxAmplitude>::tptr amp,
int type);
/**
* Return the amplitudes which need external initialization
*/
const set<Ptr<MatchboxAmplitude>::tptr>& externalAmplitudes() const {
return theExternalAmplitudes;
}
/**
* Access the amplitudes which need external initialization
*/
set<Ptr<MatchboxAmplitude>::tptr>& externalAmplitudes() {
return theExternalAmplitudes;
}
/**
* Return the virtual corrections to be considered
*/
const vector<Ptr<MatchboxInsertionOperator>::ptr>& virtuals() const { return theVirtuals; }
/**
* Access the virtual corrections to be considered
*/
vector<Ptr<MatchboxInsertionOperator>::ptr>& virtuals() { return theVirtuals; }
/**
* Return the produced NLO matrix elements
*/
const vector<Ptr<MatchboxMEBase>::ptr>& bornVirtualMEs() const { return theBornVirtualMEs; }
/**
* Access the produced NLO matrix elements
*/
vector<Ptr<MatchboxMEBase>::ptr>& bornVirtualMEs() { return theBornVirtualMEs; }
/**
* Return the real emission matrix elements to be considered
*/
const vector<Ptr<MatchboxMEBase>::ptr>& realEmissionMEs() const { return theRealEmissionMEs; }
/**
* Access the real emission matrix elements to be considered
*/
vector<Ptr<MatchboxMEBase>::ptr>& realEmissionMEs() { return theRealEmissionMEs; }
/**
* Return, which set of dipoles should be considered
*/
int dipoleSet() const { return theDipoleSet; }
/**
* Return, which set of dipoles should be considered
*/
void dipoleSet(int s) { theDipoleSet = s; }
/**
* Return the produced subtracted matrix elements
*/
const vector<Ptr<SubtractedME>::ptr>& subtractedMEs() const { return theSubtractedMEs; }
/**
* Access the produced subtracted matrix elements
*/
vector<Ptr<SubtractedME>::ptr>& subtractedMEs() { return theSubtractedMEs; }
/**
* Return the produced finite real emission matrix elements
*/
const vector<Ptr<MatchboxMEBase>::ptr>& finiteRealMEs() const { return theFiniteRealMEs; }
/**
* Access the produced finite real emission elements
*/
vector<Ptr<MatchboxMEBase>::ptr>& finiteRealMEs() { return theFiniteRealMEs; }
/**
* Return the map of Born processes to splitting dipoles
*/
const map<cPDVector,set<Ptr<SubtractionDipole>::ptr> >& splittingDipoles() const {
return theSplittingDipoles;
}
/**
* Identify a splitting channel
*/
struct SplittingChannel {
/**
* The Born XComb
*/
StdXCombPtr bornXComb;
/**
* The real XComb
*/
StdXCombPtr realXComb;
/**
* The set of tilde XCombs to consider for the real xcomb
*/
vector<StdXCombPtr> tildeXCombs;
/**
* The dipole in charge of the splitting
*/
Ptr<SubtractionDipole>::ptr dipole;
/**
* Dump the setup
*/
void print(ostream&) const;
};
/**
* Generate all splitting channels for the Born process handled by
* the given XComb
*/
list<SplittingChannel> getSplittingChannels(tStdXCombPtr xc) const;
/**
* Return the reweight objects for matrix elements
*/
const vector<ReweightPtr>& reweighters() const { return theReweighters; }
/**
* Access the reweight objects for matrix elements
*/
vector<ReweightPtr>& reweighters() { return theReweighters; }
/**
* Return the preweight objects for matrix elements
*/
const vector<ReweightPtr>& preweighters() const { return thePreweighters; }
/**
* Access the preweight objects for matrix elements
*/
vector<ReweightPtr>& preweighters() { return thePreweighters; }
//@}
/** @name Setup the matrix elements */
//@{
/**
* Return true if this object needs to be initialized before all
* other objects (except those for which this function also returns
* true). This default version always returns false, but subclasses
* may override it to return true.
*/
virtual bool preInitialize() const { return true; }
/**
* Prepare a matrix element.
*/
void prepareME(Ptr<MatchboxMEBase>::ptr);
/**
* Check consistency and switch to porduction mode.
*/
- void productionMode();
+ virtual void productionMode();
/**
* Setup everything
*/
virtual void setup();
/**
* The highest multiplicity of legs having virtual contributions.(needed for madgraph)
*/
size_t highestVirt(){return theHighestVirtualsize;}
//@}
/** @name Diagnostic information */
//@{
/**
* Return true, if verbose
*/
bool verbose() const { return theVerbose; }
/**
* Switch on diagnostic information.
*/
void setVerbose(bool on = true) { theVerbose = on; }
/**
* Return true, if verbose while initializing
*/
bool initVerbose() const { return theInitVerbose || verbose(); }
/**
* Switch on diagnostic information while initializing
*/
void setInitVerbose(bool on = true) { theInitVerbose = on; }
/**
* Dump the setup
*/
void print(ostream&) const;
/**
* Return the subtraction data prefix.
*/
const string& subtractionData() const { return theSubtractionData; }
/**
* Set the subtraction data prefix.
*/
void subtractionData(const string& s) { theSubtractionData = s; }
/**
* Return the subtraction plot type.
*/
const int& subtractionPlotType() const { return theSubtractionPlotType; }
/**
* Set the subtraction plot type.
*/
void subtractionPlotType(const int& t) { theSubtractionPlotType = t; }
/**
* Return whether subtraction data should be plotted for all phase space points individually
*/
const bool& subtractionScatterPlot() const { return theSubtractionScatterPlot; }
/**
* Set whether subtraction data should be plotted for all phase space points individually
*/
void subtractionScatterPlot(const bool& s) { theSubtractionScatterPlot = s; }
/**
* Return the pole data prefix.
*/
const string& poleData() const { return thePoleData; }
/**
* Set the pole data prefix.
*/
void poleData(const string& s) { thePoleData = s; }
/**
* Return true, if cancellationn of epsilon poles should be checked.
*/
bool checkPoles() const { return poleData() != ""; }
//@}
/** @name Process generation */
//@{
/**
* Return the particle groups.
*/
const map<string,PDVector>& particleGroups() const { return theParticleGroups; }
/**
* Access the particle groups.
*/
map<string,PDVector>& particleGroups() { return theParticleGroups; }
/**
* Return true, if the given particle is incoming
*/
bool isIncoming(cPDPtr p) const {
return theIncoming.find(p->id()) != theIncoming.end();
}
/**
* Return true, if spin correlation information should be provided, if possible.
*/
bool spinCorrelations() const { return theSpinCorrelations; }
/**
* Indicate that spin correlation information should be provided, if possible.
*/
void setSpinCorrelations(bool yes) { theSpinCorrelations = yes; }
//@}
/** @name Truncated qtilde shower information */
//@{
/**
* Return the subprocess of the real emission
*/
tSubProPtr hardTreeSubprocess() { return theHardtreeSubprocess; }
/**
* Set the subprocess of the real emission for use in calculating the shower hardtree
*/
void setHardTreeSubprocess(tSubProPtr hardTree) { theHardtreeSubprocess = hardTree; }
/**
* Return the born emitter
*/
int hardTreeEmitter() { return theHardtreeEmitter; }
/**
* Set the born emitter for use in calculating the shower hardtree
*/
void setHardTreeEmitter(int emitter) { theHardtreeEmitter = emitter; }
/**
* Return the born spectator
*/
int hardTreeSpectator() { return theHardtreeSpectator; }
/**
* Set the born spectator for use in calculating the shower hardtree
*/
void setHardTreeSpectator(int spectator) { theHardtreeSpectator = spectator; }
//@}
/** @name Data handling */
//@{
/**
* Return (and possibly create) a directory to contain amplitude
* information.
*/
const string& buildStorage();
/**
* Return (and possibly create) a directory to contain integration grid
* information.
*/
const string& runStorage();
/**
* alpha of http://arxiv.org/pdf/hep-ph/0307268v2.pdf to restrict
* dipole phase space
*/
double alphaParameter() const { return theAlphaParameter; }
/**
* set the alpha parameter (needed for massive PK-Operator)
*/
void setAlphaParameter(double a)const { theAlphaParameter = a; }
//@}
public:
/**
* Print a summary of the parameters used
*/
void summary(ostream&) const;
public:
/** @name Functions used by the persistent I/O system. */
//@{
/**
* Function used to write out object persistently.
* @param os the persistent output stream written to.
*/
void persistentOutput(PersistentOStream & os) const;
/**
* Function used to read in object persistently.
* @param is the persistent input stream read from.
* @param version the version number of the object when written.
*/
void persistentInput(PersistentIStream & is, int version);
//@}
/**
* The standard Init function used to initialize the interfaces.
* Called exactly once for each class by the class description system
* before the main function starts or
* when this class is dynamically loaded.
*/
static void Init();
protected:
/** @name Clone Methods. */
//@{
/**
* Make a simple clone of this object.
* @return a pointer to the new object.
*/
virtual IBPtr clone() const;
/** Make a clone of this object, possibly modifying the cloned object
* to make it sane.
* @return a pointer to the new object.
*/
virtual IBPtr fullclone() const;
//@}
protected:
/** @name Standard Interfaced functions. */
//@{
/**
* Initialize this object after the setup phase before saving an
* EventGenerator to disk.
* @throws InitException if object could not be initialized properly.
*/
virtual void doinit();
/**
* Initialize this object. Called in the run phase just before
* a run begins.
*/
virtual void doinitrun();
//@}
private:
/**
* Flag to indicate that at least one MatchboxFactory object is in action
*/
static bool& theIsMatchboxRun();
/**
* The diagram generator.
*/
Ptr<Tree2toNGenerator>::ptr theDiagramGenerator;
/**
* The process data object to be used
*/
Ptr<ProcessData>::ptr theProcessData;
/**
* The number of light flavours, this matrix
* element is calculated for.
*/
unsigned int theNLight;
/**
* Vector with the PDG ids of the light quark flavours,
* which are contained in the jet particle group.
*/
vector<long> theNLightJetVec;
/**
* Vector with the PDG ids of the heavy quark flavours,
* which are contained in the jet particle group.
*/
vector<long> theNHeavyJetVec;
/**
* Vector with the PDG ids of the light quark flavours,
* which are contained in the proton particle group.
*/
vector<long> theNLightProtonVec;
/**
* The order in \f$\alpha_S\f$.
*/
unsigned int theOrderInAlphaS;
/**
* The order in \f$\alpha_{EM}\f$.
*/
unsigned int theOrderInAlphaEW;
/**
* The maximum number of legs with virtual corrections.
**/
unsigned int theHighestVirtualSize;
/**
* Switch on or off Born contributions
*/
bool theBornContributions;
/**
* Switch on or off virtual contributions
*/
bool theVirtualContributions;
/**
* Switch on or off subtracted real emission contributions should be included.
*/
bool theRealContributions;
/**
* True if virtual contributions should be treated as independent subprocesses
*/
bool theIndependentVirtuals;
/**
* True if PK operator contributions should be treated as independent subprocesses
*/
bool theIndependentPKs;
/**
* The phase space generator to be used.
*/
Ptr<MatchboxPhasespace>::ptr thePhasespace;
/**
* The scale choice object
*/
Ptr<MatchboxScaleChoice>::ptr theScaleChoice;
/**
* The factorization scale factor.
*/
double theFactorizationScaleFactor;
/**
* The renormalization scale factor.
*/
double theRenormalizationScaleFactor;
/**
* Use non-running couplings.
*/
bool theFixedCouplings;
/**
* Use non-running couplings.
*/
bool theFixedQEDCouplings;
/**
* True, if veto scales should be set
* for the real emission
*/
bool theVetoScales;
/**
* The amplitudes to be considered
*/
vector<Ptr<MatchboxAmplitude>::ptr> theAmplitudes;
/**
* The Born matrix elements to be considered
*/
vector<Ptr<MatchboxMEBase>::ptr> theBornMEs;
/**
* The loop induced matrix elements to be considered
*/
vector<Ptr<MatchboxMEBase>::ptr> theLoopInducedMEs;
/**
* The virtual corrections to be considered
*/
vector<Ptr<MatchboxInsertionOperator>::ptr> theVirtuals;
/**
* The real emission matrix elements to be considered
*/
vector<Ptr<MatchboxMEBase>::ptr> theRealEmissionMEs;
/**
* The produced NLO matrix elements
*/
vector<Ptr<MatchboxMEBase>::ptr> theBornVirtualMEs;
/**
* The produced subtracted matrix elements
*/
vector<Ptr<SubtractedME>::ptr> theSubtractedMEs;
/**
* The produced finite real emission matrix elements
*/
vector<Ptr<MatchboxMEBase>::ptr> theFiniteRealMEs;
/**
* Which set of dipoles should be considered
*/
int theDipoleSet;
/**
* Switch on or off verbosity
*/
bool theVerbose;
/**
* True, if verbose while initializing
*/
bool theInitVerbose;
/**
* Prefix for subtraction data
*/
string theSubtractionData;
/**
* Set the type of plot that is to be generated for subtraction checking
*/
int theSubtractionPlotType;
/**
* Set whether subtraction data should be plotted for all phase space points individually
*/
bool theSubtractionScatterPlot;
/**
* Prefix for pole data.
*/
string thePoleData;
/**
* Command to limit the real emission process to be considered.
*/
string doSingleRealProcess(string);
/**
* The real emission process to be included; if empty, all possible
* ones will be considered.
*/
vector<vector<string> > realEmissionProcesses;
/**
* Particle groups.
*/
map<string,PDVector> theParticleGroups;
/**
* Command to start a particle group.
*/
string startParticleGroup(string);
/**
* The name of the particle group currently edited.
*/
string particleGroupName;
/**
* The particle group currently edited.
*/
PDVector particleGroup;
/**
* Command to end a particle group.
*/
string endParticleGroup(string);
protected:
/**
* Parse a process description
*/
virtual vector<string> parseProcess(string);
private:
/**
* Command to set the process.
*/
string doProcess(string);
/**
* Command to set the process.
*/
string doLoopInducedProcess(string);
/**
* The process to consider in terms of particle groups.
*/
vector<vector<string> > processes;
/**
* The loop induced process to consider in terms of particle groups.
*/
vector<vector<string> > loopInducedProcesses;
/**
* Generate subprocesses.
*/
set<PDVector> makeSubProcesses(const vector<string>&) const;
public:
/**
* Generate matrix element objects for the given process.
*/
vector<Ptr<MatchboxMEBase>::ptr> makeMEs(const vector<string>&,
unsigned int orderas,
bool virt);
private:
/**
* The shower approximation.
*/
Ptr<ShowerApproximation>::ptr theShowerApproximation;
/**
* The map of Born processes to splitting dipoles
*/
map<cPDVector,set<Ptr<SubtractionDipole>::ptr> > theSplittingDipoles;
/**
* True, if subtraction scales should be caluclated from real emission kinematics
*/
bool theRealEmissionScales;
/**
* Consider all processes with order in couplings specifying the
* maximum order.
*/
bool theAllProcesses;
/**
* The processes to be ordered from an OLP
*/
map<Ptr<MatchboxAmplitude>::tptr,map<pair<Process,int>,int> > theOLPProcesses;
/**
* Amplitudes which need external initialization
*/
set<Ptr<MatchboxAmplitude>::tptr> theExternalAmplitudes;
/**
* Amplitudes to be selected on clashing responsibilities.
*/
vector<Ptr<MatchboxAmplitude>::ptr> theSelectedAmplitudes;
/**
* Amplitudes to be deselected on clashing responsibilities.
*/
vector<Ptr<MatchboxAmplitude>::ptr> theDeselectedAmplitudes;
/**
* Reweight objects for matrix elements
*/
vector<ReweightPtr> theReweighters;
/**
* Preweight objects for matrix elements
*/
vector<ReweightPtr> thePreweighters;
/**
* Produce matrix element corrections, but no NLO
*/
bool theMECorrectionsOnly;
/**
* The highest multiplicity of legs having virtual contributions.(needed for madgraph)
*/
int theHighestVirtualsize;
/**
* Produce matrix element corrections, with LoopSim NLO
*/
bool theLoopSimCorrections;
/**
* True, if the setup has already been run.
*/
bool ranSetup;
/**
* PDG ids of incoming particles
*/
set<long> theIncoming;
/**
* True, if first incoming partons originate from perturbative PDF
*/
bool theFirstPerturbativePDF;
/**
* True, if second incoming partons originate from perturbative PDF
*/
bool theSecondPerturbativePDF;
/**
* True, if this Factory is in production mode.
*/
bool inProductionMode;
/**
* The real emission subprocess used when calculating the hardtree
* in the truncated qtilde shower
*/
tSubProPtr theHardtreeSubprocess;
/**
* The born emitter used when calculating the hardtree in
* the truncated shower
*/
int theHardtreeEmitter;
/**
* The born spectator used when calculating the hardtree in
* the truncated shower
*/
int theHardtreeSpectator;
/**
* True, if spin correlation information should be provided, if possible.
*/
bool theSpinCorrelations;
/**
* The alpha parameter to be used for the dipole subtraction
* JB: The parameter is muatble, since we need to be able to change it
* while calculating the difference of IPK with and without alpha.
*/
mutable double theAlphaParameter;
/**
* Wether or not charge conservation should be enforced for the processes
* constructed.
*/
bool theEnforceChargeConservation;
/**
* Wether or not colour conservation should be enforced for the processes
* constructed.
*/
bool theEnforceColourConservation;
/**
* Wether or not lepton number conservation should be enforced for the processes
* constructed.
*/
bool theEnforceLeptonNumberConservation;
/**
* Wether or not quark number conservation should be enforced for the processes
* constructed.
*/
bool theEnforceQuarkNumberConservation;
/**
* Assume flavour diagonal lepton interactions
*/
bool theLeptonFlavourDiagonal;
/**
* Assume flavour diagonal quark interactions
*/
bool theQuarkFlavourDiagonal;
/**
* Command for production mode
*/
string doProductionMode(string) {
productionMode(); return "";
}
private:
/**
* The assignment operator is private and must never be called.
* In fact, it should not even be implemented.
*/
MatchboxFactory & operator=(const MatchboxFactory &);
};
}
#endif /* HERWIG_MatchboxFactory_H */
diff --git a/MatrixElement/Matchbox/Matching/ShowerApproximation.cc b/MatrixElement/Matchbox/Matching/ShowerApproximation.cc
--- a/MatrixElement/Matchbox/Matching/ShowerApproximation.cc
+++ b/MatrixElement/Matchbox/Matching/ShowerApproximation.cc
@@ -1,698 +1,716 @@
// -*- C++ -*-
//
// ShowerApproximation.cc is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
//
// This is the implementation of the non-inlined, non-templated member
// functions of the ShowerApproximation class.
//
#include "ShowerApproximation.h"
#include "ThePEG/Interface/ClassDocumentation.h"
#include "ThePEG/Interface/Switch.h"
#include "ThePEG/Interface/Reference.h"
#include "ThePEG/Interface/Parameter.h"
#include "ThePEG/EventRecord/Particle.h"
#include "ThePEG/Repository/UseRandom.h"
#include "ThePEG/Repository/EventGenerator.h"
#include "ThePEG/Utilities/DescribeClass.h"
#include "ThePEG/Persistency/PersistentOStream.h"
#include "ThePEG/Persistency/PersistentIStream.h"
#include "Herwig/MatrixElement/Matchbox/Dipoles/SubtractionDipole.h"
#include "Herwig/MatrixElement/Matchbox/Phasespace/TildeKinematics.h"
#include "Herwig/MatrixElement/Matchbox/Phasespace/InvertedTildeKinematics.h"
using namespace Herwig;
ShowerApproximation::ShowerApproximation()
: HandlerBase(),
theExtrapolationX(1.0), theBelowCutoff(false),
theFFPtCut(1.0*GeV), theFFScreeningScale(ZERO),
theFIPtCut(1.0*GeV), theFIScreeningScale(ZERO),
theIIPtCut(1.0*GeV), theIIScreeningScale(ZERO),
theSafeCut(0.0*GeV),
theRestrictPhasespace(true), theHardScaleFactor(1.0),
theRenormalizationScaleFactor(1.0), theFactorizationScaleFactor(1.0),
theRealEmissionScaleInSubtraction(showerScale),
theBornScaleInSubtraction(showerScale),
theEmissionScaleInSubtraction(showerScale),
theRealEmissionScaleInSplitting(showerScale),
theBornScaleInSplitting(showerScale),
theEmissionScaleInSplitting(showerScale),
theRenormalizationScaleFreeze(1.*GeV),
theFactorizationScaleFreeze(1.*GeV),
maxPtIsMuF(false) {}
ShowerApproximation::~ShowerApproximation() {}
void ShowerApproximation::setLargeNBasis() {
assert(dipole()->realEmissionME()->matchboxAmplitude());
if ( !dipole()->realEmissionME()->matchboxAmplitude()->treeAmplitudes() )
return;
if ( !theLargeNBasis ) {
if ( !dipole()->realEmissionME()->matchboxAmplitude()->colourBasis() )
throw Exception() << "ShowerApproximation::setLargeNBasis(): Expecting a colour basis object."
<< Exception::runerror;
theLargeNBasis =
dipole()->realEmissionME()->matchboxAmplitude()->colourBasis()->cloneMe();
theLargeNBasis->clear();
theLargeNBasis->doLargeN();
}
}
void ShowerApproximation::setDipole(Ptr<SubtractionDipole>::tptr dip) {
theDipole = dip;
setLargeNBasis();
}
Ptr<SubtractionDipole>::tptr ShowerApproximation::dipole() const { return theDipole; }
Ptr<TildeKinematics>::tptr
ShowerApproximation::showerTildeKinematics() const {
return Ptr<TildeKinematics>::tptr();
}
Ptr<InvertedTildeKinematics>::tptr
ShowerApproximation::showerInvertedTildeKinematics() const {
return Ptr<InvertedTildeKinematics>::tptr();
}
void ShowerApproximation::checkCutoff() {
assert(!showerTildeKinematics());
}
void ShowerApproximation::getShowerVariables() {
// check for the cutoff
dipole()->isAboveCutoff(isAboveCutoff());
// get the hard scale
dipole()->showerHardScale(hardScale());
// set the shower scale and variables for completeness
dipole()->showerScale(dipole()->lastPt());
dipole()->showerParameters().resize(1);
dipole()->showerParameters()[0] = dipole()->lastZ();
// check for phase space
dipole()->isInShowerPhasespace(isInShowerPhasespace());
}
bool ShowerApproximation::isAboveCutoff() const {
if ( dipole()->bornEmitter() > 1 &&
dipole()->bornSpectator() > 1 ) {
return dipole()->lastPt() >= max(ffPtCut(),safeCut());
} else if ( ( dipole()->bornEmitter() > 1 &&
dipole()->bornSpectator() < 2 ) ||
( dipole()->bornEmitter() < 2 &&
dipole()->bornSpectator() > 1 ) ) {
return dipole()->lastPt() >= max(fiPtCut(),safeCut());
} else {
assert(dipole()->bornEmitter() < 2 &&
dipole()->bornSpectator() < 2);
return dipole()->lastPt() >= max(iiPtCut(),safeCut());
}
return true;
}
Energy ShowerApproximation::hardScale() const {
if ( !maxPtIsMuF ) {
if ( !bornCXComb()->mePartonData()[0]->coloured() &&
!bornCXComb()->mePartonData()[1]->coloured() ) {
Energy maxPt = (bornCXComb()->meMomenta()[0] + bornCXComb()->meMomenta()[1]).m();
maxPt *= hardScaleFactor();
return maxPt;
}
Energy maxPt = generator()->maximumCMEnergy();
vector<Lorentz5Momentum>::const_iterator p =
bornCXComb()->meMomenta().begin() + 2;
cPDVector::const_iterator pp =
bornCXComb()->mePartonData().begin() + 2;
for ( ; p != bornCXComb()->meMomenta().end(); ++p, ++pp )
if ( (**pp).coloured() )
maxPt = min(maxPt,p->mt());
if ( maxPt == generator()->maximumCMEnergy() )
maxPt = (bornCXComb()->meMomenta()[0] + bornCXComb()->meMomenta()[1]).m();
maxPt *= hardScaleFactor();
return maxPt;
} else {
return hardScaleFactor()*sqrt(bornCXComb()->lastShowerScale());
}
}
bool ShowerApproximation::isInShowerPhasespace() const {
if ( !dipole()->isAboveCutoff() )
return false;
if ( !restrictPhasespace() )
return true;
InvertedTildeKinematics& kinematics =
const_cast<InvertedTildeKinematics&>(*dipole()->invertedTildeKinematics());
tcStdXCombPtr tmpreal = kinematics.realXComb();
tcStdXCombPtr tmpborn = kinematics.bornXComb();
Ptr<SubtractionDipole>::tptr tmpdip = kinematics.dipole();
Energy hard = dipole()->showerHardScale();
Energy pt = dipole()->lastPt();
double z = dipole()->lastZ();
pair<double,double> zbounds(0.,1.);
kinematics.dipole(const_ptr_cast<Ptr<SubtractionDipole>::tptr>(theDipole));
kinematics.prepare(realCXComb(),bornCXComb());
if ( pt > hard ) {
kinematics.dipole(tmpdip);
kinematics.prepare(tmpreal,tmpborn);
return false;
}
try {
zbounds = kinematics.zBounds(pt,hard);
} catch(...) {
kinematics.dipole(tmpdip);
kinematics.prepare(tmpreal,tmpborn);
throw;
}
kinematics.dipole(tmpdip);
kinematics.prepare(tmpreal,tmpborn);
return z > zbounds.first && z < zbounds.second;
}
Energy2 ShowerApproximation::showerEmissionScale() const {
Energy2 mur = sqr(dipole()->lastPt());
if ( dipole()->bornEmitter() > 1 &&
dipole()->bornSpectator() > 1 ) {
return mur + sqr(ffScreeningScale());
} else if ( ( dipole()->bornEmitter() > 1 &&
dipole()->bornSpectator() < 2 ) ||
( dipole()->bornEmitter() < 2 &&
dipole()->bornSpectator() > 1 ) ) {
return mur + sqr(fiScreeningScale());
} else {
assert(dipole()->bornEmitter() < 2 &&
dipole()->bornSpectator() < 2);
return mur + sqr(iiScreeningScale());
}
return mur;
}
Energy2 ShowerApproximation::bornRenormalizationScale() const {
return
sqr(dipole()->underlyingBornME()->renormalizationScaleFactor()) *
dipole()->underlyingBornME()->renormalizationScale();
}
Energy2 ShowerApproximation::bornFactorizationScale() const {
return
sqr(dipole()->underlyingBornME()->factorizationScaleFactor()) *
dipole()->underlyingBornME()->factorizationScale();
}
Energy2 ShowerApproximation::realRenormalizationScale() const {
return
sqr(dipole()->realEmissionME()->renormalizationScaleFactor()) *
dipole()->realEmissionME()->renormalizationScale();
}
Energy2 ShowerApproximation::realFactorizationScale() const {
return
sqr(dipole()->realEmissionME()->factorizationScaleFactor()) *
dipole()->realEmissionME()->factorizationScale();
}
double ShowerApproximation::bornPDFWeight(Energy2 muf) const {
if ( !bornCXComb()->mePartonData()[0]->coloured() &&
!bornCXComb()->mePartonData()[1]->coloured() )
return 1.;
if ( muf < sqr(theFactorizationScaleFreeze) )
muf = sqr(theFactorizationScaleFreeze);
double pdfweight = 1.;
if ( bornCXComb()->mePartonData()[0]->coloured() &&
dipole()->underlyingBornME()->havePDFWeight1() )
pdfweight *= dipole()->underlyingBornME()->pdf1(muf,theExtrapolationX);
if ( bornCXComb()->mePartonData()[1]->coloured() &&
dipole()->underlyingBornME()->havePDFWeight2() )
pdfweight *= dipole()->underlyingBornME()->pdf2(muf,theExtrapolationX);
return pdfweight;
}
double ShowerApproximation::realPDFWeight(Energy2 muf) const {
if ( !realCXComb()->mePartonData()[0]->coloured() &&
!realCXComb()->mePartonData()[1]->coloured() )
return 1.;
if ( muf < sqr(theFactorizationScaleFreeze) )
muf = sqr(theFactorizationScaleFreeze);
double pdfweight = 1.;
if ( realCXComb()->mePartonData()[0]->coloured() &&
dipole()->realEmissionME()->havePDFWeight1() )
pdfweight *= dipole()->realEmissionME()->pdf1(muf,theExtrapolationX);
if ( realCXComb()->mePartonData()[1]->coloured() &&
dipole()->realEmissionME()->havePDFWeight2() )
pdfweight *= dipole()->realEmissionME()->pdf2(muf,theExtrapolationX);
return pdfweight;
}
double ShowerApproximation::scaleWeight(int rScale, int bScale, int eScale) const {
double emissionAlpha = 1.;
Energy2 emissionScale = ZERO;
Energy2 showerscale = ZERO;
if ( eScale == showerScale || bScale == showerScale || eScale == showerScale ) {
showerscale = showerRenormalizationScale();
if ( showerscale < sqr(theRenormalizationScaleFreeze) )
showerscale = sqr(theFactorizationScaleFreeze);
}
if ( eScale == showerScale ) {
emissionAlpha = SM().alphaS(showerscale);
emissionScale = showerFactorizationScale();
} else if ( eScale == realScale ) {
emissionAlpha = dipole()->realEmissionME()->lastXComb().lastAlphaS();
emissionScale = dipole()->realEmissionME()->lastScale();
} else if ( eScale == bornScale ) {
emissionAlpha = dipole()->underlyingBornME()->lastXComb().lastAlphaS();
emissionScale = dipole()->underlyingBornME()->lastScale();
}
double emissionPDF = realPDFWeight(emissionScale);
double couplingFactor = 1.;
if ( bScale != rScale ) {
double bornAlpha = 1.;
if ( bScale == showerScale ) {
bornAlpha = SM().alphaS(showerscale);
} else if ( bScale == realScale ) {
bornAlpha = dipole()->realEmissionME()->lastXComb().lastAlphaS();
} else if ( bScale == bornScale ) {
bornAlpha = dipole()->underlyingBornME()->lastXComb().lastAlphaS();
}
double realAlpha = 1.;
if ( rScale == showerScale ) {
realAlpha = SM().alphaS(showerscale);
} else if ( rScale == realScale ) {
realAlpha = dipole()->realEmissionME()->lastXComb().lastAlphaS();
} else if ( rScale == bornScale ) {
realAlpha = dipole()->underlyingBornME()->lastXComb().lastAlphaS();
}
couplingFactor *=
pow(realAlpha/bornAlpha,(double)(dipole()->underlyingBornME()->orderInAlphaS()));
}
Energy2 hardScale = ZERO;
if ( bScale == showerScale ) {
hardScale = showerFactorizationScale();
} else if ( bScale == realScale ) {
hardScale = dipole()->realEmissionME()->lastScale();
} else if ( bScale == bornScale ) {
hardScale = dipole()->underlyingBornME()->lastScale();
}
double bornPDF = bornPDFWeight(hardScale);
if ( bornPDF < 1e-8 )
bornPDF = 0.0;
if ( emissionPDF < 1e-8 )
emissionPDF = 0.0;
if ( emissionPDF == 0.0 || bornPDF == 0.0 )
return 0.0;
return
emissionAlpha * emissionPDF *
couplingFactor / bornPDF;
}
double ShowerApproximation::channelWeight(int emitter, int emission,
int spectator, int) const {
double cfac = 1.;
double Nc = generator()->standardModel()->Nc();
if (realCXComb()->mePartonData()[emitter]->iColour() == PDT::Colour8){
if (realCXComb()->mePartonData()[emission]->iColour() == PDT::Colour8)
cfac = Nc;
else if ( realCXComb()->mePartonData()[emission]->iColour() == PDT::Colour3 ||
realCXComb()->mePartonData()[emission]->iColour() == PDT::Colour3bar)
cfac = 0.5;
else assert(false);
}
else if ((realCXComb()->mePartonData()[emitter] ->iColour() == PDT::Colour3 ||
realCXComb()->mePartonData()[emitter] ->iColour() == PDT::Colour3bar))
cfac = (sqr(Nc)-1.)/(2.*Nc);
else assert(false);
// do the most simple thing for the time being; needs fixing later
if ( realCXComb()->mePartonData()[emission]->id() == ParticleID::g ) {
Energy2 pipk =
realCXComb()->meMomenta()[emitter] * realCXComb()->meMomenta()[spectator];
Energy2 pipj =
realCXComb()->meMomenta()[emitter] * realCXComb()->meMomenta()[emission];
Energy2 pjpk =
realCXComb()->meMomenta()[emission] * realCXComb()->meMomenta()[spectator];
return cfac *GeV2 * pipk / ( pipj * ( pipj + pjpk ) );
}
return
cfac * GeV2 / (realCXComb()->meMomenta()[emitter] * realCXComb()->meMomenta()[emission]);
}
double ShowerApproximation::channelWeight() const {
double currentChannel = channelWeight(dipole()->realEmitter(),
dipole()->realEmission(),
dipole()->realSpectator(),
dipole()->bornEmitter());
if ( currentChannel == 0. )
return 0.;
double sum = 0.;
for ( vector<Ptr<SubtractionDipole>::tptr>::const_iterator dip =
dipole()->partnerDipoles().begin();
dip != dipole()->partnerDipoles().end(); ++dip )
sum += channelWeight((**dip).realEmitter(),
(**dip).realEmission(),
(**dip).realSpectator(),
(**dip).bornEmitter());
assert(sum > 0.0);
return currentChannel / sum;
}
// If needed, insert default implementations of virtual function defined
// in the InterfacedBase class here (using ThePEG-interfaced-impl in Emacs).
void ShowerApproximation::doinit() {
if ( profileScales() ) {
if ( profileScales()->unrestrictedPhasespace() &&
restrictPhasespace() ) {
generator()->log()
<< "ShowerApproximation warning: The scale profile chosen requires an unrestricted phase space,\n"
<< "however, the phase space was set to be restricted. Will switch to unrestricted phase space.\n"
<< flush;
restrictPhasespace(false);
}
}
HandlerBase::doinit();
}
void ShowerApproximation::persistentOutput(PersistentOStream & os) const {
os << theLargeNBasis
<< theBornXComb << theRealXComb << theTildeXCombs << theDipole << theBelowCutoff
<< ounit(theFFPtCut,GeV) << ounit(theFFScreeningScale,GeV)
<< ounit(theFIPtCut,GeV) << ounit(theFIScreeningScale,GeV)
<< ounit(theIIPtCut,GeV) << ounit(theIIScreeningScale,GeV)
<< ounit(theSafeCut,GeV)
<< theRestrictPhasespace << theHardScaleFactor
<< theRenormalizationScaleFactor << theFactorizationScaleFactor
<< theExtrapolationX
<< theRealEmissionScaleInSubtraction << theBornScaleInSubtraction
<< theEmissionScaleInSubtraction << theRealEmissionScaleInSplitting
<< theBornScaleInSplitting << theEmissionScaleInSplitting
<< ounit(theRenormalizationScaleFreeze,GeV)
<< ounit(theFactorizationScaleFreeze,GeV) << maxPtIsMuF
<< theHardScaleProfile;
}
void ShowerApproximation::persistentInput(PersistentIStream & is, int) {
is >> theLargeNBasis
>> theBornXComb >> theRealXComb >> theTildeXCombs >> theDipole >> theBelowCutoff
>> iunit(theFFPtCut,GeV) >> iunit(theFFScreeningScale,GeV)
>> iunit(theFIPtCut,GeV) >> iunit(theFIScreeningScale,GeV)
>> iunit(theIIPtCut,GeV) >> iunit(theIIScreeningScale,GeV)
>> iunit(theSafeCut,GeV)
>> theRestrictPhasespace >> theHardScaleFactor
>> theRenormalizationScaleFactor >> theFactorizationScaleFactor
>> theExtrapolationX
>> theRealEmissionScaleInSubtraction >> theBornScaleInSubtraction
>> theEmissionScaleInSubtraction >> theRealEmissionScaleInSplitting
>> theBornScaleInSplitting >> theEmissionScaleInSplitting
>> iunit(theRenormalizationScaleFreeze,GeV)
>> iunit(theFactorizationScaleFreeze,GeV) >> maxPtIsMuF
>> theHardScaleProfile;
}
// *** Attention *** The following static variable is needed for the type
// description system in ThePEG. Please check that the template arguments
// are correct (the class and its base class), and that the constructor
// arguments are correct (the class name and the name of the dynamically
// loadable library where the class implementation can be found).
DescribeAbstractClass<ShowerApproximation,HandlerBase>
describeHerwigShowerApproximation("Herwig::ShowerApproximation", "Herwig.so");
void ShowerApproximation::Init() {
static ClassDocumentation<ShowerApproximation> documentation
("ShowerApproximation describes the shower emission to be used "
"in NLO matching.");
static Parameter<ShowerApproximation,Energy> interfaceFFPtCut
("FFPtCut",
"Set the pt infrared cutoff",
&ShowerApproximation::theFFPtCut, GeV, 1.0*GeV, 0.0*GeV, 0*GeV,
false, false, Interface::lowerlim);
static Parameter<ShowerApproximation,Energy> interfaceFIPtCut
("FIPtCut",
"Set the pt infrared cutoff",
&ShowerApproximation::theFIPtCut, GeV, 1.0*GeV, 0.0*GeV, 0*GeV,
false, false, Interface::lowerlim);
static Parameter<ShowerApproximation,Energy> interfaceIIPtCut
("IIPtCut",
"Set the pt infrared cutoff",
&ShowerApproximation::theIIPtCut, GeV, 1.0*GeV, 0.0*GeV, 0*GeV,
false, false, Interface::lowerlim);
static Parameter<ShowerApproximation,Energy> interfaceSafeCut
("SafeCut",
"Set the enhanced infrared cutoff for the Matching.",
&ShowerApproximation::theSafeCut, GeV, 0.0*GeV, 0.0*GeV, 0*GeV,
false, false, Interface::lowerlim);
static Parameter<ShowerApproximation,Energy> interfaceFFScreeningScale
("FFScreeningScale",
"Set the screening scale",
&ShowerApproximation::theFFScreeningScale, GeV, 0.0*GeV, 0.0*GeV, 0*GeV,
false, false, Interface::lowerlim);
static Parameter<ShowerApproximation,Energy> interfaceFIScreeningScale
("FIScreeningScale",
"Set the screening scale",
&ShowerApproximation::theFIScreeningScale, GeV, 0.0*GeV, 0.0*GeV, 0*GeV,
false, false, Interface::lowerlim);
static Parameter<ShowerApproximation,Energy> interfaceIIScreeningScale
("IIScreeningScale",
"Set the screening scale",
&ShowerApproximation::theIIScreeningScale, GeV, 0.0*GeV, 0.0*GeV, 0*GeV,
false, false, Interface::lowerlim);
static Switch<ShowerApproximation,bool> interfaceRestrictPhasespace
("RestrictPhasespace",
"Switch on or off phasespace restrictions",
&ShowerApproximation::theRestrictPhasespace, true, false, false);
static SwitchOption interfaceRestrictPhasespaceOn
(interfaceRestrictPhasespace,
"On",
"Perform phasespace restrictions",
true);
static SwitchOption interfaceRestrictPhasespaceOff
(interfaceRestrictPhasespace,
"Off",
"Do not perform phasespace restrictions",
false);
static Parameter<ShowerApproximation,double> interfaceHardScaleFactor
("HardScaleFactor",
"The hard scale factor.",
&ShowerApproximation::theHardScaleFactor, 1.0, 0.0, 0,
false, false, Interface::lowerlim);
static Parameter<ShowerApproximation,double> interfaceRenormalizationScaleFactor
("RenormalizationScaleFactor",
"The hard scale factor.",
&ShowerApproximation::theRenormalizationScaleFactor, 1.0, 0.0, 0,
false, false, Interface::lowerlim);
static Parameter<ShowerApproximation,double> interfaceFactorizationScaleFactor
("FactorizationScaleFactor",
"The hard scale factor.",
&ShowerApproximation::theFactorizationScaleFactor, 1.0, 0.0, 0,
false, false, Interface::lowerlim);
static Parameter<ShowerApproximation,double> interfaceExtrapolationX
("ExtrapolationX",
"The x from which on extrapolation should be performed.",
&ShowerApproximation::theExtrapolationX, 1.0, 0.0, 1.0,
false, false, Interface::limited);
static Switch<ShowerApproximation,int> interfaceRealEmissionScaleInSubtraction
("RealEmissionScaleInSubtraction",
"Set the scale choice for the real emission cross section in the matching subtraction.",
&ShowerApproximation::theRealEmissionScaleInSubtraction, showerScale, false, false);
static SwitchOption interfaceRealEmissionScaleInSubtractionRealScale
(interfaceRealEmissionScaleInSubtraction,
"RealScale",
"Use the real emission scale.",
realScale);
static SwitchOption interfaceRealEmissionScaleInSubtractionBornScale
(interfaceRealEmissionScaleInSubtraction,
"BornScale",
"Use the Born scale.",
bornScale);
static SwitchOption interfaceRealEmissionScaleInSubtractionShowerScale
(interfaceRealEmissionScaleInSubtraction,
"ShowerScale",
"Use the shower scale",
showerScale);
+ interfaceRealEmissionScaleInSubtraction.rank(-1);
+
static Switch<ShowerApproximation,int> interfaceBornScaleInSubtraction
("BornScaleInSubtraction",
"Set the scale choice for the Born cross section in the matching subtraction.",
&ShowerApproximation::theBornScaleInSubtraction, showerScale, false, false);
static SwitchOption interfaceBornScaleInSubtractionRealScale
(interfaceBornScaleInSubtraction,
"RealScale",
"Use the real emission scale.",
realScale);
static SwitchOption interfaceBornScaleInSubtractionBornScale
(interfaceBornScaleInSubtraction,
"BornScale",
"Use the Born scale.",
bornScale);
static SwitchOption interfaceBornScaleInSubtractionShowerScale
(interfaceBornScaleInSubtraction,
"ShowerScale",
"Use the shower scale",
showerScale);
+ interfaceBornScaleInSubtraction.rank(-1);
+
static Switch<ShowerApproximation,int> interfaceEmissionScaleInSubtraction
("EmissionScaleInSubtraction",
"Set the scale choice for the emission in the matching subtraction.",
&ShowerApproximation::theEmissionScaleInSubtraction, showerScale, false, false);
static SwitchOption interfaceEmissionScaleInSubtractionRealScale
(interfaceEmissionScaleInSubtraction,
"RealScale",
"Use the real emission scale.",
realScale);
static SwitchOption interfaceEmissionScaleInSubtractionEmissionScale
(interfaceEmissionScaleInSubtraction,
"BornScale",
"Use the Born scale.",
bornScale);
static SwitchOption interfaceEmissionScaleInSubtractionShowerScale
(interfaceEmissionScaleInSubtraction,
"ShowerScale",
"Use the shower scale",
showerScale);
+ interfaceEmissionScaleInSubtraction.rank(-1);
+
static Switch<ShowerApproximation,int> interfaceRealEmissionScaleInSplitting
("RealEmissionScaleInSplitting",
"Set the scale choice for the real emission cross section in the splitting.",
&ShowerApproximation::theRealEmissionScaleInSplitting, showerScale, false, false);
static SwitchOption interfaceRealEmissionScaleInSplittingRealScale
(interfaceRealEmissionScaleInSplitting,
"RealScale",
"Use the real emission scale.",
realScale);
static SwitchOption interfaceRealEmissionScaleInSplittingBornScale
(interfaceRealEmissionScaleInSplitting,
"BornScale",
"Use the Born scale.",
bornScale);
static SwitchOption interfaceRealEmissionScaleInSplittingShowerScale
(interfaceRealEmissionScaleInSplitting,
"ShowerScale",
"Use the shower scale",
showerScale);
+ interfaceRealEmissionScaleInSplitting.rank(-1);
+
static Switch<ShowerApproximation,int> interfaceBornScaleInSplitting
("BornScaleInSplitting",
"Set the scale choice for the Born cross section in the splitting.",
&ShowerApproximation::theBornScaleInSplitting, showerScale, false, false);
static SwitchOption interfaceBornScaleInSplittingRealScale
(interfaceBornScaleInSplitting,
"RealScale",
"Use the real emission scale.",
realScale);
static SwitchOption interfaceBornScaleInSplittingBornScale
(interfaceBornScaleInSplitting,
"BornScale",
"Use the Born scale.",
bornScale);
static SwitchOption interfaceBornScaleInSplittingShowerScale
(interfaceBornScaleInSplitting,
"ShowerScale",
"Use the shower scale",
showerScale);
+ interfaceBornScaleInSplitting.rank(-1);
+
static Switch<ShowerApproximation,int> interfaceEmissionScaleInSplitting
("EmissionScaleInSplitting",
"Set the scale choice for the emission in the splitting.",
&ShowerApproximation::theEmissionScaleInSplitting, showerScale, false, false);
static SwitchOption interfaceEmissionScaleInSplittingRealScale
(interfaceEmissionScaleInSplitting,
"RealScale",
"Use the real emission scale.",
realScale);
static SwitchOption interfaceEmissionScaleInSplittingEmissionScale
(interfaceEmissionScaleInSplitting,
"BornScale",
"Use the Born scale.",
bornScale);
static SwitchOption interfaceEmissionScaleInSplittingShowerScale
(interfaceEmissionScaleInSplitting,
"ShowerScale",
"Use the shower scale",
showerScale);
+ interfaceEmissionScaleInSplitting.rank(-1);
+
static Parameter<ShowerApproximation,Energy> interfaceRenormalizationScaleFreeze
("RenormalizationScaleFreeze",
"The freezing scale for the renormalization scale.",
&ShowerApproximation::theRenormalizationScaleFreeze, GeV, 1.0*GeV, 0.0*GeV, 0*GeV,
false, false, Interface::lowerlim);
+ interfaceRenormalizationScaleFreeze.rank(-1);
+
static Parameter<ShowerApproximation,Energy> interfaceFactorizationScaleFreeze
("FactorizationScaleFreeze",
"The freezing scale for the factorization scale.",
&ShowerApproximation::theFactorizationScaleFreeze, GeV, 1.0*GeV, 0.0*GeV, 0*GeV,
false, false, Interface::lowerlim);
+ interfaceFactorizationScaleFreeze.rank(-1);
+
static Reference<ShowerApproximation,HardScaleProfile> interfaceHardScaleProfile
("HardScaleProfile",
"The hard scale profile to use.",
&ShowerApproximation::theHardScaleProfile, false, false, true, true, false);
static Reference<ShowerApproximation,ColourBasis> interfaceLargeNBasis
("LargeNBasis",
"Set the large-N colour basis implementation.",
&ShowerApproximation::theLargeNBasis, false, false, true, true, false);
+ interfaceLargeNBasis.rank(-1);
+
static Switch<ShowerApproximation,bool> interfaceMaxPtIsMuF
("MaxPtIsMuF",
"",
&ShowerApproximation::maxPtIsMuF, false, false, false);
static SwitchOption interfaceMaxPtIsMuFYes
(interfaceMaxPtIsMuF,
"Yes",
"",
true);
static SwitchOption interfaceMaxPtIsMuFNo
(interfaceMaxPtIsMuF,
"No",
"",
false);
}
diff --git a/MatrixElement/Matchbox/Phasespace/FlatInvertibleLabframePhasespace.cc b/MatrixElement/Matchbox/Phasespace/FlatInvertibleLabframePhasespace.cc
--- a/MatrixElement/Matchbox/Phasespace/FlatInvertibleLabframePhasespace.cc
+++ b/MatrixElement/Matchbox/Phasespace/FlatInvertibleLabframePhasespace.cc
@@ -1,173 +1,171 @@
// -*- C++ -*-
//
// FlatInvertiblePhasespace.cc is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
//
// This is the implementation of the non-inlined, non-templated member
// functions of the FlatInvertibleLabframePhasespace class.
//
#include "FlatInvertibleLabframePhasespace.h"
#include "ThePEG/Interface/ClassDocumentation.h"
#include "ThePEG/Interface/Switch.h"
#include "ThePEG/EventRecord/Particle.h"
#include "ThePEG/Repository/UseRandom.h"
#include "ThePEG/Repository/EventGenerator.h"
#include "ThePEG/Utilities/DescribeClass.h"
#include "Herwig/Utilities/GSLBisection.h"
#include "ThePEG/Cuts/Cuts.h"
#include "ThePEG/Persistency/PersistentOStream.h"
#include "ThePEG/Persistency/PersistentIStream.h"
using namespace Herwig;
FlatInvertibleLabframePhasespace::FlatInvertibleLabframePhasespace()
: theLogSHat(false) {}
FlatInvertibleLabframePhasespace::~FlatInvertibleLabframePhasespace() {}
IBPtr FlatInvertibleLabframePhasespace::clone() const {
return new_ptr(*this);
}
IBPtr FlatInvertibleLabframePhasespace::fullclone() const {
return new_ptr(*this);
}
double FlatInvertibleLabframePhasespace::invertTwoToNKinematics(const vector<Lorentz5Momentum>& momenta,
double* r) const {
double weight = 1.;
Energy finalstatemass = 0*GeV;
for ( vector<Lorentz5Momentum>::const_iterator p =
momenta.begin()+2; p != momenta.end(); ++p )
finalstatemass += p->mass();
Lorentz5Momentum pinitial = momenta[0]+momenta[1];
Energy2 sh = pinitial.m2();
double tau = sh/lastS();
Energy2 shmax = lastCuts().sHatMax();
Energy2 shmin = max(lastCuts().sHatMin(),sqr(finalstatemass));
if (theLogSHat) {
r[0] = log(sh/shmin)/log(shmax/shmin);
weight *= tau*log(shmax/shmin);
} else {
r[0] = (sh-shmin)/(shmax-shmin);
weight *= (shmax-shmin)/lastS();
}
double ltau = log(tau);
r[1] = 0.5 - pinitial.rapidity()/ltau;
weight *= -ltau;
vector<Lorentz5Momentum> Pcms = momenta;
Boost toCMS = pinitial.findBoostToCM();
for ( vector<Lorentz5Momentum>::iterator pit =
Pcms.begin(); pit != Pcms.end(); ++pit )
pit->boost(toCMS);
weight *= FlatInvertiblePhasespace::invertTwoToNKinematics(Pcms, r+2);
return weight;
}
double FlatInvertibleLabframePhasespace::generateTwoToNKinematics(const double* r,
vector<Lorentz5Momentum>& momenta) {
double weight = 1.;
Energy finalstatemass = 0*GeV;
for ( vector<Lorentz5Momentum>::const_iterator p =
momenta.begin()+2; p != momenta.end(); ++p )
finalstatemass += p->mass();
Energy beamenergy = sqrt(lastS())/2.;
Energy2 shmax = lastCuts().sHatMax();
Energy2 shmin = max(lastCuts().sHatMin(),sqr(finalstatemass));
Energy2 sh;
double tau;
if (theLogSHat) {
sh = shmin*pow(shmax/shmin, r[0]);
tau = sh/lastS();
weight *= tau*log(shmax/shmin);
} else {
sh = r[0]*(shmax-shmin)+shmin;
tau = sh/lastS();
weight *= (shmax-shmin)/lastS();
}
double ltau = log(tau);
double y = ltau*(0.5 - r[1]);
weight *= -ltau;
double x1 = sqrt(tau)*exp(y);
double x2 = sqrt(tau)*exp(-y);
momenta[0] = Lorentz5Momentum(0*GeV,0*GeV,+x1*beamenergy,x1*beamenergy);
momenta[1] = Lorentz5Momentum(0*GeV,0*GeV,-x2*beamenergy,x2*beamenergy);
lastXCombPtr()->lastX1X2(make_pair(x1,x2));
lastXCombPtr()->lastSHat(sh);
weight *= FlatInvertiblePhasespace::generateTwoToNKinematics(r+2, momenta);
// find boost to the relevant partonic frame note final state kinematics are
// always generated in the CMS for this phase space algorithm
Boost boostinitial = (momenta[0]+momenta[1]).findBoostToCM();
for ( vector<Lorentz5Momentum>::iterator pit =
momenta.begin()+2; pit != momenta.end(); ++pit )
pit->boost(-boostinitial);
- fillDiagramWeights();
-
return weight;
}
// If needed, insert default implementations of virtual function defined
// in the InterfacedBase class here (using ThePEG-interfaced-impl in Emacs).
void FlatInvertibleLabframePhasespace::persistentOutput(PersistentOStream & os) const {
os << theLogSHat;
}
void FlatInvertibleLabframePhasespace::persistentInput(PersistentIStream & is, int) {
is >> theLogSHat;
}
// *** Attention *** The following static variable is needed for the type
// description system in ThePEG. Please check that the template arguments
// are correct (the class and its base class), and that the constructor
// arguments are correct (the class name and the name of the dynamically
// loadable library where the class implementation can be found).
DescribeClass<FlatInvertibleLabframePhasespace,MatchboxPhasespace>
describeHerwigFlatInvertibleLabframePhasespace("Herwig::FlatInvertibleLabframePhasespace", "Herwig.so");
void FlatInvertibleLabframePhasespace::Init() {
static ClassDocumentation<FlatInvertibleLabframePhasespace> documentation
("FlatInvertibleLabframePhasespace implements flat, invertible phase space generation in the lab frame.");
static Switch<FlatInvertibleLabframePhasespace,bool> interfaceLogSHat
("LogSHat",
"Generate a flat distribution in \\f$\\log(\\hat{s})\\f$.",
&FlatInvertibleLabframePhasespace::theLogSHat, false, false, false);
static SwitchOption interfaceLogSHatOn
(interfaceLogSHat,
"True", "Generate flat in \\f$\\log(\\hat{s})\\f$", true);
static SwitchOption interfaceLogSHatOff
(interfaceLogSHat,
"False", "Generate flat in \\f$\\hat{s}\\f$", false);
interfaceLogSHat.rank(-1);
}
diff --git a/MatrixElement/Matchbox/Phasespace/FlatInvertiblePhasespace.cc b/MatrixElement/Matchbox/Phasespace/FlatInvertiblePhasespace.cc
--- a/MatrixElement/Matchbox/Phasespace/FlatInvertiblePhasespace.cc
+++ b/MatrixElement/Matchbox/Phasespace/FlatInvertiblePhasespace.cc
@@ -1,307 +1,304 @@
// -*- C++ -*-
//
// FlatInvertiblePhasespace.cc is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
//
// This is the implementation of the non-inlined, non-templated member
// functions of the FlatInvertiblePhasespace class.
//
#include "FlatInvertiblePhasespace.h"
#include "ThePEG/Interface/ClassDocumentation.h"
#include "ThePEG/Interface/Switch.h"
#include "ThePEG/EventRecord/Particle.h"
#include "ThePEG/Repository/UseRandom.h"
#include "ThePEG/Repository/EventGenerator.h"
#include "ThePEG/Utilities/DescribeClass.h"
#include "Herwig/Utilities/GSLBisection.h"
#include "ThePEG/Cuts/Cuts.h"
#include "ThePEG/Persistency/PersistentOStream.h"
#include "ThePEG/Persistency/PersistentIStream.h"
using namespace Herwig;
FlatInvertiblePhasespace::FlatInvertiblePhasespace() {}
FlatInvertiblePhasespace::~FlatInvertiblePhasespace() {}
IBPtr FlatInvertiblePhasespace::clone() const {
return new_ptr(*this);
}
IBPtr FlatInvertiblePhasespace::fullclone() const {
return new_ptr(*this);
}
double FlatInvertiblePhasespace::bisect(double v, double n,
double target, double maxLevel) const {
if ( v != 0.0 && v != 1.0 ) {
double level = 0;
double left = 0;
double right = 1;
double checkV = -1.;
double u = -1;
while ( level < maxLevel ) {
u = (left+right)*pow(0.5,level+1.);
checkV =
pow(u,n+1.)*(n+2.-(n+1.)*u);
if ( log10(abs(1.-checkV/v)) <= target )
break;
left *= 2.;
right *= 2.;
if ( v <= checkV ) {
right -= 1.;
++level;
}
if ( v > checkV ) {
left += 1.;
++level;
}
}
return u;
}
return v;
}
-static double flatWeights[7] = {
-
- -1.,-1.,
- 0.039788735772973833942,
- 0.00012598255637968550463,
- 1.3296564302788840628E-7,
- 7.0167897579949011130E-11,
- 2.2217170114046130768E-14
-
-};
-
double FlatInvertiblePhasespace::generateIntermediates(vector<Energy>& K,
const double* r) const {
size_t n = K.size() + 1;
+
+
for ( size_t i = 2; i <= n-1; ++i ) {
double u = bisect(r[i-2],n-1-i);
K[i-1] = sqrt(u*sqr(K[i-2]));
}
-
- return flatWeights[n];
+
+ int kap = K.size() + 1;
+
+ return flatWeights(kap);
}
double FlatInvertiblePhasespace::invertIntermediates(const vector<Energy>& K,
double* r) const {
size_t n = K.size() + 1;
for ( size_t i = 2; i <= n-1; ++i ) {
double u = sqr(K[i-1]/K[i-2]);
r[i-2] = (n+1-i)*pow(u,(double)(n-i)) - (n-i)*pow(u,(double)(n+1-i));
}
- return flatWeights[n];
+ int kap = K.size() + 1;
+ return flatWeights(kap);
}
double FlatInvertiblePhasespace::generateIntermediates(vector<Energy>& M,
const vector<Energy>& m,
const double* r) const {
size_t n = M.size() + 1;
vector<Energy> K = M;
for ( size_t i = 1; i <= n; ++i )
K[0] -= m[i-1];
double w0 = generateIntermediates(K,r);
M = K;
for ( size_t i = 1; i <= n-1; ++i ) {
for ( size_t k = i; k <= n; ++k )
M[i-1] += m[k-1];
}
double weight = 8.*w0*rho(M[n-2],m[n-1],m[n-2]);
for ( size_t i = 2; i <= n-1; ++i ) {
weight *=
(rho(M[i-2],M[i-1],m[i-2])/rho(K[i-2],K[i-1],ZERO)) * (M[i-1]/K[i-1]);
}
weight *= pow(K[0]/M[0],2.*n-4.);
-
+
return weight;
}
double FlatInvertiblePhasespace::invertIntermediates(const vector<Energy>& M,
const vector<Energy>& m,
double* r) const {
size_t n = M.size() + 1;
vector<Energy> K = M;
for ( size_t i = 1; i <= n-1; ++i ) {
for ( size_t k = i; k <= n; ++k )
K[i-1] -= m[k-1];
}
double w0 = invertIntermediates(K,r);
double weight = 8.*w0*rho(M[n-2],m[n-1],m[n-2]);
for ( size_t i = 2; i <= n-1; ++i ) {
weight *=
(rho(M[i-2],M[i-1],m[i-2])/rho(K[i-2],K[i-1],ZERO)) * (M[i-1]/K[i-1]);
}
weight *= pow(K[0]/M[0],2.*n-4.);
return weight;
}
double FlatInvertiblePhasespace::generateKinematics(vector<Lorentz5Momentum>& P,
Energy Ecm,
const double* r) const {
vector<Energy> m;
for ( vector<Lorentz5Momentum>::const_iterator p =
P.begin() + 2; p != P.end(); ++p )
m.push_back(p->mass());
size_t n = P.size() - 2;
vector<Energy> M(n-1);
M[0] = Ecm;
double weight = generateIntermediates(M,m,r);
M.push_back(m.back());
Lorentz5Momentum Q(M[0]);
Lorentz5Momentum nextQ;
for ( size_t i = 2; i <= n; ++i ) {
Energy q = 4.*M[i-2]*rho(M[i-2],M[i-1],m[i-2]);
double c = 2.*r[n-6+2*i]-1.;
double s = sqrt(1.-sqr(c));
double phi = 2.*Constants::pi*r[n-5+2*i];
double cphi = cos(phi);
double sphi = sqrt(1.-sqr(cphi));
if ( phi > Constants::pi )
sphi = -sphi;
P[i].setX(q*cphi*s);
P[i].setY(q*sphi*s);
P[i].setZ(q*c);
P[i].rescaleEnergy();
P[i].boost(Q.boostVector());
P[i].rescaleEnergy();
nextQ = Q - P[i];
nextQ.setMass(M[i-1]);
nextQ.rescaleEnergy();
Q = nextQ;
}
P.back() = Q;
return weight;
}
double FlatInvertiblePhasespace::invertKinematics(const vector<Lorentz5Momentum>& P,
Energy Ecm,
double* r) const {
vector<Energy> m;
for ( vector<Lorentz5Momentum>::const_iterator p =
P.begin() + 2; p != P.end(); ++p )
m.push_back(p->mass());
size_t n = P.size() - 2;
vector<Energy> M(n-1);
M[0] = Ecm;
vector<Lorentz5Momentum> Q(n-1);
Q[0] = Lorentz5Momentum(M[0]);
for ( size_t i = 2; i <= n-1; ++i ) {
for ( size_t k = i; k <= n; ++k )
Q[i-1] += P[k+1];
M[i-1] = Q[i-1].m();
}
double weight = invertIntermediates(M,m,r);
for ( size_t i = 2; i <= n; ++i ) {
Lorentz5Momentum p = P[i];
p.boost(-Q[i-2].boostVector());
r[n-6+2*i] = (p.cosTheta()+1.)/2.;
double phi = p.phi();
if ( phi < 0. )
phi = 2.*Constants::pi + phi;
r[n-5+2*i] = phi/(2.*Constants::pi);
}
return weight;
}
double FlatInvertiblePhasespace::generateTwoToNKinematics(const double* r,
vector<Lorentz5Momentum>& momenta) {
double weight = generateKinematics(momenta,sqrt(lastXCombPtr()->lastSHat()),r);
-
- fillDiagramWeights();
-
return weight;
}
+long double FlatInvertiblePhasespace::flatWeights(int k) const{
+ using Constants::pi;
+ if(k<2) { return -1;
+ } else return pow((pi/2),(k-1)) * pow((2*pi),(4-3*k))/factorial(k-1)/factorial(k-2);
+}
+
// If needed, insert default implementations of virtual function defined
// in the InterfacedBase class here (using ThePEG-interfaced-impl in Emacs).
void FlatInvertiblePhasespace::persistentOutput(PersistentOStream &) const {}
void FlatInvertiblePhasespace::persistentInput(PersistentIStream &, int) {}
// *** Attention *** The following static variable is needed for the type
// description system in ThePEG. Please check that the template arguments
// are correct (the class and its base class), and that the constructor
// arguments are correct (the class name and the name of the dynamically
// loadable library where the class implementation can be found).
DescribeClass<FlatInvertiblePhasespace,MatchboxPhasespace>
describeHerwigFlatInvertiblePhasespace("Herwig::FlatInvertiblePhasespace", "Herwig.so");
void FlatInvertiblePhasespace::Init() {
static ClassDocumentation<FlatInvertiblePhasespace> documentation
("FlatInvertiblePhasespace implements flat, invertible phase space generation.");
}
diff --git a/MatrixElement/Matchbox/Phasespace/FlatInvertiblePhasespace.h b/MatrixElement/Matchbox/Phasespace/FlatInvertiblePhasespace.h
--- a/MatrixElement/Matchbox/Phasespace/FlatInvertiblePhasespace.h
+++ b/MatrixElement/Matchbox/Phasespace/FlatInvertiblePhasespace.h
@@ -1,194 +1,204 @@
// -*- C++ -*-
//
// FlatInvertiblePhasespace.h is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
#ifndef Herwig_FlatInvertiblePhasespace_H
#define Herwig_FlatInvertiblePhasespace_H
//
// This is the declaration of the FlatInvertiblePhasespace class.
//
#include "Herwig/MatrixElement/Matchbox/Phasespace/MatchboxPhasespace.h"
namespace Herwig {
using namespace ThePEG;
/**
* \ingroup Matchbox
* \author Simon Platzer
*
* \brief FlatInvertiblePhasespace implements flat, invertible phase space generation.
*
*/
class FlatInvertiblePhasespace: public MatchboxPhasespace {
public:
/** @name Standard constructors and destructors. */
//@{
/**
* The default constructor.
*/
FlatInvertiblePhasespace();
/**
* The destructor.
*/
virtual ~FlatInvertiblePhasespace();
//@}
public:
/**
* Generate a phase space point and return its weight.
*/
virtual double generateTwoToNKinematics(const double*,
vector<Lorentz5Momentum>& momenta);
/**
* Return the number of random numbers required to produce a given
* multiplicity final state.
*/
virtual int nDimPhasespace(int nFinal) const {
if ( nFinal == 1 )
return 1;
return 3*nFinal - 4;
}
public:
/**
* Return true, if this phase space generator is invertible
*/
virtual bool isInvertible() const { return true; }
/**
* Invert the given phase space point to the random numbers which
* would have generated it.
*/
virtual double invertTwoToNKinematics(const vector<Lorentz5Momentum>& momenta,
double* r) const {
return invertKinematics(momenta,(momenta[0]+momenta[1]).m(),r);
}
private:
/**
* Solve v = (n+2) * u^(n+1) - (n+1) * u^(n+2) for u
*/
double bisect(double v, double n,
double target = -16., double maxLevel = 80.) const;
/**
* Return rho
*/
double rho(Energy M, Energy N, Energy m) const {
return sqrt((sqr(M)-sqr(N+m))*(sqr(M)-sqr(N-m)))/(8.*sqr(M));
}
/**
* Generate intermediate masses for a massless final state
*/
double generateIntermediates(vector<Energy>& K,
const double* r) const;
/**
* Invert intermediate masses for a massless final state
*/
double invertIntermediates(const vector<Energy>& K,
double* r) const;
/**
* Generate intermediate masses for a massive final state
*/
double generateIntermediates(vector<Energy>& M,
const vector<Energy>& m,
const double* r) const;
/**
* Invert intermediate masses for a massive final state
*/
double invertIntermediates(const vector<Energy>& M,
const vector<Energy>& m,
double* r) const;
/**
* Generate momenta in the CMS
*/
double generateKinematics(vector<Lorentz5Momentum>& P,
Energy Ecm,
const double* r) const;
/**
* Invert momenta in the CMS
*/
double invertKinematics(const vector<Lorentz5Momentum>& P,
Energy Ecm,
double* r) const;
+ /**
+ * Return the appropriate phase space weight,
+ * Eq. 11 in 1308.2922
+ * with the factor (2 pi)^4/(2 pi)^(3n) included
+ * and the SHat of the process divided out to have everything expressed in the units of the ThePEG conventions, i.e.
+ * without the Q^2 factor
+ */
+
+ long double flatWeights(int n) const;
+
public:
/** @name Functions used by the persistent I/O system. */
//@{
/**
* Function used to write out object persistently.
* @param os the persistent output stream written to.
*/
void persistentOutput(PersistentOStream & os) const;
/**
* Function used to read in object persistently.
* @param is the persistent input stream read from.
* @param version the version number of the object when written.
*/
void persistentInput(PersistentIStream & is, int version);
//@}
/**
* The standard Init function used to initialize the interfaces.
* Called exactly once for each class by the class description system
* before the main function starts or
* when this class is dynamically loaded.
*/
static void Init();
protected:
/** @name Clone Methods. */
//@{
/**
* Make a simple clone of this object.
* @return a pointer to the new object.
*/
virtual IBPtr clone() const;
/** Make a clone of this object, possibly modifying the cloned object
* to make it sane.
* @return a pointer to the new object.
*/
virtual IBPtr fullclone() const;
//@}
// If needed, insert declarations of virtual function defined in the
// InterfacedBase class here (using ThePEG-interfaced-decl in Emacs).
private:
/**
* The assignment operator is private and must never be called.
* In fact, it should not even be implemented.
*/
FlatInvertiblePhasespace & operator=(const FlatInvertiblePhasespace &);
};
}
#endif /* Herwig_FlatInvertiblePhasespace_H */
diff --git a/MatrixElement/Matchbox/Phasespace/MatchboxPhasespace.cc b/MatrixElement/Matchbox/Phasespace/MatchboxPhasespace.cc
--- a/MatrixElement/Matchbox/Phasespace/MatchboxPhasespace.cc
+++ b/MatrixElement/Matchbox/Phasespace/MatchboxPhasespace.cc
@@ -1,552 +1,565 @@
// -*- C++ -*-
//
// MatchboxPhasespace.cc is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
//
// This is the implementation of the non-inlined, non-templated member
// functions of the MatchboxPhasespace class.
//
#include "MatchboxPhasespace.h"
#include "ThePEG/Interface/ClassDocumentation.h"
#include "ThePEG/Interface/Parameter.h"
#include "ThePEG/Interface/Switch.h"
#include "ThePEG/Interface/Command.h"
#include "ThePEG/Interface/Reference.h"
#include "ThePEG/EventRecord/Particle.h"
#include "ThePEG/Repository/UseRandom.h"
#include "ThePEG/Repository/EventGenerator.h"
#include "ThePEG/Utilities/DescribeClass.h"
#include "Herwig/MatrixElement/Matchbox/Utility/ProcessData.h"
#include "Herwig/MatrixElement/Matchbox/MatchboxFactory.h"
using namespace Herwig;
MatchboxPhasespace::MatchboxPhasespace()
: singularCutoff(10*GeV), theUseMassGenerators(false),
theLoopParticleIdMin(200001), theLoopParticleIdMax(200100) {}
MatchboxPhasespace::~MatchboxPhasespace() {}
void MatchboxPhasespace::cloneDependencies(const std::string&) {}
Ptr<MatchboxFactory>::tcptr MatchboxPhasespace::factory() const {
return lastMatchboxXComb()->factory();
}
Ptr<ProcessData>::tptr MatchboxPhasespace::processData() const {
return factory()->processData();
}
double MatchboxPhasespace::generateKinematics(const double* r,
vector<Lorentz5Momentum>& momenta) {
+ diagramWeights().clear();
+
cPDVector::const_iterator pd = mePartonData().begin() + 2;
vector<Lorentz5Momentum>::iterator p = momenta.begin() + 2;
double massJacobian = 1.;
Energy summ = ZERO;
if ( useMassGenerators() ) {
Energy gmass = ZERO;
tGenericMassGeneratorPtr mgen;
Energy maxMass =
(!haveX1X2() && momenta.size() > 3) ?
sqrt(lastSHat()) : sqrt(lastS());
for ( ; pd != mePartonData().end(); ++pd, ++p ) {
mgen = processData()->massGenerator(*pd);
if ( mgen && !isInvertible() ) {
Energy massMax = min((**pd).massMax(),maxMass);
Energy massMin = (**pd).massMin();
if ( massMin > massMax )
return 0.0;
gmass = mgen->mass(massJacobian,**pd,massMin,massMax,r[0]);
++r;
} else if ( (**pd).hardProcessWidth() != ZERO ) {
Energy massMax = min((**pd).massMax(),maxMass);
Energy massMin = (**pd).massMin();
if ( massMin > massMax )
return 0.0;
// use a standard Breit Wigner here which we can invert
// see invertKinematics as well
double bwILow =
atan((sqr(massMin)-sqr((**pd).hardProcessMass()))/((**pd).hardProcessMass() * (**pd).hardProcessWidth()));
double bwIUp =
atan((sqr(massMax)-sqr((**pd).hardProcessMass()))/((**pd).hardProcessMass() * (**pd).hardProcessWidth()));
gmass = sqrt(sqr((**pd).hardProcessMass()) +
(**pd).hardProcessMass()*(**pd).hardProcessWidth()*tan(bwILow+r[0]*(bwIUp-bwILow)));
++r;
} else {
gmass = (**pd).hardProcessMass();
}
maxMass -= gmass;
p->setMass(gmass);
summ += gmass;
}
} else {
for ( ; pd != mePartonData().end(); ++pd, ++p ) {
summ += (**pd).hardProcessMass();
p->setMass((**pd).hardProcessMass());
}
}
if ( momenta.size() > 3 && !haveX1X2() ) {
if ( summ > (momenta[0]+momenta[1]).m() )
return 0.0;
}
double weight = momenta.size() > 3 ?
generateTwoToNKinematics(r,momenta) :
generateTwoToOneKinematics(r,momenta);
+ fillDiagramWeights();
+
return weight*massJacobian;
}
double MatchboxPhasespace::generateTwoToOneKinematics(const double* r,
vector<Lorentz5Momentum>& momenta) {
double tau = momenta[2].mass2()/lastXCombPtr()->lastS();
double ltau = log(tau)/2.;
- double y = ltau - 2.*r[0]*ltau;
- double x1 = sqrt(tau)*exp(y);
- double x2 = sqrt(tau)*exp(-y);
+ //old: y = ltau - 2.*r[0]*ltau; x1 = sqrt(tau)*exp(y); x2 = sqrt(tau)*exp(-y);
+ double x1=pow(tau,1.-r[0]);
+ double x2=pow(tau,r[0]);
- ThreeVector<Energy> p1 =
- x1*(lastXCombPtr()->lastParticles().first->momentum().vect());
+ // Due to the proton mass and P1.e() + P2.e() == lastS() we multiply here
+ // with the correction factor abs(P1.e()/P1.z()) to produce incoming
+ // p1/2 = (e1/2,0,0,+/- e1/2)
+ Lorentz5Momentum P1 = lastXCombPtr()->lastParticles().first->momentum();
+ ThreeVector<Energy> p1 = x1 * (P1.vect()) * abs(P1.e()/P1.z());
- ThreeVector<Energy> p2 =
- x2*(lastXCombPtr()->lastParticles().second->momentum().vect());
+ Lorentz5Momentum P2 = lastXCombPtr()->lastParticles().second->momentum();
+ ThreeVector<Energy> p2 = x2 * (P2.vect()) * abs(P2.e()/P2.z());
ThreeVector<Energy> q = p1 + p2;
momenta[0] = Lorentz5Momentum(momenta[0].mass(),p1);
momenta[1] = Lorentz5Momentum(momenta[1].mass(),p2);
momenta[2] = Lorentz5Momentum(momenta[2].mass(),q);
+
+ // check for energy conservation:
+ if ((momenta[0]+momenta[1]-momenta[2]).e()>pow(10,-9)*GeV)
+ generator()->log()
+ << "Warning: Momentum conservation in generateTwoToOneKinematics not precise.\n"
+ << flush;
+
- lastXCombPtr()->lastX1X2(make_pair(x1,x2));
+ lastXCombPtr()->lastX1X2({x1,x2});
lastXCombPtr()->lastSHat((momenta[0]+momenta[1]).m2());
- fillDiagramWeights();
-
return -4.*Constants::pi*ltau;
}
double MatchboxPhasespace::invertKinematics(const vector<Lorentz5Momentum>& momenta,
double* r) const {
if ( useMassGenerators() ) {
Energy gmass = ZERO;
Energy maxMass =
(!haveX1X2() && momenta.size() > 3) ?
sqrt((momenta[0]+momenta[1]).m2()) : sqrt(lastS());
cPDVector::const_iterator pd = mePartonData().begin() + 2;
vector<Lorentz5Momentum>::const_iterator p = momenta.begin() + 2;
for ( ; pd != mePartonData().end(); ++pd, ++p ) {
if ( (**pd).hardProcessWidth() != ZERO ) {
Energy massMax = min((**pd).massMax(),maxMass);
Energy massMin = (**pd).massMin();
if ( massMin > massMax )
return 0.0;
double bwILow =
atan((sqr(massMin)-sqr((**pd).hardProcessMass()))/((**pd).hardProcessMass() * (**pd).hardProcessWidth()));
double bwIUp =
atan((sqr(massMax)-sqr((**pd).hardProcessMass()))/((**pd).hardProcessMass() * (**pd).hardProcessWidth()));
gmass = p->mass();
double bw =
atan((sqr(gmass)-sqr((**pd).hardProcessMass()))/((**pd).hardProcessMass() * (**pd).hardProcessWidth()));
r[0] = (bw-bwILow)/(bwIUp-bwILow);
++r;
} else {
gmass = (**pd).hardProcessMass();
}
maxMass -= gmass;
}
}
return momenta.size() > 3 ?
invertTwoToNKinematics(momenta,r) :
invertTwoToOneKinematics(momenta,r);
}
double MatchboxPhasespace::invertTwoToOneKinematics(const vector<Lorentz5Momentum>& momenta,
double* r) const {
double tau = momenta[2].mass2()/lastXCombPtr()->lastS();
double ltau = log(tau)/2.;
r[0] = (ltau - (momenta[0]+momenta[1]).rapidity())/(2.*ltau);
return -4.*Constants::pi*ltau;
}
void MatchboxPhasespace::setCoupling(long a, long b, long c,
double coupling, bool includeCrossings) {
cPDPtr A = getParticleData(a);
cPDPtr B = getParticleData(b);
cPDPtr C = getParticleData(c);
if ( !A || !B || !C ) {
generator()->log() << "Warning: could not determine particle data for ids "
<< a << " " << b << " " << c << " when setting coupling in MatchboxPhasespace.\n"
<< flush;
return;
}
if ( !includeCrossings ) {
theCouplings->couplings()[LTriple(a,b,c)] = coupling;
return;
}
if ( A->CC() ) {
theCouplings->couplings()[LTriple(-a,b,c)] = coupling;
theCouplings->couplings()[LTriple(-a,c,b)] = coupling;
} else {
theCouplings->couplings()[LTriple(a,b,c)] = coupling;
theCouplings->couplings()[LTriple(a,c,b)] = coupling;
}
if ( B->CC() ) {
theCouplings->couplings()[LTriple(-b,a,c)] = coupling;
theCouplings->couplings()[LTriple(-b,c,a)] = coupling;
} else {
theCouplings->couplings()[LTriple(b,a,c)] = coupling;
theCouplings->couplings()[LTriple(b,c,a)] = coupling;
}
if ( C->CC() ) {
theCouplings->couplings()[LTriple(-c,a,b)] = coupling;
theCouplings->couplings()[LTriple(-c,b,a)] = coupling;
} else {
theCouplings->couplings()[LTriple(c,a,b)] = coupling;
theCouplings->couplings()[LTriple(c,b,a)] = coupling;
}
}
string MatchboxPhasespace::doSetCoupling(string in) {
istringstream is(in);
long a,b,c; double coupling;
is >> a >> b >> c >> coupling;
if ( !is )
return "MatchboxPhasespace: error in setting coupling.";
setCoupling(a,b,c,coupling,true);
return "";
}
string MatchboxPhasespace::doSetPhysicalCoupling(string in) {
istringstream is(in);
long a,b,c; double coupling;
is >> a >> b >> c >> coupling;
if ( !is )
return "MatchboxPhasespace: error in setting coupling.";
setCoupling(a,b,c,coupling,false);
return "";
}
pair<double,Lorentz5Momentum>
MatchboxPhasespace::timeLikeWeight(const Tree2toNDiagram& diag,
int branch, double flatCut) const {
pair<int,int> children = diag.children(branch);
if ( children.first == -1 ) {
return make_pair(1.,meMomenta()[diag.externalId(branch)]);
}
pair<double,Lorentz5Momentum> res
= timeLikeWeight(diag,children.first,flatCut);
pair<double,Lorentz5Momentum> other
= timeLikeWeight(diag,children.second,flatCut);
res.first *= other.first;
res.second += other.second;
LTriple vertexKey(diag.allPartons()[branch]->id(),
diag.allPartons()[children.first]->id(),
diag.allPartons()[children.second]->id());
map<LTriple,double>::const_iterator cit = theCouplings->couplings().find(vertexKey);
if ( cit != theCouplings->couplings().end() ){
res.first *= cit->second;
}
Energy2 mass2 = sqr(diag.allPartons()[branch]->hardProcessMass());
Energy2 width2 = sqr(diag.allPartons()[branch]->hardProcessWidth());
if ( abs(diag.allPartons()[branch]->id()) >= theLoopParticleIdMin
&& abs(diag.allPartons()[branch]->id()) <= theLoopParticleIdMax ) { // "loop particle"
if ( abs((res.second.m2()-mass2)/lastSHat()) > flatCut ) {
res.first /=
abs((res.second.m2()-mass2)/GeV2);
res.first *=
log(abs((res.second.m2()-mass2)/GeV2)); // normal. of the argument in the log?
}
} else {
if ( width2 == ZERO ) {
if ( abs((res.second.m2()-mass2)/lastSHat()) > flatCut )
res.first /=
abs((res.second.m2()-mass2)/GeV2);
} else {
res.first /=
(sqr((res.second.m2()-mass2)/GeV2) +
mass2*width2/sqr(GeV2))/(abs(res.second.m2()/GeV2));
}
}
return res;
}
double MatchboxPhasespace::spaceLikeWeight(const Tree2toNDiagram& diag,
const Lorentz5Momentum& incoming,
int branch, double flatCut) const {
if ( branch == -1 )
return 1.;
pair<int,int> children = diag.children(branch);
pair<double,Lorentz5Momentum> res =
timeLikeWeight(diag,children.second,flatCut);
LTriple vertexKey(diag.allPartons()[branch]->id(),
diag.allPartons()[children.first]->id(),
diag.allPartons()[children.second]->id());
if ( children.first == diag.nSpace() - 1 ) {
if ( diag.allPartons()[children.first]->CC() )
vertexKey = LTriple(diag.allPartons()[branch]->id(),
diag.allPartons()[children.second]->id(),
diag.allPartons()[children.first]->CC()->id());
else
vertexKey = LTriple(diag.allPartons()[branch]->id(),
diag.allPartons()[children.second]->id(),
diag.allPartons()[children.first]->id());
}
map<LTriple,double>::const_iterator cit = theCouplings->couplings().find(vertexKey);
if ( cit != theCouplings->couplings().end() ){
res.first *= cit->second;
}
if ( children.first == diag.nSpace() - 1 ) {
return res.first;
}
res.second = incoming - res.second;
Energy2 mass2 = sqr(diag.allPartons()[children.first]->hardProcessMass());
Energy2 width2 = sqr(diag.allPartons()[children.first]->hardProcessWidth());
if ( abs(diag.allPartons()[children.first]->id()) >= theLoopParticleIdMin
&& (diag.allPartons()[children.first]->id()) <= theLoopParticleIdMax ) { // "loop particle"
if ( abs((res.second.m2()-mass2)/lastSHat()) > flatCut ) {
res.first /=
abs((res.second.m2()-mass2)/GeV2);
res.first *=
log(abs((res.second.m2()-mass2)/GeV2)); // normal. of the argument in the log?
}
} else {
if ( width2 == ZERO ) {
if ( abs((res.second.m2()-mass2)/lastSHat()) > flatCut )
res.first /=
abs((res.second.m2()-mass2)/GeV2);
} else {
res.first /=
(sqr((res.second.m2()-mass2)/GeV2) +
mass2*width2/sqr(GeV2))/(abs(res.second.m2()/GeV2));
}
}
return
res.first * spaceLikeWeight(diag,res.second,children.first,flatCut);
}
void MatchboxPhasespace::fillDiagramWeights(double flatCut) {
- diagramWeights().clear();
+ if ( !diagramWeights().empty() )
+ return;
for ( auto & d : lastXComb().diagrams() ) {
diagramWeights()[d->id()] =
spaceLikeWeight(dynamic_cast<const Tree2toNDiagram&>(*d),meMomenta()[0],0,flatCut);
}
}
Selector<MEBase::DiagramIndex>
MatchboxPhasespace::selectDiagrams(const MEBase::DiagramVector& diags) const {
Selector<MEBase::DiagramIndex> ret;
for ( MEBase::DiagramIndex d = 0; d < diags.size(); ++d ) {
ret.insert(diagramWeight(dynamic_cast<const Tree2toNDiagram&>(*diags[d])),d);
}
return ret;
}
bool MatchboxPhasespace::matchConstraints(const vector<Lorentz5Momentum>& momenta) {
if ( singularLimits().empty() )
return true;
lastSingularLimit() = singularLimits().begin();
for ( ; lastSingularLimit() != singularLimits().end(); ++lastSingularLimit() ) {
if ( lastSingularLimit()->first == lastSingularLimit()->second &&
momenta[lastSingularLimit()->first].t() < singularCutoff )
break;
if ( lastSingularLimit()->first != lastSingularLimit()->second &&
sqrt(momenta[lastSingularLimit()->first]*
momenta[lastSingularLimit()->second]) < singularCutoff ) {
bool match = true;
for ( set<pair<size_t,size_t> >::const_iterator other =
singularLimits().begin(); other != singularLimits().end(); ++other ) {
if ( other == lastSingularLimit() )
continue;
if ( other->first == other->second &&
momenta[other->first].t() < singularCutoff ) {
match = false;
break;
}
if ( other->first != other->second &&
sqrt(momenta[other->first]*
momenta[other->second]) < singularCutoff ) {
match = false;
break;
}
}
if ( match )
break;
}
}
return lastSingularLimit() != singularLimits().end();
}
int MatchboxPhasespace::nDim(const cPDVector& data) const {
int ndimps = nDimPhasespace(data.size()-2);
if ( useMassGenerators() ) {
for ( cPDVector::const_iterator pd = data.begin();
pd != data.end(); ++pd ) {
if ( (**pd).massGenerator() ||
(**pd).hardProcessWidth() != ZERO ) {
++ndimps;
}
}
}
return ndimps;
}
// If needed, insert default implementations of virtual function defined
// in the InterfacedBase class here (using ThePEG-interfaced-impl in Emacs).
void MatchboxPhasespace::persistentOutput(PersistentOStream & os) const {
os << theLastXComb
<< ounit(singularCutoff,GeV) << theUseMassGenerators
<< theLoopParticleIdMin << theLoopParticleIdMax
<< theCouplings;
}
void MatchboxPhasespace::persistentInput(PersistentIStream & is, int) {
is >> theLastXComb
>> iunit(singularCutoff,GeV) >> theUseMassGenerators
>> theLoopParticleIdMin >> theLoopParticleIdMax
>> theCouplings;
lastMatchboxXComb(theLastXComb);
}
// *** Attention *** The following static variable is needed for the type
// description system in ThePEG. Please check that the template arguments
// are correct (the class and its base class), and that the constructor
// arguments are correct (the class name and the name of the dynamically
// loadable library where the class implementation can be found).
DescribeAbstractClass<MatchboxPhasespace,HandlerBase>
describeMatchboxPhasespace("Herwig::MatchboxPhasespace", "Herwig.so");
void MatchboxPhasespace::Init() {
static ClassDocumentation<MatchboxPhasespace> documentation
("MatchboxPhasespace defines an abstract interface to a phase "
"space generator.");
static Parameter<MatchboxPhasespace,Energy> interfaceSingularCutoff
("SingularCutoff",
"[debug] Cutoff below which a region is considered singular.",
&MatchboxPhasespace::singularCutoff, GeV, 10.0*GeV, 0.0*GeV, 0*GeV,
false, false, Interface::lowerlim);
interfaceSingularCutoff.rank(-1);
/*
static Switch<MatchboxPhasespace,bool> interfaceUseMassGenerators
("UseMassGenerators",
"Use mass generators instead of fixed masses.",
&MatchboxPhasespace::theUseMassGenerators, false, false, false);
static SwitchOption interfaceUseMassGeneratorsYes
(interfaceUseMassGenerators,
"Yes",
"Use mass generators.",
true);
static SwitchOption interfaceUseMassGeneratorsNo
(interfaceUseMassGenerators,
"No",
"Do not use mass generators.",
false);
*/
static Command<MatchboxPhasespace> interfaceSetCoupling
("SetCoupling",
"",
&MatchboxPhasespace::doSetCoupling, false);
static Command<MatchboxPhasespace> interfaceSetPhysicalCoupling
("SetPhysicalCoupling",
"",
&MatchboxPhasespace::doSetPhysicalCoupling, false);
static Parameter<MatchboxPhasespace,int> interfaceLoopParticleIdMin
("LoopParticleIdMin",
"First id in a range of id's meant to denote fictitious "
"'ghost' particles to be used by the diagram generator "
"in loop induced processes.",
&MatchboxPhasespace::theLoopParticleIdMin, 200001, 0, 0,
false, false, Interface::lowerlim);
interfaceLoopParticleIdMin.rank(-1);
static Parameter<MatchboxPhasespace,int> interfaceLoopParticleIdMax
("LoopParticleIdMax",
"Last id in a range of id's meant to denote fictitious "
"'ghost' particles to be used by the diagram generator "
"in loop induced processes.",
&MatchboxPhasespace::theLoopParticleIdMax, 200100, 0, 0,
false, false, Interface::lowerlim);
interfaceLoopParticleIdMax.rank(-1);
static Reference<MatchboxPhasespace,PhasespaceCouplings> interfaceCouplingData
("CouplingData",
"Set the storage for the couplings.",
&MatchboxPhasespace::theCouplings, false, false, true, false, false);
interfaceCouplingData.rank(-1);
}
diff --git a/MatrixElement/Matchbox/Phasespace/MatchboxPhasespace.h b/MatrixElement/Matchbox/Phasespace/MatchboxPhasespace.h
--- a/MatrixElement/Matchbox/Phasespace/MatchboxPhasespace.h
+++ b/MatrixElement/Matchbox/Phasespace/MatchboxPhasespace.h
@@ -1,359 +1,366 @@
// -*- C++ -*-
//
// MatchboxPhasespace.h is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
#ifndef HERWIG_MatchboxPhasespace_H
#define HERWIG_MatchboxPhasespace_H
//
// This is the declaration of the MatchboxPhasespace class.
//
#include "ThePEG/Handlers/StandardXComb.h"
#include "ThePEG/Handlers/HandlerBase.h"
#include "ThePEG/MatrixElement/Tree2toNDiagram.h"
#include "Herwig/MatrixElement/Matchbox/Utility/LastMatchboxXCombInfo.h"
#include "Herwig/MatrixElement/Matchbox/Utility/ProcessData.fh"
#include "Herwig/MatrixElement/Matchbox/MatchboxFactory.fh"
#include "Herwig/MatrixElement/Matchbox/Phasespace/PhasespaceCouplings.h"
namespace Herwig {
using namespace ThePEG;
/**
* \ingroup Matchbox
* \author Simon Platzer
*
* \brief Wrap around a vector of random numbers to behave as a stream
* of those.
*/
struct StreamingRnd {
/**
* The random numbers
*/
const double* numbers;
/**
* The number of random numbers available.
*/
size_t nRnd;
/**
* Default constructor.
*/
StreamingRnd()
: numbers(0), nRnd(0) {}
/**
* Construct from random numbers.
*/
explicit StreamingRnd(const double* newNumbers,
size_t n)
: numbers(newNumbers), nRnd(n) {}
/**
* Return next random number
*/
inline double operator()() {
assert(numbers && nRnd > 0);
const double ret = numbers[0];
++numbers; --nRnd;
return ret;
}
};
/**
* \ingroup Matchbox
* \author Simon Platzer
*
* \brief MatchboxPhasespace defines an abstract interface to a phase
* space generator.
*
*/
class MatchboxPhasespace:
public HandlerBase,
public LastXCombInfo<StandardXComb>,
public LastMatchboxXCombInfo {
public:
/** @name Standard constructors and destructors. */
//@{
/**
* The default constructor.
*/
MatchboxPhasespace();
/**
* The destructor.
*/
virtual ~MatchboxPhasespace();
//@}
public:
/**
* Set the XComb object steering the Born matrix
* element this class represents virtual corrections to.
*/
virtual void setXComb(tStdXCombPtr xc) {
theLastXComb = xc;
lastMatchboxXComb(xc);
}
/**
* Return the factory object
*/
Ptr<MatchboxFactory>::tcptr factory() const;
/**
* Return the process data object
*/
Ptr<ProcessData>::tptr processData() const;
/**
* Generate a phase space point and return its weight.
*/
virtual double generateKinematics(const double* r,
vector<Lorentz5Momentum>& momenta);
/**
* Generate a phase space point and return its weight.
*/
virtual double generateTwoToNKinematics(const double*,
vector<Lorentz5Momentum>& momenta) = 0;
/**
* Generate a 2 -> 1 phase space point and return its weight.
*/
virtual double generateTwoToOneKinematics(const double*,
vector<Lorentz5Momentum>& momenta);
/**
* Return the number of random numbers required to produce a given
* multiplicity final state.
*/
virtual int nDim(const cPDVector&) const;
/**
* Return the number of random numbers required to produce a given
* multiplicity final state.
*/
virtual int nDimPhasespace(int nFinal) const = 0;
/**
* Return true, if this phasespace generator will generate incoming
* partons itself.
*/
virtual bool haveX1X2() const { return false; }
/**
* Return true, if this phase space generator expects
* the incoming partons in their center-of-mass system
*/
virtual bool wantCMS() const { return true; }
/**
* True, if mass generators should be used instead of fixed masses
*/
bool useMassGenerators() const { return theUseMassGenerators; }
/**
* Fill a diagram selector for the last phase space point.
*/
virtual Selector<MEBase::DiagramIndex> selectDiagrams(const MEBase::DiagramVector&) const;
/**
* Return the momentum and weight appropriate to the given timelike
* branch of the diagram.
*/
pair<double,Lorentz5Momentum> timeLikeWeight(const Tree2toNDiagram& diag,
int branch, double flatCut) const;
/**
* Return the weight appropriate to the given spacelike branch of
* the diagram.
*/
double spaceLikeWeight(const Tree2toNDiagram& diag,
const Lorentz5Momentum& incoming,
int branch, double flatCut) const;
/**
* Return the weight appropriate to the given diagram.
*/
double diagramWeight(const Tree2toNDiagram& diag) const {
assert( !diagramWeights().empty() );
return diagramWeights().find(diag.id())->second;
}
/**
* Fill the diagram weights.
*/
void fillDiagramWeights(double flatCut = 0.0);
/**
+ * Clear the diagram weights.
+ */
+ void clearDiagramWeights() {
+ diagramWeights().clear();
+ }
+
+ /**
* Clone this phase space generator.
*/
Ptr<MatchboxPhasespace>::ptr cloneMe() const {
return dynamic_ptr_cast<Ptr<MatchboxPhasespace>::ptr>(clone());
}
/**
* Clone the dependencies, using a given prefix.
*/
virtual void cloneDependencies(const std::string& prefix = "");
public:
/**
* Return true, if this phase space generator is invertible
*/
virtual bool isInvertible() const { return false; }
/**
* Invert the given phase space point to the random numbers which
* would have generated it.
*/
virtual double invertKinematics(const vector<Lorentz5Momentum>& momenta,
double* r) const;
/**
* Invert the given phase space point to the random numbers which
* would have generated it.
*/
virtual double invertTwoToNKinematics(const vector<Lorentz5Momentum>&,
double*) const {
return 0.;
}
/**
* Invert the given 2 -> 1 phase space point to the random numbers which
* would have generated it.
*/
virtual double invertTwoToOneKinematics(const vector<Lorentz5Momentum>&, double*) const;
public:
/**
* Limit phasespace generation to a given collinear or soft limit.
*/
void singularLimit(size_t i, size_t j) {
if ( i > j )
swap(i,j);
singularLimits().insert(make_pair(i,j));
}
/**
* Return the last matched singular limit.
*/
const pair<size_t,size_t>& lastSingularIndices() const {
assert(lastSingularLimit() != singularLimits().end());
return *lastSingularLimit();
}
/**
* Return true, if constraints on phasespace generation have been met.
*/
bool matchConstraints(const vector<Lorentz5Momentum>& momenta);
protected:
/**
* Set a coupling for the given vertex; the convention is that all
* legs are outgoing, and all possible crossings will be taken care
* of. If not set, coupling weights default to one.
*/
void setCoupling(long a, long b, long c,
double coupling, bool includeCrossings = true);
public:
/** @name Functions used by the persistent I/O system. */
//@{
/**
* Function used to write out object persistently.
* @param os the persistent output stream written to.
*/
void persistentOutput(PersistentOStream & os) const;
/**
* Function used to read in object persistently.
* @param is the persistent input stream read from.
* @param version the version number of the object when written.
*/
void persistentInput(PersistentIStream & is, int version);
//@}
public:
/**
* The standard Init function used to initialize the interfaces.
* Called exactly once for each class by the class description system
* before the main function starts or
* when this class is dynamically loaded.
*/
static void Init();
// If needed, insert declarations of virtual function defined in the
// InterfacedBase class here (using ThePEG-interfaced-decl in Emacs).
private:
/**
* A cutoff below which a region is considered singular.
*/
Energy singularCutoff;
/**
* True, if mass generators should be used instead of fixed masses
*/
bool theUseMassGenerators;
/**
* Couplings to be used in diagram weighting
*/
Ptr<PhasespaceCouplings>::ptr theCouplings;
/**
* Interface function to setcoupling
*/
string doSetCoupling(string);
/**
* Interface function to setcoupling
*/
string doSetPhysicalCoupling(string);
/**
* The first id in a range of id's meant to denote fictitious
* 'ghost' particles to be used by the diagram generator
* in loop induced processes.
*/
int theLoopParticleIdMin;
/**
* The last id in a range of id's meant to denote fictitious
* 'ghost' particles to be used by the diagram generator
* in loop induced processes.
*/
int theLoopParticleIdMax;
/**
* The assignment operator is private and must never be called.
* In fact, it should not even be implemented.
*/
MatchboxPhasespace & operator=(const MatchboxPhasespace &);
};
}
#endif /* HERWIG_MatchboxPhasespace_H */
diff --git a/MatrixElement/Matchbox/Phasespace/MatchboxRambo.cc b/MatrixElement/Matchbox/Phasespace/MatchboxRambo.cc
--- a/MatrixElement/Matchbox/Phasespace/MatchboxRambo.cc
+++ b/MatrixElement/Matchbox/Phasespace/MatchboxRambo.cc
@@ -1,264 +1,263 @@
// -*- C++ -*-
//
// MatchboxRambo.cc is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
//
// This is the implementation of the non-inlined, non-templated member
// functions of the MatchboxRambo class.
//
#include "MatchboxRambo.h"
#include "ThePEG/Interface/ClassDocumentation.h"
#include "ThePEG/Interface/Switch.h"
#include "ThePEG/EventRecord/Particle.h"
#include "ThePEG/Repository/UseRandom.h"
#include "ThePEG/Repository/EventGenerator.h"
#include "ThePEG/Utilities/DescribeClass.h"
#include "Herwig/Utilities/GSLBisection.h"
#include "ThePEG/Cuts/Cuts.h"
#include "ThePEG/Persistency/PersistentOStream.h"
#include "ThePEG/Persistency/PersistentIStream.h"
using namespace Herwig;
MatchboxRambo::MatchboxRambo()
: needToReshuffle(false), theMakeReferenceSample(false),
referenceSample(0) {}
MatchboxRambo::~MatchboxRambo() {}
IBPtr MatchboxRambo::clone() const {
return new_ptr(*this);
}
IBPtr MatchboxRambo::fullclone() const {
return new_ptr(*this);
}
static double weights[7] = {
-1.,-1.,
0.039788735772973833942,
0.00012598255637968550463,
1.3296564302788840628E-7,
7.0167897579949011130E-11,
2.2217170114046130768E-14
};
void MatchboxRambo::setXComb(tStdXCombPtr xc) {
MatchboxPhasespace::setXComb(xc);
needToReshuffle = false;
if ( xc ) {
for ( cPDVector::const_iterator d = mePartonData().begin();
d != mePartonData().end(); ++d ) {
if ( (**d).hardProcessMass() != ZERO ) {
needToReshuffle = true;
break;
}
}
}
}
void MatchboxRambo::dumpReference(const vector<Lorentz5Momentum>& momenta, double weight) const {
*referenceSample << lastX1() << " " << lastX2() << " ";
Boost toLab = (lastPartons().first->momentum() +
lastPartons().second->momentum()).boostVector();
for ( vector<Lorentz5Momentum>::const_iterator p = momenta.begin();
p != momenta.end(); ++p ) {
Lorentz5Momentum pl = *p;
if ( toLab.mag2() > Constants::epsilon )
pl.boost(toLab);
*referenceSample
<< (pl.x()/GeV) << " "
<< (pl.y()/GeV) << " "
<< (pl.z()/GeV) << " "
<< (pl.t()/GeV) << " "
<< (pl.mass()/GeV) << " ";
}
double ymax = lastCuts().yHatMax();
double ymin = lastCuts().yHatMin();
double km = log(lastCuts().sHatMax()/lastCuts().sHatMin());
ymax = min(ymax, log(lastCuts().x1Max()*sqrt(lastS()/lastSHat())));
ymin = max(ymin, -log(lastCuts().x2Max()*sqrt(lastS()/lastSHat())));
*referenceSample << weight*km*(ymax-ymin)/(lastX1()*lastX2()) << "\n" << flush;
}
double MatchboxRambo::generateTwoToNKinematics(const double* r,
vector<Lorentz5Momentum>& momenta) {
if ( theMakeReferenceSample ) {
map<cPDVector,ofstream*>::iterator ref =
referenceSamples.find(mePartonData());
if ( ref == referenceSamples.end() ) {
ostringstream refname;
for ( cPDVector::const_iterator p = mePartonData().begin();
p != mePartonData().end(); ++p ) {
refname << (**p).PDGName();
}
refname << ".rambo";
referenceSamples[mePartonData()] = new ofstream(refname.str().c_str(),std::ios_base::app);
ref = referenceSamples.find(mePartonData());
*(ref->second) << setprecision(26);
}
assert(ref != referenceSamples.end());
referenceSample = ref->second;
}
- size_t offset = dynamic_cast<const Tree2toNDiagram&>(*lastXComb().diagrams().front()).nSpace() > 0 ? 2 : 1;
+ size_t offset = 2;
+ if ( lastXCombPtr() )
+ offset = dynamic_cast<const Tree2toNDiagram&>(*lastXComb().diagrams().front()).nSpace() > 0 ? 2 : 1;
Energy w = sqrt(lastSHat());
size_t count = 0;
Lorentz5Momentum Q;
for ( vector<Lorentz5Momentum>::iterator k = momenta.begin() + offset;
k != momenta.end(); ++k ) {
Energy q = -w*log(r[count]*r[count+1]);
double ct = 2.*r[count+2]-1.;
double st = sqrt(1.-sqr(ct));
double phi = 2.*Constants::pi*r[count+3];
double cphi = cos(phi);
double sphi = sqrt(1.-sqr(cphi));
if ( phi > Constants::pi )
sphi = -sphi;
(*k).setMass(ZERO);
(*k).setT(q);
(*k).setX(q*cphi*st);
(*k).setY(q*sphi*st);
(*k).setZ(q*ct);
count += 4;
Q += *k;
}
Energy M = sqrt(Q.m2());
double x = w/M;
Boost beta = -(Q.vect() * (1./M));
double gamma = Q.t()/M;
double a = 1./(1.+gamma);
for ( vector<Lorentz5Momentum>::iterator k = momenta.begin() + offset;
k != momenta.end(); ++k ) {
Energy q = (*k).t();
Energy bq = beta*(*k).vect();
(*k).setT(x*(gamma*q+bq));
(*k).setVect(x*((*k).vect()+(q+a*bq)*beta));
}
size_t n = momenta.size()-offset;
double weight = weights[n];
if ( !needToReshuffle ) {
if ( !matchConstraints(momenta) )
return 0.;
- fillDiagramWeights();
if ( theMakeReferenceSample )
dumpReference(momenta, weight);
return weight;
}
double xi;
ReshuffleEquation solve(w,mePartonData().begin()+offset,mePartonData().end(),
momenta.begin()+2,momenta.end());
GSLBisection solver(1e-10,1e-8,10000);
try {
xi = solver.value(solve,0.0,1.1);
} catch (GSLBisection::GSLerror) {
return 0.;
} catch (GSLBisection::IntervalError) {
return 0.;
}
weight *= pow(xi,3.*(n-1.));
Energy num = ZERO;
Energy den = ZERO;
cPDVector::const_iterator d = mePartonData().begin()+offset;
for ( vector<Lorentz5Momentum>::iterator k = momenta.begin()+offset;
k != momenta.end(); ++k, ++d ) {
num += (*k).vect().mag2()/(*k).t();
Energy q = (*k).t();
(*k).setT(sqrt(sqr((**d).hardProcessMass())+xi*xi*sqr((*k).t())));
(*k).setVect(xi*(*k).vect());
weight *= q/(*k).t();
den += (*k).vect().mag2()/(*k).t();
(*k).setMass((**d).hardProcessMass());
}
if ( !matchConstraints(momenta) )
return 0.;
weight *= num/den;
- fillDiagramWeights();
-
if ( theMakeReferenceSample )
dumpReference(momenta, weight);
return weight;
}
Energy MatchboxRambo::ReshuffleEquation::operator() (double xi) const {
cPDVector::const_iterator d = dataBegin;
vector<Lorentz5Momentum>::const_iterator p = momentaBegin;
Energy res = -w;
for ( ; d != dataEnd; ++d, ++p ) {
res += sqrt(sqr((**d).hardProcessMass()) +
xi*xi*sqr(p->t()));
}
return res;
}
// If needed, insert default implementations of virtual function defined
// in the InterfacedBase class here (using ThePEG-interfaced-impl in Emacs).
void MatchboxRambo::persistentOutput(PersistentOStream & os) const {
os << needToReshuffle << theMakeReferenceSample;
}
void MatchboxRambo::persistentInput(PersistentIStream & is, int) {
is >> needToReshuffle >> theMakeReferenceSample;
}
// *** Attention *** The following static variable is needed for the type
// description system in ThePEG. Please check that the template arguments
// are correct (the class and its base class), and that the constructor
// arguments are correct (the class name and the name of the dynamically
// loadable library where the class implementation can be found).
DescribeClass<MatchboxRambo,MatchboxPhasespace>
describeHerwigMatchboxRambo("Herwig::MatchboxRambo", "Herwig.so");
void MatchboxRambo::Init() {
static ClassDocumentation<MatchboxRambo> documentation
("MatchboxRambo implements RAMBO phase space generation.");
static Switch<MatchboxRambo,bool> interfaceMakeReferenceSample
("MakeReferenceSample",
"Switch on generation of a reference sample of phase space points.",
&MatchboxRambo::theMakeReferenceSample, false, false, false);
static SwitchOption interfaceMakeReferenceSampleOn
(interfaceMakeReferenceSample,
"On",
"Generate a reference sample.",
true);
static SwitchOption interfaceMakeReferenceSampleOff
(interfaceMakeReferenceSample,
"Off",
"Do not generate a reference sample.",
false);
interfaceMakeReferenceSample.rank(-1);
}
diff --git a/MatrixElement/Matchbox/Phasespace/MatchboxReference.cc b/MatrixElement/Matchbox/Phasespace/MatchboxReference.cc
--- a/MatrixElement/Matchbox/Phasespace/MatchboxReference.cc
+++ b/MatrixElement/Matchbox/Phasespace/MatchboxReference.cc
@@ -1,107 +1,105 @@
// -*- C++ -*-
//
// MatchboxReference.cc is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
//
// This is the implementation of the non-inlined, non-templated member
// functions of the MatchboxReference class.
//
#include "MatchboxReference.h"
#include "ThePEG/Interface/ClassDocumentation.h"
#include "ThePEG/Interface/Switch.h"
#include "ThePEG/EventRecord/Particle.h"
#include "ThePEG/Repository/UseRandom.h"
#include "ThePEG/Repository/EventGenerator.h"
#include "ThePEG/Utilities/DescribeClass.h"
#include "Herwig/Utilities/GSLBisection.h"
#include "ThePEG/Cuts/Cuts.h"
#include "ThePEG/Persistency/PersistentOStream.h"
#include "ThePEG/Persistency/PersistentIStream.h"
using namespace Herwig;
MatchboxReference::MatchboxReference() {}
MatchboxReference::~MatchboxReference() {}
IBPtr MatchboxReference::clone() const {
return new_ptr(*this);
}
IBPtr MatchboxReference::fullclone() const {
return new_ptr(*this);
}
double MatchboxReference::generateTwoToNKinematics(const double*,
vector<Lorentz5Momentum>& momenta) {
map<cPDVector,ifstream*>::iterator ref =
referenceSamples.find(mePartonData());
if ( ref == referenceSamples.end() ) {
ostringstream refname;
for ( cPDVector::const_iterator p = mePartonData().begin();
p != mePartonData().end(); ++p ) {
refname << (**p).PDGName();
}
refname << ".rambo";
referenceSamples[mePartonData()] = new ifstream(refname.str().c_str());
ref = referenceSamples.find(mePartonData());
}
assert(ref != referenceSamples.end());
ifstream& in = *(ref->second);
assert(in);
double x1,x2;
double x,y,z,t,m;
double weight;
in >> x1 >> x2;
for ( vector<Lorentz5Momentum>::iterator p = momenta.begin();
p != momenta.end(); ++p ) {
in >> x >> y >> z >> t >> m;
*p = Lorentz5Momentum(x*GeV,y*GeV,z*GeV,t*GeV,m*GeV);
}
in >> weight;
lastXCombPtr()->lastX1X2(make_pair(x1,x2));
lastXCombPtr()->lastSHat((momenta[0]+momenta[1]).m2());
- fillDiagramWeights();
-
return weight;
}
// If needed, insert default implementations of virtual function defined
// in the InterfacedBase class here (using ThePEG-interfaced-impl in Emacs).
void MatchboxReference::persistentOutput(PersistentOStream &) const {}
void MatchboxReference::persistentInput(PersistentIStream &, int) {}
// *** Attention *** The following static variable is needed for the type
// description system in ThePEG. Please check that the template arguments
// are correct (the class and its base class), and that the constructor
// arguments are correct (the class name and the name of the dynamically
// loadable library where the class implementation can be found).
DescribeClass<MatchboxReference,MatchboxPhasespace>
describeHerwigMatchboxReference("Herwig::MatchboxReference", "Herwig.so");
void MatchboxReference::Init() {
static ClassDocumentation<MatchboxReference> documentation
("MatchboxReference implements reference sample phase space generation.");
}
diff --git a/MatrixElement/Matchbox/Utility/LastMatchboxXCombInfo.h b/MatrixElement/Matchbox/Utility/LastMatchboxXCombInfo.h
--- a/MatrixElement/Matchbox/Utility/LastMatchboxXCombInfo.h
+++ b/MatrixElement/Matchbox/Utility/LastMatchboxXCombInfo.h
@@ -1,528 +1,530 @@
// -*- C++ -*-
//
// MatchboxXComb.h is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
#ifndef Herwig_LastMatchboxXCombInfo_H
#define Herwig_LastMatchboxXCombInfo_H
//
// This is the declaration of the MatchboxXComb class.
//
#include "Herwig/MatrixElement/Matchbox/Utility/MatchboxXCombData.h"
namespace Herwig {
using namespace ThePEG;
/**
* \ingroup Matchbox
* \author Simon Platzer
*
* \brief Provide easy access to MatchboxXComb XComb extensions
*/
class LastMatchboxXCombInfo {
public:
/**
* Default constructor
*/
LastMatchboxXCombInfo()
: theLastMatchboxXComb(0), theLastHeadMatchboxXComb(0) {}
/**
* Return a pointer to the last selected XComb.
*/
MatchboxXCombData* lastMatchboxXComb() const { return theLastMatchboxXComb; }
/**
* If the last selected XComb object belongs to a
* group of XComb's return a pointer to the head
* XComb object for this group.
*/
MatchboxXCombData* lastHeadMatchboxXComb() const { return theLastHeadMatchboxXComb; }
public:
/**
* The crossing information as filled by the last call to
* fillCrossingMap()
*/
const vector<int>& crossingMap() const { return lastMatchboxXComb()->crossingMap(); }
/**
* The colour crossing information as filled by the last call to
* fillCrossingMap()
*/
const map<size_t,size_t>& amplitudeToColourMap() const { return lastMatchboxXComb()->amplitudeToColourMap(); }
/**
* The colour crossing information as filled by the last call to
* fillCrossingMap()
*/
const map<size_t,size_t>& colourToAmplitudeMap() const { return lastMatchboxXComb()->colourToAmplitudeMap(); }
/**
* The crossing sign as filled by the last call to
* fillCrossingMap()
*/
double crossingSign() const { return lastMatchboxXComb()->crossingSign(); }
/**
* The last renormalization scale
*/
Energy2 lastRenormalizationScale() const { return lastMatchboxXComb()->lastRenormalizationScale(); }
/**
* The amplitude parton data.
*/
const cPDVector& amplitudePartonData() const { return lastMatchboxXComb()->amplitudePartonData(); }
/**
* The crossed momenta
*/
const vector<Lorentz5Momentum>& amplitudeMomenta() const { return lastMatchboxXComb()->amplitudeMomenta(); }
/**
* True, if the the tree level amplitudes need to be calculated
*/
bool calculateTreeAmplitudes() const { return lastMatchboxXComb()->calculateTreeAmplitudes(); }
/**
* The amplitude values which have been contributing
* to the last call of prepareAmplitudes.
*/
const map<vector<int>,CVector>& lastAmplitudes() const { return lastMatchboxXComb()->lastAmplitudes(); }
/**
* The leading N amplitude values which have been
* contributing to the last call of prepareAmplitudes.
*/
const map<vector<int>,CVector>& lastLargeNAmplitudes() const { return lastMatchboxXComb()->lastLargeNAmplitudes(); }
/**
* True, if the the one-loop amplitudes need to be calculated
*/
bool calculateOneLoopAmplitudes() const { return lastMatchboxXComb()->calculateOneLoopAmplitudes(); }
/**
* The one-loop amplitude values which have been contributing
* to the last call of prepareAmplitudes.
*/
const map<vector<int>,CVector>& lastOneLoopAmplitudes() const { return lastMatchboxXComb()->lastOneLoopAmplitudes(); }
/**
* True, if the tree-level matrix element squared needs to be
* calculated.
*/
bool calculateTreeME2() const { return lastMatchboxXComb()->calculateTreeME2(); }
/**
* The last tree-level matrix element squared
*/
double lastTreeME2() const { return lastMatchboxXComb()->lastTreeME2(); }
/**
* True, if the tree-level matrix element squared needs to be
* calculated.
*/
bool calculateLargeNME2() const { return lastMatchboxXComb()->calculateLargeNME2(); }
/**
* The last tree-level matrix element squared
*/
double lastLargeNME2() const { return lastMatchboxXComb()->lastLargeNME2(); }
/**
* True, if the one-loop/tree-level interference.
* be calculated.
*/
bool calculateOneLoopInterference() const { return lastMatchboxXComb()->calculateOneLoopInterference(); }
/**
* The last one-loop/tree-level interference.
*/
double lastOneLoopInterference() const { return lastMatchboxXComb()->lastOneLoopInterference(); }
/**
* True, if the one-loop/tree-level interference.
* be calculated.
*/
bool calculateOneLoopPoles() const { return lastMatchboxXComb()->calculateOneLoopPoles(); }
/**
* The last one-loop/tree-level interference.
*/
pair<double,double> lastOneLoopPoles() const { return lastMatchboxXComb()->lastOneLoopPoles(); }
/**
* True, if the indexed colour correlated matrix element needs to be
* calculated.
*/
bool calculateColourCorrelator(const pair<int,int>& ij) const { return lastMatchboxXComb()->calculateColourCorrelator(ij); }
/**
* The colour correlated matrix element.
*/
double lastColourCorrelator(const pair<int,int>& ij) const { return lastMatchboxXComb()->lastColourCorrelator(ij); }
/**
* True, if the indexed large-N colour correlated matrix element needs to be
* calculated.
*/
bool calculateLargeNColourCorrelator(const pair<int,int>& ij) const { return lastMatchboxXComb()->calculateLargeNColourCorrelator(ij); }
/**
* The large-N colour correlated matrix element.
*/
double lastLargeNColourCorrelator(const pair<int,int>& ij) const { return lastMatchboxXComb()->lastLargeNColourCorrelator(ij); }
/**
* True, if the indexed colour/spin correlated matrix element needs to be
* calculated.
*/
bool calculateColourSpinCorrelator(const pair<int,int>& ij) const { return lastMatchboxXComb()->calculateColourSpinCorrelator(ij); }
/**
* The colour/spin correlated matrix element.
*/
Complex lastColourSpinCorrelator(const pair<int,int>& ij) const { return lastMatchboxXComb()->lastColourSpinCorrelator(ij); }
/**
* True, if the indexed spin correlated matrix element needs to be
* calculated.
*/
bool calculateSpinCorrelator(const pair<int,int>& ij) const { return lastMatchboxXComb()->calculateSpinCorrelator(ij); }
/**
* The spin correlated matrix element.
*/
Complex lastSpinCorrelator(const pair<int,int>& ij) const { return lastMatchboxXComb()->lastSpinCorrelator(ij); }
/**
* Return the number of light flavours to be considered for this process.
*/
unsigned int nLight() const { return lastMatchboxXComb()->nLight(); }
/**
* Return the vector that contains the PDG ids of
* the light flavours, which are contained in the
* jet particle group.
*/
vector<long> nLightJetVec() const { return lastMatchboxXComb()->nLightJetVec(); }
/**
* Return the vector that contains the PDG ids of
* the heavy flavours, which are contained in the
* jet particle group.
*/
vector<long> nHeavyJetVec() const { return lastMatchboxXComb()->nHeavyJetVec(); }
/**
* Return the vector that contains the PDG ids of
* the light flavours, which are contained in the
* proton particle group.
*/
vector<long> nLightProtonVec() const { return lastMatchboxXComb()->nLightProtonVec(); }
/**
* Get the dimensionality of the colour basis for this process.
*/
size_t colourBasisDim() const { return lastMatchboxXComb()->colourBasisDim(); }
/**
* Return the number of degrees of freedom required by the phase space generator
*/
int nDimPhasespace() const { return lastMatchboxXComb()->nDimPhasespace(); }
/**
* Return the number of degrees of freedom required by the amplitude
*/
int nDimAmplitude() const { return lastMatchboxXComb()->nDimAmplitude(); }
/**
* Return the number of degrees of freedom required by the insertion operators
*/
int nDimInsertions() const { return lastMatchboxXComb()->nDimInsertions(); }
/**
* Get the additional random numbers required by the amplitude
*/
const vector<double>& amplitudeRandomNumbers() const { return lastMatchboxXComb()->amplitudeRandomNumbers(); }
/**
* Get the additional random numbers required by the insertion operator
*/
const vector<double>& insertionRandomNumbers() const { return lastMatchboxXComb()->insertionRandomNumbers(); }
/**
* Return the diagram weights indexed by diagram id.
*/
const map<int,double>& diagramWeights() const { return lastMatchboxXComb()->diagramWeights(); }
/**
* Return the singular limits
*/
const set<pair<size_t,size_t> >& singularLimits() const { return lastMatchboxXComb()->singularLimits(); }
/**
* Return the last matched singular limit.
*/
const set<pair<size_t,size_t> >::const_iterator& lastSingularLimit() const { return lastMatchboxXComb()->lastSingularLimit(); }
/**
* Get the Herwig StandardModel object
*/
Ptr<StandardModel>::tcptr hwStandardModel() const { return lastMatchboxXComb()->hwStandardModel(); }
/**
* Return the symmetry factor
*/
double symmetryFactor() const { return lastMatchboxXComb()->symmetryFactor(); }
/**
* Return the OLP process id
*/
const vector<int>& olpId() const { return lastMatchboxXComb()->olpId(); }
/**
* Return the olp momentum vector
*/
double* olpMomenta() const { return lastMatchboxXComb()->olpMomenta(); }
/**
* Fill the olp momentum vector
*/
void fillOLPMomenta(const vector<Lorentz5Momentum>& mm,
const cPDVector& mePartonData,
const map<long,Energy>& reshuffleMap) const {
lastMatchboxXComb()->fillOLPMomenta(mm,mePartonData,reshuffleMap);
}
protected:
/**
* The crossing information as filled by the last call to
* fillCrossingMap()
*/
vector<int>& crossingMap() { return lastMatchboxXComb()->crossingMap(); }
/**
* The colour crossing information as filled by the last call to
* fillCrossingMap()
*/
map<size_t,size_t>& amplitudeToColourMap() { return lastMatchboxXComb()->amplitudeToColourMap(); }
/**
* The colour crossing information as filled by the last call to
* fillCrossingMap()
*/
map<size_t,size_t>& colourToAmplitudeMap() { return lastMatchboxXComb()->colourToAmplitudeMap(); }
/**
* The crossing sign as filled by the last call to
* fillCrossingMap()
*/
void crossingSign(double c) { lastMatchboxXComb()->crossingSign(c); }
/**
* The last renormalization scale
*/
void lastRenormalizationScale(Energy2 lrs) { lastMatchboxXComb()->lastRenormalizationScale(lrs); }
/**
* The amplitude parton data.
*/
cPDVector& amplitudePartonData() { return lastMatchboxXComb()->amplitudePartonData(); }
/**
* The crossed momenta
*/
vector<Lorentz5Momentum>& amplitudeMomenta() { return lastMatchboxXComb()->amplitudeMomenta(); }
/**
* True, if the the tree level amplitudes need to be calculated
*/
void haveTreeAmplitudes(bool f = true) { lastMatchboxXComb()->haveTreeAmplitudes(f); }
/**
* The amplitude values which have been contributing
* to the last call of prepareAmplitudes.
*/
map<vector<int>,CVector>& lastAmplitudes() { return lastMatchboxXComb()->lastAmplitudes(); }
/**
* The leading N amplitude values which have been
* contributing to the last call of prepareAmplitudes.
*/
map<vector<int>,CVector>& lastLargeNAmplitudes() { return lastMatchboxXComb()->lastLargeNAmplitudes(); }
/**
* True, if the the one-loop amplitudes need to be calculated
*/
void haveOneLoopAmplitudes(bool f = true) { lastMatchboxXComb()->haveOneLoopAmplitudes(f); }
/**
* The one-loop amplitude values which have been contributing
* to the last call of prepareAmplitudes.
*/
map<vector<int>,CVector>& lastOneLoopAmplitudes() { return lastMatchboxXComb()->lastOneLoopAmplitudes(); }
/**
* The last tree-level matrix element squared
*/
void lastTreeME2(double v) const { lastMatchboxXComb()->lastTreeME2(v); }
/**
* The last tree-level matrix element squared
*/
void lastLargeNME2(double v) const { lastMatchboxXComb()->lastLargeNME2(v); }
/**
* The last one-loop/tree-level interference.
*/
void lastOneLoopInterference(double v) const { lastMatchboxXComb()->lastOneLoopInterference(v); }
/**
* The last one-loop/tree-level interference.
*/
void lastOneLoopPoles(pair<double,double> v) const { lastMatchboxXComb()->lastOneLoopPoles(v); }
/**
* The colour correlated matrix element.
*/
void lastColourCorrelator(const pair<int,int>& ij, double v) const { lastMatchboxXComb()->lastColourCorrelator(ij,v); }
/**
* The large-N colour correlated matrix element.
*/
void lastLargeNColourCorrelator(const pair<int,int>& ij, double v) const { lastMatchboxXComb()->lastLargeNColourCorrelator(ij,v); }
/**
* The colour/spin correlated matrix element.
*/
void lastColourSpinCorrelator(const pair<int,int>& ij, Complex v) const { lastMatchboxXComb()->lastColourSpinCorrelator(ij,v); }
/**
* The spin correlated matrix element.
*/
void lastSpinCorrelator(const pair<int,int>& ij, Complex v) const { lastMatchboxXComb()->lastSpinCorrelator(ij,v); }
/**
* Set the number of light flavours to be considered for this process.
*/
void nLight(unsigned int n) { lastMatchboxXComb()->nLight(n); }
/**
* Set the elements of the vector that contains the PDG
* ids of the light flavours, which are contained in the
* jet particle group.
*/
void nLightJetVec(int n) { lastMatchboxXComb()->nLightJetVec(n); }
/**
* Set the elements of the vector that contains the PDG
* ids of the heavy flavours, which are contained in the
* jet particle group.
*/
void nHeavyJetVec(int n) { lastMatchboxXComb()->nHeavyJetVec(n); }
/**
* Set the elements of the vector that contains the PDG
* ids of the light flavours, which are contained in the
* proton particle group.
*/
void nLightProtonVec(int n) { lastMatchboxXComb()->nLightProtonVec(n); }
/**
* Set the dimensionality of the colour basis for this process.
*/
void colourBasisDim(size_t d) { lastMatchboxXComb()->colourBasisDim(d); }
/**
* Set the number of degrees of freedom required by the phase space generator
*/
void nDimPhasespace(int d) { lastMatchboxXComb()->nDimPhasespace(d); }
/**
* Set the number of degrees of freedom required by the amplitude
*/
void nDimAmplitude(int d) { lastMatchboxXComb()->nDimAmplitude(d); }
/**
* Set the number of degrees of freedom required by the insertion operators
*/
void nDimInsertions(int d) { lastMatchboxXComb()->nDimInsertions(d); }
/**
* Access the additional random numbers required by the amplitude
*/
vector<double>& amplitudeRandomNumbers() { return lastMatchboxXComb()->amplitudeRandomNumbers(); }
/**
* Access the additional random numbers required by the insertion operator
*/
vector<double>& insertionRandomNumbers() { return lastMatchboxXComb()->insertionRandomNumbers(); }
/**
* Access the diagram weights indexed by diagram id.
*/
map<int,double>& diagramWeights() { return lastMatchboxXComb()->diagramWeights(); }
/**
* Access the singular limits
*/
set<pair<size_t,size_t> >& singularLimits() { return lastMatchboxXComb()->singularLimits(); }
/**
* Access the last matched singular limit.
*/
set<pair<size_t,size_t> >::const_iterator& lastSingularLimit() { return lastMatchboxXComb()->lastSingularLimit(); }
/**
* Set the Herwig StandardModel object
*/
void hwStandardModel(Ptr<StandardModel>::tcptr sm) { lastMatchboxXComb()->hwStandardModel(sm); }
/**
* Set the symmetry factor
*/
void symmetryFactor(double f) const { lastMatchboxXComb()->symmetryFactor(f); }
/**
* Set the OLP process id
*/
void olpId(int pType, int id) { lastMatchboxXComb()->olpId(pType,id); }
protected:
/**
* Set the XComb pointer cast to MatchboxXComb
*/
void lastMatchboxXComb(tStdXCombPtr xc) {
- theLastMatchboxXComb = xc ? &dynamic_cast<MatchboxXCombData&>(*xc) : 0;
+ theLastMatchboxXComb = xc ?
+ dynamic_cast<MatchboxXCombData*>(PtrTraits<tStdXCombPtr>::barePointer(xc)) : 0;
theLastHeadMatchboxXComb =
- xc && xc->head() ? &dynamic_cast<MatchboxXCombData&>(*xc->head()) : 0;
+ xc && xc->head() ?
+ dynamic_cast<MatchboxXCombData*>(PtrTraits<tStdXCombPtr>::barePointer(xc->head())) : 0;
}
/**
* The XComb pointer cast to MatchboxXComb
*/
MatchboxXCombData* theLastMatchboxXComb;
/**
* The head XComb pointer cast to MatchboxXComb
*/
MatchboxXCombData* theLastHeadMatchboxXComb;
};
}
#endif // Herwig_LastMatchboxXCombInfo_H
diff --git a/Shower/Core/SplittingFunctions/SplittingFunction.h b/Shower/Core/SplittingFunctions/SplittingFunction.h
--- a/Shower/Core/SplittingFunctions/SplittingFunction.h
+++ b/Shower/Core/SplittingFunctions/SplittingFunction.h
@@ -1,390 +1,393 @@
// -*- C++ -*-
//
// SplittingFunction.h is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2011 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
#ifndef HERWIG_SplittingFunction_H
#define HERWIG_SplittingFunction_H
//
// This is the declaration of the SplittingFunction class.
//
#include "ThePEG/Interface/Interfaced.h"
#include "Herwig/Shower/Core/ShowerConfig.h"
#include "ThePEG/EventRecord/RhoDMatrix.h"
#include "Herwig/Decay/DecayMatrixElement.h"
#include "Herwig/Shower/Core/Base/ShowerKinematics.fh"
#include "ThePEG/EventRecord/ColourLine.h"
#include "ThePEG/PDT/ParticleData.h"
#include "SplittingFunction.fh"
namespace Herwig {
using namespace ThePEG;
/** \ingroup Shower
* Enum to define the possible types of colour structure which can occur in
* the branching.
*/
enum ColourStructure {Undefined=0,
TripletTripletOctet = 1,OctetOctetOctet =2,
OctetTripletTriplet = 3,TripletOctetTriplet=4,
SextetSextetOctet = 5,
ChargedChargedNeutral=-1,ChargedNeutralCharged=-2,
NeutralChargedCharged=-3,EW=-4};
/** \ingroup Shower
*
* This is an abstract class which defines the common interface
* for all \f$1\to2\f$ splitting functions, for both initial-state
* and final-state radiation.
*
* The SplittingFunction class contains a number of purely virtual members
* which must be implemented in the inheriting classes. The class also stores
* the interaction type of the spltting function.
*
* The inheriting classes need to specific the splitting function
* \f$P(z,2p_j\cdot p_k)\f$, in terms of the energy fraction \f$z\f$ and
* the evolution scale. In order to allow the splitting functions to be used
* with different choices of evolution functions the scale is given by
* \f[2p_j\cdot p_k=(p_j+p_k)^2-m_{jk}^2=Q^2-(p_j+p_k)^2=z(1-z)\tilde{q}^2=
* \frac{p_T^2}{z(1-z)}-m_{jk}^2+\frac{m_j^2}{z}+\frac{m_k^2}{1-z},\f]
* where \f$Q^2\f$ is the virtuality of the branching particle,
* $p_T$ is the relative transverse momentum of the branching products and
* \f$\tilde{q}^2\f$ is the angular variable described in hep-ph/0310083.
*
* In addition an overestimate of the
* splitting function, \f$P_{\rm over}(z)\f$ which only depends upon \f$z\f$,
* the integral, inverse of the integral for this overestimate and
* ratio of the true splitting function to the overestimate must be provided
* as they are necessary for the veto alogrithm used to implement the evolution.
*
* @see \ref SplittingFunctionInterfaces "The interfaces"
* defined for SplittingFunction.
*/
class SplittingFunction: public Interfaced {
public:
/**
* The default constructor.
* @param b All splitting functions must have an interaction order
*/
SplittingFunction(unsigned int b)
: Interfaced(), _interactionType(ShowerInteraction::UNDEFINED),
_interactionOrder(b),
_colourStructure(Undefined), _colourFactor(-1.),
angularOrdered_(true), scaleChoice_(2) {}
public:
/**
* Methods to return the interaction type and order for the splitting function
*/
//@{
/**
* Return the type of the interaction
*/
ShowerInteraction interactionType() const {return _interactionType;}
/**
* Return the order of the splitting function in the interaction
*/
unsigned int interactionOrder() const {return _interactionOrder;}
/**
* Return the colour structure
*/
ColourStructure colourStructure() const {return _colourStructure;}
/**
* Return the colour factor
*/
double colourFactor(const IdList &ids) const {
if(_colourStructure>0)
return _colourFactor;
else if(_colourStructure<0) {
if(_colourStructure==ChargedChargedNeutral ||
_colourStructure==ChargedNeutralCharged) {
return sqr(double(ids[0]->iCharge())/3.);
}
else if(_colourStructure==NeutralChargedCharged) {
- return sqr(double(ids[1]->iCharge())/3.);
+ double fact = sqr(double(ids[1]->iCharge())/3.);
+ if(ids[1]->coloured())
+ fact *= abs(double(ids[1]->iColour()));
+ return fact;
}
else if(_colourStructure==EW) {
return 1.;
}
else
assert(false);
}
else
assert(false);
}
//@}
/**
* Purely virtual method which should determine whether this splitting
* function can be used for a given set of particles.
* @param ids The PDG codes for the particles in the splitting.
*/
virtual bool accept(const IdList & ids) const = 0;
/**
* Method to check the colours are correct
*/
virtual bool checkColours(const IdList & ids) const;
/**
* Methods to return the splitting function.
*/
//@{
/**
* Purely virtual method which should return the exact value of the splitting function,
* \f$P\f$ evaluated in terms of the energy fraction, \f$z\f$, and the evolution scale
\f$\tilde{q}^2\f$.
* @param z The energy fraction.
* @param t The scale \f$t=2p_j\cdot p_k\f$.
* @param ids The PDG codes for the particles in the splitting.
* @param mass Whether or not to include the mass dependent terms
* @param rho The spin density matrix
*/
virtual double P(const double z, const Energy2 t, const IdList & ids,
const bool mass, const RhoDMatrix & rho) const = 0;
/**
* Purely virtual method which should return
* an overestimate of the splitting function,
* \f$P_{\rm over}\f$ such that the result \f$P_{\rm over}\geq P\f$. This function
* should be simple enough that it does not depend on the evolution scale.
* @param z The energy fraction.
* @param ids The PDG codes for the particles in the splitting.
*/
virtual double overestimateP(const double z, const IdList & ids) const = 0;
/**
* Purely virtual method which should return
* the ratio of the splitting function to the overestimate, i.e.
* \f$P(z,\tilde{q}^2)/P_{\rm over}(z)\f$.
* @param z The energy fraction.
* @param t The scale \f$t=2p_j\cdot p_k\f$.
* @param ids The PDG codes for the particles in the splitting.
* @param mass Whether or not to include the mass dependent terms
* @param rho The spin density matrix
*/
virtual double ratioP(const double z, const Energy2 t, const IdList & ids,
const bool mass, const RhoDMatrix & rho) const = 0;
/**
* Purely virtual method which should return the indefinite integral of the
* overestimated splitting function, \f$P_{\rm over}\f$.
* @param z The energy fraction.
* @param ids The PDG codes for the particles in the splitting.
* @param PDFfactor Which additional factor to include for the PDF
* 0 is no additional factor,
* 1 is \f$1/z\f$, 2 is \f$1/(1-z)\f$ and 3 is \f$1/z/(1-z)\f$
*
*/
virtual double integOverP(const double z, const IdList & ids,
unsigned int PDFfactor=0) const = 0;
/**
* Purely virtual method which should return the inverse of the
* indefinite integral of the
* overestimated splitting function, \f$P_{\rm over}\f$ which is used to
* generate the value of \f$z\f$.
* @param r Value of the splitting function to be inverted
* @param ids The PDG codes for the particles in the splitting.
* @param PDFfactor Which additional factor to include for the PDF
* 0 is no additional factor,
* 1 is \f$1/z\f$, 2 is \f$1/(1-z)\f$ and 3 is \f$1/z/(1-z)\f$
*/
virtual double invIntegOverP(const double r, const IdList & ids,
unsigned int PDFfactor=0) const = 0;
//@}
/**
* Purely virtual method which should make the proper colour connection
* between the emitting parent and the branching products.
* @param parent The parent for the branching
* @param first The first branching product
* @param second The second branching product
* @param partnerType The type of evolution partner
* @param back Whether this is foward or backward evolution.
*/
virtual void colourConnection(tShowerParticlePtr parent,
tShowerParticlePtr first,
tShowerParticlePtr second,
ShowerPartnerType partnerType,
const bool back) const;
/**
* Method to calculate the azimuthal angle for forward evolution
* @param z The energy fraction
* @param t The scale \f$t=2p_j\cdot p_k\f$.
* @param ids The PDG codes for the particles in the splitting.
* @param The azimuthal angle, \f$\phi\f$.
* @return The weight
*/
virtual vector<pair<int,Complex> >
generatePhiForward(const double z, const Energy2 t, const IdList & ids,
const RhoDMatrix &) = 0;
/**
* Method to calculate the azimuthal angle for backward evolution
* @param z The energy fraction
* @param t The scale \f$t=2p_j\cdot p_k\f$.
* @param ids The PDG codes for the particles in the splitting.
* @return The weight
*/
virtual vector<pair<int,Complex> >
generatePhiBackward(const double z, const Energy2 t, const IdList & ids,
const RhoDMatrix &) = 0;
/**
* Calculate the matrix element for the splitting
* @param z The energy fraction
* @param t The scale \f$t=2p_j\cdot p_k\f$.
* @param ids The PDG codes for the particles in the splitting.
* @param phi The azimuthal angle, \f$\phi\f$.
* @param timeLike Whether timelike or spacelike, affects inclusive of mass terms
*/
virtual DecayMEPtr matrixElement(const double z, const Energy2 t,
const IdList & ids, const double phi,
bool timeLike) = 0;
/**
* Whether or not the interaction is angular ordered
*/
bool angularOrdered() const {return angularOrdered_;}
/**
* Scale choice
*/
bool pTScale() const {
return scaleChoice_ == 2 ? angularOrdered_ : scaleChoice_ == 0;
}
/**
* Functions to state scales after branching happens
*/
//@{
/**
* Sort out scales for final-state emission
*/
void evaluateFinalStateScales(ShowerPartnerType type,
Energy scale, double z,
tShowerParticlePtr parent,
tShowerParticlePtr first,
tShowerParticlePtr second);
/**
* Sort out scales for initial-state emission
*/
void evaluateInitialStateScales(ShowerPartnerType type,
Energy scale, double z,
tShowerParticlePtr parent,
tShowerParticlePtr first,
tShowerParticlePtr second);
/**
* Sort out scales for decay emission
*/
void evaluateDecayScales(ShowerPartnerType type,
Energy scale, double z,
tShowerParticlePtr parent,
tShowerParticlePtr first,
tShowerParticlePtr second);
//@}
public:
/** @name Functions used by the persistent I/O system. */
//@{
/**
* Function used to write out object persistently.
* @param os the persistent output stream written to.
*/
void persistentOutput(PersistentOStream & os) const;
/**
* Function used to read in object persistently.
* @param is the persistent input stream read from.
* @param version the version number of the object when written.
*/
void persistentInput(PersistentIStream & is, int version);
//@}
/**
* The standard Init function used to initialize the interfaces.
* Called exactly once for each class by the class description system
* before the main function starts or
* when this class is dynamically loaded.
*/
static void Init();
protected:
/** @name Standard Interfaced functions. */
//@{
/**
* Initialize this object after the setup phase before saving an
* EventGenerator to disk.
* @throws InitException if object could not be initialized properly.
*/
virtual void doinit();
//@}
protected:
/**
* Set the colour factor
*/
void colourFactor(double in) {_colourFactor=in;}
private:
/**
* The assignment operator is private and must never be called.
* In fact, it should not even be implemented.
*/
SplittingFunction & operator=(const SplittingFunction &);
private:
/**
* The interaction type for the splitting function.
*/
ShowerInteraction _interactionType;
/**
* The order of the splitting function in the coupling
*/
unsigned int _interactionOrder;
/**
* The colour structure
*/
ColourStructure _colourStructure;
/**
* The colour factor
*/
double _colourFactor;
/**
* Whether or not this interaction is angular-ordered
*/
bool angularOrdered_;
/**
* The choice of scale
*/
unsigned int scaleChoice_;
};
}
#endif /* HERWIG_SplittingFunction_H */
diff --git a/Shower/Dipole/Base/DipoleEventRecord.cc b/Shower/Dipole/Base/DipoleEventRecord.cc
--- a/Shower/Dipole/Base/DipoleEventRecord.cc
+++ b/Shower/Dipole/Base/DipoleEventRecord.cc
@@ -1,1486 +1,1492 @@
// -*- C++ -*-
//
// DipoleEventRecord.cc is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2007 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
//
// This is the implementation of the non-inlined, non-templated member
// functions of the DipoleEventRecord class.
//
#include "DipoleEventRecord.h"
#include "Herwig/Shower/Dipole/Utility/DipolePartonSplitter.h"
#include "Herwig/Shower/ShowerHandler.h"
#include "ThePEG/PDT/DecayMode.h"
#include "Herwig/Decay/HwDecayerBase.h"
#include "ThePEG/Repository/EventGenerator.h"
#include "ThePEG/PDF/PartonExtractor.h"
#include "Herwig/Shower/RealEmissionProcess.h"
#include <boost/utility.hpp>
#include <algorithm>
#include <iterator>
using namespace Herwig;
PList DipoleEventRecord::colourOrdered(PPair & in,
PList & out) {
PList colour_ordered;
size_t done_size = out.size();
if (in.first->coloured())
++done_size;
if (in.second && in.second->coloured())
++done_size;
while (colour_ordered.size() != done_size) {
PPtr current;
// start with singlets, as long as we have some
if (find(colour_ordered.begin(),colour_ordered.end(),in.first) ==
colour_ordered.end() && in.first->coloured()) {
if (!in.first->hasColour() || !in.first->hasAntiColour())
current = in.first;
}
if (!current) {
for (PList::iterator p = out.begin();
p != out.end(); ++p) {
if (find(colour_ordered.begin(),colour_ordered.end(),*p) ==
colour_ordered.end() && (**p).coloured()) {
if (!(**p).hasColour() || !(**p).hasAntiColour()) {
current = *p;
break;
}
}
}
}
if (!current) {
if (in.second && find(colour_ordered.begin(),colour_ordered.end(),in.second) ==
colour_ordered.end() && in.second->coloured()) {
if (!in.second->hasColour() || !in.second->hasAntiColour())
current = in.second;
}
}
// then go on with anything else
if (!current) {
if (find(colour_ordered.begin(),colour_ordered.end(),in.first) ==
colour_ordered.end() && in.first->coloured()) {
current = in.first;
}
}
if (!current) {
for (PList::iterator p = out.begin();
p != out.end(); ++p) {
if (find(colour_ordered.begin(),colour_ordered.end(),*p) ==
colour_ordered.end() && (**p).coloured()) {
current = *p;
break;
}
}
}
if (!current) {
if (in.second && find(colour_ordered.begin(),colour_ordered.end(),in.second) ==
colour_ordered.end() && in.second->coloured()) {
current = in.second;
}
}
assert(current);
PPtr next;
Ptr<ColourLine>::ptr walk_the_line;
while (true) {
if (!walk_the_line) {
if (current->hasColour()) {
walk_the_line = current->colourLine();
}
else if (current->hasAntiColour()) {
walk_the_line = current->antiColourLine();
}
}
if (!next)
for (tPVector::const_iterator p = walk_the_line->coloured().begin();
p != walk_the_line->coloured().end(); ++p) {
if (*p == current)
continue;
if (find(out.begin(),out.end(),*p) != out.end() ||
*p == in.first ||
(in.second && *p == in.second)) {
next = *p;
if (next->hasColour() && next->hasAntiColour()) {
walk_the_line = walk_the_line == next->colourLine() ? next->antiColourLine() : next->colourLine();
}
break;
}
}
if (!next)
for (tPVector::const_iterator p = walk_the_line->antiColoured().begin();
p != walk_the_line->antiColoured().end(); ++p) {
if (*p == current)
continue;
if (find(out.begin(),out.end(),*p) != out.end() ||
*p == in.first ||
(in.second && *p == in.second)) {
next = *p;
if (next->hasColour() && next->hasAntiColour()) {
walk_the_line = walk_the_line == next->colourLine() ? next->antiColourLine() : next->colourLine();
}
break;
}
}
assert(next);
colour_ordered.push_back(current);
current = next;
// done if next is not a gluon or next is already in colour_ordered
if ((current->hasColour() && !current->hasAntiColour()) ||
(!current->hasColour() && current->hasAntiColour())) {
colour_ordered.push_back(current);
break;
}
if (next->hasColour() && next->hasAntiColour()) {
if (find(colour_ordered.begin(),colour_ordered.end(),next) != colour_ordered.end())
break;
}
next = PPtr();
}
}
return colour_ordered;
}
void DipoleEventRecord::popChain() {
assert(!theChains.empty());
theDoneChains.push_back(DipoleChain());
theDoneChains.back().dipoles().splice(theDoneChains.back().dipoles().begin(),theChains.front().dipoles());
theChains.pop_front();
}
void DipoleEventRecord::popChain(list<DipoleChain>::iterator ch) {
assert(!theChains.empty());
theDoneChains.push_back(DipoleChain());
theDoneChains.back().dipoles().splice(theDoneChains.back().dipoles().begin(),ch->dipoles());
theChains.erase(ch);
}
void DipoleEventRecord::popChains(const list<list<DipoleChain>::iterator>& chs) {
assert(!theChains.empty());
for ( list<list<DipoleChain>::iterator>::const_iterator ch =
chs.begin(); ch != chs.end(); ++ch ) {
theDoneChains.push_back(DipoleChain());
theDoneChains.back().dipoles().splice(theDoneChains.back().dipoles().begin(),(*ch)->dipoles());
}
for ( list<list<DipoleChain>::iterator>::const_iterator ch =
chs.begin(); ch != chs.end(); ++ch )
theChains.erase(*ch);
}
DipoleIndex
DipoleEventRecord::mergeIndex(list<Dipole>::iterator firstDipole, const pair<bool,bool>& whichFirst,
list<Dipole>::iterator secondDipole, const pair<bool,bool>& whichSecond) const {
tcPDPtr emitterData =
whichFirst.first ? firstDipole->leftParticle()->dataPtr() : firstDipole->rightParticle()->dataPtr();
tcPDPtr spectatorData =
whichSecond.first ? secondDipole->leftParticle()->dataPtr() : secondDipole->rightParticle()->dataPtr();
const PDF& emitterPDF =
whichFirst.first ? firstDipole->leftPDF() : firstDipole->rightPDF();
const PDF& spectatorPDF =
whichSecond.first ? secondDipole->leftPDF() : secondDipole->rightPDF();
return DipoleIndex(emitterData,spectatorData,emitterPDF,spectatorPDF);
}
SubleadingSplittingInfo
DipoleEventRecord::mergeSplittingInfo(list<DipoleChain>::iterator firstChain, list<Dipole>::iterator firstDipole,
const pair<bool,bool>& whichFirst,
list<DipoleChain>::iterator secondChain, list<Dipole>::iterator secondDipole,
const pair<bool,bool>& whichSecond) const {
SubleadingSplittingInfo res;
res.index(mergeIndex(firstDipole,whichFirst,secondDipole,whichSecond));
res.emitter(whichFirst.first ? firstDipole->leftParticle() : firstDipole->rightParticle());
res.spectator(whichSecond.first ? secondDipole->leftParticle() : secondDipole->rightParticle());
res.emitterX(whichFirst.first ? firstDipole->leftFraction() : firstDipole->rightFraction());
res.spectatorX(whichSecond.first ? secondDipole->leftFraction() : secondDipole->rightFraction());
res.configuration(whichFirst);
res.spectatorConfiguration(whichSecond);
res.emitterChain(firstChain);
res.emitterDipole(firstDipole);
res.spectatorChain(secondChain);
res.spectatorDipole(secondDipole);
return res;
}
void DipoleEventRecord::getSubleadingSplittings(list<SubleadingSplittingInfo>& res) {
static pair<bool,bool> left(true,false);
static pair<bool,bool> right(false,true);
res.clear();
for ( list<DipoleChain>::iterator cit = theChains.begin();
cit != theChains.end(); ++cit ) {
for ( list<Dipole>::iterator dit = cit->dipoles().begin();
dit != cit->dipoles().end(); ++dit ) {
for ( list<Dipole>::iterator djt = dit;
djt != cit->dipoles().end(); ++djt ) {
res.push_back(mergeSplittingInfo(cit,dit,left,cit,djt,left));
res.push_back(mergeSplittingInfo(cit,dit,right,cit,djt,right));
if ( dit != djt ) {
res.push_back(mergeSplittingInfo(cit,dit,left,cit,djt,right));
res.push_back(mergeSplittingInfo(cit,dit,right,cit,djt,left));
}
}
}
list<DipoleChain>::iterator cjt = cit; ++cjt;
for ( ; cjt != theChains.end(); ++cjt ) {
for ( list<Dipole>::iterator dit = cit->dipoles().begin();
dit != cit->dipoles().end(); ++dit ) {
for ( list<Dipole>::iterator djt = cjt->dipoles().begin();
djt != cjt->dipoles().end(); ++djt ) {
res.push_back(mergeSplittingInfo(cit,dit,left,cjt,djt,left));
res.push_back(mergeSplittingInfo(cit,dit,right,cjt,djt,right));
res.push_back(mergeSplittingInfo(cit,dit,left,cjt,djt,right));
res.push_back(mergeSplittingInfo(cit,dit,right,cjt,djt,left));
}
}
}
}
}
void DipoleEventRecord::splitSubleading(SubleadingSplittingInfo& dsplit,
pair<list<Dipole>::iterator,list<Dipole>::iterator>& childIterators,
DipoleChain*& firstChain, DipoleChain*& secondChain) {
if ( dsplit.emitterDipole() == dsplit.spectatorDipole() ) {
assert(dsplit.emitterChain() == dsplit.spectatorChain());
split(dsplit.emitterDipole(),dsplit.emitterChain(),dsplit,
childIterators,firstChain,secondChain,false);
} else {
// first need to recoil, then split
recoil(dsplit.spectatorDipole(),dsplit.spectatorChain(),dsplit);
split(dsplit.emitterDipole(),dsplit.emitterChain(),dsplit,
childIterators,firstChain,secondChain,true);
}
}
void DipoleEventRecord::findChains(const PList& ordered, const bool decay) {
+ // All uses of findChains should guarantee
+ // a non-empty list of particles
+ assert( !ordered.empty() );
+
theChains.clear();
theDoneChains.clear();
DipoleChain current_chain;
// this whole thing needs to have a more elegant implementation at some point
bool startIsTriplet =
(ordered.front()->hasColour() && !ordered.front()->hasAntiColour()) ||
(!ordered.front()->hasColour() && ordered.front()->hasAntiColour());
bool endIsTriplet =
(ordered.back()->hasColour() && !ordered.back()->hasAntiColour()) ||
(!ordered.back()->hasColour() && ordered.back()->hasAntiColour());
if (!( ordered.size() == 2 && startIsTriplet && endIsTriplet)) {
PList::const_iterator theStart = ordered.begin();
bool onceMore = false;
for (PList::const_iterator p = ordered.begin();
p != ordered.end(); ++p) {
PList::const_iterator next_it =
p != --ordered.end() ? std::next(p) : ordered.begin();
if (!DipolePartonSplitter::colourConnected(*p,*next_it)) {
// it may have happened that we need to close the chain due to another
// chain starting right now; see the above global comment for this fix
bool startIsOctet =
(**theStart).hasColour() && (**theStart).hasAntiColour();
bool endIsOctet =
(**p).hasColour() && (**p).hasAntiColour();
if ( DipolePartonSplitter::colourConnected(*p,*theStart) &&
startIsOctet && endIsOctet ) {
swap(next_it,theStart);
onceMore = true;
} else {
theStart = next_it;
current_chain.check();
theChains.push_back(current_chain);
current_chain.dipoles().clear();
continue;
}
}
pair<bool,bool> initial_state (false,false);
initial_state.first = (*p == incoming().first || *p == incoming().second);
initial_state.second = (*next_it == incoming().first || *next_it == incoming().second);
pair<int,int> which_in (-1,-1);
if (initial_state.first)
which_in.first = *p == incoming().first ? 0 : 1;
if (initial_state.second)
which_in.second = *next_it == incoming().first ? 0 : 1;
pair<double,double> xs (1.,1.);
if (initial_state.first)
xs.first = *p == incoming().first ? fractions().first : fractions().second;
if (initial_state.second)
xs.second = *next_it == incoming().first ? fractions().first : fractions().second;
pair<PDF,PDF> pdf;
if ( which_in.first == 0 )
pdf.first = pdfs().first;
else if ( which_in.first == 1 )
pdf.first = pdfs().second;
if ( which_in.second == 0 )
pdf.second = pdfs().first;
else if ( which_in.second == 1 )
pdf.second = pdfs().second;
// In the case of a decay process register which
// parton is incoming to the decay
pair<bool,bool> decayed_parton (false,false);
if (decay) {
decayed_parton.first = (*p == currentDecay()->incoming()[0].first);
decayed_parton.second = (*next_it == currentDecay()->incoming()[0].first);
}
current_chain.dipoles().push_back(Dipole({*p,*next_it},pdf,xs,decayed_parton));
if ( onceMore ) {
next_it = theStart;
current_chain.check();
theChains.push_back(current_chain);
current_chain.dipoles().clear();
onceMore = false;
}
}
} else {
// treat 2 -> singlet, singlet -> 2 and 1 + singlet -> 1 + singlet special
// to prevent duplicate dipole
assert(DipolePartonSplitter::colourConnected(ordered.front(),ordered.back()));
pair<bool,bool> initial_state (false,false);
initial_state.first = (ordered.front() == incoming().first || ordered.front() == incoming().second);
initial_state.second = (ordered.back() == incoming().first || ordered.back() == incoming().second);
pair<int,int> which_in (-1,-1);
if (initial_state.first)
which_in.first = ordered.front() == incoming().first ? 0 : 1;
if (initial_state.second)
which_in.second = ordered.back() == incoming().first ? 0 : 1;
pair<double,double> xs (1.,1.);
if (initial_state.first)
xs.first = ordered.front() == incoming().first ? fractions().first : fractions().second;
if (initial_state.second)
xs.second = ordered.back() == incoming().first ? fractions().first : fractions().second;
pair<PDF,PDF> pdf;
if ( which_in.first == 0 )
pdf.first = pdfs().first;
else if ( which_in.first == 1 )
pdf.first = pdfs().second;
if ( which_in.second == 0 )
pdf.second = pdfs().first;
else if ( which_in.second == 1 )
pdf.second = pdfs().second;
// In the case of a decay process register which
// parton is incoming to the decay
pair<bool,bool> decayed_parton (false,false);
if (decay) {
decayed_parton.first = (ordered.front() == currentDecay()->incoming()[0].first);
decayed_parton.second = (ordered.back() == currentDecay()->incoming()[0].first);
}
current_chain.dipoles().push_back(Dipole({ordered.front(),ordered.back()},pdf,xs,decayed_parton));
}
if (!current_chain.dipoles().empty()) {
current_chain.check();
theChains.push_back(current_chain);
}
}
const map<PPtr,PPtr>&
DipoleEventRecord::prepare(tSubProPtr subpro,
tStdXCombPtr xc,
const pair<PDF,PDF>& pdf,tPPair beam,
bool dipoles) {
// set the subprocess
subProcess(subpro);
// clear the event record
outgoing().clear();
theHard.clear();
theOriginals.clear();
theDecays.clear();
theCurrentDecay = PerturbativeProcessPtr();
// extract incoming particles
PPair in = subpro->incoming();
// get the incoming momentum fractions
// don't take these from the XComb as it may be null
pair<double,double> xs;
ThePEG::Direction<0> dir(true);
xs.first = in.first->momentum().dirPlus()/beam.first->momentum().dirPlus();
dir.reverse();
xs.second = in.second->momentum().dirPlus()/beam.second->momentum().dirPlus();
xcombPtr(xc);
pdfs() = pdf;
fractions() = xs;
// use ShowerHandler to split up the hard process
PerturbativeProcessPtr hard;
DecayProcessMap decay;
ShowerHandler::currentHandler()->splitHardProcess(tPVector(subpro->outgoing().begin(),
subpro->outgoing().end()),
hard,decay);
// vectors for originals and copies of the particles
vector<PPtr> original;
vector<PPtr> copies;
// fill originals
for(unsigned int ix=0;ix<2;++ix)
original.push_back(hard->incoming()[ix].first);
for(unsigned int ix=0;ix<hard->outgoing().size();++ix)
original.push_back(hard->outgoing()[ix].first);
for(DecayProcessMap::const_iterator it=decay.begin();it!=decay.end();++it) {
fillFromDecays(it->second, original);
}
// and make copies
for ( vector<PPtr>::const_iterator p = original.begin();
p != original.end(); ++p ) {
PPtr copy = new_ptr(Particle(**p));
copies.push_back(copy);
theOriginals[*p] = copy;
}
// isolate the colour of the copies from the originals
colourIsolate(original,copies);
// set the incoming particles
incoming().first = copies[0];
ParticleVector children = incoming().first->children();
for ( ParticleVector::const_iterator c = children.begin();
c != children.end(); ++c )
incoming().first->abandonChild(*c);
incoming().second = copies[1];
children = incoming().second->children();
for ( ParticleVector::const_iterator c = children.begin();
c != children.end(); ++c )
incoming().second->abandonChild(*c);
// set the outgoing particles for the hard process
for(unsigned int ix=0;ix<hard->outgoing().size();++ix) {
if(hard->outgoing()[ix].first->coloured())
outgoing().push_back(theOriginals[hard->outgoing()[ix].first]);
else
theHard.push_back(theOriginals[hard->outgoing()[ix].first]);
}
if ( dipoles ) {
PList cordered = colourOrdered(incoming(),outgoing());
- findChains(cordered,false);
+ if ( !cordered.empty() )
+ findChains(cordered,false);
}
// sort out the decays
for(auto const & dec : decay) {
// If the decay particle is in original it needs
// to be added to the decays and the decay needs to be
// changed to the copied particles.
if ( theOriginals.find(dec.second->incoming()[0].first) != theOriginals.end() ) {
theDecays[theOriginals[dec.second->incoming()[0].first]] = dec.second;
PerturbativeProcessPtr decayProc = theDecays[theOriginals[dec.second->incoming()[0].first]];
separateDecay(decayProc);
}
else {
assert( find( copies.begin(), copies.end(), dec.second->incoming()[0].first ) != copies.end() );
theDecays[dec.second->incoming()[0].first] = dec.second;
}
}
PList::const_iterator XFirst, XLast;
if ( !theHard.empty() ) {
XFirst = theHard.begin();
XLast = theHard.end();
} else {
XFirst = outgoing().begin();
XLast = outgoing().end();
}
thePX = (**XFirst).momentum();
++XFirst;
for ( ; XFirst != XLast; ++XFirst )
thePX += (**XFirst).momentum();
identifyEventType();
return theOriginals;
}
void DipoleEventRecord::slimprepare(tSubProPtr subpro,
tStdXCombPtr xc,
const pair<PDF,PDF>& pdf,tPPair beam,
bool dipoles) {
// set the subprocess
subProcess(subpro);
// clear the event record
outgoing().clear();
theHard.clear();
theOriginals.clear();
theDecays.clear();
theCurrentDecay = PerturbativeProcessPtr();
// extract incoming particles
PPair in = subpro->incoming();
// get the beam
// get the incoming momentum fractions
// don't take these from the XComb as it may be null
pair<double,double> xs;
ThePEG::Direction<0> dir(true);
xs.first = in.first->momentum().dirPlus()/beam.first->momentum().dirPlus();
dir.reverse();
xs.second = in.second->momentum().dirPlus()/beam.second->momentum().dirPlus();
xcombPtr(xc);
pdfs() = pdf;
fractions() = xs;
incoming() = in;
for(unsigned int ix=0;ix<subpro->outgoing().size();++ix) {
if(subpro->outgoing()[ix]->coloured())
outgoing().push_back(subpro->outgoing()[ix]);
}
if ( dipoles ) {
PList cordered = colourOrdered(incoming(),outgoing());
- findChains(cordered,false);
+ if ( !cordered.empty() )
+ findChains(cordered,false);
}
}
void DipoleEventRecord::fillFromDecays(PerturbativeProcessPtr decayProc, vector<PPtr>& original) {
// Loop over the outgoing of the given perturbative process
for ( auto const & outIt : decayProc->outgoing() ) {
// Add the outgoing particle to the vector of original particles
original.push_back(outIt.first);
// Iterate through the outgoing
if ( outIt.second )
fillFromDecays( outIt.second, original);
}
}
void DipoleEventRecord::separateDecay(PerturbativeProcessPtr decayProc) {
// Iteratively replace all entries in the incoming
// with their copies.
for ( auto & inIt : decayProc->incoming() ) {
if ( theOriginals.find( inIt.first ) != theOriginals.end() )
inIt.first = theOriginals[inIt.first];
}
// Iteratively replace all entries in the outgoing
// with their copies.
for ( auto & outIt : decayProc->outgoing()) {
if ( theOriginals.count( outIt.first ) )
outIt.first = theOriginals[outIt.first];
if ( outIt.second )
separateDecay(outIt.second);
}
}
void DipoleEventRecord::clear() {
ShowerEventRecord::clear();
theDecays.clear();
theHard.clear();
theChains.clear();
theDoneChains.clear();
theOriginals.clear();
}
pair<PVector,PVector> DipoleEventRecord::tmpupdate(DipoleSplittingInfo& dsplit) {
PVector inc;
PVector out;
tcPPtr IF = incoming().first;
tcPPtr IS = incoming().second;
tcPPtr DE = dsplit.emitter();
tcPPtr DS = dsplit.spectator();
if ( IF != DE && IF != DS ) {
PPtr p = IF->data().produceParticle(IF->momentum());
inc.push_back(p);
}
else if ( IF == DE ) inc.push_back( dsplit.splitEmitter() );
else if ( IF == DS ) inc.push_back( dsplit.splitSpectator() );
if ( IS != DE && IS != DS ) {
PPtr p = IS->data().produceParticle(IS->momentum());
inc.push_back(p);
}
else if ( IS == DE ) inc.push_back( dsplit.splitEmitter() );
else if ( IS == DS ) inc.push_back( dsplit.splitSpectator() );
if ( IF != DE && IS != DE)
out.push_back( dsplit.splitEmitter());
if ( IF != DS && IS != DS)
out.push_back( dsplit.splitSpectator());
out.push_back( dsplit.emission());
for ( tcPPtr h : theHard ){
PPtr p = h->data().produceParticle(h->momentum());
if ( dsplit.splittingKinematics()->doesTransform() ) {
p->set5Momentum( dsplit.splittingKinematics()->transform(p->momentum()) );
}
out.push_back(p);
}
for ( tcPPtr p : outgoing() )
if ( p != DE &&
p != DS &&
p != dsplit.emission() ){
PPtr ou = p->data().produceParticle(p->momentum());;
if ( dsplit.splittingKinematics()->doesTransform() ){
ou->set5Momentum( dsplit.splittingKinematics()->transform(ou->momentum()) );
}
out.push_back(ou);
}
return {inc,out};
}
void DipoleEventRecord::update(DipoleSplittingInfo& dsplit) {
if ( incoming().first == dsplit.emitter() ) {
intermediates().push_back(dsplit.emitter());
incoming().first = dsplit.splitEmitter();
fractions().first /= dsplit.lastEmitterZ();
} else if ( incoming().first == dsplit.spectator() ) {
intermediates().push_back(dsplit.spectator());
incoming().first = dsplit.splitSpectator();
fractions().first /= dsplit.lastSpectatorZ();
}
if ( incoming().second == dsplit.emitter() ) {
intermediates().push_back(dsplit.emitter());
incoming().second = dsplit.splitEmitter();
fractions().second /= dsplit.lastEmitterZ();
} else if ( incoming().second == dsplit.spectator() ) {
intermediates().push_back(dsplit.spectator());
incoming().second = dsplit.splitSpectator();
fractions().second /= dsplit.lastSpectatorZ();
}
PList::iterator pos;
pos = find(outgoing().begin(), outgoing().end(), dsplit.emitter());
if (pos != outgoing().end()) {
intermediates().push_back(*pos);
*pos = dsplit.splitEmitter();
}
pos = find(outgoing().begin(), outgoing().end(), dsplit.spectator());
if (pos != outgoing().end()) {
intermediates().push_back(*pos);
*pos = dsplit.splitSpectator();
}
outgoing().push_back(dsplit.emission());
if (dsplit.splittingKinematics()->doesTransform()) {
for (PList::iterator p = intermediates().begin();
p != intermediates().end(); ++p) {
(**p).set5Momentum(dsplit.splittingKinematics()->transform((**p).momentum()));
}
for (PList::iterator h = theHard.begin();
h != theHard.end(); ++h) {
(**h).set5Momentum(dsplit.splittingKinematics()->transform((**h).momentum()));
}
for (PList::iterator p = outgoing().begin();
p != outgoing().end(); ++p) {
if ((*p) != dsplit.splitEmitter() &&
(*p) != dsplit.splitSpectator() &&
(*p) != dsplit.emission())
(**p).set5Momentum(dsplit.splittingKinematics()->transform((**p).momentum()));
}
}
// Handle updates related to decays
// Showering of decay processes
// Treat the evolution of the incoming
// decayed particle as in backward evolution
if ( dsplit.isDecayProc() ) {
// Create a pointer to the decay process
PerturbativeProcessPtr decayProc = currentDecay();
// Add the emission to the outgoing of the decay process
decayProc->outgoing().push_back( {dsplit.emission(), PerturbativeProcessPtr() });
// Bools to be used throughout
const bool decayedEmtr = dsplit.index().incomingDecayEmitter();
const bool decayedSpec = dsplit.index().incomingDecaySpectator();
/*
In the current implementation, **following the hard process**
all particles in theDecays evolve independently
e.g. if we have W -> XYZ where all X, Y and Z need to be
showered and decayed, we only identify them as needing decaying
(and hence put them in theDecays) AFTER showering the decay of W.
Hence, XYZ are not even in theDecays until W has been fully
showered and then they are decayed and showered completely independently
KEY POINT - Never need to update other entries of theDecays
Note: The PPtr in theDecays should remain unchanged and all changes
should be made to the relative PerturbativeProcess.
*/
// Splittings from dipoles in the decay process which
// do not have the decayed parton as emitter or spectator.
// Update the decay process in theDecays
if ( !decayedEmtr && !decayedSpec ) {
// Find and replace the old spectator and
// emitter in the outgoing of the decay process
bool decayProcEm = false;
bool decayProcSp = false;
for ( auto & outIt : decayProc->outgoing() ) {
if ( !decayProcEm && outIt.first == dsplit.emitter() ) {
outIt = {dsplit.splitEmitter(), PerturbativeProcessPtr()};
decayProcEm = true;
}
if ( !decayProcSp && outIt.first == dsplit.spectator() ) {
outIt = {dsplit.splitSpectator(), PerturbativeProcessPtr() };
decayProcSp = true;
}
if ( decayProcEm && decayProcSp )
break;
}
// Test that nothing strange is happening
assert( (decayProcEm && decayProcSp) );
return;
}
// The spectator is the decayed particle
else if ( decayedSpec ) {
// Update the dipole event record intermediates
intermediates().push_back(dsplit.splitSpectator());
// Update the the decayProcess incoming
decayProc->incoming().clear();
decayProc->incoming().push_back({dsplit.splitSpectator(),decayProc});
// Update the decay process outgoing
// Replace the old emitter with the new emitter
for ( auto & outEmtrIt : decayProc->outgoing() ) {
if ( outEmtrIt.first == dsplit.emitter() ){
outEmtrIt = {dsplit.splitEmitter(), PerturbativeProcessPtr() };
break;
}
}
// Perform the recoil transformation
// Find all particles in the recoil system
PList recoilSystem;
for ( auto const & outIt : decayProc->outgoing() ) {
if ( outIt.first != dsplit.splitEmitter() && outIt.first != dsplit.emission() ) {
recoilSystem.push_back(outIt.first);
}
}
dsplit.splittingKinematics()->decayRecoil( recoilSystem );
return;
}
// The emitter is the decayed particle
else {
throw Exception()
<< "DipoleEventRecord: The emitter as a decayed particle is currently not implemented."
<< Exception::runerror;
assert( currentDecay()->incoming()[0].first == dsplit.emitter() && decayedEmtr && !decayedSpec );
// Update the dipole event record intermediates
intermediates().push_back(dsplit.splitEmitter());
// Update the the decayProcess incoming
decayProc->incoming().clear();
decayProc->incoming().push_back({dsplit.splitEmitter(),decayProc});
// Update the decay process outgoing
// Replace the old spectator with the new spectator
for (auto & outSpecIt : decayProc->outgoing() ) {
if ( outSpecIt.first == dsplit.spectator() ){
outSpecIt = { dsplit.splitSpectator(), PerturbativeProcessPtr() };
break;
}
}
// Perform the recoil transformation
assert(dsplit.splittingKinematics()->isDecay());
// Find all particles in the recoil system
PList recoilSystem;
for ( auto const & outIt : decayProc->outgoing() ) {
if ( outIt.first != dsplit.splitSpectator() && outIt.first != dsplit.emission() ) {
recoilSystem.push_back(outIt.first);
}
}
dsplit.splittingKinematics()->decayRecoil( recoilSystem );
return;
}
}
}
void
DipoleEventRecord::split(list<Dipole>::iterator dip,
list<DipoleChain>::iterator ch,
DipoleSplittingInfo& dsplit,
pair<list<Dipole>::iterator,list<Dipole>::iterator>& childIterators,
DipoleChain*& firstChain, DipoleChain*& secondChain,
bool colourSpectator) {
static DipoleChain empty;
pair<Dipole,Dipole> children = dip->split(dsplit,colourSpectator);
list<Dipole>::iterator breakup =
ch->insertSplitting(dip,children,childIterators);
if ( breakup == ch->dipoles().end() ) {
firstChain = &(*ch);
secondChain = &empty;
} else {
DipoleChain other;
other.dipoles().splice(other.dipoles().end(),ch->dipoles(),breakup,ch->dipoles().end());
chains().push_back(other);
firstChain = &(*ch);
secondChain = &(chains().back());
// explicitly fix iterators in case the splice implementation
// at hand does invalidate iterators (the SGI docu says, it doesn't,
// but it seems that this behaviour is not part of the standard)
childIterators.first = --firstChain->dipoles().end();
childIterators.second = secondChain->dipoles().begin(); }
if ( !colourSpectator ) {
update(dsplit); // otherwise done by recoil(...)
}
}
pair<PVector,PVector> DipoleEventRecord::tmpsplit(list<Dipole>::iterator dip,
list<DipoleChain>::iterator ,
DipoleSplittingInfo& dsplit,
pair<list<Dipole>::iterator,list<Dipole>::iterator>& ,
DipoleChain*& , DipoleChain*& ,
bool colourSpectator) {
dip->tmpsplit(dsplit,colourSpectator);
return tmpupdate(dsplit); // otherwise done by recoil(...)
}
void DipoleEventRecord::recoil(list<Dipole>::iterator dip,
list<DipoleChain>::iterator ch,
DipoleSplittingInfo& dsplit) {
dip->recoil(dsplit);
ch->updateDipole(dip);
update(dsplit);
}
list<pair<list<Dipole>::iterator,list<DipoleChain>::iterator> >
DipoleEventRecord::inDipoles() {
list<pair<list<Dipole>::iterator,list<DipoleChain>::iterator> > res;
for ( list<DipoleChain>::iterator chit = theDoneChains.begin();
chit != theDoneChains.end(); ++chit ) {
bool haveOne = false;
for ( list<Dipole>::iterator dit = chit->dipoles().begin();
dit != chit->dipoles().end(); ++dit ) {
if ( dit->leftPDF().pdf() || dit->rightPDF().pdf() ) {
haveOne = true;
break;
}
}
if ( haveOne ) {
theChains.splice(theChains.begin(),theDoneChains,chit);
for ( list<Dipole>::iterator dit = theChains.front().dipoles().begin();
dit != theChains.front().dipoles().end(); ++dit ) {
if ( dit->leftPDF().pdf() || dit->rightPDF().pdf() ) {
res.push_back({dit,theChains.begin()});
}
}
}
}
return res;
}
void DipoleEventRecord::transform(const SpinOneLorentzRotation& rot) {
Lorentz5Momentum tmp;
for (PList::iterator p = intermediates().begin();
p != intermediates().end(); ++p) {
tmp = (**p).momentum(); tmp = rot * tmp;
(**p).set5Momentum(tmp);
}
for (PList::iterator h = theHard.begin();
h != theHard.end(); ++h) {
tmp = (**h).momentum(); tmp = rot * tmp;
(**h).set5Momentum(tmp);
}
for (PList::iterator p = outgoing().begin();
p != outgoing().end(); ++p) {
tmp = (**p).momentum(); tmp = rot * tmp;
(**p).set5Momentum(tmp);
}
}
tPPair DipoleEventRecord::fillEventRecord(StepPtr step, bool firstInteraction, bool) {
PPtr inSubPro = subProcess()->incoming().first;
PPtr inParticle;
if ( !(inSubPro->parents().empty()) )
inParticle = inSubPro->parents()[0];
else
inParticle = inSubPro;
PPtr inParton = theOriginals[inSubPro];
theOriginals.erase(inSubPro);
updateColour(incoming().first,true);
if ( inParticle != inSubPro )
inParticle->abandonChild(inSubPro);
inParton->addChild(inSubPro);
if ( inParticle != inSubPro )
inParticle->addChild(incoming().first);
intermediates().push_back(inSubPro);
intermediates().push_back(inParton);
// Repeat all the above for the second incoming particle
inSubPro = subProcess()->incoming().second;
if ( !(inSubPro->parents().empty()) )
inParticle = inSubPro->parents()[0];
else
inParticle = inSubPro;
inParton = theOriginals[inSubPro];
theOriginals.erase(inSubPro);
updateColour(incoming().second,true);
if ( inParticle != inSubPro )
inParticle->abandonChild(inSubPro);
inParton->addChild(inSubPro);
if ( inParticle != inSubPro )
inParticle->addChild(incoming().second);
intermediates().push_back(inSubPro);
intermediates().push_back(inParton);
// theOriginals is populated in ::prepare and contains all of the incoming and outgoing particles of the original hard process
// Here outgoing particles from theOriginals are added into the intermediates()
while ( !theOriginals.empty() ) {
PPtr outSubPro = theOriginals.begin()->first;
PPtr outParton = theOriginals.begin()->second;
// workaround for OS X Mavericks LLVM libc++
#ifdef _LIBCPP_VERSION
map<PPtr,PPtr>::const_iterator beg = theOriginals.begin();
#else
map<PPtr,PPtr>::iterator beg = theOriginals.begin();
#endif
theOriginals.erase(beg);
updateColour(outParton,true);
outSubPro->addChild(outParton);
intermediates().push_back(outSubPro);
}
// Update the intermediates of the step
step->addIntermediates(intermediates().begin(),intermediates().end());
for (auto const & p : outgoing())
step->addDecayProduct( p );
for (auto const & p : theHard)
step->addDecayProduct( p );
if ( firstInteraction &&
(incoming().first->coloured() ||
incoming().second->coloured() ) ) {
ShowerHandler::currentHandler()->lastExtractor()
->newRemnants(subProcess()->incoming(),incoming(),step);
}
step->addIntermediate(incoming().first);
step->addIntermediate(incoming().second);
return incoming();
}
bool DipoleEventRecord::prepareDecay( PerturbativeProcessPtr decayProc ) {
// Create objects containing the incoming and outgoing partons,
// required as inputs for colourOrdered.
PList out;
for( auto const & dec : decayProc->outgoing()) {
if(dec.first->coloured()) {
out.push_back(dec.first);
}
}
// Only need to shower if we have coloured outgoing particles
if ( out.empty() )
return false;
else {
// For the incoming, use a PPair containing the incoming and a null pointer
PPair in;
in.first = decayProc->incoming()[0].first;
// Create an ordered list of particles
PList cordered;
cordered = colourOrdered(in,out);
// Find the dipole chains for this decay
findChains(cordered,true);
return true;
}
}
Energy DipoleEventRecord::decay(PPtr incoming, bool& powhegEmission) {
// get the process
PerturbativeProcessPtr process = theDecays[incoming];
assert(process);
//tDMPtr decayMode = new_ptr(DecayMode());
tDMPtr decayMode = DMPtr();
// Do not decay particles that have already been decayed
// Note the herwig decayer deals with colour connections
if ( process->outgoing().empty() ) {
process->incoming()[0].first = incoming;
DecayProcessMap decay;
// Decay the particle, returning a pointer to the decay mode
decayMode = ShowerHandler::currentHandler()->decay(process,decay,true);
}
// Sort out the colour connections of particles already decayed
else {
// sort out the colour of the incoming
map<tColinePtr,tColinePtr> cmap;
if(incoming->colourLine())
cmap[process->incoming()[0].first->colourLine()] = incoming->colourLine();
if(incoming->antiColourLine())
cmap[process->incoming()[0].first->antiColourLine()] = incoming->antiColourLine();
// fix colours of outgoing
for(auto const & outg : process->outgoing()) {
map<tColinePtr,tColinePtr>::iterator it =
cmap.find(outg.first->colourLine());
if(it!=cmap.end()) {
ColinePtr c1=outg.first->colourLine();
c1->removeColoured(outg.first);
it->second->addColoured(outg.first);
}
it = cmap.find(outg.first->antiColourLine());
if(it!=cmap.end()) {
ColinePtr c1=outg.first->antiColourLine();
c1->removeAntiColoured(outg.first);
it->second->addAntiColoured(outg.first);
}
}
// swap the incoming
process->incoming()[0].first = incoming;
}
// Set the scale of all particles involved in the decay process to the
// mass of the decaying particle
// Initialise the scale for the evolution of
// the parton shower following the decay
Energy showerScale = ZERO;
// Set the scale for the evolution of the shower
showerScale = process->incoming()[0].first->momentum().m();
Energy2 decayScaleSqr = sqr( showerScale );
process->incoming()[0].first->scale( decayScaleSqr );
for(auto & outg : process->outgoing()) {
outg.first->scale( decayScaleSqr );
}
// Update the decaying particle in the process and the event
PList::iterator posOut = find(outgoing().begin(), outgoing().end(), incoming);
PList::iterator posHard = find(hard().begin(), hard().end(), incoming);
assert((posOut!=outgoing().end() && posHard==hard().end()) ||
(posOut==outgoing().end() && posHard!=hard().end()) );
if ( posOut!=outgoing().end() ) {
outgoing().erase(posOut);
}
else {
hard().erase(posHard);
}
intermediates().push_back(process->incoming()[0].first);
// Populate the children of the incoming
for(auto const & outg : process->outgoing()) {
PPtr outgoing = outg.first;
process->incoming()[0].first->addChild(outgoing);
}
// If a decayed particle is not decayed above,
// e.g. a W in a 3-body top decay, find its decaymode.
if ( powhegEmission && !decayMode ) {
string tag = incoming->dataPtr()->name() + "->";
// Must use OrderedParticles for a tag search
ShowerHandler::OrderedParticles decayOut;
for(auto const & outg : process->outgoing()) {
decayOut.insert(outg.first->dataPtr());
}
// Construct the tag
for(auto const & dec : decayOut) {
if( dec!=*decayOut.begin() ) tag += ",";
tag +=dec->name();
}
tag += ";";
// Find the decay mode
decayMode = ShowerHandler::currentHandler()->findDecayMode(tag);
}
// Perform the powheg emission
if ( powhegEmission ) {
if ( decayMode ) {
HwDecayerBasePtr decayer;
decayer = dynamic_ptr_cast<HwDecayerBasePtr>(decayMode->decayer());
if ( decayer->hasPOWHEGCorrection() ) {
// Construct a real emission process and populate its
// incoming and outcoming prior to any powheg emission
RealEmissionProcessPtr born = new_ptr( RealEmissionProcess() );
born->bornIncoming().push_back( incoming );
for(auto const & outg : process->outgoing()) {
born->bornOutgoing().push_back(outg.first);
}
// Generate any powheg emission, returning 'real'
RealEmissionProcessPtr real = decayer->generateHardest( born );
// If no emission is generated the new incoming and
// outgoing containers will be empty.
// Only do something if an emission is generated.
if ( real && real->incoming().size() != 0 ) {
assert ( real->incoming().size() == 1 );
// Update the decay process
// Note: Do not use the new incoming particle
PPtr oldEmitter;
PPtr newEmitter;
// Use the name recoiler to avoid confusion with
// the spectator in the POWHEGDecayer
// i.e. the recoiler can be coloured or non-coloured
PPtr oldRecoiler;
PPtr newRecoiler;
if ( real->emitter() == 1 ) {
oldEmitter = real->bornOutgoing()[0];
oldRecoiler = real->bornOutgoing()[1];
newEmitter = real->outgoing()[0];
newRecoiler = real->outgoing()[1];
}
else if ( real->emitter() == 2) {
oldEmitter = real->bornOutgoing()[1];
oldRecoiler = real->bornOutgoing()[0];
newEmitter = real->outgoing()[1];
newRecoiler = real->outgoing()[0];
}
PPtr emitted = real->outgoing()[ real->emitted()-1];
// Update the scales
newRecoiler->scale(oldRecoiler->scale());
showerScale = real->pT()[ShowerInteraction::QCD];
newEmitter->scale(sqr(showerScale));
emitted->scale(sqr(showerScale));
// Update the colour flow of the new outgoing particles
// Note the emitted and newEmitter are already colour
// connected by the powheg emission function
emitted->incomingColour(oldEmitter, oldEmitter->id()<0);
if ( newRecoiler->coloured() )
newRecoiler->incomingColour(oldRecoiler, oldRecoiler->id()<0);
// Update the children of the outgoing
oldRecoiler->addChild( newRecoiler );
oldEmitter->addChild( newEmitter );
oldEmitter->addChild( emitted );
// Note: The particles in the pert proc outgoing and both outgoing
// vectors of the real emission proc are in the same order
for(unsigned int ix=0;ix<real->bornOutgoing().size();++ix) {
// Update the decay process
assert(process->outgoing()[ix].first == real->bornOutgoing()[ix]);
process->outgoing()[ix].first = real->outgoing()[ix];
// Add the outgoing from the born
// decay to the event intermediates
intermediates().push_back(real->bornOutgoing()[ix]);
}
// Add the emitted to the outgoing of the decay process
process->outgoing().push_back( { emitted, PerturbativeProcessPtr() } );
}
// No powheg emission occurred:
else
powhegEmission = false;
}
// No powheg emission occurred:
else
powhegEmission = false;
}
// No powheg emission occurred:
else
powhegEmission = false;
}
// Copy the outgoing from the decay
// process to the event record
for(auto const & outg : process->outgoing()) {
if ( outg.first->coloured() )
outgoing().push_back(outg.first);
else
hard().push_back(outg.first);
}
return showerScale;
}
void DipoleEventRecord::updateDecayMom( PPtr decayParent, PerturbativeProcessPtr decayProc ) {
// Only particles that have already been decayed
// should be passed to this function
assert( !(decayProc->outgoing().empty()) );
// Create a list of the children to update their momenta
PList children;
for ( auto const & outg : decayProc->outgoing() ) {
children.push_back( outg.first );
}
// Boost the children
PList::iterator beginChildren = children.begin();
PList::iterator endChildren = children.end();
ThePEG::UtilityBase::setMomentum(beginChildren, endChildren, decayParent->momentum().vect() );
}
void DipoleEventRecord::updateDecayChainMom( PPtr decayParent, PerturbativeProcessPtr decayProc ) {
// Note - this updates the momenta of the
// outgoing of the given decay process
// Update the momenta of the outgoing from this decay
updateDecayMom( decayParent, decayProc );
// Iteratively update the momenta of the rest of the decay chain
for ( auto & outg : decayProc->outgoing() ) {
// If a child has a corresponding pert proc
// then it has decay products
if ( outg.second ) {
for ( auto & dec : theDecays ) {
if(dec.second==outg.second) {
dec.first->setMomentum(outg.first->momentum());
break;
}
}
// Iteratively update any decay products
if ( !outg.second->outgoing().empty() )
updateDecayChainMom( outg.first, outg.second );
}
}
}
void DipoleEventRecord::updateDecays(PerturbativeProcessPtr decayProc, bool iterate) {
// Note - This does not update the momenta of the outgoing
// of decayProc.
// i.e. it is for use following the (non-)showering
// of a decay when the daughter momentum are correct.
// With iterate = true, this updates the rest of the decay chain.
// Loop over the outgoing from this decay
for ( auto & outg : decayProc->outgoing() ) {
if ( outg.second && !outg.second->outgoing().empty() ) {
// Outgoing particles which have already been decayed
PPtr newDecayed = outg.first;
PerturbativeProcessPtr newDecayProc = outg.second;
// Update the outgoing momenta from this decay
updateDecayMom( newDecayed, newDecayProc);
// If this decay is already in theDecays then erase it
for ( auto const & dec : theDecays ) {
if(dec.second==newDecayProc) {
theDecays.erase(dec.first);
break;
}
}
// Add to theDecays
theDecays[newDecayed] = newDecayProc;
//assert(theDecays[newDecayed]->incoming()[0].second==decayProc);
// Iteratively update theDecays from the decay chain
if ( iterate )
updateDecays( newDecayProc );
}
// Deal with any outgoing which need to be decayed
else if ( ShowerHandler::currentHandler()->decaysInShower(outg.first->id()) ) {
PerturbativeProcessPtr newDecay=new_ptr(PerturbativeProcess());
newDecay->incoming().push_back({ outg.first , decayProc } );
theDecays[outg.first] = newDecay;
}
}
}
void DipoleEventRecord::debugLastEvent(ostream& os) const {
bool first = ShowerHandler::currentHandler()->firstInteraction();
os << "--- DipoleEventRecord ----------------------------------------------------------\n";
os << " the " << (first ? "hard" : "secondary") << " subprocess is:\n"
<< (*subProcess());
os << " using PDF's " << pdfs().first.pdf() << " and "
<< pdfs().second.pdf() << "\n";
os << " chains showering currently:\n";
for ( list<DipoleChain>::const_iterator chit = theChains.begin();
chit != theChains.end(); ++chit )
os << (*chit);
os << " chains which finished showering:\n";
for ( list<DipoleChain>::const_iterator chit = theDoneChains.begin();
chit != theDoneChains.end(); ++chit )
os << (*chit);
os << "--------------------------------------------------------------------------------\n";
os << flush;
}
diff --git a/Shower/Dipole/Merging/MergingFactory.cc b/Shower/Dipole/Merging/MergingFactory.cc
--- a/Shower/Dipole/Merging/MergingFactory.cc
+++ b/Shower/Dipole/Merging/MergingFactory.cc
@@ -1,628 +1,648 @@
// -*- C++ -*-
//
// MergeboxFactory.cc is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2012 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
//
// This is the implementation of the non-inlined, non-templated member
// functions of the MergeboxFactory class.
//
#include "MergingFactory.h"
#include "Node.h"
+#include "ThePEG/Repository/Repository.h"
#include "ThePEG/Utilities/ColourOutput.h"
using namespace Herwig;
using std::ostream_iterator;
IBPtr MergingFactory::clone() const {
return new_ptr(*this);
}
IBPtr MergingFactory::fullclone() const {
return new_ptr(*this);
}
void MergingFactory::doinit(){
MatchboxFactory::doinit();
if (subProcessGroups()) {
throw InitException() << "There are no subprocess groups in merging!";
}
}
+void MergingFactory::productionMode() {
+ if(M()<0)
+ for ( vector<Ptr<MatchboxAmplitude>::ptr>::iterator amp
+ = amplitudes().begin(); amp != amplitudes().end(); ++amp ) {
+ Repository::clog() << "One-loop contributions from '"
+ << (**amp).name()
+ << "' are not required and will be disabled.\n"
+ << flush;
+ (**amp).disableOneLoop();
+ }
+ MatchboxFactory::productionMode();
+}
+
+
void MergingFactory::fillMEsMap() {
olpProcesses().clear();
assert( getProcesses().size() == 1 );
processMap[0] = getProcesses()[0];
if ( MH()->M() >= 0 )
setHighestVirt(processMap[0].size()+MH()->M());
MH()->N0(processMap[0].size());
for ( int i = 1 ; i <= MH()->N() ; ++i ) {
processMap[i] = processMap[i - 1];
processMap[i].push_back("j");
}
for ( int i = 0 ; i <= MH()->N() ; ++i ) {
const bool below_maxNLO = i < MH()->M() + 1;
vector<MatchboxMEBasePtr> ames
= makeMEs(processMap[i], orderInAlphaS() + i, below_maxNLO );
copy(ames.begin(), ames.end(), back_inserter(pureMEsMap()[i]));
}
}
#include "Herwig/MatrixElement/Matchbox/Base/DipoleRepository.h"
void MergingFactory::prepare_BV(int i) {
// check if we have virtual contributions
bool haveVirtuals = true;
for ( auto born : pureMEsMap()[i]) {
prepareME(born);
if ( born->isOLPTree() ) {
int id = orderOLPProcess(born->subProcess(),
born->matchboxAmplitude(),
ProcessType::treeME2);
born->olpProcess(ProcessType::treeME2,id);
id = orderOLPProcess(born->subProcess(),
born->matchboxAmplitude(),
ProcessType::colourCorrelatedME2);
born->olpProcess(ProcessType::colourCorrelatedME2,id);
bool haveGluon = false;
for ( const auto & p : born->subProcess().legs )
if ( p->id() == 21 ) {
haveGluon = true;
break;
}
if ( haveGluon ) {
id = orderOLPProcess(born->subProcess(),
born->matchboxAmplitude(),
ProcessType::spinColourCorrelatedME2);
born->olpProcess(ProcessType::spinColourCorrelatedME2,id);
}
}
if ( born->isOLPLoop() && i <= MH()->M() ) {
int id = orderOLPProcess(born->subProcess(),
born->matchboxAmplitude(),
ProcessType::oneLoopInterference);
born->olpProcess(ProcessType::oneLoopInterference,id);
if ( !born->onlyOneLoop() && born->needsOLPCorrelators() ) {
id = orderOLPProcess(born->subProcess(),
born->matchboxAmplitude(),
ProcessType::colourCorrelatedME2);
born->olpProcess(ProcessType::colourCorrelatedME2,id);
}
}
haveVirtuals &= born->haveOneLoop();
}
// check for consistent conventions on virtuals, if we are to include MH()->M()
if (!(i > MH()->M()||haveVirtuals))
throw InitException()
<< MH()->M()
<< " NLO corrections requested,\n"
<< "but no virtual contributions are found.";
for ( auto & virt : DipoleRepository::insertionIOperators(dipoleSet()) )
virt->factory(this);
for ( auto & virt : DipoleRepository::insertionPKOperators(dipoleSet()) )
virt->factory(this);
}
void MergingFactory::prepare_R(int i) {
for ( auto real : pureMEsMap()[i])
prepareME(real);
}
#include "Herwig/MatrixElement/Matchbox/Base/DipoleRepository.h"
void MergingFactory::getVirtuals(MatchboxMEBasePtr nlo, bool clone){
const auto & partons = nlo->diagrams().front()->partons();
for ( auto I : DipoleRepository::insertionIOperators(dipoleSet()) )
if ( I->apply(partons) ){
auto myI = I;
if ( clone ) myI = I->cloneMe();
nlo->virtuals().push_back(myI);
}
for ( auto PK : DipoleRepository::insertionPKOperators(dipoleSet()) )
if ( PK->apply(partons) ){
auto myPK = PK;
if ( clone ) myPK = PK->cloneMe();
nlo->virtuals().push_back(myPK);
}
}
void MergingFactory::pushB(MatchboxMEBasePtr born, int i) {
MatchboxMEBasePtr bornme = born->cloneMe();
bornme->maxMultCKKW(1);
bornme->minMultCKKW(0);
string pname = fullName() + "/" + bornme->name() + ".Born";
if ( !(generator()->preinitRegister(bornme, pname)) )
throw InitException()
<< "Born ME "<< pname << " already existing.";
if (MH()->gamma()!=1.)
getVirtuals(bornme,false);
NodePtr clusternode = new_ptr(Node(bornme, 0, MH()));
clusternode->deepHead(clusternode);
MH()->firstNodeMap(bornme,clusternode);
bornme->factory(this);
bornme->merger(MH());
vector<NodePtr> current = {{clusternode}};
vector<NodePtr> children;
unsigned int k = 1;
while ( ! thePureMEsMap[i - k].empty() ) {
for ( auto tmp : current ){//j
tmp->birth(thePureMEsMap[i - k]);
for ( auto tmpchild : tmp->children() ) {//m
children.push_back(tmpchild);
}
}
current = children;
children.clear();
++k;
}
if ( MH()->N() > i )
bornme->needsCorrelations();
else
bornme->needsNoCorrelations();
bornme->cloneDependencies();
MEs().push_back(bornme);
}
void MergingFactory::pushV(MatchboxMEBasePtr born, int i) {
MatchboxMEBasePtr nlo = born->cloneMe();
string pname = fullName() + "/" + nlo->name() + ".Virtual";
if ( !(generator()->preinitRegister(nlo, pname)) )
throw InitException()
<< "Virtual ME "<< pname << " already existing.";
////////////////////////////////////NLO///////////////////////////
nlo->virtuals().clear();
getVirtuals(nlo , false);
if ( nlo->virtuals().empty() )
throw InitException()
<< "No insertion operators have been found for "
<< born->name() << ".\n";
nlo->doOneLoopNoBorn();
////////////////////////////////////NLO///////////////////////////
NodePtr clusternode = new_ptr(Node(nlo, 0,MH()));
clusternode->deepHead(clusternode);
clusternode->virtualContribution(true);
MH()->firstNodeMap(nlo,clusternode);
nlo->merger(MH());
vector<NodePtr> current = {{clusternode}};
vector<NodePtr> children;
unsigned int k = 1;
while ( ! thePureMEsMap[i - k].empty() ) {
for ( auto tmp : current ){
tmp->birth(thePureMEsMap[i - k]);
for ( auto tmpchild : tmp->children())
children.push_back(tmpchild);
}
current = children;
children.clear();
++k;
}
if ( nlo->isOLPLoop() ) {
int id = orderOLPProcess(nlo->subProcess(),
born->matchboxAmplitude(),
ProcessType::oneLoopInterference);
nlo->olpProcess(ProcessType::oneLoopInterference,id);
if ( !nlo->onlyOneLoop() && nlo->needsOLPCorrelators() ) {
id = orderOLPProcess(nlo->subProcess(),
born->matchboxAmplitude(),
ProcessType::colourCorrelatedME2);
nlo->olpProcess(ProcessType::colourCorrelatedME2,id);
}
}
nlo->needsCorrelations();
nlo->cloneDependencies();
MEs().push_back(nlo);
}
void MergingFactory::pushR(MatchboxMEBasePtr born, int i) {
MatchboxMEBasePtr bornme = born->cloneMe();
string pname = fullName() + "/" + bornme->name() + ".Real";
if ( !(generator()->preinitRegister(bornme, pname)) )
throw InitException()
<< "Subtracted ME " << pname << " already existing.";
NodePtr clusternode = new_ptr(Node(bornme, 1, MH()));
clusternode->deepHead(clusternode);
clusternode->subtractedReal(true);
MH()->firstNodeMap(bornme,clusternode);
bornme->merger(MH());
vector<NodePtr> current = {{clusternode}};
vector<NodePtr> children;
unsigned int k = 1;
while ( ! thePureMEsMap[i - k].empty() ) {
for ( auto tmp : current ){
tmp->birth(thePureMEsMap[i - k]);
for ( auto tmpchild : tmp->children())
children.push_back(tmpchild);
}
current = children;
children.clear();
++k;
}
if(clusternode->children().empty()){
// This is a finite real contribution.
// This process is included in the LO merging.
return;
}
if ( MH()->N() > i ) bornme->needsCorrelations();
else bornme->needsNoCorrelations();
bornme->cloneDependencies(pname);
MEs().push_back(bornme);
}
// MergingFactory should never order OLPs here,
// they're done elsewhere.
void MergingFactory::orderOLPs() {}
#include "ThePEG/Utilities/StringUtils.h"
vector<string> MergingFactory::parseProcess(string in) {
vector<string> process = StringUtils::split(in);
if ( process.size() < 3 )
throw Exception()
<< "MatchboxFactory: Invalid process."<< Exception::runerror;
for ( string & p : process) {
p = StringUtils::stripws(p);
}
theN = 0;
bool prodprocess = true;
vector<string> result;
for ( const string & p : process ) {
if ( p == "->" )
continue;
if (p=="[") {
prodprocess = false;
} else if (p=="]") {
prodprocess = false;
// TODO what if there's stuff after the bracket?
assert( p == process.back() );
break;
} else if (p=="[j") {
prodprocess = false;
++theN;
} else if (p=="j" && !prodprocess) {
++theN;
prodprocess = false;
} else if (p=="j]") {
++theN;
prodprocess = false;
// TODO what if there's stuff after the bracket?
assert( p == process.back() );
break;
} else if ( prodprocess ) {
result.push_back(p);
} else {
throw InitException()
<< "Unknown particle class \"" << p << '"'
<< " in the process definition merging bracket.\n"
<< "Only jets (\"j\") are supported at the moment.";
}
}
return result;
}
#include <boost/progress.hpp>
void MergingFactory::setup() {
useMe();
DipoleShowerHandlerPtr dsh=dynamic_ptr_cast<DipoleShowerHandlerPtr>(this->CKKWHandler());
if(! dsh )throw InitException() << "The showerhandlerfor the MergingFactory must be the DipoleShower. ";
dsh->setMerger(MH());
MH()->largeNBasis()->factory(this);
MH()->setFactory(this);
MH()->setDipoleShower(dsh);
if(!ransetup){
generator()->log() <<"\nStarting merging setup.\n\n";
olpProcesses().clear();
externalAmplitudes().clear();
// We set the couplings in the ME to be fixed
// and reweight in the history weight for this.
setFixedCouplings(true);
setFixedQEDCouplings(true);
// rebind the particle data objects, can't use rebind() function
for ( auto & g : particleGroups()) {
for ( auto & p : g.second) {
p = getParticleData(p->id());
}
}
const PDVector& partons = particleGroups()["j"];
unsigned int nl = 0;
for ( const auto p : partons ) {
const Energy mass = p->hardProcessMass();
const long pid = p->id();
if ( abs(pid) < 7 && mass == ZERO )
++nl;
if ( pid > 0 && pid < 7 && mass == ZERO )
nLightJetVec( pid );
if ( pid > 0 && pid < 7 && mass != ZERO )
nHeavyJetVec( pid );
}
nLight(nl/2);
const PDVector& partonsInP = particleGroups()["p"];
for ( const auto pip : partonsInP )
if ( pip->id() > 0 && pip->id() < 7 && pip->hardProcessMass() == ZERO )
nLightProtonVec( pip->id() );
for ( auto & amp: amplitudes() ) amp->factory(this);
//fill the amplitudes
if ( !amplitudes().empty() ) fillMEsMap();
// prepare the Born and virtual matrix elements
for ( int i = 0 ; i <= max(0, MH()->N()) ; ++i ) prepare_BV(i);
// prepare the real emission matrix elements
for ( int i = 0 ; i <= MH()->N() ; ++i ) prepare_R(i);
if (MH()->N()<=MH()->M()) {
throw InitException() << "Merging: The number of NLOs need to be"
<< "\nsmaller than the number of LO processes.\n";
}
// Order the external Amplitudes.
orderOLPs();
// start creating matrix elements
MEs().clear();
// count the subprocesses
size_t numb = 0;
size_t numv = 0;
size_t numr = 0;
for (int i = 0; i <= max(0, MH()->N()) ; ++i ) {
for ( auto born : thePureMEsMap[i] ) {
if (bornContributions()
) {
numb++;
}
}
}
for (int i = 0 ; i <=max(0, MH()->N()); ++i )
for ( auto virt : thePureMEsMap[i] )
if ( virtualContributions() && i <= MH()->M()) {
numv++;
}
for (int i = 1; i <= max(0, MH()->N()) ; ++i )
for ( auto real : thePureMEsMap[i] )
if (realContributions() && i <= MH()->M() + 1 ){
numr++;
}
generator()->log() << ANSI::red << "Preparing Merging: ";
generator()->log() << ANSI::green << numb << " x Born " << ANSI::red;
if (MH()->M()>-1) {
generator()->log() << ANSI::yellow << numv << " x Virtual ";
generator()->log() << ANSI::blue << numr << " x Real " << ANSI::red << flush;
}
boost::progress_display * progressBar = new boost::progress_display(numb+numv+numr,generator()->log());
for (int i = 0; i <= max(0, MH()->N()) ; ++i ){
for ( auto born : thePureMEsMap[i]){
if (bornContributions() ){
pushB(born, i);
generator()->log() << ANSI::green;
++(*progressBar);
generator()->log() << ANSI::reset;
}
}
}
for (int i = 0 ; i <=max(0, MH()->N()); ++i )
for ( auto virt : thePureMEsMap[i])
if ( virtualContributions() && i <= MH()->M()){
pushV(virt, i);
generator()->log() << ANSI::yellow;
++(*progressBar);
}
for (int i = 1; i <= max(0, MH()->N()) ; ++i )
for ( auto real : thePureMEsMap[i] )
if (realContributions()&& i <= MH()->M() + 1 ){
pushR(real, i);
generator()->log() << ANSI::blue;
++(*progressBar);
}
generator()->log() << ANSI::reset;
delete progressBar;
if ( !externalAmplitudes().empty() ) {
generator()->log() << "Initializing external amplitudes." << endl;
boost::progress_display * progressBar =
new boost::progress_display(externalAmplitudes().size(),generator()->log());
for ( const auto ext : externalAmplitudes()) {
if ( ! ext->initializeExternal() ) {
throw InitException()
<< "error: failed to initialize amplitude '" << ext->name() << "'\n";
}
++(*progressBar);
}
delete progressBar;
generator()->log()
<< "---------------------------------------------------" << endl;
}
if ( !olpProcesses().empty() ) {
generator()->log() << "Initializing one-loop provider(s)." << endl;
map<Ptr<MatchboxAmplitude>::tptr, map<pair<Process, int>, int> > olps;
for (const auto oit : olpProcesses()) {
olps[oit.first] = oit.second;
}
boost::progress_display * progressBar = new boost::progress_display(olps.size(), generator()->log());
for ( const auto olpit : olps ) {
if ( !olpit.first->startOLP(olpit.second) ) {
throw InitException() << "error: failed to start OLP for amplitude '" << olpit.first->name() << "'\n";
}
++(*progressBar);
}
delete progressBar;
generator()->log()
<< "---------------------------------------------------\n" << flush;
}
generator()->log() <<"\nGenerated "<<MEs().size()<<" Subprocesses.\n"<<flush;
generator()->log()
<< "---------------------------------------------------\n" << flush;
generator()->log() <<"\n\n" << ANSI::red
<<"Note: Due to the unitarization of the higher "
<<"\nmultiplicities, the individual cross sections "
<<"\ngiven in the integration and run step are not"
<<"\nmeaningful without merging." << ANSI::reset << endl;
ransetup=true;
}
}
#include "ThePEG/Persistency/PersistentOStream.h"
#include "ThePEG/Persistency/PersistentIStream.h"
void MergingFactory::persistentOutput(PersistentOStream & os) const {
os
<< theonlymulti
<< ransetup
- << processMap << theMergingHelper <<theM<<theN;
+ << processMap << theMergingHelper <<theM<<theN<<theNonQCDCuts;
}
void MergingFactory::persistentInput(PersistentIStream & is, int) {
is
>> theonlymulti
>> ransetup
- >> processMap >> theMergingHelper >>theM>>theN;
+ >> processMap >> theMergingHelper >>theM>>theN>>theNonQCDCuts;
}
#include "ThePEG/Interface/ClassDocumentation.h"
#include "ThePEG/Utilities/DescribeClass.h"
#include "ThePEG/Interface/Reference.h"
#include "ThePEG/Interface/RefVector.h"
#include "ThePEG/Interface/Switch.h"
#include "ThePEG/Interface/Parameter.h"
#include "ThePEG/Interface/Command.h"
void MergingFactory::Init() {
static Parameter<MergingFactory, int> interfaceonlymulti("onlymulti",
"Calculate only the ME with k additional partons.",
&MergingFactory::theonlymulti, -1, -1, 0,
false, false, Interface::lowerlim);
static Switch<MergingFactory, bool> interface_Unitarized("Unitarized",
"Unitarize the cross section (default is unitarised. NLO merging must be unitarised).",
&MergingFactory::unitarized, true, false, false);
static SwitchOption interface_UnitarizedOn(interface_Unitarized, "On",
"Switch on the unitarized cross section.", true);
static SwitchOption interface_UnitarizedOff(interface_Unitarized, "Off",
"Switch off the unitarized cross section.", false);
static Reference<MergingFactory,Merger> interfaceMergingHelper("MergingHelper",
"Pointer to the Merging Helper.",
&MergingFactory::theMergingHelper, false, false, true, true, false);
static Parameter<MergingFactory, int> interfaceaddNLOLegs("NLOProcesses",
"Set the number of virtual corrections to consider. 0 is default for no virtual correction.",
&MergingFactory::theM, 0, 0, 0, false, false, Interface::lowerlim);
+
+ static Reference<MergingFactory, Cuts > interfaceNonQcdCuts("NonQCDCuts",
+ "Cut on non-QCD modified observables. Be carefull!",
+ &MergingFactory::theNonQCDCuts, false, false, true, true, false);
+
}
// *** Attention *** The following static variable is needed for the type
// description system in ThePEG. Please check that the template arguments
// are correct (the class and its base class), and that the constructor
// arguments are correct (the class name and the name of the dynamically
// loadable library where the class implementation can be found).
DescribeClass<MergingFactory, Herwig::MatchboxFactory>
describeHerwigMergingFactory("Herwig::MergingFactory", "HwDipoleShower.so");
diff --git a/Shower/Dipole/Merging/MergingFactory.h b/Shower/Dipole/Merging/MergingFactory.h
--- a/Shower/Dipole/Merging/MergingFactory.h
+++ b/Shower/Dipole/Merging/MergingFactory.h
@@ -1,162 +1,168 @@
/// -*- C++ -*-
//
/// MergingFactory.h is a part of Herwig - A multi-purpose Monte Carlo event generator
/// Copyright (C) 2002-2012 The Herwig Collaboration
//
/// Herwig is licenced under version 2 of the GPL, see COPYING for details.
/// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
#ifndef HERWIG_MergingFactory_H
#define HERWIG_MergingFactory_H
//
/// This is the declaration of the MergingFactory class.
//
#include "MergingFactory.fh"
#include "Herwig/MatrixElement/Matchbox/MatchboxFactory.h"
#include "Node.fh"
#include "Merger.h"
#include "ThePEG/Persistency/PersistentOStream.h"
#include "ThePEG/Persistency/PersistentIStream.h"
namespace Herwig {
using namespace ThePEG;
/**
* \ingroup Matchbox
* \author Johannes Bellm
*
* \brief MergingFactory automatically sets up a NLO
* QCD merging.
*
* @see \ref MergingFactoryInterfaces "The interfaces"
* defined for MergeboxFactory.
*/
class MergingFactory : public MatchboxFactory {
public:
+ ///Check consistency and switch to porduction mode.
+ void productionMode();
/// main method to setup the ME vector
virtual void setup();
/// fill all amplitudes, stored in pureMEsMap
void fillMEsMap();
/// prepare the Born and virtual matrix elements.
void prepare_BV(int i);
/// prepare the real emission matrix elements.
void prepare_R(int i);
/// push the born contributions to the ME vector.
void pushB(MatchboxMEBasePtr, int);
//push the virtual contributions to the ME vector.
void pushV(MatchboxMEBasePtr, int);
/// push the real contributions to the ME vector.
void pushR(MatchboxMEBasePtr, int);
/// order matrix elements from one loop provider.
void orderOLPs();
/// Debugging: push only multiplicities to the ME vector
/// in range of specified mulltiplicity.
int onlymulti()const {
return theonlymulti==-1?-1:(theonlymulti+processMap.find(0)->second.size());
}
/// pointer to the merging helper.
MergerPtr MH() {return theMergingHelper;}
/// maximal NLO mulitplicity: 0=NLO corrections to the productio process.
int M() const {return theM-1;}
/// leg size of highest multiplicity.
int N() const {return theN;}
/// Return the Map of matrix elements to be considered
/// (the Key is the number of additional jets)
const map<int, vector<MatchboxMEBasePtr> >& pureMEsMap() const {
return thePureMEsMap;
}
/// Access the Map of matrix elements to be considered
/// (the Key is the number of additional jets)
map<int, vector<MatchboxMEBasePtr> >& pureMEsMap() {
return thePureMEsMap;
}
//Parse a process description
virtual vector<string> parseProcess(string);
// fill the virtuals vector (these are IPK-operators)
void getVirtuals(MatchboxMEBasePtr nlo, bool clone );
// In the merged setup we only produce single phase space points.
bool subProcessGroups() const { return false;}
+ // Cut on non-QCD observables.
+ Ptr<Cuts>::ptr nonQCDCuts(){return theNonQCDCuts;}
public:
/** @name Functions used by the persistent I/O system. */
//@{
/**
* Function used to write out object persistently.
* @param os the persistent output stream written to.
*/
void persistentOutput(PersistentOStream & os) const;
/**
* Function used to read in object persistently.
* @param is the persistent input stream read from.
* @param version the version number of the object when written.
*/
void persistentInput(PersistentIStream & is, int);
//@}
static void Init();
protected:
/** @name Standard Interfaced functions. */
//@{
/**
* Initialize this object after the setup phase before saving an
* EventGenerator to disk.
* @throws InitException if object could not be initialized properly.
*/
virtual void doinit();
//@}
protected:
/** @name Clone Methods. */
//@{
/**
* Make a simple clone of this object.
* @return a pointer to the new object.
*/
virtual IBPtr clone() const;
/**
* Make a clone of this object, possibly modifying the cloned object
* to make it sane.
* @return a pointer to the new object.
*/
virtual IBPtr fullclone() const;
//@}
private:
/// unitarise the LO contributions.
bool unitarized = true;
/// did run setup.
bool ransetup = false;
/// Debugging: push only multiplicities to the ME vector
/// in range of specified mulltiplicity.
int theonlymulti = -1;
/// maximal legsize for NLO corrections.
int theM = -1;
/// maximal legsize for LO contributions.
int theN = -1;
/// map for processes.
map< int, vector<string> > processMap;
//The matrix elements: int = number of additional jets
map< int, vector<MatchboxMEBasePtr> > thePureMEsMap;
/// the merging helper
MergerPtr theMergingHelper;
-
+ /// Cut on non-QCD modified observables.
+ Ptr<Cuts>::ptr theNonQCDCuts;
/**
* The assignment operator is private and must never be called.
* In fact, it should not even be implemented.
*/
MergingFactory & operator=(const MergingFactory &) = delete;
+
};
}
#endif /* HERWIG_MergingFactory_H */
diff --git a/Shower/Dipole/Merging/Node.cc b/Shower/Dipole/Merging/Node.cc
--- a/Shower/Dipole/Merging/Node.cc
+++ b/Shower/Dipole/Merging/Node.cc
@@ -1,538 +1,552 @@
// -*- C++ -*-
//
// This is the implementation of the non-inlined, non-templated member
// functions of the Node class.
//
#include "Node.h"
#include "MergingFactory.h"
#include "Merger.h"
using namespace Herwig;
Node::Node(MatchboxMEBasePtr nodeME, int cutstage, MergerPtr mh)
:Interfaced(),
thenodeMEPtr(nodeME),
thedipol(),
theparent(),
theCutStage(cutstage),
isOrdered(true),
theSubtractedReal(false),
theVirtualContribution(false),
theMergingHelper(mh)
{
nodeME->maxMultCKKW(1);
nodeME->minMultCKKW(0);
}
Node::Node(NodePtr deephead,
NodePtr head,
SubtractionDipolePtr dipol,
MatchboxMEBasePtr nodeME,
int cutstage)
:Interfaced(), thenodeMEPtr(nodeME),
thedipol(dipol),
theparent(head),
theDeepHead(deephead),
theCutStage(cutstage),
isOrdered(true),
theSubtractedReal(false),
theVirtualContribution(false),
theMergingHelper() //The subnodes have no merging helper
{
}
Node::~Node() { }
SubtractionDipolePtr Node::dipole() const {
return thedipol;
}
/** returns the matrix element pointer */
const MatchboxMEBasePtr Node::nodeME() const {
return thenodeMEPtr;
}
/** access the matrix element pointer */
MatchboxMEBasePtr Node::nodeME() {
return thenodeMEPtr;
}
pair<PVector , PVector> Node::getInOut( ){
PVector in;
const auto me= nodeME();
const auto pd=me->mePartonData();
for( auto i : {0 , 1} )
in.push_back(pd[i]->produceParticle( me->lastMEMomenta()[i] ) );
PVector out;
for ( size_t i = 2;i< pd.size();i++ ){
PPtr p = pd[i]->produceParticle( me->lastMEMomenta()[i] );
out.push_back( p );
}
return { in , out };
}
int Node::legsize() const {return nodeME()->legsize();}
NodePtr Node::randomChild() {
return thechildren[UseRandom::irnd(thechildren.size())];
}
bool Node::allAbove(Energy pt) {
for (NodePtr child : thechildren)
if ( child->pT() < pt )
return false;
return true;
}
Energy Node::maxChildPt(){
Energy maxi=-1*GeV;
for (NodePtr child : thechildren)maxi=max(child->pT(),maxi);
return maxi;
}
bool Node::isInHistoryOf(NodePtr other) {
while (other->parent()) {
if (other == this)
return true;
other = other->parent();
}
return false;
}
void Node::flushCaches() {
if (didflush) return;
didflush=true;
for ( auto const & ch: thechildren) {
ch->xcomb()->clean();
ch->nodeME()->flushCaches();
ch->flushCaches();
}
}
void Node::setKinematics() {
for (auto const & ch: thechildren) {
ch->dipole()->setXComb(ch->xcomb());
ch->dipole()->setKinematics();
ch->nodeME()->setKinematics();
ch->setKinematics();
}
}
void Node::clearKinematics() {
for (auto const & ch: thechildren) {
ch->dipole()->setXComb(ch->xcomb());
ch->nodeME()->clearKinematics();
ch->dipole()->clearKinematics();
ch->clearKinematics();
}
}
bool Node::generateKinematics(const double *r, bool directCut) {
didflush=false;
// If there are no children to the child process we are done.
if(children().empty()) return true;
assert(parent());
if ( ! directCut && pT() < deepHead()->MH()->mergePt()) {
// Real emission:
// If there are children to the child process,
// we now require that all subsequent children
// with pt < merging scale are in their ME region.
// Since the possible children of the real emission
// contribution are now in their ME region,
// it is clear that a second clustering is possible
// -- modulo phase space restrictions.
// Therefore the real emission contribution
// are unitarised and the cross section is
// hardly modified.
auto inOutPair = getInOut();
NodePtr rc = randomChild();
rc->dipole()->setXComb(rc->xcomb());
if(!rc->dipole()->generateKinematics(r))assert(false);
// If not in ME -> return false
if(!deepHead()->MH()->matrixElementRegion( inOutPair.first ,
inOutPair.second ,
rc->pT() ,
deepHead()->MH()->mergePt() ) )return false;
}
for (auto & ch : children() ) {
ch->dipole()->setXComb(ch->xcomb());
if ( !ch->dipole()->generateKinematics(r) ) { assert(false); }
ch->generateKinematics( r, true);
}
return true;
}
bool Node::firstgenerateKinematics(const double *r, bool directCut) {
didflush=false;
// This is called form the merging helper for the first node. So:
assert(!parent());
assert(xcomb());
+
+ if(MH()->treefactory()->nonQCDCuts()){
+ tcPDVector outdata(xcomb()->mePartonData().begin()+2,
+ xcomb()->mePartonData().end());
+ vector<LorentzMomentum> outmomenta(xcomb()->meMomenta().begin()+2,
+ xcomb()->meMomenta().end());
+
+
+ if ( !MH()->treefactory()->nonQCDCuts()->passCuts(outdata,outmomenta,
+ xcomb()->mePartonData()[0],
+ xcomb()->mePartonData()[1]) )
+ return false;
+ }
+
///// This should not be needed!!!
///// ( Warning inMerger::matrixElementRegion gets triggered.)
flushCaches();
//Set here the new merge Pt for the next phase space point.( Smearing!!!)
MH()->smearMergePt();
// If there are no children to this node, we are done here:
if (children().empty())
return true;
// directCut is for born and for virtual contributions.
// if directCut is true, then cut on the first ME region.
// call recursiv generate kinematics for subsequent nodes.
if ( directCut ){
auto inOutPair = getInOut();
NodePtr rc = randomChild();
rc->dipole()->setXComb(rc->xcomb());
if ( !rc->dipole()->generateKinematics(r) ) { return false; }
rc->nodeME()->setXComb(rc->xcomb());
if(MH()->gamma() == 1.){
if(!MH()->matrixElementRegion( inOutPair.first ,
inOutPair.second ,
rc->pT() ,
MH()->mergePt() ) ){
return false;
}
}else{
// Different treatment if gamma is not 1.
// Since the dipoles need to be calculated always
// their alpha region is touched.
// AlphaRegion != MERegion !!!
bool inAlphaPS = false;
for (auto const & ch: thechildren) {
ch->dipole()->setXComb(ch->xcomb());
if ( !ch->dipole()->generateKinematics(r) )
return false;
MH()->treefactory()->setAlphaParameter( MH()->gamma() );
inAlphaPS |= ch->dipole()->aboveAlpha();
MH()->treefactory()->setAlphaParameter( 1. );
}
NodePtr rc = randomChild();
if(!inAlphaPS&&
!MH()->matrixElementRegion( inOutPair.first ,
inOutPair.second ,
rc->pT() ,
MH()->mergePt() ) )
return false;
}
}
for (auto const & ch: thechildren) {
ch->dipole()->setXComb(ch->xcomb());
if ( !ch->dipole()->generateKinematics(r) ) { cout<<"\nCould not generate dipole kinematics";;return false; }
if( ! ch->generateKinematics(r,directCut) )return false;
}
return true;
}
StdXCombPtr Node::xcomb() const {
assert(thexcomb);
return thexcomb;
}
StdXCombPtr Node::xcomb(){
if(thexcomb)return thexcomb;
assert(parent());
thexcomb=dipole()->makeBornXComb(parent()->xcomb());
xcomb()->head(parent()->xcomb());
dipole()->setXComb(thexcomb);
return thexcomb;
}
void Node::setXComb(tStdXCombPtr xc) {
assert ( !parent() );
thexcomb=xc;
assert(thexcomb->lastParticles().first);
}
#include "Herwig/MatrixElement/Matchbox/Base/DipoleRepository.h"
void Node::birth(const vector<MatchboxMEBasePtr> & vec) {
// produce the children
vector<SubtractionDipolePtr> dipoles =
nodeME()->getDipoles(DipoleRepository::dipoles(
nodeME()->factory()->dipoleSet()), vec, true);
for ( auto const & dip : dipoles ) {
dip->doSubtraction();
NodePtr node = new_ptr(Node(theDeepHead,
this,
dip,
dip->underlyingBornME(),
theDeepHead->cutStage()));
thechildren.push_back(node);
}
}
namespace{
/**
* Triangular / Kallen function
*/
double rootOfKallen (double a, double b, double c) {
return sqrt( a*a + b*b + c*c - 2.*( a*b+a*c+b*c ) ); }
}
vector<NodePtr> Node::getNextOrderedNodes(bool normal, double hardScaleFactor) const {
vector<NodePtr> temp = children();
vector<NodePtr> res;
for (NodePtr const & child : children()) {
if(deepHead()->MH()->mergePt()>child->pT()) {
res.clear();
return res;
}
}
for (NodePtr const & child: children()) {
if (parent()&& normal) {
if ( child->pT() < pT() ) {
continue;
}
}
if ( child->children().size() != 0 ) {
for (NodePtr itChild: child->children()) {
if( itChild->pT() > child->pT()&&child->inShowerPS(itChild->pT()) ) {
res.push_back(child);
break;
}
}
}
else {
const auto sc=child->nodeME()->factory()->scaleChoice();
sc->setXComb(child->xcomb());
if ( sqr(hardScaleFactor)*
sc->renormalizationScale() >= sqr(child->pT()) &&
child->inShowerPS(hardScaleFactor*sqrt(sc->renormalizationScale()))) {
res.push_back(child);
}
}
}
return res;
}
bool Node::inShowerPS(Energy hardpT)const {
// Here we decide if the current phase space
// point can be reached from the underlying Node.
// Full phase space available -> Tilde Kinematic is always fine.
if(deepHead()->MH()->openZBoundaries()==1)
return true;
double z_ = dipole()->lastZ();
// restrict according to hard scale
if(deepHead()->MH()->openZBoundaries()==0){
pair<double, double> zbounds =
dipole()->tildeKinematics()->zBounds(pT(), hardpT);
return (zbounds.first<z_&&z_<zbounds.second);
}
// restrict according to min ( dipole scale , kinematic limit )
// where here due to the tilde kinematics always the kinematic
// limit is produced. So
assert(deepHead()->MH()->openZBoundaries()==2);
if( dipole()->bornEmitter()>1&& dipole()->bornSpectator()>1 ) return true;
bool isMassiv = (dipole()->tildeKinematics()->realEmitterData()->hardProcessMass()
+dipole()->tildeKinematics()->realEmissionData()->hardProcessMass()
+dipole()->tildeKinematics()->realSpectatorData()->hardProcessMass())!=ZERO;
Energy scale=sqrt(2.*dipole()->tildeKinematics()->bornEmitterMomentum()*
dipole()->tildeKinematics()->bornSpectatorMomentum());
Energy hard=ZERO;
assert(scale>=ZERO);
// II
if( dipole()->bornEmitter()<2&& dipole()->bornSpectator()<2 ) {
hard = min(scale,(1.-dipole()->tildeKinematics()->emitterX())
*scale/(2.*sqrt(dipole()->tildeKinematics()->emitterX())));
}else
// IF
if( dipole()->bornEmitter()<2&& dipole()->bornSpectator() >= 2){
if(isMassiv){
hard = scale * min(1.,sqrt(1.-dipole()->tildeKinematics()->emitterX()) /2.);
}
else{
hard = scale * min(1.,sqrt((1.-dipole()->tildeKinematics()->emitterX())/
dipole()->tildeKinematics()->emitterX()) /2.);
}
}
// FI
else{
if(isMassiv){
Energy2 mi2 = sqr(dipole()->tildeKinematics()->realEmitterData()->hardProcessMass());
Energy2 m2 = sqr(dipole()->tildeKinematics()->realEmissionData()->hardProcessMass());
Energy2 Mi2 = sqr(dipole()->tildeKinematics()->bornEmitterData()->hardProcessMass());
Energy2 scale=2.*dipole()->tildeKinematics()->bornEmitterMomentum()*
dipole()->tildeKinematics()->bornSpectatorMomentum();
Energy2 s = scale * (1.-dipole()->tildeKinematics()->spectatorX())/
dipole()->tildeKinematics()->spectatorX() + Mi2;
Energy2 sdip = scale + Mi2;
hard = .5 * sqrt(s) * rootOfKallen( s/s, mi2/s, m2/s );
hard = min( .5 * sqrt(sdip) * rootOfKallen( sdip/sdip, mi2/sdip, m2/sdip ),hard);
}
else{
hard = scale*min(1.,sqrt((1.-dipole()->tildeKinematics()->spectatorX())/
dipole()->tildeKinematics()->spectatorX())/2.);
}
}
pair<double, double> zbounds =
dipole()->tildeKinematics()->zBounds(pT(), hard);
return (zbounds.first<z_&&z_<zbounds.second);
}
NodePtr Node::getHistory(bool normal, double hardScaleFactor) {
NodePtr res = this;
vector<NodePtr> temp = getNextOrderedNodes(normal, hardScaleFactor);
Energy minpt = Constants::MaxEnergy;
Selector<NodePtr> subprosel;
while (temp.size() != 0) {
minpt = Constants::MaxEnergy;
subprosel.clear();
for (NodePtr const & child : temp) {
if( child->dipole()->underlyingBornME()->largeNColourCorrelatedME2(
{child->dipole()->bornEmitter(),
child->dipole()->bornSpectator()},
deepHead()->MH()->largeNBasis()) != 0.
) {
double weight = 1.;
if ( deepHead()->MH()->chooseHistory() == 0 )
weight = abs(child->dipole()->dSigHatDR()/nanobarn);
else if ( deepHead()->MH()->chooseHistory() == 1 )
weight = abs(child->dipole()->dSigHatDR()/child->nodeME()->dSigHatDRB());
else if ( deepHead()->MH()->chooseHistory() == 2 )
weight = 1.;
else if ( deepHead()->MH()->chooseHistory() == 3 )
weight = 1_GeV/child->pT();
else
assert(false);
if(weight != 0.) {
subprosel.insert(weight , child);
minpt = min(minpt, child->pT());
}
}
}
if (subprosel.empty())
return res;
res = subprosel.select(UseRandom::rnd());
temp = res->getNextOrderedNodes(true, hardScaleFactor);
}
return res;
}
pair<CrossSection, CrossSection> Node::calcDipandPS(Energy scale)const {
return dipole()->dipandPs(sqr(scale), deepHead()->MH()->largeNBasis());
}
CrossSection Node::calcPs(Energy scale)const {
return dipole()->ps(sqr(scale), deepHead()->MH()->largeNBasis());
}
CrossSection Node::calcDip(Energy scale)const {
return dipole()->dip(sqr(scale));
}
IBPtr Node::clone() const {
return new_ptr(*this);
}
IBPtr Node::fullclone() const {
return new_ptr(*this);
}
#include "ThePEG/Persistency/PersistentOStream.h"
void Node::persistentOutput(PersistentOStream & os) const {
os <<
thexcomb<<
thenodeMEPtr<<
thedipol<<
thechildren<<
theparent<<
theProjector<<
theDeepHead<<
theCutStage<<
ounit(theRunningPt, GeV)<<
theSubtractedReal<<
theVirtualContribution<<
theMergingHelper;
}
#include "ThePEG/Persistency/PersistentIStream.h"
void Node::persistentInput(PersistentIStream & is, int) {
is >>
thexcomb>>
thenodeMEPtr>>
thedipol>>
thechildren>>
theparent>>
theProjector>>
theDeepHead>>
theCutStage>>
iunit(theRunningPt, GeV)>>
theSubtractedReal>>
theVirtualContribution>>
theMergingHelper;
}
// *** Attention *** The following static variable is needed for the type
// description system in ThePEG. Please check that the template arguments
// are correct (the class and its base class), and that the constructor
// arguments are correct (the class name and the name of the dynamically
// loadable library where the class implementation can be found).
#include "ThePEG/Utilities/DescribeClass.h"
DescribeClass<Node, Interfaced>
describeHerwigNode("Herwig::Node", "HwDipoleShower.so");
void Node::Init() {
static ClassDocumentation<Node>
documentation("There is no documentation for the Node class");
}
diff --git a/Shower/ShowerHandler.cc b/Shower/ShowerHandler.cc
--- a/Shower/ShowerHandler.cc
+++ b/Shower/ShowerHandler.cc
@@ -1,1103 +1,1103 @@
// -*- C++ -*-
//
// ShowerHandler.cc is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2011 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
//
// This is the implementation of the non-inlined, non-templated member
// functions of the ShowerHandler class.
//
#include "ShowerHandler.h"
#include "ThePEG/Interface/ClassDocumentation.h"
#include "ThePEG/Interface/Reference.h"
#include "ThePEG/Interface/Parameter.h"
#include "ThePEG/Interface/ParVector.h"
#include "ThePEG/Interface/Switch.h"
#include "ThePEG/Interface/Command.h"
#include "ThePEG/PDF/PartonExtractor.h"
#include "ThePEG/PDF/PartonBinInstance.h"
#include "Herwig/PDT/StandardMatchers.h"
#include "ThePEG/Cuts/Cuts.h"
#include "ThePEG/Handlers/StandardXComb.h"
#include "ThePEG/Utilities/Throw.h"
#include "ThePEG/Utilities/StringUtils.h"
#include "ThePEG/Persistency/PersistentOStream.h"
#include "ThePEG/Persistency/PersistentIStream.h"
#include "ThePEG/Repository/EventGenerator.h"
#include "Herwig/Utilities/EnumParticles.h"
#include "Herwig/PDF/MPIPDF.h"
#include "Herwig/PDF/MinBiasPDF.h"
#include "ThePEG/Handlers/EventHandler.h"
#include "Herwig/Shower/Core/Base/ShowerTree.h"
#include "Herwig/PDF/HwRemDecayer.h"
#include <cassert>
#include "ThePEG/Utilities/DescribeClass.h"
#include "Herwig/Decay/DecayIntegrator.h"
#include "Herwig/Decay/DecayPhaseSpaceMode.h"
using namespace Herwig;
DescribeClass<ShowerHandler,CascadeHandler>
describeShowerHandler ("Herwig::ShowerHandler","HwShower.so");
ShowerHandler::~ShowerHandler() {}
tShowerHandlerPtr ShowerHandler::currentHandler_ = tShowerHandlerPtr();
void ShowerHandler::doinit() {
CascadeHandler::doinit();
// copy particles to decay before showering from input vector to the
// set used in the simulation
if ( particlesDecayInShower_.empty() )
particlesDecayInShower_.insert(inputparticlesDecayInShower_.begin(),
inputparticlesDecayInShower_.end());
ShowerTree::_vmin2 = vMin_;
ShowerTree::_spaceTime = includeSpaceTime_;
if ( profileScales() ) {
if ( profileScales()->unrestrictedPhasespace() &&
restrictPhasespace() ) {
generator()->log()
<< "ShowerApproximation warning: The scale profile chosen requires an unrestricted phase space,\n"
<< "however, the phase space was set to be restricted. Will switch to unrestricted phase space.\n"
<< flush;
restrictPhasespace_ = false;
}
}
}
IBPtr ShowerHandler::clone() const {
return new_ptr(*this);
}
IBPtr ShowerHandler::fullclone() const {
return new_ptr(*this);
}
ShowerHandler::ShowerHandler() :
maxtry_(10),maxtryMPI_(10),maxtryDP_(10),maxtryDecay_(100),
factorizationScaleFactor_(1.0),
renormalizationScaleFactor_(1.0),
hardScaleFactor_(1.0),
restrictPhasespace_(true), maxPtIsMuF_(false),
pdfFreezingScale_(2.5*GeV),
doFSR_(true), doISR_(true),
splitHardProcess_(true),
includeSpaceTime_(false), vMin_(0.1*GeV2),
reweight_(1.0) {
inputparticlesDecayInShower_.push_back( 6 ); // top
inputparticlesDecayInShower_.push_back( 23 ); // Z0
inputparticlesDecayInShower_.push_back( 24 ); // W+/-
inputparticlesDecayInShower_.push_back( 25 ); // h0
}
void ShowerHandler::doinitrun(){
CascadeHandler::doinitrun();
//can't use isMPIOn here, because the EventHandler is not set at that stage
if(MPIHandler_) {
MPIHandler_->initialize();
if(MPIHandler_->softInt())
remDec_->initSoftInteractions(MPIHandler_->Ptmin(), MPIHandler_->beta());
}
ShowerTree::_vmin2 = vMin_;
ShowerTree::_spaceTime = includeSpaceTime_;
}
void ShowerHandler::dofinish() {
CascadeHandler::dofinish();
if(MPIHandler_) MPIHandler_->finalize();
}
void ShowerHandler::persistentOutput(PersistentOStream & os) const {
os << remDec_ << ounit(pdfFreezingScale_,GeV) << maxtry_
<< maxtryMPI_ << maxtryDP_ << maxtryDecay_
<< inputparticlesDecayInShower_
<< particlesDecayInShower_ << MPIHandler_ << PDFA_ << PDFB_
<< PDFARemnant_ << PDFBRemnant_
<< includeSpaceTime_ << ounit(vMin_,GeV2)
<< factorizationScaleFactor_ << renormalizationScaleFactor_
<< hardScaleFactor_
<< restrictPhasespace_ << maxPtIsMuF_ << hardScaleProfile_
<< showerVariations_ << doFSR_ << doISR_ << splitHardProcess_;
}
void ShowerHandler::persistentInput(PersistentIStream & is, int) {
is >> remDec_ >> iunit(pdfFreezingScale_,GeV) >> maxtry_
>> maxtryMPI_ >> maxtryDP_ >> maxtryDecay_
>> inputparticlesDecayInShower_
>> particlesDecayInShower_ >> MPIHandler_ >> PDFA_ >> PDFB_
>> PDFARemnant_ >> PDFBRemnant_
>> includeSpaceTime_ >> iunit(vMin_,GeV2)
>> factorizationScaleFactor_ >> renormalizationScaleFactor_
>> hardScaleFactor_
>> restrictPhasespace_ >> maxPtIsMuF_ >> hardScaleProfile_
>> showerVariations_ >> doFSR_ >> doISR_ >> splitHardProcess_;
}
void ShowerHandler::Init() {
static ClassDocumentation<ShowerHandler> documentation
("Main driver class for the showering.");
static Reference<ShowerHandler,HwRemDecayer>
interfaceRemDecayer("RemDecayer",
"A reference to the Remnant Decayer object",
&Herwig::ShowerHandler::remDec_,
false, false, true, false);
static Parameter<ShowerHandler,Energy> interfacePDFFreezingScale
("PDFFreezingScale",
"The PDF freezing scale",
&ShowerHandler::pdfFreezingScale_, GeV, 2.5*GeV, 2.0*GeV, 10.0*GeV,
false, false, Interface::limited);
static Parameter<ShowerHandler,unsigned int> interfaceMaxTry
("MaxTry",
"The maximum number of attempts for the main showering loop",
&ShowerHandler::maxtry_, 10, 1, 100,
false, false, Interface::limited);
static Parameter<ShowerHandler,unsigned int> interfaceMaxTryMPI
("MaxTryMPI",
"The maximum number of regeneration attempts for an additional scattering",
&ShowerHandler::maxtryMPI_, 10, 0, 100,
false, false, Interface::limited);
static Parameter<ShowerHandler,unsigned int> interfaceMaxTryDP
("MaxTryDP",
"The maximum number of regeneration attempts for an additional hard scattering",
&ShowerHandler::maxtryDP_, 10, 0, 100,
false, false, Interface::limited);
static ParVector<ShowerHandler,long> interfaceDecayInShower
("DecayInShower",
"PDG codes of the particles to be decayed in the shower",
&ShowerHandler::inputparticlesDecayInShower_, -1, 0l, -10000000l, 10000000l,
false, false, Interface::limited);
static Reference<ShowerHandler,UEBase> interfaceMPIHandler
("MPIHandler",
"The object that administers all additional scatterings.",
&ShowerHandler::MPIHandler_, false, false, true, true);
static Reference<ShowerHandler,PDFBase> interfacePDFA
("PDFA",
"The PDF for beam particle A. Overrides the particle's own PDF setting."
"By default used for both the shower and forced splitting in the remnant",
&ShowerHandler::PDFA_, false, false, true, true, false);
static Reference<ShowerHandler,PDFBase> interfacePDFB
("PDFB",
"The PDF for beam particle B. Overrides the particle's own PDF setting."
"By default used for both the shower and forced splitting in the remnant",
&ShowerHandler::PDFB_, false, false, true, true, false);
static Reference<ShowerHandler,PDFBase> interfacePDFARemnant
("PDFARemnant",
"The PDF for beam particle A used to generate forced splittings of the remnant."
" This overrides both the particle's own PDF setting and the value set by PDFA if used.",
&ShowerHandler::PDFARemnant_, false, false, true, true, false);
static Reference<ShowerHandler,PDFBase> interfacePDFBRemnant
("PDFBRemnant",
"The PDF for beam particle B used to generate forced splittings of the remnant."
" This overrides both the particle's own PDF setting and the value set by PDFB if used.",
&ShowerHandler::PDFBRemnant_, false, false, true, true, false);
static Switch<ShowerHandler,bool> interfaceIncludeSpaceTime
("IncludeSpaceTime",
"Whether to include the model for the calculation of space-time distances",
&ShowerHandler::includeSpaceTime_, false, false, false);
static SwitchOption interfaceIncludeSpaceTimeYes
(interfaceIncludeSpaceTime,
"Yes",
"Include the model",
true);
static SwitchOption interfaceIncludeSpaceTimeNo
(interfaceIncludeSpaceTime,
"No",
"Only include the displacement from the particle-s lifetime for decaying particles",
false);
static Parameter<ShowerHandler,Energy2> interfaceMinimumVirtuality
("MinimumVirtuality",
"The minimum virtuality for the space-time model",
&ShowerHandler::vMin_, GeV2, 0.1*GeV2, 0.0*GeV2, 1000.0*GeV2,
false, false, Interface::limited);
static Parameter<ShowerHandler,double> interfaceFactorizationScaleFactor
("FactorizationScaleFactor",
"The factorization scale factor.",
&ShowerHandler::factorizationScaleFactor_, 1.0, 0.0, 0,
false, false, Interface::lowerlim);
static Parameter<ShowerHandler,double> interfaceRenormalizationScaleFactor
("RenormalizationScaleFactor",
"The renormalization scale factor.",
&ShowerHandler::renormalizationScaleFactor_, 1.0, 0.0, 0,
false, false, Interface::lowerlim);
static Parameter<ShowerHandler,double> interfaceHardScaleFactor
("HardScaleFactor",
"The hard scale factor.",
&ShowerHandler::hardScaleFactor_, 1.0, 0.0, 0,
false, false, Interface::lowerlim);
static Parameter<ShowerHandler,unsigned int> interfaceMaxTryDecay
("MaxTryDecay",
"The maximum number of attempts to generate a decay",
&ShowerHandler::maxtryDecay_, 200, 10, 0,
false, false, Interface::lowerlim);
static Reference<ShowerHandler,HardScaleProfile> interfaceHardScaleProfile
("HardScaleProfile",
"The hard scale profile to use.",
&ShowerHandler::hardScaleProfile_, false, false, true, true, false);
static Switch<ShowerHandler,bool> interfaceMaxPtIsMuF
("MaxPtIsMuF",
"",
&ShowerHandler::maxPtIsMuF_, false, false, false);
static SwitchOption interfaceMaxPtIsMuFYes
(interfaceMaxPtIsMuF,
"Yes",
"",
true);
static SwitchOption interfaceMaxPtIsMuFNo
(interfaceMaxPtIsMuF,
"No",
"",
false);
static Switch<ShowerHandler,bool> interfaceRestrictPhasespace
("RestrictPhasespace",
"Switch on or off phasespace restrictions",
&ShowerHandler::restrictPhasespace_, true, false, false);
static SwitchOption interfaceRestrictPhasespaceOn
(interfaceRestrictPhasespace,
"On",
"Perform phasespace restrictions",
true);
static SwitchOption interfaceRestrictPhasespaceOff
(interfaceRestrictPhasespace,
"Off",
"Do not perform phasespace restrictions",
false);
static Command<ShowerHandler> interfaceAddVariation
("AddVariation",
"Add a shower variation.",
&ShowerHandler::doAddVariation, false);
static Switch<ShowerHandler,bool> interfaceDoFSR
("DoFSR",
"Switch on or off final state radiation.",
&ShowerHandler::doFSR_, true, false, false);
static SwitchOption interfaceDoFSROn
(interfaceDoFSR,
"Yes",
"Switch on final state radiation.",
true);
static SwitchOption interfaceDoFSROff
(interfaceDoFSR,
"No",
"Switch off final state radiation.",
false);
static Switch<ShowerHandler,bool> interfaceDoISR
("DoISR",
"Switch on or off initial state radiation.",
&ShowerHandler::doISR_, true, false, false);
static SwitchOption interfaceDoISROn
(interfaceDoISR,
"Yes",
"Switch on initial state radiation.",
true);
static SwitchOption interfaceDoISROff
(interfaceDoISR,
"No",
"Switch off initial state radiation.",
false);
static Switch<ShowerHandler,bool> interfaceSplitHardProcess
("SplitHardProcess",
"Whether or not to try and split the hard process into production and decay processes",
&ShowerHandler::splitHardProcess_, true, false, false);
static SwitchOption interfaceSplitHardProcessYes
(interfaceSplitHardProcess,
"Yes",
"Split the hard process",
true);
static SwitchOption interfaceSplitHardProcessNo
(interfaceSplitHardProcess,
"No",
"Don't split the hard process",
false);
}
Energy ShowerHandler::hardScale() const {
assert(false);
}
void ShowerHandler::cascade() {
useMe();
// Initialise the weights in the event object
// so that any variations are output regardless of
// whether showering occurs for the given event
initializeWeights();
// get the PDF's from ThePEG (if locally overridden use the local versions)
tcPDFPtr first = PDFA_ ? tcPDFPtr(PDFA_) : firstPDF().pdf();
tcPDFPtr second = PDFB_ ? tcPDFPtr(PDFB_) : secondPDF().pdf();
resetPDFs(make_pair(first,second));
// set the PDFs for the remnant
if( ! rempdfs_.first)
rempdfs_.first = PDFARemnant_ ? PDFPtr(PDFARemnant_) : const_ptr_cast<PDFPtr>(first);
if( ! rempdfs_.second)
rempdfs_.second = PDFBRemnant_ ? PDFPtr(PDFBRemnant_) : const_ptr_cast<PDFPtr>(second);
// get the incoming partons
tPPair incomingPartons =
eventHandler()->currentCollision()->primarySubProcess()->incoming();
// and the parton bins
PBIPair incomingBins =
make_pair(lastExtractor()->partonBinInstance(incomingPartons.first),
lastExtractor()->partonBinInstance(incomingPartons.second));
// and the incoming hadrons
tPPair incomingHadrons =
eventHandler()->currentCollision()->incoming();
remnantDecayer()->setHadronContent(incomingHadrons);
// check if incoming hadron == incoming parton
// and get the incoming hadron if exists or parton otherwise
incoming_ = make_pair(incomingBins.first ?
incomingBins.first ->particle() : incomingPartons.first,
incomingBins.second ?
incomingBins.second->particle() : incomingPartons.second);
// check the collision is of the beam particles
// and if not boost collision to the right frame
// i.e. the hadron-hadron CMF of the collision
bool btotal(false);
LorentzRotation rtotal;
if(incoming_.first != incomingHadrons.first ||
incoming_.second != incomingHadrons.second ) {
btotal = true;
boostCollision(false);
}
// set the current ShowerHandler
setCurrentHandler();
// first shower the hard process
try {
SubProPtr sub = eventHandler()->currentCollision()->primarySubProcess();
incomingPartons = cascade(sub,lastXCombPtr());
}
catch(ShowerTriesVeto &veto){
throw Exception() << "Failed to generate the shower after "
<< veto.tries
<< " attempts in ShowerHandler::cascade()"
<< Exception::eventerror;
}
if(showerHardProcessVeto()) throw Veto();
// if a non-hadron collision return (both incoming non-hadronic)
if( ( !incomingBins.first||
!isResolvedHadron(incomingBins.first ->particle()))&&
( !incomingBins.second||
!isResolvedHadron(incomingBins.second->particle()))) {
// boost back to lab if needed
if(btotal) boostCollision(true);
// perform the reweighting for the hard process shower
combineWeights();
// unset the current ShowerHandler
unSetCurrentHandler();
return;
}
// get the remnants for hadronic collision
pair<tRemPPtr,tRemPPtr> remnants(getRemnants(incomingBins));
// set the starting scale of the forced splitting to the PDF freezing scale
remnantDecayer()->initialize(remnants, incoming_, *currentStep(), pdfFreezingScale());
// do the first forcedSplitting
try {
remnantDecayer()->doSplit(incomingPartons, make_pair(rempdfs_.first,rempdfs_.second), true);
}
catch (ExtraScatterVeto) {
throw Exception() << "Remnant extraction failed in "
<< "ShowerHandler::cascade() from primary interaction"
<< Exception::eventerror;
}
// perform the reweighting for the hard process shower
combineWeights();
// if no MPI return
if( !isMPIOn() ) {
remnantDecayer()->finalize();
// boost back to lab if needed
if(btotal) boostCollision(true);
// unset the current ShowerHandler
unSetCurrentHandler();
return;
}
// generate the multiple scatters use modified pdf's now:
setMPIPDFs();
// additional "hard" processes
unsigned int tries(0);
// This is the loop over additional hard scatters (most of the time
// only one, but who knows...)
for(unsigned int i=1; i <= getMPIHandler()->additionalHardProcs(); i++){
//counter for regeneration
unsigned int multSecond = 0;
// generate the additional scatters
while( multSecond < getMPIHandler()->multiplicity(i) ) {
// generate the hard scatter
tStdXCombPtr lastXC = getMPIHandler()->generate(i);
SubProPtr sub = lastXC->construct();
// add to the Step
newStep()->addSubProcess(sub);
// increment the counters
tries++;
multSecond++;
if(tries == maxtryDP_)
throw Exception() << "Failed to establish the requested number "
<< "of additional hard processes. If this error "
<< "occurs often, your selection of additional "
<< "scatter is probably unphysical"
<< Exception::eventerror;
// Generate the shower. If not possible veto the event
try {
incomingPartons = cascade(sub,lastXC);
}
catch(ShowerTriesVeto &veto){
throw Exception() << "Failed to generate the shower of "
<< "a secondary hard process after "
<< veto.tries
<< " attempts in Evolver::showerHardProcess()"
<< Exception::eventerror;
}
try {
// do the forcedSplitting
remnantDecayer()->doSplit(incomingPartons, make_pair(remmpipdfs_.first,remmpipdfs_.second), false);
}
catch(ExtraScatterVeto){
//remove all particles associated with the subprocess
newStep()->removeParticle(incomingPartons.first);
newStep()->removeParticle(incomingPartons.second);
//remove the subprocess from the list
newStep()->removeSubProcess(sub);
//regenerate the scattering
multSecond--;
continue;
}
// connect with the remnants but don't set Remnant colour,
// because that causes problems due to the multiple colour lines.
if ( !remnants.first ->extract(incomingPartons.first , false) ||
!remnants.second->extract(incomingPartons.second, false) )
throw Exception() << "Remnant extraction failed in "
<< "ShowerHandler::cascade() for additional scatter"
<< Exception::runerror;
}
// perform the reweighting for the additional hard scatter shower
combineWeights();
}
// the underlying event processes
unsigned int ptveto(1), veto(0);
unsigned int max(getMPIHandler()->multiplicity());
for(unsigned int i=0; i<max; i++) {
// check how often this scattering has been regenerated
if(veto > maxtryMPI_) break;
//generate PSpoint
tStdXCombPtr lastXC = getMPIHandler()->generate();
SubProPtr sub = lastXC->construct();
//If Algorithm=1 additional scatters of the signal type
// with pt > ptmin have to be vetoed
//with probability 1/(m+1), where m is the number of occurances in this event
if( getMPIHandler()->Algorithm() == 1 ){
//get the pT
Energy pt = sub->outgoing().front()->momentum().perp();
if(pt > getMPIHandler()->PtForVeto() && UseRandom::rnd() < 1./(ptveto+1) ){
ptveto++;
i--;
continue;
}
}
// add to the SubProcess to the step
newStep()->addSubProcess(sub);
// Run the Shower. If not possible veto the scattering
try {
incomingPartons = cascade(sub,lastXC);
}
// discard this extra scattering, but try the next one
catch(ShowerTriesVeto) {
newStep()->removeSubProcess(sub);
//regenerate the scattering
veto++;
i--;
continue;
}
try{
//do the forcedSplitting
remnantDecayer()->doSplit(incomingPartons, make_pair(remmpipdfs_.first,remmpipdfs_.second), false);
}
catch (ExtraScatterVeto) {
//remove all particles associated with the subprocess
newStep()->removeParticle(incomingPartons.first);
newStep()->removeParticle(incomingPartons.second);
//remove the subprocess from the list
newStep()->removeSubProcess(sub);
//regenerate the scattering
veto++;
i--;
continue;
}
//connect with the remnants but don't set Remnant colour,
//because that causes problems due to the multiple colour lines.
if ( !remnants.first ->extract(incomingPartons.first , false) ||
!remnants.second->extract(incomingPartons.second, false) )
throw Exception() << "Remnant extraction failed in "
<< "ShowerHandler::cascade() for MPI hard scattering"
<< Exception::runerror;
//reset veto counter
veto = 0;
// perform the reweighting for the MPI process shower
combineWeights();
}
// finalize the remnants
remnantDecayer()->finalize(getMPIHandler()->colourDisrupt(),
getMPIHandler()->softMultiplicity());
// boost back to lab if needed
if(btotal) boostCollision(true);
// unset the current ShowerHandler
unSetCurrentHandler();
getMPIHandler()->clean();
resetPDFs(make_pair(first,second));
}
void ShowerHandler::initializeWeights() {
if ( !showerVariations().empty() ) {
tEventPtr event = eventHandler()->currentEvent();
for ( map<string,ShowerVariation>::const_iterator var =
showerVariations().begin();
var != showerVariations().end(); ++var ) {
// Check that this is behaving as intended
//map<string,double>::iterator wi = event->optionalWeights().find(var->first);
//assert(wi == event->optionalWeights().end() );
event->optionalWeights()[var->first] = 1.0;
currentWeights_[var->first] = 1.0;
}
}
reweight_ = 1.0;
}
void ShowerHandler::resetWeights() {
for ( map<string,double>::iterator w = currentWeights_.begin();
w != currentWeights_.end(); ++w ) {
w->second = 1.0;
}
reweight_ = 1.0;
}
void ShowerHandler::combineWeights() {
tEventPtr event = eventHandler()->currentEvent();
for ( map<string,double>::const_iterator w =
currentWeights_.begin(); w != currentWeights_.end(); ++w ) {
map<string,double>::iterator ew = event->optionalWeights().find(w->first);
if ( ew != event->optionalWeights().end() )
ew->second *= w->second;
else {
assert(false && "Weight name unknown.");
//event->optionalWeights()[w->first] = w->second;
}
}
if ( reweight_ != 1.0 ) {
Ptr<StandardEventHandler>::tptr eh =
dynamic_ptr_cast<Ptr<StandardEventHandler>::tptr>(eventHandler());
if ( !eh ) {
throw Exception() << "ShowerHandler::combineWeights() : Cross section reweighting "
<< "through the shower is currently only available with standard "
<< "event generators" << Exception::runerror;
}
eh->reweight(reweight_);
}
}
string ShowerHandler::doAddVariation(string in) {
if ( in.empty() )
return "expecting a name and a variation specification";
string name = StringUtils::car(in);
ShowerVariation var;
string res = var.fromInFile(StringUtils::cdr(in));
if ( res.empty() ) {
if ( !var.firstInteraction && !var.secondaryInteractions ) {
// TODO what about decay showers?
return "variation does not apply to any shower";
}
if ( var.renormalizationScaleFactor == 1.0 &&
var.factorizationScaleFactor == 1.0 ) {
return "variation does not vary anything";
}
/*
Repository::clog() << "adding a variation with tag '" << name << "' using\nxir = "
<< var.renormalizationScaleFactor
<< " xif = "
<< var.factorizationScaleFactor
<< "\napplying to:\n"
<< "first interaction = " << var.firstInteraction << " "
<< "secondary interactions = " << var.secondaryInteractions << "\n"
<< flush;
*/
showerVariations()[name] = var;
}
return res;
}
tPPair ShowerHandler::cascade(tSubProPtr, XCPtr) {
assert(false);
}
ShowerHandler::RemPair
ShowerHandler::getRemnants(PBIPair incomingBins) {
RemPair remnants;
// first beam particle
if(incomingBins.first&&!incomingBins.first->remnants().empty()) {
remnants.first =
dynamic_ptr_cast<tRemPPtr>(incomingBins.first->remnants()[0] );
if(remnants.first) {
ParticleVector children=remnants.first->children();
for(unsigned int ix=0;ix<children.size();++ix) {
if(children[ix]->dataPtr()==remnants.first->dataPtr())
remnants.first = dynamic_ptr_cast<RemPPtr>(children[ix]);
}
//remove existing colour lines from the remnants
if(remnants.first->colourLine())
remnants.first->colourLine()->removeColoured(remnants.first);
if(remnants.first->antiColourLine())
remnants.first->antiColourLine()->removeAntiColoured(remnants.first);
}
}
// seconnd beam particle
if(incomingBins.second&&!incomingBins. second->remnants().empty()) {
remnants.second =
dynamic_ptr_cast<tRemPPtr>(incomingBins.second->remnants()[0] );
if(remnants.second) {
ParticleVector children=remnants.second->children();
for(unsigned int ix=0;ix<children.size();++ix) {
if(children[ix]->dataPtr()==remnants.second->dataPtr())
remnants.second = dynamic_ptr_cast<RemPPtr>(children[ix]);
}
//remove existing colour lines from the remnants
if(remnants.second->colourLine())
remnants.second->colourLine()->removeColoured(remnants.second);
if(remnants.second->antiColourLine())
remnants.second->antiColourLine()->removeAntiColoured(remnants.second);
}
}
assert(remnants.first || remnants.second);
return remnants;
}
namespace {
void addChildren(tPPtr in,set<tPPtr> & particles) {
particles.insert(in);
for(unsigned int ix=0;ix<in->children().size();++ix)
addChildren(in->children()[ix],particles);
}
}
void ShowerHandler::boostCollision(bool boost) {
// calculate boost from lab to rest
if(!boost) {
Lorentz5Momentum ptotal=incoming_.first ->momentum()+incoming_.second->momentum();
boost_ = LorentzRotation(-ptotal.boostVector());
Axis axis((boost_*incoming_.first ->momentum()).vect().unit());
if(axis.perp2()>0.) {
double sinth(sqrt(sqr(axis.x())+sqr(axis.y())));
boost_.rotate(-acos(axis.z()),Axis(-axis.y()/sinth,axis.x()/sinth,0.));
}
}
// first call performs the boost and second inverse
// get the particles to be boosted
set<tPPtr> particles;
addChildren(incoming_.first,particles);
addChildren(incoming_.second,particles);
// apply the boost
for(set<tPPtr>::const_iterator cit=particles.begin();
cit!=particles.end();++cit) {
(*cit)->transform(boost_);
}
if(!boost) boost_.invert();
}
void ShowerHandler::setMPIPDFs() {
if ( !mpipdfs_.first ) {
// first have to check for MinBiasPDF
tcMinBiasPDFPtr first = dynamic_ptr_cast<tcMinBiasPDFPtr>(firstPDF().pdf());
if(first)
mpipdfs_.first = new_ptr(MPIPDF(first->originalPDF()));
else
mpipdfs_.first = new_ptr(MPIPDF(firstPDF().pdf()));
}
if ( !mpipdfs_.second ) {
tcMinBiasPDFPtr second = dynamic_ptr_cast<tcMinBiasPDFPtr>(secondPDF().pdf());
if(second)
mpipdfs_.second = new_ptr(MPIPDF(second->originalPDF()));
else
mpipdfs_.second = new_ptr(MPIPDF(secondPDF().pdf()));
}
if( !remmpipdfs_.first ) {
tcMinBiasPDFPtr first = dynamic_ptr_cast<tcMinBiasPDFPtr>(rempdfs_.first);
if(first)
remmpipdfs_.first = new_ptr(MPIPDF(first->originalPDF()));
else
remmpipdfs_.first = new_ptr(MPIPDF(rempdfs_.first));
}
if( !remmpipdfs_.second ) {
tcMinBiasPDFPtr second = dynamic_ptr_cast<tcMinBiasPDFPtr>(rempdfs_.second);
if(second)
remmpipdfs_.second = new_ptr(MPIPDF(second->originalPDF()));
else
remmpipdfs_.second = new_ptr(MPIPDF(rempdfs_.second));
}
// reset the PDFs stored in the base class
resetPDFs(mpipdfs_);
}
bool ShowerHandler::isResolvedHadron(tPPtr particle) {
if(!HadronMatcher::Check(particle->data())) return false;
for(unsigned int ix=0;ix<particle->children().size();++ix) {
if(particle->children()[ix]->id()==ParticleID::Remnant) return true;
}
return false;
}
namespace {
bool decayProduct(tSubProPtr subProcess,
tPPtr particle) {
// must be time-like and not incoming
if(particle->momentum().m2()<=ZERO||
particle == subProcess->incoming().first||
particle == subProcess->incoming().second) return false;
// if only 1 outgoing and this is it
if(subProcess->outgoing().size()==1 &&
subProcess->outgoing()[0]==particle) return true;
// must not be the s-channel intermediate otherwise
if(find(subProcess->incoming().first->children().begin(),
subProcess->incoming().first->children().end(),particle)!=
subProcess->incoming().first->children().end()&&
find(subProcess->incoming().second->children().begin(),
subProcess->incoming().second->children().end(),particle)!=
subProcess->incoming().second->children().end()&&
subProcess->incoming().first ->children().size()==1&&
subProcess->incoming().second->children().size()==1)
return false;
// if non-coloured this is enough
if(!particle->dataPtr()->coloured()) return true;
// if coloured must be unstable
if(particle->dataPtr()->stable()) return false;
// must not have same particle type as a child
int id = particle->id();
for(unsigned int ix=0;ix<particle->children().size();++ix)
if(particle->children()[ix]->id()==id) return false;
// otherwise its a decaying particle
return true;
}
PPtr findParent(PPtr original, bool & isHard,
set<PPtr> outgoingset,
tSubProPtr subProcess) {
PPtr parent=original;
isHard |=(outgoingset.find(original) != outgoingset.end());
if(!original->parents().empty()) {
PPtr orig=original->parents()[0];
if(CurrentGenerator::current().currentEventHandler()->currentStep()->
find(orig)&&decayProduct(subProcess,orig)) {
parent=findParent(orig,isHard,outgoingset,subProcess);
}
}
return parent;
}
}
void ShowerHandler::findDecayProducts(PPtr in,PerturbativeProcessPtr hard,
- DecayProcessMap decay) const {
+ DecayProcessMap & decay) const {
ParticleVector children=in->children();
for(ParticleVector::const_iterator it=children.begin(); it!=children.end();++it) {
// if decayed or should be decayed in shower make the PerturbaitveProcess
bool radiates = false;
if(!(**it).children().empty()) {
// remove d,u,s,c,b quarks and leptons other than on-shell taus
if( StandardQCDPartonMatcher::Check((**it).id()) ||
( LeptonMatcher::Check((**it).id()) && !(abs((**it).id())==ParticleID::tauminus &&
abs((**it).mass()-(**it).dataPtr()->mass())<MeV))) {
radiates = true;
}
else {
bool foundParticle(false),foundGauge(false);
for(unsigned int iy=0;iy<(**it).children().size();++iy) {
if((**it).children()[iy]->id()==(**it).id()) {
foundParticle = true;
}
else if((**it).children()[iy]->id()==ParticleID::g ||
(**it).children()[iy]->id()==ParticleID::gamma) {
foundGauge = true;
}
}
radiates = foundParticle && foundGauge;
}
}
if(radiates) {
findDecayProducts(*it,hard,decay);
}
else if(!(**it).children().empty()||
(decaysInShower((**it).id())&&!(**it).dataPtr()->stable())) {
- createDecayProcess(in,hard,decay);
+ createDecayProcess(*it,hard,decay);
}
else {
hard->outgoing().push_back(make_pair(*it,PerturbativeProcessPtr()));
}
}
}
void ShowerHandler::splitHardProcess(tPVector tagged, PerturbativeProcessPtr & hard,
DecayProcessMap & decay) const {
// temporary storage of the particles
set<PPtr> hardParticles;
// tagged particles in a set
set<PPtr> outgoingset(tagged.begin(),tagged.end());
bool isHard=false;
// loop over the tagged particles
for (tParticleVector::const_iterator taggedP = tagged.begin();
taggedP != tagged.end(); ++taggedP) {
// skip remnants
if (eventHandler()->currentCollision()&&
eventHandler()->currentCollision()->isRemnant(*taggedP)) continue;
// find the parent and whether its a decaying particle
bool isDecayProd=false;
// check if hard
isHard |=(outgoingset.find(*taggedP) != outgoingset.end());
if(splitHardProcess_) {
tPPtr parent = *taggedP;
// check if from s channel decaying colourless particle
while(parent&&!parent->parents().empty()&&!isDecayProd) {
parent = parent->parents()[0];
if(parent == subProcess_->incoming().first ||
parent == subProcess_->incoming().second ) break;
isDecayProd = decayProduct(subProcess_,parent);
}
if (isDecayProd)
hardParticles.insert(findParent(parent,isHard,outgoingset,subProcess_));
}
if (!isDecayProd)
hardParticles.insert(*taggedP);
}
// there must be something to shower
if(hardParticles.empty())
throw Exception() << "No particles to shower in "
<< "ShowerHandler::splitHardProcess()"
<< Exception::eventerror;
// must be a hard process
if(!isHard)
throw Exception() << "Starting on decay not yet implemented in "
<< "ShowerHandler::splitHardProcess()"
<< Exception::runerror;
// create the hard process
hard = new_ptr(PerturbativeProcess());
// incoming particles
hard->incoming().push_back(make_pair(subProcess_->incoming().first ,PerturbativeProcessPtr()));
hard->incoming().push_back(make_pair(subProcess_->incoming().second,PerturbativeProcessPtr()));
// outgoing particles
for(set<PPtr>::const_iterator it=hardParticles.begin();it!=hardParticles.end();++it) {
// if decayed or should be decayed in shower make the tree
PPtr orig = *it;
bool radiates = false;
if(!orig->children().empty()) {
// remove d,u,s,c,b quarks and leptons other than on-shell taus
if( StandardQCDPartonMatcher::Check(orig->id()) ||
( LeptonMatcher::Check(orig->id()) &&
!(abs(orig->id())==ParticleID::tauminus && abs(orig->mass()-orig->dataPtr()->mass())<MeV))) {
radiates = true;
}
else {
bool foundParticle(false),foundGauge(false);
for(unsigned int iy=0;iy<orig->children().size();++iy) {
if(orig->children()[iy]->id()==orig->id()) {
foundParticle = true;
}
else if(orig->children()[iy]->id()==ParticleID::g ||
orig->children()[iy]->id()==ParticleID::gamma) {
foundGauge = true;
}
}
radiates = foundParticle && foundGauge;
}
}
if(radiates) {
findDecayProducts(orig,hard,decay);
}
else if(!(**it).children().empty()||
(decaysInShower((**it).id())&&!(**it).dataPtr()->stable())) {
createDecayProcess(*it,hard,decay);
}
else {
hard->outgoing().push_back(make_pair(*it,PerturbativeProcessPtr()));
}
}
}
void ShowerHandler::createDecayProcess(PPtr in,PerturbativeProcessPtr hard, DecayProcessMap & decay) const {
// there must be an incoming particle
assert(in);
// create the new process and connect with the parent
PerturbativeProcessPtr newDecay=new_ptr(PerturbativeProcess());
newDecay->incoming().push_back(make_pair(in,hard));
Energy width=in->dataPtr()->generateWidth(in->mass());
decay.insert(make_pair(width,newDecay));
hard->outgoing().push_back(make_pair(in,newDecay));
// we need to deal with the decay products if decayed
ParticleVector children = in->children();
if(!children.empty()) {
for(ParticleVector::const_iterator it = children.begin();
it!= children.end(); ++it) {
// if decayed or should be decayed in shower make the tree
in->abandonChild(*it);
bool radiates = false;
if(!(**it).children().empty()) {
if(StandardQCDPartonMatcher::Check((**it).id())||
(LeptonMatcher::Check((**it).id())&& !(abs((**it).id())==ParticleID::tauminus &&
abs((**it).mass()-(**it).dataPtr()->mass())<MeV))) {
radiates = true;
}
else {
bool foundParticle(false),foundGauge(false);
for(unsigned int iy=0;iy<(**it).children().size();++iy) {
if((**it).children()[iy]->id()==(**it).id()) {
foundParticle = true;
}
else if((**it).children()[iy]->id()==ParticleID::g ||
(**it).children()[iy]->id()==ParticleID::gamma) {
foundGauge = true;
}
}
radiates = foundParticle && foundGauge;
}
// finally assume all non-decaying particles are in this class
// pr 27/11/15 not sure about this bit
// if(!radiates) {
// radiates = !decaysInShower((**it).id());
// }
}
if(radiates) {
findDecayProducts(*it,newDecay,decay);
}
else if(!(**it).children().empty()||
(decaysInShower((**it).id())&&!(**it).dataPtr()->stable())) {
createDecayProcess(*it,newDecay,decay);
}
else {
newDecay->outgoing().push_back(make_pair(*it,PerturbativeProcessPtr()));
}
}
}
}
tDMPtr ShowerHandler::decay(PerturbativeProcessPtr process,
DecayProcessMap & decayMap,
bool radPhotons ) const {
PPtr parent = process->incoming()[0].first;
assert(parent);
if(parent->spinInfo()) parent->spinInfo()->decay(true);
unsigned int ntry = 0;
ParticleVector children;
tDMPtr dm = DMPtr();
while (true) {
// exit if fails
if (++ntry>=maxtryDecay_)
throw Exception() << "Failed to perform decay in ShowerHandler::decay()"
<< " after " << maxtryDecay_
<< " attempts for " << parent->PDGName()
<< Exception::eventerror;
// select decay mode
dm = parent->data().selectMode(*parent);
if(!dm)
throw Exception() << "Failed to select decay mode in ShowerHandler::decay()"
<< "for " << parent->PDGName()
<< Exception::eventerror;
if(!dm->decayer())
throw Exception() << "No Decayer for selected decay mode "
<< " in ShowerHandler::decay()"
<< Exception::runerror;
// start of try block
try {
children = dm->decayer()->decay(*dm, *parent);
// if no children have another go
if(children.empty()) continue;
if(radPhotons){
// generate radiation in the decay
tDecayIntegratorPtr hwdec=dynamic_ptr_cast<tDecayIntegratorPtr>(dm->decayer());
if (hwdec && hwdec->canGeneratePhotons())
children = hwdec->generatePhotons(*parent,children);
}
// set up parent
parent->decayMode(dm);
// add children
for (unsigned int i = 0, N = children.size(); i < N; ++i ) {
children[i]->setLabVertex(parent->labDecayVertex());
//parent->addChild(children[i]);
}
// if succeeded break out of loop
break;
}
catch(Veto) {
}
}
assert(!children.empty());
for(ParticleVector::const_iterator it = children.begin();
it!= children.end(); ++it) {
if(!(**it).children().empty()||
(decaysInShower((**it).id())&&!(**it).dataPtr()->stable())) {
createDecayProcess(*it,process,decayMap);
}
else {
process->outgoing().push_back(make_pair(*it,PerturbativeProcessPtr()));
}
}
return dm;
}
// Note: The tag must be constructed from an ordered particle container.
tDMPtr ShowerHandler::findDecayMode(const string & tag) const {
static map<string,DMPtr> cache;
map<string,DMPtr>::const_iterator pos = cache.find(tag);
if ( pos != cache.end() )
return pos->second;
tDMPtr dm = CurrentGenerator::current().findDecayMode(tag);
cache[tag] = dm;
return dm;
}
/**
* Operator for the particle ordering
* @param p1 The first ParticleData object
* @param p2 The second ParticleData object
*/
bool ShowerHandler::ParticleOrdering::operator() (tcPDPtr p1, tcPDPtr p2) {
return abs(p1->id()) > abs(p2->id()) ||
( abs(p1->id()) == abs(p2->id()) && p1->id() > p2->id() ) ||
( p1->id() == p2->id() && p1->fullName() > p2->fullName() );
}
diff --git a/Shower/ShowerHandler.h b/Shower/ShowerHandler.h
--- a/Shower/ShowerHandler.h
+++ b/Shower/ShowerHandler.h
@@ -1,822 +1,822 @@
// -*- C++ -*-
//
// ShowerHandler.h is a part of Herwig - A multi-purpose Monte Carlo event generator
// Copyright (C) 2002-2011 The Herwig Collaboration
//
// Herwig is licenced under version 2 of the GPL, see COPYING for details.
// Please respect the MCnet academic guidelines, see GUIDELINES for details.
//
#ifndef HERWIG_ShowerHandler_H
#define HERWIG_ShowerHandler_H
//
// This is the declaration of the ShowerHandler class.
//
#include "ThePEG/Handlers/EventHandler.h"
#include "ThePEG/Handlers/CascadeHandler.h"
#include "ShowerVariation.h"
#include "Herwig/PDF/HwRemDecayer.fh"
#include "ThePEG/EventRecord/RemnantParticle.fh"
#include "UEBase.h"
#include "PerturbativeProcess.h"
#include "Herwig/MatrixElement/Matchbox/Matching/HardScaleProfile.h"
#include "ShowerHandler.fh"
namespace Herwig {
using namespace ThePEG;
/** \ingroup Shower
*
* This class is the main driver of the shower: it is responsible for
* the proper handling of all other specific collaborating classes
* and for the storing of the produced particles in the event record.
*
* @see \ref ShowerHandlerInterfaces "The interfaces"
*
* @see ThePEG::CascadeHandler
* @see MPIHandler
* @see HwRemDecayer
*/
class ShowerHandler: public CascadeHandler {
public:
/**
* Typedef for a pair of ThePEG::RemnantParticle pointers.
*/
typedef pair<tRemPPtr, tRemPPtr> RemPair;
public:
/**
* Default constructor
*/
ShowerHandler();
/**
* Destructor
*/
virtual ~ShowerHandler();
public:
/**
* The main method which manages the multiple interactions and starts
* the shower by calling cascade(sub, lastXC).
*/
virtual void cascade();
/**
* pointer to "this", the current ShowerHandler.
*/
static const tShowerHandlerPtr currentHandler() {
assert(currentHandler_);
return currentHandler_;
}
public:
/**
* Hook to allow vetoing of event after showering hard sub-process
* as in e.g. MLM merging.
*/
virtual bool showerHardProcessVeto() const { return false; }
/**
* Return true, if this cascade handler will perform reshuffling from hard
* process masses.
*/
virtual bool isReshuffling() const { return true; }
/**
* Return true, if the shower handler can generate a truncated
* shower for POWHEG style events generated using Matchbox
*/
virtual bool canHandleMatchboxTrunc() const { return false; }
/**
* Get the PDF freezing scale
*/
Energy pdfFreezingScale() const { return pdfFreezingScale_; }
/**
* Get the local PDFs.
*/
PDFPtr getPDFA() const {return PDFA_;}
/**
* Get the local PDFs.
*/
PDFPtr getPDFB() const {return PDFB_;}
/**
* Return true if currently the primary subprocess is showered.
*/
bool firstInteraction() const {
if (!eventHandler()->currentCollision())return true;
return ( subProcess_ ==
eventHandler()->currentCollision()->primarySubProcess() );
}
/**
* Return the remnant decayer.
*/
tHwRemDecPtr remnantDecayer() const { return remDec_; }
/**
* Split the hard process into production and decays
* @param tagged The tagged particles from the StepHandler
* @param hard The hard perturbative process
* @param decay The decay particles
*/
void splitHardProcess(tPVector tagged, PerturbativeProcessPtr & hard,
DecayProcessMap & decay) const;
/**
* Information if the Showerhandler splits the hard process.
*/
bool doesSplitHardProcess()const {return splitHardProcess_;}
/**
* Decay a particle.
* radPhotons switches the generation of photon
* radiation on/off.
* Required for Dipole Shower but not QTilde Shower.
*/
tDMPtr decay(PerturbativeProcessPtr,
DecayProcessMap & decay,
bool radPhotons = false) const;
/**
* Cached lookup of decay modes.
* Generator::findDecayMode() is not efficient.
*/
tDMPtr findDecayMode(const string & tag) const;
/**
* A struct to order the particles in the same way as in the DecayMode's
*/
struct ParticleOrdering {
bool operator() (tcPDPtr p1, tcPDPtr p2);
};
/**
* A container for ordered particles required
* for constructing tags for decay mode lookup.
*/
typedef multiset<tcPDPtr,ParticleOrdering> OrderedParticles;
public:
/**
* @name Switches for initial- and final-state radiation
*/
//@{
/**
* Switch for any radiation
*/
bool doRadiation() const {return doFSR_ || doISR_;}
/**
* Switch on or off final state radiation.
*/
bool doFSR() const { return doFSR_;}
/**
* Switch on or off initial state radiation.
*/
bool doISR() const { return doISR_;}
//@}
public:
/**
* @name Switches for scales
*/
//@{
/**
* Return true if maximum pt should be deduced from the factorization scale
*/
bool hardScaleIsMuF() const { return maxPtIsMuF_; }
/**
* The factorization scale factor.
*/
double factorizationScaleFactor() const {
return factorizationScaleFactor_;
}
/**
* The renormalization scale factor.
*/
double renFac() const {
return renormalizationScaleFactor_;
}
/**
* The factorization scale factor.
*/
double facFac() const {
return factorizationScaleFactor_;
}
/**
* The renormalization scale factor.
*/
double renormalizationScaleFactor() const {
return renormalizationScaleFactor_;
}
/**
* The scale factor for the hard scale
*/
double hardScaleFactor() const {
return hardScaleFactor_;
}
/**
* Return true, if the phase space restrictions of the dipole shower should
* be applied.
*/
bool restrictPhasespace() const { return restrictPhasespace_; }
/**
* Return profile scales
*/
Ptr<HardScaleProfile>::tptr profileScales() const { return hardScaleProfile_; }
/**
* Return the relevant hard scale to be used in the profile scales
*/
virtual Energy hardScale() const;
//@}
public:
/**
* Access the shower variations
*/
map<string,ShowerVariation>& showerVariations() {
return showerVariations_;
}
/**
* Return the shower variations
*/
const map<string,ShowerVariation>& showerVariations() const {
return showerVariations_;
}
/**
* Access the current Weights
*/
map<string,double>& currentWeights() {
return currentWeights_;
}
/**
* Return the current Weights
*/
const map<string,double>& currentWeights() const {
return currentWeights_;
}
/**
* Change the current reweighting factor
*/
void reweight(double w) {
reweight_ = w;
}
/**
* Return the current reweighting factor
*/
double reweight() const {
return reweight_;
}
public:
/**
* struct that is used to catch exceptions which are thrown
* due to energy conservation issues of additional scatters
*/
struct ExtraScatterVeto {};
/**
* struct that is used to catch exceptions which are thrown
* due to fact that the Shower has been invoked more than
* a defined threshold on a certain configuration
*/
struct ShowerTriesVeto {
/** variable to store the number of attempts */
const int tries;
/** constructor */
ShowerTriesVeto(int t) : tries(t) {}
};
public:
/** @name Functions used by the persistent I/O system. */
//@{
/**
* Function used to write out object persistently.
* @param os the persistent output stream written to.
*/
void persistentOutput(PersistentOStream & os) const;
/**
* Function used to read in object persistently.
* @param is the persistent input stream read from.
* @param version the version number of the object when written.
*/
void persistentInput(PersistentIStream & is, int version);
//@}
/**
* The standard Init function used to initialize the interfaces.
* Called exactly once for each class by the class description system
* before the main function starts or
* when this class is dynamically loaded.
*/
static void Init();
protected:
/** @name Functions to perform the cascade
*/
//@{
/**
* The main method which manages the showering of a subprocess.
*/
virtual tPPair cascade(tSubProPtr sub, XCPtr xcomb);
/**
* Set up for the cascade
*/
void prepareCascade(tSubProPtr sub) {
current_ = currentStep();
subProcess_ = sub;
}
/**
* Boost all the particles in the collision so that the collision always occurs
* in the rest frame with the incoming particles along the z axis
*/
void boostCollision(bool boost);
//@}
protected:
/**
* Set/unset the current shower handler
*/
//@{
/**
* Set the current handler
*/
void setCurrentHandler() {
currentHandler_ = tShowerHandlerPtr(this);
}
/**
* Unset the current handler
*/
void unSetCurrentHandler() {
currentHandler_ = tShowerHandlerPtr();
}
//@}
protected:
/**
* @name Members relating to the underlying event and MPI
*/
//@{
/**
* Return true if multiple parton interactions are switched on
* and can be used for this beam setup.
*/
bool isMPIOn() const {
return MPIHandler_ && MPIHandler_->beamOK();
}
/**
* Access function for the MPIHandler, it should only be called after
* checking with isMPIOn.
*/
tUEBasePtr getMPIHandler() const {
assert(MPIHandler_);
return MPIHandler_;
}
/**
* Is a beam particle where hadronic structure is resolved
*/
bool isResolvedHadron(tPPtr);
/**
* Get the remnants from the ThePEG::PartonBinInstance es and
* do some checks.
*/
RemPair getRemnants(PBIPair incbins);
/**
* Reset the PDF's after the hard collision has been showered
*/
void setMPIPDFs();
//@}
public:
/**
* Check if a particle decays in the shower
* @param id The PDG code for the particle
*/
bool decaysInShower(long id) const {
return ( particlesDecayInShower_.find( abs(id) ) !=
particlesDecayInShower_.end() );
}
protected:
/**
* Members to handle splitting up of hard process and decays
*/
//@{
/**
* Find decay products from the hard process and create decay processes
* @param parent The parent particle
* @param hard The hard process
* @param decay The decay processes
*/
- void findDecayProducts(PPtr parent, PerturbativeProcessPtr hard, DecayProcessMap decay) const;
+ void findDecayProducts(PPtr parent, PerturbativeProcessPtr hard, DecayProcessMap & decay) const;
/**
* Find decay products from the hard process and create decay processes
* @param parent The parent particle
* @param hard The parent hard process
* @param decay The decay processes
*/
void createDecayProcess(PPtr parent,PerturbativeProcessPtr hard, DecayProcessMap & decay) const;
//@}
/**
* @name Functions to return information relevant to the process being showered
*/
//@{
/**
* Return the currently used SubProcess.
*/
tSubProPtr currentSubProcess() const {
assert(subProcess_);
return subProcess_;
}
/**
* Access to the incoming beam particles
*/
tPPair incomingBeams() const {
return incoming_;
}
//@}
protected:
/**
* Weight handling for shower variations
*/
//@
/**
* Combine the variation weights which have been encountered
*/
void combineWeights();
/**
* Initialise the weights in currentEvent()
*/
void initializeWeights();
/**
* Reset the current weights
*/
void resetWeights();
//@}
protected:
/**
* Return the maximum number of attempts for showering
* a given subprocess.
*/
unsigned int maxtry() const { return maxtry_; }
protected:
/** @name Clone Methods. */
//@{
/**
* Make a simple clone of this object.
* @return a pointer to the new object.
*/
virtual IBPtr clone() const;
/** Make a clone of this object, possibly modifying the cloned object
* to make it sane.
* @return a pointer to the new object.
*/
virtual IBPtr fullclone() const;
//@}
protected:
/** @name Standard Interfaced functions. */
//@{
/**
* Initialize this object after the setup phase before saving an
* EventGenerator to disk.
* @throws InitException if object could not be initialized properly.
*/
virtual void doinit();
/**
* Initialize this object. Called in the run phase just before
* a run begins.
*/
virtual void doinitrun();
/**
* Finalize this object. Called in the run phase just after a
* run has ended. Used eg. to write out statistics.
*/
virtual void dofinish();
//@}
private:
/**
* The assignment operator is private and must never be called.
* In fact, it should not even be implemented.
*/
ShowerHandler & operator=(const ShowerHandler &);
private:
/**
* pointer to "this", the current ShowerHandler.
*/
static tShowerHandlerPtr currentHandler_;
/**
* a MPIHandler to administer the creation of several (semihard)
* partonic interactions.
*/
UEBasePtr MPIHandler_;
/**
* Pointer to the HwRemDecayer
*/
HwRemDecPtr remDec_;
private:
/**
* Maximum tries for various stages of the showering process
*/
//@{
/**
* Maximum number of attempts for the
* main showering loop
*/
unsigned int maxtry_;
/**
* Maximum number of attempts for the regeneration of an additional
* scattering, before the number of scatters is reduced.
*/
unsigned int maxtryMPI_;
/**
* Maximum number of attempts for the regeneration of an additional
* hard scattering, before this event is vetoed.
*/
unsigned int maxtryDP_;
/**
* Maximum number of attempts to generate a decay
*/
unsigned int maxtryDecay_;
//@}
private:
/**
* Factors for the various scales
*/
//@{
/**
* The factorization scale factor.
*/
double factorizationScaleFactor_;
/**
* The renormalization scale factor.
*/
double renormalizationScaleFactor_;
/**
* The scale factor for the hard scale
*/
double hardScaleFactor_;
/**
* True, if the phase space restrictions of the dipole shower should
* be applied.
*/
bool restrictPhasespace_;
/**
* True if maximum pt should be deduced from the factorization scale
*/
bool maxPtIsMuF_;
/**
* The profile scales
*/
Ptr<HardScaleProfile>::ptr hardScaleProfile_;
//@}
private:
/**
* Storage of information about the current event
*/
//@{
/**
* The incoming beam particles for the current collision
*/
tPPair incoming_;
/**
* Boost to get back to the lab
*/
LorentzRotation boost_;
/**
* Const pointer to the currently handeled ThePEG::SubProcess
*/
tSubProPtr subProcess_;
/**
* Const pointer to the current step
*/
tcStepPtr current_;
//@}
private:
/**
* PDFs to be used for the various stages and related parameters
*/
//@{
/**
* The PDF freezing scale
*/
Energy pdfFreezingScale_;
/**
* PDFs to be used for the various stages and related parameters
*/
//@{
/**
* The PDF for beam particle A. Overrides the particle's own PDF setting.
*/
PDFPtr PDFA_;
/**
* The PDF for beam particle B. Overrides the particle's own PDF setting.
*/
PDFPtr PDFB_;
/**
* The PDF for beam particle A for remnant splitting. Overrides the particle's own PDF setting.
*/
PDFPtr PDFARemnant_;
/**
* The PDF for beam particle B for remnant splitting. Overrides the particle's own PDF setting.
*/
PDFPtr PDFBRemnant_;
/**
* The MPI PDF's to be used for secondary scatters.
*/
pair <PDFPtr, PDFPtr> mpipdfs_;
/**
* The MPI PDF's to be used for secondary scatters.
*/
pair <PDFPtr, PDFPtr> rempdfs_;
/**
* The MPI PDF's to be used for secondary scatters.
*/
pair <PDFPtr, PDFPtr> remmpipdfs_;
//@}
private:
/**
* @name Parameters for initial- and final-state radiation
*/
//@{
/**
* Switch on or off final state radiation.
*/
bool doFSR_;
/**
* Switch on or off initial state radiation.
*/
bool doISR_;
//@}
private:
/**
* @name Parameters for particle decays
*/
//@{
/**
* Whether or not to split into hard and decay trees
*/
bool splitHardProcess_;
/**
* PDG codes of the particles which decay during showering
* this is fast storage for use during running
*/
set<long> particlesDecayInShower_;
/**
* PDG codes of the particles which decay during showering
* this is a vector that is interfaced so they can be changed
*/
vector<long> inputparticlesDecayInShower_;
//@}
private:
/**
* Parameters for the space-time model
*/
//@{
/**
* Whether or not to include spa-cetime distances in the shower
*/
bool includeSpaceTime_;
/**
* The minimum virtuality for the space-time model
*/
Energy2 vMin_;
//@}
private:
/**
* Parameters relevant for reweight and variations
*/
//@{
/**
* The shower variations
*/
map<string,ShowerVariation> showerVariations_;
/**
* Command to add a shower variation
*/
string doAddVariation(string);
/**
* A reweighting factor applied by the showering
*/
double reweight_;
/**
* The shower variation weights
*/
map<string,double> currentWeights_;
//@}
};
}
#endif /* HERWIG_ShowerHandler_H */
diff --git a/Tests/Makefile.am b/Tests/Makefile.am
--- a/Tests/Makefile.am
+++ b/Tests/Makefile.am
@@ -1,366 +1,370 @@
AM_LDFLAGS += -module -avoid-version -rpath /dummy/path/not/used
EXTRA_DIST = Inputs python Rivet
dist-hook:
rm -rf $(distdir)/Inputs/.svn
rm -rf $(distdir)/python/.svn
rm -rf $(distdir)/Rivet/.svn
EXTRA_LTLIBRARIES = LeptonTest.la GammaTest.la HadronTest.la DISTest.la
if WANT_LIBFASTJET
EXTRA_LTLIBRARIES += HadronJetTest.la LeptonJetTest.la
HadronJetTest_la_SOURCES = \
Hadron/VHTest.h Hadron/VHTest.cc\
Hadron/VTest.h Hadron/VTest.cc\
Hadron/HTest.h Hadron/HTest.cc
HadronJetTest_la_CPPFLAGS = $(AM_CPPFLAGS) $(FASTJETINCLUDE) \
-I$(FASTJETPATH)
HadronJetTest_la_LIBADD = $(FASTJETLIBS)
LeptonJetTest_la_SOURCES = \
Lepton/TopDecay.h Lepton/TopDecay.cc
LeptonJetTest_la_CPPFLAGS = $(AM_CPPFLAGS) $(FASTJETINCLUDE) \
-I$(FASTJETPATH)
LeptonJetTest_la_LIBADD = $(FASTJETLIBS)
endif
LeptonTest_la_SOURCES = \
Lepton/VVTest.h Lepton/VVTest.cc \
Lepton/VBFTest.h Lepton/VBFTest.cc \
Lepton/VHTest.h Lepton/VHTest.cc \
Lepton/FermionTest.h Lepton/FermionTest.cc
GammaTest_la_SOURCES = \
Gamma/GammaMETest.h Gamma/GammaMETest.cc \
Gamma/GammaPMETest.h Gamma/GammaPMETest.cc
DISTest_la_SOURCES = \
DIS/DISTest.h DIS/DISTest.cc
HadronTest_la_SOURCES = \
Hadron/HadronVVTest.h Hadron/HadronVVTest.cc\
Hadron/HadronVBFTest.h Hadron/HadronVBFTest.cc\
Hadron/WHTest.h Hadron/WHTest.cc\
Hadron/ZHTest.h Hadron/ZHTest.cc\
Hadron/VGammaTest.h Hadron/VGammaTest.cc\
Hadron/ZJetTest.h Hadron/ZJetTest.cc\
Hadron/WJetTest.h Hadron/WJetTest.cc\
Hadron/QQHTest.h Hadron/QQHTest.cc
REPO = $(top_builddir)/src/HerwigDefaults.rpo
HERWIG = $(top_builddir)/src/Herwig
HWREAD = $(HERWIG) read --repo $(REPO) -L $(builddir)/.libs -i $(top_builddir)/src
HWRUN = $(HERWIG) run
tests : tests-LEP tests-DIS tests-LHC tests-Gamma
if WANT_LIBFASTJET
tests-LEP : test-LEP-VV test-LEP-VH test-LEP-VBF test-LEP-BB test-LEP-Quarks test-LEP-Leptons \
test-LEP-default test-LEP-Powheg test-LEP-TopDecay
else
tests-LEP : test-LEP-VV test-LEP-VH test-LEP-VBF test-LEP-BB test-LEP-Quarks test-LEP-Leptons
endif
tests-DIS : test-DIS-Charged test-DIS-Neutral
if WANT_LIBFASTJET
tests-LHC : test-LHC-WW test-LHC-WZ test-LHC-ZZ test-LHC-ZGamma test-LHC-WGamma \
test-LHC-ZH test-LHC-WH test-LHC-ZJet test-LHC-WJet test-LHC-Z test-LHC-W test-LHC-ZZVBF test-LHC-VBF \
test-LHC-WWVBF test-LHC-bbH test-LHC-ttH test-LHC-GammaGamma test-LHC-GammaJet test-LHC-Higgs \
test-LHC-HiggsJet test-LHC-QCDFast test-LHC-QCD test-LHC-Top test-LHC-Bottom \
test-LHC-WHJet test-LHC-ZHJet test-LHC-HJet test-LHC-ZShower test-LHC-WShower\
test-LHC-WHJet-Powheg test-LHC-ZHJet-Powheg test-LHC-HJet-Powheg \
test-LHC-ZShower-Powheg test-LHC-WShower-Powheg
else
tests-LHC : test-LHC-WW test-LHC-WZ test-LHC-ZZ test-LHC-ZGamma test-LHC-WGamma \
test-LHC-ZH test-LHC-WH test-LHC-ZJet test-LHC-WJet test-LHC-Z test-LHC-W test-LHC-ZZVBF test-LHC-VBF \
test-LHC-WWVBF test-LHC-bbH test-LHC-ttH test-LHC-GammaGamma test-LHC-GammaJet test-LHC-Higgs \
test-LHC-HiggsJet test-LHC-QCDFast test-LHC-QCD test-LHC-Top
endif
tests-Gamma : test-Gamma-FF test-Gamma-WW test-Gamma-P
if WANT_LIBFASTJET
test-LEP-% : Inputs/LEP-%.in LeptonTest.la LeptonJetTest.la
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
else
test-LEP-% : Inputs/LEP-%.in LeptonTest.la
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
endif
Rivet-LHC-Matchbox-% : Rivet/LHC-Matchbox-%.in
if [ ! -d Rivet-$(notdir $(subst .in,,$<)) ]; then mkdir Rivet-$(notdir $(subst .in,,$<)); fi;
cd Rivet-$(notdir $(subst .in,,$<)); echo `pwd`; \
../$(HERWIG) read --repo ../$(REPO) -L ../$(top_builddir)/lib -i ../$(top_builddir)/src ../$<; \
../$(HERWIG) run $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}; \
mv $(notdir $(subst .in,.yoda,$<)) ..; \
cd ..
Rivet-TVT-Matchbox-% : Rivet/TVT-Matchbox-%.in
if [ ! -d Rivet-$(notdir $(subst .in,,$<)) ]; then mkdir Rivet-$(notdir $(subst .in,,$<)); fi;
cd Rivet-$(notdir $(subst .in,,$<)); echo `pwd`; \
../$(HERWIG) read --repo ../$(REPO) -L ../$(top_builddir)/lib -i ../$(top_builddir)/src ../$<; \
../$(HERWIG) run $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}; \
mv $(notdir $(subst .in,.yoda,$<)) ..; \
cd ..
Rivet-TVT-Dipole-% : Rivet/TVT-Dipole-%.in
if [ ! -d Rivet-$(notdir $(subst .in,,$<)) ]; then mkdir Rivet-$(notdir $(subst .in,,$<)); fi;
cd Rivet-$(notdir $(subst .in,,$<)); echo `pwd`; \
../$(HERWIG) read --repo ../$(REPO) -L ../$(top_builddir)/lib -i ../$(top_builddir)/src ../$<; \
../$(HERWIG) run $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}; \
mv $(notdir $(subst .in,.yoda,$<)) ..; \
cd ..
Rivet-LHC-Dipole-% : Rivet/LHC-Dipole-%.in
if [ ! -d Rivet-$(notdir $(subst .in,,$<)) ]; then mkdir Rivet-$(notdir $(subst .in,,$<)); fi;
cd Rivet-$(notdir $(subst .in,,$<)); echo `pwd`; \
../$(HERWIG) read --repo ../$(REPO) -L ../$(top_builddir)/lib -i ../$(top_builddir)/src ../$<; \
../$(HERWIG) run $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}; \
mv $(notdir $(subst .in,.yoda,$<)) ..; \
cd ..
Rivet/LEP-%.in :
python/make_input_files.py $(notdir $(subst .in,,$@))
Rivet/DIS-%.in :
python/make_input_files.py $(notdir $(subst .in,,$@))
Rivet/BFactory-%.in:
python/make_input_files.py $(notdir $(subst .in,,$@))
Rivet/TVT-%.in:
python/make_input_files.py $(notdir $(subst .in,,$@))
Rivet/LHC-%.in:
python/make_input_files.py $(notdir $(subst .in,,$@))
Rivet/Star-%.in:
python/make_input_files.py $(notdir $(subst .in,,$@))
Rivet/SppS-%.in:
python/make_input_files.py $(notdir $(subst .in,,$@))
Rivet/ISR-%.in:
python/make_input_files.py $(notdir $(subst .in,,$@))
Rivet-LEP-Matchbox-% : Rivet/LEP-Matchbox-%.in
if [ ! -d Rivet-$(notdir $(subst .in,,$<)) ]; then mkdir Rivet-$(notdir $(subst .in,,$<)); fi;
cd Rivet-$(notdir $(subst .in,,$<)); echo `pwd`; \
../$(HERWIG) read --repo ../$(REPO) -L ../$(top_builddir)/lib -i ../$(top_builddir)/src ../$<; \
../$(HERWIG) run $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}; \
mv $(notdir $(subst .in,.yoda,$<)) ..; \
cd ..
Rivet-LEP-Dipole-% : Rivet/LEP-Dipole-%.in
if [ ! -d Rivet-$(notdir $(subst .in,,$<)) ]; then mkdir Rivet-$(notdir $(subst .in,,$<)); fi;
cd Rivet-$(notdir $(subst .in,,$<)); echo `pwd`; \
../$(HERWIG) read --repo ../$(REPO) -L ../$(top_builddir)/lib -i ../$(top_builddir)/src ../$<; \
../$(HERWIG) run $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}; \
mv $(notdir $(subst .in,.yoda,$<)) ..; \
cd ..
Rivet-BFactory-Matchbox-% : Rivet/BFactory-Matchbox-%.in
if [ ! -d Rivet-$(notdir $(subst .in,,$<)) ]; then mkdir Rivet-$(notdir $(subst .in,,$<)); fi;
cd Rivet-$(notdir $(subst .in,,$<)); echo `pwd`; \
../$(HERWIG) read --repo ../$(REPO) -L ../$(top_builddir)/lib -i ../$(top_builddir)/src ../$<; \
../$(HERWIG) run $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}; \
mv $(notdir $(subst .in,.yoda,$<)) ..; \
cd ..
Rivet-LEP-% : Rivet/LEP-%.in
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
Rivet-BFactory-% : Rivet/BFactory-%.in
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
Rivet-TVT-% : Rivet/TVT-%.in
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
Rivet-DIS-% : Rivet/DIS-%.in
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
Rivet-LHC-% : Rivet/LHC-%.in
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
Rivet-Star-% : Rivet/Star-%.in
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
Rivet-SppS-% : Rivet/SppS-%.in
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
Rivet-ISR-% : Rivet/ISR-%.in
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
-Rivet-inputfiles: $(shell echo Rivet/LEP{,-Powheg,-Matchbox,-Dipole,-Matchbox-Powheg,-Merging}-{10,22,35,44,91,130,133,136,161,172,177,183,189,192,196,197,200,202,206,91-nopi}.in) \
+
+Rivet-inputfiles: $(shell echo Rivet/LEP{,-Powheg,-Matchbox,-Dipole,-Matchbox-Powheg,-Merging}-{9.4,12,13,17,27.6,29,30.2,30.7,30.75,30,31.3,34.8,43.6,50,52,55,56,57,60.8,60,61.4,10,12.8,22,26.8,35,44,48.0,91,93.0,130,133,136,161,172,177,183,189,192,196,197,200,202,206,91-nopi}.in) \
$(shell echo Rivet/LEP{,-Powheg,-Matchbox-Powheg}-14.in) \
+ $(shell echo Rivet/LEP-{10.5,11.96,12.8,13.96,16.86,21.84,26.8,28.48,35.44,48.0,97.0}-gg.in) \
$(shell echo Rivet/BFactory{,-Powheg,-Matchbox,-Dipole,-Matchbox-Powheg}-{10.52,10.52-sym,10.54,10.45}.in) \
$(shell echo Rivet/BFactory-{Upsilon,Upsilon2,Upsilon4,Tau,10.58-res}.in) \
$(shell echo Rivet/DIS{,-NoME,-Powheg,-Matchbox,-Dipole,-Matchbox-Powheg,-Merging}-{e--LowQ2,e+-LowQ2,e+-HighQ2}.in) \
$(shell echo Rivet/TVT{,-Powheg,-Matchbox,-Dipole,-Matchbox-Powheg,-Merging}-{Run-I-Z,Run-I-W,Run-I-WZ,Run-II-Z-e,Run-II-Z-{,LowMass-,HighMass-}mu,Run-II-W}.in) \
$(shell echo Rivet/TVT-Run-II-{DiPhoton-GammaGamma,DiPhoton-GammaJet,PromptPhoton}.in) \
$(shell echo Rivet/TVT-Powheg-Run-II-{DiPhoton-GammaGamma,DiPhoton-GammaJet}.in) \
$(shell echo Rivet/TVT{,-Dipole,-Matchbox,-Matchbox-Powheg,-Merging}-{Run-II-Jets-{0..11},Run-I-Jets-{1..8}}.in ) \
$(shell echo Rivet/TVT{,-Dipole,-Matchbox,-Matchbox-Powheg,-Merging}-{630-Jets-{1..3},300-Jets-1,900-Jets-1}.in ) \
$(shell echo Rivet/TVT-{Run-I,Run-II,300,630,900}-UE.in) \
$(shell echo Rivet/LHC{,-Dipole,-Matchbox,-Matchbox-Powheg,-Merging}-7-DiJets-{1..7}-{A,B,C}.in ) \
$(shell echo Rivet/LHC{,-Dipole,-Matchbox,-Matchbox-Powheg,-Merging}-{7,8,13}-Jets-{0..10}.in ) \
$(shell echo Rivet/LHC-{900,2360,2760,7,8,13}-UE.in ) \
$(shell echo Rivet/LHC-{900,7,13}-UE-Long.in ) \
$(shell echo Rivet/LHC{,-Dipole,-Matchbox,-Matchbox-Powheg,-Merging}-7-Charm-{1..5}.in) \
$(shell echo Rivet/LHC{,-Dipole,-Matchbox,-Matchbox-Powheg,-Merging}-7-Bottom-{0..8}.in) \
$(shell echo Rivet/LHC{,-Matchbox,-Matchbox-Powheg,-Merging}-7-Top-{L,SL}.in) \
$(shell echo Rivet/LHC{,-Matchbox,-Matchbox-Powheg,-Merging}-{7,8,13}-Top-All.in) \
$(shell echo Rivet/Star-{UE,Jets-{1..4}}.in ) \
$(shell echo Rivet/SppS-{200,500,900,546}-UE.in ) \
$(shell echo Rivet/LHC{,-Matchbox,-Matchbox-Powheg,-Powheg,-Dipole,-Merging}-{W-{e,mu},13-Z-{e,mu},8-Z-Mass{1..4}-{e,mu},Z-{e,mu,mu-SOPHTY},Z-LowMass-{e,mu},Z-MedMass-e,WZ,WW-{emu,ll},ZZ-{ll,lv},8-ZZ-lv,W-Z-{e,mu}}.in) \
$(shell echo Rivet/LHC-7-{W,Z}Gamma-{e,mu}.in) \
$(shell echo Rivet/LHC{,-Matchbox,-Matchbox-Powheg,-Dipole,-Merging}-{7-W-Jet-{1..3}-e,7-Z-Jet-{0..3}-e,7-Z-Jet-0-mu}.in) \
$(shell echo Rivet/LHC{-Matchbox,-Matchbox-Powheg,-Dipole,-Merging}-{Z-b,Z-bb,W-b,8-Z-jj}.in) \
$(shell echo Rivet/LHC-{7,8}-PromptPhoton-{1..4}.in) Rivet/LHC-GammaGamma-7.in \
$(shell echo Rivet/LHC{,-Powheg}-7-{DiPhoton-GammaGamma,DiPhoton-GammaJet}.in) \
$(shell echo Rivet/LHC{,-Powheg,-Matchbox,-Matchbox-Powheg,-Dipole,-Merging}-{ggH,VBF,WH,ZH}.in) \
$(shell echo Rivet/LHC{,-Powheg,-Matchbox,-Matchbox-Powheg,-Dipole,-Merging}-8-{ggH,VBF,WH,ZH}{,-GammaGamma}.in) \
$(shell echo Rivet/LHC{,-Matchbox,-Matchbox-Powheg,-Dipole,-Merging}-ggHJet.in)
# $(shell echo Rivet/ISR-{30,44,53,62}-UE.in ) $(shell echo Rivet/SppS-{53,63}-UE.in )
-Rivet-LEP: $(shell echo Rivet-LEP{,-Powheg,-Matchbox,-Dipole}-{10,22,35,44,91,130,133,136,161,172,177,183,189,192,196,197,200,202,206,91-nopi})
+Rivet-LEP: $(shell echo Rivet-LEP{,-Powheg,-Matchbox,-Dipole}-{9.4,12,13,17,27.6,29,30.2,30.7,30.75,30,31.3,34.8,43.6,50,52,55,56,57,60.8,60,61.4,10,12.8,22,26.8,35,44,48.0,91,93.0,130,133,136,161,172,177,183,189,192,196,197,200,202,206,91-nopi}) \
+ $(shell echo Rivet-LEP-{10.5,11.96,12.8,13.96,16.86,21.84,26.8,28.48,35.44,48.0,97.0}-gg) \
+ $(shell echo Rivet-LEP{,-Powheg,-Matchbox-Powheg}-14.in)
rm -rf Rivet-LEP
- python/merge-LEP LEP
+ python/merge-LEP --with-gg LEP
python/merge-LEP LEP-Powheg
python/merge-LEP LEP-Matchbox
python/merge-LEP LEP-Dipole
rivet-mkhtml -o Rivet-LEP LEP.yoda:Hw LEP-Powheg.yoda:Hw-Powheg LEP-Matchbox.yoda:Hw-Matchbox LEP-Dipole.yoda:Hw-Dipole
Rivet-BFactory: $(shell echo Rivet-BFactory{,-Powheg,-Matchbox,-Dipole}-{10.52,10.52-sym,10.54,10.45}) \
$(shell echo Rivet-BFactory-{Upsilon,Upsilon2,Upsilon4,Tau,10.58-res,10.58})
rm -rf Rivet-BFactory
python/merge-BFactory BFactory
python/merge-BFactory BFactory-Powheg
python/merge-BFactory BFactory-Matchbox
python/merge-BFactory BFactory-Dipole
rivet-mkhtml -o Rivet-BFactory BFactory.yoda:Hw BFactory-Powheg.yoda:Hw-Powheg BFactory-Matchbox.yoda:Hw-Matchbox BFactory-Dipole.yoda:Hw-Dipole
Rivet-DIS: $(shell echo Rivet-DIS{,-NoME,-Powheg,-Matchbox,-Dipole}-{e--LowQ2,e+-LowQ2,e+-HighQ2})
rm -rf Rivet-DIS
python/merge-DIS DIS
python/merge-DIS DIS-Powheg
python/merge-DIS DIS-NoME
python/merge-DIS DIS-Matchbox
python/merge-DIS DIS-Dipole
rivet-mkhtml -o Rivet-DIS DIS.yoda:Hw DIS-Powheg.yoda:Hw-Powheg DIS-NoME.yoda:Hw-NoME DIS-Matchbox.yoda:Hw-Matchbox DIS-Dipole.yoda:Hw-Dipole
Rivet-TVT-WZ: $(shell echo Rivet-TVT{,-Powheg,-Matchbox,-Dipole}-{Run-I-Z,Run-I-W,Run-I-WZ,Run-II-Z-{e,{,LowMass-,HighMass-}mu},Run-II-W})
rm -rf Rivet-TVT-WZ
python/merge-TVT-EW TVT-Run-II-W.yoda TVT-Run-II-Z-{e,{,LowMass-,HighMass-}mu}.yoda\
TVT-Run-I-{W,Z,WZ}.yoda -o TVT-WZ.yoda
python/merge-TVT-EW TVT-Powheg-Run-II-W.yoda TVT-Powheg-Run-II-Z-{e,{,LowMass-,HighMass-}mu}.yoda\
TVT-Powheg-Run-I-{W,Z,WZ}.yoda -o TVT-Powheg-WZ.yoda
python/merge-TVT-EW TVT-Matchbox-Run-II-W.yoda TVT-Matchbox-Run-II-Z-{e,{,LowMass-,HighMass-}mu}.yoda\
TVT-Matchbox-Run-I-{W,Z,WZ}.yoda -o TVT-Matchbox-WZ.yoda
python/merge-TVT-EW TVT-Dipole-Run-II-W.yoda TVT-Dipole-Run-II-Z-{e,{,LowMass-,HighMass-}mu}.yoda\
TVT-Dipole-Run-I-{W,Z,WZ}.yoda -o TVT-Dipole-WZ.yoda
rivet-mkhtml -o Rivet-TVT-WZ TVT-WZ.yoda:Hw TVT-Powheg-WZ.yoda:Hw-Powheg TVT-Matchbox-WZ.yoda:Hw-Matchbox TVT-Dipole-WZ.yoda:Hw-Dipole
Rivet-TVT-Photon: $(shell echo Rivet-TVT-Run-II-{DiPhoton-GammaGamma,DiPhoton-GammaJet,PromptPhoton}) \
$(shell echo Rivet-TVT-Powheg-Run-II-{DiPhoton-GammaGamma,DiPhoton-GammaJet})
rm -rf Rivet-TVT-Photon
python/merge-TVT-Photon TVT -o TVT-Photon.yoda
python/merge-TVT-Photon TVT-Powheg -o TVT-Powheg-Photon.yoda
rivet-mkhtml -o Rivet-TVT-Photon TVT-Photon.yoda:Hw TVT-Powheg-Photon.yoda:Hw-Powheg
Rivet-TVT-Jets: $(shell echo Rivet-TVT-{Run-II-Jets-{0..11},Run-I-Jets-{1..8}} ) \
$(shell echo Rivet-TVT-{630-Jets-{1..3},300-Jets-1,900-Jets-1} ) \
$(shell echo Rivet-TVT-{Run-I,Run-II,300,630,900}-UE)
rm -rf Rivet-TVT-Jets
python/merge-TVT-Jets TVT
rivet-mkhtml -o Rivet-TVT-Jets TVT-Jets.yoda:Hw
#python/merge-TVT-Energy TVT
#rivet-merge-CDF_2012_NOTE10874 TVT-300-Energy.yoda TVT-900-Energy.yoda TVT-1960-Energy.yoda
#flat2yoda RatioPlots.dat -o TVT-RatioPlots.yoda
Rivet-LHC-Jets: $(shell echo Rivet-LHC-7-DiJets-{1..7}-{A,B,C} ) \
$(shell echo Rivet-LHC-{7,8,13}-Jets-{0..10} ) \
$(shell echo Rivet-LHC-{900,2360,2760,7,8,13}-UE ) \
$(shell echo Rivet-LHC-{900,7,13}-UE-Long ) \
$(shell echo Rivet-LHC-7-Charm-{1..5}) \
$(shell echo Rivet-LHC-7-Bottom-{0..8}) \
$(shell echo Rivet-LHC-7-Top-{L,SL})\
$(shell echo Rivet-LHC-{7,8,13}-Top-All)
rm -rf Rivet-LHC-Jets
python/merge-LHC-Jets LHC
rivet-mkhtml -o Rivet-LHC-Jets LHC-Jets.yoda:Hw
Rivet-Star: $(shell echo Rivet-Star-{UE,Jets-{1..4}} )
rm -rf Rivet-Star
python/merge-Star Star
rivet-mkhtml -o Rivet-Star Star.yoda
Rivet-SppS: $(shell echo Rivet-ISR-{30,44,53,62}-UE ) \
$(shell echo Rivet-SppS-{53,63,200,500,900,546}-UE )
rm -rf Rivet-SppS
python/merge-SppS SppS
rivet-mkhtml -o Rivet-SppS SppS.yoda
Rivet-LHC-EW: $(shell echo Rivet-LHC{,-Matchbox,-Powheg,-Dipole}-{13-Z-{e,mu},8-Z-Mass{1..4}-{e,mu},W-{e,mu},Z-{e,mu,mu-SOPHTY},Z-LowMass-{e,mu},Z-MedMass-e,WZ,WW-{emu,ll},ZZ-{ll,lv},8-ZZ-lv,W-Z-{e,mu}}) \
$(shell echo Rivet-LHC{,-Matchbox,-Dipole}-{7-W-Jet-{1..3}-e,7-Z-Jet-{0..3}-e,7-Z-Jet-0-mu}) \
$(shell echo Rivet-LHC{-Matchbox,-Dipole}-{Z-b,Z-bb,W-b,8-Z-jj}) \
$(shell echo Rivet-LHC-7-{W,Z}Gamma-{e,mu}) \
rm -rf Rivet-LHC-EW;
python/merge-LHC-EW LHC-{13-Z-{e,mu},8-Z-Mass{1..4}-{e,mu},W-{e,mu},Z-{e,mu,mu-Short},Z-LowMass-{e,mu},Z-MedMass-e,W-Z-{e,mu},WW-{emu,ll},WZ,ZZ-{ll,lv},8-ZZ-lv}.yoda LHC-7-{W,Z}-Jet-{1,2,3}-e.yoda LHC-7-{W,Z}Gamma-{e,mu}.yoda -o LHC-EW.yoda;
python/merge-LHC-EW LHC-Matchbox-{13-Z-{e,mu},8-Z-Mass{1..4}-{e,mu},W-{e,mu},Z-{e,mu,mu-Short},Z-LowMass-{e,mu},Z-MedMass-e,W-Z-{e,mu},WW-{emu,ll},WZ,ZZ-{ll,lv},8-ZZ-lv}.yoda LHC-Matchbox-7-{W,Z}-Jet-{1,2,3}-e.yoda -o LHC-Matchbox-EW.yoda;
python/merge-LHC-EW LHC-Dipole-{13-Z-{e,mu},8-Z-Mass{1..4}-{e,mu},W-{e,mu},Z-{e,mu,mu-Short},Z-LowMass-{e,mu},Z-MedMass-e,W-Z-{e,mu},WW-{emu,ll},WZ,ZZ-{ll,lv},8-ZZ-lv}.yoda LHC-Dipole-7-{W,Z}-Jet-{1,2,3}-e.yoda -o LHC-Dipole-EW.yoda;
python/merge-LHC-EW LHC-Powheg-{W-{e,mu},Z-{e,mu},Z-LowMass-{e,mu},Z-MedMass-e,W-Z-{e,mu},WW-{emu,ll},WZ,ZZ-{ll,lv},8-ZZ-lv}.yoda -o LHC-Powheg-EW.yoda;
rivet-mkhtml -o Rivet-LHC-EW LHC-EW.yoda:Hw LHC-Powheg-EW.yoda:Hw-Powheg LHC-Matchbox-EW.yoda:Hw-Matchbox LHC-Matchbox-Z-b.yoda:Hw-Matchbox-Zb \
LHC-Matchbox-Z-bb.yoda:Hw-Matchbox-Zbb LHC-Matchbox-W-b.yoda:Hw-Matchbox-W-bb LHC-Dipole-EW.yoda:Hw-Dipole \
LHC-Dipole-Z-b.yoda:Hw-Dipole-Zb LHC-Dipole-Z-bb.yoda:Hw-Dipole-Zbb LHC-Dipole-W-b.yoda:Hw-Dipole-W-bb \
LHC-Z-mu-SOPHTY.yoda:Hw LHC-Powheg-Z-mu-SOPHTY.yoda:Hw-Powheg LHC-Matchbox-Z-mu-SOPHTY.yoda:Hw-Matchbox
Rivet-LHC-Photon: $(shell echo Rivet-LHC-{7,8}-PromptPhoton-{1..4}) Rivet-LHC-GammaGamma-7 \
$(shell echo Rivet-LHC{,-Powheg}-7-{DiPhoton-GammaGamma,DiPhoton-GammaJet})
rm -rf Rivet-LHC-Photon
python/merge-LHC-Photon LHC -o LHC-Photon.yoda
python/merge-LHC-Photon LHC-Powheg -o LHC-Powheg-Photon.yoda
rivet-mkhtml -o Rivet-LHC-Photon LHC-Photon.yoda:Hw LHC-Powheg-Photon.yoda:Hw-Powheg
Rivet-LHC-Higgs: $(shell echo Rivet-LHC{,-Powheg}-{ggH,VBF,WH,ZH})\
$(shell echo Rivet-LHC{,-Powheg}-8-{ggH,VBF,WH,ZH}{,-GammaGamma}) Rivet-LHC-ggHJet
rm -rf Rivet-LHC-Higgs
rivet-mkhtml -o Rivet-LHC-Higgs LHC-Powheg-ggH.yoda:gg-Powheg LHC-ggH.yoda:gg LHC-ggHJet.yoda:HJet \
LHC-Powheg-VBF.yoda:VBF-Powheg LHC-VBF.yoda:VBF LHC-WH.yoda:WH LHC-ZH.yoda:ZH \
LHC-Powheg-WH.yoda:WH-Powheg LHC-Powheg-ZH.yoda:ZH-Powheg
tests-Rivet : Rivet-LEP Rivet-BFactory Rivet-DIS Rivet-TVT-WZ Rivet-TVT-Photon Rivet-TVT-Jets Rivet-LHC-Jets Rivet-Star Rivet-SppS Rivet-LHC-EW Rivet-LHC-Photon Rivet-LHC-Higgs
test-Gamma-% : Inputs/Gamma-%.in GammaTest.la
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
test-DIS-% : Inputs/DIS-%.in DISTest.la
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
if WANT_LIBFASTJET
test-LHC-% : Inputs/LHC-%.in HadronTest.la GammaTest.la HadronJetTest.la
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
else
test-LHC-% : Inputs/LHC-%.in HadronTest.la GammaTest.la
$(HWREAD) $<
$(HWRUN) $(notdir $(subst .in,.run,$<)) -N $${NUMEVENTS:-10000}
endif
clean-local:
rm -f *.out *.log *.tex *.top *.run *.dump *.mult *.Bmult *.yoda
diff --git a/Tests/Rivet/LEP/LEP-10.5-gg.in b/Tests/Rivet/LEP/LEP-10.5-gg.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-10.5-gg.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 10.5
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I631361
diff --git a/Tests/Rivet/LEP/LEP-11.96-gg.in b/Tests/Rivet/LEP/LEP-11.96-gg.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-11.96-gg.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 11.96
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I631361
diff --git a/Tests/Rivet/LEP/LEP-12.8-gg.in b/Tests/Rivet/LEP/LEP-12.8-gg.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-12.8-gg.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 12.8
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I648738
diff --git a/Tests/Rivet/LEP/LEP-12.8.in b/Tests/Rivet/LEP/LEP-12.8.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-12.8.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 12.8
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I648738
diff --git a/Tests/Rivet/LEP/LEP-12.in b/Tests/Rivet/LEP/LEP-12.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-12.in
@@ -0,0 +1,12 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 12.0
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.0
+##################################################
+# select the analyses
+##################################################
+# Validated
+##################################################
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PLUTO_1980_I154270
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 JADE_1983_I190818
diff --git a/Tests/Rivet/LEP/LEP-13.96-gg.in b/Tests/Rivet/LEP/LEP-13.96-gg.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-13.96-gg.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 13.96
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I631361
diff --git a/Tests/Rivet/LEP/LEP-13.in b/Tests/Rivet/LEP/LEP-13.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-13.in
@@ -0,0 +1,11 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 13.0
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.0
+##################################################
+# select the analyses
+##################################################
+# Validated
+##################################################
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PLUTO_1980_I154270
diff --git a/Tests/Rivet/LEP/LEP-14.in b/Tests/Rivet/LEP/LEP-14.in
--- a/Tests/Rivet/LEP/LEP-14.in
+++ b/Tests/Rivet/LEP/LEP-14.in
@@ -1,11 +1,11 @@
##################################################
# LEP physics parameters (override defaults)
##################################################
set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 14.
set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 13.*GeV
##################################################
# select the analyses
##################################################
# tasso event shapes at various low energies
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 TASSO_1990_S2148048
-#insert /Herwig/Analysis/RivetAnalysis:Analyses 0 TASSO_1989_I277658
\ No newline at end of file
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 TASSO_1989_I277658
\ No newline at end of file
diff --git a/Tests/Rivet/LEP/LEP-16.86-gg.in b/Tests/Rivet/LEP/LEP-16.86-gg.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-16.86-gg.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 16.86
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I631361
diff --git a/Tests/Rivet/LEP/LEP-17.in b/Tests/Rivet/LEP/LEP-17.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-17.in
@@ -0,0 +1,11 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 17.
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.0
+##################################################
+# select the analyses
+##################################################
+# Validated
+##################################################
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PLUTO_1980_I154270
diff --git a/Tests/Rivet/LEP/LEP-197.in b/Tests/Rivet/LEP/LEP-197.in
--- a/Tests/Rivet/LEP/LEP-197.in
+++ b/Tests/Rivet/LEP/LEP-197.in
@@ -1,11 +1,11 @@
##################################################
# LEP physics parameters (override defaults)
##################################################
set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 197.
##################################################
# select the analyses
##################################################
# OPAL event shapes and multiplicities at different energies
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_S6132243
# OPAL from gluon paper
-#insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I648738
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I648738
diff --git a/Tests/Rivet/LEP/LEP-21.84-gg.in b/Tests/Rivet/LEP/LEP-21.84-gg.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-21.84-gg.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 21.84
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I631361
diff --git a/Tests/Rivet/LEP/LEP-22.in b/Tests/Rivet/LEP/LEP-22.in
--- a/Tests/Rivet/LEP/LEP-22.in
+++ b/Tests/Rivet/LEP/LEP-22.in
@@ -1,14 +1,14 @@
##################################################
# LEP physics parameters (override defaults)
##################################################
set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 22.
set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 21*GeV
##################################################
# select the analyses
##################################################
# JADE jet rates at many energies
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 JADE_1998_S3612880
# tasso event shapes at various low energies
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 TASSO_1990_S2148048
-#insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PLUTO_1980_I154270
-#insert /Herwig/Analysis/RivetAnalysis:Analyses 0 TASSO_1989_I277658
\ No newline at end of file
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PLUTO_1980_I154270
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 TASSO_1989_I277658
\ No newline at end of file
diff --git a/Tests/Rivet/LEP/LEP-26.8-gg.in b/Tests/Rivet/LEP/LEP-26.8-gg.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-26.8-gg.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 26.8
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I648738
diff --git a/Tests/Rivet/LEP/LEP-26.8.in b/Tests/Rivet/LEP/LEP-26.8.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-26.8.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 26.8
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I648738
diff --git a/Tests/Rivet/LEP/LEP-27.6.in b/Tests/Rivet/LEP/LEP-27.6.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-27.6.in
@@ -0,0 +1,11 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 27.6
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.0
+##################################################
+# select the analyses
+##################################################
+# Validated
+##################################################
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PLUTO_1980_I154270
diff --git a/Tests/Rivet/LEP/LEP-28.48-gg.in b/Tests/Rivet/LEP/LEP-28.48-gg.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-28.48-gg.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 28.48
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I631361
diff --git a/Tests/Rivet/LEP/LEP-29.in b/Tests/Rivet/LEP/LEP-29.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-29.in
@@ -0,0 +1,12 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 29.0
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.0
+##################################################
+# select the analyses
+##################################################
+# Validated
+##################################################
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 HRS_1986_I18502
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 TPC_1987_I235694
diff --git a/Tests/Rivet/LEP/LEP-30.2.in b/Tests/Rivet/LEP/LEP-30.2.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-30.2.in
@@ -0,0 +1,11 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 30.2
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.0
+##################################################
+# select the analyses
+##################################################
+# Validated
+##################################################
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PLUTO_1980_I154270
diff --git a/Tests/Rivet/LEP/LEP-30.7.in b/Tests/Rivet/LEP/LEP-30.7.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-30.7.in
@@ -0,0 +1,11 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 30.7
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.0
+##################################################
+# select the analyses
+##################################################
+# Validated
+##################################################
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PLUTO_1980_I154270
diff --git a/Tests/Rivet/LEP/LEP-30.75.in b/Tests/Rivet/LEP/LEP-30.75.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-30.75.in
@@ -0,0 +1,11 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 30.75
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.0
+##################################################
+# select the analyses
+##################################################
+# Validated
+##################################################
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PLUTO_1980_I154270
diff --git a/Tests/Rivet/LEP/LEP-30.in b/Tests/Rivet/LEP/LEP-30.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-30.in
@@ -0,0 +1,11 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 30.0
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.0
+##################################################
+# select the analyses
+##################################################
+# Validated
+##################################################
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 JADE_1983_I190818
diff --git a/Tests/Rivet/LEP/LEP-31.3.in b/Tests/Rivet/LEP/LEP-31.3.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-31.3.in
@@ -0,0 +1,11 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 31.3
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.0
+##################################################
+# select the analyses
+##################################################
+# Validated
+##################################################
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PLUTO_1980_I154270
diff --git a/Tests/Rivet/LEP/LEP-34.8.in b/Tests/Rivet/LEP/LEP-34.8.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-34.8.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 34.8
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 13.*GeV
+##################################################
+# select the analyses
+##################################################
+# tasso charged mult
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 TASSO_1989_I277658
diff --git a/Tests/Rivet/LEP/LEP-35.44-gg.in b/Tests/Rivet/LEP/LEP-35.44-gg.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-35.44-gg.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 35.44
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I631361
diff --git a/Tests/Rivet/LEP/LEP-35.in b/Tests/Rivet/LEP/LEP-35.in
--- a/Tests/Rivet/LEP/LEP-35.in
+++ b/Tests/Rivet/LEP/LEP-35.in
@@ -1,17 +1,17 @@
##################################################
# LEP physics parameters (override defaults)
##################################################
set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 35.
##################################################
# select the analyses
##################################################
# OPAL/JADE jet rates at many energies
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 JADE_OPAL_2000_S4300807
# JADE jet rates at many energies
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 JADE_1998_S3612880
# tasso event shapes at various low energies
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 TASSO_1990_S2148048
# PDG hadron multiplicities and ratios
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PDG_HADRON_MULTIPLICITIES
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PDG_HADRON_MULTIPLICITIES_RATIOS
-#insert /Herwig/Analysis/RivetAnalysis:Analyses 0 JADE_1983_I190818
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 JADE_1983_I190818
diff --git a/Tests/Rivet/LEP/LEP-43.6.in b/Tests/Rivet/LEP/LEP-43.6.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-43.6.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 43.6
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 13.*GeV
+##################################################
+# select the analyses
+##################################################
+# tasso charged mult
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 TASSO_1989_I277658
diff --git a/Tests/Rivet/LEP/LEP-48.0-gg.in b/Tests/Rivet/LEP/LEP-48.0-gg.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-48.0-gg.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 48.0
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I648738
diff --git a/Tests/Rivet/LEP/LEP-48.0.in b/Tests/Rivet/LEP/LEP-48.0.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-48.0.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 48.0
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I648738
diff --git a/Tests/Rivet/LEP/LEP-50.in b/Tests/Rivet/LEP/LEP-50.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-50.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 50.
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 13.*GeV
+##################################################
+# select the analyses
+##################################################
+# tasso charged mult
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 AMY_1990_I295160
diff --git a/Tests/Rivet/LEP/LEP-52.in b/Tests/Rivet/LEP/LEP-52.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-52.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 52.
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 13.*GeV
+##################################################
+# select the analyses
+##################################################
+# tasso charged mult
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 AMY_1990_I295160
diff --git a/Tests/Rivet/LEP/LEP-55.in b/Tests/Rivet/LEP/LEP-55.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-55.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 55.
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 13.*GeV
+##################################################
+# select the analyses
+##################################################
+# tasso charged mult
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 AMY_1990_I295160
diff --git a/Tests/Rivet/LEP/LEP-56.in b/Tests/Rivet/LEP/LEP-56.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-56.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 56.
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 13.*GeV
+##################################################
+# select the analyses
+##################################################
+# tasso charged mult
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 AMY_1990_I295160
diff --git a/Tests/Rivet/LEP/LEP-57.in b/Tests/Rivet/LEP/LEP-57.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-57.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 57.
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 13.*GeV
+##################################################
+# select the analyses
+##################################################
+# tasso charged mult
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 AMY_1990_I295160
diff --git a/Tests/Rivet/LEP/LEP-60.8.in b/Tests/Rivet/LEP/LEP-60.8.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-60.8.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 60.8
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 13.*GeV
+##################################################
+# select the analyses
+##################################################
+# tasso charged mult
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 AMY_1990_I295160
diff --git a/Tests/Rivet/LEP/LEP-60.in b/Tests/Rivet/LEP/LEP-60.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-60.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 60.
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 13.*GeV
+##################################################
+# select the analyses
+##################################################
+# tasso charged mult
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 AMY_1990_I295160
diff --git a/Tests/Rivet/LEP/LEP-61.4.in b/Tests/Rivet/LEP/LEP-61.4.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-61.4.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 61.4
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 13.*GeV
+##################################################
+# select the analyses
+##################################################
+# tasso charged mult
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 AMY_1990_I295160
diff --git a/Tests/Rivet/LEP/LEP-9.4.in b/Tests/Rivet/LEP/LEP-9.4.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-9.4.in
@@ -0,0 +1,11 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 9.4
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.0
+##################################################
+# select the analyses
+##################################################
+# Validated
+##################################################
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PLUTO_1980_I154270
diff --git a/Tests/Rivet/LEP/LEP-91.in b/Tests/Rivet/LEP/LEP-91.in
--- a/Tests/Rivet/LEP/LEP-91.in
+++ b/Tests/Rivet/LEP/LEP-91.in
@@ -1,84 +1,85 @@
##################################################
# LEP physics parameters (override defaults)
##################################################
set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 91.2
##################################################
# select the analyses
##################################################
# Validated
##################################################
# ALEPH charged particle multiplicity
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 ALEPH_1991_S2435284
# OPAL charged particle multiplicity
-#insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_1992_I321190
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_1992_I321190
# DELPHI charged particle multiplicity
-#insert /Herwig/Analysis/RivetAnalysis:Analyses 0 DELPHI_1991_I301657
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 DELPHI_1991_I301657
# ALEPH main LEP I QCD summary paper
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 ALEPH_1996_S3486095
# ALEPH D*
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 ALEPH_1999_S4193598
# OPAL charged hadron analysis
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_1994_S2927284
# OPAL Delta++ analysis
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_1995_S3198391
# OPAL J/Psi analysis analysis
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_1996_S3257789
# ALEPH eta/omega analysis
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 ALEPH_2002_S4823664
# OPAL K*0 analysis
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_1997_S3608263
# OPAL flavour specific charged multiplicities etc
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_1998_S3780481
# OPAL f_0,f_2 and phi production
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_1998_S3702294
# OPAL gamma,pi0,eta,eta',rho+/-,a0+/-
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_1998_S3749908
# OPAL K0
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2000_S4418603
# OPAL K* +/-
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_1993_I342766
# SLD flavour specific charged multiplicities etc
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 SLD_1996_S3398250
# SLD flavour specific charged multiplicities etc
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 SLD_1999_S3743934
# SLD flavour specific charged multiplicities etc
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 SLD_2004_S5693039
# OPAL event shapes and multiplicities at different energies
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_S6132243
# ALEPH jet and event shapes at many energies
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 ALEPH_2004_S5765862
# OPAL/JADE jet rates at many energies
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 JADE_OPAL_2000_S4300807
# DELPHI strange baryon production
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 DELPHI_1995_S3137023
# DELPHI f_0, rho_0 and f_2 production
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 DELPHI_1999_S3960137
# OPAL strange baryon production
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_1997_S3396100
# DELPHI tuning paper
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 DELPHI_1996_S3430090
# DELPHI b quark
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 DELPHI_2002_069_CONF_603
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 DELPHI_2011_I890503
# ALEPH b quark
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 ALEPH_2001_S4656318
# SLD b quark
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 SLD_2002_S4869273
# OPAL b quark
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2003_I599181
# PDG hadron multiplicities and ratios
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PDG_HADRON_MULTIPLICITIES
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 PDG_HADRON_MULTIPLICITIES_RATIOS
# OPAL from gluon paper
-# #insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I648738
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I648738
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I631361_qq
# L3 eta
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 L3_1992_I336180
# L3 jet rates
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 L3_2004_I652683
# ALEPH pi+-, K+- and (p, anti-p)
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 ALEPH_1995_I382179
##################################################
# unvalidated
##################################################
# OPAL 4 jet angles
insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2001_S4553896
diff --git a/Tests/Rivet/LEP/LEP-93.0.in b/Tests/Rivet/LEP/LEP-93.0.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-93.0.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 93.0
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I648738
diff --git a/Tests/Rivet/LEP/LEP-97.0-gg.in b/Tests/Rivet/LEP/LEP-97.0-gg.in
new file mode 100644
--- /dev/null
+++ b/Tests/Rivet/LEP/LEP-97.0-gg.in
@@ -0,0 +1,10 @@
+##################################################
+# LEP physics parameters (override defaults)
+##################################################
+set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 97.0
+set /Herwig/Generators/EventGenerator:EventHandler:Cuts:MHatMin 9.99
+##################################################
+# select the analyses
+##################################################
+# PDG hadron multiplicities and ratios
+insert /Herwig/Analysis/RivetAnalysis:Analyses 0 OPAL_2004_I648738
diff --git a/Tests/Rivet/Templates/DIS-Merging.in b/Tests/Rivet/Templates/DIS-Merging.in
--- a/Tests/Rivet/Templates/DIS-Merging.in
+++ b/Tests/Rivet/Templates/DIS-Merging.in
@@ -1,60 +1,62 @@
# -*- ThePEG-repository -*-
##################################################
## Herwig/Matchbox example input file
##################################################
##################################################
## Collider type
##################################################
read snippets/DipoleMerging.in
read snippets/EPCollider.in
read snippets/MonacoSampler.in
##################################################
## Process selection
##################################################
## Note that event generation may fail if no matching matrix element has
## been found. Coupling orders are with respect to the Born process,
## i.e. NLO QCD does not require an additional power of alphas.
## Model assumptions
read Matchbox/StandardModelLike.in
read Matchbox/DiagonalCKM.in
## Set the order of the couplings
read Matchbox/MadGraph-OpenLoops.in
set /Herwig/Merging/MergingFactory:OrderInAlphaS 0
set /Herwig/Merging/MergingFactory:OrderInAlphaEW 2
set /Herwig/Merging/MergingFactory:ScaleChoice /Herwig/MatrixElements/Matchbox/Scales/LeptonQ2Scale
##################################################
## PDF and AlphaS choice
##################################################
read Matchbox/FiveFlavourNoBMassScheme.in
read Matchbox/MMHT2014.in
set /Herwig/Couplings/NLOAlphaS:input_alpha_s 0.118
read Merging/FactorCMWScheme.in
-do /Herwig/Merging/MergingFactory:ProductionMode
+
# switch off initial state QED radiation
set /Herwig/Particles/e-:PDF /Herwig/Partons/NoPDF
set /Herwig/Particles/e+:PDF /Herwig/Partons/NoPDF
# create the Rivet analysis
create ThePEG::RivetAnalysis /Herwig/Analysis/RivetAnalysis RivetAnalysis.so
insert /Herwig/Generators/EventGenerator:AnalysisHandlers 0 /Herwig/Analysis/RivetAnalysis
read ${parameterFile}
## Select the process
cd /Herwig/Merging/
set Merger:MergingScale 10.*GeV
${process}
+do /Herwig/Merging/MergingFactory:ProductionMode
+
cd /Herwig/Generators
set EventGenerator:MaxErrors 1000000
saverun ${runname} EventGenerator
diff --git a/Tests/Rivet/Templates/Hadron-Merging.in b/Tests/Rivet/Templates/Hadron-Merging.in
--- a/Tests/Rivet/Templates/Hadron-Merging.in
+++ b/Tests/Rivet/Templates/Hadron-Merging.in
@@ -1,45 +1,47 @@
# -*- ThePEG-repository -*-
##################################################
## Collider type
##################################################
read snippets/DipoleMerging.in
read snippets/PPCollider.in
read snippets/MonacoSampler.in
##################################################
## Matrix element library selection
##################################################
## Model assumptions
read Matchbox/StandardModelLike.in
read Matchbox/DiagonalCKM.in
read Matchbox/MadGraph-OpenLoops.in
##################################################
## PDF and AlphaS choice
##################################################
read Matchbox/FiveFlavourNoBMassScheme.in
read Matchbox/MMHT2014.in
set /Herwig/Couplings/NLOAlphaS:input_alpha_s 0.118
read Merging/FactorCMWScheme.in
##################################################
# Create the Herwig analysis
##################################################
create ThePEG::RivetAnalysis /Herwig/Analysis/RivetAnalysis RivetAnalysis.so
insert /Herwig/Generators/EventGenerator:AnalysisHandlers 0 /Herwig/Analysis/RivetAnalysis
set /Herwig/Analysis/RivetAnalysis:Debug No
set /Herwig/Decays/DecayHandler:MaxLifeTime 10*mm
-##################################################
-## Save the generator
-##################################################
-do /Herwig/Merging/MergingFactory:ProductionMode
+
## Select the process
cd /Herwig/Merging/
set Merger:MergingScale 15.*GeV
${process}
read ${parameterFile}
+##################################################
+## Save the generator
+##################################################
+do /Herwig/Merging/MergingFactory:ProductionMode
+
cd /Herwig/Generators
set EventGenerator:MaxErrors 1000000
saverun ${runname} EventGenerator
diff --git a/Tests/Rivet/Templates/LEP-Merging.in b/Tests/Rivet/Templates/LEP-Merging.in
--- a/Tests/Rivet/Templates/LEP-Merging.in
+++ b/Tests/Rivet/Templates/LEP-Merging.in
@@ -1,62 +1,64 @@
# -*- ThePEG-repository -*-
##################################################
## Collider type
##################################################
read snippets/DipoleMerging.in
read snippets/EECollider.in
read snippets/MonacoSampler.in
##################################################
## Process selection
##################################################
## Model assumptions
read Matchbox/StandardModelLike.in
read Matchbox/DiagonalCKM.in
## Set the order of the couplings
cd /Herwig/Merging/
set MergingFactory:OrderInAlphaS 0
set MergingFactory:OrderInAlphaEW 2
##################################################
## Matrix element library selection
##################################################
read Matchbox/MadGraph-OpenLoops.in
##################################################
## Scale choice
## See the documentation for more options
##################################################
cd /Herwig/Merging/
set MergingFactory:ScaleChoice /Herwig/MatrixElements/Matchbox/Scales/SHatScale
##################################################
## PDF and AlphaS choice
##################################################
set /Herwig/Couplings/NLOAlphaS:input_alpha_s 0.118
read Merging/FactorCMWScheme.in
##################################################
# Switch off ISR
##################################################
set /Herwig/Particles/e-:PDF /Herwig/Partons/NoPDF
set /Herwig/Particles/e+:PDF /Herwig/Partons/NoPDF
##################################################
# Create the Herwig analysis
##################################################
create ThePEG::RivetAnalysis /Herwig/Analysis/RivetAnalysis RivetAnalysis.so
insert /Herwig/Generators/EventGenerator:AnalysisHandlers 0 /Herwig/Analysis/RivetAnalysis
##################################################
## Do not apply profile scales for LEP as hard
## scale coincides with kinematic limit
##################################################
set /Herwig/DipoleShower/DipoleShowerHandler:HardScaleProfile NULL
-##################################################
-## Save the generator
-##################################################
-do /Herwig/Merging/MergingFactory:ProductionMode
+
## Select the process
cd /Herwig/Merging/
set Merger:MergingScale 5.*GeV
${process}
read ${parameterFile}
+##################################################
+## Save the generator
+##################################################
+do /Herwig/Merging/MergingFactory:ProductionMode
+
cd /Herwig/Generators
set EventGenerator:MaxErrors 1000000
saverun ${runname} EventGenerator
diff --git a/Tests/python/make_input_files.py b/Tests/python/make_input_files.py
--- a/Tests/python/make_input_files.py
+++ b/Tests/python/make_input_files.py
@@ -1,1686 +1,1836 @@
#! /usr/bin/env python
import logging,sys,os
from string import strip, Template
import sys
if sys.version_info[:3] < (2,4,0):
print "rivet scripts require Python version >= 2.4.0... exiting"
sys.exit(1)
if __name__ == "__main__":
import logging
from optparse import OptionParser, OptionGroup
parser = OptionParser(usage="%prog name [...]")
+simulation=""
+
+
+numberOfAddedProcesses=0
def addProcess(thefactory,theProcess,Oas,Oew,scale,mergedlegs,NLOprocesses):
+ global numberOfAddedProcesses
+ global simulation
+ numberOfAddedProcesses+=1
res ="set "+thefactory+":OrderInAlphaS "+Oas+"\n"
res+="set "+thefactory+":OrderInAlphaEW "+Oew+"\n"
res+="do "+thefactory+":Process "+theProcess+" "
if ( mergedlegs != 0 ):
+ if simulation!="Merging":
+ print "simulation is not Merging, trying to add merged legs."
+ sys.exit(1)
res+="["
for j in range(mergedlegs):
res+=" j "
res+="]"
res+="\n"
if (NLOprocesses!=0):
+ if simulation!="Merging":
+ print "simulation is not Merging, trying to add NLOProcesses."
+ sys.exit(1)
res+="set MergingFactory:NLOProcesses %s \n" % NLOprocesses
if ( scale != "" ):
res+="set "+thefactory+":ScaleChoice /Herwig/MatrixElements/Matchbox/Scales/"+scale+"\n"
return res
def addLeptonPairCut(minmass,maxmass):
return "set /Herwig/Cuts/LeptonPairMassCut:MinMass "+minmass+"*GeV\nset /Herwig/Cuts/LeptonPairMassCut:MaxMass "+maxmass+"*GeV\n"
didaddfirstjet=False
def addFirstJet(ptcut):
global didaddfirstjet
if(didaddfirstjet):
logging.error("Can only add jetcut once.")
sys.exit(1)
res="set /Herwig/Cuts/Cuts:JetFinder /Herwig/Cuts/JetFinder\n"
res+="insert /Herwig/Cuts/Cuts:MultiCuts 0 /Herwig/Cuts/JetCuts\n"
res+="insert /Herwig/Cuts/JetCuts:JetRegions 0 /Herwig/Cuts/FirstJet\n"
if(ptcut!=""):
res+="set /Herwig/Cuts/FirstJet:PtMin "+ptcut+".*GeV\n"
didaddfirstjet=True
return res
didaddsecondjet=False
def addSecondJet(ptcut):
global didaddsecondjet
if(didaddsecondjet):
logging.error("Can only add second jetcut once.")
sys.exit(1)
res="insert /Herwig/Cuts/JetCuts:JetRegions 0 /Herwig/Cuts/SecondJet\n"
res+="set /Herwig/Cuts/SecondJet:PtMin "+ptcut+".*GeV\n"
didaddsecondjet=True
return res
didaddjetpair=False
def addJetPairCut(minmass):
global didaddjetpair
if(didaddjetpair):
logging.error("Can only add second jetcut once.")
sys.exit(1)
res="create ThePEG::JetPairRegion /Herwig/Cuts/JetPairMass JetCuts.so\n"
res+="set /Herwig/Cuts/JetPairMass:FirstRegion /Herwig/Cuts/FirstJet\n"
res+="set /Herwig/Cuts/JetPairMass:SecondRegion /Herwig/Cuts/SecondJet\n"
res+="insert /Herwig/Cuts/JetCuts:JetPairRegions 0 /Herwig/Cuts/JetPairMass\n"
res+="set /Herwig/Cuts/JetPairMass:MassMin "+minmass+".*GeV\n"
didaddjetpair=True
return res
+addedBRReweighter=False
def addBRReweighter():
+ global addedBRReweighter
+ if(addedBRReweighter):
+ logging.error("Can only add BRReweighter once.")
+ sys.exit(1)
res="create Herwig::BranchingRatioReweighter /Herwig/Generators/BRReweighter\n"
res+="insert /Herwig/Generators/EventGenerator:EventHandler:PostHadronizationHandlers 0 /Herwig/Generators/BRReweighter\n"
+ addedBRReweighter=True
return res
def setHardProcessWidthToZero(list1):
res=""
for i in list1:
res+="set /Herwig/Particles/"+i+":HardProcessWidth 0.\n"
return res
+selecteddecaymode=False
+def selectDecayMode(particle,decaymodes):
+ global selecteddecaymode
+ res="do /Herwig/Particles/"+particle+":SelectDecayModes"
+ for decay in decaymodes:
+ res+=" /Herwig/Particles/"+particle+"/"+decay
+ res+="\n"
+ selecteddecaymode=True
+ return res
+
(opts, args) = parser.parse_args()
## Check args
if len(args) != 1:
logging.error("Must specify at least input file")
sys.exit(1)
name=args[0]
# settings for four flavour scheme
fourFlavour="read Matchbox/FourFlavourScheme.in\ndo /Herwig/MatrixElements/Matchbox/Factory:StartParticleGroup bjet\ninsert /Herwig/MatrixElements/Matchbox/Factory:ParticleGroup 0 /Herwig/Particles/b\ninsert /Herwig/MatrixElements/Matchbox/Factory:ParticleGroup 0 /Herwig/Particles/bbar\ninsert /Herwig/MatrixElements/Matchbox/Factory:ParticleGroup 0 /Herwig/Particles/c\ninsert /Herwig/MatrixElements/Matchbox/Factory:ParticleGroup 0 /Herwig/Particles/cbar\ninsert /Herwig/MatrixElements/Matchbox/Factory:ParticleGroup 0 /Herwig/Particles/s\ninsert /Herwig/MatrixElements/Matchbox/Factory:ParticleGroup 0 /Herwig/Particles/sbar\ninsert /Herwig/MatrixElements/Matchbox/Factory:ParticleGroup 0 /Herwig/Particles/d\ninsert /Herwig/MatrixElements/Matchbox/Factory:ParticleGroup 0 /Herwig/Particles/dbar\ninsert /Herwig/MatrixElements/Matchbox/Factory:ParticleGroup 0 /Herwig/Particles/u\ninsert /Herwig/MatrixElements/Matchbox/Factory:ParticleGroup 0 /Herwig/Particles/ubar\ninsert /Herwig/MatrixElements/Matchbox/Factory:ParticleGroup 0 /Herwig/Particles/g\ndo /Herwig/MatrixElements/Matchbox/Factory:EndParticleGroup\nset /Herwig/Cuts/MatchboxJetMatcher:Group bjet\n"
collider=""
# select the template to load
# collider
parameters = {}
if(name.find("BFactory")==0) :
collider="BFactory"
elif(name.find("LEP")==0) :
collider="LEP"
elif(name.find("DIS")==0) :
collider="DIS"
elif(name.find("TVT")==0) :
collider="TVT"
elif(name.find("LHC-GammaGamma")==0) :
collider="LHC-GammaGamma"
elif(name.find("LHC")==0) :
collider="LHC"
elif(name.find("ISR")==0) :
collider="ISR"
elif(name.find("SppS")==0) :
collider="SppS"
elif(name.find("Star")==0) :
collider="Star"
-simulation=""
+
thefactory="Factory"
istart = 1
print name
if(name.find("Matchbox-Powheg")>0) :
istart = 3
simulation="Matchbox"
parameters["shower"] = "read Matchbox/Powheg-DefaultShower.in\n"
elif(name.find("Matchbox")>0) :
istart = 2
simulation="Matchbox"
parameters["shower"] = "read Matchbox/MCatNLO-DefaultShower.in\n"
elif(name.find("Dipole")>0) :
istart = 2
simulation="Matchbox"
parameters["shower"] = "read Matchbox/MCatNLO-DipoleShower.in\n"
elif(name.find("Powheg")>0) :
istart = 2
simulation="Powheg"
elif(name.find("Merging")>0) :
istart = 2
simulation="Merging"
thefactory="MergingFactory"
if(simulation=="Matchbox") :
parameters["bscheme"] = "read Matchbox/FiveFlavourScheme.in\n"
if(parameters["shower"].find("Dipole")>=0) :
parameters["bscheme"] += "read Matchbox/FiveFlavourNoBMassScheme.in\n"
if(collider.find("DIS")<0) :
parameters["nlo"] = "read Matchbox/MadGraph-OpenLoops.in\n"
if(collider=="") :
logging.error("Can\'t find collider")
sys.exit(1)
# find the template
if(simulation=="") :
if(collider.find("LHC-GammaGamma") >=0) :
istart += 1
templateName="Hadron-Gamma.in"
elif(collider.find("TVT")>=0 or collider.find("LHC") >=0 or
collider.find("ISR")>=0 or collider.find("SppS")>=0 or
collider.find("Star")>=0) :
templateName="Hadron.in"
elif(collider.find("BFactory")<0) :
templateName= "%s.in" % (collider)
else :
templateName= "LEP.in"
else :
if(collider.find("TVT")>=0 or collider.find("LHC") >=0 or
collider.find("ISR")>=0 or collider.find("SppS")>=0 or
collider.find("Star")>=0) :
templateName= "Hadron-%s.in" % (simulation)
elif(collider.find("BFactory")<0) :
templateName= "%s-%s.in" % (collider,simulation)
else :
templateName= "LEP-%s.in" % (simulation)
with open(os.path.join("Rivet/Templates",templateName), 'r') as f:
templateText = f.read()
template = Template( templateText )
# work out the name of the parameter file
nameSplit=name.split("-")
parameterName=nameSplit[istart]
for i in range(istart+1,len(nameSplit)) :
parameterName += "-%s" % nameSplit[i]
# work out the process and parameters
process=""
# Bfactory
if(collider=="BFactory") :
if(simulation=="") :
if(parameterName=="10.58-res") :
process += "\ncreate Herwig::MEee2VectorMeson /Herwig/MatrixElements/MEUpsilon HwMELepton.so\nset /Herwig/MatrixElements/MEUpsilon:VectorMeson /Herwig/Particles/Upsilon(4S)\nset /Herwig/MatrixElements/MEUpsilon:Coupling 0.0004151809\ninsert /Herwig/MatrixElements/SubProcess:MatrixElements 0 /Herwig/MatrixElements/MEUpsilon"
elif(parameterName=="10.58") :
process += "\ncreate Herwig::MEee2VectorMeson /Herwig/MatrixElements/MEUpsilon HwMELepton.so\nset /Herwig/MatrixElements/MEUpsilon:VectorMeson /Herwig/Particles/Upsilon(4S)\nset /Herwig/MatrixElements/MEUpsilon:Coupling 0.0004151809\ninsert /Herwig/MatrixElements/SubProcess:MatrixElements 0 /Herwig/MatrixElements/MEUpsilon\n"
process += "set /Herwig/MatrixElements/MEee2gZ2qq:MaximumFlavour 4\n"
else :
process+="insert /Herwig/MatrixElements/SubProcess:MatrixElements 0 /Herwig/MatrixElements/MEee2gZ2qq\n"
process+= "set /Herwig/MatrixElements/MEee2gZ2qq:MaximumFlavour 4\n"
elif(simulation=="Powheg") :
process = "set /Herwig/MatrixElements/PowhegMEee2gZ2qq:MaximumFlavour 4\n"
elif(simulation=="Matchbox" ) :
process =addProcess(thefactory,"e- e+ -> u ubar","0","2","",0,0)
process+=addProcess(thefactory,"e- e+ -> d dbar","0","2","",0,0)
process+=addProcess(thefactory,"e- e+ -> c cbar","0","2","",0,0)
process+=addProcess(thefactory,"e- e+ -> s sbar","0","2","",0,0)
elif(simulation=="Merging" ) :
logging.warning("BFactory not explicitly tested for %s " % simulation)
sys.exit(0)
# DIS
elif(collider=="DIS") :
if(simulation=="") :
if(parameterName.find("NoME")>=0) :
process = "set /Herwig/Shower/ShowerHandler:HardEmission None"
parameterName=parameterName.replace("NoME-","")
else :
process = ""
elif(simulation=="Powheg") :
process = ""
elif(simulation=="Matchbox" ) :
if(parameterName.find("e-")>=0) :
process=addProcess(thefactory,"e- p -> e- j","0","2","",0,0)
else :
process=addProcess(thefactory,"e+ p -> e+ j","0","2","",0,0)
elif(simulation=="Merging" ) :
if(parameterName.find("e-")>=0) :
process=addProcess(thefactory,"e- p -> e- j","0","2","",2,2)
else :
process=addProcess(thefactory,"e+ p -> e+ j","0","2","",2,2)
# LEP
elif(collider=="LEP") :
if(simulation=="") :
if(parameterName.find("gg")>=0) :
process ="create Herwig::MEee2Higgs2SM /Herwig/MatrixElements/MEee2Higgs2SM\n"
process+="insert /Herwig/MatrixElements/SubProcess:MatrixElements[0] /Herwig/MatrixElements/MEee2Higgs2SM\n"
process+="set /Herwig/MatrixElements/MEee2Higgs2SM:Allowed Gluon\n"
else :
process="insert /Herwig/MatrixElements/SubProcess:MatrixElements 0 /Herwig/MatrixElements/MEee2gZ2qq\n"
if(parameterName=="10") :
process+="set /Herwig/MatrixElements/MEee2gZ2qq:MaximumFlavour 4"
elif(simulation=="Powheg") :
process=""
if(parameterName=="10") :
process="set /Herwig/MatrixElements/PowhegMEee2gZ2qq:MaximumFlavour 4"
elif(simulation=="Matchbox" ) :
if(parameterName=="10") :
process =addProcess(thefactory,"e- e+ -> u ubar","0","2","",0,0)
process+=addProcess(thefactory,"e- e+ -> d dbar","0","2","",0,0)
process+=addProcess(thefactory,"e- e+ -> c cbar","0","2","",0,0)
process+=addProcess(thefactory,"e- e+ -> s sbar","0","2","",0,0)
else :
process=addProcess(thefactory,"e- e+ -> j j","0","2","",0,0)
elif(simulation=="Merging" ) :
if(parameterName=="10") :
- process=addProcess(thefactory,"e- e+ -> u ubar","0","2","",1,1)
- process+=addProcess(thefactory,"e- e+ -> d dbar","0","2","",1,1)
- process+=addProcess(thefactory,"e- e+ -> c cbar","0","2","",1,1)
- process+=addProcess(thefactory,"e- e+ -> s sbar","0","2","",1,1)
+ process=addProcess(thefactory,"e- e+ -> j j","0","2","",2,2)
+ process+="read Matchbox/FourFlavourScheme.in"
else :
- process=addProcess(thefactory,"e- e+ -> j j","0","2","",1,1)
+ process=addProcess(thefactory,"e- e+ -> j j","0","2","",2,2)
# TVT
elif(collider=="TVT") :
process="set /Herwig/Generators/EventGenerator:EventHandler:BeamB /Herwig/Particles/pbar-\n"
if(parameterName.find("Run-II")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 1960.0\n"
elif(parameterName.find("Run-I")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 1800.0\n"
elif(parameterName.find("900")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 900.0\n"
elif(parameterName.find("630")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 630.0\n"
elif(parameterName.find("300")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 300.0\n"
if(simulation=="") :
if(parameterName.find("PromptPhoton")>=0) :
process+="insert SubProcess:MatrixElements[0] MEGammaJet\n"
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 15.\n"
elif(parameterName.find("DiPhoton-GammaGamma")>=0) :
process+="insert SubProcess:MatrixElements[0] MEGammaGamma\n"
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 5.\n"
parameterName=parameterName.replace("-GammaGamma","")
elif(parameterName.find("DiPhoton-GammaJet")>=0) :
process+="insert SubProcess:MatrixElements[0] MEGammaJet\n"
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 5.\n"
parameterName=parameterName.replace("-GammaJet","")
elif(parameterName.find("UE")>=0) :
process += "insert SubProcess:MatrixElements[0] MEMinBias\n"
process += "set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
process += "set /Herwig/Generators/EventGenerator:EventHandler:Cuts /Herwig/Cuts/MinBiasCuts\n"
process += "create Herwig::MPIXSecReweighter /Herwig/Generators/MPIXSecReweighter\n"
process += "insert /Herwig/Generators/EventGenerator:EventHandler:PostSubProcessHandlers 0 /Herwig/Generators/MPIXSecReweighter\n"
process += "set /Herwig/Decays/DecayHandler:LifeTimeOption 0\n"
process += "set /Herwig/Decays/DecayHandler:MaxLifeTime 10*mm\n"
elif(parameterName.find("Jets")>=0) :
process+="insert SubProcess:MatrixElements[0] MEQCD2to2\n"
process+="set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
if(parameterName.find("Run-II-Jets-10")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 30.\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 500.*GeV\n"
elif(parameterName.find("Run-II-Jets-11")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 30.\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 900.*GeV\n"
elif(parameterName.find("Run-I-Jets-1")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 20.\n"
elif(parameterName.find("Run-I-Jets-2")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 40.\n"
elif(parameterName.find("Run-I-Jets-3")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 65.\n"
elif(parameterName.find("Run-I-Jets-4")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 90.\n"
elif(parameterName.find("Run-I-Jets-5")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 160.\n"
elif(parameterName.find("Run-I-Jets-6")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 30.\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 100.*GeV\n"
elif(parameterName.find("Run-I-Jets-7")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 30.\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 400.*GeV\n"
elif(parameterName.find("Run-I-Jets-8")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 30.\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 700.*GeV\n"
elif(parameterName.find("Run-II-Jets-0")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 15.\n"
elif(parameterName.find("Run-II-Jets-1")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 25.\n"
elif(parameterName.find("Run-II-Jets-2")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 40.\n"
elif(parameterName.find("Run-II-Jets-3")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 60.\n"
elif(parameterName.find("Run-II-Jets-4")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 85.\n"
elif(parameterName.find("Run-II-Jets-5")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 110.\n"
elif(parameterName.find("Run-II-Jets-6")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 160.\n"
elif(parameterName.find("Run-II-Jets-7")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 250.\n"
elif(parameterName.find("Run-II-Jets-8")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 30.\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 100.*GeV\n"
elif(parameterName.find("Run-II-Jets-9")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 30.\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 300.*GeV\n"
elif(parameterName.find("900-Jets-1")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 10.\n"
elif(parameterName.find("300-Jets-1")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 6.\n"
elif(parameterName.find("630-Jets-1")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 20.\n"
elif(parameterName.find("630-Jets-2")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 40.\n"
elif(parameterName.find("630-Jets-3")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 75.\n"
elif(parameterName.find("900-Jets-1")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 10.\n"
elif(parameterName.find("Run-I-WZ")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2W2ff\nset MEqq2W2ff:Process Electron\ninsert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Electron\n"
elif(parameterName.find("Run-I-W")>=0 or parameterName.find("Run-II-W")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2W2ff\nset MEqq2W2ff:Process Electron\n"
elif(parameterName.find("Run-I-Z")>=0 or parameterName.find("Run-II-Z-e")>=0) :
process +="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Electron\n"
elif(parameterName.find("Run-II-Z-LowMass-mu")>=0) :
process +="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Muon\n"
process+=addLeptonPairCut("25","70")
elif(parameterName.find("Run-II-Z-HighMass-mu")>=0) :
process +="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Muon\n"
process+=addLeptonPairCut("150","600")
elif(parameterName.find("Run-II-Z-mu")>=0) :
process +="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Muon\n"
elif(simulation=="Powheg") :
if(parameterName.find("Run-I-WZ")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2W2ff\nset PowhegMEqq2W2ff:Process Electron\ninsert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Electron\n"
elif(parameterName.find("Run-I-W")>=0 or parameterName.find("Run-II-W")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2W2ff\nset PowhegMEqq2W2ff:Process Electron\n"
elif(parameterName.find("Run-I-Z")>=0 or parameterName.find("Run-II-Z-e")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Electron\n"
elif(parameterName.find("Run-II-Z-LowMass-mu")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Muon\n"
process+=addLeptonPairCut("25","70")
elif(parameterName.find("Run-II-Z-HighMass-mu")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Muon\n"
process+=addLeptonPairCut("150","600")
elif(parameterName.find("Run-II-Z-mu")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Muon\n"
elif(parameterName.find("DiPhoton-GammaGamma")>=0) :
process+="insert SubProcess:MatrixElements[0] MEGammaGammaPowheg\n"
process+="set MEGammaGammaPowheg:Process GammaGamma\n"
process+="insert SubProcess:MatrixElements[0] MEGammaGamma\n"
process+="set MEGammaGamma:Process gg\n"
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 5.\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 5.\n"
parameterName=parameterName.replace("-GammaGamma","")
elif(parameterName.find("DiPhoton-GammaJet")>=0) :
process+="insert SubProcess:MatrixElements[0] MEGammaGammaPowheg\n"
process+="set MEGammaGammaPowheg:Process VJet\n"
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 5.\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 5.\n"
parameterName=parameterName.replace("-GammaJet","")
elif(simulation=="Matchbox" or simulation=="Merging" ) :
if(parameterName.find("Jets")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p -> j j","2","0","MaxJetPtScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p -> j j","2","0","MaxJetPtScale",1,0)
process+="set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
if(parameterName.find("Run-II-Jets-10")>=0) :
process+=addFirstJet("30")
process+=addSecondJet("25")
process+=addJetPairCut("500")
elif(parameterName.find("Run-II-Jets-11")>=0) :
process+=addFirstJet("30")
process+=addSecondJet("25")
process+=addJetPairCut("900")
elif(parameterName.find("Run-II-Jets-12")>=0) :
process+=addFirstJet("30")
process+=addSecondJet("25")
process+=addJetPairCut("300")
elif(parameterName.find("Run-I-Jets-1")>=0) :
process+=addFirstJet("20")
elif(parameterName.find("Run-I-Jets-2")>=0) :
process+=addFirstJet("40")
elif(parameterName.find("Run-I-Jets-3")>=0) :
process+=addFirstJet("65")
elif(parameterName.find("Run-I-Jets-4")>=0) :
process+=addFirstJet("90")
elif(parameterName.find("Run-I-Jets-5")>=0) :
process+=addFirstJet("160")
elif(parameterName.find("Run-I-Jets-6")>=0) :
process+=addFirstJet("30")
process+=addSecondJet("25")
process+=addJetPairCut("100")
elif(parameterName.find("Run-I-Jets-7")>=0) :
process+=addFirstJet("30")
process+=addSecondJet("25")
process+=addJetPairCut("400")
elif(parameterName.find("Run-I-Jets-8")>=0) :
process+=addFirstJet("30")
process+=addSecondJet("25")
process+=addJetPairCut("700")
elif(parameterName.find("Run-II-Jets-0")>=0) :
process+=addFirstJet("15")
elif(parameterName.find("Run-II-Jets-1")>=0) :
process+=addFirstJet("25")
elif(parameterName.find("Run-II-Jets-2")>=0) :
process+=addFirstJet("40")
elif(parameterName.find("Run-II-Jets-3")>=0) :
process+=addFirstJet("60")
elif(parameterName.find("Run-II-Jets-4")>=0) :
process+=addFirstJet("85")
elif(parameterName.find("Run-II-Jets-5")>=0) :
process+=addFirstJet("110")
elif(parameterName.find("Run-II-Jets-6")>=0) :
process+=addFirstJet("160")
elif(parameterName.find("Run-II-Jets-7")>=0) :
process+=addFirstJet("250")
elif(parameterName.find("Run-II-Jets-8")>=0) :
process+=addFirstJet("30")
process+=addSecondJet("25")
process+=addJetPairCut("100")
elif(parameterName.find("Run-II-Jets-9")>=0) :
process+=addFirstJet("30")
process+=addSecondJet("25")
process+=addJetPairCut("300")
elif(parameterName.find("900-Jets-1")>=0) :
process+=addFirstJet("10")
elif(parameterName.find("300-Jets-1")>=0) :
process+=addFirstJet("6")
elif(parameterName.find("630-Jets-1")>=0) :
process+=addFirstJet("20")
elif(parameterName.find("630-Jets-2")>=0) :
process+=addFirstJet("40")
elif(parameterName.find("630-Jets-3")>=0) :
process+=addFirstJet("75")
elif(parameterName.find("900-Jets-1")>=0) :
process+=addFirstJet("10")
else :
logging.error("Exit 00007")
sys.exit(1)
elif(parameterName.find("Run-I-WZ")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p pbar e+ e-","0","2","LeptonPairMassScale",0,0)
process+=addProcess(thefactory,"p pbar e+ nu","0","2","LeptonPairMassScale",0,0)
process+=addProcess(thefactory,"p pbar e- nu","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
- process+=addProcess(thefactory,"p pbar e+ e-","0","2","LeptonPairMassScale",2,2)
- process+=addProcess(thefactory,"p pbar e+ nu","0","2","LeptonPairMassScale",2,2)
- process+=addProcess(thefactory,"p pbar e- nu","0","2","LeptonPairMassScale",2,2)
+ process+="do "+thefactory+":StartParticleGroup epm\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/e+\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/e-\n"
+ process+="do "+thefactory+":EndParticleGroup\n"
+ process+="do "+thefactory+":StartParticleGroup epmnu\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/e+\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/e-\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/nu_e\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/nu_ebar\n"
+ process+="do "+thefactory+":EndParticleGroup\n"
+ process+=addProcess(thefactory,"p pbar epm epmnu","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("60","120")
elif(parameterName.find("Run-I-W")>=0 or parameterName.find("Run-II-W")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p pbar e+ nu","0","2","LeptonPairMassScale",0,0)
process+=addProcess(thefactory,"p pbar e- nu","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
- process+=addProcess(thefactory,"p pbar e+ nu","0","2","LeptonPairMassScale",2,2)
- process+=addProcess(thefactory,"p pbar e- nu","0","2","LeptonPairMassScale",2,2)
+ process+="do "+thefactory+":StartParticleGroup epm\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/e+\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/e-\n"
+ process+="do "+thefactory+":EndParticleGroup\n"
+ process+=addProcess(thefactory,"p pbar epm nu","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("60","120")
elif(parameterName.find("Run-I-Z")>=0 or parameterName.find("Run-II-Z-e")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p pbar e+ e-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p pbar e+ e-","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("60","120")
elif(parameterName.find("Run-II-Z-LowMass-mu")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p pbar mu+ mu-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p pbar mu+ mu-","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("25","70")
elif(parameterName.find("Run-II-Z-HighMass-mu")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p pbar mu+ mu-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p pbar mu+ mu-","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("150","600")
elif(parameterName.find("Run-II-Z-mu")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p pbar mu+ mu-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p pbar mu+ mu-","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("60","120")
# Star
elif(collider=="Star" ) :
process = "set /Herwig/Decays/DecayHandler:LifeTimeOption 0\n"
process+= "set /Herwig/Decays/DecayHandler:MaxLifeTime 10*mm\n"
process+= "set /Herwig/Generators/EventGenerator:EventHandler:BeamB /Herwig/Particles/p+\n"
process+= "set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 200.0\n"
process+= "set /Herwig/Cuts/Cuts:X2Min 0.01\n"
if(simulation=="") :
if(parameterName.find("UE")>=0) :
process += "insert SubProcess:MatrixElements[0] MEMinBias\n"
process += "set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
process += "set /Herwig/Generators/EventGenerator:EventHandler:Cuts /Herwig/Cuts/MinBiasCuts\n"
process += "create Herwig::MPIXSecReweighter /Herwig/Generators/MPIXSecReweighter\n"
process += "insert /Herwig/Generators/EventGenerator:EventHandler:PostSubProcessHandlers 0 /Herwig/Generators/MPIXSecReweighter\n"
else :
process+="insert SubProcess:MatrixElements[0] MEQCD2to2\n"
process+="set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
if(parameterName.find("Jets-1")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 2.\n"
elif(parameterName.find("Jets-2")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 5.\n"
elif(parameterName.find("Jets-3")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 20.\n"
elif(parameterName.find("Jets-4")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 25.\n"
else :
logging.error("Star not supported for %s " % simulation)
sys.exit(1)
# ISR and SppS
elif(collider=="ISR" or collider =="SppS" ) :
process="set /Herwig/Decays/DecayHandler:LifeTimeOption 0\n"
process+="set /Herwig/Decays/DecayHandler:MaxLifeTime 10*mm\n"
if(collider=="SppS") :
process ="set /Herwig/Generators/EventGenerator:EventHandler:BeamB /Herwig/Particles/pbar-\n"
if(parameterName.find("30")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 30.4\n"
elif(parameterName.find("44")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 44.4\n"
elif(parameterName.find("53")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 53.0\n"
elif(parameterName.find("62")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 62.2\n"
elif(parameterName.find("63")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 63.0\n"
elif(parameterName.find("200")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 200.0\n"
elif(parameterName.find("500")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 500.0\n"
elif(parameterName.find("546")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 546.0\n"
elif(parameterName.find("900")>=0) :
process+="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 900.0\n"
if(simulation=="") :
process += "insert SubProcess:MatrixElements[0] MEMinBias\n"
process += "set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
process += "set /Herwig/Generators/EventGenerator:EventHandler:Cuts /Herwig/Cuts/MinBiasCuts\n"
process += "create Herwig::MPIXSecReweighter /Herwig/Generators/MPIXSecReweighter\n"
process += "insert /Herwig/Generators/EventGenerator:EventHandler:PostSubProcessHandlers 0 /Herwig/Generators/MPIXSecReweighter\n"
else :
logging.error(" SppS and ISR not supported for %s " % simulation)
sys.exit(1)
# LHC
elif(collider=="LHC") :
if(parameterName.find("7-")==0) :
process="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 7000.0\n"
elif(parameterName.find("8-")==0) :
process="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 8000.0\n"
elif(parameterName.find("13-")==0) :
process="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 13000.0\n"
elif(parameterName.find("900")==0) :
process="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 900.0\n"
elif(parameterName.find("2360")==0) :
process="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 2360.0\n"
elif(parameterName.find("2760")==0) :
process="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 2760.0\n"
else :
process="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 7000.0\n"
if(simulation=="") :
if(parameterName.find("8-VBF")>=0) :
process+="insert SubProcess:MatrixElements[0] MEPP2HiggsVBF\n"
elif(parameterName.find("VBF")>=0) :
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->tau-,tau+;\n"
+ process+=selectDecayMode("h0",["h0->tau-,tau+;"])
+ process+=addBRReweighter()
process+="set /Herwig/Particles/tau-:Stable Stable\n"
process+="insert SubProcess:MatrixElements[0] MEPP2HiggsVBF\n"
elif(parameterName.find("ggHJet")>=0) :
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->tau-,tau+;\n"
+ process+=selectDecayMode("h0",["h0->tau-,tau+;"])
+ process+=addBRReweighter()
process+="set /Herwig/Particles/tau-:Stable Stable\n"
process+="insert SubProcess:MatrixElements[0] MEHiggsJet\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 20.\n"
elif(parameterName.find("8-ggH")>=0) :
process+="insert SubProcess:MatrixElements[0] MEHiggs\n"
process+="insert SubProcess:MatrixElements[0] MEHiggsJet\n"
process+="set MEHiggsJet:Process qqbar\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 0.0*GeV\n"
elif(parameterName.find("ggH")>=0) :
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->tau-,tau+;\n"
+ process+=selectDecayMode("h0",["h0->tau-,tau+;"])
+ process+=addBRReweighter()
process+="set /Herwig/Particles/tau-:Stable Stable\n"
process+="insert SubProcess:MatrixElements[0] MEHiggs\n"
process+="insert SubProcess:MatrixElements[0] MEHiggsJet\n"
process+="set MEHiggsJet:Process qqbar\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 0.0*GeV\n"
elif(parameterName.find("PromptPhoton")>=0) :
process+="insert SubProcess:MatrixElements[0] MEGammaJet\n"
if(parameterName.find("PromptPhoton-1")>=0) :
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 5.\n"
elif(parameterName.find("PromptPhoton-2")>=0) :
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 25.\n"
elif(parameterName.find("PromptPhoton-3")>=0) :
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 80.\n"
elif(parameterName.find("PromptPhoton-4")>=0) :
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 150.\n"
elif(parameterName.find("DiPhoton-GammaGamma")>=0) :
process+="insert SubProcess:MatrixElements[0] MEGammaGamma\n"
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 5.\n"
parameterName=parameterName.replace("-GammaGamma","")
elif(parameterName.find("DiPhoton-GammaJet")>=0) :
process+="insert SubProcess:MatrixElements[0] MEGammaJet\n"
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 5.\n"
parameterName=parameterName.replace("-GammaJet","")
elif(parameterName.find("8-WH")>=0) :
process+="insert SubProcess:MatrixElements[0] MEPP2WH\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 0.0*GeV\n"
elif(parameterName.find("8-ZH")>=0) :
process+="insert SubProcess:MatrixElements[0] MEPP2ZH\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 0.0*GeV\n"
elif(parameterName.find("WH")>=0) :
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->b,bbar;\n"
- process+="do /Herwig/Particles/W+:SelectDecayModes W+->nu_e,e+; W+->nu_mu,mu+;\n"
+ process+=selectDecayMode("h0",["h0->b,bbar;"])
+ process+=selectDecayMode("W+",["W+->nu_e,e+;",
+ "W+->nu_mu,mu+;"])
+ process+=addBRReweighter()
process+="insert SubProcess:MatrixElements[0] MEPP2WH\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 0.0*GeV\n"
elif(parameterName.find("ZH")>=0) :
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->b,bbar;\n"
- process+="do /Herwig/Particles/Z0:SelectDecayModes Z0->e-,e+; Z0->mu-,mu+;\n"
+ process+=selectDecayMode("h0",["h0->b,bbar;"])
+ process+=selectDecayMode("Z0",["Z0->e-,e+;",
+ "Z0->mu-,mu+;"])
+ process+=addBRReweighter()
process+="insert SubProcess:MatrixElements[0] MEPP2ZH\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 0.0*GeV\n"
elif(parameterName.find("UE")>=0) :
process += "insert SubProcess:MatrixElements[0] MEMinBias\n"
process += "set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
process += "set /Herwig/Generators/EventGenerator:EventHandler:Cuts /Herwig/Cuts/MinBiasCuts\n"
process += "create Herwig::MPIXSecReweighter /Herwig/Generators/MPIXSecReweighter\n"
process += "insert /Herwig/Generators/EventGenerator:EventHandler:PostSubProcessHandlers 0 /Herwig/Generators/MPIXSecReweighter\n"
if(parameterName.find("Long")>=0) :
process += "set /Herwig/Decays/DecayHandler:MaxLifeTime 100*mm\n"
elif(parameterName.find("7-DiJets")>=0 or parameterName.find("8-DiJets")>=0) :
process+="insert SubProcess:MatrixElements[0] MEQCD2to2\n"
process+="set MEQCD2to2:MaximumFlavour 5\n"
process+="set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
if(parameterName.find("-A")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 45.\n"
process+="set /Herwig/Cuts/JetKtCut:MinEta -3.\n"
process+="set /Herwig/Cuts/JetKtCut:MaxEta 3.\n"
elif(parameterName.find("-B")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 20.\n"
process+="set /Herwig/Cuts/JetKtCut:MinEta -2.7\n"
process+="set /Herwig/Cuts/JetKtCut:MaxEta 2.7\n"
elif(parameterName.find("-C")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 20.\n"
process+="set /Herwig/Cuts/JetKtCut:MinEta -4.8\n"
process+="set /Herwig/Cuts/JetKtCut:MaxEta 4.8\n"
if(parameterName.find("DiJets-1")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 90.*GeV\n"
elif(parameterName.find("DiJets-2")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 200.*GeV\n"
elif(parameterName.find("DiJets-3")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 450.*GeV\n"
elif(parameterName.find("DiJets-4")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 750.*GeV\n"
elif(parameterName.find("DiJets-5")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 950.*GeV\n"
elif(parameterName.find("DiJets-6")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 1550.*GeV\n"
elif(parameterName.find("DiJets-7")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 2150.*GeV\n"
elif(parameterName.find("DiJets-8")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 2750.*GeV\n"
elif(parameterName.find("7-Jets")>=0 or parameterName.find("8-Jets")>=0 or \
parameterName.find("13-Jets")>=0) :
process+="insert SubProcess:MatrixElements[0] MEQCD2to2\n"
process+="set MEQCD2to2:MaximumFlavour 5\n"
process+="set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
if(parameterName.find("Jets-10")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 1800.\n"
elif(parameterName.find("Jets-0")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 5.\n"
elif(parameterName.find("Jets-1")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 10.\n"
elif(parameterName.find("Jets-2")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 20.\n"
elif(parameterName.find("Jets-3")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 40.\n"
elif(parameterName.find("Jets-4")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 70.\n"
elif(parameterName.find("Jets-5")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 150.\n"
elif(parameterName.find("Jets-6")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 200.\n"
elif(parameterName.find("Jets-7")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 300.\n"
elif(parameterName.find("Jets-8")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 500.\n"
elif(parameterName.find("Jets-9")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 800.\n"
elif(parameterName.find("7-Charm")>=0 or \
parameterName.find("7-Bottom")>=0) :
if(parameterName.find("7-Bottom")>=0) :
process+="cp MEHeavyQuark MEBottom\n"
process+="set MEBottom:QuarkType Bottom\n"
process+="insert SubProcess:MatrixElements[0] MEBottom\n"
else :
process+="cp MEHeavyQuark MECharm\n"
process+="set MECharm:QuarkType Charm\n"
process+="insert SubProcess:MatrixElements[0] MECharm\n"
process+="set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
if(parameterName.find("-0")>=0) :
if(parameterName.find("7-Bottom")>=0) :
process+="set MEBottom:Process Pair\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 0.\n"
elif(parameterName.find("-1")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 5.\n"
elif(parameterName.find("-2")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 20.\n"
elif(parameterName.find("-3")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 50.\n"
elif(parameterName.find("-4")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 80.\n"
elif(parameterName.find("-5")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 110.\n"
elif(parameterName.find("-6")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 30.\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 90.*GeV\n"
elif(parameterName.find("-7")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 30.\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 340.*GeV\n"
elif(parameterName.find("-8")>=0) :
process+="set /Herwig/Cuts/JetKtCut:MinKT 30.\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 500.*GeV\n"
elif(parameterName.find("Top-L")>=0) :
process+="set MEHeavyQuark:QuarkType Top\n"
process+="insert SubProcess:MatrixElements[0] MEHeavyQuark\n"
- process+="do /Herwig/Particles/t:SelectDecayModes t->nu_e,e+,b; t->nu_mu,mu+,b;\n"
+ process+=selectDecayMode("t",["t->nu_e,e+,b;",
+ "t->nu_mu,mu+,b;"])
process+=addBRReweighter()
elif(parameterName.find("Top-SL")>=0) :
process+="set MEHeavyQuark:QuarkType Top\n"
process+="insert SubProcess:MatrixElements[0] MEHeavyQuark\n"
process+="set /Herwig/Particles/t:Synchronized Not_synchronized\n"
process+="set /Herwig/Particles/tbar:Synchronized Not_synchronized\n"
- process+="do /Herwig/Particles/t:SelectDecayModes t->nu_e,e+,b; t->nu_mu,mu+,b;\n"
- process+="do /Herwig/Particles/tbar:SelectDecayModes tbar->b,bbar,cbar; tbar->bbar,cbar,d; tbar->bbar,cbar,s; tbar->bbar,s,ubar; tbar->bbar,ubar,d;\n"
+ process+=selectDecayMode("t",["t->nu_e,e+,b;","t->nu_mu,mu+,b;"])
+ process+=selectDecayMode("tbar",["tbar->b,bbar,cbar;",
+ "tbar->bbar,cbar,d;",
+ "tbar->bbar,cbar,s;",
+ "tbar->bbar,s,ubar;",
+ "tbar->bbar,ubar,d;"])
process+=addBRReweighter()
elif(parameterName.find("Top-All")>=0) :
process+="set MEHeavyQuark:QuarkType Top\n"
process+="insert SubProcess:MatrixElements[0] MEHeavyQuark\n"
elif(parameterName.find("WZ")>=0) :
process+="insert SubProcess:MatrixElements[0] MEPP2VV\nset MEPP2VV:Process WZ\n"
- process+="do /Herwig/Particles/W+:SelectDecayModes /Herwig/Particles/W+/W+->nu_e,e+; /Herwig/Particles/W+/W+->nu_mu,mu+;\n"
- process+="do /Herwig/Particles/W-:SelectDecayModes /Herwig/Particles/W-/W-->nu_ebar,e-; /Herwig/Particles/W-/W-->nu_mubar,mu-;\n"
- process+="do /Herwig/Particles/Z0:SelectDecayModes /Herwig/Particles/Z0/Z0->e-,e+; /Herwig/Particles/Z0/Z0->mu-,mu+;\n"
+ process+=selectDecayMode("W+",["W+->nu_e,e+;",
+ "W+->nu_mu,mu+;"])
+ process+=selectDecayMode("W-",["W-->nu_ebar,e-;",
+ "W-->nu_mubar,mu-;"])
+ process+=selectDecayMode("W-",["Z0->e-,e+;",
+ "Z0->mu-,mu+;"])
process+=addBRReweighter()
elif(parameterName.find("WW-emu")>=0) :
process+="insert SubProcess:MatrixElements[0] MEPP2VV\nset MEPP2VV:Process WW\n"
process+="set /Herwig/Particles/W+:Synchronized 0\n"
process+="set /Herwig/Particles/W-:Synchronized 0\n"
- process+="do /Herwig/Particles/W+:SelectDecayModes /Herwig/Particles/W+/W+->nu_e,e+;\n"
- process+="do /Herwig/Particles/W-:SelectDecayModes /Herwig/Particles/W-/W-->nu_mubar,mu-;\n"
+ process+=selectDecayMode("W+",["W+->nu_e,e+;"])
+ process+=selectDecayMode("W-",["W-->nu_mubar,mu-;"])
process+=addBRReweighter()
elif(parameterName.find("WW-ll")>=0) :
process+="insert SubProcess:MatrixElements[0] MEPP2VV\nset MEPP2VV:Process WW\n"
- process+="do /Herwig/Particles/W+:SelectDecayModes /Herwig/Particles/W+/W+->nu_e,e+; /Herwig/Particles/W+/W+->nu_mu,mu+; /Herwig/Particles/W+/W+->nu_tau,tau+;\n"
+ process+=selectDecayMode("W+",["W+->nu_e,e+;","W+->nu_mu,mu+;","W+->nu_tau,tau+;"])
process+=addBRReweighter()
elif(parameterName.find("ZZ-ll")>=0) :
process+="insert SubProcess:MatrixElements[0] MEPP2VV\nset MEPP2VV:Process ZZ\n"
- process+="do /Herwig/Particles/Z0:SelectDecayModes /Herwig/Particles/Z0/Z0->e-,e+; /Herwig/Particles/Z0/Z0->mu-,mu+; /Herwig/Particles/Z0/Z0->tau-,tau+;\n"
+ process+=selectDecayMode("Z0",["Z0->e-,e+;",
+ "Z0->mu-,mu+;",
+ "Z0->tau-,tau+;"])
process+=addBRReweighter()
-
+
elif(parameterName.find("ZZ-lv")>=0) :
process+="insert SubProcess:MatrixElements[0] MEPP2VV\nset MEPP2VV:Process ZZ\n"
- process+="do /Herwig/Particles/Z0:SelectDecayModes /Herwig/Particles/Z0/Z0->e-,e+; /Herwig/Particles/Z0/Z0->mu-,mu+; /Herwig/Particles/Z0/Z0->tau-,tau+; /Herwig/Particles/Z0/Z0->nu_e,nu_ebar; /Herwig/Particles/Z0/Z0->nu_mu,nu_mubar; /Herwig/Particles/Z0/Z0->nu_tau,nu_taubar;\n"
+ process+=selectDecayMode("Z0",["Z0->e-,e+;",
+ "Z0->mu-,mu+;",
+ "Z0->tau-,tau+;",
+ "Z0->nu_e,nu_ebar;",
+ "Z0->nu_mu,nu_mubar;",
+ "Z0->nu_tau,nu_taubar;"])
process+=addBRReweighter()
elif(parameterName.find("W-Z-e")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Electron\n"
process+="insert SubProcess:MatrixElements[0] MEqq2W2ff\nset MEqq2W2ff:Process Electron\n"
+
elif(parameterName.find("W-Z-mu")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Muon\n"
process+="insert SubProcess:MatrixElements[0] MEqq2W2ff\nset MEqq2W2ff:Process Muon\n"
elif(parameterName.find("W-e")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2W2ff\nset MEqq2W2ff:Process Electron\n"
elif(parameterName.find("W-mu")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2W2ff\nset MEqq2W2ff:Process Muon\n"
elif(parameterName.find("Z-e")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Electron\n"
elif(parameterName.find("Z-mu")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Muon\n"
elif(parameterName.find("Z-LowMass-e")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Electron\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 20.*GeV\nset /Herwig/Cuts/MassCut:MinM 20.*GeV\nset /Herwig/Cuts/MassCut:MaxM 70.*GeV\n"
elif(parameterName.find("Z-MedMass-e")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Electron\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 40.*GeV\nset /Herwig/Cuts/MassCut:MinM 40.*GeV\nset /Herwig/Cuts/MassCut:MaxM 130.*GeV\n"
elif(parameterName.find("Z-LowMass-mu")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Muon\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 10.*GeV\nset /Herwig/Cuts/MassCut:MinM 10.*GeV\nset /Herwig/Cuts/MassCut:MaxM 70.*GeV\n"
elif(parameterName.find("Z-Mass1")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 10.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MinM 10.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MaxM 35.*GeV\n"
if(parameterName.find("-e")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Electron\n"
else :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Muon\n"
elif(parameterName.find("Z-Mass2")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 25.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MinM 25.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MaxM 70.*GeV\n"
if(parameterName.find("-e")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Electron\n"
else :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Muon\n"
elif(parameterName.find("Z-Mass3")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 60.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MinM 60.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MaxM 120.*GeV\n"
if(parameterName.find("-e")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Electron\n"
else :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Muon\n"
elif(parameterName.find("Z-Mass4")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 110.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MinM 110.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MaxM 8000.*GeV\n"
if(parameterName.find("-e")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Electron\n"
else :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Muon\n"
elif(parameterName.find("W-Jet")>=0) :
process+="insert SubProcess:MatrixElements[0] MEWJet\nset MEWJet:WDecay Electron\n"
if(parameterName.find("W-Jet-1-e")>=0) :
process+="set /Herwig/Cuts/WBosonKtCut:MinKT 100.0*GeV\n"
parameterName=parameterName.replace("W-Jet-1-e","W-Jet-e")
elif(parameterName.find("W-Jet-2-e")>=0) :
process+="set /Herwig/Cuts/WBosonKtCut:MinKT 190.0*GeV\n"
parameterName=parameterName.replace("W-Jet-2-e","W-Jet-e")
elif(parameterName.find("W-Jet-3-e")>=0) :
process+="set /Herwig/Cuts/WBosonKtCut:MinKT 270.0*GeV\n"
parameterName=parameterName.replace("W-Jet-3-e","W-Jet-e")
elif(parameterName.find("Z-Jet")>=0) :
if(parameterName.find("-e")>=0) :
process+="insert SubProcess:MatrixElements[0] MEZJet\nset MEZJet:ZDecay Electron\n"
if(parameterName.find("Z-Jet-0-e")>=0) :
process+="set /Herwig/Cuts/ZBosonKtCut:MinKT 35.0*GeV\n"
parameterName=parameterName.replace("Z-Jet-0-e","Z-Jet-e")
elif(parameterName.find("Z-Jet-1-e")>=0) :
process+="set /Herwig/Cuts/ZBosonKtCut:MinKT 100.0*GeV\n"
parameterName=parameterName.replace("Z-Jet-1-e","Z-Jet-e")
elif(parameterName.find("Z-Jet-2-e")>=0) :
process+="set /Herwig/Cuts/ZBosonKtCut:MinKT 190.0*GeV\n"
parameterName=parameterName.replace("Z-Jet-2-e","Z-Jet-e")
elif(parameterName.find("Z-Jet-3-e")>=0) :
process+="set /Herwig/Cuts/ZBosonKtCut:MinKT 270.0*GeV\n"
parameterName=parameterName.replace("Z-Jet-3-e","Z-Jet-e")
else :
process+="insert SubProcess:MatrixElements[0] MEZJet\nset MEZJet:ZDecay Muon\n"
process+="set /Herwig/Cuts/ZBosonKtCut:MinKT 35.0*GeV\n"
parameterName=parameterName.replace("Z-Jet-0-mu","Z-Jet-mu")
elif(parameterName.find("WGamma")>=0) :
process+="insert SubProcess:MatrixElements[0] MEPP2VGamma\nset MEPP2VGamma:Process 1\nset MEPP2VGamma:MassOption 1\n"
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 10.\n"
- process+=addBRReweighter()
+
if(parameterName.find("-e")>=0) :
- process+="do /Herwig/Particles/W+:SelectDecayModes W+->nu_e,e+;\n"
+ process+=selectDecayMode("W+",["W+->nu_e,e+;"])
+ process+=addBRReweighter()
else :
- process+="do /Herwig/Particles/W+:SelectDecayModes W+->nu_mu,mu+;\n"
+ process+=selectDecayMode("W+",["W+->nu_mu,mu+;"])
+ process+=addBRReweighter()
elif(parameterName.find("ZGamma")>=0) :
process+="insert SubProcess:MatrixElements[0] MEPP2VGamma\nset MEPP2VGamma:Process 2\n"
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 10.\n"
if(parameterName.find("-e")>=0) :
- process+="do /Herwig/Particles/Z0:SelectDecayModes Z0->e-,e+;\n"
+ process+=selectDecayMode("Z0",["Z0->e-,e+;"])
+ process+=addBRReweighter()
else :
- process+="do /Herwig/Particles/Z0:SelectDecayModes Z0->mu-,mu+;\n"
+ process+=selectDecayMode("Z0",["Z0->mu-,mu+;"])
+ process+=addBRReweighter()
else :
logging.error(" Process %s not supported for internal matrix elements" % name)
sys.exit(1)
elif(simulation=="Powheg") :
if(parameterName.find("8-VBF")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEPP2HiggsVBF\n"
elif(parameterName.find("VBF")>=0) :
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->tau-,tau+;\n"
+ process+=selectDecayMode("h0",["h0->tau-,tau+;"])
+ process+=addBRReweighter()
process+="set /Herwig/Particles/tau-:Stable Stable\n"
process+="insert SubProcess:MatrixElements[0] PowhegMEPP2HiggsVBF\n"
elif(parameterName.find("ggHJet")>=0) :
logging.error(" Process %s not supported for POWHEG matrix elements" % name)
sys.exit(1)
elif(parameterName.find("8-ggH")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEHiggs\n"
elif(parameterName.find("ggH")>=0) :
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->tau-,tau+;\n"
+ process+=selectDecayMode("h0",["h0->tau-,tau+;"])
+ process+=addBRReweighter()
process+="set /Herwig/Particles/tau-:Stable Stable\n"
process+="insert SubProcess:MatrixElements[0] PowhegMEHiggs\n"
elif(parameterName.find("8-WH")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEPP2WH\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 0.0*GeV\n"
elif(parameterName.find("8-ZH")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEPP2ZH\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 0.0*GeV\n"
elif(parameterName.find("WH")>=0) :
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->b,bbar;\n"
- process+="do /Herwig/Particles/W+:SelectDecayModes W+->nu_e,e+; W+->nu_mu,mu+;\n"
+ process+=selectDecayMode("h0",["h0->b,bbar;"])
+ process+=selectDecayMode("W+",["W+->nu_e,e+;",
+ "W+->nu_mu,mu+;"])
+ process+=addBRReweighter()
process+="insert SubProcess:MatrixElements[0] PowhegMEPP2WH\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 0.0*GeV\n"
elif(parameterName.find("ZH")>=0) :
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->b,bbar;\n"
- process+="do /Herwig/Particles/Z0:SelectDecayModes Z0->e-,e+; Z0->mu-,mu+;\n"
+ process+=selectDecayMode("h0",["h0->b,bbar;"])
+ process+=selectDecayMode("Z0",["Z0->e-,e+;",
+ "Z0->mu-,mu+;"])
+ process+=addBRReweighter()
process+="insert SubProcess:MatrixElements[0] PowhegMEPP2ZH\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 0.0*GeV\n"
elif(parameterName.find("UE")>=0) :
logging.error(" Process %s not supported for powheg matrix elements" % name)
sys.exit(1)
elif(parameterName.find("WZ")>=0) :
process+="create Herwig::HwDecayHandler /Herwig/NewPhysics/DecayHandler\n"
process+="set /Herwig/NewPhysics/DecayHandler:NewStep No\n"
process+="set /Herwig/Shower/ShowerHandler:SplitHardProcess No\n";
process+="set /Herwig/Decays/ZDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/ZPowhegDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/WDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/WPowhegDecayer:PhotonGenerator NULL\n";
process+="insert /Herwig/NewPhysics/DecayHandler:Excluded 0 /Herwig/Particles/tau-\n"
process+="insert /Herwig/NewPhysics/DecayHandler:Excluded 1 /Herwig/Particles/tau+\n"
process+="insert /Herwig/Generators/EventGenerator:EventHandler:PreCascadeHandlers 0 /Herwig/NewPhysics/DecayHandler\n"
process+="insert SubProcess:MatrixElements[0] PowhegMEPP2VV\nset PowhegMEPP2VV:Process WZ\n"
- process+="do /Herwig/Particles/W+:SelectDecayModes /Herwig/Particles/W+/W+->nu_e,e+; /Herwig/Particles/W+/W+->nu_mu,mu+;\n"
- process+="do /Herwig/Particles/W-:SelectDecayModes /Herwig/Particles/W-/W-->nu_ebar,e-; /Herwig/Particles/W-/W-->nu_mubar,mu-;\n"
- process+="do /Herwig/Particles/Z0:SelectDecayModes /Herwig/Particles/Z0/Z0->e-,e+; /Herwig/Particles/Z0/Z0->mu-,mu+;\n"
+ process+=selectDecayMode("W+",["W+->nu_e,e+;",
+ "W+->nu_mu,mu+;"])
+ process+=selectDecayMode("W-",["W-->nu_ebar,e-;",
+ "W-->nu_mubar,mu-;"])
+ process+=selectDecayMode("Z0",["Z0->e-,e+;",
+ "Z0->mu-,mu+;"])
process+=addBRReweighter()
elif(parameterName.find("WW-emu")>=0) :
process+="create Herwig::HwDecayHandler /Herwig/NewPhysics/DecayHandler\n"
process+="set /Herwig/NewPhysics/DecayHandler:NewStep No\n"
process+="set /Herwig/Shower/ShowerHandler:SplitHardProcess No\n";
process+="set /Herwig/Decays/ZDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/ZPowhegDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/WDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/WPowhegDecayer:PhotonGenerator NULL\n";
process+="insert /Herwig/NewPhysics/DecayHandler:Excluded 0 /Herwig/Particles/tau-\n"
process+="insert /Herwig/NewPhysics/DecayHandler:Excluded 1 /Herwig/Particles/tau+\n"
process+="insert /Herwig/Generators/EventGenerator:EventHandler:PreCascadeHandlers 0 /Herwig/NewPhysics/DecayHandler\n"
process+="insert SubProcess:MatrixElements[0] PowhegMEPP2VV\nset PowhegMEPP2VV:Process WW\n"
process+="set /Herwig/Particles/W+:Synchronized 0\n"
process+="set /Herwig/Particles/W-:Synchronized 0\n"
- process+="do /Herwig/Particles/W+:SelectDecayModes /Herwig/Particles/W+/W+->nu_e,e+;\n"
- process+="do /Herwig/Particles/W-:SelectDecayModes /Herwig/Particles/W-/W-->nu_mubar,mu-;\n"
+ process+=selectDecayMode("W+",["W+->nu_e,e+;"])
+ process+=selectDecayMode("W-",["W-->nu_mubar,mu-;"])
process+=addBRReweighter()
elif(parameterName.find("WW-ll")>=0) :
process+="create Herwig::HwDecayHandler /Herwig/NewPhysics/DecayHandler\n"
process+="set /Herwig/NewPhysics/DecayHandler:NewStep No\n"
process+="set /Herwig/Shower/ShowerHandler:SplitHardProcess No\n";
process+="set /Herwig/Decays/ZDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/ZPowhegDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/WDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/WPowhegDecayer:PhotonGenerator NULL\n";
process+="insert /Herwig/NewPhysics/DecayHandler:Excluded 0 /Herwig/Particles/tau-\n"
process+="insert /Herwig/NewPhysics/DecayHandler:Excluded 1 /Herwig/Particles/tau+\n"
process+="insert /Herwig/Generators/EventGenerator:EventHandler:PreCascadeHandlers 0 /Herwig/NewPhysics/DecayHandler\n"
process+="insert SubProcess:MatrixElements[0] PowhegMEPP2VV\nset PowhegMEPP2VV:Process WW\n"
- process+="do /Herwig/Particles/W+:SelectDecayModes /Herwig/Particles/W+/W+->nu_e,e+; /Herwig/Particles/W+/W+->nu_mu,mu+; /Herwig/Particles/W+/W+->nu_tau,tau+;\n"
+ process+=selectDecayMode("W+",["W+->nu_e,e+;",
+ "W+->nu_mu,mu+;",
+ "W+->nu_tau,tau+;"])
process+=addBRReweighter()
elif(parameterName.find("ZZ-ll")>=0) :
process+="create Herwig::HwDecayHandler /Herwig/NewPhysics/DecayHandler\n"
process+="set /Herwig/NewPhysics/DecayHandler:NewStep No\n"
process+="set /Herwig/Shower/ShowerHandler:SplitHardProcess No\n";
process+="set /Herwig/Decays/ZDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/ZPowhegDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/WDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/WPowhegDecayer:PhotonGenerator NULL\n";
process+="insert /Herwig/NewPhysics/DecayHandler:Excluded 0 /Herwig/Particles/tau-\n"
process+="insert /Herwig/NewPhysics/DecayHandler:Excluded 1 /Herwig/Particles/tau+\n"
process+="insert /Herwig/Generators/EventGenerator:EventHandler:PreCascadeHandlers 0 /Herwig/NewPhysics/DecayHandler\n"
process+="insert SubProcess:MatrixElements[0] PowhegMEPP2VV\nset PowhegMEPP2VV:Process ZZ\n"
- process+="do /Herwig/Particles/Z0:SelectDecayModes /Herwig/Particles/Z0/Z0->e-,e+; /Herwig/Particles/Z0/Z0->mu-,mu+; /Herwig/Particles/Z0/Z0->tau-,tau+;\n"
+ process+=selectDecayMode("Z0",["Z0->e-,e+;",
+ "Z0->mu-,mu+;",
+ "Z0->tau-,tau+;"])
process+=addBRReweighter()
elif(parameterName.find("ZZ-lv")>=0) :
process+="create Herwig::HwDecayHandler /Herwig/NewPhysics/DecayHandler\n"
process+="set /Herwig/NewPhysics/DecayHandler:NewStep No\n"
process+="set /Herwig/Shower/ShowerHandler:SplitHardProcess No\n";
process+="set /Herwig/Decays/ZDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/ZPowhegDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/WDecayer:PhotonGenerator NULL\n";
process+="set /Herwig/Decays/WPowhegDecayer:PhotonGenerator NULL\n";
process+="insert /Herwig/NewPhysics/DecayHandler:Excluded 0 /Herwig/Particles/tau-\n"
process+="insert /Herwig/NewPhysics/DecayHandler:Excluded 1 /Herwig/Particles/tau+\n"
process+="insert /Herwig/Generators/EventGenerator:EventHandler:PreCascadeHandlers 0 /Herwig/NewPhysics/DecayHandler\n"
process+="insert SubProcess:MatrixElements[0] PowhegMEPP2VV\nset PowhegMEPP2VV:Process ZZ\n"
- process+="do /Herwig/Particles/Z0:SelectDecayModes /Herwig/Particles/Z0/Z0->e-,e+; /Herwig/Particles/Z0/Z0->mu-,mu+; /Herwig/Particles/Z0/Z0->tau-,tau+; /Herwig/Particles/Z0/Z0->nu_e,nu_ebar; /Herwig/Particles/Z0/Z0->nu_mu,nu_mubar; /Herwig/Particles/Z0/Z0->nu_tau,nu_taubar;\n"
+ process+=selectDecayMode("Z0",["Z0->e-,e+;",
+ "Z0->mu-,mu+;",
+ "Z0->tau-,tau+;",
+ "Z0->nu_e,nu_ebar;",
+ "Z0->nu_mu,nu_mubar;",
+ "Z0->nu_tau,nu_taubar;"])
process+=addBRReweighter()
elif(parameterName.find("W-Z-e")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Electron\n"
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2W2ff\nset PowhegMEqq2W2ff:Process Electron\n"
elif(parameterName.find("W-Z-mu")>=0) :
process+="insert SubProcess:MatrixElements[0] MEqq2gZ2ff\nset MEqq2gZ2ff:Process Muon\n"
process+="insert SubProcess:MatrixElements[0] MEqq2W2ff\nset MEqq2W2ff:Process Muon\n"
elif(parameterName.find("W-e")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2W2ff\nset PowhegMEqq2W2ff:Process Electron\n"
elif(parameterName.find("W-mu")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2W2ff\nset PowhegMEqq2W2ff:Process Muon\n"
elif(parameterName.find("Z-e")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Electron\n"
elif(parameterName.find("Z-mu")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Muon\n"
elif(parameterName.find("Z-LowMass-e")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Electron\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 20.*GeV\nset /Herwig/Cuts/MassCut:MinM 20.*GeV\nset /Herwig/Cuts/MassCut:MaxM 70.*GeV\n"
elif(parameterName.find("Z-MedMass-e")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Electron\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 40.*GeV\nset /Herwig/Cuts/MassCut:MinM 40.*GeV\nset /Herwig/Cuts/MassCut:MaxM 130.*GeV\n"
elif(parameterName.find("Z-LowMass-mu")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Muon\n"
process+="set /Herwig/Cuts/Cuts:MHatMin 10.*GeV\nset /Herwig/Cuts/MassCut:MinM 10.*GeV\nset /Herwig/Cuts/MassCut:MaxM 70.*GeV\n"
elif(parameterName.find("Z-Mass1")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 10.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MinM 10.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MaxM 35.*GeV\n"
if(parameterName.find("-e")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Electron\n"
else :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Muon\n"
elif(parameterName.find("Z-Mass2")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 25.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MinM 25.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MaxM 70.*GeV\n"
if(parameterName.find("-e")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Electron\n"
else :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Muon\n"
elif(parameterName.find("Z-Mass3")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 60.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MinM 60.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MaxM 120.*GeV\n"
if(parameterName.find("-e")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Electron\n"
else :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Muon\n"
elif(parameterName.find("Z-Mass4")>=0) :
process+="set /Herwig/Cuts/Cuts:MHatMin 110.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MinM 110.*GeV\n"
process+="set /Herwig/Cuts/MassCut:MaxM 8000.*GeV\n"
if(parameterName.find("-e")>=0) :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Electron\n"
else :
process+="insert SubProcess:MatrixElements[0] PowhegMEqq2gZ2ff\nset PowhegMEqq2gZ2ff:Process Muon\n"
elif(parameterName.find("DiPhoton-GammaGamma")>=0) :
process+="insert SubProcess:MatrixElements[0] MEGammaGammaPowheg\n"
process+="set MEGammaGammaPowheg:Process GammaGamma\n"
process+="insert SubProcess:MatrixElements[0] MEGammaGamma\n"
process+="set MEGammaGamma:Process gg\n"
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 5.\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 5.\n"
parameterName=parameterName.replace("-GammaGamma","")
elif(parameterName.find("DiPhoton-GammaJet")>=0) :
process+="insert SubProcess:MatrixElements[0] MEGammaGammaPowheg\n"
process+="set MEGammaGammaPowheg:Process VJet\n"
process+="set /Herwig/Cuts/PhotonKtCut:MinKT 5.\n"
process+="set /Herwig/Cuts/JetKtCut:MinKT 5.\n"
parameterName=parameterName.replace("-GammaJet","")
else :
logging.error(" Process %s not supported for internal POWHEG matrix elements" % name)
sys.exit(1)
elif( simulation=="Matchbox" or simulation=="Merging" ) :
if(parameterName.find("8-VBF")>=0) :
parameters["nlo"] = "read Matchbox/VBFNLO.in\n"
if(simulation=="Merging"):
process+="cd /Herwig/Merging/"
process+="insert "+thefactory+":DiagramGenerator:RestrictLines 0 /Herwig/Particles/Z0\n"
process+="insert "+thefactory+":DiagramGenerator:RestrictLines 0 /Herwig/Particles/W+\n"
process+="insert "+thefactory+":DiagramGenerator:RestrictLines 0 /Herwig/Particles/W-\n"
process+="insert "+thefactory+":DiagramGenerator:RestrictLines 0 /Herwig/Particles/gamma\n"
process+="do "+thefactory+":DiagramGenerator:TimeLikeRange 0 0\n"
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p h0 j j","0","3","FixedScale",0,0)
elif(simulation=="Merging"):
- process+=addProcess(thefactory,"p p h0 j j","0","3","FixedScale",1,0)
+ process+=addProcess(thefactory,"p p h0 j j","0","3","FixedScale",1,1)
process+=setHardProcessWidthToZero(["h0"])
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 125.7\n"
if(parameterName.find("GammaGamma")>=0) :
+ process+=selectDecayMode("h0",["h0->gamma,gamma;"])
process+=addBRReweighter()
elif(parameterName.find("VBF")>=0) :
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->tau-,tau+;\n"
+ process+=selectDecayMode("h0",["h0->tau-,tau+;"])
+ process+=addBRReweighter()
process+="set /Herwig/Particles/tau-:Stable Stable\n"
parameters["nlo"] = "read Matchbox/VBFNLO.in\n"
if(simulation=="Merging"):
process+="cd /Herwig/Merging/"
process+="insert "+thefactory+":DiagramGenerator:RestrictLines 0 /Herwig/Particles/Z0\n"
process+="insert "+thefactory+":DiagramGenerator:RestrictLines 0 /Herwig/Particles/W+\n"
process+="insert "+thefactory+":DiagramGenerator:RestrictLines 0 /Herwig/Particles/W-\n"
process+="insert "+thefactory+":DiagramGenerator:RestrictLines 0 /Herwig/Particles/gamma\n"
process+="do "+thefactory+":DiagramGenerator:TimeLikeRange 0 0\n"
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p h0 j j","0","3","FixedScale",0,0)
elif(simulation=="Merging"):
- process+=addProcess(thefactory,"p p h0 j j","0","3","FixedScale",1,0)
+ process+=addProcess(thefactory,"p p h0 j j","0","3","FixedScale",1,1)
process+=setHardProcessWidthToZero(["h0"])
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 125.7\n"
elif(parameterName.find("ggHJet")>=0) :
if(simulation=="Merging"):
logging.warning("ggHJet not explicitly tested for %s " % simulation)
sys.exit(0)
parameters["nlo"] = "read Matchbox/MadGraph-GoSam.in\nread Matchbox/HiggsEffective.in\n"
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->tau-,tau+;\n"
+ process+=selectDecayMode("h0",["h0->tau-,tau+;"])
+ process+=addBRReweighter()
process+="set /Herwig/Particles/tau-:Stable Stable\n"
process+=setHardProcessWidthToZero(["h0"])
process+=addProcess(thefactory,"p p h0 j","3","1","FixedScale",0,0)
process+=addFirstJet("20")
process+="set "+thefactory+":ScaleChoice /Herwig/MatrixElements/Matchbox/Scales/FixedScale\n"
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 125.7\n"
elif(parameterName.find("8-ggH")>=0) :
parameters["nlo"] = "read Matchbox/MadGraph-GoSam.in\nread Matchbox/HiggsEffective.in\n"
if(simulation=="Merging"):
- process+= "read Matchbox/MadGraph-OpenLoops.in\nread Matchbox/HiggsEffective.in\n"
- process+="cd /Herwig/Merging/"
+ process+= "cd /Herwig/MatrixElements/Matchbox/Amplitudes\nset OpenLoops:HiggsEff On\nset MadGraph:Model heft\n"
+ process+="cd /Herwig/Merging/\n"
process+=setHardProcessWidthToZero(["h0"])
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p h0","2","1","FixedScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p h0","2","1","FixedScale",2,2)
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 125.7\n"
if(parameterName.find("GammaGamma")>=0) :
+ process+=selectDecayMode("h0",["h0->gamma,gamma;"])
process+=addBRReweighter()
elif(parameterName.find("ggH")>=0) :
parameters["nlo"] = "read Matchbox/MadGraph-GoSam.in\nread Matchbox/HiggsEffective.in\n"
if(simulation=="Merging"):
- process+= "read Matchbox/MadGraph-OpenLoops.in\nread Matchbox/HiggsEffective.in\n"
- process+="cd /Herwig/Merging/"
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->tau-,tau+;\n"
+ process+= "cd /Herwig/MatrixElements/Matchbox/Amplitudes\nset OpenLoops:HiggsEff On\nset MadGraph:Model heft\n"
+ process+="cd /Herwig/Merging/\n"
+ process+=selectDecayMode("h0",["h0->tau-,tau+;"])
+ process+=addBRReweighter()
process+="set /Herwig/Particles/tau-:Stable Stable\n"
process+=setHardProcessWidthToZero(["h0"])
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p h0","2","1","FixedScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p h0","2","1","FixedScale",2,2)
process+="set "+thefactory+":ScaleChoice /Herwig/MatrixElements/Matchbox/Scales/FixedScale\n"
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 125.7\n"
elif(parameterName.find("8-WH")>=0) :
if(simulation=="Merging"):
logging.warning("8-WH not explicitly tested for %s " % simulation)
sys.exit(0)
process+=setHardProcessWidthToZero(["h0","W+","W-"])
process+=addProcess(thefactory,"p p W+ h0","0","2","FixedScale",0,0)
process+=addProcess(thefactory,"p p W- h0","2","1","FixedScale",0,0)
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 125.7\n"
if(parameterName.find("GammaGamma")>=0) :
+ process+=selectDecayMode("h0",["h0->gamma,gamma;"])
process+=addBRReweighter()
elif(parameterName.find("8-ZH")>=0) :
if(simulation=="Merging"):
logging.warning("8-ZH not explicitly tested for %s " % simulation)
sys.exit(0)
process+=setHardProcessWidthToZero(["h0","Z0"])
process+=addProcess(thefactory,"p p Z0 h0","0","2","FixedScale",0,0)
- process+=addProcess(thefactory,"p p Z0 h0","0","2","FixedScale",0,0)
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 125.7\n"
if(parameterName.find("GammaGamma")>=0) :
+ process+=selectDecayMode("h0",["h0->gamma,gamma;"])
process+=addBRReweighter()
elif(parameterName.find("WH")>=0) :
if(simulation=="Merging"):
logging.warning("WH not explicitly tested for %s " % simulation)
sys.exit(0)
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->b,bbar;\n"
+ process+=selectDecayMode("h0",["h0->b,bbar;"])
+ process+=addBRReweighter()
process+=setHardProcessWidthToZero(["h0"])
process+=addProcess(thefactory,"p p e+ nu h0","0","3","LeptonPairMassScale",0,0)
process+=addProcess(thefactory,"p p e- nu h0","0","3","LeptonPairMassScale",0,0)
process+=addProcess(thefactory,"p p mu+ nu h0","0","3","LeptonPairMassScale",0,0)
process+=addProcess(thefactory,"p p mu- nu h0","0","3","LeptonPairMassScale",0,0)
process+=addLeptonPairCut("60","120")
elif(parameterName.find("ZH")>=0) :
if(simulation=="Merging"):
logging.warning("ZH not explicitly tested for %s " % simulation)
sys.exit(0)
- process+="do /Herwig/Particles/h0:SelectDecayModes h0->b,bbar;\n"
+ process+=selectDecayMode("h0",["h0->b,bbar;"])
+ process+=addBRReweighter()
process+=setHardProcessWidthToZero(["h0"])
process+=addProcess(thefactory,"p p e+ e- h0","0","3","LeptonPairMassScale",0,0)
process+=addProcess(thefactory,"p p mu+ mu- h0","0","3","LeptonPairMassScale",0,0)
process+=addLeptonPairCut("60","120")
elif(parameterName.find("UE")>=0) :
logging.error(" Process %s not supported for Matchbox matrix elements" % name)
sys.exit(1)
elif(parameterName.find("7-DiJets")>=0 or parameterName.find("8-DiJets")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p j j","2","0","MaxJetPtScale",0,0)
elif(simulation=="Merging"):
- process+=addProcess(thefactory,"p p j j","2","0","MaxJetPtScale",1,0)
+ process+=addProcess(thefactory,"p p j j","2","0","MaxJetPtScale",1,1)
process+="set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
if(parameterName.find("-A")>=0) :
process+=addFirstJet("45")
process+=addSecondJet("25")
process+="set /Herwig/Cuts/FirstJet:YRange -3. 3.\n"
process+="set /Herwig/Cuts/SecondJet:YRange -3. 3.\n"
elif(parameterName.find("-B")>=0) :
process+=addFirstJet("20")
process+=addSecondJet("15")
process+="set /Herwig/Cuts/FirstJet:YRange -2.7 2.7\n"
process+="set /Herwig/Cuts/SecondJet:YRange -2.7 2.7\n"
elif(parameterName.find("-C")>=0) :
process+=addFirstJet("20")
process+=addSecondJet("15")
process+="set /Herwig/Cuts/FirstJet:YRange -4.8 4.8\n"
process+="set /Herwig/Cuts/SecondJet:YRange -4.8 4.8\n"
else :
logging.error("Exit 00001")
sys.exit(1)
if(parameterName.find("DiJets-1")>=0) :
process+=addJetPairCut("90")
elif(parameterName.find("DiJets-2")>=0) :
process+=addJetPairCut("200")
elif(parameterName.find("DiJets-3")>=0) :
process+=addJetPairCut("450")
elif(parameterName.find("DiJets-4")>=0) :
process+=addJetPairCut("750")
elif(parameterName.find("DiJets-5")>=0) :
process+=addJetPairCut("950")
elif(parameterName.find("DiJets-6")>=0) :
process+=addJetPairCut("1550")
elif(parameterName.find("DiJets-7")>=0) :
process+=addJetPairCut("2150")
elif(parameterName.find("DiJets-8")>=0) :
process+=addJetPairCut("2750")
else :
logging.error("Exit 00002")
sys.exit(1)
elif(parameterName.find("7-Jets")>=0 or parameterName.find("8-Jets")>=0 or \
parameterName.find("13-Jets")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p j j","2","0","MaxJetPtScale",0,0)
elif(simulation=="Merging"):
- process+=addProcess(thefactory,"p p j j","2","0","MaxJetPtScale",1,0)
+ process+=addProcess(thefactory,"p p j j","2","0","MaxJetPtScale",1,1)
process+="set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
if(parameterName.find("Jets-10")>=0) :
process+=addFirstJet("1800")
elif(parameterName.find("Jets-0")>=0) :
process+=addFirstJet("5")
elif(parameterName.find("Jets-1")>=0) :
process+=addFirstJet("10")
elif(parameterName.find("Jets-2")>=0) :
process+=addFirstJet("20")
elif(parameterName.find("Jets-3")>=0) :
process+=addFirstJet("40")
elif(parameterName.find("Jets-4")>=0) :
process+=addFirstJet("70")
elif(parameterName.find("Jets-5")>=0) :
process+=addFirstJet("150")
elif(parameterName.find("Jets-6")>=0) :
process+=addFirstJet("200")
elif(parameterName.find("Jets-7")>=0) :
process+=addFirstJet("300")
elif(parameterName.find("Jets-8")>=0) :
process+=addFirstJet("500")
elif(parameterName.find("Jets-9")>=0) :
process+=addFirstJet("800")
else :
logging.error("Exit 00003")
sys.exit(1)
elif(parameterName.find("7-Charm")>=0 or \
parameterName.find("7-Bottom")>=0) :
parameters["bscheme"]=fourFlavour
process+="set /Herwig/Particles/b:HardProcessMass 4.2*GeV\n"
process+="set /Herwig/Particles/bbar:HardProcessMass 4.2*GeV\n"
if(parameterName.find("7-Bottom")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p b bbar","2","0","MaxJetPtScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p b bbar","2","0","MaxJetPtScale",1,0)
else:
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p c cbar","2","0","MaxJetPtScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p c cbar","2","0","MaxJetPtScale",1,0)
process+="set /Herwig/UnderlyingEvent/MPIHandler:IdenticalToUE 0\n"
if(parameterName.find("-0")>=0) :
process+=addFirstJet("0")
elif(parameterName.find("-1")>=0) :
process+=addFirstJet("5")
elif(parameterName.find("-2")>=0) :
process+=addFirstJet("20")
elif(parameterName.find("-3")>=0) :
process+=addFirstJet("50")
elif(parameterName.find("-4")>=0) :
process+=addFirstJet("80")
elif(parameterName.find("-5")>=0) :
process+=addFirstJet("110")
elif(parameterName.find("-6")>=0) :
process+=addFirstJet("30")
process+=addSecondJet("25")
process+=addJetPairCut("90")
elif(parameterName.find("-7")>=0) :
process+=addFirstJet("30")
process+=addSecondJet("25")
process+=addJetPairCut("340")
elif(parameterName.find("-8")>=0) :
process+=addFirstJet("30")
process+=addSecondJet("25")
process+=addJetPairCut("500")
else :
logging.error("Exit 00004")
sys.exit(1)
elif(parameterName.find("Top-L")>=0) :
process+=setHardProcessWidthToZero(["t","tbar"])
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p t tbar","2","0","TopPairMTScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p t tbar","2","0","TopPairMTScale",2,2)
- process+="do /Herwig/Particles/t:SelectDecayModes t->nu_e,e+,b; t->nu_mu,mu+,b;\n"
+ process+=selectDecayMode("t",["t->nu_e,e+,b;",
+ "t->nu_mu,mu+,b;"])
process+=addBRReweighter()
elif(parameterName.find("Top-SL")>=0) :
process+=setHardProcessWidthToZero(["t","tbar"])
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p t tbar","2","0","TopPairMTScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p t tbar","2","0","TopPairMTScale",2,2)
process+="set /Herwig/Particles/t:Synchronized Not_synchronized\n"
process+="set /Herwig/Particles/tbar:Synchronized Not_synchronized\n"
- process+="do /Herwig/Particles/t:SelectDecayModes t->nu_e,e+,b; t->nu_mu,mu+,b;\n"
- process+="do /Herwig/Particles/tbar:SelectDecayModes tbar->b,bbar,cbar; tbar->bbar,cbar,d; tbar->bbar,cbar,s; tbar->bbar,s,ubar; tbar->bbar,ubar,d;\n"
+ process+=selectDecayMode("t",["t->nu_e,e+,b;",
+ "t->nu_mu,mu+,b;"])
+ process+=selectDecayMode("tbar",["tbar->b,bbar,cbar;",
+ "tbar->bbar,cbar,d;",
+ "tbar->bbar,cbar,s;",
+ "tbar->bbar,s,ubar;",
+ "tbar->bbar,ubar,d;"])
process+=addBRReweighter()
elif(parameterName.find("Top-All")>=0) :
process+=setHardProcessWidthToZero(["t","tbar"])
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p t tbar","2","0","TopPairMTScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p t tbar","2","0","TopPairMTScale",2,2)
elif(parameterName.find("WZ")>=0) :
if(simulation=="Merging"):
logging.warning("WZ not explicitly tested for %s " % simulation)
sys.exit(0)
process+=setHardProcessWidthToZero(["W+","W-","Z0"])
process+=addProcess(thefactory,"p p W+ Z0","0","2","FixedScale",0,0)
process+=addProcess(thefactory,"p p W- Z0","0","2","FixedScale",0,0)
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 171.6*GeV\n\n"
- process+="do /Herwig/Particles/W+:SelectDecayModes /Herwig/Particles/W+/W+->nu_e,e+; /Herwig/Particles/W+/W+->nu_mu,mu+;\n"
- process+="do /Herwig/Particles/W-:SelectDecayModes /Herwig/Particles/W-/W-->nu_ebar,e-; /Herwig/Particles/W-/W-->nu_mubar,mu-;\n"
- process+="do /Herwig/Particles/Z0:SelectDecayModes /Herwig/Particles/Z0/Z0->e-,e+; /Herwig/Particles/Z0/Z0->mu-,mu+;\n"
+ process+=selectDecayMode("W+",["W+->nu_e,e+;",
+ "W+->nu_mu,mu+;"])
+ process+=selectDecayMode("W-",["W-->nu_ebar,e-;",
+ "W-->nu_mubar,mu-;"])
+ process+=selectDecayMode("Z0",["Z0->e-,e+;",
+ "Z0->mu-,mu+;"])
process+=addBRReweighter()
-
process+=addLeptonPairCut("60","120")
elif(parameterName.find("WW-emu")>=0) :
if(simulation=="Merging"):
logging.warning("WW-emu not explicitly tested for %s " % simulation)
sys.exit(0)
process+=setHardProcessWidthToZero(["W+","W-","Z0"])
process+=addProcess(thefactory,"p p W+ W-","0","2","FixedScale",0,0)
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 160.8*GeV\n"
process+="set /Herwig/Particles/W+:Synchronized 0\n"
process+="set /Herwig/Particles/W-:Synchronized 0\n"
- process+="do /Herwig/Particles/W+:SelectDecayModes /Herwig/Particles/W+/W+->nu_e,e+;\n"
- process+="do /Herwig/Particles/W-:SelectDecayModes /Herwig/Particles/W-/W-->nu_mubar,mu-;\n"
+ process+=selectDecayMode("W+",["W+->nu_e,e+;"])
+ process+=selectDecayMode("W-",["W-->nu_mubar,mu-;"])
process+=addBRReweighter()
process+=addLeptonPairCut("60","120")
elif(parameterName.find("WW-ll")>=0) :
if(simulation=="Merging"):
logging.warning("WW-ll not explicitly tested for %s " % simulation)
sys.exit(0)
process+=setHardProcessWidthToZero(["W+","W-","Z0"])
process+=addProcess(thefactory,"p p W+ W-","0","2","FixedScale",0,0)
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 160.8*GeV\n"
- process+="do /Herwig/Particles/W+:SelectDecayModes /Herwig/Particles/W+/W+->nu_e,e+; /Herwig/Particles/W+/W+->nu_mu,mu+; /Herwig/Particles/W+/W+->nu_tau,tau+;\n"
+ process+=selectDecayMode("W+",["W+->nu_e,e+;",
+ "W+->nu_mu,mu+;",
+ "W+->nu_tau,tau+;"])
process+=addBRReweighter()
-
process+=addLeptonPairCut("60","120")
elif(parameterName.find("ZZ-ll")>=0) :
if(simulation=="Merging"):
logging.warning("ZZ-ll not explicitly tested for %s " % simulation)
sys.exit(0)
process+=setHardProcessWidthToZero(["W+","W-","Z0"])
process+=addProcess(thefactory,"p p Z0 Z0","0","2","FixedScale",0,0)
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 182.2*GeV\n"
- process+="do /Herwig/Particles/Z0:SelectDecayModes /Herwig/Particles/Z0/Z0->e-,e+; /Herwig/Particles/Z0/Z0->mu-,mu+; /Herwig/Particles/Z0/Z0->tau-,tau+;\n"
+ process+=selectDecayMode("Z0",["Z0->e-,e+;",
+ "Z0->mu-,mu+;",
+ "Z0->tau-,tau+;"])
process+=addBRReweighter()
-
process+=addLeptonPairCut("60","120")
elif(parameterName.find("ZZ-lv")>=0) :
if(simulation=="Merging"):
logging.warning("ZZ-lv not explicitly tested for %s " % simulation)
sys.exit(0)
process+=setHardProcessWidthToZero(["W+","W-","Z0"])
process+=addProcess(thefactory,"p p Z0 Z0","0","2","FixedScale",0,0)
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 182.2*GeV\n"
- process+="do /Herwig/Particles/Z0:SelectDecayModes /Herwig/Particles/Z0/Z0->e-,e+; /Herwig/Particles/Z0/Z0->mu-,mu+; /Herwig/Particles/Z0/Z0->tau-,tau+; /Herwig/Particles/Z0/Z0->nu_e,nu_ebar; /Herwig/Particles/Z0/Z0->nu_mu,nu_mubar; /Herwig/Particles/Z0/Z0->nu_tau,nu_taubar;\n"
+ process+=selectDecayMode("Z0",["Z0->e-,e+;",
+ "Z0->mu-,mu+;",
+ "Z0->tau-,tau+;",
+ "Z0->nu_e,nu_ebar;",
+ "Z0->nu_mu,nu_mubar;",
+ "Z0->nu_tau,nu_taubar;"])
process+=addBRReweighter()
-
process+=addLeptonPairCut("60","120")
elif(parameterName.find("W-Z-e")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",0,0)
process+=addProcess(thefactory,"p p e+ nu","0","2","LeptonPairMassScale",0,0)
process+=addProcess(thefactory,"p p e- nu","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
- process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",2,2)
- process+=addProcess(thefactory,"p p e+ nu","0","2","LeptonPairMassScale",2,2)
- process+=addProcess(thefactory,"p p e- nu","0","2","LeptonPairMassScale",2,2)
+ process+="do "+thefactory+":StartParticleGroup epm\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/e+\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/e-\n"
+ process+="do "+thefactory+":EndParticleGroup\n"
+ process+="do "+thefactory+":StartParticleGroup epmnu\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/e+\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/e-\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/nu_e\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/nu_ebar\n"
+ process+="do "+thefactory+":EndParticleGroup\n"
+ process+=addProcess(thefactory,"p p epm epmnu","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("60","120")
elif(parameterName.find("W-Z-mu")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",0,0)
process+=addProcess(thefactory,"p p mu+ nu","0","2","LeptonPairMassScale",0,0)
process+=addProcess(thefactory,"p p mu- nu","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
- process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",2,2)
- process+=addProcess(thefactory,"p p mu+ nu","0","2","LeptonPairMassScale",2,2)
- process+=addProcess(thefactory,"p p mu- nu","0","2","LeptonPairMassScale",2,2)
+ process+="do "+thefactory+":StartParticleGroup mupm\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/mu+\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/mu-\n"
+ process+="do "+thefactory+":EndParticleGroup\n"
+ process+="do "+thefactory+":StartParticleGroup mupmnu\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/mu+\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/mu-\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/nu_mu\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/nu_mubar\n"
+ process+="do "+thefactory+":EndParticleGroup\n"
+ process+=addProcess(thefactory,"p p mupm mupmnu","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("60","120")
elif(parameterName.find("W-e")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p e+ nu","0","2","LeptonPairMassScale",0,0)
- process+=addProcess(thefactory,"p p e- nu","0","2","LeptonPairMassScale",2,2)
+ process+=addProcess(thefactory,"p p e- nu","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
- process+=addProcess(thefactory,"p p e+ nu","0","2","LeptonPairMassScale",0,0)
- process+=addProcess(thefactory,"p p e- nu","0","2","LeptonPairMassScale",2,2)
+ process+="do "+thefactory+":StartParticleGroup epm\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/e+\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/e-\n"
+ process+="do "+thefactory+":EndParticleGroup\n"
+ process+=addProcess(thefactory,"p p epm nu","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("60","120")
elif(parameterName.find("W-mu")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p mu+ nu","0","2","LeptonPairMassScale",0,0)
process+=addProcess(thefactory,"p p mu- nu","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
- process+=addProcess(thefactory,"p p mu+ nu","0","2","LeptonPairMassScale",2,2)
- process+=addProcess(thefactory,"p p mu- nu","0","2","LeptonPairMassScale",2,2)
+ process+="do "+thefactory+":StartParticleGroup mupm\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/mu+\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/mu-\n"
+ process+="do "+thefactory+":EndParticleGroup\n"
+ process+=addProcess(thefactory,"p p mupm nu","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("60","120")
elif(parameterName.find("Z-e")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("60","120")
elif(parameterName.find("Z-mu")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("60","120")
elif(parameterName.find("Z-jj")>=0) :
if(simulation=="Merging"):
logging.warning("Z-jj not explicitly tested for %s " % simulation)
sys.exit(0)
process+=addProcess(thefactory,"p p e+ e- j j","2","2","LeptonPairMassScale",0,0)
process+=addFirstJet("40")
process+=addSecondJet("30")
process+=addLeptonPairCut("60","120")
elif(parameterName.find("Z-LowMass-e")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("20","70")
elif(parameterName.find("Z-MedMass-e")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("40","130")
elif(parameterName.find("Z-LowMass-mu")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",2,2)
process+=addLeptonPairCut("10","70")
elif(parameterName.find("Z-Mass1")>=0) :
process+=addLeptonPairCut("10","35")
if(parameterName.find("-e")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",2,2)
else :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",2,2)
elif(parameterName.find("Z-Mass2")>=0) :
process+=addLeptonPairCut("25","70")
if(parameterName.find("-e")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",2,2)
else :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",2,2)
elif(parameterName.find("Z-Mass3")>=0) :
process+=addLeptonPairCut("60","120")
if(parameterName.find("-e")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",2,2)
else :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",2,2)
elif(parameterName.find("Z-Mass4")>=0) :
process+=addLeptonPairCut("115","8000")
if(parameterName.find("-e")>=0) :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p e+ e-","0","2","LeptonPairMassScale",2,2)
else :
if(simulation=="Matchbox"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",0,0)
elif(simulation=="Merging"):
process+=addProcess(thefactory,"p p mu+ mu-","0","2","LeptonPairMassScale",2,2)
elif(parameterName.find("W-Jet")>=0) :
if(simulation=="Merging"):
logging.warning("W-Jet not explicitly tested for %s " % simulation)
sys.exit(0)
process+=addProcess(thefactory,"p p e+ nu j","1","2","HTScale",0,0)
process+=addProcess(thefactory,"p p e- nu j","1","2","HTScale",0,0)
process+=addLeptonPairCut("60","120")
if(parameterName.find("W-Jet-1-e")>=0) :
process+=addFirstJet("100")
parameterName=parameterName.replace("W-Jet-1-e","W-Jet-e")
elif(parameterName.find("W-Jet-2-e")>=0) :
process+=addFirstJet("190")
parameterName=parameterName.replace("W-Jet-2-e","W-Jet-e")
elif(parameterName.find("W-Jet-3-e")>=0) :
process+=addFirstJet("270")
parameterName=parameterName.replace("W-Jet-3-e","W-Jet-e")
else :
logging.error("Exit 00005")
sys.exit(1)
elif(parameterName.find("Z-Jet")>=0) :
if(simulation=="Merging"):
logging.warning("Z-Jet not explicitly tested for %s " % simulation)
sys.exit(0)
if(parameterName.find("-e")>=0) :
process+=addProcess(thefactory,"p p e+ e- j","1","2","HTScale",0,0)
if(parameterName.find("Z-Jet-0-e")>=0) :
process+=addFirstJet("35")
parameterName=parameterName.replace("Z-Jet-0-e","Z-Jet-e")
elif(parameterName.find("Z-Jet-1-e")>=0) :
process+=addFirstJet("100")
parameterName=parameterName.replace("Z-Jet-1-e","Z-Jet-e")
elif(parameterName.find("Z-Jet-2-e")>=0) :
process+=addFirstJet("190")
parameterName=parameterName.replace("Z-Jet-2-e","Z-Jet-e")
elif(parameterName.find("Z-Jet-3-e")>=0) :
process+=addFirstJet("270")
parameterName=parameterName.replace("Z-Jet-3-e","Z-Jet-e")
else :
logging.error("Exit 00006")
sys.exit(1)
else :
process+=addProcess(thefactory,"p p mu+ mu- j","1","2","HTScale",0,0)
process+=addFirstJet("35")
parameterName=parameterName.replace("Z-Jet-0-mu","Z-Jet-mu")
process+=addLeptonPairCut("60","120")
elif(parameterName.find("Z-bb")>=0) :
if(simulation=="Merging"):
logging.warning("Z-bb not explicitly tested for %s " % simulation)
sys.exit(0)
parameters["bscheme"]=fourFlavour
process+="set /Herwig/Particles/b:HardProcessMass 4.2*GeV\nset /Herwig/Particles/bbar:HardProcessMass 4.2*GeV\n"
process+=addProcess(thefactory,"p p e+ e- b bbar","2","2","FixedScale",0,0)
process+=addLeptonPairCut("66","116")
process+=addFirstJet("18")
process+=addSecondJet("15")
process+=addLeptonPairCut("60","120")
elif(parameterName.find("Z-b")>=0) :
if(simulation=="Merging"):
logging.warning("Z-b not explicitly tested for %s " % simulation)
sys.exit(0)
process+="do "+thefactory+":StartParticleGroup bjet\n"
- process+="insert Factory:ParticleGroup 0 /Herwig/Particles/b\n"
- process+="insert Factory:ParticleGroup 0 /Herwig/Particles/bbar\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/b\n"
+ process+="insert "+thefactory+":ParticleGroup 0 /Herwig/Particles/bbar\n"
process+="do "+thefactory+":EndParticleGroup\n"
process+=addProcess(thefactory,"p p e+ e- bjet","1","2","FixedScale",0,0)
process+="set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 91.2*GeV\n"
process+=addLeptonPairCut("60","120")
process+=addFirstJet("15")
elif(parameterName.find("W-b")>=0) :
if(simulation=="Merging"):
logging.warning("W-b not explicitly tested for %s " % simulation)
sys.exit(0)
parameters["bscheme"]=fourFlavour
process += "set /Herwig/Particles/b:HardProcessMass 4.2*GeV\nset /Herwig/Particles/bbar:HardProcessMass 4.2*GeV\n"
process+=addProcess(thefactory,"p p e- nu b bbar","2","2","FixedScale",0,0)
process+=addProcess(thefactory,"p p mu+ nu b bbar","2","2","FixedScale",0,0)
process += "set /Herwig/MatrixElements/Matchbox/Scales/FixedScale:FixedScale 80.4*GeV\n"
process+=addFirstJet("30")
process+=addLeptonPairCut("60","120")
else :
logging.error(" Process %s not supported for Matchbox matrix elements" % name)
sys.exit(1)
# LHC-GammaGamma
elif(collider=="LHC-GammaGamma" ) :
if(parameterName.find("-7-")>=0) :
process="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 7000.0\n"
elif(parameterName.find("-8-")>=0) :
process="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 8000.0\n"
else :
process="set /Herwig/Generators/EventGenerator:EventHandler:LuminosityFunction:Energy 7000.0\n"
if(simulation=="") :
if(parameterName.find("7")>=0) :
process += "insert SubProcess:MatrixElements 0 /Herwig/MatrixElements/MEgg2ff\n"
process += "set /Herwig/MatrixElements/MEgg2ff:Process Muon\n"
else :
logging.error(" Process %s not supported for default matrix elements" % name)
sys.exit(1)
else :
logging.error("LHC-GammaGamma not supported for %s " % simulation)
sys.exit(1)
parameters['parameterFile'] = os.path.join(collider,collider+"-"+parameterName+".in")
parameters['runname'] = name
parameters['process'] = process
+
+#check if selecteddecaymode and addedBRReweighter is consistent
+
+if selecteddecaymode and not addedBRReweighter:
+ logging.error("Decaymode was selected but no BRReweighter was added.")
+ sys.exit(1)
+
+if addedBRReweighter and not selecteddecaymode:
+ logging.error("BRReweighter was added but no Decaymode was selected.")
+ sys.exit(1)
+
+# check that we only add one process if in merging mode:
+
+if numberOfAddedProcesses > 1 and simulation =="Merging":
+ logging.error("In Merging only one process is allowed at the moment. See ticket #403.")
+ sys.exit(1)
+
+# Check if a process was added for Merging or Matchbox:
+
+if numberOfAddedProcesses == 0 and (simulation =="Merging" or simulation =="Matchbox"):
+ logging.error("No process was selected.")
+ sys.exit(1)
+
# write the file
with open(os.path.join("Rivet",name+".in") ,'w') as f:
f.write( template.substitute(parameters))
diff --git a/Tests/python/merge-BFactory b/Tests/python/merge-BFactory
--- a/Tests/python/merge-BFactory
+++ b/Tests/python/merge-BFactory
@@ -1,212 +1,213 @@
#! /usr/bin/env python
import logging
import sys
if sys.version_info[:3] < (2,4,0):
print "rivet scripts require Python version >= 2.4.0... exiting"
sys.exit(1)
import os, yoda
# #############################################
def fillAbove(desthisto, sourcehistosbysqrts):
for sqrts, h in sorted(sourcehistosbysqrts.iteritems()) :
for i in range(0,h.numPoints) :
if(h.points[i].x-0.01<sqrts and
h.points[i].x+0.01>sqrts) :
desthisto.addPoint(h.points[i])
def merge(hpath):
global inhistos
global outhistos
try:
fillAbove(outhistos[hpath], inhistos[hpath])
except:
logging.error("Unknown analysis object" + hpath)
sys.exit(1)
def useOne(hpath, sqrts):
global inhistos
global outhistos
try:
outhistos[hpath] = inhistos[hpath][float(sqrts)]
except:
pass
if __name__ == "__main__":
import logging
from optparse import OptionParser, OptionGroup
parser = OptionParser(usage="%prog name")
verbgroup = OptionGroup(parser, "Verbosity control")
verbgroup.add_option("-v", "--verbose", action="store_const", const=logging.DEBUG, dest="LOGLEVEL",
default=logging.INFO, help="print debug (very verbose) messages")
verbgroup.add_option("-q", "--quiet", action="store_const", const=logging.WARNING, dest="LOGLEVEL",
default=logging.INFO, help="be very quiet")
parser.add_option_group(verbgroup)
(opts, args) = parser.parse_args()
logging.basicConfig(level=opts.LOGLEVEL, format="%(message)s")
## Check args
if len(args) < 1:
logging.error("Must specify at least the name of the files")
sys.exit(1)
# #######################################
yodafiles=["-10.52.yoda","-10.52-sym.yoda","-10.54.yoda",
"-10.58-res.yoda","-10.58.yoda","-Upsilon.yoda",
"-Upsilon2.yoda","-Upsilon4.yoda","-10.45.yoda","-Tau.yoda"]
## Get histos
inhistos = {}
outhistos={}
weights = {}
for f in yodafiles:
file = args[0]+f
if(file.find("10.45")>0) :
sqrts=10.45
elif(file.find("10.52")>0) :
sqrts=10.52
elif(file.find("10.54")>0) :
sqrts=10.54
elif(file.find("10.58")>0) :
sqrts=10.58
elif(file.find("Tau")>0) :
sqrts=10.58
elif(file.find("Upsilon4")>0) :
sqrts=10.58
elif(file.find("Upsilon2")>0) :
sqrts=10.02
elif(file.find("Upsilon")>0) :
sqrts=9.46
if not os.access(file, os.R_OK):
if(file.find("Upsilon")>=0 or file.find("Tau")>=0) : continue
logging.error("%s can not be read" % file)
continue
try:
aos = yoda.read(file)
except:
logging.error("%s can not be parsed as yoda" % file)
continue
## Get histos from this YODA file
for aopath, ao in aos.iteritems() :
# jet shapes
if(aopath.find("6265367")>0 or aopath.find("6895344")>0 or
aopath.find("6181155")>0 or aopath.find("2789213")>0 or
aopath.find("2669951")>0) :
if not inhistos.has_key(aopath):
inhistos[aopath] = {}
tmpE = inhistos[aopath]
sqrttemp=sqrts
if(aopath.find("2669951")>0 and aopath.find("d01")>0 and
sqrts==10.45) :
sqrts=9.9
if not tmpE.has_key(sqrts):
tmpE[sqrts] = ao
else:
raise Exception("A set with sqrts = %s already exists" % ( sqrts))
sqrts=sqrttemp
else :
outhistos[aopath] = ao
## Make empty output histos if needed
for hpath,hsets in inhistos.iteritems():
if( hpath.find("2669951")>0) :
if(type(hsets.values()[0])==yoda.core.Scatter2D) :
outhistos[hpath] = yoda.core.Scatter2D(hsets.values()[0].path,hsets.values()[0].title)
else :
outhistos[hpath] = hsets.values()[0]
# BELLE
useOne("/BELLE_2006_S6265367/d01-x01-y01","10.52")
useOne("/BELLE_2006_S6265367/d01-x01-y02","10.52")
useOne("/BELLE_2006_S6265367/d01-x01-y03","10.52")
useOne("/BELLE_2006_S6265367/d01-x01-y04","10.52")
useOne("/BELLE_2006_S6265367/d01-x01-y05","10.52")
useOne("/BELLE_2006_S6265367/d01-x01-y06","10.52")
useOne("/BELLE_2006_S6265367/d01-x01-y07","10.52")
useOne("/BELLE_2006_S6265367/d01-x01-y08","10.52")
useOne("/BELLE_2006_S6265367/d02-x01-y01","10.52")
useOne("/BELLE_2006_S6265367/d02-x01-y02","10.52")
useOne("/BELLE_2006_S6265367/d03-x01-y01","10.52")
useOne("/BELLE_2006_S6265367/d03-x01-y02","10.52")
useOne("/BELLE_2006_S6265367/d04-x01-y01","10.52")
useOne("/BELLE_2006_S6265367/d04-x01-y02","10.52")
useOne("/BELLE_2006_S6265367/d05-x01-y01","10.52")
useOne("/BELLE_2006_S6265367/d05-x01-y02","10.52")
useOne("/BELLE_2006_S6265367/d06-x01-y01","10.52")
useOne("/BELLE_2006_S6265367/d06-x01-y02","10.52")
useOne("/BELLE_2006_S6265367/d07-x01-y01","10.52")
useOne("/BELLE_2006_S6265367/d07-x01-y02","10.52")
useOne("/BELLE_2006_S6265367/d08-x01-y01","10.52")
useOne("/BELLE_2006_S6265367/d08-x01-y02","10.52")
useOne("/BELLE_2006_S6265367/d09-x01-y01","10.58")
useOne("/BELLE_2006_S6265367/d09-x01-y02","10.58")
useOne("/BELLE_2006_S6265367/d10-x01-y01","10.58")
useOne("/BELLE_2006_S6265367/d10-x01-y02","10.58")
useOne("/BELLE_2006_S6265367/d11-x01-y01","10.58")
useOne("/BELLE_2006_S6265367/d11-x01-y02","10.58")
useOne("/BELLE_2006_S6265367/d12-x01-y01","10.58")
useOne("/BELLE_2006_S6265367/d12-x01-y02","10.58")
useOne("/BELLE_2006_S6265367/d13-x01-y01","10.58")
useOne("/BELLE_2006_S6265367/d13-x01-y02","10.58")
useOne("/BELLE_2006_S6265367/d14-x01-y01","10.58")
useOne("/BELLE_2006_S6265367/d14-x01-y02","10.58")
useOne("/BELLE_2006_S6265367/d15-x01-y01","10.58")
useOne("/BELLE_2006_S6265367/d15-x01-y02","10.58")
# BABAR
useOne("/BABAR_2007_S6895344/d01-x01-y01","10.54")
useOne("/BABAR_2007_S6895344/d02-x01-y01","10.54")
useOne("/BABAR_2007_S6895344/d03-x01-y01","10.58")
useOne("/BABAR_2007_S6895344/d04-x01-y01","10.58")
# BABAR
useOne("/BABAR_2005_S6181155/d01-x01-y01","10.58")
useOne("/BABAR_2005_S6181155/d02-x01-y01","10.58")
useOne("/BABAR_2005_S6181155/d02-x01-y02","10.54")
useOne("/BABAR_2005_S6181155/d03-x01-y01","10.54")
useOne("/BABAR_2005_S6181155/d04-x01-y01","10.58")
useOne("/BABAR_2005_S6181155/d05-x01-y01","10.58")
useOne("/BABAR_2005_S6181155/d05-x01-y02","10.54")
# ARGUS
useOne("/ARGUS_1993_S2789213/d01-x01-y01","10.45")
useOne("/ARGUS_1993_S2789213/d01-x01-y02","10.45")
useOne("/ARGUS_1993_S2789213/d01-x01-y03","10.45")
useOne("/ARGUS_1993_S2789213/d01-x01-y04","10.45")
useOne("/ARGUS_1993_S2789213/d01-x01-y05","10.45")
useOne("/ARGUS_1993_S2789213/d02-x01-y01", "9.46")
useOne("/ARGUS_1993_S2789213/d02-x01-y02", "9.46")
useOne("/ARGUS_1993_S2789213/d02-x01-y03", "9.46")
useOne("/ARGUS_1993_S2789213/d02-x01-y04", "9.46")
useOne("/ARGUS_1993_S2789213/d02-x01-y05", "9.46")
useOne("/ARGUS_1993_S2789213/d03-x01-y01","10.58")
useOne("/ARGUS_1993_S2789213/d03-x01-y02","10.58")
useOne("/ARGUS_1993_S2789213/d03-x01-y03","10.58")
useOne("/ARGUS_1993_S2789213/d03-x01-y04","10.58")
useOne("/ARGUS_1993_S2789213/d03-x01-y05","10.58")
useOne("/ARGUS_1993_S2789213/d04-x01-y01","10.45")
useOne("/ARGUS_1993_S2789213/d05-x01-y01", "9.46")
useOne("/ARGUS_1993_S2789213/d06-x01-y01","10.58")
useOne("/ARGUS_1993_S2789213/d07-x01-y01","10.45")
useOne("/ARGUS_1993_S2789213/d08-x01-y01", "9.46")
useOne("/ARGUS_1993_S2789213/d09-x01-y01","10.58")
useOne("/ARGUS_1993_S2789213/d10-x01-y01","10.45")
useOne("/ARGUS_1993_S2789213/d11-x01-y01", "9.46")
useOne("/ARGUS_1993_S2789213/d12-x01-y01","10.58")
useOne("/ARGUS_1993_S2789213/d13-x01-y01","10.45")
useOne("/ARGUS_1993_S2789213/d14-x01-y01", "9.46")
useOne("/ARGUS_1993_S2789213/d15-x01-y01","10.58")
-useOne("/ARGUS_1993_S2669951/d02-x01-y01","10.45")
-useOne("/ARGUS_1993_S2669951/d03-x01-y01","9.46")
-useOne("/ARGUS_1993_S2669951/d04-x01-y01","10.02")
-merge("/ARGUS_1993_S2669951/d01-x01-y01")
-merge("/ARGUS_1993_S2669951/d01-x01-y02")
-merge("/ARGUS_1993_S2669951/d05-x01-y01")
+if("/ARGUS_1993_S2669951/d04-x01-y01" in outhistos) :
+ useOne("/ARGUS_1993_S2669951/d02-x01-y01","10.45")
+ useOne("/ARGUS_1993_S2669951/d03-x01-y01","9.46")
+ useOne("/ARGUS_1993_S2669951/d04-x01-y01","10.02")
+ merge("/ARGUS_1993_S2669951/d01-x01-y01")
+ merge("/ARGUS_1993_S2669951/d01-x01-y02")
+ merge("/ARGUS_1993_S2669951/d05-x01-y01")
# Choose output file
name = args[0]+".yoda"
# output the yoda file
yoda.writeYODA(outhistos,name)
sys.exit(0)
diff --git a/Tests/python/merge-LEP b/Tests/python/merge-LEP
--- a/Tests/python/merge-LEP
+++ b/Tests/python/merge-LEP
@@ -1,917 +1,887 @@
#! /usr/bin/env python
# import lighthisto
import logging
import sys
if sys.version_info[:3] < (2,4,0):
print "rivet scripts require Python version >= 2.4.0... exiting"
sys.exit(1)
import os, yoda, copy
# # #############################################
def fillAbove(desthisto, sourcehistosbysqrts):
if type(desthisto) is yoda.core.Scatter2D :
if(desthisto.numPoints!=1) :
- print desthisto.numPoints
logging.error("Must have one bin for a specific sqrt(s) for %s" % desthisto.path)
sys.exit(1)
for sqrts, h in sorted(sourcehistosbysqrts.iteritems()) :
if(h.numPoints!=1) :
continue
if(desthisto.points[0].x != h.points[0].x) :
desthisto.addPoint(h.points[0])
+
+ elif(type(desthisto)==yoda.core.Profile1D) :
+ for sqrts, h in sorted(sourcehistosbysqrts.iteritems()) :
+ for i in range(0,h.numBins) :
+ if(sqrts>=h.bins[i].xMin and \
+ sqrts<=h.bins[i].xMax) :
+ desthisto.bins[i] += h.bins[i]
+ break
else :
logging.error("Unknown analysis object" + desthisto.path)
sys.exit(1)
def merge(hpath):
global inhistos
global outhistos
try:
fillAbove(outhistos[hpath], inhistos[hpath])
except:
pass
def useOne(hpath, sqrts):
global inhistos
global outhistos
try:
outhistos[hpath] = inhistos[hpath][float(sqrts)]
except:
pass
if __name__ == "__main__":
import logging
from optparse import OptionParser, OptionGroup
parser = OptionParser(usage="%prog name")
verbgroup = OptionGroup(parser, "Verbosity control")
verbgroup.add_option("-v", "--verbose", action="store_const", const=logging.DEBUG, dest="LOGLEVEL",
default=logging.INFO, help="print debug (very verbose) messages")
verbgroup.add_option("-q", "--quiet", action="store_const", const=logging.WARNING, dest="LOGLEVEL",
default=logging.INFO, help="be very quiet")
parser.add_option_group(verbgroup)
parser.add_option("--with-gg",
action='store_true' ,
dest="gg",
default=False,
help="Include gg analyese")
parser.add_option("--without-gg",
action='store_false',
dest="gg",
default=False,
help="Don\'t include gg analyses")
(opts, args) = parser.parse_args()
logging.basicConfig(level=opts.LOGLEVEL, format="%(message)s")
## Check args
if len(args) < 1:
logging.error("Must specify at least the name of the files")
sys.exit(1)
#######################################
yodafiles=["-130","-133","-136","-177","-192",
"-196","-202","-206","-91" ,"-91-nopi" ,\
"-161","-183","-197","-35" ,"-172",\
"-189","-200","-44","-14","-22","-10",\
- "-12.8","-26.8","-48.0","-93.0" ]
+ "-12.8","-26.8","-48.0","-93.0",\
+ "-12","-13","-17","-27.6","-29","-30.2","-30.75",\
+ "-30.7","-30","-31.3","-34.8","-43.6","-50","-52",\
+ "-55","-56","-57","-60.8","-60","-61.4","-9.4" ]
# add gg if needed
if(opts.gg) :
yodafiles += ["-10.5-gg","-12.8-gg","-16.86-gg","-26.8-gg",\
"-35.44-gg","-97.0-gg","-11.96-gg","-13.96-gg",\
"-21.84-gg","-28.48-gg","-48.0-gg"]
## Get histos
inhistos = {}
outhistos={}
for f in yodafiles:
file = args[0]+f+".yoda"
- if(file.find("10.5")>0) :
- sqrts=10.5
- elif(file.find("10")>0) :
- sqrts=10
- elif(file.find("11.96")>0) :
- sqrts=11.96
- elif(file.find("12.8")>0) :
- sqrts=12.8
- elif(file.find("13.96")>0) :
- sqrts=13.96
- elif(file.find("14")>0) :
- sqrts=14
- elif(file.find("16.86")>0) :
- sqrts=16.86
- elif(file.find("21.84")>0) :
- sqrts=21.84
- elif(file.find("22")>0) :
- sqrts=22
- elif(file.find("26.8")>0) :
- sqrts=26.8
- elif(file.find("28.48")>0) :
- sqrts=28.48
- elif(file.find("35")>0) :
- sqrts=35
- elif(file.find("44")>0) :
- sqrts=44
- elif(file.find("48.0")>0) :
- sqrts=48.0
- elif(file.find("91")>0) :
- sqrts=91
- elif(file.find("93.0")>0) :
- sqrts=93
- elif(file.find("97.0")>0) :
- sqrts=97
- elif(file.find("130")>0) :
- sqrts=130
- elif(file.find("133")>0) :
- sqrts=133
- elif(file.find("136")>0) :
- sqrts=136
- elif(file.find("161")>0) :
- sqrts=161
- elif(file.find("172")>0) :
- sqrts=172
- elif(file.find("177")>0) :
- sqrts=177
- elif(file.find("183")>0) :
- sqrts=183
- elif(file.find("189")>0) :
- sqrts=189
- elif(file.find("192")>0) :
- sqrts=192
- elif(file.find("196")>0) :
- sqrts=196
- elif(file.find("197")>0) :
- sqrts=197
- elif(file.find("200")>0) :
- sqrts=200
- elif(file.find("202")>0) :
- sqrts=202
- elif(file.find("206")>0) :
- sqrts=206
- else :
- print file
- quit()
-
+ sqrts=float(file.split("-")[1].replace(".yoda",""))
if not os.access(file, os.R_OK):
logging.error("%s can not be read" % file)
continue
try:
aos = yoda.read(file)
except:
logging.error("%s can not be parsed as yoda" % file)
continue
## Get histos from this YODA file
for aopath, ao in aos.iteritems() :
# jet shapes
if(aopath.find("4300807")>0 or aopath.find("6132243")>0 or
aopath.find("5765862")>0 or aopath.find("3612880")>0 or
aopath.find("4328825")>0 or aopath.find("5361494")>0 or
- aopath.find("2148048")>0 or aopath.find("MULTIPLICITIES")>0 ) :
+ aopath.find("2148048")>0 or aopath.find("295160")>0 or
+ aopath.find("190818" )>0 or aopath.find("154270")>0 or
+ aopath.find("277658")>0 or
+ aopath.find("MULTIPLICITIES")>0) :
if not inhistos.has_key(aopath):
inhistos[aopath] = {}
if not inhistos[aopath].has_key(sqrts):
inhistos[aopath][sqrts] = ao
else:
raise Exception("A set with sqrts = %s already exists" % ( sqrts))
elif(aopath.find("OPAL_2004_I648738")>=0) :
if(file.find("gg")>=0) :
if(aopath.find("y03")>=0) :
outhistos[aopath] = ao
else :
if(aopath.find("y03")<0) :
outhistos[aopath] = ao
else :
outhistos[aopath] = ao
# ## Make empty output histos if needed
for hpath,hsets in inhistos.iteritems():
if( hpath.find("4300807")>0 or hpath.find("6132243")>0 or
- hpath.find("5765862")>0 or
- hpath.find("4328825")>0 or hpath.find("5361494")>0) :
+ hpath.find("5765862")>0 or hpath.find("295160")>0 or
+ hpath.find("4328825")>0 or hpath.find("5361494")>0 or
+ hpath.find("190818")>0 or hpath.find("154270")>0 or
+ hpath.find("277658")>0) :
# workhisto = copy.deepcopy(hsets.values()[0])
# outhistos[hpath] = workhisto
outhistos[hpath] = hsets.values()[0]
# tasso
useOne("/TASSO_1990_S2148048/d06-x01-y01","14")
useOne("/TASSO_1990_S2148048/d07-x01-y01","14")
useOne("/TASSO_1990_S2148048/d08-x01-y01","14")
useOne("/TASSO_1990_S2148048/d06-x01-y02","22")
useOne("/TASSO_1990_S2148048/d07-x01-y02","22")
useOne("/TASSO_1990_S2148048/d08-x01-y02","22")
useOne("/TASSO_1990_S2148048/d06-x01-y03","35")
useOne("/TASSO_1990_S2148048/d07-x01-y03","35")
useOne("/TASSO_1990_S2148048/d08-x01-y03","35")
useOne("/TASSO_1990_S2148048/d06-x01-y04","44")
useOne("/TASSO_1990_S2148048/d07-x01-y04","44")
useOne("/TASSO_1990_S2148048/d08-x01-y04","44")
# jade
useOne("/JADE_1998_S3612880/d02-x01-y01","44")
useOne("/JADE_1998_S3612880/d03-x01-y01","44")
useOne("/JADE_1998_S3612880/d04-x01-y01","44")
useOne("/JADE_1998_S3612880/d05-x01-y01","44")
useOne("/JADE_1998_S3612880/d06-x01-y01","35")
useOne("/JADE_1998_S3612880/d07-x01-y01","35")
useOne("/JADE_1998_S3612880/d08-x01-y01","35")
useOne("/JADE_1998_S3612880/d09-x01-y01","35")
useOne("/JADE_1998_S3612880/d10-x01-y01","44")
useOne("/JADE_1998_S3612880/d11-x01-y01","35")
useOne("/JADE_1998_S3612880/d12-x01-y01","22")
# opal/jade
useOne("/JADE_OPAL_2000_S4300807/d07-x01-y01","35")
useOne("/JADE_OPAL_2000_S4300807/d07-x01-y02","35")
useOne("/JADE_OPAL_2000_S4300807/d07-x01-y03","35")
useOne("/JADE_OPAL_2000_S4300807/d07-x01-y04","35")
useOne("/JADE_OPAL_2000_S4300807/d07-x01-y05","35")
useOne("/JADE_OPAL_2000_S4300807/d08-x01-y01","44")
useOne("/JADE_OPAL_2000_S4300807/d08-x01-y02","44")
useOne("/JADE_OPAL_2000_S4300807/d08-x01-y03","44")
useOne("/JADE_OPAL_2000_S4300807/d08-x01-y04","44")
useOne("/JADE_OPAL_2000_S4300807/d08-x01-y05","44")
useOne("/JADE_OPAL_2000_S4300807/d09-x01-y01","91")
useOne("/JADE_OPAL_2000_S4300807/d09-x01-y02","91")
useOne("/JADE_OPAL_2000_S4300807/d09-x01-y03","91")
useOne("/JADE_OPAL_2000_S4300807/d09-x01-y04","91")
useOne("/JADE_OPAL_2000_S4300807/d09-x01-y05","91")
useOne("/JADE_OPAL_2000_S4300807/d10-x01-y01","133")
useOne("/JADE_OPAL_2000_S4300807/d10-x01-y02","133")
useOne("/JADE_OPAL_2000_S4300807/d10-x01-y03","133")
useOne("/JADE_OPAL_2000_S4300807/d10-x01-y04","133")
useOne("/JADE_OPAL_2000_S4300807/d10-x01-y05","133")
useOne("/JADE_OPAL_2000_S4300807/d11-x01-y01","161")
useOne("/JADE_OPAL_2000_S4300807/d11-x01-y02","161")
useOne("/JADE_OPAL_2000_S4300807/d11-x01-y03","161")
useOne("/JADE_OPAL_2000_S4300807/d11-x01-y04","161")
useOne("/JADE_OPAL_2000_S4300807/d11-x01-y05","161")
useOne("/JADE_OPAL_2000_S4300807/d12-x01-y01","172")
useOne("/JADE_OPAL_2000_S4300807/d12-x01-y02","172")
useOne("/JADE_OPAL_2000_S4300807/d12-x01-y03","172")
useOne("/JADE_OPAL_2000_S4300807/d12-x01-y04","172")
useOne("/JADE_OPAL_2000_S4300807/d12-x01-y05","172")
useOne("/JADE_OPAL_2000_S4300807/d13-x01-y01","183")
useOne("/JADE_OPAL_2000_S4300807/d13-x01-y02","183")
useOne("/JADE_OPAL_2000_S4300807/d13-x01-y03","183")
useOne("/JADE_OPAL_2000_S4300807/d13-x01-y04","183")
useOne("/JADE_OPAL_2000_S4300807/d13-x01-y05","183")
useOne("/JADE_OPAL_2000_S4300807/d14-x01-y01","189")
useOne("/JADE_OPAL_2000_S4300807/d14-x01-y02","189")
useOne("/JADE_OPAL_2000_S4300807/d14-x01-y03","189")
useOne("/JADE_OPAL_2000_S4300807/d14-x01-y04","189")
useOne("/JADE_OPAL_2000_S4300807/d14-x01-y05","189")
useOne("/JADE_OPAL_2000_S4300807/d16-x01-y01","35")
useOne("/JADE_OPAL_2000_S4300807/d16-x01-y02","35")
useOne("/JADE_OPAL_2000_S4300807/d16-x01-y03","35")
useOne("/JADE_OPAL_2000_S4300807/d16-x01-y04","35")
useOne("/JADE_OPAL_2000_S4300807/d16-x01-y05","35")
useOne("/JADE_OPAL_2000_S4300807/d17-x01-y01","44")
useOne("/JADE_OPAL_2000_S4300807/d17-x01-y02","44")
useOne("/JADE_OPAL_2000_S4300807/d17-x01-y03","44")
useOne("/JADE_OPAL_2000_S4300807/d17-x01-y04","44")
useOne("/JADE_OPAL_2000_S4300807/d17-x01-y05","44")
useOne("/JADE_OPAL_2000_S4300807/d18-x01-y01","91")
useOne("/JADE_OPAL_2000_S4300807/d18-x01-y02","91")
useOne("/JADE_OPAL_2000_S4300807/d18-x01-y03","91")
useOne("/JADE_OPAL_2000_S4300807/d18-x01-y04","91")
useOne("/JADE_OPAL_2000_S4300807/d18-x01-y05","91")
useOne("/JADE_OPAL_2000_S4300807/d19-x01-y01","133")
useOne("/JADE_OPAL_2000_S4300807/d19-x01-y02","133")
useOne("/JADE_OPAL_2000_S4300807/d19-x01-y03","133")
useOne("/JADE_OPAL_2000_S4300807/d19-x01-y04","133")
useOne("/JADE_OPAL_2000_S4300807/d19-x01-y05","133")
useOne("/JADE_OPAL_2000_S4300807/d20-x01-y01","161")
useOne("/JADE_OPAL_2000_S4300807/d20-x01-y02","161")
useOne("/JADE_OPAL_2000_S4300807/d20-x01-y03","161")
useOne("/JADE_OPAL_2000_S4300807/d20-x01-y04","161")
useOne("/JADE_OPAL_2000_S4300807/d20-x01-y05","161")
useOne("/JADE_OPAL_2000_S4300807/d21-x01-y01","172")
useOne("/JADE_OPAL_2000_S4300807/d21-x01-y02","172")
useOne("/JADE_OPAL_2000_S4300807/d21-x01-y03","172")
useOne("/JADE_OPAL_2000_S4300807/d21-x01-y04","172")
useOne("/JADE_OPAL_2000_S4300807/d21-x01-y05","172")
useOne("/JADE_OPAL_2000_S4300807/d22-x01-y01","183")
useOne("/JADE_OPAL_2000_S4300807/d22-x01-y02","183")
useOne("/JADE_OPAL_2000_S4300807/d22-x01-y03","183")
useOne("/JADE_OPAL_2000_S4300807/d22-x01-y04","183")
useOne("/JADE_OPAL_2000_S4300807/d22-x01-y05","183")
useOne("/JADE_OPAL_2000_S4300807/d23-x01-y01","189")
useOne("/JADE_OPAL_2000_S4300807/d23-x01-y02","189")
useOne("/JADE_OPAL_2000_S4300807/d23-x01-y03","189")
useOne("/JADE_OPAL_2000_S4300807/d23-x01-y04","189")
useOne("/JADE_OPAL_2000_S4300807/d23-x01-y05","189")
useOne("/JADE_OPAL_2000_S4300807/d24-x01-y01","35")
useOne("/JADE_OPAL_2000_S4300807/d24-x01-y02","35")
useOne("/JADE_OPAL_2000_S4300807/d24-x01-y03","35")
useOne("/JADE_OPAL_2000_S4300807/d24-x01-y04","35")
useOne("/JADE_OPAL_2000_S4300807/d25-x01-y01","44")
useOne("/JADE_OPAL_2000_S4300807/d25-x01-y02","44")
useOne("/JADE_OPAL_2000_S4300807/d25-x01-y03","44")
useOne("/JADE_OPAL_2000_S4300807/d25-x01-y04","44")
useOne("/JADE_OPAL_2000_S4300807/d26-x01-y01","91")
useOne("/JADE_OPAL_2000_S4300807/d26-x01-y02","91")
useOne("/JADE_OPAL_2000_S4300807/d26-x01-y03","91")
useOne("/JADE_OPAL_2000_S4300807/d26-x01-y04","91")
useOne("/JADE_OPAL_2000_S4300807/d27-x01-y01","133")
useOne("/JADE_OPAL_2000_S4300807/d27-x01-y02","133")
useOne("/JADE_OPAL_2000_S4300807/d27-x01-y03","133")
useOne("/JADE_OPAL_2000_S4300807/d27-x01-y04","133")
useOne("/JADE_OPAL_2000_S4300807/d28-x01-y01","161")
useOne("/JADE_OPAL_2000_S4300807/d28-x01-y02","161")
useOne("/JADE_OPAL_2000_S4300807/d28-x01-y03","161")
useOne("/JADE_OPAL_2000_S4300807/d28-x01-y04","161")
useOne("/JADE_OPAL_2000_S4300807/d29-x01-y01","172")
useOne("/JADE_OPAL_2000_S4300807/d29-x01-y02","172")
useOne("/JADE_OPAL_2000_S4300807/d29-x01-y03","172")
useOne("/JADE_OPAL_2000_S4300807/d29-x01-y04","172")
useOne("/JADE_OPAL_2000_S4300807/d30-x01-y01","183")
useOne("/JADE_OPAL_2000_S4300807/d30-x01-y02","183")
useOne("/JADE_OPAL_2000_S4300807/d30-x01-y03","183")
useOne("/JADE_OPAL_2000_S4300807/d30-x01-y04","183")
useOne("/JADE_OPAL_2000_S4300807/d31-x01-y01","189")
useOne("/JADE_OPAL_2000_S4300807/d31-x01-y02","189")
useOne("/JADE_OPAL_2000_S4300807/d31-x01-y03","189")
useOne("/JADE_OPAL_2000_S4300807/d31-x01-y04","189")
useOne("/OPAL_2004_S6132243/d01-x01-y01","91")
useOne("/OPAL_2004_S6132243/d01-x01-y02","133")
useOne("/OPAL_2004_S6132243/d01-x01-y03","177")
useOne("/OPAL_2004_S6132243/d01-x01-y04","197")
useOne("/OPAL_2004_S6132243/d02-x01-y01","91")
useOne("/OPAL_2004_S6132243/d02-x01-y02","133")
useOne("/OPAL_2004_S6132243/d02-x01-y03","177")
useOne("/OPAL_2004_S6132243/d02-x01-y04","197")
useOne("/OPAL_2004_S6132243/d03-x01-y01","91")
useOne("/OPAL_2004_S6132243/d03-x01-y02","133")
useOne("/OPAL_2004_S6132243/d03-x01-y03","177")
useOne("/OPAL_2004_S6132243/d03-x01-y04","197")
useOne("/OPAL_2004_S6132243/d04-x01-y01","91")
useOne("/OPAL_2004_S6132243/d04-x01-y02","133")
useOne("/OPAL_2004_S6132243/d04-x01-y03","177")
useOne("/OPAL_2004_S6132243/d04-x01-y04","197")
useOne("/OPAL_2004_S6132243/d05-x01-y01","91")
useOne("/OPAL_2004_S6132243/d05-x01-y02","133")
useOne("/OPAL_2004_S6132243/d05-x01-y03","177")
useOne("/OPAL_2004_S6132243/d05-x01-y04","197")
useOne("/OPAL_2004_S6132243/d06-x01-y01","91")
useOne("/OPAL_2004_S6132243/d06-x01-y02","133")
useOne("/OPAL_2004_S6132243/d06-x01-y03","177")
useOne("/OPAL_2004_S6132243/d06-x01-y04","197")
useOne("/OPAL_2004_S6132243/d07-x01-y01","91")
useOne("/OPAL_2004_S6132243/d07-x01-y02","133")
useOne("/OPAL_2004_S6132243/d07-x01-y03","177")
useOne("/OPAL_2004_S6132243/d07-x01-y04","197")
useOne("/OPAL_2004_S6132243/d08-x01-y01","91")
useOne("/OPAL_2004_S6132243/d08-x01-y02","133")
useOne("/OPAL_2004_S6132243/d08-x01-y03","177")
useOne("/OPAL_2004_S6132243/d08-x01-y04","197")
useOne("/OPAL_2004_S6132243/d09-x01-y01","91")
useOne("/OPAL_2004_S6132243/d09-x01-y02","133")
useOne("/OPAL_2004_S6132243/d09-x01-y03","177")
useOne("/OPAL_2004_S6132243/d09-x01-y04","197")
useOne("/OPAL_2004_S6132243/d10-x01-y01","91")
useOne("/OPAL_2004_S6132243/d10-x01-y02","133")
useOne("/OPAL_2004_S6132243/d10-x01-y03","177")
useOne("/OPAL_2004_S6132243/d10-x01-y04","197")
useOne("/OPAL_2004_S6132243/d11-x01-y01","91")
useOne("/OPAL_2004_S6132243/d11-x01-y02","133")
useOne("/OPAL_2004_S6132243/d11-x01-y03","177")
useOne("/OPAL_2004_S6132243/d11-x01-y04","197")
useOne("/OPAL_2004_S6132243/d12-x01-y01","91")
useOne("/OPAL_2004_S6132243/d12-x01-y02","133")
useOne("/OPAL_2004_S6132243/d12-x01-y03","177")
useOne("/OPAL_2004_S6132243/d12-x01-y04","197")
useOne("/OPAL_2004_S6132243/d13-x01-y01","91")
useOne("/OPAL_2004_S6132243/d13-x01-y02","133")
useOne("/OPAL_2004_S6132243/d13-x01-y03","177")
useOne("/OPAL_2004_S6132243/d13-x01-y04","197")
useOne("/OPAL_2004_S6132243/d14-x01-y01","91")
useOne("/OPAL_2004_S6132243/d14-x01-y02","133")
useOne("/OPAL_2004_S6132243/d14-x01-y03","177")
useOne("/OPAL_2004_S6132243/d14-x01-y04","197")
useOne("/OPAL_2004_S6132243/d15-x01-y01","91")
useOne("/OPAL_2004_S6132243/d15-x01-y02","133")
useOne("/OPAL_2004_S6132243/d15-x01-y03","177")
useOne("/OPAL_2004_S6132243/d15-x01-y04","197")
useOne("/OPAL_2004_S6132243/d16-x01-y01","91")
useOne("/OPAL_2004_S6132243/d16-x01-y02","133")
useOne("/OPAL_2004_S6132243/d16-x01-y03","177")
useOne("/OPAL_2004_S6132243/d16-x01-y04","197")
useOne("/OPAL_2004_S6132243/d17-x01-y01","91")
useOne("/OPAL_2004_S6132243/d17-x01-y02","133")
useOne("/OPAL_2004_S6132243/d17-x01-y03","177")
useOne("/OPAL_2004_S6132243/d17-x01-y04","197")
useOne("/OPAL_2004_S6132243/d18-x01-y01","91")
useOne("/OPAL_2004_S6132243/d18-x01-y02","133")
useOne("/OPAL_2004_S6132243/d18-x01-y03","177")
useOne("/OPAL_2004_S6132243/d18-x01-y04","197")
useOne("/OPAL_2004_S6132243/d19-x01-y01","91")
useOne("/OPAL_2004_S6132243/d19-x01-y02","133")
useOne("/OPAL_2004_S6132243/d19-x01-y03","177")
useOne("/OPAL_2004_S6132243/d19-x01-y04","197")
useOne("/OPAL_2004_S6132243/d20-x01-y01","91")
useOne("/OPAL_2004_S6132243/d20-x01-y02","133")
useOne("/OPAL_2004_S6132243/d20-x01-y03","177")
useOne("/OPAL_2004_S6132243/d20-x01-y04","197")
useOne("/OPAL_2004_S6132243/d21-x01-y01","91")
useOne("/OPAL_2004_S6132243/d21-x01-y02","133")
useOne("/OPAL_2004_S6132243/d21-x01-y03","177")
useOne("/OPAL_2004_S6132243/d21-x01-y04","197")
useOne("/OPAL_2004_S6132243/d22-x01-y01","91")
useOne("/OPAL_2004_S6132243/d22-x01-y02","133")
useOne("/OPAL_2004_S6132243/d22-x01-y03","177")
useOne("/OPAL_2004_S6132243/d22-x01-y04","197")
useOne("/OPAL_2004_S6132243/d23-x01-y01","91")
useOne("/OPAL_2004_S6132243/d23-x01-y02","133")
useOne("/OPAL_2004_S6132243/d23-x01-y03","177")
useOne("/OPAL_2004_S6132243/d23-x01-y04","197")
useOne("/OPAL_2004_S6132243/d24-x01-y01","91")
useOne("/OPAL_2004_S6132243/d24-x01-y02","133")
useOne("/OPAL_2004_S6132243/d24-x01-y03","177")
useOne("/OPAL_2004_S6132243/d24-x01-y04","197")
useOne("/OPAL_2004_S6132243/d25-x01-y01","91")
useOne("/OPAL_2004_S6132243/d25-x01-y02","133")
useOne("/OPAL_2004_S6132243/d25-x01-y03","177")
useOne("/OPAL_2004_S6132243/d25-x01-y04","197")
useOne("/OPAL_2004_S6132243/d26-x01-y01","91")
useOne("/OPAL_2004_S6132243/d26-x01-y02","133")
useOne("/OPAL_2004_S6132243/d26-x01-y03","177")
useOne("/OPAL_2004_S6132243/d26-x01-y04","197")
merge( "/OPAL_2002_S5361494/d01-x01-y01")
merge( "/OPAL_2002_S5361494/d01-x01-y02")
merge( "/OPAL_2002_S5361494/d01-x01-y03")
merge( "/OPAL_2002_S5361494/d01-x01-y04")
merge("/DELPHI_2000_S4328825/d01-x01-y01")
merge("/DELPHI_2000_S4328825/d01-x01-y02")
merge("/DELPHI_2000_S4328825/d01-x01-y03")
merge("/DELPHI_2000_S4328825/d01-x01-y04")
merge("/ALEPH_2004_S5765862/d01-x01-y01")
useOne("/ALEPH_2004_S5765862/d02-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d03-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d04-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d05-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d06-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d07-x01-y01","196")
useOne("/ALEPH_2004_S5765862/d08-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d09-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d11-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d12-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d13-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d14-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d15-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d16-x01-y01","196")
useOne("/ALEPH_2004_S5765862/d17-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d18-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d19-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d20-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d21-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d22-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d23-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d24-x01-y01","196")
useOne("/ALEPH_2004_S5765862/d25-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d26-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d27-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d28-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d29-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d30-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d31-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d32-x01-y01","196")
useOne("/ALEPH_2004_S5765862/d33-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d34-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d35-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d36-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d37-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d38-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d39-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d40-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d41-x01-y01","196")
useOne("/ALEPH_2004_S5765862/d42-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d43-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d44-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d45-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d46-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d47-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d48-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d49-x01-y01","196")
useOne("/ALEPH_2004_S5765862/d50-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d51-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d54-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d55-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d56-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d57-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d58-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d59-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d60-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d61-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d62-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d63-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d64-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d65-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d66-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d67-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d68-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d69-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d70-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d71-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d72-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d73-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d74-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d75-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d76-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d77-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d78-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d79-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d80-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d81-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d82-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d83-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d84-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d85-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d86-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d87-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d88-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d89-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d90-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d91-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d92-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d93-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d94-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d95-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d96-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d97-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d98-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d99-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d100-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d101-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d102-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d103-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d104-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d105-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d106-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d107-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d108-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d109-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d110-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d111-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d112-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d113-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d114-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d115-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d116-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d117-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d118-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d119-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d120-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d121-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d122-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d123-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d124-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d125-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d126-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d127-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d128-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d129-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d130-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d131-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d132-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d133-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d134-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d135-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d136-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d137-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d138-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d139-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d140-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d141-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d142-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d143-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d144-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d145-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d146-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d147-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d148-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d149-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d150-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d151-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d152-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d153-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d154-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d155-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d156-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d157-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d158-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d159-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d160-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d161-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d162-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d163-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d164-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d165-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d166-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d167-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d168-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d169-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d170-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d172-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d173-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d174-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d175-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d176-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d177-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d178-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d179-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d180-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d181-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d182-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d183-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d184-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d185-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d186-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d187-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d188-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d189-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d190-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d191-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d192-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d193-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d194-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d195-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d196-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d197-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d198-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d199-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d200-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d201-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d202-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d203-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d204-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d205-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d206-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d207-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d208-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d209-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d210-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d211-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d212-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d213-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d214-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d215-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d216-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d217-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d218-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d219-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d220-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d221-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d222-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d223-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d224-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d225-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d226-x01-y01","206")
useOne("/ALEPH_2004_S5765862/d227-x01-y01","91")
useOne("/ALEPH_2004_S5765862/d228-x01-y01","133")
useOne("/ALEPH_2004_S5765862/d229-x01-y01","161")
useOne("/ALEPH_2004_S5765862/d230-x01-y01","172")
useOne("/ALEPH_2004_S5765862/d231-x01-y01","183")
useOne("/ALEPH_2004_S5765862/d232-x01-y01","189")
useOne("/ALEPH_2004_S5765862/d233-x01-y01","200")
useOne("/ALEPH_2004_S5765862/d234-x01-y01","206")
# hadron multiplicities
useOne("/PDG_HADRON_MULTIPLICITIES/d01-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d02-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d03-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d04-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d05-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d06-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d07-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d08-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d09-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d13-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d15-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d17-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d18-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d19-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d20-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d21-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d22-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d23-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d25-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d31-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d38-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d39-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d40-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d44-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d45-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d46-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d47-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d48-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d49-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d50-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d51-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d53-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d54-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES/d01-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d02-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d03-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d04-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d05-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d06-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d07-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d08-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d09-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d13-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d15-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d18-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d19-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d20-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d21-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d22-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d31-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d33-x01-y01","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d34-x01-y01","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d38-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d39-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d44-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d46-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d47-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d48-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d50-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d51-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES/d01-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d02-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d03-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d04-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d05-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d06-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d07-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d08-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d09-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d10-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d11-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d12-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d13-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d14-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d15-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d16-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d17-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d18-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d19-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d20-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d21-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d23-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d24-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d25-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d26-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d27-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d28-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d29-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d30-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d31-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d32-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d34-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d35-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d36-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d37-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d38-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d39-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d40-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d41-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d42-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d43-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d44-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d45-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d46-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d47-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d48-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d49-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d50-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d51-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d52-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d54-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES/d01-x01-y04","177")
useOne("/PDG_HADRON_MULTIPLICITIES/d03-x01-y04","177")
useOne("/PDG_HADRON_MULTIPLICITIES/d04-x01-y04","177")
useOne("/PDG_HADRON_MULTIPLICITIES/d38-x01-y04","177")
useOne("/PDG_HADRON_MULTIPLICITIES/d39-x01-y04","177")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d02-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d03-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d04-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d05-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d06-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d07-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d08-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d09-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d13-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d15-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d17-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d18-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d19-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d20-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d21-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d22-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d23-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d25-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d31-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d38-x01-y01","10" )
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d39-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d40-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d44-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d45-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d46-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d47-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d48-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d49-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d50-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d51-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d53-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d54-x01-y01","10")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d02-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d03-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d04-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d05-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d06-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d07-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d08-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d09-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d13-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d15-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d18-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d19-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d20-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d21-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d22-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d31-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d33-x01-y01","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d34-x01-y01","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d38-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d39-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d44-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d46-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d47-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d48-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d50-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d51-x01-y02","35")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d02-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d03-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d04-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d05-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d06-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d07-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d08-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d09-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d10-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d11-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d12-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d13-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d14-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d15-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d16-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d17-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d18-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d19-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d20-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d21-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d23-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d24-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d25-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d26-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d27-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d28-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d29-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d30-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d31-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d32-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d34-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d35-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d36-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d37-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d38-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d39-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d40-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d41-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d42-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d43-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d44-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d45-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d46-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d47-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d48-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d49-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d50-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d51-x01-y03","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d52-x01-y01","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d54-x01-y02","91")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d03-x01-y04","177")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d04-x01-y04","177")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d38-x01-y04","177")
useOne("/PDG_HADRON_MULTIPLICITIES_RATIOS/d39-x01-y04","177")
+# AMY analysis
+useOne("/AMY_1990_I295160/d01-x01-y01","50")
+useOne("/AMY_1990_I295160/d01-x01-y02","52")
+useOne("/AMY_1990_I295160/d01-x01-y03","55")
+useOne("/AMY_1990_I295160/d01-x01-y04","56")
+useOne("/AMY_1990_I295160/d01-x01-y05","57")
+useOne("/AMY_1990_I295160/d01-x01-y06","60")
+useOne("/AMY_1990_I295160/d01-x01-y07","60.8")
+useOne("/AMY_1990_I295160/d01-x01-y08","61.4")
+useOne("/AMY_1990_I295160/d01-x01-y09","57")
+useOne("/AMY_1990_I295160/d02-x02-y01","57")
+merge("/AMY_1990_I295160/d02-x01-y01")
+merge("/JADE_1983_I190818/d01-x01-y01")
+useOne("/PLUTO_1980_I154270/d01-x02-y01","30.75")
+merge("/PLUTO_1980_I154270/d01-x01-y01")
+merge("/TASSO_1989_I277658/d02-x01-y01")
+useOne("/TASSO_1989_I277658/d05-x01-y01","14")
+useOne("/TASSO_1989_I277658/d05-x01-y02","22")
+useOne("/TASSO_1989_I277658/d05-x01-y03","34.8")
+useOne("/TASSO_1989_I277658/d05-x01-y04","43.6")
# Choose output file
name = args[0]+".yoda"
# output the yoda file
yoda.writeYODA(outhistos,name)
sys.exit(0)
diff --git a/src/defaults/Shower.in b/src/defaults/Shower.in
--- a/src/defaults/Shower.in
+++ b/src/defaults/Shower.in
@@ -1,338 +1,339 @@
# -*- ThePEG-repository -*-
############################################################
# Setup of default parton shower
#
# Useful switches for users are marked near the top of
# this file.
#
# Don't edit this file directly, but reset the switches
# in your own input files!
############################################################
library HwMPI.so
library HwShower.so
library HwMatching.so
mkdir /Herwig/Shower
cd /Herwig/Shower
create Herwig::QTildeShowerHandler ShowerHandler
newdef ShowerHandler:MPIHandler /Herwig/UnderlyingEvent/MPIHandler
newdef ShowerHandler:RemDecayer /Herwig/Partons/RemnantDecayer
# use LO PDFs for Shower, can be changed later
newdef ShowerHandler:PDFA /Herwig/Partons/ShowerLOPDF
newdef ShowerHandler:PDFB /Herwig/Partons/ShowerLOPDF
newdef ShowerHandler:PDFARemnant /Herwig/Partons/RemnantPDF
newdef ShowerHandler:PDFBRemnant /Herwig/Partons/RemnantPDF
#####################################
# initial setup, don't change these!
#####################################
create Herwig::SplittingGenerator SplittingGenerator
create Herwig::ShowerAlphaQCD AlphaQCD
create Herwig::ShowerAlphaQED AlphaQED
set AlphaQED:CouplingSource Thompson
create Herwig::ShowerAlphaQED AlphaEW
set AlphaEW:CouplingSource MZ
create Herwig::QTildeModel ShowerModel
create Herwig::QTildeFinder PartnerFinder
newdef PartnerFinder:PartnerMethod 1
newdef PartnerFinder:ScaleChoice 1
create Herwig::QTildeReconstructor KinematicsReconstructor
newdef KinematicsReconstructor:ReconstructionOption Colour3
newdef KinematicsReconstructor:InitialStateReconOption SofterFraction
newdef KinematicsReconstructor:InitialInitialBoostOption LongTransBoost
newdef /Herwig/Partons/RemnantDecayer:AlphaS AlphaQCD
newdef /Herwig/Partons/RemnantDecayer:AlphaEM AlphaQED
newdef ShowerModel:PartnerFinder PartnerFinder
newdef ShowerModel:KinematicsReconstructor KinematicsReconstructor
newdef ShowerHandler:ShowerModel ShowerModel
newdef ShowerHandler:SplittingGenerator SplittingGenerator
newdef ShowerHandler:Interactions QEDQCD
newdef ShowerHandler:SpinCorrelations Yes
newdef ShowerHandler:SoftCorrelations Singular
##################################################################
# Intrinsic pT
#
# Recommended:
# 1.9 GeV for Tevatron W/Z production.
# 2.1 GeV for LHC W/Z production at 10 TeV
# 2.2 GeV for LHC W/Z production at 14 TeV
#
# Set all parameters to 0 to disable
##################################################################
newdef ShowerHandler:IntrinsicPtGaussian 1.3*GeV
newdef ShowerHandler:IntrinsicPtBeta 0
newdef ShowerHandler:IntrinsicPtGamma 0*GeV
newdef ShowerHandler:IntrinsicPtIptmax 0*GeV
#############################################################
# Set up truncated shower handler.
#############################################################
create Herwig::PowhegShowerHandler PowhegShowerHandler
set PowhegShowerHandler:MPIHandler /Herwig/UnderlyingEvent/MPIHandler
set PowhegShowerHandler:RemDecayer /Herwig/Partons/RemnantDecayer
newdef PowhegShowerHandler:PDFA /Herwig/Partons/ShowerLOPDF
newdef PowhegShowerHandler:PDFB /Herwig/Partons/ShowerLOPDF
newdef PowhegShowerHandler:PDFARemnant /Herwig/Partons/RemnantPDF
newdef PowhegShowerHandler:PDFBRemnant /Herwig/Partons/RemnantPDF
newdef PowhegShowerHandler:MPIHandler /Herwig/UnderlyingEvent/MPIHandler
newdef PowhegShowerHandler:RemDecayer /Herwig/Partons/RemnantDecayer
newdef PowhegShowerHandler:PDFA /Herwig/Partons/ShowerLOPDF
newdef PowhegShowerHandler:PDFB /Herwig/Partons/ShowerLOPDF
newdef PowhegShowerHandler:PDFARemnant /Herwig/Partons/RemnantPDF
newdef PowhegShowerHandler:PDFBRemnant /Herwig/Partons/RemnantPDF
newdef PowhegShowerHandler:ShowerModel ShowerModel
newdef PowhegShowerHandler:SplittingGenerator SplittingGenerator
newdef PowhegShowerHandler:Interactions QEDQCD
newdef PowhegShowerHandler:SpinCorrelations Yes
newdef PowhegShowerHandler:SoftCorrelations Singular
newdef PowhegShowerHandler:IntrinsicPtGaussian 1.3*GeV
newdef PowhegShowerHandler:IntrinsicPtBeta 0
newdef PowhegShowerHandler:IntrinsicPtGamma 0*GeV
newdef PowhegShowerHandler:IntrinsicPtIptmax 0*GeV
newdef PowhegShowerHandler:ReconstructionOption OffShell3
#############################################################
# End of interesting user servicable section.
#
# Anything that follows below should only be touched if you
# know what you're doing.
#
# Really.
#############################################################
#
# a few default values
newdef ShowerHandler:MECorrMode 1
newdef ShowerHandler:ReconstructionOption OffShell3
newdef AlphaQCD:ScaleFactor 1.0
newdef AlphaQCD:NPAlphaS 2
newdef AlphaQCD:Qmin 0.935
newdef AlphaQCD:NumberOfLoops 2
newdef AlphaQCD:InputOption 1
newdef AlphaQCD:AlphaMZ 0.134
#
#
# Lets set up all the splittings
create Herwig::HalfHalfOneSplitFn QtoQGammaSplitFn
set QtoQGammaSplitFn:InteractionType QED
set QtoQGammaSplitFn:ColourStructure ChargedChargedNeutral
set QtoQGammaSplitFn:AngularOrdered Yes
create Herwig::HalfHalfOneSplitFn QtoQGSplitFn
newdef QtoQGSplitFn:InteractionType QCD
newdef QtoQGSplitFn:ColourStructure TripletTripletOctet
set QtoQGSplitFn:AngularOrdered Yes
create Herwig::OneOneOneSplitFn GtoGGSplitFn
newdef GtoGGSplitFn:InteractionType QCD
newdef GtoGGSplitFn:ColourStructure OctetOctetOctet
set GtoGGSplitFn:AngularOrdered Yes
create Herwig::OneHalfHalfSplitFn GtoQQbarSplitFn
newdef GtoQQbarSplitFn:InteractionType QCD
newdef GtoQQbarSplitFn:ColourStructure OctetTripletTriplet
set GtoQQbarSplitFn:AngularOrdered Yes
create Herwig::OneHalfHalfSplitFn GammatoQQbarSplitFn
newdef GammatoQQbarSplitFn:InteractionType QED
newdef GammatoQQbarSplitFn:ColourStructure NeutralChargedCharged
set GammatoQQbarSplitFn:AngularOrdered Yes
create Herwig::HalfOneHalfSplitFn QtoGQSplitFn
newdef QtoGQSplitFn:InteractionType QCD
newdef QtoGQSplitFn:ColourStructure TripletOctetTriplet
set QtoGQSplitFn:AngularOrdered Yes
create Herwig::HalfOneHalfSplitFn QtoGammaQSplitFn
newdef QtoGammaQSplitFn:InteractionType QED
newdef QtoGammaQSplitFn:ColourStructure ChargedNeutralCharged
set QtoGammaQSplitFn:AngularOrdered Yes
create Herwig::HalfHalfOneEWSplitFn QtoQWZSplitFn
newdef QtoQWZSplitFn:InteractionType EW
newdef QtoQWZSplitFn:ColourStructure EW
#
# Now the Sudakovs
create Herwig::QTildeSudakov SudakovCommon
newdef SudakovCommon:Alpha AlphaQCD
newdef SudakovCommon:cutoffKinScale 0.0*GeV
newdef SudakovCommon:PDFmax 1.0
newdef SudakovCommon:CutOffOption pT
newdef SudakovCommon:pTmin 1.67*GeV
cp SudakovCommon QtoQGSudakov
newdef QtoQGSudakov:SplittingFunction QtoQGSplitFn
newdef QtoQGSudakov:PDFmax 1.9
cp SudakovCommon QtoQGammaSudakov
set QtoQGammaSudakov:SplittingFunction QtoQGammaSplitFn
set QtoQGammaSudakov:Alpha AlphaQED
set QtoQGammaSudakov:PDFmax 1.9
cp QtoQGammaSudakov LtoLGammaSudakov
cp SudakovCommon QtoQWZSudakov
set QtoQWZSudakov:SplittingFunction QtoQWZSplitFn
set QtoQWZSudakov:Alpha AlphaEW
set QtoQWZSudakov:PDFmax 1.9
cp QtoQWZSudakov LtoLWZSudakov
cp SudakovCommon GtoGGSudakov
newdef GtoGGSudakov:SplittingFunction GtoGGSplitFn
newdef GtoGGSudakov:PDFmax 2.0
cp SudakovCommon GtoQQbarSudakov
newdef GtoQQbarSudakov:SplittingFunction GtoQQbarSplitFn
newdef GtoQQbarSudakov:PDFmax 120.0
cp SudakovCommon GammatoQQbarSudakov
newdef GammatoQQbarSudakov:SplittingFunction GammatoQQbarSplitFn
+set GammatoQQbarSudakov:Alpha AlphaQED
newdef GammatoQQbarSudakov:PDFmax 120.0
cp SudakovCommon GtobbbarSudakov
newdef GtobbbarSudakov:SplittingFunction GtoQQbarSplitFn
newdef GtobbbarSudakov:PDFmax 40000.0
cp SudakovCommon GtoccbarSudakov
newdef GtoccbarSudakov:SplittingFunction GtoQQbarSplitFn
newdef GtoccbarSudakov:PDFmax 2000.0
cp SudakovCommon QtoGQSudakov
newdef QtoGQSudakov:SplittingFunction QtoGQSplitFn
cp SudakovCommon QtoGammaQSudakov
newdef QtoGammaQSudakov:SplittingFunction QtoGammaQSplitFn
cp SudakovCommon utoGuSudakov
newdef utoGuSudakov:SplittingFunction QtoGQSplitFn
newdef utoGuSudakov:PDFFactor OverOneMinusZ
newdef utoGuSudakov:PDFmax 5.0
cp SudakovCommon dtoGdSudakov
newdef dtoGdSudakov:SplittingFunction QtoGQSplitFn
newdef dtoGdSudakov:PDFFactor OverOneMinusZ
#
# Now add the final splittings
#
do SplittingGenerator:AddFinalSplitting u->u,g; QtoQGSudakov
do SplittingGenerator:AddFinalSplitting d->d,g; QtoQGSudakov
do SplittingGenerator:AddFinalSplitting s->s,g; QtoQGSudakov
do SplittingGenerator:AddFinalSplitting c->c,g; QtoQGSudakov
do SplittingGenerator:AddFinalSplitting b->b,g; QtoQGSudakov
do SplittingGenerator:AddFinalSplitting t->t,g; QtoQGSudakov
#
do SplittingGenerator:AddFinalSplitting g->g,g; GtoGGSudakov
#
do SplittingGenerator:AddFinalSplitting g->u,ubar; GtoQQbarSudakov
do SplittingGenerator:AddFinalSplitting g->d,dbar; GtoQQbarSudakov
do SplittingGenerator:AddFinalSplitting g->s,sbar; GtoQQbarSudakov
do SplittingGenerator:AddFinalSplitting g->c,cbar; GtoccbarSudakov
do SplittingGenerator:AddFinalSplitting g->b,bbar; GtobbbarSudakov
do SplittingGenerator:AddFinalSplitting g->t,tbar; GtoQQbarSudakov
#
do SplittingGenerator:AddFinalSplitting gamma->u,ubar; GammatoQQbarSudakov
do SplittingGenerator:AddFinalSplitting gamma->d,dbar; GammatoQQbarSudakov
do SplittingGenerator:AddFinalSplitting gamma->s,sbar; GammatoQQbarSudakov
do SplittingGenerator:AddFinalSplitting gamma->c,cbar; GammatoQQbarSudakov
do SplittingGenerator:AddFinalSplitting gamma->b,bbar; GammatoQQbarSudakov
do SplittingGenerator:AddFinalSplitting gamma->t,tbar; GammatoQQbarSudakov
do SplittingGenerator:AddFinalSplitting gamma->e-,e+; GammatoQQbarSudakov
do SplittingGenerator:AddFinalSplitting gamma->mu-,mu+; GammatoQQbarSudakov
do SplittingGenerator:AddFinalSplitting gamma->tau-,tau+; GammatoQQbarSudakov
#
do SplittingGenerator:AddFinalSplitting u->u,gamma; QtoQGammaSudakov
do SplittingGenerator:AddFinalSplitting d->d,gamma; QtoQGammaSudakov
do SplittingGenerator:AddFinalSplitting s->s,gamma; QtoQGammaSudakov
do SplittingGenerator:AddFinalSplitting c->c,gamma; QtoQGammaSudakov
do SplittingGenerator:AddFinalSplitting b->b,gamma; QtoQGammaSudakov
do SplittingGenerator:AddFinalSplitting t->t,gamma; QtoQGammaSudakov
do SplittingGenerator:AddFinalSplitting e-->e-,gamma; LtoLGammaSudakov
do SplittingGenerator:AddFinalSplitting mu-->mu-,gamma; LtoLGammaSudakov
do SplittingGenerator:AddFinalSplitting tau-->tau-,gamma; LtoLGammaSudakov
#
# Now lets add the initial splittings. Remember the form a->b,c; means
# that the current particle b is given and we backward branch to new
# particle a which is initial state and new particle c which is final state
#
do SplittingGenerator:AddInitialSplitting u->u,g; QtoQGSudakov
do SplittingGenerator:AddInitialSplitting d->d,g; QtoQGSudakov
do SplittingGenerator:AddInitialSplitting s->s,g; QtoQGSudakov
do SplittingGenerator:AddInitialSplitting c->c,g; QtoQGSudakov
do SplittingGenerator:AddInitialSplitting b->b,g; QtoQGSudakov
do SplittingGenerator:AddInitialSplitting u->u,gamma; QtoQGammaSudakov
do SplittingGenerator:AddInitialSplitting d->d,gamma; QtoQGammaSudakov
do SplittingGenerator:AddInitialSplitting s->s,gamma; QtoQGammaSudakov
do SplittingGenerator:AddInitialSplitting c->c,gamma; QtoQGammaSudakov
do SplittingGenerator:AddInitialSplitting b->b,gamma; QtoQGammaSudakov
do SplittingGenerator:AddInitialSplitting t->t,gamma; QtoQGammaSudakov
do SplittingGenerator:AddInitialSplitting g->g,g; GtoGGSudakov
#
do SplittingGenerator:AddInitialSplitting g->d,dbar; GtoQQbarSudakov
do SplittingGenerator:AddInitialSplitting g->u,ubar; GtoQQbarSudakov
do SplittingGenerator:AddInitialSplitting g->s,sbar; GtoQQbarSudakov
do SplittingGenerator:AddInitialSplitting g->c,cbar; GtoccbarSudakov
do SplittingGenerator:AddInitialSplitting g->b,bbar; GtobbbarSudakov
#
do SplittingGenerator:AddInitialSplitting gamma->d,dbar; GammatoQQbarSudakov
do SplittingGenerator:AddInitialSplitting gamma->u,ubar; GammatoQQbarSudakov
do SplittingGenerator:AddInitialSplitting gamma->s,sbar; GammatoQQbarSudakov
do SplittingGenerator:AddInitialSplitting gamma->c,cbar; GammatoQQbarSudakov
do SplittingGenerator:AddInitialSplitting gamma->b,bbar; GammatoQQbarSudakov
#
do SplittingGenerator:AddInitialSplitting d->g,d; dtoGdSudakov
do SplittingGenerator:AddInitialSplitting u->g,u; utoGuSudakov
do SplittingGenerator:AddInitialSplitting s->g,s; QtoGQSudakov
do SplittingGenerator:AddInitialSplitting c->g,c; QtoGQSudakov
do SplittingGenerator:AddInitialSplitting b->g,b; QtoGQSudakov
do SplittingGenerator:AddInitialSplitting dbar->g,dbar; dtoGdSudakov
do SplittingGenerator:AddInitialSplitting ubar->g,ubar; utoGuSudakov
do SplittingGenerator:AddInitialSplitting sbar->g,sbar; QtoGQSudakov
do SplittingGenerator:AddInitialSplitting cbar->g,cbar; QtoGQSudakov
do SplittingGenerator:AddInitialSplitting bbar->g,bbar; QtoGQSudakov
#
do SplittingGenerator:AddInitialSplitting d->gamma,d; QtoGammaQSudakov
do SplittingGenerator:AddInitialSplitting u->gamma,u; QtoGammaQSudakov
do SplittingGenerator:AddInitialSplitting s->gamma,s; QtoGammaQSudakov
do SplittingGenerator:AddInitialSplitting c->gamma,c; QtoGammaQSudakov
do SplittingGenerator:AddInitialSplitting b->gamma,b; QtoGammaQSudakov
do SplittingGenerator:AddInitialSplitting dbar->gamma,dbar; QtoGammaQSudakov
do SplittingGenerator:AddInitialSplitting ubar->gamma,ubar; QtoGammaQSudakov
do SplittingGenerator:AddInitialSplitting sbar->gamma,sbar; QtoGammaQSudakov
do SplittingGenerator:AddInitialSplitting cbar->gamma,cbar; QtoGammaQSudakov
do SplittingGenerator:AddInitialSplitting bbar->gamma,bbar; QtoGammaQSudakov
#
# Electroweak
#
do SplittingGenerator:AddFinalSplitting u->u,Z0; QtoQWZSudakov
do SplittingGenerator:AddFinalSplitting d->d,Z0; QtoQWZSudakov
do SplittingGenerator:AddFinalSplitting s->s,Z0; QtoQWZSudakov
do SplittingGenerator:AddFinalSplitting c->c,Z0; QtoQWZSudakov
do SplittingGenerator:AddFinalSplitting b->b,Z0; QtoQWZSudakov
do SplittingGenerator:AddFinalSplitting t->t,Z0; QtoQWZSudakov
do SplittingGenerator:AddInitialSplitting u->u,Z0; QtoQWZSudakov
do SplittingGenerator:AddInitialSplitting d->d,Z0; QtoQWZSudakov
do SplittingGenerator:AddInitialSplitting s->s,Z0; QtoQWZSudakov
do SplittingGenerator:AddInitialSplitting c->c,Z0; QtoQWZSudakov
do SplittingGenerator:AddInitialSplitting b->b,Z0; QtoQWZSudakov
do SplittingGenerator:AddInitialSplitting t->t,Z0; QtoQWZSudakov
do SplittingGenerator:AddFinalSplitting u->d,W+; QtoQWZSudakov
do SplittingGenerator:AddFinalSplitting c->s,W+; QtoQWZSudakov
do SplittingGenerator:AddFinalSplitting d->u,W-; QtoQWZSudakov
do SplittingGenerator:AddFinalSplitting s->c,W-; QtoQWZSudakov
do SplittingGenerator:AddInitialSplitting u->d,W+; QtoQWZSudakov
do SplittingGenerator:AddInitialSplitting c->s,W+; QtoQWZSudakov
do SplittingGenerator:AddInitialSplitting d->u,W-; QtoQWZSudakov
do SplittingGenerator:AddInitialSplitting s->c,W-; QtoQWZSudakov

File Metadata

Mime Type
text/x-diff
Expires
Sat, Dec 21, 4:51 PM (15 h, 25 s)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
4023528
Default Alt Text
(676 KB)

Event Timeline