18 #ifndef Pythia8_JetMatching_H
19 #define Pythia8_JetMatching_H
22 #include "Pythia8/Pythia.h"
23 #include "Pythia8Plugins/GeneratorInput.h"
29 class HJSlowJet:
public SlowJet {
33 HJSlowJet(
int powerIn,
double Rin,
double pTjetMinIn = 0.,
34 double etaMaxIn = 25.,
int selectIn = 1,
int massSetIn = 2,
35 SlowJetHook* sjHookPtrIn = 0,
bool useFJcoreIn =
false,
36 bool useStandardRin =
true) :
37 SlowJet(powerIn, Rin, pTjetMinIn, etaMaxIn, selectIn, massSetIn,
38 sjHookPtrIn, useFJcoreIn, useStandardRin) {}
52 void HJSlowJet::findNext() {
60 for (
int i = 1; i < clSize; ++i) {
61 for (
int j = 0; j < i; ++j) {
62 if (dij[i*(i-1)/2 + j] < dMin) {
65 dMin = dij[i*(i-1)/2 + j];
90 JetMatching() : cellJet(NULL), slowJet(NULL), slowJetHard(NULL),
93 if (cellJet)
delete cellJet;
94 if (slowJet)
delete slowJet;
95 if (slowJetHard)
delete slowJetHard;
96 if (hjSlowJet)
delete hjSlowJet;
100 cout <<
"\n *------- JetMatching Error and Warning Messages Statistics"
101 <<
" -----------------------------------------------------* \n"
104 <<
" | times message "
110 map<string, int>::iterator messageEntry = messages.begin();
111 if (messageEntry == messages.end())
112 cout <<
" | 0 no errors or warnings to report "
114 while (messageEntry != messages.end()) {
116 string temp = messageEntry->first;
117 int len = temp.length();
118 temp.insert( len, max(0, 102 - len),
' ');
119 cout <<
" | " << setw(6) << messageEntry->second <<
" "
127 <<
" *------- End JetMatching Error and Warning Messages "
128 <<
"Statistics -------------------------------------------------* "
133 virtual bool initAfterBeams() = 0;
136 bool canVetoProcessLevel() {
return doMerge; }
137 bool doVetoProcessLevel(
Event& process) {
138 eventProcessOrig = process;
143 bool canVetoPartonLevelEarly() {
return doMerge; }
144 bool doVetoPartonLevelEarly(
const Event& event);
147 int numberVetoStep() {
return 1;}
148 bool canVetoStep() {
return false; }
149 bool doVetoStep(
int,
int,
int,
const Event& ) {
return false; }
156 virtual void sortIncomingProcess(
const Event &)=0;
157 virtual void jetAlgorithmInput(
const Event &,
int)=0;
158 virtual void runJetAlgorithm()=0;
159 virtual bool matchPartonsToJets(
int)=0;
160 virtual int matchPartonsToJetsLight()=0;
161 virtual int matchPartonsToJetsHeavy()=0;
164 void errorMsg(
string messageIn) {
166 int times = messages[messageIn];
167 ++messages[messageIn];
169 if (times < TIMESTOPRINT) cout <<
" PYTHIA " << messageIn << endl;
175 static const bool MATCHINGDEBUG, MATCHINGCHECK;
177 enum vetoStatus { NONE, LESS_JETS, MORE_JETS, HARD_JET,
178 UNMATCHED_PARTON, INCLUSIVE_VETO };
179 enum partonTypes { ID_CHARM=4, ID_BOT=5, ID_TOP=6, ID_LEPMIN=11,
180 ID_LEPMAX=16, ID_GLUON=21, ID_PHOTON=22 };
193 double eTjetMin, coneRadius, etaJetMax, etaJetMaxAlgo;
198 SlowJet* slowJetHard;
199 HJSlowJet* hjSlowJet;
208 Event eventProcessOrig, eventProcess, workEventJet;
211 vector<int> typeIdx[3];
216 vector<Vec4> jetMomenta;
220 double eTseed, eTthreshold;
223 int jetAllow, jetMatch, exclusiveMode;
224 double coneMatchLight, coneRadiusHeavy, coneMatchHeavy;
231 map<string, int> messages;
233 static const int TIMESTOPRINT = 1;
250 bool initAfterBeams();
255 void sortIncomingProcess(
const Event &);
256 void jetAlgorithmInput(
const Event &,
int);
257 void runJetAlgorithm();
258 bool matchPartonsToJets(
int);
259 int matchPartonsToJetsLight();
260 int matchPartonsToJetsHeavy();
263 void sortTypeIdx(vector < int > &vecIn);
266 static const double GHOSTENERGY, ZEROTHRESHOLD;
283 bool initAfterBeams();
286 bool canVetoProcessLevel() {
return doMerge; }
287 bool doVetoProcessLevel(
Event& process);
290 int numberVetoStep() {
return 1;}
291 bool canVetoStep() {
return doShowerKt; }
292 bool doVetoStep(
int,
int,
int,
const Event& );
299 vector<double> getDJR() {
return DJR;}
300 pair<int,int> nMEpartons() {
return nMEpartonsSave;}
306 Event getWorkEventJet() {
return workEventJetSave; }
307 Event getProcessSubset() {
return processSubsetSave; }
308 bool getExclusive() {
return exclusive; }
309 double getPTfirst() {
return pTfirstSave; }
316 void sortIncomingProcess(
const Event &);
317 void jetAlgorithmInput(
const Event &,
int);
318 void runJetAlgorithm();
319 bool matchPartonsToJets(
int);
320 int matchPartonsToJetsLight();
321 int matchPartonsToJetsHeavy();
322 int matchPartonsToJetsOther();
323 bool doShowerKtVeto(
double pTfirst);
326 void clearDJR() { DJR.resize(0);}
327 void setDJR(
const Event& event);
329 void clear_nMEpartons() { nMEpartonsSave.first = nMEpartonsSave.second =-1;}
330 void set_nMEpartons(
const int nOrig,
const int nMatch) {
332 nMEpartonsSave.first = nOrig;
333 nMEpartonsSave.second = nMatch;
344 Event processSubsetSave;
345 Event workEventJetSave;
353 vector<int> origTypeIdx[3];
355 double qCut, qCutSq, clFact;
358 double qCutME, qCutMESq;
364 pair<int,int> nMEpartonsSave;
377 const bool JetMatching::MATCHINGDEBUG =
false;
378 const bool JetMatching::MATCHINGCHECK =
false;
384 inline bool JetMatching::doVetoPartonLevelEarly(
const Event& event) {
396 sortIncomingProcess(event);
400 if ( doShowerKt )
return false;
405 cout << endl <<
"-------- Begin Madgraph Debug --------" << endl;
407 cout << endl <<
"Original incoming process:";
408 eventProcessOrig.list();
410 cout << endl <<
"Final-state incoming process:";
413 for (
size_t i = 0; i < typeIdx[0].size(); i++)
414 cout << ((i == 0) ?
"Light jets: " :
", ") << setw(3) << typeIdx[0][i];
415 if( typeIdx[0].size()== 0 )
416 cout <<
"Light jets: None";
418 for (
size_t i = 0; i < typeIdx[1].size(); i++)
419 cout << ((i == 0) ?
"\nHeavy jets: " :
", ") << setw(3) << typeIdx[1][i];
420 for (
size_t i = 0; i < typeIdx[2].size(); i++)
421 cout << ((i == 0) ?
"\nOther: " :
", ") << setw(3) << typeIdx[2][i];
423 cout << endl << endl <<
"Event:";
426 cout << endl <<
"Work event:";
431 int iTypeEnd = (typeIdx[2].empty()) ? 2 : 3;
432 for (
int iType = 0; iType < iTypeEnd; iType++) {
436 jetAlgorithmInput(event, iType);
441 cout << endl <<
"Jet algorithm event (iType = " << iType <<
"):";
450 if (matchPartonsToJets(iType) ==
true) {
453 cout << endl <<
"Event vetoed" << endl
454 <<
"---------- End MLM Debug ----------" << endl;
462 cout << endl <<
"Event accepted" << endl
463 <<
"---------- End MLM Debug ----------" << endl;
484 const double JetMatchingAlpgen::GHOSTENERGY = 1e-15;
487 const double JetMatchingAlpgen::ZEROTHRESHOLD = 1e-10;
495 inline void JetMatchingAlpgen::sortTypeIdx(vector < int > &vecIn) {
496 for (
size_t i = 0; i < vecIn.size(); i++) {
498 double vMax = (jetAlgorithm == 1) ?
499 eventProcess[vecIn[i]].eT() :
500 eventProcess[vecIn[i]].pT();
501 for (
size_t j = i + 1; j < vecIn.size(); j++) {
502 double vNow = (jetAlgorithm == 1)
503 ? eventProcess[vecIn[j]].eT() : eventProcess[vecIn[j]].pT();
509 if (jMax != i) swap(vecIn[i], vecIn[jMax]);
518 inline bool JetMatchingAlpgen::initAfterBeams() {
521 doMerge = settingsPtr->flag(
"JetMatching:merge");
522 jetAlgorithm = settingsPtr->mode(
"JetMatching:jetAlgorithm");
523 nJet = settingsPtr->mode(
"JetMatching:nJet");
524 nJetMax = settingsPtr->mode(
"JetMatching:nJetMax");
525 eTjetMin = settingsPtr->parm(
"JetMatching:eTjetMin");
526 coneRadius = settingsPtr->parm(
"JetMatching:coneRadius");
527 etaJetMax = settingsPtr->parm(
"JetMatching:etaJetMax");
528 doShowerKt = settingsPtr->flag(
"JetMatching:doShowerKt");
531 etaJetMaxAlgo = etaJetMax + coneRadius;
534 nEta = settingsPtr->mode(
"JetMatching:nEta");
535 nPhi = settingsPtr->mode(
"JetMatching:nPhi");
536 eTseed = settingsPtr->parm(
"JetMatching:eTseed");
537 eTthreshold = settingsPtr->parm(
"JetMatching:eTthreshold");
540 slowJetPower = settingsPtr->mode(
"JetMatching:slowJetPower");
541 coneMatchLight = settingsPtr->parm(
"JetMatching:coneMatchLight");
542 coneRadiusHeavy = settingsPtr->parm(
"JetMatching:coneRadiusHeavy");
543 if (coneRadiusHeavy < 0.) coneRadiusHeavy = coneRadius;
544 coneMatchHeavy = settingsPtr->parm(
"JetMatching:coneMatchHeavy");
547 jetAllow = settingsPtr->mode(
"JetMatching:jetAllow");
548 jetMatch = settingsPtr->mode(
"JetMatching:jetMatch");
549 exclusiveMode = settingsPtr->mode(
"JetMatching:exclusive");
552 if (!doMerge)
return true;
555 if (exclusiveMode == 2) {
558 if (nJet < 0 || nJetMax < 0) {
559 errorMsg(
"Warning in JetMatchingAlpgen:init: "
560 "missing jet multiplicity information; running in exclusive mode");
565 exclusive = (nJet == nJetMax) ?
false :
true;
570 exclusive = (exclusiveMode == 0) ?
false :
true;
574 if (jetAlgorithm == 1) {
579 int nSel = 2, smear = 0;
580 double resolution = 0.5, upperCut = 2.;
581 cellJet =
new CellJet(etaJetMaxAlgo, nEta, nPhi, nSel,
582 smear, resolution, upperCut, eTthreshold);
585 }
else if (jetAlgorithm == 2) {
586 slowJet =
new SlowJet(slowJetPower, coneRadius, eTjetMin, etaJetMaxAlgo);
590 if (jetAlgorithm == 1 && jetMatch == 2) {
591 errorMsg(
"Warning in JetMatchingAlpgen:init: "
592 "jetMatch = 2 only valid with SlowJet algorithm. "
593 "Reverting to jetMatch = 1");
598 eventProcessOrig.init(
"(eventProcessOrig)", particleDataPtr);
599 eventProcess.init(
"(eventProcess)", particleDataPtr);
600 workEventJet.init(
"(workEventJet)", particleDataPtr);
603 string jetStr = (jetAlgorithm == 1) ?
"CellJet" :
604 (slowJetPower == -1) ?
"anti-kT" :
605 (slowJetPower == 0) ?
"C/A" :
606 (slowJetPower == 1) ?
"kT" :
"unknown";
607 string modeStr = (exclusive) ?
"exclusive" :
"inclusive";
608 stringstream nJetStr, nJetMaxStr;
609 if (nJet >= 0) nJetStr << nJet;
else nJetStr <<
"unknown";
610 if (nJetMax >= 0) nJetMaxStr << nJetMax;
else nJetMaxStr <<
"unknown";
612 <<
" *------- MLM matching parameters -------*" << endl
613 <<
" | nJet | " << setw(14)
614 << nJetStr.str() <<
" |" << endl
615 <<
" | nJetMax | " << setw(14)
616 << nJetMaxStr.str() <<
" |" << endl
617 <<
" | Jet algorithm | " << setw(14)
618 << jetStr <<
" |" << endl
619 <<
" | eTjetMin | " << setw(14)
620 << eTjetMin <<
" |" << endl
621 <<
" | coneRadius | " << setw(14)
622 << coneRadius <<
" |" << endl
623 <<
" | etaJetMax | " << setw(14)
624 << etaJetMax <<
" |" << endl
625 <<
" | jetAllow | " << setw(14)
626 << jetAllow <<
" |" << endl
627 <<
" | jetMatch | " << setw(14)
628 << jetMatch <<
" |" << endl
629 <<
" | coneMatchLight | " << setw(14)
630 << coneMatchLight <<
" |" << endl
631 <<
" | coneRadiusHeavy | " << setw(14)
632 << coneRadiusHeavy <<
" |" << endl
633 <<
" | coneMatchHeavy | " << setw(14)
634 << coneMatchHeavy <<
" |" << endl
635 <<
" | Mode | " << setw(14)
636 << modeStr <<
" |" << endl
637 <<
" *-----------------------------------------*" << endl;
646 inline void JetMatchingAlpgen::sortIncomingProcess(
const Event &event) {
650 omitResonanceDecays(eventProcessOrig,
true);
651 eventProcess = workEvent;
662 for (
int i = 0; i < 3; i++) {
666 for (
int i = 0; i < eventProcess.size(); i++) {
668 if (!eventProcess[i].isFinal())
continue;
672 if (eventProcess[i].
id() == ID_GLUON
673 || (eventProcess[i].idAbs() <= ID_BOT
674 && abs(eventProcess[i].m()) < ZEROTHRESHOLD)) idx = 0;
677 else if (eventProcess[i].idAbs() >= ID_CHARM
678 && eventProcess[i].idAbs() <= ID_TOP) idx = 1;
681 typeIdx[idx].push_back(i);
682 typeSet[idx].insert(eventProcess[i].daughter1());
694 inline void JetMatchingAlpgen::jetAlgorithmInput(
const Event &event,
698 workEventJet = workEvent;
701 for (
int i = 0; i < workEventJet.size(); ++i) {
702 if (!workEventJet[i].isFinal())
continue;
709 int id = workEventJet[i].idAbs();
710 if ( (
id >= ID_LEPMIN &&
id <= ID_LEPMAX) ||
id == ID_TOP
711 ||
id == ID_PHOTON) {
712 workEventJet[i].statusNeg();
718 int idx = workEventJet[i].daughter1();
727 if (typeSet[1].find(idx) != typeSet[1].end() ||
728 typeSet[2].find(idx) != typeSet[2].end()) {
729 workEventJet[i].statusNeg();
736 idx =
event[idx].mother1();
739 }
else if (iType == 1) {
742 if (typeSet[1].find(idx) != typeSet[1].end())
break;
747 workEventJet[i].statusNeg();
752 idx =
event[idx].mother1();
755 }
else if (iType == 2) {
758 if (typeSet[2].find(idx) != typeSet[2].end())
break;
763 workEventJet[i].statusNeg();
768 idx =
event[idx].mother1();
777 for (
int i = 0; i < int(typeIdx[iType].size()); i++) {
779 Vec4 pIn = eventProcess[typeIdx[iType][i]].p();
780 double y = pIn.rap();
781 double phi = pIn.phi();
784 double e = GHOSTENERGY;
785 double e2y = exp(2. * y);
786 double pz = e * (e2y - 1.) / (e2y + 1.);
787 double pt = sqrt(e*e - pz*pz);
788 double px = pt * cos(phi);
789 double py = pt * sin(phi);
790 workEventJet.append( ID_GLUON, 99, 0, 0, 0, 0, 0, 0, px, py, pz, e);
795 int lastIdx = workEventJet.size() - 1;
796 if (abs(y - workEventJet[lastIdx].y()) > ZEROTHRESHOLD ||
797 abs(phi - workEventJet[lastIdx].phi()) > ZEROTHRESHOLD)
798 errorMsg(
"Warning in JetMatchingAlpgen:jetAlgorithmInput: "
799 "ghost particle y/phi mismatch");
810 inline void JetMatchingAlpgen::runJetAlgorithm() {
813 if (jetAlgorithm == 1)
814 cellJet->analyze(workEventJet, eTjetMin, coneRadius, eTseed);
816 slowJet->analyze(workEventJet);
822 int iJet = (jetAlgorithm == 1) ? cellJet->size() - 1:
823 slowJet->sizeJet() - 1;
824 for (
int i = iJet; i > -1; i--) {
825 Vec4 jetMom = (jetAlgorithm == 1) ? cellJet->pMassive(i) :
827 double eta = jetMom.eta();
829 if (abs(eta) > etaJetMax) {
830 if (jetAlgorithm == 2) slowJet->removeJet(i);
833 jetMomenta.push_back(jetMom);
837 reverse(jetMomenta.begin(), jetMomenta.end());
844 inline bool JetMatchingAlpgen::matchPartonsToJets(
int iType) {
848 if (iType == 0)
return (matchPartonsToJetsLight() > 0);
849 else if (iType == 1)
return (matchPartonsToJetsHeavy() > 0);
850 else if (iType == 2)
return false;
867 inline int JetMatchingAlpgen::matchPartonsToJetsLight() {
870 if (jetMomenta.size() < typeIdx[0].size())
return LESS_JETS;
872 if (exclusive && jetMomenta.size() > typeIdx[0].size())
return MORE_JETS;
875 sortTypeIdx(typeIdx[0]);
878 int nParton = typeIdx[0].size();
881 vector < bool > jetAssigned;
882 jetAssigned.assign(jetMomenta.size(),
false);
888 for (
int i = 0; i < nParton; i++) {
889 Vec4 p1 = eventProcess[typeIdx[0][i]].p();
896 for (
int j = 0; j < int(jetMomenta.size()); j++) {
897 if (jetAssigned[j])
continue;
900 double dR = (jetAlgorithm == 1)
901 ? REtaPhi(p1, jetMomenta[j]) : RRapPhi(p1, jetMomenta[j]);
902 if (jMin < 0 || dR < dRmin) {
909 if (jMin >= 0 && dRmin < coneRadius * coneMatchLight) {
914 if (jMin >= nParton)
return HARD_JET;
917 jetAssigned[jMin] =
true;
920 }
else return UNMATCHED_PARTON;
928 for (
int i = workEventJet.size() - nParton;
929 i < workEventJet.size(); i++) {
930 int jMin = slowJet->jetAssignment(i);
936 if (jMin >= nParton)
return HARD_JET;
937 if (jMin < 0 || jetAssigned[jMin])
return UNMATCHED_PARTON;
940 jetAssigned[jMin] =
true;
948 eTpTlightMin = (jetAlgorithm == 1) ? jetMomenta[nParton - 1].eT()
949 : jetMomenta[nParton - 1].pT();
967 inline int JetMatchingAlpgen::matchPartonsToJetsHeavy() {
970 if (jetMomenta.empty())
return NONE;
973 int nParton = typeIdx[1].size();
976 set < int > removeJets;
982 for (
int i = 0; i < nParton; i++) {
983 Vec4 p1 = eventProcess[typeIdx[1][i]].p();
986 for (
int j = 0; j < int(jetMomenta.size()); j++) {
987 double dR = (jetAlgorithm == 1) ?
988 REtaPhi(p1, jetMomenta[j]) : RRapPhi(p1, jetMomenta[j]);
989 if (dR < coneRadiusHeavy * coneMatchHeavy)
990 removeJets.insert(j);
1000 for (
int i = workEventJet.size() - nParton;
1001 i < workEventJet.size(); i++) {
1002 int jMin = slowJet->jetAssignment(i);
1003 if (jMin >= 0) removeJets.insert(jMin);
1009 for (set < int >::reverse_iterator it = removeJets.rbegin();
1010 it != removeJets.rend(); it++)
1011 jetMomenta.erase(jetMomenta.begin() + *it);
1014 if (!jetMomenta.empty()) {
1017 if (exclusive)
return MORE_JETS;
1020 else if (eTpTlightMin >= 0.)
1021 for (
size_t j = 0; j < jetMomenta.size(); j++) {
1023 if ( (jetAlgorithm == 1 && jetMomenta[j].eT() > eTpTlightMin) ||
1024 (jetAlgorithm == 2 && jetMomenta[j].pT() > eTpTlightMin) )
1045 inline bool JetMatchingMadgraph::initAfterBeams() {
1049 processSubsetSave.init(
"(eventProcess)", particleDataPtr);
1050 workEventJetSave.init(
"(workEventJet)", particleDataPtr);
1053 bool setMad = settingsPtr->flag(
"JetMatching:setMad");
1057 string parStr = infoPtr->header(
"MGRunCard");
1058 if (!parStr.empty()) {
1065 if ( par.haveParam(
"xqcut") && par.haveParam(
"maxjetflavor")
1066 && par.haveParam(
"alpsfact") && par.haveParam(
"ickkw") ) {
1067 settingsPtr->flag(
"JetMatching:merge", par.getParam(
"ickkw"));
1068 settingsPtr->parm(
"JetMatching:qCut", par.getParam(
"xqcut"));
1069 settingsPtr->mode(
"JetMatching:nQmatch",
1070 par.getParamAsInt(
"maxjetflavor"));
1071 settingsPtr->parm(
"JetMatching:clFact",
1072 clFact = par.getParam(
"alpsfact"));
1073 if (par.getParamAsInt(
"ickkw") == 0)
1074 errorMsg(
"Error in JetMatchingMadgraph:init: "
1075 "Madgraph file parameters are not set for merging");
1079 errorMsg(
"Warning in JetMatchingMadgraph:init: "
1080 "Madgraph merging parameters not found");
1081 if (!par.haveParam(
"xqcut")) errorMsg(
"Warning in "
1082 "JetMatchingMadgraph:init: No xqcut");
1083 if (!par.haveParam(
"ickkw")) errorMsg(
"Warning in "
1084 "JetMatchingMadgraph:init: No ickkw");
1085 if (!par.haveParam(
"maxjetflavor")) errorMsg(
"Warning in "
1086 "JetMatchingMadgraph:init: No maxjetflavor");
1087 if (!par.haveParam(
"alpsfact")) errorMsg(
"Warning in "
1088 "JetMatchingMadgraph:init: No alpsfact");
1093 doFxFx = settingsPtr->flag(
"JetMatching:doFxFx");
1094 nPartonsNow = settingsPtr->mode(
"JetMatching:nPartonsNow");
1095 qCutME = settingsPtr->parm(
"JetMatching:qCutME");
1096 qCutMESq = pow(qCutME,2);
1099 doMerge = settingsPtr->flag(
"JetMatching:merge");
1100 doShowerKt = settingsPtr->flag(
"JetMatching:doShowerKt");
1101 qCut = settingsPtr->parm(
"JetMatching:qCut");
1102 nQmatch = settingsPtr->mode(
"JetMatching:nQmatch");
1103 clFact = settingsPtr->parm(
"JetMatching:clFact");
1106 jetAlgorithm = settingsPtr->mode(
"JetMatching:jetAlgorithm");
1107 nJetMax = settingsPtr->mode(
"JetMatching:nJetMax");
1108 eTjetMin = settingsPtr->parm(
"JetMatching:eTjetMin");
1109 coneRadius = settingsPtr->parm(
"JetMatching:coneRadius");
1110 etaJetMax = settingsPtr->parm(
"JetMatching:etaJetMax");
1111 slowJetPower = settingsPtr->mode(
"JetMatching:slowJetPower");
1114 jetAllow = settingsPtr->mode(
"JetMatching:jetAllow");
1115 exclusiveMode = settingsPtr->mode(
"JetMatching:exclusive");
1116 qCutSq = pow(qCut,2);
1117 etaJetMaxAlgo = etaJetMax;
1120 performVeto = settingsPtr->flag(
"JetMatching:doVeto");
1123 if (!doMerge)
return true;
1126 if (exclusiveMode == 2) {
1130 errorMsg(
"Warning in JetMatchingMadgraph:init: "
1131 "missing jet multiplicity information; running in exclusive mode");
1141 slowJet =
new SlowJet(slowJetPower, coneRadius, eTjetMin,
1142 etaJetMaxAlgo, 2, 2, NULL,
false);
1147 slowJetHard =
new SlowJet(slowJetPower, coneRadius, qCutME,
1148 etaJetMaxAlgo, 2, 2, NULL,
false);
1151 slowJetDJR =
new SlowJet(slowJetPower, coneRadius, qCutME,
1152 etaJetMaxAlgo, 2, 2, NULL,
false);
1155 hjSlowJet =
new HJSlowJet(slowJetPower, coneRadius, 0.0,
1156 100.0, 1, 2, NULL,
false,
true);
1159 eventProcessOrig.init(
"(eventProcessOrig)", particleDataPtr);
1160 eventProcess.init(
"(eventProcess)", particleDataPtr);
1161 workEventJet.init(
"(workEventJet)", particleDataPtr);
1164 string jetStr = (jetAlgorithm == 1) ?
"CellJet" :
1165 (slowJetPower == -1) ?
"anti-kT" :
1166 (slowJetPower == 0) ?
"C/A" :
1167 (slowJetPower == 1) ?
"kT" :
"unknown";
1168 string modeStr = (exclusiveMode) ?
"exclusive" :
"inclusive";
1170 <<
" *----- Madgraph matching parameters -----*" << endl
1171 <<
" | qCut | " << setw(14)
1172 << qCut <<
" |" << endl
1173 <<
" | nQmatch | " << setw(14)
1174 << nQmatch <<
" |" << endl
1175 <<
" | clFact | " << setw(14)
1176 << clFact <<
" |" << endl
1177 <<
" | Jet algorithm | " << setw(14)
1178 << jetStr <<
" |" << endl
1179 <<
" | eTjetMin | " << setw(14)
1180 << eTjetMin <<
" |" << endl
1181 <<
" | etaJetMax | " << setw(14)
1182 << etaJetMax <<
" |" << endl
1183 <<
" | jetAllow | " << setw(14)
1184 << jetAllow <<
" |" << endl
1185 <<
" | Mode | " << setw(14)
1186 << modeStr <<
" |" << endl
1187 <<
" *-----------------------------------------*" << endl;
1196 inline bool JetMatchingMadgraph::doVetoProcessLevel(
Event& process) {
1198 eventProcessOrig = process;
1205 sortIncomingProcess(process);
1208 if ( !doFxFx &&
int(typeIdx[0].size()) > nJetMax )
1210 if ( doFxFx && npNLO() < nJetMax &&
int(typeIdx[0].size()) > nJetMax )
1220 inline bool JetMatchingMadgraph::doVetoStep(
int iPos,
int nISR,
int nFSR,
1221 const Event& event) {
1224 if ( !doShowerKt )
return false;
1227 if ( nISR + nFSR > 1 )
return false;
1230 if (iPos == 5)
return false;
1234 sortIncomingProcess(event);
1237 double pTfirst = 0.;
1240 vector<int> weakBosons;
1241 for (
int i = 0; i <
event.size(); i++) {
1242 if ( event[i].
id() == 22
1243 &&
event[i].id() == 23
1244 &&
event[i].idAbs() == 24)
1245 weakBosons.push_back(i);
1248 for (
int i = workEvent.size()-1; i > 0; --i) {
1249 if ( workEvent[i].isFinal() && workEvent[i].colType() != 0
1250 && (workEvent[i].statusAbs() == 43 || workEvent[i].statusAbs() == 51)) {
1254 bool QCDemission =
true;
1257 int iPosOld = workEvent[i].daughter1();
1258 for (
int j = 0; i < int(weakBosons.size()); ++i)
1259 if ( event[iPosOld].isAncestor(j)) {
1260 QCDemission =
false;
1265 pTfirst = workEvent[i].pT();
1272 pTfirstSave = pTfirst;
1274 if (!performVeto)
return false;
1277 if ( doShowerKtVeto(pTfirst) )
return true;
1286 inline bool JetMatchingMadgraph::doShowerKtVeto(
double pTfirst) {
1289 if ( !doShowerKt )
return false;
1292 bool doVeto =
false;
1296 int nParton = typeIdx[0].size();
1297 double pTminME=1e10;
1298 for (
int i = 0; i < nParton; ++i)
1299 pTminME = min(pTminME,eventProcess[typeIdx[0][i]].pT());
1302 if ( nParton > 0 && pow(pTminME,2) < qCutSq ) doVeto =
true;
1306 if ( exclusive && pow(pTfirst,2) > qCutSq ) {
1310 }
else if ( !exclusive && nParton > 0 && pTfirst > pTminME ) {
1323 inline void JetMatchingMadgraph::setDJR(
const Event& event) {
1327 vector<double> result;
1330 if (!slowJetDJR->setup(event) ) {
1331 errorMsg(
"Warning in JetMatchingMadgraph:setDJR"
1332 ": the SlowJet algorithm failed on setup");
1337 while ( slowJetDJR->sizeAll() - slowJetDJR->sizeJet() > 0 ) {
1339 result.push_back(sqrt(slowJetDJR->dNext()));
1341 slowJetDJR->doStep();
1345 for (
int i=
int(result.size())-1; i >= 0; --i)
1346 DJR.push_back(result[i]);
1355 inline int JetMatchingMadgraph::npNLO(){
1356 string npIn = infoPtr->getEventAttribute(
"npNLO",
true);
1357 int np = (npIn !=
"") ? atoi((
char*)npIn.c_str()) : -1;
1367 inline void JetMatchingMadgraph::sortIncomingProcess(
const Event &event) {
1371 omitResonanceDecays(eventProcessOrig,
true);
1379 eventProcess.clear();
1380 workEventJet.clear();
1381 for(
int i=0; i < workEvent.size(); ++i) {
1384 int id = workEvent[i].idAbs();
1385 if ((
id >= ID_LEPMIN &&
id <= ID_LEPMAX) ||
id == ID_TOP
1386 ||
id == ID_PHOTON ||
id == 23 ||
id == 24 ||
id == 25) {
1387 eventProcess.append(workEvent[i]);
1389 workEventJet.append(workEvent[i]);
1394 if (!slowJetHard->setup(workEventJet) ) {
1395 errorMsg(
"Warning in JetMatchingMadgraph:sortIncomingProcess"
1396 ": the SlowJet algorithm failed on setup");
1401 double localQcutSq = qCutMESq;
1403 while ( slowJetHard->sizeAll() - slowJetHard->sizeJet() > 0 ) {
1405 if( slowJetHard->dNext() > localQcutSq )
break;
1407 if( slowJetHard->sizeAll()-slowJetHard->sizeJet() <= npNLO())
break;
1408 slowJetHard->doStep();
1414 int nJets = slowJetHard->sizeJet();
1415 int nClus = slowJetHard->sizeAll();
1417 for (
int i = nJets; i < nClus; ++i) {
1419 if (i < nClus-nJets) parts = slowJetHard->clusConstituents(i);
1420 else parts = slowJetHard->constituents(nClus-nJets-i);
1421 int flavour = ID_GLUON;
1422 for(
int j=0; j < int(parts.size()); ++j)
1423 if (workEventJet[parts[j]].
id() == ID_BOT)
1425 eventProcess.append( flavour, 98,
1426 workEventJet[parts.back()].mother1(),
1427 workEventJet[parts.back()].mother2(),
1428 workEventJet[parts.back()].daughter1(),
1429 workEventJet[parts.back()].daughter2(),
1430 0, 0, slowJetHard->p(i).px(), slowJetHard->p(i).py(),
1431 slowJetHard->p(i).pz(), slowJetHard->p(i).e() );
1436 workEventJet.clear();
1441 eventProcess = workEvent;
1453 for (
int i = 0; i < 3; i++) {
1456 origTypeIdx[i].clear();
1458 for (
int i = 0; i < eventProcess.size(); i++) {
1460 if (!eventProcess[i].isFinal())
continue;
1465 if (eventProcess[i].isGluon()
1466 || (eventProcess[i].idAbs() <= nQmatch) ) {
1470 idx = ( eventProcess[i].scale() < 1.999 * sqrt(infoPtr->eA()
1471 * infoPtr->eB()) ) ? 0 : 2;
1475 else if (eventProcess[i].idAbs() > nQmatch
1476 && eventProcess[i].idAbs() <= ID_TOP) {
1480 }
else if (eventProcess[i].colType() != 0
1481 && eventProcess[i].idAbs() > ID_TOP) {
1485 if( idx < 0 )
continue;
1487 typeIdx[idx].push_back(i);
1488 typeSet[idx].insert(eventProcess[i].daughter1());
1489 origTypeIdx[orig_idx].push_back(i);
1493 if (exclusiveMode == 2) {
1496 int nParton = origTypeIdx[0].size();
1497 exclusive = (nParton == nJetMax) ?
false :
true;
1501 exclusive = (exclusiveMode == 0) ?
false :
true;
1509 int nParton = typeIdx[0].size();
1510 processSubsetSave.clear();
1511 for (
int i = 0; i < nParton; ++i)
1512 processSubsetSave.append( eventProcess[typeIdx[0][i]] );
1520 inline void JetMatchingMadgraph::jetAlgorithmInput(
const Event &event,
1524 workEventJet = workEvent;
1527 for (
int i = 0; i < workEventJet.size(); ++i) {
1528 if (!workEventJet[i].isFinal())
continue;
1531 if (jetAllow == 1) {
1533 if( workEventJet[i].colType() == 0 ) {
1534 workEventJet[i].statusNeg();
1540 int idx = workEventJet[i].daughter1();
1549 if (typeSet[1].find(idx) != typeSet[1].end() ||
1550 typeSet[2].find(idx) != typeSet[2].end()) {
1551 workEventJet[i].statusNeg();
1556 if (idx == 0)
break;
1558 idx =
event[idx].mother1();
1561 }
else if (iType == 1) {
1564 if (typeSet[1].find(idx) != typeSet[1].end())
break;
1569 workEventJet[i].statusNeg();
1574 idx =
event[idx].mother1();
1577 }
else if (iType == 2) {
1580 if (typeSet[2].find(idx) != typeSet[2].end())
break;
1585 workEventJet[i].statusNeg();
1590 idx =
event[idx].mother1();
1603 inline void JetMatchingMadgraph::runJetAlgorithm() {; }
1609 inline bool JetMatchingMadgraph::matchPartonsToJets(
int iType) {
1616 setDJR(workEventJet);
1617 set_nMEpartons(origTypeIdx[0].size(), typeIdx[0].size());
1619 return (matchPartonsToJetsLight() > 0);
1620 }
else if (iType == 1) {
1621 return (matchPartonsToJetsHeavy() > 0);
1623 return (matchPartonsToJetsOther() > 0);
1641 inline int JetMatchingMadgraph::matchPartonsToJetsLight() {
1644 workEventJetSave = workEventJet;
1646 if (!performVeto)
return false;
1649 int nParton = typeIdx[0].size();
1652 if (!slowJet->setup(workEventJet) ) {
1653 errorMsg(
"Warning in JetMatchingMadgraph:matchPartonsToJets"
1654 "Light: the SlowJet algorithm failed on setup");
1657 double localQcutSq = qCutSq;
1660 while ( slowJet->sizeAll() - slowJet->sizeJet() > 0 ) {
1661 if( slowJet->dNext() > localQcutSq )
break;
1662 dOld = slowJet->dNext();
1665 int nJets = slowJet->sizeJet();
1666 int nClus = slowJet->sizeAll();
1669 if (MATCHINGDEBUG) slowJet->list(
true);
1672 int nCLjets = nClus - nJets;
1674 int nRequested = (doFxFx) ? npNLO() : nParton;
1677 if ( nCLjets < nRequested )
return LESS_JETS;
1680 if ( exclusive && !doFxFx ) {
1681 if ( nCLjets > nRequested )
return MORE_JETS;
1687 if ( doFxFx && nRequested < nJetMax && nCLjets > nRequested )
1694 if (!slowJet->setup(workEventJet) ) {
1695 errorMsg(
"Warning in JetMatchingMadgraph:matchPartonsToJets"
1696 "Light: the SlowJet algorithm failed on setup");
1703 while ( slowJet->sizeAll() - slowJet->sizeJet() > 0 ) {
1704 if( slowJet->dNext() > localQcutSq )
break;
1710 while ( slowJet->sizeAll() - slowJet->sizeJet() > nParton )
1717 if ( clFact >= 0. && nParton > 0 ) {
1718 vector<double> partonPt;
1719 for (
int i = 0; i < nParton; ++i)
1720 partonPt.push_back( eventProcess[typeIdx[0][i]].pT2() );
1721 sort( partonPt.begin(), partonPt.end());
1722 localQcutSq = max( qCutSq, partonPt[0]);
1724 nJets = slowJet->sizeJet();
1725 nClus = slowJet->sizeAll();
1728 if ( clFact != 0. ) localQcutSq *= pow2(clFact);
1731 tempEvent.init(
"(tempEvent)", particleDataPtr);
1733 double pTminEstimate = -1.;
1737 for (
int i = nJets; i < nClus; ++i) {
1738 tempEvent.append( ID_GLUON, 98, 0, 0, 0, 0, 0, 0, slowJet->p(i).px(),
1739 slowJet->p(i).py(), slowJet->p(i).pz(), slowJet->p(i).e() );
1741 pTminEstimate = max( pTminEstimate, slowJet->pT(i));
1742 if(nPass == nRequested)
break;
1745 int tempSize = tempEvent.size();
1747 vector<bool> jetAssigned;
1748 jetAssigned.assign( tempSize,
false);
1752 vector< vector<bool> > partonMatchesJet;
1753 for (
int i=0; i < nParton; ++i )
1754 partonMatchesJet.push_back( vector<bool>(tempEvent.size(),
false) );
1770 while ( doFxFx && iNow < tempSize ) {
1774 tempEventJet.init(
"(tempEventJet)", particleDataPtr);
1775 for (
int i=0; i < nParton; ++i ) {
1782 tempEventJet.clear();
1783 tempEventJet.append( ID_GLUON, 98, 0, 0, 0, 0, 0, 0,
1784 tempEvent[iNow].px(), tempEvent[iNow].py(),
1785 tempEvent[iNow].pz(), tempEvent[iNow].e() );
1787 Vec4 pIn = eventProcess[typeIdx[0][i]].p();
1788 tempEventJet.append( ID_GLUON, 99, 0, 0, 0, 0, 0, 0,
1789 pIn.px(), pIn.py(), pIn.pz(), pIn.e() );
1792 if ( !slowJet->setup(tempEventJet) ) {
1793 errorMsg(
"Warning in JetMatchingMadgraph:matchPartonsToJets"
1794 "Light: the SlowJet algorithm failed on setup");
1800 if ( slowJet->iNext() == tempEventJet.size() - 1
1801 && slowJet->jNext() > -1 && slowJet->dNext() < localQcutSq ) {
1802 jetAssigned[iNow] =
true;
1803 partonMatchesJet[i][iNow] =
true;
1809 if ( jetAssigned[iNow] ) nMatched++;
1817 if ( nRequested < nJetMax && nMatched != nRequested )
1818 return UNMATCHED_PARTON;
1819 if ( nRequested == nJetMax && nMatched < nRequested )
1820 return UNMATCHED_PARTON;
1831 while (!doFxFx && iNow < nParton ) {
1833 tempEventJet.init(
"(tempEventJet)", particleDataPtr);
1834 for (
int i = 0; i < tempSize; ++i) {
1835 if (jetAssigned[i])
continue;
1836 Vec4 pIn = tempEvent[i].p();
1838 tempEventJet.append( ID_GLUON, 98, 0, 0, 0, 0, 0, 0,
1839 pIn.px(), pIn.py(), pIn.pz(), pIn.e() );
1842 Vec4 pIn = eventProcess[typeIdx[0][iNow]].p();
1844 tempEventJet.append( ID_GLUON, 99, 0, 0, 0, 0, 0, 0,
1845 pIn.px(), pIn.py(), pIn.pz(), pIn.e() );
1846 if ( !slowJet->setup(tempEventJet) ) {
1847 errorMsg(
"Warning in JetMatchingMadgraph:matchPartonsToJets"
1848 "Light: the SlowJet algorithm failed on setup");
1853 if ( slowJet->iNext() == tempEventJet.size() - 1
1854 && slowJet->jNext() > -1 && slowJet->dNext() < localQcutSq ) {
1856 for (
int i = 0; i != tempSize; ++i) {
1857 if (jetAssigned[i])
continue;
1860 if (iKnt == slowJet->jNext() ) jetAssigned[i] =
true;
1863 return UNMATCHED_PARTON;
1871 if (nParton > 0 && pTminEstimate > 0) eTpTlightMin = pTminEstimate;
1872 else eTpTlightMin = -1.;
1875 setDJR(workEventJet);
1891 inline int JetMatchingMadgraph::matchPartonsToJetsHeavy() {
1903 int nParton = typeIdx[1].size();
1905 Event tempEventJet(workEventJet);
1911 for(
int i=0; i<nParton; ++i) {
1912 scaleF = eventProcessOrig[0].e()/workEventJet[typeIdx[1][i]].pT();
1913 tempEventJet[typeIdx[1][i]].rescale5(scaleF);
1916 if (!hjSlowJet->setup(tempEventJet) ) {
1917 errorMsg(
"Warning in JetMatchingMadgraph:matchPartonsToJets"
1918 "Heavy: the SlowJet algorithm failed on setup");
1923 while ( hjSlowJet->sizeAll() - hjSlowJet->sizeJet() > 0 ) {
1924 if( hjSlowJet->dNext() > qCutSq )
break;
1925 hjSlowJet->doStep();
1931 for(
int idx=0 ; idx< hjSlowJet->sizeAll(); ++idx) {
1932 if( hjSlowJet->pT(idx) > sqrt(qCutSq) ) nCLjets++;
1936 if (MATCHINGDEBUG) hjSlowJet->list(
true);
1941 int nRequested = nParton;
1944 if ( nCLjets < nRequested ) {
1945 if (MATCHINGDEBUG) cout <<
"veto : hvy LESS_JETS " << endl;
1946 if (MATCHINGDEBUG) cout <<
"nCLjets = " << nCLjets <<
"; nRequest = "
1947 << nRequested << endl;
1953 if ( nCLjets > nRequested ) {
1954 if (MATCHINGDEBUG) cout <<
"veto : excl hvy MORE_JETS " << endl;
1973 inline int JetMatchingMadgraph::matchPartonsToJetsOther() {
1985 int nParton = typeIdx[2].size();
1987 Event tempEventJet(workEventJet);
1993 for(
int i=0; i<nParton; ++i) {
1994 scaleF = eventProcessOrig[0].e()/workEventJet[typeIdx[2][i]].pT();
1995 tempEventJet[typeIdx[2][i]].rescale5(scaleF);
1998 if (!hjSlowJet->setup(tempEventJet) ) {
1999 errorMsg(
"Warning in JetMatchingMadgraph:matchPartonsToJets"
2000 "Heavy: the SlowJet algorithm failed on setup");
2005 while ( hjSlowJet->sizeAll() - hjSlowJet->sizeJet() > 0 ) {
2006 if( hjSlowJet->dNext() > qCutSq )
break;
2007 hjSlowJet->doStep();
2013 for(
int idx=0 ; idx< hjSlowJet->sizeAll(); ++idx) {
2014 if( hjSlowJet->pT(idx) > sqrt(qCutSq) ) nCLjets++;
2018 if (MATCHINGDEBUG) hjSlowJet->list(
true);
2023 int nRequested = nParton;
2026 if ( nCLjets < nRequested ) {
2027 if (MATCHINGDEBUG) cout <<
"veto : other LESS_JETS " << endl;
2028 if (MATCHINGDEBUG) cout <<
"nCLjets = " << nCLjets <<
"; nRequest = "
2029 << nRequested << endl;
2035 if ( nCLjets > nRequested ) {
2036 if (MATCHINGDEBUG) cout <<
"veto : excl other MORE_JETS" << endl;
2049 #endif // end Pythia8_JetMatching_H