Jpp
Head.hh
Go to the documentation of this file.
1 #ifndef HEAD_HH_INCLUDED
2 #define HEAD_HH_INCLUDED
3 
4 #include "Vec.hh"
5 #include "Exception.hh"
6 
7 #include "TObject.h"
8 
9 #include <string>
10 #include <sstream>
11 #include <iostream>
12 #include <map>
13 #include <algorithm>
14 
15 
16 /**
17  * Split string into separate tokens.
18  *
19  * \param str input string
20  * \param delim token delimiter
21  * \return list of tokens
22  */
23 inline std::vector<std::string> splitstring(const std::string& str, char delim = ' ')
24 {
25  using namespace std;
26 
28 
29  stringstream ss(str);
30  string token;
31  while (getline(ss, token, delim)) r.push_back(token);
32  return r;
33 }
34 
35 
36 /**
37  * The Head class reflects the header of Monte-Carlo event files, which consists of keys (also referred to as "tags") and values.
38  */
39 struct Head : public TObject, std::map<std::string, std::string>
40 {
41 
42  /**
43  * Check availability of data with the given key.
44  *
45  * \param key key
46  * \return true if data are available; else false
47  */
48  bool have_line (std::string key ) const
49  {
50  return count( key ) != 0;
51  }
52 
53  /**
54  * Get data with the given key.\n
55  * This method throws a run-time exception if no data are available.
56  *
57  * \param key key
58  * \return data
59  */
60  const std::string& get_line( std::string key ) const
61  {
62  return this->at(key);
63  }
64 
65  /**
66  * Get data with the given key.\n
67  * This method throws a run-time exception if no data are available.
68  *
69  * \param key key
70  * \return data
71  */
72  std::string& get_line( std::string key )
73  {
74  return this->at(key);
75  }
76 
77  /**
78  * Set data with the given key.
79  *
80  * \param key key
81  * \param line data
82  */
83  void set_line( std::string key, std::string line )
84  {
86  }
87 
88  /**
89  * Get data with the given key at given index.\n
90  * This method throws a run-time exception if no data are available.
91  *
92  * \param key key
93  * \param idx index
94  * \return data
95  */
96  std::string get_field( std::string key, int idx ) const
97  {
98  using namespace std;
99 
101 
102  if ( idx < 0 || idx > int ( v.size() ) )
103  {
104  THROW(Exception, "Cannot find word number " << idx << " in line " << get_line(key) << " for key: " << key);
105  }
106  return v[idx];
107  }
108 
109  /**
110  * Get index of data with the given key at given field.\n
111  *
112  * Note that this method uses the dictionary define in method Head::_hdr_dict.
113  *
114  * \param key key
115  * \param field field
116  * \return index (-1 if not present)
117  */
118  int get_index_of_field(std::string key, std::string field) const
119  {
120  auto v = _hdr_dict()[key];
121  auto i = std::find (v.begin(), v.end(), field );
122  if (i== v.end()) return -1;
123  return i - v.begin();
124  }
125 
126  /**
127  * Get data with the given key at given field.\n
128  * This method throws a run-time exception if no field is available.
129  *
130  * Note that this method uses the dictionary define in method Head::_hdr_dict.
131  *
132  * \param key key
133  * \param field field
134  * \return data
135  */
136  std::string get_field( std::string key, std::string field ) const
137  {
138  int idx = get_index_of_field(key, field);
139 
140  if ( idx == -1 )
141  {
142  THROW(Exception, "Failed to find" << key << " " << field);
143  }
144 
145  return get_field( key, idx );
146  }
147 
148 
149  /**
150  * Set data with the given key at given field.\n
151  * This method throws a run-time exception if no field available.
152  *
153  * Note that this method uses the dictionary define in method Head::_hdr_dict.
154  *
155  * \param key key
156  * \param field field
157  * \param value vakue
158  */
159  void set_field( std::string key, std::string field, std::string value )
160  {
161  using namespace std;
162 
163  if ( field == "" ) get_line( key ) = value;
164 
165  int idx = get_index_of_field( key, field );
166 
167  if ( idx < 0 )
168  {
169  THROW(Exception, "GFailed to find field in header line: " << key << " " << field);
170  }
171 
172  vector<string> vals = splitstring( get_line( key ) );
173 
174  // if the fields before do not exist, add padding
175  while ( int( vals.size() ) <= idx ) vals.push_back("0");
176 
177  vals[idx] = value;
178  ostringstream ss;
179  for( auto v : vals )
180  {
181  ss << v;
182  }
183  set_line( key, ss.str() );
184 
185  }
186 
187  /**
188  * Print header.
189  *
190  * \param out output stream
191  */
192  void print ( std::ostream& out = std::cout ) const
193  {
194  if (count("start_run")) out<< "start_run: " << at("start_run") << std::endl;
195 
196  for( auto& p : *this )
197  {
198  if ( p.first == "start_run" || p.first == "end_event" ) continue;
199  out<< p.first << ": " << p.second << std::endl ;
200  }
201  out<< "end_event:" << std::endl;
202  }
203 
204  /**
205  * Get internal description of the known lines in header.
206  *
207  * \return internal dictionary
208  */
210  {
211  using namespace std;
212 
213  // map with, for each tag (key), a vector of field-names
214 
215  static map<string,vector<string> > r;
216  if ( r.size() > 0 ) return r;
217 
218  string desc =
219  "DAQ:livetime\n"
220  "cut_primary cut_seamuon cut_in cut_nu:Emin Emax cosTmin cosTmax\n"
221  "generator physics simul: program version date time\n"
222  "seed:program level iseed\n"
223  "PM1_type_area:type area TTS\n"
224  "PDF:i1 i2\n"
225  "model:interaction muon scattering numberOfEnergyBins\n"
226  "can:zmin zmax r\n"
227  "genvol:zmin zmax r volume numberOfEvents\n"
228  "merge:time gain\n"
229  "coord_origin:x y z\n"
230  "translate:x y z\n"
231  "genhencut:gDir Emin\n"
232  "k40: rate time\n"
233  "norma:primaryFlux numberOfPrimaries\n"
234  "livetime:numberOfSeconds errorOfSeconds\n"
235  "flux:type key file_1 file_2\n"
236  "spectrum:alpha\n"
237  "fixedcan:xcenter ycenter zmin zmax radius\n"
238  "start_run:run_id";
239 
240  for( auto line: splitstring(desc,'\n') )
241  {
242  auto v = splitstring( line, ':');
243 
244  vector< string > fields = splitstring( v[1] );
245  for( auto key : splitstring( v[0] ) )
246  {
247  r[key] = fields;
248  }
249  }
250  return r;
251  }
252 
253 
254  /**
255  * Get the number of generated events needed for computing event rates.
256  *
257  * \return number of events
258  */
259  double ngen() const
260  {
261  return stod ( get_field("genvol","numberOfEvents") );
262  }
263 
264  /**
265  * Get the the live time provided by the DAQ sytstem (=number of processed timeslices * frametime).
266  *
267  * \return live time [s]
268  */
269  double daq_livetime() const
270  {
271  return stod ( get_field("DAQ","livetime") );
272  }
273 
274 
275  /**
276  * Get the Monte Carlo live time
277  *
278  * \return live time [s]
279  */
280  double mc_livetime() const
281  {
282  return stod ( get_field("livetime","numberOfSeconds") );
283  }
284 
285  /**
286  * Get coordinate origin.
287  *
288  * \return position
289  */
290  Vec coord_origin() const
291  {
292  return Vec( stod( get_field("coord_origin","x") ),
293  stod( get_field("coord_origin","y") ),
294  stod( get_field("coord_origin","z") ));
295  }
296 
297  /**
298  * Get coordinate translation.
299  *
300  * \return translation
301  */
302  Vec translate() const
303  {
304  return Vec( stod( get_field("translate","x") ),
305  stod( get_field("translate","y") ),
306  stod( get_field("translate","z") ));
307  }
308 
309  virtual ~Head() {}
310  ClassDef(Head, 2 );
311 };
312 
313 
314 /**
315  * Print header.
316  *
317  * \param out output stream
318  * \param h header
319  * \return output stream
320  */
321 inline std::ostream& operator<<(std::ostream& out, const Head& h)
322 {
323  h.print(out);
324  return out;
325 }
326 
327 
328 #endif
TObject
Definition: JRoot.hh:19
Head::_hdr_dict
static std::map< std::string, std::vector< std::string > > & _hdr_dict()
Get internal description of the known lines in header.
Definition: Head.hh:209
Exception.hh
Head::ClassDef
ClassDef(Head, 2)
Head::set_field
void set_field(std::string key, std::string field, std::string value)
Set data with the given key at given field.
Definition: Head.hh:159
std::vector< std::string >
Head::get_field
std::string get_field(std::string key, std::string field) const
Get data with the given key at given field.
Definition: Head.hh:136
Head::daq_livetime
double daq_livetime() const
Get the the live time provided by the DAQ sytstem (=number of processed timeslices * frametime).
Definition: Head.hh:269
Vec.hh
splitstring
std::vector< std::string > splitstring(const std::string &str, char delim=' ')
Split string into separate tokens.
Definition: Head.hh:23
Head::translate
Vec translate() const
Get coordinate translation.
Definition: Head.hh:302
Head
The Head class reflects the header of Monte-Carlo event files, which consists of keys (also referred ...
Definition: Head.hh:39
THROW
#define THROW(JException_t, A)
Marco for throwing exception with std::ostream compatible message.
Definition: JException.hh:670
Exception
General exception.
Definition: Exception.hh:13
Head::print
void print(std::ostream &out=std::cout) const
Print header.
Definition: Head.hh:192
std::map
Definition: JSTDTypes.hh:16
operator<<
std::ostream & operator<<(std::ostream &out, const Head &h)
Print header.
Definition: Head.hh:321
Head::get_line
const std::string & get_line(std::string key) const
Get data with the given key.
Definition: Head.hh:60
JTOOLS::v
data_type v[N+1][M+1]
Definition: JPolint.hh:707
Head::get_field
std::string get_field(std::string key, int idx) const
Get data with the given key at given index.
Definition: Head.hh:96
Head::get_index_of_field
int get_index_of_field(std::string key, std::string field) const
Get index of data with the given key at given field.
Definition: Head.hh:118
std
Definition: jaanetDictionary.h:36
Head::coord_origin
Vec coord_origin() const
Get coordinate origin.
Definition: Head.hh:290
Vec
The Vec class is a straightforward 3-d vector, which also works in pyroot.
Definition: Vec.hh:12
Head::mc_livetime
double mc_livetime() const
Get the Monte Carlo live time.
Definition: Head.hh:280
JTOOLS::r
data_type r[M+1]
Definition: JPolint.hh:709
Head::set_line
void set_line(std::string key, std::string line)
Set data with the given key.
Definition: Head.hh:83
JLANG::getline
std::istream & getline(std::istream &in, JString &object)
Read string from input stream until end of line.
Definition: JString.hh:468
Head::get_line
std::string & get_line(std::string key)
Get data with the given key.
Definition: Head.hh:72
Head::ngen
double ngen() const
Get the number of generated events needed for computing event rates.
Definition: Head.hh:259
Head::~Head
virtual ~Head()
Definition: Head.hh:309
Head::have_line
bool have_line(std::string key) const
Check availability of data with the given key.
Definition: Head.hh:48