Fork me on GitHub

source: svn/trunk/Utilities/HepMC/src/GenParticle.cc@ 961

Last change on this file since 961 was 571, checked in by cp3-support, 13 years ago

upgrade HepMC to version 2.06.05

File size: 9.0 KB
Line 
1//////////////////////////////////////////////////////////////////////////
2// Matt.Dobbs@Cern.CH, September 1999
3// Updated: 07.02.2000 no longer does particle point to ParticleData,
4// but rather it uses an int id which can be looked up
5// particle within an event coming in/out of a vertex
6//////////////////////////////////////////////////////////////////////////
7#include "GenEvent.h"
8#include "GenVertex.h"
9#include "GenParticle.h"
10#include <iomanip> // needed for formatted output
11
12namespace HepMC {
13
14 GenParticle::GenParticle( void ) :
15 m_momentum(0), m_pdg_id(0), m_status(0), m_flow(this),
16 m_polarization(0), m_production_vertex(0), m_end_vertex(0),
17 m_barcode(0), m_generated_mass(0.)
18 {}
19 //{
20 //s_counter++;
21 //}
22
23 GenParticle::GenParticle( const FourVector& momentum,
24 int pdg_id, int status,
25 const Flow& itsflow,
26 const Polarization& polar ) :
27 m_momentum(momentum), m_pdg_id(pdg_id), m_status(status), m_flow(this),
28 m_polarization(polar), m_production_vertex(0), m_end_vertex(0),
29 m_barcode(0), m_generated_mass(momentum.m())
30 {
31 // Establishing *this as the owner of m_flow is done above,
32 // then we set it equal to the other flow pattern (subtle)
33 set_flow(itsflow);
34 //s_counter++;
35 }
36
37 GenParticle::GenParticle( const GenParticle& inparticle ) :
38 m_momentum( inparticle.momentum() ),
39 m_pdg_id( inparticle.pdg_id() ),
40 m_status( inparticle.status() ),
41 m_flow(inparticle.flow()),
42 m_polarization( inparticle.polarization() ),
43 m_production_vertex(0),
44 m_end_vertex(0),
45 m_barcode(0),
46 m_generated_mass( inparticle.generated_mass() )
47 {
48 /// Shallow copy: does not copy the vertex pointers
49 /// (note - impossible to copy vertex pointers which having the vertex
50 /// and particles in/out point-back to one another -- unless you
51 /// copy the entire tree -- which we don't want to do)
52 set_production_vertex_( 0 );
53 set_end_vertex_( 0 );
54 suggest_barcode( inparticle.barcode() );
55 //s_counter++;
56 }
57
58 GenParticle::~GenParticle() {
59 if ( parent_event() ) parent_event()->remove_barcode(this);
60 //s_counter--;
61 }
62
63 void GenParticle::swap( GenParticle & other)
64 {
65 // if a container has a swap method, use that for improved performance
66 m_momentum.swap( other.m_momentum );
67 std::swap( m_pdg_id, other.m_pdg_id );
68 std::swap( m_status, other.m_status );
69 m_flow.swap( other.m_flow );
70 m_polarization.swap( other.m_polarization );
71 std::swap( m_production_vertex, other.m_production_vertex );
72 std::swap( m_end_vertex, other.m_end_vertex );
73 std::swap( m_barcode, other.m_barcode );
74 std::swap( m_generated_mass, other.m_generated_mass );
75 }
76
77 GenParticle& GenParticle::operator=( const GenParticle& inparticle ) {
78 /// Shallow: does not copy the vertex pointers
79 /// (note - impossible to copy vertex pointers which having the vertex
80 /// and particles in/out point-back to one another -- unless you
81 /// copy the entire tree -- which we don't want to do)
82
83 // best practices implementation
84 GenParticle tmp( inparticle );
85 swap( tmp );
86 return *this;
87 }
88
89 bool GenParticle::operator==( const GenParticle& a ) const {
90 /// consistent with the definition of the copy constructor as a shallow
91 /// constructor,.. this operator does not test the vertex pointers.
92 /// Does not compare barcodes.
93 if ( a.momentum() != this->momentum() ) return false;
94 if ( a.generated_mass() != this->generated_mass() ) return false;
95 if ( a.pdg_id() != this->pdg_id() ) return false;
96 if ( a.status() != this->status() ) return false;
97 if ( a.m_flow != this->m_flow ) return false;
98 if ( a.polarization() != this->polarization() ) return false;
99 return true;
100 }
101
102 bool GenParticle::operator!=( const GenParticle& a ) const {
103 return !( a == *this );
104 }
105
106 void GenParticle::print( std::ostream& ostr ) const {
107 /// Dump this particle's full info to ostr, where by default
108 /// particle.print(); will dump to cout.
109 ostr << "GenParticle: "
110 << barcode() << " ID:" << pdg_id()
111 << " (P,E)=" << momentum().px() << "," << momentum().py()
112 << "," << momentum().pz() << "," << momentum().e()
113 << " Stat:" << status();
114 if ( production_vertex() && production_vertex()->barcode()!=0 ) {
115 ostr << " PV:" << production_vertex()->barcode();
116 } else ostr << " PV:" << production_vertex();
117 if ( end_vertex() && end_vertex()->barcode()!=0 ) {
118 ostr << " EV:" << end_vertex()->barcode();
119 } else ostr << " EV:" << end_vertex();
120 ostr << " Pol:" << polarization() << " F:" << m_flow << std::endl;
121 }
122
123 GenEvent* GenParticle::parent_event() const {
124 if ( production_vertex() ) return production_vertex()->parent_event();
125 if ( end_vertex() ) return end_vertex()->parent_event();
126 return 0;
127 }
128
129 void GenParticle::set_production_vertex_( GenVertex* prodvertex )
130 {
131 GenEvent* its_orig_event = parent_event();
132 m_production_vertex = prodvertex;
133 GenEvent* its_new_event = parent_event();
134 // Next bit of logic ensures the barcode maps are kept up to date
135 // in the GenEvent containers.
136 if ( its_orig_event != its_new_event ) {
137 if ( its_new_event ) its_new_event->set_barcode( this, barcode() );
138 if ( its_orig_event ) its_orig_event->remove_barcode( this );
139 }
140 }
141
142 void GenParticle::set_end_vertex_( GenVertex* decayvertex )
143 {
144 GenEvent* its_orig_event = parent_event();
145 m_end_vertex = decayvertex;
146 GenEvent* its_new_event = parent_event();
147 if ( its_orig_event != its_new_event ) {
148 if ( its_new_event ) its_new_event->set_barcode( this, barcode() );
149 if ( its_orig_event ) its_orig_event->remove_barcode( this );
150 }
151 }
152
153 bool GenParticle::suggest_barcode( int the_bar_code )
154 {
155 /// allows a barcode to be suggested for this particle.
156 /// In general it is better to let the event pick the barcode for
157 /// you, which is automatic.
158 /// Returns TRUE if the suggested barcode has been accepted (i.e. the
159 /// suggested barcode has not already been used in the event,
160 /// and so it was used).
161 /// Returns FALSE if the suggested barcode was rejected, or if the
162 /// particle is not yet part of an event, such that it is not yet
163 /// possible to know if the suggested barcode will be accepted).
164 if ( the_bar_code <0 ) {
165 std::cerr << "GenParticle::suggest_barcode WARNING, particle bar "
166 << "\n codes MUST be positive integers. Negative "
167 << "\n integers are reserved for vertices only. Your "
168 << "\n suggestion has been rejected." << std::endl;
169 return false;
170 }
171 bool success = false;
172 if ( parent_event() ) {
173 success = parent_event()->set_barcode( this, the_bar_code );
174 } else { set_barcode_( the_bar_code ); }
175 return success;
176 }
177
178 /////////////
179 // Static //
180 /////////////
181 //unsigned int GenParticle::counter() { return s_counter; }
182 //unsigned int GenParticle::s_counter = 0U;
183
184 /////////////
185 // Friends //
186 /////////////
187
188 /// Dump this particle's full info to ostr
189 std::ostream& operator<<( std::ostream& ostr, const GenParticle& part ) {
190 // find the current stream state
191 std::ios_base::fmtflags orig = ostr.flags();
192 std::streamsize prec = ostr.precision();
193 ostr << " ";
194 ostr.width(9);
195 ostr << part.barcode();
196 ostr.width(9);
197 ostr << part.pdg_id() << " ";
198 ostr.width(9);
199 ostr.precision(2);
200 ostr.setf(std::ios::scientific, std::ios::floatfield);
201 ostr.setf(std::ios_base::showpos);
202 ostr << part.momentum().px() << ",";
203 ostr.width(9);
204 ostr << part.momentum().py() << ",";
205 ostr.width(9);
206 ostr << part.momentum().pz() << ",";
207 ostr.width(9);
208 ostr << part.momentum().e() << " ";
209 ostr.setf(std::ios::fmtflags(0), std::ios::floatfield);
210 ostr.unsetf(std::ios_base::showpos);
211 if ( part.end_vertex() && part.end_vertex()->barcode()!=0 ) {
212 ostr.width(3);
213 ostr << part.status() << " ";
214 ostr.width(9);
215 ostr << part.end_vertex()->barcode();
216 } else if ( !part.end_vertex() ) {
217 // There is no valid end_vertex
218 // For consistency across different compilers, do not print anything
219 ostr.width(3);
220 ostr << part.status();
221 } else {
222 // In this case the end_vertex does not have a unique
223 // barcode assigned, so we choose instead to print its address
224 ostr.width(3);
225 ostr << part.status() << " ";
226 ostr.width(9);
227 ostr << (void*)part.end_vertex();
228 }
229 // restore the stream state
230 ostr.flags(orig);
231 ostr.precision(prec);
232 return ostr;
233 }
234
235
236 double GenParticle::generated_mass() const {
237 return m_generated_mass;
238 }
239
240 void GenParticle::set_generated_mass( const double & m ) {
241 m_generated_mass = m;
242 }
243
244 /// scale the momentum vector and generated mass
245 /// this method is only for use by GenEvent
246 void GenParticle::convert_momentum( const double & f ) {
247 m_momentum = FourVector( f*m_momentum.px(),
248 f*m_momentum.py(),
249 f*m_momentum.pz(),
250 f*m_momentum.e() );
251 if( m_generated_mass > 0. ) m_generated_mass = f*m_generated_mass;
252 }
253
254} // HepMC
255
Note: See TracBrowser for help on using the repository browser.