StdHepToLcioConvertor.cc

Go to the documentation of this file.
00001 // $Header: /cvs/lcd/slic/src/StdHepToLcioConvertor.cc,v 1.32 2007/04/27 01:54:35 jeremy Exp $
00002 #include "StdHepToLcioConvertor.hh"
00003 
00004 // slic
00005 #include "LcioMcpManager.hh"
00006 
00007 // lcio
00008 #include "IMPL/LCEventImpl.h"
00009 #include "UTIL/LCTOOLS.h"
00010 
00011 // geant4
00012 #include "G4ParticleDefinition.hh"
00013 #include "G4ParticleTable.hh"
00014 
00015 // stl
00016 #include <cassert>
00017 #include <cmath>
00018 
00019 using EVENT::LCIO;
00020 using EVENT::LCCollection;
00021 using IMPL::LCEventImpl;
00022 using IMPL::MCParticleImpl;
00023 using UTIL::LCTOOLS;
00024 
00025 namespace slic
00026 {
00027   StdHepToLcioConvertor::StdHepToLcioConvertor(lStdHep* rdr)
00028     : Module("StdHepToLcioConverter"),
00029       m_reader(rdr)
00030   {
00031     assert( rdr );
00032   }
00033 
00034   StdHepToLcioConvertor::StdHepToLcioConvertor()
00035     : Module("StdHepToLcioConverter"),
00036       m_reader(0)
00037   {}
00038 
00039   StdHepToLcioConvertor::~StdHepToLcioConvertor()
00040   {}
00041 
00042   void StdHepToLcioConvertor::setCurrentMcpCollection(EVENT::LCCollection* mcpColl)
00043   {
00044     m_currentMcpColl = mcpColl;
00045   }
00046 
00047   EVENT::LCCollection* StdHepToLcioConvertor::getCurrentMcpCollection()
00048   {
00049     return m_currentMcpColl;
00050   }
00051 
00052   void StdHepToLcioConvertor::fillCurrentMcpCollectionFromStdHep()
00053   {
00054 #ifdef SLIC_LOG
00055     log() << LOG::debug << "********** Creating LCIO MCParticle Collection from StdHep **********" << LOG::done;
00056 #endif
00057 
00058     assert( m_reader );
00059     assert( m_currentMcpColl );
00060 
00061 #ifdef SLIC_LOG
00062     log() << LOG::debug << "******** loop 1: create MCParticles ********" << LOG::done;
00063 #endif
00064 
00065     /* Loop #1 : Create MCParticles with no parentage or daughter links. */
00066     int ntracks = m_reader->nTracks();
00067     for ( int ihep = 0;
00068           ihep < ntracks;
00069           ihep++ ) {
00070 
00071 #ifdef SLIC_DEBUG
00072       printTrack( ihep );
00073 #endif
00074 
00075 #ifdef SLIC_DEBUG
00076       checkParentage( ihep );
00077 #endif
00078 
00079       // create MCP and add to coll
00080       createMcpFromStdHep( ihep );
00081 
00082 #ifdef SLIC_LOG
00083       log() << LOG::debug << LOG::endl << "--" << LOG::endl << LOG::done;
00084 #endif
00085     }
00086 
00087 #ifdef SLIC_LOG
00088     log() << LOG::debug << "******** loop 2: parent setup ********" << LOG::done << LOG::done;
00089 #endif
00090 
00091     /* Loop #2 : Set the MCParticle parentage. */
00092     for ( int ihep = 0;
00093           ihep < ntracks;
00094           ihep++ ) {
00095 
00096 #ifdef SLIC_LOG
00097       printIndex( ihep );
00098       printMothers( ihep );      
00099 #endif
00100 
00101       MCParticleImpl* mcp =
00102         dynamic_cast<MCParticleImpl*> ( m_currentMcpColl->getElementAt(ihep) );
00103 
00104       if ( mcp ) {
00105         setupParents( ihep, mcp );
00106       }
00107 
00108 #ifdef SLIC_LOG
00109       log() << LOG::debug << LOG::done << "--" << LOG::done << LOG::done;
00110 #endif
00111 
00112     }
00113 
00114 #ifdef SLIC_LOG
00115     log() << LOG::debug << "******** loop 3: daughter setup ********" << LOG::done << LOG::done;
00116 #endif
00117 
00118     /* Loop #3 : Setup the daughters. */
00119     for ( int ihep = 0;
00120           ihep < ntracks;
00121           ihep++ ) {
00122 
00123 #ifdef SLIC_LOG
00124       printIndex( ihep );
00125       printDaughters( ihep );
00126 #endif
00127 
00128       MCParticleImpl* mcp =
00129         dynamic_cast<MCParticleImpl*> ( m_currentMcpColl->getElementAt(ihep) );
00130 
00131       if ( mcp ) {
00132         setupDaughters( ihep, mcp );
00133       }
00134       else {
00135         log() << LOG::error << "mcp is null; ihep <" << ihep << "> does not appear to be a valid idx!" << LOG::done;
00136       }
00137 
00138 #ifdef SLIC_LOG
00139       log() << LOG::debug << LOG::done << "--" << LOG::done << LOG::done;
00140 #endif
00141 
00142     }
00143 
00144 #ifdef SLIC_LOG
00145     log() << LOG::debug << LOG::done;
00146 #endif
00147   }
00148 
00149   IMPL::MCParticleImpl* StdHepToLcioConvertor::createMcpFromStdHep( int ihep )
00150   {
00151     // new MCP
00152     MCParticleImpl* mcp = new MCParticleImpl();
00153 
00154     // PDG
00155     int pdgid = m_reader->pid( ihep );
00156     mcp->setPDG(pdgid);
00157 
00158     G4ParticleDefinition* pdef = G4ParticleTable::GetParticleTable()->FindParticle(pdgid);
00159 
00160 #ifdef SLIC_LOG
00161     if ( pdef != 0 ) {
00162       log() << LOG::debug << "found pdef for particle <" << pdef->GetParticleName() << "> with pdgid <" << pdgid << ">" << LOG::done;
00163     }
00164     else {
00165       log() << LOG::debug << "no pdef for pdgid <" << pdgid << ">" << LOG::done;
00166     }
00167 #endif
00168 
00169     /*
00170      * Geant4 Particle definition exists for this MCParticle,
00171      * so set the charge from it.
00172      */
00173     if ( pdef != 0 ) {
00174       mcp->setCharge( pdef->GetPDGCharge() );
00175     }
00176     /*
00177      * No Geant4 particle definition, so flag charge as invalid.
00178      */
00179     else {
00180       mcp->setCharge( LcioMcpManager::m_NAN );
00181     }
00182 
00183     // momentum vec
00184     float p[3] = { m_reader->Px( ihep ),
00185                    m_reader->Py( ihep ),
00186                    m_reader->Pz( ihep ) };
00187     mcp->setMomentum( p );
00188 
00189     // mass
00190     mcp->setMass( m_reader->M( ihep ) );
00191 
00192     // vertex
00193     double vtx[3] = { m_reader->X( ihep ),
00194                       m_reader->Y( ihep ),
00195                       m_reader->Z( ihep ) };
00196     mcp->setVertex( vtx );
00197 
00198     // generator status
00199     mcp->setGeneratorStatus( m_reader->status( ihep ) );
00200 
00201     // sim status = none
00202     mcp->setSimulatorStatus( 0 );
00203 
00204     // creation time
00205     mcp->setTime( m_reader->T( ihep ) / c_light );
00206 
00207     // add to mcpColl
00208      m_currentMcpColl->addElement( mcp );
00209 
00210     return mcp;
00211   }
00212 
00213   // util functions
00214   void StdHepToLcioConvertor::setupParents( int ihep, IMPL::MCParticleImpl* mcp )
00215   {
00216 #ifdef SLIC_LOG
00217     log() << LOG::debug << "setupParents" << LOG::done;
00218 #endif
00219 
00220     // get parent indices
00221     int mom1_idx = m_reader->mother1( ihep ) - 1;
00222     int mom2_idx = m_reader->mother2( ihep ) - 1;
00223 
00224     std::vector<int> parVec;
00225     makeIndexVec( mom1_idx, mom2_idx, parVec );
00226 
00227     if ( parVec.size() > 0 ) {
00228       for ( std::vector<int>::iterator it = parVec.begin();
00229             it != parVec.end();
00230             it++ ) {
00231         if ( *it != ihep ) {
00232           addMcpParent( *it, mcp );
00233         }
00234 #ifdef SLIC_LOG
00235         else {
00236           log() << LOG::warning << "Ignoring parent pointing to self!" << LOG::done;
00237         }
00238 #endif
00239       }
00240     }
00241 #ifdef SLIC_LOG
00242     log() << LOG::debug << "particle has no parents" << LOG::done;    
00243 #endif
00244   }
00245 
00246   void StdHepToLcioConvertor::setupDaughters( int ihep, IMPL::MCParticleImpl* mcp )
00247   {
00248 #ifdef SLIC_LOG
00249     log() << LOG::debug << "setupDaughters" << LOG::done;    
00250 #endif
00251 
00252     // get dau indices
00253     int dau1_idx = m_reader->daughter1( ihep ) % 10000 - 1;
00254     int dau2_idx = m_reader->daughter2( ihep ) % 10000 - 1;
00255 
00256     std::vector<int> dauVec;
00257     dauVec = makeIndexVec( dau1_idx, dau2_idx, dauVec );
00258 
00259     if ( dauVec.size() > 0 ) {
00260       for ( std::vector<int>::iterator it = dauVec.begin();
00261             it != dauVec.end();
00262             it++ ) {
00263         if ( *it != ihep ) {
00264           addMcpDaughter( *it, mcp );
00265         }
00266         else {
00267           log() << LOG::error << "Ignoring daughter pointing to self!" << LOG::done;
00268         }
00269       }
00270     }
00271 #ifdef SLIC_LOG
00272     else {
00273       log() << LOG::debug << "particle has no daughters" << LOG::done;
00274     }
00275 #endif
00276   }
00277 
00278   bool StdHepToLcioConvertor::hasParent( IMPL::MCParticleImpl* dauMcp, IMPL::MCParticleImpl* parMcp)
00279   {
00280     bool isPar = false;
00281     if ( dauMcp && parMcp ) {
00282       int numParents = dauMcp->getParents().size();
00283 
00284       MCParticleImpl* pMomMcp;
00285 
00286       // find if already lists as parent
00287       for ( int i = 0;
00288             i < numParents;
00289             i++ ) {
00290 
00291         pMomMcp = static_cast<MCParticleImpl*>
00292           ( dauMcp->getParents()[i] );
00293 
00294         if ( pMomMcp == parMcp ) {
00295           isPar = true;
00296           break;
00297         }
00298       }
00299     }
00300 
00301     return isPar;
00302   }
00303 
00304   void StdHepToLcioConvertor::addMcpDaughter( int dauIdx, IMPL::MCParticleImpl* parMcp )
00305   {
00306     if ( dauIdx >= 0 ) {
00307 
00308       MCParticleImpl* dauMcp = static_cast<MCParticleImpl*>
00309         ( m_currentMcpColl->getElementAt( dauIdx ) );
00310       assert( dauMcp );
00311 
00312       if ( dauMcp ) {
00313         if ( !hasParent( dauMcp, parMcp ) ) {
00314           dauMcp->addParent( parMcp );
00315 
00316 #ifdef SLIC_LOG
00317           log() << LOG::debug << "added daughter <" << dauIdx << ">" << LOG::done;
00318 #endif
00319         }
00320 #ifdef SLIC_LOG
00321         else {
00322           log() << LOG::debug << "daughter <" << dauIdx << "> already has this parent" << LOG::done;
00323         }
00324 #endif
00325       }
00326 #ifdef SLIC_LOG
00327       else {
00328         log() << LOG::error << "WARNING: dauMcp or parMcp is null!" << LOG::done;
00329       }
00330 #endif
00331 
00332     }
00333   }
00334 
00335   void StdHepToLcioConvertor::addMcpParent( int parIdx, IMPL::MCParticleImpl* mcp )
00336   {
00337 #ifdef SLIC_LOG
00338     log() << LOG::debug << "addMcpParent" << LOG::done;
00339 #endif
00340 
00341     if ( parIdx >= 0 ) {
00342 
00343       /* If index is > size of collection, the particle's parent doesn't exist yet.  We need to die! */
00344       if ( parIdx > m_currentMcpColl->getNumberOfElements() ) {
00345 #ifdef SLIC_LOG
00346         log() << LOG::fatal << "StdHepToLcioConverter::addMcpParent - Parent index is out of range <" << parIdx << ">" << LOG::done;
00347 #endif
00348         G4Exception("ERROR: StdHep index (ihep) is out of range.");
00349       }
00350 
00351       MCParticleImpl* parMcp = static_cast<MCParticleImpl*>
00352         ( m_currentMcpColl->getElementAt( parIdx ) );
00353 
00354       if ( parMcp ) {
00355         if ( !hasParent(mcp, parMcp) ) {
00356           mcp->addParent( parMcp );
00357 
00358 #ifdef SLIC_LOG
00359           log() << LOG::debug << "added parent <" << parIdx << ">" << LOG::done;
00360 #endif
00361         }
00362 #ifdef SLIC_LOG
00363         else {
00364           log() << LOG::debug << "daughter already has parent <" << parIdx << ">" << LOG::done;
00365         }
00366 #endif
00367       }
00368       else {
00369         G4Exception("Failed to get parent particle from MCParticle collection.");
00370       }
00371     }
00372 #ifdef SLIC_LOG
00373     else {
00374       log() << LOG::debug << "ignoring parIdx = -1 " << LOG::done;
00375     }
00376 #endif
00377   }
00378 
00379   std::vector<int> StdHepToLcioConvertor::makeIndexVec( int idx1, int idx2, std::vector<int>& vec )
00380   {
00381 #ifdef SLIC_LOG
00382     log() << LOG::debug << "idx1 <" << idx1 << ">" << LOG::done;
00383     log() << LOG::debug << "idx2 <" << idx2 << ">" << LOG::done;  
00384 #endif
00385 
00386     if ( idx1 >= 0 && idx2 >= 0 ) {
00387 
00388       if ( idx1 < idx2 ) {
00389 
00390 #ifdef SLIC_LOG
00391         log() << LOG::debug << "range: idx1 to idx2" << LOG::done;
00392 #endif
00393 
00394         for ( int i = idx1;
00395               i < (idx2 + 1);
00396               i++ ) {
00397           vec.push_back(i);
00398         }
00399       }
00400       else if ( idx1 > idx2 ) {
00401 
00402 #ifdef SLIC_LOG
00403         log() << LOG::debug << "discrete: idx1 and idx2" << LOG::done;
00404 #endif
00405 
00406         vec.push_back(idx1);
00407         vec.push_back(idx2);
00408       }
00409       // indices are equal
00410       else {
00411 
00412 #ifdef SLIC_LOG
00413         log() << LOG::debug << "single: idx1 == idx2" << LOG::done;     
00414 #endif
00415 
00416         vec.push_back(idx1);
00417       }
00418     }
00419     else if ( idx1 >= 0 ) {
00420 
00421 #ifdef SLIC_LOG
00422       log() << LOG::debug << "single: idx1 only" << LOG::done;
00423 #endif
00424 
00425       vec.push_back(idx1);
00426     }
00427     else if ( idx2 >= 0 ) {
00428 
00429 #ifdef SLIC_LOG
00430         log() << LOG::debug << "single: idx2 only" << LOG::done;
00431 #endif
00432 
00433       vec.push_back(idx2);
00434     }
00435 
00436     return vec;
00437   }
00438 
00439   void StdHepToLcioConvertor::printIndex( int ihep )
00440   {
00441     log() << LOG::debug << "ihep <" << ihep << ">" << LOG::done;
00442   }
00443 
00444   void StdHepToLcioConvertor::printMothers( int ihep )
00445   {
00446     log() << LOG::debug << "mom1 <" << m_reader->mother1(ihep) - 1 << ">" << LOG::done;
00447     log() << LOG::debug << "mom2 <" << m_reader->mother2(ihep) - 1 << ">" << LOG::done;
00448   }
00449 
00450   void StdHepToLcioConvertor::printDaughters( int ihep )
00451   {
00452     log() << LOG::debug << "dau1 <" << m_reader->daughter1(ihep) - 1 << ">" << LOG::done;
00453     log() << LOG::debug << "dau2 <" << m_reader->daughter2(ihep) - 1 << ">" << LOG::done;
00454   }
00455 
00456   void StdHepToLcioConvertor::printTrack( int ihep )
00457   {
00458     printIndex( ihep );
00459 
00460     log() << LOG::debug << "pid <" << m_reader->pid( ihep ) << ">" << LOG::done;
00461     log() << LOG::debug << "M = " << m_reader->M( ihep ) << LOG::done;
00462     log() << LOG::debug << "T = " << m_reader->T( ihep ) << LOG::done;
00463     log() << LOG::debug << "status <" << m_reader->status( ihep ) << ">" << LOG::done;
00464 
00465     printMothers(ihep);
00466     printDaughters(ihep);
00467 
00468     log() << LOG::debug << "P = ("
00469          << m_reader->Px( ihep ) << ", "
00470          << m_reader->Py( ihep ) << ", "
00471          << m_reader->Pz( ihep) << ")"
00472          << LOG::done;
00473 
00474     log() << LOG::debug << "Vtx = ("
00475          << m_reader->X( ihep ) << ", "
00476          << m_reader->Y( ihep ) << ", "
00477          << m_reader->Z( ihep ) << ")"
00478          << LOG::done;
00479 
00480     log() << LOG::debug << LOG::done;
00481   }
00482 
00483   void StdHepToLcioConvertor::checkParentage(int ihep )
00484   {
00485     int mom1 = m_reader->mother1(ihep) - 1;
00486     int mom2 = m_reader->mother2(ihep) - 1;
00487     int dau1 = m_reader->daughter1(ihep) - 1;
00488     int dau2 = m_reader->daughter2(ihep) -1;
00489 
00490     // dau1 < ihep
00491     if ( dau1 >= 0 && dau1 < ihep ) {
00492       log() << LOG::debug << "WARNING: dau1 < ihep" << LOG::done;
00493     }
00494 
00495     // dau2 < ihep
00496     if ( dau2 >= 0 && dau2 < ihep ) {
00497       log() << LOG::debug << "WARNING: dau2 < ihep" << LOG::done;
00498     }
00499 
00500     // mom1 > ihep
00501     if ( mom1 >= 0 && mom1 > ihep ) {
00502       log() << LOG::debug << "WARNING: mom1 > ihep" << LOG::done;
00503     }
00504 
00505     // mom2 > ihep
00506     if ( mom2 >= 0 && mom2 > ihep ) {
00507       log() << LOG::debug << "WARNING: mom2 > ihep" << LOG::done;
00508     }
00509 
00510     // first particle in list has parents
00511     if ( ihep == 0 && ( mom1 >= 0 || mom2 >= 0 ) ) {
00512       log() << LOG::debug << "WARNING: ihep == 0 has parents" << LOG::done;
00513     }
00514 
00515     // particle past first 2 with no mother
00516     if ( ihep > 1 && ( mom1 < 0 && mom2 < 0 ) ) {
00517       log() << LOG::debug << "WARNING: ihep > 1 with no mother" << LOG::done;
00518     }
00519 
00520     // mother points to self
00521     if ( ihep == mom1 || ihep == mom2 ) {
00522       log() << LOG::debug << "WARNING: mom1 or mom2 == ihep" << LOG::done;
00523     }
00524 
00525     // daughter points to self
00526     if ( ihep == dau1 || ihep == dau2 ) {
00527       log() << LOG::debug << "WARNING: dau1 or dau2 == ihep" << LOG::done;
00528     }
00529   }
00530 
00531 } // namespace slic

Generated on Thu Nov 15 15:24:16 2007 for Simulator for the Linear Collider by  doxygen 1.5.4