test_hepmc.cc

Go to the documentation of this file.
00001 // ----------------------------------------------------------------------
00002 // 
00003 // ----------------------------------------------------------------------
00004 
00005 #include <iostream>
00006 #include <sstream>
00007 #include <vector>
00008 #include <cmath>
00009 
00010 #include "HepMC/GenEvent.h"
00011 #include "HepMC/SimpleVector.h"
00012 
00013 #include "test_hepmc.h"
00014 
00015 using namespace std;
00016 
00017 // ----------------------------------------------------------------------
00018 bool testHepMC( const HepMC::GenEvent* genEvt )
00019 {
00020   double totalPx = 0;
00021   double totalPy = 0;
00022   double totalPz = 0;
00023   double totalE  = 0;
00024   vector< int > negEnPart;
00025   vector< int > tacheons;
00026   vector< int > orphans;
00027   vector< int > unstNoEnd;
00028   vector< int > unDecPi0;
00029   
00030   const int k_pdg = 15;
00031   const double k_energy_diff = 1000.;
00032   const double k_cm_energy = 7000000.;
00033   //const double k_cm_energy = 14000000.;
00034 
00035   for ( HepMC::GenEvent::particle_const_iterator pitr = genEvt->particles_begin();
00036          pitr != genEvt->particles_end(); ++pitr ) {
00037 
00038       // Check for NaNs
00039     if ( std::isnan((*pitr)->momentum().px()) || std::isinf((*pitr)->momentum().px()) ||
00040       std::isnan((*pitr)->momentum().py()) || std::isinf((*pitr)->momentum().py()) ||
00041       std::isnan((*pitr)->momentum().pz()) || std::isinf((*pitr)->momentum().pz()) ||
00042       std::isnan((*pitr)->momentum().e())  || std::isinf((*pitr)->momentum().e()) ) {
00043 
00044       cerr << "NaN (Not A Number) found in the event record" << endl;
00045       return false;
00046     }
00047 
00048       // Check for undecayed pi0
00049     if ( (*pitr)->pdg_id() == 111 && !(*pitr)->end_vertex() ) {
00050       unDecPi0.push_back( (*pitr)->barcode());
00051     }
00052 
00053 
00054     // Check for unstables with no end vertex, such as undecayed gluons
00055     if ( (*pitr)->status() == 2 && !(*pitr)->end_vertex() ) {
00056       // NB. PYTHIA 6.4xx with MSTP(95)=2 produces zero momentum gluons
00057       bool notdumglu = true;
00058 
00059       /// @todo BPK: "temporarily" disabled: WHY?
00060       notdumglu = false;
00061       //if ((*pitr)->pdg_id() == 21 && (*pitr)->momentum().mag() == 0.) {   // new version of HepMC uses 'rho' insted of 'mag'
00062       if ((*pitr)->pdg_id() == 21 && (*pitr)->momentum().rho() == 0.) {
00063         cout << "Dummy gluon found! BARCODE=" << (*pitr)->barcode() << endl;
00064         notdumglu = false;
00065       }
00066       if (notdumglu) {
00067         unstNoEnd.push_back((*pitr)->barcode());
00068       }
00069     }
00070 
00071 
00072     // Check for production vertices of stable and unstable particles (documentary particles are not included in the check)
00073     if ( (*pitr)->status() == 1 || (*pitr)->status() == 2) {
00074       // Sequential resonance decays in PYTHIA externals (e.g. AcerMC tt~) don't have bosons hooked up to anywhere so skip
00075       // Also, a pythia bug has zero parent strings attached.
00076       // if (!(*pitr)->production_vertex()) orphans.push_back((*pitr)->barcode());
00077 
00078       // "Temporarily" disable check (WHY?)
00079       bool tmpdisable = true;
00080       if (!(*pitr)->production_vertex()) {
00081         if (!tmpdisable) {
00082           if (!(abs((*pitr)->pdg_id()) > 20 && abs((*pitr)->pdg_id()) < 27) &&
00083               !(abs((*pitr)->pdg_id()) < 10)) {
00084             if (abs((*pitr)->pdg_id()) != 2101 &&
00085                 abs((*pitr)->pdg_id()) != 2103 && abs((*pitr)->pdg_id()) != 2203 &&
00086                 abs((*pitr)->pdg_id()) != 2201) {
00087               orphans.push_back((*pitr)->barcode());
00088               cout << "Orphan found! BARCODE=" << (*pitr)->barcode() << ", ID= " << (*pitr)->pdg_id() << endl;
00089             }
00090           }
00091         }
00092       } else if (!((*pitr)->production_vertex()->particles_in_size()) &&  !tmpdisable) {
00093     // HERWIG record inserts initial particles with production vertex but no particle attached to it, check for px, py > 0
00094         if ((*pitr)->momentum().px() > 1e-7 ||  (*pitr)->momentum().py() > 1e-7) {
00095           orphans.push_back((*pitr)->barcode());
00096         }
00097       }
00098     }
00099 
00100 
00101     if ( (*pitr)->status() == 1 && !(*pitr)->end_vertex() ) {
00102       totalPx += (*pitr)->momentum().px();
00103       totalPy += (*pitr)->momentum().py();
00104       totalPz += (*pitr)->momentum().pz();
00105       totalE  += (*pitr)->momentum().e();
00106       if ( (*pitr)->momentum().e() < 0. ) negEnPart.push_back((*pitr)->barcode());
00107         //      double mass2 = (*pitr)->momentum().e()*(*pitr)->momentum().e() -
00108         //        (*pitr)->momentum().px()*(*pitr)->momentum().px() -
00109         //        (*pitr)->momentum().py()*(*pitr)->momentum().py() -
00110         //        (*pitr)->momentum().pz()*(*pitr)->momentum().pz();
00111         //      if ( mass2 < 0. ) tacheons.push_back((*pitr)->barcode());
00112       double aener = fabs((*pitr)->momentum().e());
00113       if ( aener < fabs((*pitr)->momentum().px()) ||
00114            aener < fabs((*pitr)->momentum().py()) ||
00115            aener < fabs((*pitr)->momentum().pz()) ) {
00116         tacheons.push_back((*pitr)->barcode());
00117       }
00118     }
00119 
00120     int p_id = (*pitr)->pdg_id();
00121     int tau_child = 0;
00122     if (abs(p_id) == k_pdg && (*pitr)->status() < 3) {
00123       HepMC::GenVertex *vtx = (*pitr)->end_vertex();
00124       if (vtx) {
00125         double p_energy = 0;
00126         for ( HepMC::GenVertex::particle_iterator desc = (vtx)->particles_begin(HepMC::descendants);
00127               desc != (vtx)->particles_end(HepMC::descendants); ++desc) {
00128           if (abs((*desc)->pdg_id() )== k_pdg) tau_child =1;
00129           if ((*desc)->status()==1) p_energy += (*desc)->momentum().e();
00130         }
00131         if (fabs( p_energy - (*pitr)->momentum().e()) > k_energy_diff && !tau_child) {
00132           cout << "EnergySum (decay products) - "
00133                << "Energy (original particle) > " << k_energy_diff << " MeV, "
00134                << "Event #" << genEvt->event_number() << ", "
00135                << "Barcode of the original particle = " << (*pitr)->barcode() << endl;
00136         }
00137       } else {
00138         cout << "UNDECAYED PARTICLE WITH PDG_ID = " << k_pdg << endl;
00139       }
00140     }
00141   }
00142 
00143 
00144     // Energy Balance
00145   double loste = fabs(totalE - k_cm_energy);
00146   if ( loste > k_energy_diff ) {
00147     cout << "ENERGY BALANCE FAILED : E-difference = " << loste << " MeV" << endl;
00148     return false;
00149   }
00150 
00151     // Momentum Balance
00152   if ( fabs(totalPx) > k_energy_diff || fabs(totalPy) > k_energy_diff || fabs(totalPz) > k_energy_diff ) {
00153     cout << "MOMENTUM BALANCE FAILED : SumPx = " << totalPx << " SumPy = " <<  totalPy << " SumPz = " <<  totalPz << " MeV"<< endl;
00154     return false;
00155   }
00156 
00157     // Negative energy particles
00158   if (negEnPart.size() > 0) {
00159     stringstream ss;
00160     ss << "NEGATIVE ENERGY PARTICLES FOUND : BARCODES =";
00161     for (vector<int>::const_iterator b = negEnPart.begin(); b != negEnPart.end(); ++b)
00162       ss << " " << *b;
00163     cout << ss.str() << endl;
00164     return false;
00165   }
00166 
00167     // Tacheons
00168   if (tacheons.size() > 0) {
00169     stringstream ss;
00170     ss << "PARTICLES WITH |E| < |Pi| (i=x,y,z) FOUND : BARCODES =";
00171     for (vector<int>::const_iterator b = tacheons.begin(); b != tacheons.end(); ++b)
00172       ss << " " << *b;
00173     cout << ss.str() << endl;
00174     return false;
00175   }
00176 
00177     // Stable or unstable particles with no parent (no documentaries)
00178   if (orphans.size() > 0) {
00179     stringstream ss;
00180     ss << "Particle with no parent found: BARCODES =";
00181     for (vector<int>::const_iterator b = orphans.begin(); b != orphans.end(); ++b)
00182       ss << " " << *b;
00183     cout << ss.str() << endl;
00184     return false;
00185   }
00186 
00187     // Unstable particles with no decay vertex
00188   if (unstNoEnd.size() > 0) {
00189     stringstream ss;
00190     ss << "Unstable particle with no decay vertex found: BARCODES =";
00191     for (vector<int>::const_iterator b = unstNoEnd.begin(); b != unstNoEnd.end(); ++b)
00192       ss << " " << *b;
00193     cout << ss.str() << endl;
00194     return false;
00195   }
00196 
00197     // Undecayed pi0
00198   if (unDecPi0.size() > 0) {
00199     stringstream ss;
00200     ss << "pi0 with no decay vertex found: BARCODES =";
00201     for (vector<int>::const_iterator b = unDecPi0.begin(); b != unDecPi0.end(); ++b)
00202       ss << " " << *b;
00203     cout << ss.str() << endl;;
00204     return false;
00205   }
00206 
00207   return true; 
00208 }
00209 

Generated on Wed Aug 31 09:44:47 2011 for HepMCAnalysis by  doxygen 1.4.7