23 : m_file(filename), m_stream(0), m_isstream(false)
26 ERROR(
"ReaderAscii: could not open input file: "<<filename )
34 : m_stream(&stream), m_isstream(true)
37 ERROR(
"ReaderAscii: could not open input stream " )
51 const size_t max_buffer_size=512*512;
52 char buf[max_buffer_size];
53 bool parsed_event_header =
false;
54 bool is_parsing_successful =
true;
55 pair<int,int> vertices_and_particles(0,0);
68 if( strlen(buf) == 0 )
continue;
71 if( strncmp(buf,
"HepMC",5) == 0 ) {
72 if( strncmp(buf,
"HepMC::Version",14) != 0 && strncmp(buf,
"HepMC::Asciiv3",14)!=0 )
74 WARNING(
"ReaderAscii: found unsupported expression in header. Will close the input." )
75 std::cout<<buf<<std::endl;
78 if(parsed_event_header) {
79 is_parsing_successful =
true;
88 if (vertices_and_particles.second < 0) {
89 is_parsing_successful =
false;
91 is_parsing_successful =
true;
92 parsed_event_header =
true;
102 if ( parsed_event_header )
114 if ( parsed_event_header )
120 WARNING(
"ReaderAscii: skipping unrecognised prefix: " << buf[0] )
121 is_parsing_successful =
true;
125 if( !is_parsing_successful )
break;
129 if( parsed_event_header && peek==
'E' )
break;
134 if ((
int)evt.
particles().size() > vertices_and_particles.second ) {
135 ERROR(
"ReaderAscii: too many particles were parsed" )
136 printf(
"%zu vs %i expected\n",evt.
particles().size(),vertices_and_particles.second );
137 is_parsing_successful =
false;
139 if ((
int)evt.
particles().size() < vertices_and_particles.second ) {
140 ERROR(
"ReaderAscii: too few particles were parsed" )
141 printf(
"%zu vs %i expected\n",evt.
particles().size(),vertices_and_particles.second );
142 is_parsing_successful =
false;
145 if ((
int)evt.
vertices().size() > vertices_and_particles.first) {
146 ERROR(
"ReaderAscii: too many vertices were parsed" )
147 printf(
"%zu vs %i expected\n",evt.
vertices().size(),vertices_and_particles.first );
148 is_parsing_successful =
false;
151 if ((
int)evt.
vertices().size() < vertices_and_particles.first) {
152 ERROR(
"ReaderAscii: too few vertices were parsed" )
153 printf(
"%zu vs %i expected\n",evt.
vertices().size(),vertices_and_particles.first );
154 is_parsing_successful =
false;
157 if( !is_parsing_successful ) {
158 ERROR(
"ReaderAscii: event parsing failed. Returning empty event" )
159 DEBUG( 1,
"Parsing failed at line:" << endl << buf )
168 if (p.second==v->id())
169 v->add_particle_out(p.first);
173 std::vector<int> all_ids;
174 std::vector<int> filled_ids;
175 std::vector<int> diff;
176 for (
auto v: evt.
vertices())
if (v->id()!=0) filled_ids.push_back(v->id());
177 for (
int i=-((
long)evt.
vertices().size()); i<0; i++) all_ids.push_back(i);
178 std::sort(all_ids.begin(),all_ids.end());
179 std::sort(filled_ids.begin(),filled_ids.end());
181 std::set_difference(all_ids.begin(), all_ids.end(), filled_ids.begin(), filled_ids.end(), std::inserter(diff, diff.begin()));
182 auto it= diff.rbegin();
184 for (
auto v: evt.
vertices())
if (v->id()==0) { v->set_id(*it); it++;}
191 static const pair<int,int> err(-1,-1);
192 pair<int,int> ret(-1,-1);
193 const char *cursor = buf;
198 if( !(cursor = strchr(cursor+1,
' ')) )
return err;
199 event_no = atoi(cursor);
203 if( !(cursor = strchr(cursor+1,
' ')) )
return err;
204 ret.first = atoi(cursor);
207 if( !(cursor = strchr(cursor+1,
' ')) )
return err;
208 ret.second = atoi(cursor);
211 if( (cursor = strchr(cursor+1,
'@')) ) {
214 if( !(cursor = strchr(cursor+1,
' ')) )
return err;
215 position.
setX(atof(cursor));
218 if( !(cursor = strchr(cursor+1,
' ')) )
return err;
219 position.
setY(atof(cursor));
222 if( !(cursor = strchr(cursor+1,
' ')) )
return err;
223 position.
setZ(atof(cursor));
226 if( !(cursor = strchr(cursor+1,
' ')) )
return err;
227 position.
setT(atof(cursor));
231 DEBUG( 10,
"ReaderAscii: E: "<<event_no<<
" ("<<ret.first<<
"V, "<<ret.second<<
"P)" )
239 std::istringstream iss(buf + 1);
242 while ( iss >> w ) wts.push_back(w);
244 &&
run_info()->weight_names().size() != wts.size() )
245 throw std::logic_error(
"ReaderAscii::parse_weight_values: " 246 "The number of weights ("+std::to_string((
long long int)(wts.size()))+
") does not match " 247 "the number weight names("+std::to_string((
long long int)(
run_info()->weight_names().size()))+
") in the GenRunInfo object");
255 const char *cursor = buf;
258 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
263 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
267 evt.
set_units(momentum_unit,length_unit);
276 GenVertexPtr data = make_shared<GenVertex>();
278 const char *cursor = buf;
279 const char *cursor2 =
nullptr;
284 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
288 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
289 data->set_status( atoi(cursor) );
292 if( !(cursor = strchr(cursor+1,
'[')) )
return false;
297 int particle_in = atoi(cursor);
300 if( particle_in > 0) {
302 if (particle_in <= highest_id)
303 data->add_particle_in( evt.
particles()[particle_in-1] );
309 if( !(cursor = strchr(cursor+1,
',')) ) {
310 if( !(cursor = strchr(cursor2+1,
']')) )
return false;
316 if( (cursor = strchr(cursor+1,
'@')) ) {
319 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
320 position.setX(atof(cursor));
323 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
324 position.setY(atof(cursor));
327 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
328 position.setZ(atof(cursor));
331 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
332 position.setT(atof(cursor));
333 data->set_position( position );
337 DEBUG( 10,
"ReaderAscii: V: "<<
id<<
" with "<<data->particles_in().size()<<
" particles)" )
348 GenParticlePtr data = make_shared<GenParticle>();
350 const char *cursor = buf;
354 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
356 if( atoi(cursor) != (int)evt.
particles().size() + 1 ) {
358 ERROR(
"ReaderAscii: particle ID mismatch" )
363 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
364 mother_id = atoi(cursor);
367 if( mother_id > 0 && mother_id <= (
int)evt.
particles().size() ) {
369 GenParticlePtr mother = evt.
particles()[ mother_id-1 ];
370 GenVertexPtr vertex = mother->end_vertex();
374 vertex = make_shared<GenVertex>();
375 vertex->add_particle_in(mother);
378 vertex->add_particle_out(data);
384 else if( mother_id < 0 )
388 for (
auto v: evt.
vertices())
if (v->id()==mother_id) {v->add_particle_out(data); found=
true;
break; }
399 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
400 data->set_pid( atoi(cursor) );
403 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
404 momentum.setPx(atof(cursor));
407 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
408 momentum.setPy(atof(cursor));
411 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
412 momentum.setPz(atof(cursor));
415 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
416 momentum.setE(atof(cursor));
417 data->set_momentum(momentum);
420 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
421 data->set_generated_mass( atof(cursor) );
424 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
425 data->set_status( atoi(cursor) );
429 DEBUG( 10,
"ReaderAscii: P: "<<data->id()<<
" ( mother: "<<mother_id<<
", pid: "<<data->pid()<<
")" )
436 const char *cursor = buf;
437 const char *cursor2 = buf;
441 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
444 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
447 if( !(cursor2 = strchr(cursor,
' ')) )
return false;
448 sprintf(name,
"%.*s", (
int)(cursor2-cursor), cursor);
452 shared_ptr<Attribute> att =
461 const char *cursor = buf;
462 const char *cursor2 = buf;
465 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
468 if( !(cursor2 = strchr(cursor,
' ')) )
return false;
469 sprintf(name,
"%.*s", (
int)(cursor2-cursor), cursor);
473 shared_ptr<StringAttribute> att =
476 run_info()->add_attribute(
string(name), att);
484 const char *cursor = buf;
486 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
489 istringstream iss(
unescape(cursor));
490 vector<string> names;
492 while ( iss >> name ) names.push_back(name);
494 run_info()->set_weight_names(names);
501 const char *cursor = buf;
503 if( !(cursor = strchr(cursor+1,
' ')) )
return false;
507 string::size_type pos = line.find(
"\n");
508 tool.
name = line.substr(0, pos);
509 line = line.substr(pos + 1);
510 pos = line.find(
"\n");
511 tool.
version = line.substr(0, pos);
513 run_info()->tools().push_back(tool);
522 ret.reserve(s.length());
523 for ( string::const_iterator it = s.begin(); it != s.end(); ++it ) {
540 if( !
m_file.is_open())
return;
void set_run_info(shared_ptr< GenRunInfo > run)
Set the GenRunInfo object by smart pointer.
bool parse_run_attribute(const char *buf)
Parse run-level attribute.
const Units::MomentumUnit & momentum_unit() const
Get momentum unit.
const Units::LengthUnit & length_unit() const
Get length unit.
ReaderAscii(const std::string &filename)
Constructor.
bool parse_units(GenEvent &evt, const char *buf)
Parse units.
void add_vertex(GenVertexPtr v)
Add vertex.
static LengthUnit length_unit(const std::string &name)
Get length unit based on its name.
bool parse_tool(const char *buf)
Parse run-level tool information.
#define ERROR(MESSAGE)
Macro for printing error messages.
Definition of class GenParticle.
const std::vector< ConstGenVertexPtr > & vertices() const
Get list of vertices (const)
shared_ptr< GenRunInfo > run_info() const
Get the global GenRunInfo object.
std::pair< int, int > parse_event_information(GenEvent &evt, const char *buf)
Parse event.
std::ifstream m_file
Input file.
std::map< GenVertexPtr, std::set< int > > m_forward_mothers
Temp storage for outgoing particle ids.
Definition of class GenVertex.
Attribute that holds a string.
void add_particle(GenParticlePtr p)
Add particle.
static std::string name(MomentumUnit u)
Get name of momentum unit.
bool failed()
Return status of the stream.
bool parse_weight_names(const char *buf)
Parse run-level weight names.
bool parse_attribute(GenEvent &evt, const char *buf)
Parse attribute.
#define DEBUG(LEVEL, MESSAGE)
Macro for printing debug messages with appropriate debug level.
const std::vector< double > & weights() const
Get event weight values as a vector.
LengthUnit
Position units.
MomentumUnit
Momentum units.
Stores event-related information.
std::istream * m_stream
For ctor when reading from stdin.
bool read_event(GenEvent &evt)
Load event from file.
Definition of class ReaderAscii.
const std::vector< ConstGenParticlePtr > & particles() const
Get list of particles (const)
Definition of class Units.
#define WARNING(MESSAGE)
Macro for printing warning messages.
static MomentumUnit momentum_unit(const std::string &name)
Get momentum unit based on its name.
std::map< GenParticlePtr, int > m_forward_daughters
Temp storage for prod vertex ids.
bool m_isstream
toggles usage of m_file or m_stream
void set_units(Units::MomentumUnit new_momentum_unit, Units::LengthUnit new_length_unit)
Change event units Converts event from current units to new ones.
void add_attribute(const string &name, const shared_ptr< Attribute > &att, const int &id=0)
Add event attribute to event.
void set_run_info(shared_ptr< GenRunInfo > run)
Set the global GenRunInfo object.
bool parse_vertex_information(GenEvent &evt, const char *buf)
Parse vertex.
std::string unescape(const std::string &s)
Unsecape '\' and ' ' characters in string.
Definition of class GenEvent.
bool parse_particle_information(GenEvent &evt, const char *buf)
Parse particle.
void close()
Close file stream.
~ReaderAscii()
Destructor.
void clear()
Remove contents of this event.
bool parse_weight_values(GenEvent &evt, const char *buf)
Parse weight value lines.
void set_event_number(const int &num)
Set event number.
void shift_position_to(const FourVector &newpos)
Shift position of all vertices in the event to op.