StRoot  1
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
ParticleDecays.cc
1 // ParticleDecays.cc is a part of the PYTHIA event generator.
2 // Copyright (C) 2018 Torbjorn Sjostrand.
3 // PYTHIA is licenced under the GNU GPL v2 or later, see COPYING for details.
4 // Please respect the MCnet Guidelines, see GUIDELINES for details.
5 
6 // Function definitions (not found in the header) for the
7 // ParticleDecays class.
8 
9 #include "Pythia8/ParticleDecays.h"
10 
11 namespace Pythia8 {
12 
13 //==========================================================================
14 
15 // The ParticleDecays class.
16 
17 //--------------------------------------------------------------------------
18 
19 // Constants: could be changed here if desired, but normally should not.
20 // These are of technical nature, as described for each.
21 
22 // Number of times one tries to let decay happen (for 2 nested loops).
23 const int ParticleDecays::NTRYDECAY = 10;
24 
25 // Number of times one tries to pick valid hadronic content in decay.
26 const int ParticleDecays::NTRYPICK = 100;
27 
28 // Number of times one tries to pick decay topology.
29 const int ParticleDecays::NTRYMEWT = 1000;
30 
31 // Maximal loop count in Dalitz decay treatment.
32 const int ParticleDecays::NTRYDALITZ = 1000;
33 
34 // Minimal Dalitz pair mass this factor above threshold.
35 const double ParticleDecays::MSAFEDALITZ = 1.000001;
36 
37 // These numbers are hardwired empirical parameters,
38 // intended to speed up the M-generator.
39 const double ParticleDecays::WTCORRECTION[11] = { 1., 1., 1.,
40  2., 5., 15., 60., 250., 1250., 7000., 50000. };
41 
42 //--------------------------------------------------------------------------
43 
44 // Initialize and save pointers.
45 
46 void ParticleDecays::init(Info* infoPtrIn, Settings& settings,
47  ParticleData* particleDataPtrIn, Rndm* rndmPtrIn,
48  Couplings* couplingsPtrIn, TimeShower* timesDecPtrIn,
49  StringFlav* flavSelPtrIn, DecayHandler* decayHandlePtrIn,
50  vector<int> handledParticles) {
51 
52  // Save pointers to error messages handling and flavour generation.
53  infoPtr = infoPtrIn;
54  particleDataPtr = particleDataPtrIn;
55  rndmPtr = rndmPtrIn;
56  couplingsPtr = couplingsPtrIn;
57  flavSelPtr = flavSelPtrIn;
58 
59  // Save pointer to timelike shower, as needed in some few decays.
60  timesDecPtr = timesDecPtrIn;
61 
62  // Save pointer for external handling of some decays.
63  decayHandlePtr = decayHandlePtrIn;
64 
65  // Set which particles should be handled externally.
66  if (decayHandlePtr != 0)
67  for (int i = 0; i < int(handledParticles.size()); ++i)
68  particleDataPtr->doExternalDecay(handledParticles[i], true);
69 
70  // Safety margin in mass to avoid troubles.
71  mSafety = settings.parm("ParticleDecays:mSafety");
72 
73  // Lifetime and vertex rules for determining whether decay allowed.
74  limitTau0 = settings.flag("ParticleDecays:limitTau0");
75  tau0Max = settings.parm("ParticleDecays:tau0Max");
76  limitTau = settings.flag("ParticleDecays:limitTau");
77  tauMax = settings.parm("ParticleDecays:tauMax");
78  limitRadius = settings.flag("ParticleDecays:limitRadius");
79  rMax = settings.parm("ParticleDecays:rMax");
80  limitCylinder = settings.flag("ParticleDecays:limitCylinder");
81  xyMax = settings.parm("ParticleDecays:xyMax");
82  zMax = settings.parm("ParticleDecays:zMax");
83  limitDecay = limitTau0 || limitTau || limitRadius || limitCylinder;
84 
85  // B-Bbar mixing parameters.
86  mixB = settings.flag("ParticleDecays:mixB");
87  xBdMix = settings.parm("ParticleDecays:xBdMix");
88  xBsMix = settings.parm("ParticleDecays:xBsMix");
89 
90  // Suppression of extra-hadron momenta in semileptonic decays.
91  sigmaSoft = settings.parm("ParticleDecays:sigmaSoft");
92 
93  // Selection of multiplicity and colours in "phase space" model.
94  multIncrease = settings.parm("ParticleDecays:multIncrease");
95  multIncreaseWeak = settings.parm("ParticleDecays:multIncreaseWeak");
96  multRefMass = settings.parm("ParticleDecays:multRefMass");
97  multGoffset = settings.parm("ParticleDecays:multGoffset");
98  colRearrange = settings.parm("ParticleDecays:colRearrange");
99 
100  // Minimum energy in system (+ m_q) from StringFragmentation.
101  stopMass = settings.parm("StringFragmentation:stopMass");
102 
103  // Parameters for Dalitz decay virtual gamma mass spectrum.
104  sRhoDal = pow2(particleDataPtr->m0(113));
105  wRhoDal = pow2(particleDataPtr->mWidth(113));
106 
107  // Allow showers in decays to qqbar/gg/ggg/gammagg.
108  doFSRinDecays = settings.flag("ParticleDecays:FSRinDecays");
109  doGammaRad = settings.flag("ParticleDecays:allowPhotonRadiation");
110 
111  // Use standard decays or dedicated tau decay package
112  tauMode = settings.mode("TauDecays:mode");
113 
114  // Initialize the dedicated tau decay handler.
115  if (tauMode) tauDecayer.init(infoPtr, &settings,
116  particleDataPtr, rndmPtr, couplingsPtr);
117 
118 }
119 
120 //--------------------------------------------------------------------------
121 
122 // Decay a particle; main method.
123 
124 bool ParticleDecays::decay( int iDec, Event& event) {
125 
126  // Check whether a decay is allowed, given the upcoming decay vertex.
127  Particle& decayer = event[iDec];
128  hasPartons = false;
129  keepPartons = false;
130  if (limitDecay && !checkVertex(decayer)) return true;
131 
132  // Do not allow resonance decays (beyond handling capability).
133  if (decayer.isResonance()) {
134  infoPtr->errorMsg("Warning in ParticleDecays::decay: "
135  "resonance left undecayed");
136  return true;
137  }
138 
139  // Fill the decaying particle in slot 0 of arrays.
140  idDec = decayer.id();
141  iProd.resize(0);
142  idProd.resize(0);
143  mProd.resize(0);
144  iProd.push_back( iDec );
145  idProd.push_back( idDec );
146  mProd.push_back( decayer.m() );
147 
148  // Check for oscillations B0 <-> B0bar or B_s0 <-> B_s0bar.
149  bool hasOscillated = (abs(idDec) == 511 || abs(idDec) == 531)
150  ? oscillateB(decayer) : false;
151  if (hasOscillated) {idDec = - idDec; idProd[0] = idDec;}
152 
153  // Particle data for decaying particle.
154  decDataPtr = &decayer.particleDataEntry();
155 
156  // Optionally send on to external decay program.
157  bool doneExternally = false;
158  if (decDataPtr->doExternalDecay()) {
159  motherProd.resize(0);
160  motherProd.push_back( 0 );
161  pProd.resize(0);
162  pProd.push_back(decayer.p());
163  doneExternally = decayHandlePtr->chainDecay( idProd, motherProd,
164  mProd, pProd, iDec, event);
165  if (!doneExternally) doneExternally = decayHandlePtr->decay( idProd,
166  mProd, pProd, iDec, event);
167 
168  // If it worked, then store the decay products in the event record.
169  if (doneExternally) {
170  int oldSize = event.size();
171  mult = idProd.size() - 1;
172  while (int(motherProd.size()) <= mult) motherProd.push_back( 0 );
173  int status = (hasOscillated) ? 94 : 93;
174  for (int i = 1; i <= mult; ++i) {
175  int iMo = (motherProd[i] == 0) ? iDec : oldSize + motherProd[i] - 1;
176  int iPos = event.append( idProd[i], status, iMo, 0, 0, 0,
177  0, 0, pProd[i], mProd[i]);
178  iProd.push_back( iPos);
179 
180  // Also mark mother(s) decayed and store daughters.
181  event[iMo].statusNeg();
182  if ( event[iMo].daughter1() == 0) event[iMo].daughter1( iPos);
183  else event[iMo].daughter2( iPos);
184  }
185  }
186  }
187 
188  // Check if the particle is tau and let the special tau decayer handle it.
189  if (decayer.idAbs() == 15 && !doneExternally && tauMode) {
190  doneExternally = tauDecayer.decay(iDec, event);
191  if (doneExternally) return true;
192  }
193 
194  // Now begin normal internal decay treatment.
195  if (!doneExternally) {
196 
197  // Allow up to ten tries to pick a channel.
198  if (!decDataPtr->preparePick(idDec, decayer.m())) return false;
199  bool foundChannel = false;
200  bool hasStored = false;
201  for (int iTryChannel = 0; iTryChannel < NTRYDECAY; ++iTryChannel) {
202 
203  // Remove previous failed channel.
204  if (hasStored) event.popBack(mult);
205  hasStored = false;
206 
207  // Pick new channel. Read out basics.
208  DecayChannel& channel = decDataPtr->pickChannel();
209  meMode = channel.meMode();
210  keepPartons = (meMode > 90 && meMode <= 100);
211  mult = channel.multiplicity();
212 
213  // Allow up to ten tries for each channel (e.g with different masses).
214  bool foundMode = false;
215  iProd.resize(1);
216  for (int iTryMode = 0; iTryMode < NTRYDECAY; ++iTryMode) {
217  idProd.resize(1);
218  mProd.resize(1);
219  scale = 0.;
220 
221  // Extract and store the decay products in local arrays.
222  hasPartons = false;
223  for (int i = 0; i < mult; ++i) {
224  int idNow = channel.product(i);
225  int idAbs = abs(idNow);
226  if ( idAbs < 10 || idAbs == 21 || idAbs == 81 || idAbs == 82
227  || idAbs == 83 || (idAbs > 1000 && idAbs < 10000
228  && (idAbs/10)%10 == 0) ) hasPartons = true;
229  if (idDec < 0 && particleDataPtr->hasAnti(idNow)) idNow = -idNow;
230  double mNow = particleDataPtr->mSel(idNow);
231  idProd.push_back( idNow);
232  mProd.push_back( mNow);
233  }
234 
235  // Decays into partons usually translate into hadrons.
236  if (hasPartons && !keepPartons && !pickHadrons()) continue;
237 
238  // Need to set colour flow if explicit decay to partons.
239  cols.resize(0);
240  acols.resize(0);
241  for (int i = 0; i <= mult; ++i) {
242  cols.push_back(0);
243  acols.push_back(0);
244  }
245  if (hasPartons && keepPartons && !setColours(event)) continue;
246 
247  // Check that enough phase space for decay.
248  if (mult > 1) {
249  double mDiff = mProd[0];
250  for (int i = 1; i <= mult; ++i) mDiff -= mProd[i];
251  if (mDiff < mSafety) continue;
252  }
253 
254  // End of inner trial loops. Check if succeeded or not.
255  foundMode = true;
256  break;
257  }
258  if (!foundMode) continue;
259 
260  // Store decay products in the event record.
261  int status = (hasOscillated) ? 92 : 91;
262  for (int i = 1; i <= mult; ++i) {
263  int iPos = event.append( idProd[i], status, iDec, 0, 0, 0,
264  cols[i], acols[i], Vec4(0., 0., 0., 0.), mProd[i], scale);
265  iProd.push_back( iPos);
266  }
267  hasStored = true;
268 
269  // Pick mass of Dalitz decay. Temporarily change multiplicity.
270  if ( (meMode == 11 || meMode == 12 || meMode == 13)
271  && !dalitzMass() ) continue;
272 
273  // Do a decay, split by multiplicity.
274  bool decayed = false;
275  if (mult == 1) decayed = oneBody(event);
276  else if (mult == 2) decayed = twoBody(event);
277  else if (mult == 3) decayed = threeBody(event);
278  else decayed = mGenerator(event);
279  if (!decayed) continue;
280 
281  // Kinematics of gamma* -> l- l+ in Dalitz decay. Restore multiplicity.
282  if (meMode == 11 || meMode == 12 || meMode == 13)
283  dalitzKinematics(event);
284 
285  // End of outer trial loops.
286  foundChannel = true;
287  break;
288  }
289 
290  // If the decay worked, then mark mother decayed and store daughters.
291  if (foundChannel) {
292  event[iDec].statusNeg();
293  event[iDec].daughters( iProd[1], iProd[mult]);
294 
295  // Else remove unused daughters and return failure.
296  } else {
297  if (hasStored) event.popBack(mult);
298  infoPtr->errorMsg("Error in ParticleDecays::decay: "
299  "failed to find workable decay channel");
300  return false;
301  }
302 
303  // Now finished normal internal decay treatment.
304  }
305 
306  // Set decay vertex when this is displaced.
307  if (event[iDec].hasVertex() || event[iDec].tau() > 0.) {
308  Vec4 vDec = event[iDec].vDec();
309  for (int i = event[iDec].daughter1(); i <= event[iDec].daughter2(); ++i)
310  event[i].vProd( vDec );
311  }
312 
313  // Set lifetime of daughters. Check if they decayed in their turn.
314  for (int i = iProd[1]; i <= iProd[mult]; ++i) {
315  event[i].tau( event[i].tau0() * rndmPtr->exp() );
316  if (!event[i].isFinal() && (event[i].hasVertex() || event[i].tau() > 0.)) {
317  Vec4 vDecR = event[i].vDec();
318  for (int iR = event[i].daughter1(); iR <= event[i].daughter2(); ++iR)
319  event[iR].vProd( vDecR );
320  }
321  }
322 
323  // In a decay explicitly to partons then optionally do a shower,
324  // and always flag that partonic system should be fragmented.
325  if (hasPartons && keepPartons && doFSRinDecays)
326  timesDecPtr->shower( iProd[1], iProd.back(), event, mProd[0]);
327 
328  // Photon radiation implemented only for two-body decay to leptons.
329  else if (doGammaRad && mult == 2 && event[iProd[1]].isLepton()
330  && event[iProd[2]].isLepton())
331  timesDecPtr->showerQED( iProd[1], iProd[2], event, mProd[0]);
332 
333  // For Hidden Valley particles also allow leptons to shower.
334  else if (event[iDec].idAbs() > 4900000 && event[iDec].idAbs() < 5000000
335  && doFSRinDecays && mult == 2 && event[iProd[1]].isLepton()) {
336  event[iProd[1]].scale(mProd[0]);
337  event[iProd[2]].scale(mProd[0]);
338  timesDecPtr->shower( iProd[1], iProd.back(), event, mProd[0]);
339  }
340 
341  // Done.
342  return true;
343 
344 }
345 
346 //--------------------------------------------------------------------------
347 
348 // Check whether a decay is allowed, given the upcoming decay vertex.
349 
350 bool ParticleDecays::checkVertex(Particle& decayer) {
351 
352  // Check whether any of the conditions are not fulfilled.
353  if (limitTau0 && decayer.tau0() > tau0Max) return false;
354  if (limitTau && decayer.tau() > tauMax) return false;
355  if (limitRadius && pow2(decayer.xDec()) + pow2(decayer.yDec())
356  + pow2(decayer.zDec()) > pow2(rMax)) return false;
357  if (limitCylinder && (pow2(decayer.xDec()) + pow2(decayer.yDec())
358  > pow2(xyMax) || abs(decayer.zDec()) > zMax) ) return false;
359 
360  // Done.
361  return true;
362 
363 }
364 
365 //--------------------------------------------------------------------------
366 
367 // Check for oscillations B0 <-> B0bar or B_s0 <-> B_s0bar.
368 
369 bool ParticleDecays::oscillateB(Particle& decayer) {
370 
371  // Extract relevant information and decide.
372  if (!mixB) return false;
373  double xBmix = (abs(decayer.id()) == 511) ? xBdMix : xBsMix;
374  double tau = decayer.tau();
375  double tau0 = decayer.tau0();
376  double probosc = pow2(sin(0.5 * xBmix * tau / tau0));
377  return (probosc > rndmPtr->flat());
378 
379 }
380 
381 //--------------------------------------------------------------------------
382 
383 // Do a one-body decay. (Rare; e.g. for K0 -> K0_short.)
384 
385 bool ParticleDecays::oneBody(Event& event) {
386 
387  // References to the particles involved.
388  Particle& decayer = event[iProd[0]];
389  Particle& prod = event[iProd[1]];
390 
391  // Set momentum and expand mother information.
392  prod.p( decayer.p() );
393  prod.m( decayer.m() );
394  prod.mother2( iProd[0] );
395 
396  // Done.
397  return true;
398 
399 }
400 
401 //--------------------------------------------------------------------------
402 
403 // Do a two-body decay.
404 
405 bool ParticleDecays::twoBody(Event& event) {
406 
407  // References to the particles involved.
408  Particle& decayer = event[iProd[0]];
409  Particle& prod1 = event[iProd[1]];
410  Particle& prod2 = event[iProd[2]];
411 
412  // Masses.
413  double m0 = mProd[0];
414  double m1 = mProd[1];
415  double m2 = mProd[2];
416 
417  // Energies and absolute momentum in the rest frame.
418  if (m1 + m2 + mSafety > m0) return false;
419  double e1 = 0.5 * (m0*m0 + m1*m1 - m2*m2) / m0;
420  double e2 = 0.5 * (m0*m0 + m2*m2 - m1*m1) / m0;
421  double pAbs = 0.5 * sqrtpos( (m0 - m1 - m2) * (m0 + m1 + m2)
422  * (m0 + m1 - m2) * (m0 - m1 + m2) ) / m0;
423 
424  // When meMode = 2, for V -> PS2 + PS3 (V = vector, pseudoscalar),
425  // need to check if production is PS0 -> PS1/gamma + V.
426  int iMother = event[iProd[0]].mother1();
427  int idSister = 0;
428  if (meMode == 2) {
429  if (iMother <= 0 || iMother >= iProd[0]) meMode = 0;
430  else {
431  int iDaughter1 = event[iMother].daughter1();
432  int iDaughter2 = event[iMother].daughter2();
433  if (iDaughter2 != iDaughter1 + 1) meMode = 0;
434  else {
435  int idMother = abs( event[iMother].id() );
436  if (idMother <= 100 || idMother%10 !=1
437  || (idMother/1000)%10 != 0) meMode = 0;
438  else {
439  int iSister = (iProd[0] == iDaughter1) ? iDaughter2 : iDaughter1;
440  idSister = abs( event[iSister].id() );
441  if ( (idSister <= 100 || idSister%10 !=1
442  || (idSister/1000)%10 != 0) && idSister != 22) meMode = 0;
443  }
444  }
445  }
446  }
447 
448  // Begin loop over matrix-element corrections.
449  double wtME, wtMEmax;
450  int loop = 0;
451  do {
452  wtME = 1.;
453  wtMEmax = 1.;
454  ++loop;
455 
456  // Isotropic angles give three-momentum.
457  double cosTheta = 2. * rndmPtr->flat() - 1.;
458  double sinTheta = sqrt(1. - cosTheta*cosTheta);
459  double phi = 2. * M_PI * rndmPtr->flat();
460  double pX = pAbs * sinTheta * cos(phi);
461  double pY = pAbs * sinTheta * sin(phi);
462  double pZ = pAbs * cosTheta;
463 
464  // Fill four-momenta and boost them away from mother rest frame.
465  prod1.p( pX, pY, pZ, e1);
466  prod2.p( -pX, -pY, -pZ, e2);
467  prod1.bst( decayer.p(), decayer.m() );
468  prod2.bst( decayer.p(), decayer.m() );
469 
470  // Matrix element for PS0 -> PS1 + V1 -> PS1 + PS2 + PS3 of form
471  // cos**2(theta02) in V1 rest frame, and for PS0 -> gamma + V1
472  // -> gamma + PS2 + PS3 of form sin**2(theta02).
473  if (meMode == 2) {
474  double p10 = decayer.p() * event[iMother].p();
475  double p12 = decayer.p() * prod1.p();
476  double p02 = event[iMother].p() * prod1.p();
477  double s0 = pow2(event[iMother].m());
478  double s1 = pow2(decayer.m());
479  double s2 = pow2(prod1.m());
480  if (idSister != 22) wtME = pow2(p10 * p12 - s1 * p02);
481  else wtME = s1 * (2. * p10 * p12 * p02 - s1 * p02*p02
482  - s0 * p12*p12 - s2 * p10*p10 + s1 * s0 * s2);
483  wtME = max( wtME, 1e-6 * s1*s1 * s0 * s2);
484  wtMEmax = (p10*p10 - s1 * s0) * (p12*p12 - s1 * s2);
485  }
486 
487  // Break out of loop if no sensible ME weight.
488  if(loop > NTRYMEWT) {
489  infoPtr->errorMsg("ParticleDecays::twoBody: "
490  "caught in infinite ME weight loop");
491  wtME = abs(wtMEmax);
492  }
493 
494  // If rejected, try again with new invariant masses.
495  } while ( wtME < rndmPtr->flat() * wtMEmax );
496 
497  // Done.
498  return true;
499 
500 }
501 
502 //--------------------------------------------------------------------------
503 
504 // Do a three-body decay (except Dalitz decays).
505 
506 bool ParticleDecays::threeBody(Event& event) {
507 
508  // References to the particles involved.
509  Particle& decayer = event[iProd[0]];
510  Particle& prod1 = event[iProd[1]];
511  Particle& prod2 = event[iProd[2]];
512  Particle& prod3 = event[iProd[3]];
513 
514  // Mother and sum daughter masses. Fail if too close.
515  double m0 = mProd[0];
516  double m1 = mProd[1];
517  double m2 = mProd[2];
518  double m3 = mProd[3];
519  double mSum = m1 + m2 + m3;
520  double mDiff = m0 - mSum;
521  if (mDiff < mSafety) return false;
522 
523  // Kinematical limits for 2+3 mass. Maximum phase-space weight.
524  double m23Min = m2 + m3;
525  double m23Max = m0 - m1;
526  double p1Max = 0.5 * sqrtpos( (m0 - m1 - m23Min) * (m0 + m1 + m23Min)
527  * (m0 + m1 - m23Min) * (m0 - m1 + m23Min) ) / m0;
528  double p23Max = 0.5 * sqrtpos( (m23Max - m2 - m3) * (m23Max + m2 + m3)
529  * (m23Max + m2 - m3) * (m23Max - m2 + m3) ) / m23Max;
530  double wtPSmax = 0.5 * p1Max * p23Max;
531 
532  // Begin loop over matrix-element corrections.
533  double wtME, wtMEmax, wtPS, m23, p1Abs, p23Abs;
534  do {
535  wtME = 1.;
536  wtMEmax = 1.;
537 
538  // Pick an intermediate mass m23 flat in the allowed range.
539  do {
540  m23 = m23Min + rndmPtr->flat() * mDiff;
541 
542  // Translate into relative momenta and find phase-space weight.
543  p1Abs = 0.5 * sqrtpos( (m0 - m1 - m23) * (m0 + m1 + m23)
544  * (m0 + m1 - m23) * (m0 - m1 + m23) ) / m0;
545  p23Abs = 0.5 * sqrtpos( (m23 - m2 - m3) * (m23 + m2 + m3)
546  * (m23 + m2 - m3) * (m23 - m2 + m3) ) / m23;
547  wtPS = p1Abs * p23Abs;
548 
549  // If rejected, try again with new invariant masses.
550  } while ( wtPS < rndmPtr->flat() * wtPSmax );
551 
552  // Set up m23 -> m2 + m3 isotropic in its rest frame.
553  double cosTheta = 2. * rndmPtr->flat() - 1.;
554  double sinTheta = sqrt(1. - cosTheta*cosTheta);
555  double phi = 2. * M_PI * rndmPtr->flat();
556  double pX = p23Abs * sinTheta * cos(phi);
557  double pY = p23Abs * sinTheta * sin(phi);
558  double pZ = p23Abs * cosTheta;
559  double e2 = sqrt( m2*m2 + p23Abs*p23Abs);
560  double e3 = sqrt( m3*m3 + p23Abs*p23Abs);
561  prod2.p( pX, pY, pZ, e2);
562  prod3.p( -pX, -pY, -pZ, e3);
563 
564  // Set up m0 -> m1 + m23 isotropic in its rest frame.
565  cosTheta = 2. * rndmPtr->flat() - 1.;
566  sinTheta = sqrt(1. - cosTheta*cosTheta);
567  phi = 2. * M_PI * rndmPtr->flat();
568  pX = p1Abs * sinTheta * cos(phi);
569  pY = p1Abs * sinTheta * sin(phi);
570  pZ = p1Abs * cosTheta;
571  double e1 = sqrt( m1*m1 + p1Abs*p1Abs);
572  double e23 = sqrt( m23*m23 + p1Abs*p1Abs);
573  prod1.p( pX, pY, pZ, e1);
574 
575  // Boost 2 + 3 to the 0 rest frame.
576  Vec4 p23( -pX, -pY, -pZ, e23);
577  prod2.bst( p23, m23 );
578  prod3.bst( p23, m23 );
579 
580  // Matrix-element weight for omega/phi -> pi+ pi- pi0.
581  if (meMode == 1) {
582  double p1p2 = prod1.p() * prod2.p();
583  double p1p3 = prod1.p() * prod3.p();
584  double p2p3 = prod2.p() * prod3.p();
585  wtME = pow2(m1 * m2 * m3) - pow2(m1 * p2p3) - pow2(m2 * p1p3)
586  - pow2(m3 * p1p2) + 2. * p1p2 * p1p3 * p2p3;
587  wtMEmax = pow3(m0 * m0) / 150.;
588 
589  // Effective matrix element for nu spectrum in tau -> nu + hadrons.
590  } else if (meMode == 21) {
591  double x1 = 2. * prod1.e() / m0;
592  wtME = x1 * (3. - 2. * x1);
593  double xMax = min( 0.75, 2. * (1. - mSum / m0) );
594  wtMEmax = xMax * (3. - 2. * xMax);
595 
596  // Matrix element for weak decay (only semileptonic for c and b).
597  } else if ((meMode == 22 || meMode == 23) && prod1.isLepton()) {
598  wtME = m0 * prod1.e() * (prod2.p() * prod3.p());
599  wtMEmax = min( pow4(m0) / 16., m0 * (m0 - m1 - m2) * (m0 - m1 - m3)
600  * (m0 - m2 - m3) );
601 
602  // Effective matrix element for weak decay to hadrons (B -> D, D -> K).
603  } else if (meMode == 22 || meMode == 23) {
604  double x1 = 2. * prod1.pAbs() / m0;
605  wtME = x1 * (3. - 2. * x1);
606  double xMax = min( 0.75, 2. * (1. - mSum / m0) );
607  wtMEmax = xMax * (3. - 2. * xMax);
608 
609  // Effective matrix element for gamma spectrum in B -> gamma + hadrons.
610  } else if (meMode == 31) {
611  double x1 = 2. * prod1.e() / m0;
612  wtME = pow3(x1);
613  double x1Max = 1. - pow2(mSum / m0);
614  wtMEmax = pow3(x1Max);
615 
616  // Matrix-element weight for "onium" -> g + g + g or gamma + g + g.
617  } else if (meMode == 92) {
618  double x1 = 2. * prod1.e() / m0;
619  double x2 = 2. * prod2.e() / m0;
620  double x3 = 2. * prod3.e() / m0;
621  wtME = pow2( (1. - x1) / (x2 * x3) ) + pow2( (1. - x2) / (x1 * x3) )
622  + pow2( (1. - x3) / (x1 * x2) );
623  wtMEmax = 2.;
624  // For gamma + g + g require minimum mass for g + g system.
625  if (prod1.id() == 22 && sqrt(1. - x1) * m0 < 2. * stopMass) wtME = 0.;
626  if (prod2.id() == 22 && sqrt(1. - x2) * m0 < 2. * stopMass) wtME = 0.;
627  if (prod3.id() == 22 && sqrt(1. - x3) * m0 < 2. * stopMass) wtME = 0.;
628  }
629 
630  // If rejected, try again with new invariant masses.
631  } while ( wtME < rndmPtr->flat() * wtMEmax );
632 
633  // Boost 1 + 2 + 3 to the current frame.
634  prod1.bst( decayer.p(), decayer.m() );
635  prod2.bst( decayer.p(), decayer.m() );
636  prod3.bst( decayer.p(), decayer.m() );
637 
638  // Done.
639  return true;
640 
641 }
642 
643 //--------------------------------------------------------------------------
644 
645 // Do a multibody decay using the M-generator algorithm.
646 
647 bool ParticleDecays::mGenerator(Event& event) {
648 
649  // Mother and sum daughter masses. Fail if too close or inconsistent.
650  double m0 = mProd[0];
651  double mSum = mProd[1];
652  for (int i = 2; i <= mult; ++i) mSum += mProd[i];
653  double mDiff = m0 - mSum;
654  if (mDiff < mSafety) return false;
655 
656  // Begin setup of intermediate invariant masses.
657  mInv.resize(0);
658  for (int i = 0; i <= mult; ++i) mInv.push_back( mProd[i]);
659 
660  // Calculate the maximum weight in the decay.
661  double wtPS, wtME, wtMEmax;
662  double wtPSmax = 1. / WTCORRECTION[mult];
663  double mMax = mDiff + mProd[mult];
664  double mMin = 0.;
665  for (int i = mult - 1; i > 0; --i) {
666  mMax += mProd[i];
667  mMin += mProd[i+1];
668  double mNow = mProd[i];
669  wtPSmax *= 0.5 * sqrtpos( (mMax - mMin - mNow) * (mMax + mMin + mNow)
670  * (mMax + mMin - mNow) * (mMax - mMin + mNow) ) / mMax;
671  }
672 
673  // Begin loop over matrix-element corrections.
674  do {
675  wtME = 1.;
676  wtMEmax = 1.;
677 
678  // Begin loop to find the set of intermediate invariant masses.
679  do {
680  wtPS = 1.;
681 
682  // Find and order random numbers in descending order.
683  rndmOrd.resize(0);
684  rndmOrd.push_back(1.);
685  for (int i = 1; i < mult - 1; ++i) {
686  double rndm = rndmPtr->flat();
687  rndmOrd.push_back(rndm);
688  for (int j = i - 1; j > 0; --j) {
689  if (rndm > rndmOrd[j]) swap( rndmOrd[j], rndmOrd[j+1] );
690  else break;
691  }
692  }
693  rndmOrd.push_back(0.);
694 
695  // Translate into intermediate masses and find weight.
696  for (int i = mult - 1; i > 0; --i) {
697  mInv[i] = mInv[i+1] + mProd[i] + (rndmOrd[i-1] - rndmOrd[i]) * mDiff;
698  wtPS *= 0.5 * sqrtpos( (mInv[i] - mInv[i+1] - mProd[i])
699  * (mInv[i] + mInv[i+1] + mProd[i]) * (mInv[i] + mInv[i+1] - mProd[i])
700  * (mInv[i] - mInv[i+1] + mProd[i]) ) / mInv[i];
701  }
702 
703  // If rejected, try again with new invariant masses.
704  } while ( wtPS < rndmPtr->flat() * wtPSmax );
705 
706  // Perform two-particle decays in the respective rest frame.
707  pInv.resize(mult + 1);
708  for (int i = 1; i < mult; ++i) {
709  double pAbs = 0.5 * sqrtpos( (mInv[i] - mInv[i+1] - mProd[i])
710  * (mInv[i] + mInv[i+1] + mProd[i]) * (mInv[i] + mInv[i+1] - mProd[i])
711  * (mInv[i] - mInv[i+1] + mProd[i]) ) / mInv[i];
712 
713  // Isotropic angles give three-momentum.
714  double cosTheta = 2. * rndmPtr->flat() - 1.;
715  double sinTheta = sqrt(1. - cosTheta*cosTheta);
716  double phi = 2. * M_PI * rndmPtr->flat();
717  double pX = pAbs * sinTheta * cos(phi);
718  double pY = pAbs * sinTheta * sin(phi);
719  double pZ = pAbs * cosTheta;
720 
721  // Calculate energies, fill four-momenta.
722  double eHad = sqrt( mProd[i]*mProd[i] + pAbs*pAbs);
723  double eInv = sqrt( mInv[i+1]*mInv[i+1] + pAbs*pAbs);
724  event[iProd[i]].p( pX, pY, pZ, eHad);
725  pInv[i+1].p( -pX, -pY, -pZ, eInv);
726  }
727 
728  // Boost decay products to the mother rest frame.
729  event[iProd[mult]].p( pInv[mult] );
730  for (int iFrame = mult - 1; iFrame > 1; --iFrame)
731  for (int i = iFrame; i <= mult; ++i)
732  event[iProd[i]].bst( pInv[iFrame], mInv[iFrame]);
733 
734  // Effective matrix element for nu spectrum in tau -> nu + hadrons.
735  if (meMode == 21 && event[iProd[1]].isLepton()) {
736  double x1 = 2. * event[iProd[1]].e() / m0;
737  wtME = x1 * (3. - 2. * x1);
738  double xMax = min( 0.75, 2. * (1. - mSum / m0) );
739  wtMEmax = xMax * (3. - 2. * xMax);
740 
741  // Effective matrix element for weak decay (only semileptonic for c and b).
742  // Particles 4 onwards should be made softer explicitly?
743  } else if ((meMode == 22 || meMode == 23) && event[iProd[1]].isLepton()) {
744  Vec4 pRest = event[iProd[3]].p();
745  for (int i = 4; i <= mult; ++i) pRest += event[iProd[i]].p();
746  wtME = m0 * event[iProd[1]].e() * (event[iProd[2]].p() * pRest);
747  for (int i = 4; i <= mult; ++i) wtME
748  *= exp(- event[iProd[i]].pAbs2() / pow2(sigmaSoft) );
749  wtMEmax = pow4(m0) / 16.;
750 
751  // Effective matrix element for weak decay to hadrons (B -> D, D -> K).
752  } else if (meMode == 22 || meMode == 23) {
753  double x1 = 2. * event[iProd[1]].pAbs() / m0;
754  wtME = x1 * (3. - 2. * x1);
755  double xMax = min( 0.75, 2. * (1. - mSum / m0) );
756  wtMEmax = xMax * (3. - 2. * xMax);
757 
758  // Effective matrix element for gamma spectrum in B -> gamma + hadrons.
759  } else if (meMode == 31) {
760  double x1 = 2. * event[iProd[1]].e() / m0;
761  wtME = pow3(x1);
762  double x1Max = 1. - pow2(mSum / m0);
763  wtMEmax = pow3(x1Max);
764  }
765 
766  // If rejected, try again with new invariant masses.
767  } while ( wtME < rndmPtr->flat() * wtMEmax );
768 
769  // Boost decay products to the current frame.
770  pInv[1].p( event[iProd[0]].p() );
771  for (int i = 1; i <= mult; ++i) event[iProd[i]].bst( pInv[1], mInv[1] );
772 
773  // Done.
774  return true;
775 
776 }
777 
778 //--------------------------------------------------------------------------
779 
780 // Select mass of lepton pair in a Dalitz decay.
781 
782 bool ParticleDecays::dalitzMass() {
783 
784  // Mother and sum daughter masses.
785  double mSum1 = 0;
786  for (int i = 1; i <= mult - 2; ++i) mSum1 += mProd[i];
787  if (meMode == 13) mSum1 *= MSAFEDALITZ;
788  double mSum2 = MSAFEDALITZ * (mProd[mult -1] + mProd[mult]);
789  double mDiff = mProd[0] - mSum1 - mSum2;
790 
791  // Fail if too close or inconsistent.
792  if (mDiff < mSafety) return false;
793  if (idProd[mult - 1] + idProd[mult] != 0
794  || mProd[mult - 1] != mProd[mult]) {
795  infoPtr->errorMsg("Error in ParticleDecays::dalitzMass:"
796  " inconsistent flavour/mass assignments");
797  return false;
798  }
799  if ( meMode == 13 && (idProd[1] + idProd[2] != 0
800  || mProd[1] != mProd[2]) ) {
801  infoPtr->errorMsg("Error in ParticleDecays::dalitzMass:"
802  " inconsistent flavour/mass assignments");
803  return false;
804  }
805 
806  // Case 1: one Dalitz pair.
807  if (meMode == 11 || meMode == 12) {
808 
809  // Kinematical limits for gamma* squared mass.
810  double sGamMin = pow2(mSum2);
811  double sGamMax = pow2(mProd[0] - mSum1);
812  // Select virtual gamma squared mass. Guessed form for meMode == 12.
813  double sGam, wtGam;
814  int loop = 0;
815  do {
816  if (++loop > NTRYDALITZ) return false;
817  sGam = sGamMin * pow( sGamMax / sGamMin, rndmPtr->flat() );
818  wtGam = (1. + 0.5 * sGamMin / sGam) * sqrt(1. - sGamMin / sGam)
819  * pow3(1. - sGam / sGamMax) * sRhoDal * (sRhoDal + wRhoDal)
820  / ( pow2(sGam - sRhoDal) + sRhoDal * wRhoDal );
821  } while ( wtGam < rndmPtr->flat() );
822 
823  // Store results in preparation for doing a one-less-body decay.
824  --mult;
825  mProd[mult] = sqrt(sGam);
826 
827  // Case 2: two Dalitz pairs.
828  } else {
829 
830  // Kinematical limits for 1 + 2 and 3 + 4 gamma* masses.
831  double s0 = pow2(mProd[0]);
832  double s12Min = pow2(mSum1);
833  double s12Max = pow2(mProd[0] - mSum2);
834  double s34Min = pow2(mSum2);
835  double s34Max = pow2(mProd[0] - mSum1);
836 
837  // Select virtual gamma squared masses. Guessed form for meMode == 13.
838  double s12, s34, wt12, wt34, wtPAbs, wtAll;
839  int loop = 0;
840  do {
841  if (++loop > NTRYDALITZ) return false;
842  s12 = s12Min * pow( s12Max / s12Min, rndmPtr->flat() );
843  wt12 = (1. + 0.5 * s12Min / s12) * sqrt(1. - s12Min / s12)
844  * sRhoDal * (sRhoDal + wRhoDal)
845  / ( pow2(s12 - sRhoDal) + sRhoDal * wRhoDal );
846  s34 = s34Min * pow( s34Max / s34Min, rndmPtr->flat() );
847  wt34 = (1. + 0.5 * s34Min / s34) * sqrt(1. - s34Min / s34)
848  * sRhoDal * (sRhoDal + wRhoDal)
849  / ( pow2(s34 - sRhoDal) + sRhoDal * wRhoDal );
850  wtPAbs = sqrtpos( pow2(1. - (s12 + s34)/ s0)
851  - 4. * s12 * s34 / (s0 * s0) );
852  wtAll = wt12 * wt34 * pow3(wtPAbs);
853  if (wtAll > 1.) infoPtr->errorMsg(
854  "Error in ParticleDecays::dalitzMass: weight > 1");
855  } while (wtAll < rndmPtr->flat());
856 
857  // Store results in preparation for doing a two-body decay.
858  mult = 2;
859  mProd[1] = sqrt(s12);
860  mProd[2] = sqrt(s34);
861  }
862 
863  // Done.
864  return true;
865 
866 }
867 
868 //--------------------------------------------------------------------------
869 
870 // Do kinematics of gamma* -> l- l+ in Dalitz decay.
871 
872 bool ParticleDecays::dalitzKinematics(Event& event) {
873 
874  // Restore multiplicity.
875  int nDal = (meMode < 13) ? 1 : 2;
876  mult += nDal;
877 
878  // Loop over one or two lepton pairs.
879  for (int iDal = 0; iDal < nDal; ++iDal) {
880 
881  // References to the particles involved.
882  Particle& decayer = event[iProd[0]];
883  Particle& prodA = (iDal == 0) ? event[iProd[mult - 1]]
884  : event[iProd[1]];
885  Particle& prodB = (iDal == 0) ? event[iProd[mult]]
886  : event[iProd[2]];
887 
888  // Reconstruct required rotations and boosts backwards.
889  Vec4 pDec = decayer.p();
890  int iGam = (meMode < 13) ? mult - 1 : 2 - iDal;
891  Vec4 pGam = event[iProd[iGam]].p();
892  pGam.bstback( pDec, decayer.m() );
893  double phiGam = pGam.phi();
894  pGam.rot( 0., -phiGam);
895  double thetaGam = pGam.theta();
896  pGam.rot( -thetaGam, 0.);
897 
898  // Masses and phase space in gamma* rest frame.
899  double mGam = (meMode < 13) ? mProd[mult - 1] : mProd[2 - iDal];
900  double mA = prodA.m();
901  double mB = prodB.m();
902  double mGamMin = MSAFEDALITZ * (mA + mB);
903  double mGamRat = pow2(mGamMin / mGam);
904  double pGamAbs = 0.5 * sqrtpos( (mGam - mA - mB) * (mGam + mA + mB) );
905 
906  // Set up decay in gamma* rest frame, reference along +z axis.
907  double cosTheta, cos2Theta;
908  do {
909  cosTheta = 2. * rndmPtr->flat() - 1.;
910  cos2Theta = cosTheta * cosTheta;
911  } while ( 1. + cos2Theta + mGamRat * (1. - cos2Theta)
912  < 2. * rndmPtr->flat() );
913  double sinTheta = sqrt(1. - cosTheta*cosTheta);
914  double phi = 2. * M_PI * rndmPtr->flat();
915  double pX = pGamAbs * sinTheta * cos(phi);
916  double pY = pGamAbs * sinTheta * sin(phi);
917  double pZ = pGamAbs * cosTheta;
918  double eA = sqrt( mA*mA + pGamAbs*pGamAbs);
919  double eB = sqrt( mB*mB + pGamAbs*pGamAbs);
920  prodA.p( pX, pY, pZ, eA);
921  prodB.p( -pX, -pY, -pZ, eB);
922 
923  // Boost to lab frame.
924  prodA.bst( pGam, mGam);
925  prodB.bst( pGam, mGam);
926  prodA.rot( thetaGam, phiGam);
927  prodB.rot( thetaGam, phiGam);
928  prodA.bst( pDec, decayer.m() );
929  prodB.bst( pDec, decayer.m() );
930  }
931 
932  // Done.
933  return true;
934 
935 }
936 
937 //--------------------------------------------------------------------------
938 
939 // Translate a partonic content into a set of actual hadrons.
940 
941 bool ParticleDecays::pickHadrons() {
942 
943  // Find partonic decay products. Rest are known id's, mainly hadrons,
944  // when necessary shuffled to beginning of idProd list.
945  idPartons.resize(0);
946  int nPartons = 0;
947  int nKnown = 0;
948  bool closedGLoop = false;
949  for (int i = 1; i <= mult; ++i) {
950  int idAbs = abs(idProd[i]);
951  if ( idAbs < 9 || (idAbs > 1000 && idAbs < 10000 && (idAbs/10)%10 == 0)
952  || idAbs == 81 || idAbs == 82 || idAbs == 83) {
953  ++nPartons;
954  idPartons.push_back(idProd[i]);
955  if (idAbs == 83) closedGLoop = true;
956  } else {
957  ++nKnown;
958  if (nPartons > 0) {
959  idProd[nKnown] = idProd[i];
960  mProd[nKnown] = mProd[i];
961  }
962  }
963  }
964 
965  // Replace generic spectator flavour code by the actual one.
966  for (int i = 0; i < nPartons; ++i) {
967  int idPart = idPartons[i];
968  int idNew = idPart;
969  if (idPart == 81) {
970  int idAbs = abs(idDec);
971  if ( (idAbs/1000)%10 == 0 ) {
972  idNew = -(idAbs/10)%10;
973  if ((idAbs/100)%2 == 1) idNew = -idNew;
974  } else if ( (idAbs/100)%10 >= (idAbs/10)%10 )
975  idNew = 100 * ((idAbs/10)%100) + 3;
976  else idNew = 1000 * ((idAbs/10)%10) + 100 * ((idAbs/100)%10) + 1;
977  if (idDec < 0) idNew = -idNew;
978 
979  // Replace generic random flavour by a randomly selected one.
980  } else if (idPart == 82 || idPart == 83) {
981  double mFlav;
982  do {
983  int idDummy = -flavSelPtr->pickLightQ();
984  FlavContainer flavDummy(idDummy, idPart - 82);
985  do idNew = flavSelPtr->pick(flavDummy).id;
986  while (idNew == 0);
987  mFlav = particleDataPtr->constituentMass(idNew);
988  } while (2. * mFlav + stopMass > mProd[0]);
989  } else if (idPart == -82 || idPart == -83) {
990  idNew = -idPartons[i-1];
991  }
992  idPartons[i] = idNew;
993  }
994 
995  // Determine whether fixed multiplicity or to be selected at random.
996  int nMin = max( 2, nKnown + nPartons / 2);
997  if (meMode == 23) nMin = 3;
998  if (meMode > 41 && meMode <= 50) nMin = meMode - 40;
999  if (meMode > 51 && meMode <= 60) nMin = meMode - 50;
1000  int nFix = 0;
1001  if (meMode == 0) nFix = nMin;
1002  if (meMode == 11) nFix = 3;
1003  if (meMode == 12) nFix = 4;
1004  if (meMode > 61 && meMode <= 70) nFix = meMode - 60;
1005  if (meMode > 71 && meMode <= 80) nFix = meMode - 70;
1006  if (nFix > 0 && nKnown + nPartons/2 > nFix) return false;
1007 
1008  // Initial values for loop to set new hadronic content.
1009  int nFilled, nTotal, nNew, nSpec, nLeft;
1010  double mDiff;
1011  int nTry = 0;
1012  bool diquarkClash = false;
1013  bool usedChannel = false;
1014 
1015  // Begin loop; interrupt if multiple tries fail.
1016  do {
1017  ++nTry;
1018  if (nTry > NTRYPICK) return false;
1019 
1020  // Initialize variables inside new try.
1021  nFilled = nKnown + 1;
1022  idProd.resize(nFilled);
1023  mProd.resize(nFilled);
1024  nTotal = nKnown;
1025  nSpec = 0;
1026  nLeft = nPartons;
1027  mDiff = mProd[0];
1028  for (int i = 1; i < nFilled; ++i) mDiff -= mProd[i];
1029  diquarkClash = false;
1030  usedChannel = false;
1031 
1032  // For weak decays collapse spectators to one particle.
1033  if ( (meMode == 22 || meMode == 23) && nLeft > 1) {
1034  FlavContainer flav1( idPartons[nPartons - 2] );
1035  FlavContainer flav2( idPartons[nPartons - 1] );
1036  int idHad;
1037  do idHad = flavSelPtr->combine( flav1, flav2);
1038  while (idHad == 0);
1039  double mHad = particleDataPtr->mSel(idHad);
1040  mDiff -= mHad;
1041  idProd.push_back( idHad);
1042  mProd.push_back( mHad);
1043  ++nFilled;
1044  nSpec = 1;
1045  nLeft -= 2;
1046  }
1047 
1048  // If there are partons left, then determine how many hadrons to pick.
1049  if (nLeft > 0) {
1050 
1051  // For B -> gamma + X use geometrical distribution.
1052  if (meMode == 31) {
1053  double geom = rndmPtr->flat();
1054  nTotal = 1;
1055  do {
1056  ++nTotal;
1057  geom *= 2.;
1058  } while (geom < 1. && nTotal < 10);
1059 
1060  // Calculate mass excess and from there average multiplicity.
1061  } else if (nFix == 0) {
1062  double multIncreaseNow = (meMode == 23)
1063  ? multIncreaseWeak : multIncrease;
1064  double mDiffPS = mDiff;
1065  for (int i = 0; i < nLeft; ++i)
1066  mDiffPS -= particleDataPtr->constituentMass( idPartons[i] );
1067  double average = 0.5 * (nKnown + nSpec) + 0.25 * nPartons
1068  + multIncreaseNow * log( max( 1.1, mDiffPS / multRefMass ) );
1069  if (closedGLoop) average += multGoffset;
1070 
1071  // Pick multiplicity according to Poissonian.
1072  double value = 1.;
1073  double sum = 1.;
1074  for (int nNow = nMin + 1; nNow <= 10; ++nNow) {
1075  value *= average / nNow;
1076  sum += value;
1077  }
1078  nTotal = nMin;
1079  value = 1.;
1080  sum *= rndmPtr->flat();
1081  sum -= value;
1082  if (sum > 0.) do {
1083  ++nTotal;
1084  value *= average / nTotal;
1085  sum -= value;
1086  } while (sum > 0. && nTotal < 10);
1087 
1088  // Alternatively predetermined multiplicity.
1089  } else {
1090  nTotal = nFix;
1091  }
1092  nNew = nTotal - nKnown - nSpec;
1093 
1094  // Set up ends of fragmented system, as copy of idPartons.
1095  flavEnds.resize(0);
1096  for (int i = 0; i < nLeft; ++i) {
1097  flavEnds.push_back( FlavContainer(idPartons[i]) );
1098  if (abs(idPartons[i]) > 100) flavSelPtr->assignPopQ( flavEnds[i] );
1099  }
1100 
1101  // Fragment off at random, but save nLeft/2 for final recombination.
1102  if (nNew > nLeft/2) {
1103  FlavContainer flavNew;
1104  int idHad;
1105  for (int i = 0; i < nNew - nLeft/2; ++i) {
1106  // When four quarks consider last one to be spectator.
1107  int iEnd = int( (nLeft - 1.) * rndmPtr->flat() );
1108  // Pick new flavour and form a new hadron.
1109  do {
1110  flavNew = flavSelPtr->pick( flavEnds[iEnd] );
1111  idHad = flavSelPtr->combine( flavEnds[iEnd], flavNew);
1112  } while (idHad == 0);
1113  // Store new hadron and endpoint flavour.
1114  idProd.push_back( idHad);
1115  flavEnds[iEnd].anti(flavNew);
1116  }
1117  }
1118 
1119  // When only two quarks left, combine to form final hadron.
1120  if (nLeft == 2) {
1121  int idHad;
1122  if ( abs(flavEnds[0].id) > 8 && abs(flavEnds[1].id) > 8)
1123  diquarkClash = true;
1124  else {
1125  do idHad = flavSelPtr->combine( flavEnds[0], flavEnds[1]);
1126  while (idHad == 0);
1127  idProd.push_back( idHad);
1128  }
1129 
1130  // If four quarks, decide how to pair them up.
1131  } else {
1132  int iEnd1 = 0;
1133  int iEnd2 = 1;
1134  int iEnd3 = 2;
1135  int iEnd4 = 3;
1136  if ( rndmPtr->flat() < colRearrange) iEnd2 = 3;
1137  int relColSign =
1138  ( (flavEnds[iEnd1].id > 0 && flavEnds[iEnd1].id < 9)
1139  || flavEnds[iEnd1].id < -10 ) ? 1 : -1;
1140  if ( (flavEnds[iEnd2].id < 0 && flavEnds[iEnd2].id > -9)
1141  || flavEnds[iEnd2].id > 10 ) relColSign *= -1;
1142  if (relColSign == 1) iEnd2 = 2;
1143  if (iEnd2 == 2) iEnd3 = 1;
1144  if (iEnd2 == 3) iEnd4 = 1;
1145 
1146  // Then combine to get final two hadrons.
1147  int idHad;
1148  if ( abs(flavEnds[iEnd1].id) > 8 && abs(flavEnds[iEnd2].id) > 8)
1149  diquarkClash = true;
1150  else {
1151  do idHad = flavSelPtr->combine( flavEnds[iEnd1], flavEnds[iEnd2]);
1152  while (idHad == 0);
1153  idProd.push_back( idHad);
1154  }
1155  if ( abs(flavEnds[iEnd3].id) > 8 && abs(flavEnds[iEnd4].id) > 8)
1156  diquarkClash = true;
1157  else {
1158  do idHad = flavSelPtr->combine( flavEnds[iEnd3], flavEnds[iEnd4]);
1159  while (idHad == 0);
1160  idProd.push_back( idHad);
1161  }
1162  }
1163 
1164  // Find masses of the new hadrons.
1165  for (int i = nFilled; i < int(idProd.size()) ; ++i) {
1166  double mHad = particleDataPtr->mSel(idProd[i]);
1167  mProd.push_back( mHad);
1168  mDiff -= mHad;
1169  }
1170  }
1171 
1172  // Optional: check that this decay mode is not explicitly defined.
1173  if ( ( (meMode > 51 && meMode <= 60) || (meMode > 71 && meMode <= 80) )
1174  && mDiff > mSafety && !diquarkClash ) {
1175  int idMatch[10], idPNow;
1176  usedChannel = false;
1177  bool matched = false;
1178  // Loop through all channels. Done if not same multiplicity.
1179  for (int i = 0; i < decDataPtr->sizeChannels(); ++i) {
1180  DecayChannel& channel = decDataPtr->channel(i);
1181  if (channel.multiplicity() != nTotal) continue;
1182  for (int k = 0; k < nTotal; ++k) idMatch[k] = channel.product(k);
1183  // Match particles one by one until fail.
1184  // Do not distinguish K0/K0bar/K0short/K0long at this stage.
1185  for (int j = 0; j < nTotal; ++j) {
1186  matched = false;
1187  idPNow = idProd[j + 1];
1188  if (idPNow == -311 || idPNow == 130 || idPNow == 310) idPNow = 311;
1189  for (int k = 0; k < nTotal - j; ++k)
1190  if (idMatch[k] == idPNow || (idMatch[k] == -311 && idPNow == 311)) {
1191  // Compress list of unmatched when matching worked.
1192  idMatch[k] = idMatch[nTotal - 1 - j];
1193  matched = true;
1194  break;
1195  }
1196  if (!matched) break;
1197  }
1198  // If matching worked, then chosen channel to be rejected.
1199  if (matched) {usedChannel = true; break;}
1200  }
1201  }
1202 
1203  // Keep on trying until enough phase space and no clash.
1204  } while (mDiff < mSafety || diquarkClash || usedChannel);
1205 
1206  // Update particle multiplicity.
1207  mult = idProd.size() - 1;
1208 
1209  // For Dalitz decays shuffle Dalitz pair to the end of the list.
1210  if (meMode == 11 || meMode == 12) {
1211  int iL1 = 0;
1212  int iL2 = 0;
1213  for (int i = 1; i <= mult; ++i) {
1214  if (idProd[i] == 11 || idProd[i] == 13 || idProd[i] == 15) iL1 = i;
1215  if (idProd[i] == -11 || idProd[i] == -13 || idProd[i] == -15) iL2 = i;
1216  }
1217  if (iL1 > 0 && iL2 > 0) {
1218  int idL1 = idProd[iL1];
1219  int idL2 = idProd[iL2];
1220  double mL1 = mProd[iL1];
1221  double mL2 = mProd[iL2];
1222  int iMove = 0;
1223  for (int i = 1; i <= mult; ++i) if (i != iL1 && i != iL2) {
1224  ++iMove;
1225  idProd[iMove] = idProd[i];
1226  mProd[iMove] = mProd[i];
1227  }
1228  idProd[mult - 1] = idL1;
1229  idProd[mult] = idL2;
1230  mProd[mult - 1] = mL1;
1231  mProd[mult] = mL2;
1232  }
1233  }
1234 
1235  // Done.
1236  return true;
1237 
1238 }
1239 
1240 //--------------------------------------------------------------------------
1241 
1242 // Set colour flow and scale in a decay explicitly to partons.
1243 
1244 bool ParticleDecays::setColours(Event& event) {
1245 
1246  // Decay to q qbar (or qbar q).
1247  if (meMode == 91 && idProd[1] > 0 && idProd[1] < 9) {
1248  int newCol = event.nextColTag();
1249  cols[1] = newCol;
1250  acols[2] = newCol;
1251  } else if (meMode == 91 && idProd[1] < 0 && idProd[1] > -9) {
1252  int newCol = event.nextColTag();
1253  cols[2] = newCol;
1254  acols[1] = newCol;
1255 
1256  // Decay to g g.
1257  } else if (meMode == 91 && idProd[1] == 21) {
1258  int newCol1 = event.nextColTag();
1259  int newCol2 = event.nextColTag();
1260  cols[1] = newCol1;
1261  acols[1] = newCol2;
1262  cols[2] = newCol2;
1263  acols[2] = newCol1;
1264 
1265  // Decay to g g g.
1266  } else if (meMode == 92 && idProd[1] == 21 && idProd[2] == 21
1267  && idProd[3] == 21) {
1268  int newCol1 = event.nextColTag();
1269  int newCol2 = event.nextColTag();
1270  int newCol3 = event.nextColTag();
1271  cols[1] = newCol1;
1272  acols[1] = newCol2;
1273  cols[2] = newCol2;
1274  acols[2] = newCol3;
1275  cols[3] = newCol3;
1276  acols[3] = newCol1;
1277 
1278  // Decay to g g gamma: locate which is gamma.
1279  } else if (meMode == 92) {
1280  int iGlu1 = (idProd[1] == 21) ? 1 : 3;
1281  int iGlu2 = (idProd[2] == 21) ? 2 : 3;
1282  int newCol1 = event.nextColTag();
1283  int newCol2 = event.nextColTag();
1284  cols[iGlu1] = newCol1;
1285  acols[iGlu1] = newCol2;
1286  cols[iGlu2] = newCol2;
1287  acols[iGlu2] = newCol1;
1288 
1289  // Unknown decay mode means failure.
1290  } else return false;
1291 
1292  // Set maximum scale to be mass of decaying particle.
1293  scale = mProd[0];
1294 
1295  // Done.
1296  return true;
1297 
1298 }
1299 
1300 //==========================================================================
1301 
1302 } // end namespace Pythia8
Definition: AgUStep.h:26