susy_cfa  b611ccad937ea179f86a1f5663960264616c0a20
generate_small_tree.cxx
Go to the documentation of this file.
2 
3 #include <cstring>
4 
5 #include <stdexcept>
6 #include <iostream>
7 #include <iomanip>
8 #include <vector>
9 #include <string>
10 #include <fstream>
11 #include <set>
12 
13 #include <unistd.h>
14 
15 using namespace std;
16 
17 string ToCaps(string str){
18  for(string::iterator it = str.begin();
19  it != str.end();
20  ++it){
21  *it = toupper(*it);
22  }
23  return str;
24 }
25 
26 string execute(const string &cmd){
27  FILE *pipe = popen(cmd.c_str(), "r");
28  if(!pipe) throw runtime_error("Could not open pipe.");
29  const size_t buffer_size = 128;
30  char buffer[buffer_size];
31  string result = "";
32  while(!feof(pipe)){
33  if(fgets(buffer, buffer_size, pipe) != NULL) result += buffer;
34  }
35 
36  pclose(pipe);
37  return result;
38 }
39 
40 vector<string> Tokenize(const string& input,
41  const string& tokens = " "){
42  char* ipt(new char[input.size()+1]);
43  memcpy(ipt, input.data(), input.size());
44  ipt[input.size()]=static_cast<char>(0);
45  char* ptr(strtok(ipt, tokens.c_str()));
46  vector<string> output(0);
47  while(ptr!=NULL){
48  output.push_back(ptr);
49  ptr=strtok(NULL, tokens.c_str());
50  }
51  return output;
52 }
53 
54 string FixName(string name){
55  //Variable names can have alphanumeric characters and underscores only
56  string allowed = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz1234567890_";
57 
58  //Remove illegal characters
59  size_t pos = name.find_first_not_of(allowed);
60  while(pos < name.size()){
61  name.at(pos) = '_';
62  pos = name.find_first_not_of(allowed);
63  }
64 
65  //Replace double underscore with single underscore
66  pos = name.rfind("__");
67  while(pos < name.size()){
68  name.replace(pos, 2, "_");
69  pos = name.rfind("__");
70  }
71 
72  //Remove leading and trailing spaces
73  pos = 0;
74  for(pos = 0; pos < name.size(); ++pos){
75  if(name.at(pos) != ' ') break;
76  }
77  size_t endpos = name.size();
78  for(endpos = name.size(); endpos != 0; --endpos){
79  if(name.at(endpos-1) != ' ') break;
80  }
81 
82  return name.substr(pos, endpos-pos);
83 }
84 
85 set<Variable> GetVariables(const string &file_name){
86  string allowed = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz1234567890_";
87  set<Variable> vars;
88 
89  ifstream infile(("txt/small_tree_cfg/"+file_name).c_str());
90  string line;
91  while(getline(infile, line)){
92  size_t start = line.find_first_not_of(" ");
93  if(start >= line.size() || line.at(start) == '#' || line.at(start) == '/') continue;
94 
95  //Replace double space with single space
96  size_t pos = line.rfind(" ");
97  while(pos < line.size()){
98  line.replace(pos, 2, " ");
99  pos = line.rfind(" ");
100  }
101  size_t end = line.find_last_of(allowed)+1;
102  size_t split = line.rfind(' ', end)+1;
103 
104  vars.insert(Variable(line.substr(start, split-start),
105  line.substr(split, end-split)));
106  }
107  infile.close();
108 
109  return vars;
110 }
111 
112 int main(int argc, char *argv[]){
113  int c = 0;
114  bool do_event_handler = true;
115  while((c=getopt(argc, argv, "t"))!=-1){
116  switch(c){
117  case 't':
118  do_event_handler = false;
119  break;
120  default:
121  break;
122  }
123  }
124  vector<string> file_names = Tokenize(execute("ls txt/small_tree_cfg/ 2> /dev/null"), "\n");
125 
126  vector<pair<string, set<Variable> > > sep_vars(file_names.size());
127  vector<string> fixed_names(file_names.size());
128  for(size_t ifile = 0; ifile < file_names.size(); ++ifile){
129  fixed_names.at(ifile) = FixName(file_names.at(ifile));
130  sep_vars.at(ifile).first = fixed_names.at(ifile);
131  sep_vars.at(ifile).second = GetVariables(file_names.at(ifile));
132  }
133 
134  set<Variable> all_vars;
135  for(size_t ifile = 0; ifile < sep_vars.size(); ++ifile){
136  for(set<Variable>::const_iterator var = sep_vars.at(ifile).second.begin();
137  var != sep_vars.at(ifile).second.end();
138  ++var){
139  all_vars.insert(*var);
140  }
141  }
142 
143  set<Variable> com_vars;
144  if(sep_vars.size()){
145  for(set<Variable>::const_iterator var = sep_vars.at(0).second.begin();
146  var != sep_vars.at(0).second.end();
147  ++var){
148  bool found_in_all = true;
149  for(size_t ifile = 1; found_in_all && ifile < sep_vars.size(); ++ifile){
150  if(sep_vars.at(ifile).second.find(*var) == sep_vars.at(ifile).second.end()){
151  found_in_all = false;
152  }
153  }
154  if(found_in_all){
155  com_vars.insert(*var);
156  }
157  }
158  for(set<Variable>::const_iterator var = com_vars.begin();
159  var != com_vars.end();
160  ++var){
161  for(size_t ifile = 0; ifile < sep_vars.size(); ++ifile){
162  sep_vars.at(ifile).second.erase(*var);
163  }
164  }
165  }
166 
167  WriteBaseHeader(all_vars, com_vars, fixed_names);
168  WriteBaseSource(all_vars, com_vars, fixed_names);
169 
170  for(size_t ifile = 0; ifile < sep_vars.size(); ++ifile){
171  WriteSepHeader(sep_vars.at(ifile));
172  WriteSepSource(sep_vars.at(ifile));
173  }
174 
175  if(do_event_handler){
176  vector<string> existing = Tokenize(execute("ls src/event_handler* 2> /dev/null"));
177  set<string> to_generate;
178  for(size_t iname = 0; iname < fixed_names.size(); ++iname){
179  bool found = false;
180  for(size_t iexist = 0; !found && iexist < existing.size(); ++iexist){
181  if(Contains(existing.at(iexist), fixed_names.at(iname))) found = true;
182  }
183  if(!found) to_generate.insert(fixed_names.at(iname));
184  }
185 
188 
189  for(set<string>::const_iterator name = to_generate.begin();
190  name != to_generate.end();
191  ++name){
194  }
195 
196  GenerateEventHandlerMergeHeader(fixed_names);
197  GenerateEventHandlerMergeSource(fixed_names);
198  }
199 }
200 
201 bool Contains(const string &text, const string &pattern){
202  return text.find(pattern) != string::npos;
203 }
204 
205 void WriteBaseHeader(const set<Variable> &all_vars,
206  const set<Variable> &com_vars,
207  const vector<string> &names){
208  ofstream file("inc/small_tree.hpp");
209 
210  file << "// small_tree: base class to handle reduced tree ntuples\n";
211  file << "// File generated with generate_small_tree.exe\n\n";
212 
213  file << "#ifndef H_SMALL_TREE\n";
214  file << "#define H_SMALL_TREE\n\n";
215 
216  file << "#include <vector>\n";
217  file << "#include <string>\n\n";
218 
219  file << "#include \"TTree.h\"\n";
220  file << "#include \"TChain.h\"\n";
221  file << "#include \"TTreeFormula.h\"\n\n";
222 
223  file << "class small_tree{\n";
224  file << "public:\n";
225  file << " small_tree(); // Constructor to create tree\n";
226  file << " small_tree(const std::string &filename); // Constructor to read tree\n\n";
227 
228  file << " int Add(const std::string &filename);\n";
229 
230  file << " long GetEntries() const;\n";
231  file << " virtual void GetEntry(const long entry);\n";
232  file << " bool PassString(TString cut);\n\n";
233 
234  file << " virtual void Fill();\n";
235  file << " void Write();\n\n";
236 
237  file << " virtual std::string Type() const;\n\n";
238 
239  file << " static const double bad_val_;\n\n";
240 
241  file << " virtual ~small_tree();\n\n";
242 
243  for(set<Variable>::const_iterator var = com_vars.begin();
244  var != com_vars.end();
245  ++var){
246  file << " " << var->type_ << " const & " << var->name_ << "() const;\n";
247  file << " " << var->type_ << " & " << var->name_ << "();\n";
248  }
249  file << '\n';
250 
251  for(set<Variable>::const_iterator var = all_vars.begin();
252  var != all_vars.end();
253  ++var){
254  if(com_vars.find(*var) != com_vars.end()) continue;
255  file << " __attribute__((noreturn)) virtual "
256  << var->type_ << " const & " << var->name_ << "() const;\n";
257  file << " __attribute__((noreturn)) virtual "
258  << var->type_ << " & " << var->name_ << "();\n";
259  }
260  file << '\n';
261 
262  file << "protected:\n";
263  file << " TChain chain_;\n";
264  file << " TTree tree_;\n";
265  file << " long entry_;\n";
266  file << " const bool read_only_;\n\n";
267 
268  file << "private:\n";
269  file << " class VectorLoader{\n";
270  file << " public:\n";
271  file << " VectorLoader();\n";
272  file << " private:\n";
273  file << " static bool loaded_;\n";
274  file << " };\n\n";
275 
276  file << " static VectorLoader vl_;\n";
277  for(set<Variable>::const_iterator var = com_vars.begin();
278  var != com_vars.end();
279  ++var){
280  file << " " << var->type_ << ' ' << var->name_ << "_;\n";
281  if(Contains(var->type_, "vector")){
282  file << " " << var->type_ << " *p_" << var->name_ << "_;\n";
283  }
284  file << " TBranch *b_" << var->name_ << "_;\n";
285  file << " mutable bool c_" << var->name_ << "_;\n";
286  }
287  file << "};\n\n";
288 
289  file << "small_tree* NewTree(const std::type_info &type);\n\n";
290 
291  for(size_t i = 0; i < names.size(); ++i){
292  file << "#include \"small_tree_" << names.at(i) << ".hpp\"\n";
293  }
294  file <<'\n';
295 
296  file << "#endif" << endl;
297 
298  file.close();
299 }
300 
301 void WriteBaseSource(const set<Variable> &all_vars,
302  const set<Variable> &com_vars,
303  const vector<string> &names){
304  ofstream file("src/small_tree.cpp");
305 
306  file << "// small_tree: base class to handle reduce tree ntuples\n";
307  file << "//File generated with generate_small_tree.exe\n\n";
308 
309  file << "#include \"small_tree.hpp\"\n\n";
310 
311  file << "#include <stdexcept>\n";
312  file << "#include <string>\n";
313  file << "#include <iostream>\n";
314  file << "#include <vector>\n\n";
315 
316  file << "#include \"TROOT.h\"\n";
317  file << "#include \"TTree.h\"\n";
318  file << "#include \"TBranch.h\"\n";
319  file << "#include \"TChain.h\"\n";
320  file << "#include \"TTreeFormula.h\"\n\n";
321 
322  file << "using namespace std;\n\n";
323 
324  file << "bool small_tree::VectorLoader::loaded_ = false;\n\n";
325 
326  file << "small_tree::VectorLoader small_tree::vl_ = small_tree::VectorLoader();\n\n";
327 
328  file << "small_tree::VectorLoader::VectorLoader(){\n";
329  file << " if(!loaded_){\n";
330  file << " gROOT->ProcessLine(\"#include <vector>\");\n";
331  file << " loaded_ = true;\n";
332  file << " }\n";
333  file << "}\n\n";
334 
335  file << "const double small_tree::bad_val_ = -999.;\n\n";
336 
337  file << "small_tree::small_tree():\n";
338  file << " chain_(\"junk\", \"junk\"),\n";
339  file << " tree_(\"tree\", \"tree\"),\n";
340  file << " entry_(0),\n";
341  if(com_vars.size()){
342  const set<Variable>::const_iterator com_end_2 = --com_vars.end();
343  file << " read_only_(false),\n";
344  for(set<Variable>::const_iterator var = com_vars.begin();
345  var != com_end_2;
346  ++var){
347  file << " " << var->name_ << "_(0),\n";
348  if(Contains(var->type_, "vector")){
349  file << " p_" << var->name_ << "_(&" << var->name_ << "_),\n";
350  file << " b_" << var->name_ << "_(tree_.Branch(\"" << var->name_ << "\", &p_" << var->name_ << "_)),\n";
351  }else{
352  file << " b_" << var->name_ << "_(tree_.Branch(\"" << var->name_ << "\", &" << var->name_ << "_)),\n";
353  }
354  file << " c_" << var->name_ << "_(false),\n";
355  }
356  file << " " << com_end_2->name_ << "_(0),\n";
357  file << " b_" << com_end_2->name_ << "_(tree_.Branch(\"" << com_end_2->name_ << "\", &" << com_end_2->name_ << "_)),\n";
358  file << " c_" << com_end_2->name_ << "_(false){\n";
359  }else{
360  file << " read_only_(false){\n";
361  }
362  file << "}\n\n";
363 
364  file << "small_tree::small_tree(const string &filename):\n";
365  file << " chain_(\"tree\",\"tree\"),\n";
366  file << " tree_(\"junk\",\"junk\"),\n";
367  file << " entry_(0),\n";
368  if(com_vars.size()){
369  const set<Variable>::const_iterator com_end_2 = --com_vars.end();
370  file << " read_only_(true),\n";
371  for(set<Variable>::const_iterator var = com_vars.begin();
372  var != com_end_2;
373  ++var){
374  file << " " << var->name_ << "_(0),\n";
375  if(Contains(var->type_, "vector")){
376  file << " p_" << var->name_ << "_(&" << var->name_ << "_),\n";
377  }
378  file << " b_" << var->name_ << "_(NULL),\n";
379  file << " c_" << var->name_ << "_(false),\n";
380  }
381  file << " " << com_end_2->name_ << "_(0),\n";
382  if(Contains(com_end_2->type_, "vector")){
383  file << " p_" << com_end_2->name_ << "_(&" << com_end_2->name_ << "_),\n";
384  }
385  file << " b_" << com_end_2->name_ << "_(NULL),\n";
386  file << " c_" << com_end_2->name_ << "_(false){\n";
387  }else{
388  file << " read_only_(true){\n";
389  }
390  file << " chain_.Add(filename.c_str());\n";
391  for(set<Variable>::const_iterator var = com_vars.begin(); var != com_vars.end(); ++var){
392  if(Contains(var->type_, "vector")){
393  file << " chain_.SetBranchAddress(\"" << var->name_ << "\", &p_" << var->name_ << "_, &b_" << var->name_ << "_);\n";
394  }else{
395  file << " chain_.SetBranchAddress(\"" << var->name_ << "\", &" << var->name_ << "_, &b_" << var->name_ << "_);\n";
396  }
397  }
398  file << "}\n\n";
399 
400  file << "void small_tree::Fill(){\n";
401  file << " if(read_only_){\n";
402  file << " throw std::logic_error(\"Trying to write to read-only tree\");\n";
403  file << " }else{\n";
404  file << " tree_.Fill();\n";
405  file << " }\n\n";
406 
407  file << " //Resetting variables\n";
408  for(set<Variable>::const_iterator var = com_vars.begin(); var != com_vars.end(); ++var){
409  if(Contains(var->type_, "vector")){
410  file << " " << var->name_ << "_.clear();\n";
411  }else if(Contains(var->type_, "tring")){
412  file << " " << var->name_ << "_ = \"\";\n";
413  }else{
414  file << " " << var->name_ << "_ = static_cast<" << var->type_ << ">(bad_val_);\n";
415  }
416  }
417  file << "}\n\n";
418 
419  file << "void small_tree::Write(){\n";
420  file << " if(read_only_){\n";
421  file << " throw std::logic_error(\"Trying to write to read-only tree.\");\n";
422  file << " }else{\n";
423  file << " tree_.Write();\n";
424  file << " }\n";
425  file << "}\n\n";
426 
427  file << "string small_tree::Type() const{\n";
428  file << " return \"\";\n";
429  file << "}\n\n";
430 
431  file << "small_tree::~small_tree(){\n";
432  file << "}\n\n";
433 
434  file << "int small_tree::Add(const std::string &filename){\n";
435  file << " if(!read_only_){\n";
436  file << " throw std::logic_error(\"Trying to add files to tree opened for writing.\");\n";
437  file << " }\n";
438  file << " return chain_.Add(filename.c_str());\n";
439  file << "}\n\n";
440 
441 
442  file << "bool small_tree::PassString(TString cut){\n";
443  file << " TTreeFormula f(\"formula\",cut, &chain_);\n";
444  file << " bool result = f.EvalInstance(0);\n";
445  file << " return result;\n";
446  file << "}\n\n";
447 
448  file << "long small_tree::GetEntries() const{\n";
449  file << " if(read_only_){\n";
450  file << " return chain_.GetEntries();\n";
451  file << " }else{\n";
452  file << " return tree_.GetEntries();\n";
453  file << " }\n";
454  file << "}\n\n";
455 
456  file << "void small_tree::GetEntry(const long entry){\n";
457  file << " if(!read_only_){\n";
458  file << " throw std::logic_error(\"Trying to read from write-only tree.\");\n";
459  file << " }\n\n";
460 
461  for(set<Variable>::const_iterator var = com_vars.begin(); var!= com_vars.end(); ++var){
462  file << " c_" << var->name_ << "_ = false;\n";
463  }
464  file << " entry_ = chain_.LoadTree(entry);\n";
465  file << "}\n\n";
466 
467  for(set<Variable>::const_iterator var = com_vars.begin(); var != com_vars.end(); ++var){
468  file << var->type_ << " const & small_tree::" << var->name_ << "() const{\n";
469  file << " if(!read_only_){\n";
470  file << " throw std::logic_error(\"Trying to write to const tree.\");\n";
471  file << " }\n";
472  file << " if(!c_" << var->name_ << "_ && b_" << var->name_ <<"_){\n";
473  file << " b_" << var->name_ << "_->GetEntry(entry_);\n";
474  file << " c_" << var->name_ << "_ = true;\n";
475  file << " }\n";
476  file << " return " << var->name_ << "_;\n";
477  file << "}\n\n";
478  }
479 
480  for(set<Variable>::const_iterator var = com_vars.begin(); var != com_vars.end(); ++var){
481  file << var->type_ << " & small_tree::" << var->name_ << "(){\n";
482  file << " if(read_only_ && !c_" << var->name_ << "_ && b_" << var->name_ <<"_){\n";
483  file << " b_" << var->name_ << "_->GetEntry(entry_);\n";
484  file << " c_" << var->name_ << "_ = true;\n";
485  file << " }\n";
486  file << " return " << var->name_ << "_;\n";
487  file << "}\n\n";
488  }
489 
490  for(set<Variable>::const_iterator var = all_vars.begin(); var != all_vars.end(); ++var){
491  if(com_vars.find(*var) != com_vars.end()) continue;
492  file << var->type_ << " const & small_tree::" << var->name_ << "() const{\n";
493  file << " throw std::logic_error(\"" << var->name_
494  << " does not exist in this small_tree version.\");\n";
495  file << "}\n\n";
496  }
497 
498  for(set<Variable>::const_iterator var = all_vars.begin(); var != all_vars.end(); ++var){
499  if(com_vars.find(*var) != com_vars.end()) continue;
500  file << var->type_ << " & small_tree::" << var->name_ << "(){\n";
501  file << " throw std::logic_error(\"" << var->name_
502  << " does not exist in this small_tree version.\");\n";
503  file << "}\n\n";
504  }
505 
506  for(size_t i = 0; i < names.size(); ++i){
507  file << "#include \"small_tree_" << names.at(i) << ".hpp\"\n";
508  }
509  file << "small_tree* NewTree(const std::type_info &type){\n\n";
510  file << " if(type == typeid(small_tree)) return new small_tree;\n";
511  for(size_t i = 0; i < names.size(); ++i){
512  file << " else if(type == typeid(small_tree_" << names.at(i) << ")) return static_cast<small_tree*>(new small_tree_" << names.at(i) << ");\n";
513  }
514  file << " else return new small_tree;\n";
515  file << "}\n\n";
516 
517  file.close();
518 }
519 
520 void WriteSepHeader(const pair<string, set<Variable> > &sep_vars){
521  string name = sep_vars.first;
522  string NAME = ToCaps(name);
523  set<Variable> vars = sep_vars.second;
524  ofstream file(("inc/small_tree_"+name+".hpp").c_str());
525 
526  file << "// small_tree_" << name << ": " << name << " version of small_tree to handle reduce tree ntuples\n";
527  file << "// File generated with generate_small_tree.exe\n\n";
528 
529  file << "#ifndef H_SMALL_TREE_" << NAME << "\n";
530  file << "#define H_SMALL_TREE_" << NAME << "\n\n";
531 
532  file << "#include <vector>\n";
533  file << "#include <string>\n\n";
534 
535  file << "#include \"TTree.h\"\n";
536  file << "#include \"TChain.h\"\n\n";
537 
538  file << "#include \"small_tree.hpp\"\n\n";
539 
540  file << "class small_tree_" << name << " : public small_tree{\n";
541  file << "public:\n";
542  file << " small_tree_" << name << "(); // Constructor to create tree\n";
543  file << " small_tree_" << name << "(const std::string &filename); // Constructor to read tree\n\n";
544 
545  file << " virtual void GetEntry(const long entry);\n\n";
546 
547  file << " virtual void Fill();\n\n";
548 
549  file << " virtual std::string Type() const;\n\n";
550 
551  file << " virtual ~small_tree_" << name << "();\n\n";
552 
553  for(set<Variable>::const_iterator var = vars.begin();
554  var != vars.end();
555  ++var){
556  file << " virtual " << var->type_ << " const & " << var->name_ << "() const;\n";
557  file << " virtual " << var->type_ << " & " << var->name_ << "();\n";
558  }
559  file << '\n';
560 
561  file << "private:\n";
562  for(set<Variable>::const_iterator var = vars.begin();
563  var != vars.end();
564  ++var){
565  file << " " << var->type_ << ' ' << var->name_ << "_;\n";
566  if(Contains(var->type_, "vector")){
567  file << " " << var->type_ << " *p_" << var->name_ << "_;\n";
568  }
569  file << " TBranch *b_" << var->name_ << "_;\n";
570  file << " mutable bool c_" << var->name_ << "_;\n";
571  }
572  file << "};\n\n";
573 
574  file << "#endif" << endl;
575 
576  file.close();
577 }
578 
579 void WriteSepSource(const pair<string, set<Variable> > &sep_vars){
580  string name = sep_vars.first;
581  string NAME = ToCaps(name);
582  set<Variable> vars = sep_vars.second;
583  ofstream file(("src/small_tree_"+name+".cpp").c_str());
584 
585  file << "// small_tree_" << name << ": " << name << " version of small_tree to handle reduce tree ntuples\n";
586  file << "//File generated with generate_small_tree.exe\n\n";
587 
588  file << "#include \"small_tree.hpp\"\n\n";
589  file << "#include \"small_tree_" << name << ".hpp\"\n\n";
590 
591  file << "#include <stdexcept>\n";
592  file << "#include <string>\n";
593  file << "#include <vector>\n\n";
594 
595  file << "#include \"TTree.h\"\n";
596  file << "#include \"TBranch.h\"\n";
597  file << "#include \"TChain.h\"\n\n";
598 
599  file << "using namespace std;\n\n";
600 
601  file << "small_tree_" << name << "::small_tree_" << name << "():\n";
602  if(vars.size()){
603  const set<Variable>::const_iterator vars_end_2 = --vars.end();
604  file << " small_tree(),\n";
605  for(set<Variable>::const_iterator var = vars.begin();
606  var != vars_end_2;
607  ++var){
608  file << " " << var->name_ << "_(0),\n";
609  if(Contains(var->type_, "vector")){
610  file << " p_" << var->name_ << "_(&" << var->name_ << "_),\n";
611  file << " b_" << var->name_ << "_(tree_.Branch(\"" << var->name_ << "\", &p_" << var->name_ << "_)),\n";
612  }else{
613  file << " b_" << var->name_ << "_(tree_.Branch(\"" << var->name_ << "\", &" << var->name_ << "_)),\n";
614  }
615  file << " c_" << var->name_ << "_(false),\n";
616  }
617  file << " " << vars_end_2->name_ << "_(0),\n";
618  if(Contains(vars_end_2->type_, "vector")){
619  file << " p_" << vars_end_2->name_ << "_(&" << vars_end_2->name_ << "_),\n";
620  file << " b_" << vars_end_2->name_ << "_(tree_.Branch(\"" << vars_end_2->name_ << "\", &p_" << vars_end_2->name_ << "_)),\n";
621  }else{
622  file << " b_" << vars_end_2->name_ << "_(tree_.Branch(\"" << vars_end_2->name_ << "\", &" << vars_end_2->name_ << "_)),\n";
623  }
624  file << " c_" << vars_end_2->name_ << "_(false){\n";
625  }else{
626  file << " small_tree(){\n";
627  }
628  file << "}\n\n";
629 
630  file << "small_tree_" << name << "::small_tree_" << name << "(const string &filename):\n";
631  if(vars.size()){
632  const set<Variable>::const_iterator vars_end_2 = --vars.end();
633  file << " small_tree(filename),\n";
634  for(set<Variable>::const_iterator var = vars.begin();
635  var != vars_end_2;
636  ++var){
637  file << " " << var->name_ << "_(0),\n";
638  if(Contains(var->type_, "vector")){
639  file << " p_" << var->name_ << "_(&" << var->name_ << "_),\n";
640  }
641  file << " b_" << var->name_ << "_(NULL),\n";
642  file << " c_" << var->name_ << "_(false),\n";
643  }
644  file << " " << vars_end_2->name_ << "_(0),\n";
645  if(Contains(vars_end_2->type_, "vector")){
646  file << " p_" << vars_end_2->name_ << "_(&" << vars_end_2->name_ << "_),\n";
647  }
648  file << " b_" << vars_end_2->name_ << "_(NULL),\n";
649  file << " c_" << vars_end_2->name_ << "_(false){\n";
650  }else{
651  file << " small_tree(filename){\n";
652  }
653  for(set<Variable>::const_iterator var = vars.begin(); var != vars.end(); ++var){
654  if(Contains(var->type_, "vector")){
655  file << " chain_.SetBranchAddress(\"" << var->name_ << "\", &p_" << var->name_ << "_, &b_" << var->name_ << "_);\n";
656  }else{
657  file << " chain_.SetBranchAddress(\"" << var->name_ << "\", &" << var->name_ << "_, &b_" << var->name_ << "_);\n";
658  }
659  }
660  file << "}\n\n";
661 
662  file << "void small_tree_" << name << "::Fill(){\n";
663  file << " small_tree::Fill();\n";
664 
665  file << " //Resetting variables\n";
666  for(set<Variable>::const_iterator var = vars.begin(); var != vars.end(); ++var){
667  if(Contains(var->type_, "vector")){
668  file << " " << var->name_ << "_.clear();\n";
669  }else if(Contains(var->type_, "tring")){
670  file << " " << var->name_ << "_ = \"\";\n";
671  }else{
672  file << " " << var->name_ << "_ = static_cast<" << var->type_ << ">(bad_val_);\n";
673  }
674  }
675  file << "}\n\n";
676 
677  file << "string small_tree_" << name << "::Type() const{\n";
678  file << " return \"" << name << "\";\n";
679  file << "}\n\n";
680 
681  file << "small_tree_" << name << "::~small_tree_" << name << "(){\n";
682  file << "}\n\n";
683 
684  file << "void small_tree_" << name << "::GetEntry(const long entry){\n";
685  file << " small_tree::GetEntry(entry);\n\n";
686 
687  for(set<Variable>::const_iterator var = vars.begin(); var!= vars.end(); ++var){
688  file << " c_" << var->name_ << "_ = false;\n";
689  }
690  file << "}\n\n";
691 
692  for(set<Variable>::const_iterator var = vars.begin(); var != vars.end(); ++var){
693  file << var->type_ << " const & small_tree_" << name << "::" << var->name_ << "() const{\n";
694  file << " if(!read_only_){\n";
695  file << " throw std::logic_error(\"Trying to write to const tree.\");\n";
696  file << " }\n";
697  file << " if(!c_" << var->name_ << "_ && b_" << var->name_ <<"_){\n";
698  file << " b_" << var->name_ << "_->GetEntry(entry_);\n";
699  file << " c_" << var->name_ << "_ = true;\n";
700  file << " }\n";
701  file << " return " << var->name_ << "_;\n";
702  file << "}\n\n";
703  }
704 
705  for(set<Variable>::const_iterator var = vars.begin(); var != vars.end(); ++var){
706  file << var->type_ << " & small_tree_" << name << "::" << var->name_ << "(){\n";
707  file << " if(read_only_ && !c_" << var->name_ << "_ && b_" << var->name_ <<"_){\n";
708  file << " b_" << var->name_ << "_->GetEntry(entry_);\n";
709  file << " c_" << var->name_ << "_ = true;\n";
710  file << " }\n";
711  file << " return " << var->name_ << "_;\n";
712  file << "}\n\n";
713  }
714 
715  file.close();
716 }
717 
719  ofstream file("inc/event_handler_base.hpp");
720 
721  file << " // event_handler_base: base class for reduced tree production\n";
722  file << " // File generated with generate_small_tree.exe\n\n";
723 
724  file << "#ifndef H_EVENT_HANDLER_BASE\n";
725  file << "#define H_EVENT_HANDLER_BASE\n\n";
726 
727  file << "#include <string>\n\n";
728 
729  file << "#include \"TString.h\"\n\n";
730 
731  file << "#include \"phys_objects.hpp\"\n\n";
732 
733  file << "class event_handler_base : public phys_objects{\n";
734  file << "public:\n";
735  file << " event_handler_base(const std::string &file_name);\n\n";
736 
737  file << " virtual void ReduceTree(int num_entries,\n";
738  file << " const TString &out_file_name,\n";
739  file << " int num_total_entries) = 0;\n\n";
740 
741  file << " virtual ~event_handler_base();\n";
742 
743  file << "};\n\n";
744 
745  file << "#endif\n";
746 
747  file.close();
748 }
749 
751  ofstream file("src/event_handler_base.cpp");
752 
753  file << "// event_handle_base: base class for reduced tree production\n";
754  file << "// File generated with generate_small_tree.exe\n\n";
755 
756  file << "#include \"event_handler_base.hpp\"\n\n";
757 
758  file << "#include <string>\n";
759 
760  file << "using namespace std;\n\n";
761 
762  file << "event_handler_base::event_handler_base(const string &file_name):\n";
763  file << " phys_objects(file_name){\n";
764  file << "}\n\n";
765 
766  file << "event_handler_base::~event_handler_base(){\n";
767  file << "}\n\n";
768 }
769 
770 void GenerateEventHandlerHeader(const string &name){
771  string NAME = ToCaps(name);
772  ofstream file(("inc/event_handler_"+name+".hpp").c_str());
773 
774  file << " // event_handler_" << name << ": derived class for specialized reduced tree production\n";
775  file << " // File generated with generate_small_tree.exe\n\n";
776 
777  file << "#ifndef H_EVENT_HANDLER_" << NAME << "\n";
778  file << "#define H_EVENT_HANDLER_" << NAME << "\n";
779 
780  file << "#include <string>\n";
781 
782  file << "#include \"TString.h\"\n\n";
783 
784  file << "#include \"event_handler_base.hpp\"\n\n";
785 
786  file << "class event_handler_" << name << " : public event_handler_base{\n";
787  file << "public:\n";
788  file << " event_handler_" << name << "(const std::string &file_name);\n\n";
789 
790  file << " virtual void ReduceTree(int num_entries,\n";
791  file << " const TString &out_file_name,\n";
792  file << " int num_total_entries);\n\n";
793 
794  file << " virtual ~event_handler_" << name << "();\n";
795 
796  file << "};\n\n";
797 
798  file << "#endif\n";
799 
800  file.close();
801 }
802 
803 void GenerateEventHandlerSource(const string &name){
804  ofstream file(("src/event_handler_"+name+".cpp").c_str());
805 
806  file << " // event_handler_" << name << ": derived class for specialized reduced tree production\n";
807  file << " // File generated with generate_small_tree.exe\n\n";
808 
809  file << "#include \"event_handler_" << name << ".hpp\"\n\n";
810 
811  file << "#include <string>\n";
812 
813  file << "#include \"TString.h\"\n\n";
814 
815  file << "#include \"event_handler_base.hpp\"\n\n";
816 
817  file << "using namespace std;\n\n";
818 
819  file << "event_handler_" << name << "::event_handler_" << name << "(const string &file_name):\n";
820  file << " event_handler_base(file_name){\n";
821  file << "}\n\n";
822 
823  file << "void event_handler_" << name << "::ReduceTree(int /*num_entries*/, const TString &/*out_file_name*/, int /*num_total_entries*/){\n";
824  file << "}\n\n";
825 
826  file << "event_handler_" << name << "::~event_handler_" << name << "(){\n";
827  file << "}\n";
828 
829  file.close();
830 }
831 
832 void GenerateEventHandlerMergeHeader(const vector<string> &names){
833  ofstream file("inc/event_handler.hpp");
834 
835  file << " // event_handler: main class for reduced tree production\n";
836  file << " //File generated with generate_small_tree.exe\n\n";
837 
838  file << "#ifndef H_EVENT_HANDLER\n";
839  file << "#define H_EVENT_HANDLER\n\n";
840 
841  file << "#include <string>\n";
842 
843  file << "#include \"TString.h\"\n\n";
844 
845  file << "#include \"event_handler_base.hpp\"\n\n";
846  for(vector<string>::const_iterator name = names.begin(); name != names.end(); ++name){
847  file << "#include \"event_handler_" << *name << ".hpp\"\n";
848  }
849 
850  file << "class event_handler{\n";
851  file << "public:\n";
852  file << " event_handler(const std::string &file_name, const std::string &type);\n";
853  file << " void ReduceTree(int num_entries, const TString &out_file_name, int num_total_entries);\n";
854  file << " long TotalEntries() const;\n";
855  file << " short GetVersion() const;\n";
856  file << " const std::string& SampleName() const;\n";
857  file << " const std::string& SampleName(const std::string &sample_name);\n";
858  file << " void SetFile(const std::string &file, bool is_8TeV = false);\n";
859  file << " void AddFiles(const std::string &file);\n";
860  file << " ~event_handler();\n";
861  file << " event_handler_base *ehb;\n";
862  file << "private:\n";
863  file << " static event_handler_base * LookUpType(const std::string &file_name, const std::string &type);\n";
864  file << "};\n\n";
865 
866  file << "#endif\n";
867 
868  file.close();
869 }
870 
871 void GenerateEventHandlerMergeSource(const vector<string> &names){
872  ofstream file("src/event_handler.cpp");
873 
874  file << "// event_handler: main class for reduced tree production\n";
875  file << " //File generated with generate_small_tree.exe\n\n";
876 
877  file << "#include \"event_handler.hpp\"\n\n";
878 
879  file << "#include <typeinfo>\n";
880  file << "#include <string>\n\n";
881 
882  file << "#include \"TString.h\"\n\n";
883 
884  file << "#include \"event_handler_base.hpp\"\n\n";
885  for(vector<string>::const_iterator name = names.begin(); name != names.end(); ++name){
886  file << "#include \"event_handler_" << *name << ".hpp\"\n";
887  }
888 
889  file << "using namespace std;\n\n";
890 
891  file << "#include \"event_handler_base.hpp\"\n\n";
892  for(vector<string>::const_iterator name = names.begin(); name != names.end(); ++name){
893  file << "#include \"event_handler_" << *name << ".hpp\"\n";
894  }
895 
896  file << "event_handler::event_handler(const string &file_name, const string &type):\n";
897  file << " ehb(LookUpType(file_name, type)){\n";
898  file << "}\n\n";
899 
900  file << "void event_handler::ReduceTree(int num_entries, const TString &out_file_name, int num_total_entries){\n";
901  file << " ehb->ReduceTree(num_entries, out_file_name, num_total_entries);\n";
902  file << "}\n\n";
903 
904  if(names.size()){
905  file << "event_handler_base * event_handler::LookUpType(const string &file_name, const string &type){\n";
906  file << " if(type == \"" << names.front() << "\"){\n";
907  file << " return new event_handler_" << names.front() << "(file_name);\n";
908  for(size_t itype = 1; itype < names.size(); ++itype){
909  file << " }else if(type == \"" << names.at(itype) << "\"){\n";
910  file << " return new event_handler_" << names.at(itype) << "(file_name);\n";
911  }
912  file << " }else{\n";
913  file << " return NULL;\n";
914  file << " }\n";
915  }else{
916  file << "event_handler_base * LookUpType(const string &/*file_name*/, const string &/*type*/){\n";
917  file << " return NULL;\n";
918  }
919  file << "}\n\n";
920 
921  file << "long event_handler::TotalEntries() const{\n";
922  file << " return ehb->TotalEntries();\n";
923  file << "}\n\n";
924 
925  file << "short event_handler::GetVersion() const{\n";
926  file << " return ehb->GetVersion();\n";
927  file << "}\n\n";
928 
929  file << "const std::string& event_handler::SampleName() const{\n";
930  file << " return ehb->SampleName();\n";
931  file << "}\n\n";
932 
933  file << "const std::string& event_handler::SampleName(const std::string &sample_name){\n";
934  file << " return ehb->SampleName(sample_name);\n";
935  file << "}\n\n";
936 
937  file << "void event_handler::SetFile(const std::string &file, bool is_8TeV){\n";
938  file << " ehb->SetFile(file, is_8TeV);\n";
939  file << "}\n\n";
940 
941  file << "void event_handler::AddFiles(const std::string &file){\n";
942  file << " ehb->AddFiles(file);\n";
943  file << "}\n\n";
944 
945  file << "event_handler::~event_handler(){\n";
946  file << " if(ehb){\n";
947  file << " delete ehb;\n";
948  file << " ehb = NULL;\n";
949  file << " }\n";
950  file << "}\n\n";
951 }
string FixName(string name)
void WriteBaseHeader(const set< Variable > &all_vars, const set< Variable > &com_vars, const vector< string > &names)
void WriteSepSource(const pair< string, set< Variable > > &sep_vars)
STL namespace.
string ToCaps(string str)
void GenerateEventHandlerSource(const string &name)
void WriteBaseSource(const set< Variable > &all_vars, const set< Variable > &com_vars, const vector< string > &names)
string execute(const string &cmd)
int main(int argc, char *argv[])
void GenerateEventHandlerMergeSource(const vector< string > &names)
set< Variable > GetVariables(const string &file_name)
bool Contains(const string &text, const string &pattern)
void WriteSepHeader(const pair< string, set< Variable > > &sep_vars)
void GenerateEventHandlerHeader(const string &name)
vector< string > Tokenize(const string &input, const string &tokens=" ")
void GenerateEventHandlerBaseSource()
void GenerateEventHandlerMergeHeader(const vector< string > &names)
void GenerateEventHandlerBaseHeader()