Jpp 20.0.0-rc.2
the software that should make you happy
Loading...
Searching...
No Matches
JZebraMantis.cc
Go to the documentation of this file.
1#include <iostream>
2#include <fstream>
3
4#include "TString.h"
5#include "TRegexp.h"
6#include "TObjArray.h"
7#include "TObjString.h"
8#include "TFile.h"
9#include "TKey.h"
10
11#include "Jeep/JParser.hh"
12
13#include "JSupport/JMeta.hh"
14
15#include "JLang/JPredicate.hh"
16#include "JLang/JVectorize.hh"
17
20
22
23namespace {
24
25 /*
26 * Gets list of ROOT object identifiers in a ROOT TDirectory and stores it in a vector.
27 * Note: Subdirectories are searched recursively.
28 *
29 * \param dir The ROOT directory
30 */
32
33 using namespace std;
34 using namespace JPP;
35
36 vector<JRootObjectID> buffer1;
37
38 TIter iter(dir->GetListOfKeys());
39
40 for (TKey* key; (key = (TKey*) iter.Next()) != NULL; ) {
41
42 if (key->IsFolder()){
43
44 TDirectory *subdir = dir->GetDirectory(key->GetName());
45
46 vector<JRootObjectID> buffer2 = readDir(subdir);
47
48 buffer1.insert(buffer1.end(), buffer2.begin(), buffer2.end());
49
50 } else {
51
52 const string fullName = MAKE_STRING(dir->GetPath() <<
53 JRootObjectID::PATHNAME_SEPARATOR <<
54 key->GetName());
55
56 JRootObjectID objectID(fullName);
57
58 buffer1.push_back(objectID);
59 }
60 }
61
62 return buffer1;
63 }
64}
65
66
67/**
68 * \file
69 *
70 * Program to compare histograms in root files that have same directory structure,\n
71 * and where the histograms have the same names.
72 * The input histograms and the test to be applied for each histogram are specified\n
73 * in an ASCII formatted steering file which is passed by the command line.\n\n
74 *
75 * Each row of the steering file should have multiple columns.\n\n
76 *
77 * Column 1 is the name of the histogram to be compared (including the full path inside the root file)\n
78 * Column 2 is an integer value that indicates the test to be performed. See JTestDictionary()\n
79 * Columns 3..n are reserved for the different parameters of the test.\n\n
80 *
81 * \author rgruiz, bjung
82 */
83int main(int argc, char** argv) {
84
85 using namespace JPP;
86 using namespace std;
87
88 string steeringFile;
89
90 string file1;
91 string file2;
92
93 string output;
94 string ascii;
95
96 vector<string> keys;
97
98 bool onlyFailures;
99
100 int debug;
101
102 const array_type<string> listOfKeys = get_keys(JTestSummary().getProperties());
103
104 try {
105
106 const string keysExplainer = MAKE_STRING("Terminal output:" << endl << listOfKeys);
107
108 JParser<> zap("\nProgram to compare histograms in root files that have the same directory structure. See the link below this usage for further details.\n");
109
110 zap['s'] = make_field(steeringFile , "ASCII steering file with list of histograms and tests");
111 zap['a'] = make_field(file1 , "input file 1");
112 zap['b'] = make_field(file2 , "input file 2");
113 zap['o'] = make_field(output , "output file root") = "zebramantis.root";
114 zap['t'] = make_field(ascii , "output file txt" ) = "zebramantis.txt";
115 zap['k'] = make_field(keys , keysExplainer ) = JPARSER::initialised();
116 zap['w'] = make_field(onlyFailures , "write only failed tests" );
117 zap['d'] = make_field(debug) = 2;
118
119 zap(argc,argv);
120 }
121 catch(const exception &error) {
122 ERROR(error.what() << endl);
123 }
124
125 if (keys.empty()) {
126 keys = listOfKeys;
127 }
128
129 TFile* f1 = TFile::Open(file1.c_str());
130 TFile* f2 = TFile::Open(file2.c_str());
131
132 TFile out(output.c_str(),"recreate");
133
134 ofstream results;
135 results.open (ascii);
136 results << "# " << listOfKeys << endl;
137
138 const vector<JRootObjectID> objectIDs = readDir(f1);
139
140 std::ifstream infile(steeringFile);
141
143
144 size_t npassed = 0;
145 size_t nfailed = 0;
146
147 for (string line; getline(infile, line); ) {
148
149 istringstream iss(line);
150
151 TString name;
152 int testID;
153
154 if (!(iss >> name >> testID)) {
155 continue;
156 }
157
158 DEBUG("Input: " << name << ' ' << testID << endl);
159
160 const TRegexp regexp(name);
161
162 for (vector<JRootObjectID>::const_iterator objectID = objectIDs.cbegin() ; objectID != objectIDs.cend() ; ++objectID) {
163
164 const TString& dirName = objectID->getDirectory();
165 const TString& fullName = objectID->getFullObjectName();
166
167 DEBUG("Key: " << fullName << " match = " << fullName.Contains(regexp) << endl);
168
169 if ((fullName.Index(regexp) != -1)) {
170
171 TObject* obj1 = (TObject*)f1->Get(fullName);
172 TObject* obj2 = (TObject*)f2->Get(fullName);
173
174 if (!obj1 || !obj2) {
175 DEBUG("Could not retrieve " << fullName << endl);
176 continue;
177 }
178
179 d[testID]->read(iss);
180 d[testID]->test(obj1,obj2);
181
182 if (dirName.Length() > 0 && !out.GetDirectory(dirName)) {
183
184 if (dirName[0] == JRootObjectID::PATHNAME_SEPARATOR) { // Remove leading forward slash
185 out.mkdir(TString(dirName(1, dirName.Length() - 1)));
186 } else {
187 out.mkdir(dirName);
188 }
189 }
190
191 out.cd(dirName);
192
193 for (vector<JTestResult>::iterator r = d[testID]->begin() ; r != d[testID]->end() ; ++r) {
194
195 if (onlyFailures && r->passed) {
196 continue;
197 }
198
199 print(cout, *r, keys.cbegin(), keys.cend(), false);
200 print(results, *r, listOfKeys.cbegin(), listOfKeys.cend(), true);
201
202 r->obj->Write();
203 }
204
205 const size_t Npass = count_if(d[testID]->cbegin(), d[testID]->cend(),
206 make_predicate(&JTestResult::passed, true));
207
208 npassed += Npass;
209 nfailed += (d[testID]->size() - Npass);
210
211 d[testID]->clear();
212 }
213 }
214 }
215
216 infile.close();
217
218 results << WHITE << "# PASSED: " << npassed << " " << " FAILED: " << nfailed << " FAILURE FRACTION: " << float (nfailed)/(nfailed+npassed) << endl;
219
220 putObject(&out, JMeta(argc, argv));
221 JMeta::copy(file1.c_str(), out);
222 JMeta::copy(file2.c_str(), out);
223
224 results.close();
225 out .Close();
226
227 return 0;
228}
#define DEBUG(A)
Message macros.
Definition JMessage.hh:62
#define ERROR(A)
Definition JMessage.hh:66
int debug
debug level
Definition JSirene.cc:72
ROOT I/O of application specific meta data.
Utility class to parse command line options.
#define make_field(A,...)
macro to convert parameter to JParserTemplateElement object
Definition JParser.hh:2142
void readDir(TDirectory *dir, std::vector< TString > &v)
#define MAKE_STRING(A)
Make string.
Definition JPrint.hh:63
void print(const TH1 &h1, std::ostream &out)
Print histogram parameters.
Auxiliary methods to convert data members or return values of member methods of a set of objects to a...
int main(int argc, char **argv)
Dictionary to map different tests to unique integer indices.
Class dedicated to standardize the title of the graphical objects produced by the JTest_t() derived c...
Auxiliary class to handle file name, ROOT directory and object name.
Utility class to parse command line options.
Definition JParser.hh:1698
This name space includes all other name spaces (except KM3NETDAQ, KM3NET and ANTARES).
Auxiliary data structure for return type of make methods.
Definition JVectorize.hh:28
Empty structure for specification of parser element that is initialised (i.e. does not require input)...
Definition JParser.hh:68
Auxiliary class for ROOT I/O of application specific meta data.
Definition JMeta.hh:72