Line data Source code
1 : // $Id$
2 : /**************************************************************************
3 : * This file is property of and copyright by the ALICE HLT Project *
4 : * All rights reserved. *
5 : * *
6 : * Primary Authors: *
7 : * Artur Szostak <artursz@iafrica.com> *
8 : * *
9 : * Permission to use, copy, modify and distribute this software and its *
10 : * documentation strictly for non-commercial purposes is hereby granted *
11 : * without fee, provided that the above copyright notice appears in all *
12 : * copies and that both the copyright notice and this permission notice *
13 : * appear in the supporting documentation. The authors make no claims *
14 : * about the suitability of this software for any purpose. It is *
15 : * provided "as is" without express or implied warranty. *
16 : **************************************************************************/
17 :
18 : /// @file AliHLTScalars.cxx
19 : /// @author Artur Szostak <artursz@iafrica.com>
20 : /// @date 28 Sep 2010
21 : /// @brief Implementation of the HLT scalars class.
22 : ///
23 : /// This implements the scalars class for the HLT, which is a collection of
24 : /// named scalar values. Searching for a named scalar is optimised by using
25 : /// using a hash map.
26 :
27 : #include "AliHLTScalars.h"
28 : #include "TString.h"
29 : #include "AliHLTLogging.h" // HLT logging
30 : #include "TClass.h" // for Class_Name macro for logging
31 : #include "TIterator.h"
32 : #include "Riostream.h"
33 : #include <cassert>
34 :
35 126 : ClassImp(AliHLTScalars);
36 126 : ClassImp(AliHLTScalars::AliScalar);
37 :
38 :
39 : AliHLTScalars::AliHLTScalars() :
40 0 : TObject(),
41 0 : fScalars(AliHLTScalars::AliScalar::Class(), 128),
42 0 : fMap(TCollection::kInitHashTableCapacity, 2)
43 0 : {
44 : // Default constructor.
45 :
46 0 : fMap.SetOwner(kFALSE);
47 0 : }
48 :
49 :
50 : AliHLTScalars::AliHLTScalars(const AliHLTScalars& obj) :
51 0 : TObject(obj),
52 0 : fScalars(obj.fScalars),
53 0 : fMap(obj.fMap.GetSize(), obj.fMap.GetRehashLevel())
54 0 : {
55 : // Copy constructor performs a deep copy.
56 :
57 0 : fMap.SetOwner(kFALSE);
58 0 : fMap.AddAll(&fScalars);
59 0 : }
60 :
61 :
62 : AliHLTScalars::AliHLTScalars(const TClass* cl, Int_t initSize) :
63 0 : TObject(),
64 0 : fScalars(cl, initSize),
65 0 : fMap(TCollection::kInitHashTableCapacity, 2)
66 0 : {
67 : // Constructor to be able to specify a custom class for the fScalars TClonesArray object.
68 :
69 0 : fMap.SetOwner(kFALSE);
70 0 : }
71 :
72 :
73 : AliHLTScalars::~AliHLTScalars()
74 0 : {
75 : // Default destructor.
76 :
77 0 : Clear();
78 0 : }
79 :
80 :
81 : AliHLTScalars::AliScalar* AliHLTScalars::NewScalar(UInt_t i, const char* name, const char* description, Double_t value)
82 : {
83 : // Creates a new scalar object.
84 :
85 0 : return new (fScalars[i]) AliScalar(name, description, value);
86 0 : }
87 :
88 :
89 : const AliHLTScalars::AliScalar& AliHLTScalars::Sentinel() const
90 : {
91 : // Returns an empty sentinel object.
92 :
93 0 : static AliHLTScalars::AliScalar sentinel;
94 0 : return sentinel;
95 0 : }
96 :
97 :
98 : bool AliHLTScalars::Add(AliScalar*& scalar, const char* name, const char* description, Double_t value)
99 : {
100 : // Adds a new scalar (internal version).
101 :
102 0 : scalar = static_cast<AliScalar*>( fMap.FindObject(name) );
103 0 : bool exists = scalar != NULL;
104 0 : if (not exists)
105 : {
106 0 : scalar = NewScalar(fScalars.GetEntriesFast(), name, description, value);
107 0 : fMap.Add(scalar);
108 0 : }
109 : else
110 : {
111 0 : scalar->Value(value);
112 : }
113 0 : return exists;
114 : }
115 :
116 :
117 : bool AliHLTScalars::Add(const char* name, const char* description, Double_t value)
118 : {
119 : // Adds a new scalar.
120 :
121 0 : AliScalar* scalar = NULL;
122 0 : return Add(scalar, name, description, value);
123 0 : }
124 :
125 :
126 : bool AliHLTScalars::Remove(const char* name)
127 : {
128 : // Removes a scalar from the list.
129 :
130 0 : TNamed x(name, "");
131 0 : TObject* scalar = fMap.Remove(&x);
132 0 : bool existed = scalar != NULL;
133 0 : if (existed)
134 : {
135 0 : fScalars.Remove(scalar);
136 0 : fScalars.Compress();
137 : }
138 : return existed;
139 0 : }
140 :
141 :
142 : const AliHLTScalars::AliScalar& AliHLTScalars::GetScalar(const char* name) const
143 : {
144 : // Fetch the named scalar object.
145 :
146 0 : const TObject* scalar = fMap.FindObject(name);
147 0 : if (scalar != NULL)
148 : {
149 0 : return *static_cast<const AliScalar*>(scalar);
150 : }
151 : else
152 : {
153 0 : return Sentinel();
154 : }
155 0 : }
156 :
157 :
158 : AliHLTScalars::AliScalar& AliHLTScalars::GetScalar(const char* name)
159 : {
160 : // Fetch the named scalar object for editing.
161 :
162 0 : TObject* scalar = fMap.FindObject(name);
163 0 : if (scalar == NULL)
164 : {
165 0 : scalar = NewScalar(fScalars.GetEntriesFast(), name, "", 0);
166 0 : fMap.Add(scalar);
167 0 : }
168 0 : return *static_cast<AliScalar*>(scalar);
169 : }
170 :
171 :
172 : const AliHLTScalars::AliScalar& AliHLTScalars::GetScalarN(UInt_t n) const
173 : {
174 : // Fetch the n'th scalar object.
175 :
176 0 : if (n < NumberOfScalars())
177 : {
178 0 : const TObject* scalar = fScalars.UncheckedAt(Int_t(n));
179 0 : return *static_cast<const AliScalar*>(scalar);
180 : }
181 : else
182 : {
183 0 : return Sentinel();
184 : }
185 0 : }
186 :
187 :
188 : AliHLTScalars::AliScalar& AliHLTScalars::GetScalarN(UInt_t n)
189 : {
190 : // Fetch the n'th scalar object for editing.
191 :
192 : TObject* scalar = NULL;
193 0 : if (n < NumberOfScalars())
194 : {
195 0 : scalar = fScalars.UncheckedAt(Int_t(n));
196 0 : }
197 : else
198 : {
199 : // We have to create all missing scalars since there cannot
200 : // be gaps in the TClonesArray. This can cause segfaults during
201 : // ROOT I/O of the class otherwise.
202 0 : for (UInt_t i = NumberOfScalars(); i <= n; ++i)
203 : {
204 : // Make sure the the name of the scalar is not taken.
205 : // If it is then find an unused name.
206 0 : TString nameToUse = Form("Scalar%d", i);
207 0 : if (FindObject(nameToUse.Data()) != NULL)
208 : {
209 : UInt_t m = 0;
210 0 : do
211 : {
212 0 : nameToUse = Form("Scalar%d_%d", i, m++);
213 0 : }
214 0 : while (FindObject(nameToUse.Data()) != NULL);
215 0 : }
216 0 : scalar = NewScalar(i, nameToUse.Data(), "", 0);
217 0 : fMap.Add(scalar);
218 0 : }
219 : }
220 0 : return *static_cast<AliScalar*>(scalar);
221 0 : }
222 :
223 :
224 : void AliHLTScalars::Reset()
225 : {
226 : // Sets all the scalar values to zero.
227 :
228 0 : for (Int_t i = 0; i < fScalars.GetEntriesFast(); ++i)
229 : {
230 0 : AliScalar* scalar = static_cast<AliScalar*>( fScalars.UncheckedAt(i) );
231 0 : scalar->Value(0);
232 : }
233 0 : }
234 :
235 :
236 : void AliHLTScalars::Clear(Option_t* option)
237 : {
238 : // Clears the array of scalars.
239 :
240 0 : fMap.Clear();
241 0 : fScalars.Delete(option);
242 0 : }
243 :
244 :
245 : void AliHLTScalars::Copy(TObject& object) const
246 : {
247 : // Performs a deep copy.
248 :
249 0 : if (object.IsA() != AliHLTScalars::Class())
250 : {
251 0 : AliHLTLogging log;
252 0 : log.LoggingVarargs(kHLTLogError, Class_Name() , FUNCTIONNAME() , __FILE__ , __LINE__ , "Cannot copy to an object of type '%s'.", object.ClassName());
253 : return;
254 0 : }
255 0 : AliHLTScalars* obj = static_cast<AliHLTScalars*>(&object);
256 0 : obj->operator = (*this);
257 0 : }
258 :
259 :
260 : void AliHLTScalars::Print(Option_t* option) const
261 : {
262 : // Prints the HLT trigger scalars.
263 :
264 0 : TIter next(&fScalars);
265 : const AliScalar* scalar = NULL;
266 :
267 0 : TString opt = option;
268 0 : if (opt == "compact")
269 : {
270 0 : scalar = static_cast<const AliScalar*>(next());
271 0 : if (scalar != NULL) cout << scalar->Value();
272 0 : while ((scalar = static_cast<const AliScalar*>(next())) != NULL)
273 : {
274 0 : cout << ", " << scalar->Value();
275 : }
276 0 : cout << endl;
277 0 : return;
278 : }
279 :
280 : // Calculate the maximum field width required to keep things aligned.
281 : int fieldwidth = 0;
282 0 : while ((scalar = static_cast<const AliScalar*>(next())) != NULL)
283 : {
284 0 : int length = strlen(scalar->Name()) + strlen(scalar->Description()) + 3;
285 0 : if (length > fieldwidth) fieldwidth = length;
286 : }
287 0 : if (fieldwidth > 80) fieldwidth = 80;
288 :
289 0 : cout << "HLT scalars:" << endl;
290 0 : next.Reset();
291 0 : while ((scalar = static_cast<const AliScalar*>(next())) != NULL)
292 : {
293 0 : TString str = scalar->Description();
294 0 : str += " (";
295 0 : str += scalar->Name();
296 0 : str += ")";
297 0 : cout << setw(fieldwidth) << str.Data() << setw(0)
298 0 : << " = " << scalar->Value() << setw(0)
299 0 : << endl;
300 0 : }
301 0 : if (fScalars.GetEntriesFast() == 0) cout << "(none)" << endl;
302 0 : }
303 :
304 :
305 : AliHLTScalars& AliHLTScalars::operator = (const AliHLTScalars& obj)
306 : {
307 : // Performs a deep copy.
308 :
309 0 : if (this == &obj) return *this;
310 0 : Clear(); // Remove existing scalars.
311 0 : TObject::operator = (obj);
312 0 : for (Int_t i = 0; i < obj.fScalars.GetEntriesFast(); ++i)
313 : {
314 0 : const AliScalar* x = static_cast<const AliScalar*>(obj.fScalars.UncheckedAt(i));
315 0 : new (fScalars[i]) AliScalar(*x);
316 : }
317 0 : fMap.AddAll(&fScalars);
318 0 : return *this;
319 0 : }
320 :
321 :
322 : Bool_t AliHLTScalars::IsEqual(const TObject *obj) const
323 : {
324 : // Checks if two sets of scalar lists have the same scalars.
325 :
326 0 : assert(obj != NULL);
327 0 : if (obj->IsA()->GetBaseClass(AliHLTScalars::Class()) == NULL)
328 : {
329 0 : AliHLTLogging log;
330 0 : log.LoggingVarargs(kHLTLogError, Class_Name() , FUNCTIONNAME() , __FILE__ , __LINE__ , "Cannot compare object of type '%s'' with an object of type '%s'.",
331 0 : this->ClassName(), obj->ClassName()
332 : );
333 : return kFALSE;
334 0 : }
335 0 : const AliHLTScalars* rhs = static_cast<const AliHLTScalars*>(obj);
336 0 : if (fScalars.GetEntriesFast() != rhs->fScalars.GetEntriesFast()) return kFALSE;
337 0 : TIter next(&fScalars);
338 : const AliScalar* scalar = NULL;
339 0 : while ((scalar = static_cast<const AliScalar*>(next())) != NULL)
340 : {
341 0 : if (rhs->fScalars.FindObject(scalar->Name()) == NULL) return kFALSE;
342 : }
343 0 : return kTRUE;
344 0 : }
345 :
346 :
347 : bool AliHLTScalars::operator == (const AliHLTScalars& obj) const
348 : {
349 : // Compares two scalar lists to see that they have the same scalar values.
350 :
351 0 : if (fScalars.GetEntriesFast() != obj.fScalars.GetEntriesFast()) return false;
352 0 : TIter next(&fScalars);
353 : const AliScalar* a = NULL;
354 0 : while ((a = static_cast<const AliScalar*>(next())) != NULL)
355 : {
356 0 : const AliScalar* b = static_cast<const AliScalar*>(
357 0 : obj.fScalars.FindObject(a->Name())
358 : );
359 0 : if (b == NULL) return false;
360 0 : if (a->Value() != b->Value()) return false;
361 0 : }
362 0 : return true;
363 0 : }
364 :
365 :
366 : void AliHLTScalars::AliScalar::Copy(TObject& object) const
367 : {
368 : // Performs a deep copy.
369 :
370 0 : if (object.IsA() != AliHLTScalars::AliScalar::Class())
371 : {
372 0 : AliHLTLogging log;
373 0 : log.LoggingVarargs(kHLTLogError, Class_Name() , FUNCTIONNAME() , __FILE__ , __LINE__ , "Cannot copy to an object of type '%s'.", object.ClassName());
374 : return;
375 0 : }
376 0 : AliHLTScalars::AliScalar* obj = static_cast<AliHLTScalars::AliScalar*>(&object);
377 0 : *obj = *this;
378 0 : }
|