21 const int RHadrons::IDRHADSB[14] = { 1000512, 1000522, 1000532,
22 1000542, 1000552, 1005113, 1005211, 1005213, 1005223, 1005311,
23 1005313, 1005321, 1005323, 1005333 };
25 const int RHadrons::IDRHADST[14] = { 1000612, 1000622, 1000632,
26 1000642, 1000652, 1006113, 1006211, 1006213, 1006223, 1006311,
27 1006313, 1006321, 1006323, 1006333 };
30 const int RHadrons::IDRHADGO[38] = { 1000993, 1009113, 1009213,
31 1009223, 1009313, 1009323, 1009333, 1009413, 1009423, 1009433,
32 1009443, 1009513, 1009523, 1009533, 1009543, 1009553, 1091114,
33 1092114, 1092214, 1092224, 1093114, 1093214, 1093224, 1093314,
34 1093324, 1093334, 1094114, 1094214, 1094224, 1094314, 1094324,
35 1094334, 1095114, 1095214, 1095224, 1095314, 1095324, 1095334 };
38 const int RHadrons::NTRYMAX = 10;
41 const double RHadrons::MSAFETY = 0.1;
44 const double RHadrons::EGBORROWMAX = 4.;
50 bool RHadrons::init( Info* infoPtrIn, Settings& settings,
51 ParticleData* particleDataPtrIn, Rndm* rndmPtrIn) {
55 particleDataPtr = particleDataPtrIn;
59 allowRH = settings.flag(
"RHadrons:allow");
60 maxWidthRH = settings.parm(
"RHadrons:maxWidth");
61 idRSb = settings.mode(
"RHadrons:idSbottom");
62 idRSt = settings.mode(
"RHadrons:idStop");
63 idRGo = settings.mode(
"RHadrons:idGluino");
64 setMassesRH = settings.flag(
"RHadrons:setMasses");
65 probGluinoballRH = settings.parm(
"RHadrons:probGluinoball");
66 mOffsetCloudRH = settings.parm(
"RHadrons:mOffsetCloud");
67 mCollapseRH = settings.parm(
"RHadrons:mCollapse");
68 diquarkSpin1RH = settings.parm(
"RHadrons:diquarkSpin1");
71 allowRSb = allowRH && idRSb > 0
72 && (particleDataPtr->mWidth(idRSb) < maxWidthRH);
73 allowRSt = allowRH && idRSt > 0
74 && (particleDataPtr->mWidth(idRSt) < maxWidthRH);
75 allowRGo = allowRH && idRGo > 0
76 && (particleDataPtr->mWidth(idRGo) < maxWidthRH);
77 allowSomeR = allowRSb || allowRSt || allowRGo;
81 m0Sb = particleDataPtr->m0(idRSb);
83 for (
int i = 0; i < 14; ++i) {
84 int idR = IDRHADSB[i];
85 double m0RHad = m0Sb + mOffsetCloudRH;
86 m0RHad += particleDataPtr->constituentMass( (idR%100)/10);
88 m0RHad += particleDataPtr->constituentMass( (idR%1000)/100 );
89 particleDataPtr->m0( idR, m0RHad);
94 double mWidthRHad = particleDataPtr->mWidth(idRSb);
95 double tau0RHad = particleDataPtr->tau0( idRSb);
96 for (
int i = 0; i < 14; ++i) {
97 particleDataPtr->mWidth( IDRHADSB[i], mWidthRHad);
98 particleDataPtr->tau0( IDRHADSB[i], tau0RHad);
104 m0St = particleDataPtr->m0(idRSt);
106 for (
int i = 0; i < 14; ++i) {
107 int idR = IDRHADST[i];
108 double m0RHad = m0St + mOffsetCloudRH;
109 m0RHad += particleDataPtr->constituentMass( (idR%100)/10);
111 m0RHad += particleDataPtr->constituentMass( (idR%1000)/100 );
112 particleDataPtr->m0( idR, m0RHad);
117 double mWidthRHad = particleDataPtr->mWidth(idRSt);
118 double tau0RHad = particleDataPtr->tau0( idRSt);
119 for (
int i = 0; i < 14; ++i) {
120 particleDataPtr->mWidth( IDRHADST[i], mWidthRHad);
121 particleDataPtr->tau0( IDRHADST[i], tau0RHad);
127 m0Go = particleDataPtr->m0(idRGo);
129 particleDataPtr->m0( IDRHADGO[0], m0Go + 2. * mOffsetCloudRH
130 + particleDataPtr->constituentMass(21) );
131 for (
int i = 1; i < 38; ++i) {
132 int idR = IDRHADGO[i];
133 double m0RHad = m0Go + 2. * mOffsetCloudRH;
134 m0RHad += particleDataPtr->constituentMass( (idR%1000)/100 );
135 m0RHad += particleDataPtr->constituentMass( (idR%100)/10);
137 m0RHad += particleDataPtr->constituentMass( (idR%10000)/1000 );
138 particleDataPtr->m0( idR, m0RHad);
143 double mWidthRHad = particleDataPtr->mWidth(idRGo);
144 double tau0RHad = particleDataPtr->tau0( idRGo);
145 for (
int i = 0; i < 38; ++i) {
146 particleDataPtr->mWidth( IDRHADGO[i], mWidthRHad);
147 particleDataPtr->tau0( IDRHADGO[i], tau0RHad);
159 bool RHadrons::givesRHadron(
int id) {
160 if (allowRSb && abs(
id) == idRSb)
return true;
161 if (allowRSt && abs(
id) == idRSt)
return true;
162 if (allowRGo &&
id == idRGo)
return true;
171 bool RHadrons::produce( ColConfig& colConfig,
Event& event) {
174 if (!allowSomeR)
return true;
185 for (
int i = 0; i <
event.size(); ++i)
186 if (event[i].isFinal() && givesRHadron(event[i].
id())) {
187 iBefRHad.push_back(i);
188 iCreRHad.push_back(i);
189 iRHadron.push_back(0);
190 iAftRHad.push_back(0);
191 isTriplet.push_back(
true);
193 nRHad = iRHadron.size();
196 if (nRHad == 0)
return true;
200 infoPtr->errorMsg(
"Error in RHadrons::produce: "
201 "cannot handle more than two R-hadrons");
204 if (nRHad > 1 && rndmPtr->flat() > 0.5) swap( iBefRHad[0], iBefRHad[1]);
208 iSys = colConfig.findSinglet( iBef);
209 systemPtr = &colConfig[iSys];
210 if (systemPtr->hasJunction && !splitOffJunction( colConfig, event)) {
211 infoPtr->errorMsg(
"Error in RHadrons::produce: "
212 "cannot handle system with junction");
217 iSys = colConfig.findSinglet( iBefRHad[1]);
218 systemPtr = &colConfig[iSys];
219 if (systemPtr->hasJunction && !splitOffJunction( colConfig, event)) {
220 infoPtr->errorMsg(
"Error in RHadrons::produce: "
221 "cannot handle system with junction");
228 iSys = colConfig.findSinglet( iBef);
229 systemPtr = &colConfig[iSys];
230 if (systemPtr->isClosed && !openClosedLoop( colConfig, event)) {
231 infoPtr->errorMsg(
"Error in RHadrons::produce: "
232 "cannot open up closed gluon/gluino loop");
237 iSys = colConfig.findSinglet( iBefRHad[1]);
238 systemPtr = &colConfig[iSys];
239 if (systemPtr->isClosed && !openClosedLoop( colConfig, event)) {
240 infoPtr->errorMsg(
"Error in RHadrons::produce: "
241 "cannot open up closed gluon/gluino loop");
248 int iSys1 = colConfig.findSinglet( iBefRHad[0]);
249 int iSys2 = colConfig.findSinglet( iBefRHad[1]);
250 if (iSys2 == iSys1) {
252 systemPtr = &colConfig[iSys];
253 if ( !splitSystem( colConfig, event) ) {
254 infoPtr->errorMsg(
"Error in RHadrons::produce: "
255 "failed to handle two sparticles in same system");
262 for (iRHad = 0; iRHad < nRHad; ++iRHad) {
263 iBef = iBefRHad[iRHad];
264 iSys = colConfig.findSinglet( iBef);
266 infoPtr->errorMsg(
"Error in RHadrons::produce: "
267 "sparticle not in any colour singlet");
270 systemPtr = &colConfig[iSys];
273 if (systemPtr->hasJunction) {
274 infoPtr->errorMsg(
"Error in RHadrons::produce: "
275 "cannot handle system with junction");
278 if (systemPtr->isClosed) {
279 infoPtr->errorMsg(
"Error in RHadrons::produce: "
280 "cannot handle closed colour loop");
285 if (event[iBef].
id() == idRGo) isTriplet[iRHad] =
false;
286 bool formed = (isTriplet[iRHad]) ? produceSquark( colConfig, event)
287 : produceGluino( colConfig, event);
288 if (!formed)
return false;
301 bool RHadrons::decay(
Event& event) {
304 for (iRHad = 0; iRHad < nRHad; ++iRHad) {
305 int iRNow = iRHadron[iRHad];
306 int iRBef = iBefRHad[iRHad];
307 int idRHad =
event[iRNow].id();
308 double mRHad =
event[iRNow].m();
309 double mRBef =
event[iRBef].m();
314 pair<int,int> idPair = (isTriplet[iRHad])
315 ? fromIdWithSquark( idRHad) : fromIdWithGluino( idRHad);
316 int id1 = idPair.first;
317 int id2 = idPair.second;
321 double fracR = mRBef / mRHad;
323 infoPtr->errorMsg(
"Error in RHadrons::decay: "
324 "too low R-hadron mass for decay");
329 if (isTriplet[iRHad]) {
330 int colNew =
event.nextColTag();
331 int col = (
event[iRBef].col() != 0) ? colNew : 0;
332 int acol = (col == 0) ? colNew : 0;
335 iR0 =
event.append( id1, 106, iRNow, 0, 0, 0, col, acol,
336 fracR * event[iRNow].p(), fracR * mRHad, 0.);
337 iR2 =
event.append( id2, 106, iRNow, 0, 0, 0, acol, col,
338 (1. - fracR) * event[iRNow].p(), (1. - fracR) * mRHad, 0.);
342 double m1Eff = particleDataPtr->constituentMass(id1) + mOffsetCloudRH;
343 double m2Eff = particleDataPtr->constituentMass(id2) + mOffsetCloudRH;
344 double frac1 = (1. - fracR) * m1Eff / ( m1Eff + m2Eff);
345 double frac2 = (1. - fracR) * m2Eff / ( m1Eff + m2Eff);
348 int col1 =
event.nextColTag();
349 int col2 =
event.nextColTag();
352 iR0 =
event.append( idRGo, 106, iRNow, 0, 0, 0, col2, col1,
353 fracR * event[iRNow].p(), fracR * mRHad, 0.);
354 event.append( id1, 106, iRNow, 0, 0, 0, col1, 0,
355 frac1 * event[iRNow].p(), frac1 * mRHad, 0.);
356 iR2 =
event.append( id2, 106, iRNow, 0, 0, 0, 0, col2,
357 frac2 * event[iRNow].p(), frac2 * mRHad, 0.);
361 event[iRNow].statusNeg();
362 event[iRNow].daughters( iR0, iR2);
363 iAftRHad[iRHad] = iR0;
366 Vec4 vDec =
event[iRNow].vProd() +
event[iRNow].tau()
367 *
event[iR0].p() /
event[iR0].m();
368 for (
int iRd = iR0; iRd <= iR2; ++iRd) event[iRd].vProd( vDec);
383 bool RHadrons::splitOffJunction( ColConfig& colConfig,
Event& event) {
386 vector<int> leg1, leg2, leg3;
391 for (
int i = 0; i < systemPtr->size(); ++i) {
393 int iP = systemPtr->iParton[i];
397 }
else if (iLeg == 1) leg1.push_back( iP);
398 else if (iLeg == 2) leg2.push_back( iP);
399 else if (iLeg == 3) leg3.push_back( iP);
405 if (iLegSP == 0)
return false;
409 if (iLegSP == 2) swap(leg2, leg1);
410 else if (iLegSP == 3) swap(leg3, leg1);
411 for (
int i = 0; i < iPosSP; ++i)
412 if (event[leg1[i]].
id() != 21)
return true;
416 Vec4 pSP =
event[iBef].p();
418 for (
int i = 0; i < int(leg2.size()); ++i) pRec += event[leg2[i]].p();
419 for (
int i = 0; i < int(leg3.size()); ++i) pRec += event[leg3[i]].p();
420 double mSys = (pSP + pRec).mCalc();
421 double mSP = pSP.mCalc();
422 double mRec = pRec.mCalc();
423 double eKin = mSys - mSP - mRec;
426 double mNewG = EGBORROWMAX * eKin / (EGBORROWMAX + eKin) ;
427 Vec4 pNewG = (mNewG / mSys) * (pSP + pRec);
428 int newCol =
event.nextColTag();
429 bool isCol = (
event[leg1.back()].col() > 0);
430 int colNG = (isCol)? newCol : event[iBef].acol();
431 int acolNG = (isCol) ? event[iBef].col() : newCol;
432 int iNewG =
event.append( 21, 101, iBef, 0, 0, 0, colNG, acolNG,
434 leg1.insert( leg1.begin(), iNewG);
438 double mNewSys = mSys - mNewG;
439 double pAbsOld = 0.5 * sqrtpos( pow2(mSys*mSys - mSP*mSP - mRec*mRec)
440 - pow2(2. * mSP * mRec) ) / mSys;
441 double pAbsNew = 0.5 * sqrtpos( pow2(mNewSys*mNewSys - mSP*mSP - mRec*mRec)
442 - pow2(2. * mSP * mRec) ) / mNewSys;
443 RotBstMatrix MtoCM, MfromCM, MSP, MRec;
444 MtoCM.toCMframe( pSP, pRec);
448 MSP.bst( 0., 0., -pAbsOld / sqrt(mSP * mSP + pAbsOld * pAbsOld));
449 MSP.bst( 0., 0., pAbsNew / sqrt(mSP * mSP + pAbsNew * pAbsNew));
450 MSP.rotbst( MfromCM);
452 MRec.bst( 0., 0., pAbsOld / sqrt(mRec * mRec + pAbsOld * pAbsOld));
453 MRec.bst( 0., 0., -pAbsNew / sqrt(mRec * mRec + pAbsNew * pAbsNew));
454 MRec.rotbst( MfromCM);
457 int iNewSP =
event.copy( iBef, 101);
458 event[iNewSP].rotbst( MSP);
459 leg1[iPosSP] = iNewSP;
460 if (iBefRHad[0] == iBef) iBefRHad[0] = iNewSP;
461 else if (nRHad > 1 && iBefRHad[1] == iBef) iBefRHad[1] = iNewSP;
463 for (
int i = 0; i < int(leg2.size()); ++i) {
464 int iCopy =
event.copy( leg2[i], 101);
465 event[iCopy].rotbst( MRec);
466 if (iBefRHad[0] == leg2[i]) iBefRHad[0] = iCopy;
467 else if (nRHad > 1 && iBefRHad[1] == leg2[i]) iBefRHad[1] = iCopy;
470 for (
int i = 0; i < int(leg3.size()); ++i) {
471 int iCopy =
event.copy( leg3[i], 101);
472 event[iCopy].rotbst( MRec);
473 if (iBefRHad[0] == leg3[i]) iBefRHad[0] = iCopy;
474 else if (nRHad > 1 && iBefRHad[1] == leg3[i]) iBefRHad[1] = iCopy;
483 double eGspl =
event[leg1[0]].p() *
event[iBef].p();
484 for (
int i = 1; i < iPosSP; ++i) {
485 double eGnow =
event[leg1[i]].p() *
event[iBef].p();
491 int iG = leg1[iGspl];
494 int idNewQ = flavSelPtr->pickLightQ();
495 int iNewQ =
event.append( idNewQ, 101, iG, 0, 0, 0, event[iG].col(), 0,
496 0.5 * event[iG].p(), 0.5 * event[iG].m(), 0.);
497 int iNewQb =
event.append( -idNewQ, 101, iG, 0, 0, 0, 0, event[iG].acol(),
498 0.5 * event[iG].p(), 0.5 * event[iG].m(), 0.);
499 event[iG].statusNeg();
500 event[iG].daughters( iNewQ, iNewQb);
501 if (event[leg1.back()].col() == 0) swap( iNewQ, iNewQb);
504 vector<int> iNewSys1, iNewSys2;
505 iNewSys1.push_back( iNewQb);
506 for (
int i = iGspl + 1; i < int(leg1.size()); ++i)
507 iNewSys1.push_back( leg1[i]);
508 iNewSys2.push_back( -10);
509 for (
int i = 0; i < iGspl; ++i) iNewSys2.push_back( leg1[i]);
510 iNewSys2.push_back( iNewQ);
511 iNewSys2.push_back( -11);
512 for (
int i = 0; i < int(leg2.size()); ++i) iNewSys2.push_back( leg2[i]);
513 iNewSys2.push_back( -12);
514 for (
int i = 0; i < int(leg3.size()); ++i) iNewSys2.push_back( leg3[i]);
517 colConfig.erase(iSys);
518 colConfig.insert( iNewSys1, event);
519 colConfig.insert( iNewSys2, event);
530 bool RHadrons::openClosedLoop( ColConfig& colConfig,
Event& event) {
535 for (
int i = 0; i < systemPtr->size(); ++i) {
536 int iGNow = systemPtr->iParton[i];
537 if (event[iGNow].
id() == 21) {
538 double eGnow =
event[iGNow].p() *
event[iBef].p();
545 if (iGspl == -1)
return false;
548 int iG = systemPtr->iParton[iGspl];
549 int idNewQ = flavSelPtr->pickLightQ();
550 int iNewQ =
event.append( idNewQ, 101, iG, 0, 0, 0, event[iG].col(), 0,
551 0.5 * event[iG].p(), 0.5 * event[iG].m(), 0.);
552 int iNewQb =
event.append( -idNewQ, 101, iG, 0, 0, 0, 0, event[iG].acol(),
553 0.5 * event[iG].p(), 0.5 * event[iG].m(), 0.);
554 event[iG].statusNeg();
555 event[iG].daughters( iNewQ, iNewQb);
558 int iNext = iGspl + 1;
559 if (iNext == systemPtr->size()) iNext = 0;
560 if (event[ systemPtr->iParton[iNext]].acol() !=
event[iNewQ].col())
561 swap( iNewQ, iNewQb);
563 iNewSys.push_back( iNewQ);
564 for (
int i = iGspl + 1; i < systemPtr->size(); ++i)
565 iNewSys.push_back( systemPtr->iParton[i]);
566 for (
int i = 0; i < iGspl; ++i)
567 iNewSys.push_back( systemPtr->iParton[i]);
568 iNewSys.push_back( iNewQb);
571 colConfig.erase(iSys);
572 colConfig.insert( iNewSys, event);
584 bool RHadrons::splitSystem( ColConfig& colConfig,
Event& event) {
589 for (
int i = 0; i < int(systemPtr->size()); ++i) {
590 int iTmp = systemPtr->iParton[i];
591 if ( givesRHadron( event[iTmp].
id()) ) {
592 if (iFirst == -1) iFirst = i;
596 int nLeg = iSecond - iFirst;
599 int idNewQ = flavSelPtr->pickLightQ();
600 double mNewQ = particleDataPtr->constituentMass( idNewQ);
601 vector<int> iNewSys1, iNewSys2;
607 int i1Old = systemPtr->iParton[iFirst];
608 int i2Old = systemPtr->iParton[iSecond];
611 double mHat = (
event[i1Old].p() +
event[i2Old].p()).mCalc();
612 double mMax = mHat -
event[i1Old].m() -
event[i2Old].m();
613 if (mMax < 2. * (mNewQ + MSAFETY))
return false;
614 double mEff = min( 2. * (mNewQ + mOffsetCloudRH), mMax - 2. * MSAFETY);
615 double frac = mEff / mHat;
616 Vec4 pEff = frac * (
event[i1Old].p() +
event[i2Old].p());
621 if ( !newKin( event[i1Old].p(), event[i2Old].p(),
622 event[i1Old].m() / (1. - frac), event[i2Old].m() / (1. - frac),
623 p1New, p2New) )
return false;
628 int i1New, i2New, i3New, i4New;
629 int newCol =
event.nextColTag();
630 i1New =
event.copy( i1Old, 101);
631 if (event[i2Old].acol() == event[i1Old].col()) {
632 i3New =
event.append( -idNewQ, 101, i1Old, 0, 0, 0,
633 0, event[i2Old].acol(), 0.5 * pEff, 0.5 * mEff, 0.);
634 i2New =
event.copy( i2Old, 101);
635 event[i2New].acol( newCol);
636 i4New =
event.append( idNewQ, 101, i2Old, 0, 0, 0,
637 newCol, 0, 0.5 * pEff, 0.5 * mEff, 0.);
639 i3New =
event.append( idNewQ, 101, i1Old, 0, 0, 0,
640 event[i2Old].col(), 0, 0.5 * pEff, 0.5 * mEff, 0.);
641 i2New =
event.copy( i2Old, 101);
642 event[i2New].col( newCol);
643 i4New =
event.append( -idNewQ, 101, i2Old, 0, 0, 0,
644 0, newCol, 0.5 * pEff, 0.5 * mEff, 0.);
649 event[i1New].p( p1New);
650 event[i2New].p( p2New);
651 event[i1Old].daughters( i1New, i3New);
652 event[i1New].mother2( 0);
653 event[i2Old].daughters( i2New, i4New);
654 event[i2New].mother2( 0);
659 for (
int i = 0; i < iFirst; ++i)
660 iNewSys1.push_back( systemPtr->iParton[i]);
661 iNewSys1.push_back( i1New);
662 iNewSys1.push_back( i3New);
663 iNewSys2.push_back( i4New);
664 iNewSys2.push_back( i2New);
665 for (
int i = iSecond + 1; i < int(systemPtr->size()); ++i)
666 iNewSys2.push_back( systemPtr->iParton[i]);
670 }
else if (nLeg == 2) {
673 int iOld = systemPtr->iParton[iFirst + 1];
674 int i1New =
event.append( idNewQ, 101, iOld, 0, 0, 0,
675 event[iOld].col(), 0, 0.5 * event[iOld].p(),
676 0.5 * event[iOld].m(), 0.);
677 int i2New =
event.append( -idNewQ, 101, iOld, 0, 0, 0,
678 0, event[iOld].acol(), 0.5 * event[iOld].p(),
679 0.5 * event[iOld].m(), 0.);
680 event[iOld].statusNeg();
681 event[iOld].daughters( i1New, i2New);
684 if (event[systemPtr->iParton[iFirst]].col() ==
event[i2New].acol())
686 for (
int i = 0; i <= iFirst; ++i)
687 iNewSys1.push_back( systemPtr->iParton[i]);
688 iNewSys1.push_back( i1New);
689 iNewSys2.push_back( i2New);
690 for (
int i = iSecond; i < int(systemPtr->size()); ++i)
691 iNewSys2.push_back( systemPtr->iParton[i]);
702 for (
int i = iFirst + 1; i < iSecond - 1; ++i) {
703 int i1Tmp = systemPtr->iParton[i];
704 int i2Tmp = systemPtr->iParton[i + 1];
705 double mTmp = (
event[i1Tmp].p() +
event[i2Tmp].p()).mCalc();
713 double mEff = min( mNewQ + mOffsetCloudRH, 0.4 * mMin);
717 if ( !newKin( event[i1Old].p(), event[i2Old].p(),
718 mEff, mEff, p1New, p2New,
false) )
return false;
722 if (event[systemPtr->iParton[0]].acol() == 0) {
723 i1New =
event.append( -idNewQ, 101, i1Old, 0, 0, 0,
724 0, event[i1Old].acol(), p1New, mEff, 0.);
725 i2New =
event.append( idNewQ, 101, i2Old, 0, 0, 0,
726 event[i2Old].col(), 0, p2New, mEff, 0.);
728 i1New =
event.append( idNewQ, 101, i1Old, 0, 0, 0,
729 event[i1Old].col(), 0, p1New, mEff, 0.);
730 i2New =
event.append( -idNewQ, 101, i2Old, 0, 0, 0,
731 0, event[i2Old].acol(), p2New, mEff, 0.);
733 event[i1Old].statusNeg();
734 event[i2Old].statusNeg();
735 event[i1Old].daughters( i1New, 0);
736 event[i2Old].daughters( i2New, 0);
739 for (
int i = 0; i < iMin; ++i)
740 iNewSys1.push_back( systemPtr->iParton[i]);
741 iNewSys1.push_back( i1New);
742 iNewSys2.push_back( i2New);
743 for (
int i = iMin + 2; i < int(systemPtr->size()); ++i)
744 iNewSys2.push_back( systemPtr->iParton[i]);
748 colConfig.erase(iSys);
749 colConfig.insert( iNewSys1, event);
750 colConfig.insert( iNewSys2, event);
761 bool RHadrons::produceSquark( ColConfig& colConfig,
Event& event) {
770 int idAbsTop =
event[ systemPtr->iParton[0] ].idAbs();
771 bool sqAtTop = (allowRSb && idAbsTop == idRSb)
772 || (allowRSt && idAbsTop == idRSt);
775 int iBeg =
event.size();
776 iCreRHad[iRHad] = iBeg;
777 if (sqAtTop)
for (
int i = 0; i < systemPtr->size(); ++i)
778 event.copy( systemPtr->iParton[i], 102);
779 else for (
int i = systemPtr->size() - 1; i >= 0; --i)
780 event.copy( systemPtr->iParton[i], 102);
781 int iEnd =
event.size() - 1;
784 int idOldH =
event[iBeg].id();
785 int idOldL =
event[iEnd].id();
788 FlavContainer flavOld( idOldH%10);
789 int idNewQ = flavSelPtr->pick(flavOld).id;
790 int idRHad = toIdWithSquark( idOldH, idNewQ);
792 infoPtr->errorMsg(
"Error in RHadrons::produceSquark: "
793 "cannot form R-hadron code");
798 double mRHad = particleDataPtr->m0(idRHad) +
event[iBeg].m()
799 - ( (abs(idOldH) == idRSb) ? m0Sb : m0St );
800 double z = zSelPtr->zFrag( idOldH, idNewQ, mRHad*mRHad);
803 Vec4 pOldH =
event[iBeg].p();
804 int iOldL = iBeg + 1;
805 Vec4 pOldL =
event[iOldL].p();
806 double mOldL =
event[iOldL].m();
807 double mNewH = mRHad / z;
808 double sSys = (pOldH + pOldL).m2Calc();
809 double sRem = (1. - z) * (sSys - mNewH*mNewH);
810 double sMin = pow2(mOldL + mCollapseRH);
813 while ( ( sRem < sMin || sSys < pow2(mNewH + mOldL + MSAFETY) )
816 pOldL +=
event[iOldL].p();
817 mOldL =
event[iOldL].m();
818 sSys = (pOldH + pOldL).m2Calc();
819 sRem = (1. - z) * (sSys - mNewH*mNewH);
820 sMin = pow2(mOldL + mCollapseRH);
824 if ( sRem > sMin && sSys > pow2(mNewH + mOldL + MSAFETY) ) {
826 if ( !newKin( pOldH, pOldL, mNewH, mOldL, pNewH, pNewL) ) {
827 infoPtr->errorMsg(
"Error in RHadrons::produceSquark: "
828 "failed to construct kinematics with reduced system");
833 iRNow =
event.append( idRHad, 104, iBeg, iOldL, 0, 0, 0, 0,
834 z * pNewH, mRHad, 0.);
838 bool hasCol = (idNewQ > 0 && idNewQ < 10) || idNewQ < -10;
839 int col = (hasCol) ? event[iOldL].acol() : 0;
840 int acol = (hasCol) ? 0 : event[iOldL].col();
841 iNewQ =
event.append( idNewQ, 105, iBeg, iOldL, 0, 0, col, acol,
842 (1. - z) * pNewH, (1. - z) * mNewH, 0.);
843 iNewL =
event.copy( iOldL, 105);
844 event[iNewL].mothers( iBeg, iOldL);
845 event[iNewL].p( pNewL);
853 FlavContainer flav1( idOldL);
854 FlavContainer flav2( -idNewQ);
856 int idNewL = flavSelPtr->combine( flav1, flav2);
857 while (++iTry < NTRYMAX && idNewL == 0)
858 idNewL = flavSelPtr->combine( flav1, flav2);
860 infoPtr->errorMsg(
"Error in RHadrons::produceSquark: "
861 "cannot form light hadron code");
864 double mNewL = particleDataPtr->mass( idNewL);
867 if ( sSys > pow2(mRHad + mNewL + MSAFETY) ) {
869 if ( !newKin( pOldH, pOldL, mRHad, mNewL, pRHad, pNewL) ) {
870 infoPtr->errorMsg(
"Error in RHadrons::produceSquark: "
871 "failed to construct kinematics for two-hadron decay");
876 iRNow =
event.append( idRHad, 104, iBeg, iOldL, 0, 0, 0, 0,
878 event.append( idNewL, 105, iBeg, iOldL, 0, 0, 0, 0,
888 idRHad = toIdWithSquark( idOldH, idOldL);
890 infoPtr->errorMsg(
"Error in RHadrons::produceSquark: "
891 "cannot form R-hadron code");
896 iRNow =
event.append( idRHad, 104, iBeg, iOldL, 0, 0, 0, 0,
897 systemPtr->pSum, systemPtr->mass, 0.);
904 iRHadron[iRHad] = iRNow;
905 int iLast =
event.size() - 1;
906 for (
int i = iBeg; i <= iOldL; ++i) {
907 event[i].statusNeg();
908 event[i].daughters( iRNow, iLast);
912 colConfig.erase(iSys);
915 iNewSys.push_back( iNewQ);
916 iNewSys.push_back( iNewL);
917 for (
int i = iOldL + 1; i <= iEnd; ++i) iNewSys.push_back( i);
918 colConfig.insert( iNewSys, event);
922 event[iRNow].tau( event[iBef].tau() );
923 if (event[iBef].hasVertex())
event[iRNow].vProd( event[iBef].vProd() );
934 bool RHadrons::produceGluino( ColConfig& colConfig,
Event& event) {
941 vector<int> iSide1, iSide2, iSideTmp, iNewSys1, iNewSys2;
942 Vec4 pGlui, pSide1, pSide2;
945 bool isGBall = (rndmPtr->flat() < probGluinoballRH);
948 for (
int i = 0; i < systemPtr->size(); ++i) {
949 int iTmp = systemPtr->iParton[i];
950 if (iGlui == 0 && event[ iTmp ].
id() == idRGo) {
952 pGlui =
event[ iTmp ].p();
953 }
else if (iGlui == 0) {
954 iSideTmp.push_back( iTmp);
955 pSide1 +=
event[ iTmp ].p();
957 iSide2.push_back( iTmp);
958 pSide2 +=
event[ iTmp ].p();
963 for (
int i =
int(iSideTmp.size()) - 1; i >= 0; --i)
964 iSide1.push_back( iSideTmp[i]);
965 double m1H = (pGlui + pSide1).mCalc() -
event[ iSide1.back() ].m();
966 double m2H = (pGlui + pSide2).mCalc() -
event[ iSide2.back() ].m();
968 swap( iSide1, iSide2);
969 swap( pSide1, pSide2);
973 for (
int iSide = 1; iSide < 3; ++iSide) {
985 int iBeg =
event.size();
987 iCreRHad[iRHad] = iBeg;
988 event.copy( iGlui, 102);
989 for (
int i = 0; i < int(iSide1.size()); ++i)
990 event.copy( iSide1[i], 102);
992 event.copy( iGlui, 102);
993 for (
int i = 0; i < int(iSide2.size()); ++i)
994 event.copy( iSide2[i], 102);
996 int iEnd =
event.size() - 1;
999 int idOldL =
event[iEnd].id();
1003 FlavContainer flavOld( idOldL);
1004 idNewQ = -flavSelPtr->pick(flavOld).id;
1005 }
while (iSide == 2 && isDiq1 && abs(idNewQ) > 10);
1006 if (iSide == 1) isDiq1 = (abs(idNewQ) > 10);
1008 bool hasCol = (
event[iEnd].col() > 0);
1015 idRHad = (hasCol) ? 1009002 : -1009002;
1016 if (hasCol) colR =
event[iBeg].col();
1017 else acolR =
event[iBeg].acol();
1019 double mNewQ = particleDataPtr->constituentMass( idNewQ);
1020 if (isGBall) mNewQ *= 0.5;
1021 mRHad =
event[iBeg].m() + mOffsetCloudRH + mNewQ;
1023 idRHad = toIdWithGluino( idSave, idNewQ);
1025 infoPtr->errorMsg(
"Error in RHadrons::produceGluino: "
1026 "cannot form R-hadron code");
1030 mRHad = particleDataPtr->m0(idRHad) +
event[iBeg].m() - m0Go;
1034 double z = zSelPtr->zFrag( idRGo, idNewQ, mRHad*mRHad);
1037 Vec4 pOldH =
event[iBeg].p();
1038 int iOldL = iBeg + 1;
1039 Vec4 pOldL =
event[iOldL].p();
1040 double mOldL =
event[iOldL].m();
1041 double mNewH = mRHad / z;
1042 double sSys = (pOldH + pOldL).m2Calc();
1043 double sRem = (1. - z) * (sSys - mNewH*mNewH);
1044 double sMin = pow2(mOldL + mCollapseRH);
1047 while ( ( sRem < sMin || sSys < pow2(mNewH + mOldL + MSAFETY) )
1050 pOldL +=
event[iOldL].p();
1051 mOldL =
event[iOldL].m();
1052 sSys = (pOldH + pOldL).m2Calc();
1053 sRem = (1. - z) * (sSys - mNewH*mNewH);
1054 sMin = pow2(mOldL + mCollapseRH);
1058 if ( sRem > sMin && sSys > pow2(mNewH + mOldL + MSAFETY) ) {
1060 if ( !newKin( pOldH, pOldL, mNewH, mOldL, pNewH, pNewL) ) {
1061 infoPtr->errorMsg(
"Error in RHadrons::produceGluino: "
1062 "failed to construct kinematics with reduced system");
1067 iRNow =
event.append( idRHad, statusRHad, iBeg, iOldL,
1068 0, 0, colR, acolR, z * pNewH, mRHad, 0.);
1071 if (!isGBall) idNewQ = -idNewQ;
1072 int colN = (hasCol) ? 0 : event[iOldL].acol();
1073 int acolN = (hasCol) ? event[iOldL].col() : 0;
1074 iNewQ =
event.append( idNewQ, 105, iBeg, iOldL, 0, 0,
1075 colN, acolN, (1. - z) * pNewH, (1. - z) * mNewH, 0.);
1076 iNewL =
event.copy( iOldL, 105);
1077 event[iNewL].mothers( iBeg, iOldL);
1078 event[iNewL].p( pNewL);
1082 iNewSys1.push_back( iNewQ);
1083 iNewSys1.push_back( iNewL);
1084 for (
int i = iOldL + 1; i <= iEnd; ++i) iNewSys1.push_back( i);
1086 iNewSys2.push_back( iNewQ);
1087 iNewSys2.push_back( iNewL);
1088 for (
int i = iOldL + 1; i <= iEnd; ++i) iNewSys2.push_back( i);
1096 if (nBody == 0 && isGBall && iSide == 1) {
1097 idQLeap =
event[iOldL].id();
1098 Vec4 pNewH =
event[iBeg].p() + pOldL;
1101 iRNow =
event.append( idRHad, statusRHad, iBeg, iEnd,
1102 0, 0, colR, acolR, pNewH, pNewH.mCalc(), 0.);
1108 if (nBody == 0 && (!isGBall || (iSide == 2 && idQLeap != 0) )) {
1109 if (isGBall) idNewQ = -idQLeap;
1110 FlavContainer flav1( idOldL);
1111 FlavContainer flav2( -idNewQ);
1113 int idNewL = flavSelPtr->combine( flav1, flav2);
1114 while (++iTry < NTRYMAX && idNewL == 0)
1115 idNewL = flavSelPtr->combine( flav1, flav2);
1117 infoPtr->errorMsg(
"Error in RHadrons::produceGluino: "
1118 "cannot form light hadron code");
1121 double mNewL = particleDataPtr->mass( idNewL);
1124 if ( sSys > pow2(mRHad + mNewL + MSAFETY) ) {
1126 if ( !newKin( pOldH, pOldL, mRHad, mNewL, pRHad, pNewL) ) {
1127 infoPtr->errorMsg(
"Error in RHadrons::produceGluino: "
1128 "failed to construct kinematics for two-hadron decay");
1133 iRNow =
event.append( idRHad, statusRHad, iBeg, iOldL, 0, 0,
1134 colR, acolR, pRHad, mRHad, 0.);
1135 event.append( idNewL, 105, iBeg, iOldL, 0, 0, 0, 0,
1146 if (nBody == 0 && (!isGBall || (iSide == 2 && idQLeap != 0) )) {
1147 if (isGBall) idSave = idQLeap;
1148 if (iSide == 1) idSave = idOldL;
1149 else idRHad = toIdWithGluino( idSave, idOldL);
1151 infoPtr->errorMsg(
"Error in RHadrons::produceGluino: "
1152 "cannot form R-hadron code");
1157 iRNow =
event.append( idRHad, statusRHad, iBeg, iOldL, 0, 0,
1158 colR, acolR, pOldH + pOldL, (pOldH + pOldL).mCalc(), 0.);
1166 int iLast =
event.size() - 1;
1167 for (
int i = iBeg; i <= iOldL; ++i) {
1168 event[i].statusNeg();
1169 event[i].daughters( iRNow, iLast);
1178 infoPtr->errorMsg(
"Error in RHadrons::produceGluino: "
1179 "could not handle gluinoball kinematics");
1182 iRHadron[iRHad] = iGlui;
1183 colConfig.erase(iSys);
1187 if (iNewSys1.size() > 0) colConfig.insert( iNewSys1, event);
1188 if (iNewSys2.size() > 0) colConfig.insert( iNewSys2, event);
1192 }
else if (idQLeap == 0) {
1193 int iG1 = iNewSys1[0];
1194 int iG2 = iNewSys2[0];
1195 int colG =
event[iG1].col() +
event[iG2].col();
1196 int acolG =
event[iG1].acol() +
event[iG2].acol();
1197 Vec4 pG =
event[iG1].p() +
event[iG2].p();
1198 int iG12 =
event.append( 21, 105, iG1, iG2, 0, 0, colG, acolG,
1199 pG, pG.mCalc(), 0.);
1204 event[iG1].statusNeg();
1205 event[iG2].statusNeg();
1206 int colBridge =
event.nextColTag();
1207 if (event[iG1].col() == 0) {
1208 event[iG1].col( colBridge);
1209 event[iG2].acol( colBridge);
1211 event[iG1].acol( colBridge);
1212 event[iG2].col( colBridge);
1216 vector<int> iNewSys12;
1217 for (
int i =
int(iNewSys1.size()) - 1; i > 0; --i)
1218 iNewSys12.push_back( iNewSys1[i]);
1219 iNewSys12.push_back( iG12);
1220 for (
int i = 1; i < int(iNewSys2.size()); ++i)
1221 iNewSys12.push_back( iNewSys2[i]);
1222 colConfig.insert( iNewSys12, event);
1227 int iG2 = iNewSys2[0];
1228 event[iG2].id( idQLeap);
1229 colConfig.insert( iNewSys2, event);
1233 event[iGlui].tau( event[iBef].tau() );
1234 if (event[iBef].hasVertex())
event[iGlui].vProd( event[iBef].vProd() );
1246 int RHadrons::toIdWithSquark(
int id1,
int id2) {
1249 int id1Abs = abs(id1);
1250 int id2Abs = abs(id2);
1251 if (id2Abs < 10 && id1 > 0 && id2 > 0)
return 0;
1252 if (id2Abs < 10 && id1 < 0 && id2 < 0)
return 0;
1253 if (id2Abs > 10 && id1 > 0 && id2 < 0)
return 0;
1254 if (id2Abs > 10 && id1 < 0 && id2 > 0)
return 0;
1257 bool isSt = (id1Abs == idRSt);
1258 int idRHad = 1000000;
1259 if (id2Abs < 10) idRHad += ((isSt) ? 600 : 500) + 10 * id2Abs + 2;
1260 else idRHad += ((isSt) ? 6000 : 5000) + 10 * (id2Abs/100) + id2Abs%10;
1261 if (id1 < 0) idRHad = -idRHad;
1273 pair<int,int> RHadrons::fromIdWithSquark(
int idRHad) {
1276 int idLight = (abs(idRHad) - 1000000) / 10;
1277 int idSq = (idLight < 100) ? idLight/10 : idLight/100;
1278 int id1 = (idSq == 6) ? idRSt : idRSb;
1279 if (idRHad < 0) id1 = -id1;
1282 int id2 = (idLight < 100) ? idLight%10 : idLight%100;
1283 if (id2 > 10) id2 = 100 * id2 + abs(idRHad)%10;
1284 if ((id2 < 10 && idRHad > 0) || (id2 > 10 && idRHad < 0)) id2 = -id2;
1287 return make_pair( id1, id2);
1295 int RHadrons::toIdWithGluino(
int id1,
int id2) {
1298 int id1Abs = abs(id1);
1299 int id2Abs = abs(id2);
1300 if (id1Abs == 21 && id2Abs == 21)
return 1000993;
1301 int idMax = max( id1Abs, id2Abs);
1302 int idMin = min( id1Abs, id2Abs);
1303 if (idMin > 10)
return 0;
1304 if (idMax > 10 && id1 > 0 && id2 < 0)
return 0;
1305 if (idMax > 10 && id1 < 0 && id2 > 0)
return 0;
1306 if (idMax < 10 && id1 > 0 && id2 > 0)
return 0;
1307 if (idMax < 10 && id1 < 0 && id2 < 0)
return 0;
1312 idRHad = 1009003 + 100 * idMax + 10 * idMin;
1313 if (idMin != idMax && idMax%2 == 1) {
1314 if (id1Abs == idMax && id1 > 0) idRHad = -idRHad;
1315 if (id2Abs == idMax && id2 > 0) idRHad = -idRHad;
1317 if (idMin != idMax && idMax%2 == 0) {
1318 if (id1Abs == idMax && id1 < 0) idRHad = -idRHad;
1319 if (id2Abs == idMax && id2 < 0) idRHad = -idRHad;
1324 int idA = idMax/1000;
1325 int idB = (idMax/100)%10;
1327 if (idC > idB) swap( idB, idC);
1328 if (idB > idA) swap( idA, idB);
1329 if (idC > idB) swap( idB, idC);
1330 idRHad = 1090004 + 1000 * idA + 100 * idB + 10 * idC;
1331 if (id1 < 0) idRHad = -idRHad;
1344 pair<int,int> RHadrons::fromIdWithGluino(
int idRHad) {
1347 int idLight = (abs(idRHad) - 1000000) / 10;
1348 int id1, id2, idTmp, idA, idB, idC;
1351 if (idLight < 100) {
1352 id1 = (rndmPtr->flat() < 0.5) ? 1 : 2;
1356 }
else if (idLight < 1000) {
1357 id1 = (idLight / 10) % 10;
1358 id2 = -(idLight % 10);
1369 idA = (idLight / 100) % 10;
1370 idB = (idLight / 10) % 10;
1372 double rndmQ = 3. * rndmPtr->flat();
1373 if (idA > 3) rndmQ = 0.5;
1376 id2 = 1000 * idB + 100 * idC + 3;
1377 if (idB != idC && rndmPtr->flat() > diquarkSpin1RH) id2 -= 2;
1378 }
else if (rndmQ < 2.) {
1380 id2 = 1000 * idA + 100 * idC + 3;
1381 if (idA != idC && rndmPtr->flat() > diquarkSpin1RH) id2 -= 2;
1384 id2 = 1000 * idA + 100 * idB +3;
1385 if (idA != idB && rndmPtr->flat() > diquarkSpin1RH) id2 -= 2;
1397 return make_pair( id1, id2);
1407 bool RHadrons::newKin( Vec4 pOld1, Vec4 pOld2,
double mNew1,
double mNew2,
1408 Vec4& pNew1, Vec4& pNew2,
bool checkMargin) {
1411 double sSum = (pOld1 + pOld2).m2Calc();
1412 double sOld1 = pOld1.m2Calc();
1413 double sOld2 = pOld2.m2Calc();
1414 double sNew1 = mNew1 * mNew1;
1415 double sNew2 = mNew2 * mNew2;
1418 if (checkMargin && pow2(mNew1 + mNew2 + MSAFETY) > sSum)
return false;
1421 double lamOld = sqrt( pow2(sSum - sOld1 - sOld2) - 4. * sOld1 * sOld2 );
1422 double lamNew = sqrt( pow2(sSum - sNew1 - sNew2) - 4. * sNew1 * sNew2 );
1423 double move1 = (lamNew * (sSum - sOld1 + sOld2)
1424 - lamOld * (sSum - sNew1 + sNew2)) / (2. * sSum * lamOld);
1425 double move2 = (lamNew * (sSum + sOld1 - sOld2)
1426 - lamOld * (sSum + sNew1 - sNew2)) / (2. * sSum * lamOld);
1429 pNew1 = (1. + move1) * pOld1 - move2 * pOld2;
1430 pNew2 = (1. + move2) * pOld2 - move1 * pOld1;