Belle II Software  release-05-01-25
State.cc
1 //-----------------------------------------------------------------------------
2 // $Id$
3 //-----------------------------------------------------------------------------
4 // Filename : TRGState.cc
5 // Section : TRG
6 // Owner : Yoshihito Iwasaki
7 // Email : yoshihito.iwasaki@kek.jp
8 //-----------------------------------------------------------------------------
9 // Description : A class to represent a state of multi bits
10 //-----------------------------------------------------------------------------
11 // $Log$
12 //-----------------------------------------------------------------------------
13 
14 #include <algorithm>
15 #include <iostream>
16 #include <ctype.h>
17 #include <cstring>
18 #include "trg/trg/Utilities.h"
19 #include "trg/trg/State.h"
20 
21 using namespace std;
22 
23 namespace Belle2 {
29  const unsigned
30  TRGState::_su = sizeof(unsigned);
31 
32  const unsigned
33  TRGState::_bsu = 8 * sizeof(unsigned);
34 
35  TRGState::TRGState(unsigned bitSize)
36  : _size(bitSize),
37  _n(0),
38  _state(0)
39  {
40  _n = _size / _bsu;
41  if (_size % _bsu) ++_n;
42  if (_n)
43  _state = (unsigned*) calloc(_n, _su);
44  }
45 
46  TRGState::TRGState(unsigned bitSize, unsigned value)
47  : _size(bitSize),
48  _n(0),
49  _state(0)
50  {
51  _n = _size / _bsu;
52  if (_size % _bsu) ++_n;
53  if (_n)
54  _state = (unsigned*) calloc(_n, _su);
55 
56  for (unsigned i = 0; i < bitSize; i++) {
57  const unsigned wp = i / _bsu;
58  const unsigned bp = i % _bsu;
59  if (value & (1 << i))
60  _state[wp] |= (1 << bp);
61  }
62  }
63 
64  TRGState::TRGState(unsigned bitSize, const bool* const s)
65  : _size(bitSize),
66  _n(0),
67  _state(0)
68  {
69 
70  _n = _size / _bsu;
71  if (_size % _bsu) ++_n;
72  _state = (unsigned*) calloc(_n, _su);
73 
74  for (unsigned i = 0; i < _size; i++) {
75  const unsigned wp = i / _bsu;
76  const unsigned bp = i % _bsu;
77  if (s[i])
78  _state[wp] |= (1 << bp);
79  else
80  _state[wp] &= ~(1 << bp);
81  }
82  }
83 
84  TRGState::TRGState(vector<bool> states)
85  : _size(0),
86  _n(0),
87  _state(0)
88  {
89 
90  _size = states.size();
91  _n = _size / _bsu;
92  if (_size % _bsu) ++_n;
93  _state = (unsigned*) calloc(_n, _su);
94 
95  for (unsigned i = 0; i < _size; i++) {
96  const unsigned wp = i / _bsu;
97  const unsigned bp = i % _bsu;
98  if (states[i])
99  _state[wp] |= (1 << bp);
100  else
101  _state[wp] &= ~(1 << bp);
102 
103 // cout << "size,given,states=" << _size << "," << states[i] << ","
104 // << _state[wp] << endl;
105 
106  }
107  }
108 
109  TRGState::TRGState(vector<unsigned>& states, unsigned order)
110  : _size(0),
111  _n(0),
112  _state(0)
113  {
114 
115  _size = states.size() * _bsu;
116  _n = _size / _bsu;
117  _state = (unsigned*) calloc(_n, _su);
118 
119  for (unsigned i = 0; i < _n; i++) {
120 
121  if (order == 0) _state[i] = states[i];
122  else _state[_n - 1 - i] = states[i];
123 // cout << "size,given,states=" << _size << "," << states[i] << ","
124 // << _state[wp] << endl;
125 
126  }
127  }
128 
129  TRGState::TRGState(const char* inChar, unsigned inType)
130  : _size(0),
131  _n(0),
132  _state(0)
133  {
134 
135  if (inType == 0) {
136  _size = strlen(inChar);
137  // Check if all values are binary
138  for (unsigned iBit = 0; iBit < _size; iBit++) {
139  if (!(inChar[iBit] == '0' || inChar[iBit] == '1')) {
140 #ifdef TRG_DEBUG
141  cout << "TRGState::TRGState !!! invalid char found : aborted"
142  << endl;
143  cout << " invalid char = [" << inChar[iBit]
144  << "]" << endl;
145 #endif
146  return;
147  }
148  }
149  } else if (inType == 1) {
150  _size = strlen(inChar) * 4;
151  // Check if all values are hex
152  for (unsigned iChar = 0; iChar < _size / 4; iChar++) {
153  if (!isxdigit(inChar[iChar])) {
154 #ifdef TRG_DEBUG
155  cout << "TRGState::TRGState !!! invalid char found : aborted"
156  << endl;
157  cout << " invalid char = ["
158  << inChar[iChar] << "]" << endl;
159 #endif
160  return;
161  }
162  }
163  } else {
164 #ifdef TRG_DEBUG
165  cout << "TRGState::TRGState !!! invalid type : aborted"
166  << endl;
167  cout << " invalid type = " << inType
168  << endl;
169 #endif
170  return;
171  }
172 
173  _n = _size / _bsu;
174  if (_size % _bsu) ++_n;
175  _state = (unsigned*) calloc(_n, _su);
176  if (inType == 0) {
177  for (unsigned iBit = 0; iBit < _size; iBit++) {
178  const unsigned wp = iBit / _bsu;
179  const unsigned bp = iBit % _bsu;
180  if (inChar[_size - 1 - iBit] == '1')
181  _state[wp] |= (1 << bp);
182  else
183  _state[wp] &= ~(1 << bp);
184  }
185  } else if (inType == 1) {
186  for (unsigned iChar = 0; iChar < _size / 4; iChar++) {
187  if (iChar % 8 == 0) _state[iChar / 8] = 0;
188  short unsigned t_int;
189  unsigned charP = _size / 4 - 1 - iChar;
190  if (inChar[charP] > 47 && inChar[charP] < 58) t_int = inChar[charP] - 48;
191  else t_int = inChar[charP] - 97 + 10;
192  _state[iChar / 8] += t_int << ((iChar % 8) * 4);
193  }
194  }
195  }
196 
198  {
199  if (_state)
200  free(_state);
201  }
202 
203  void
204  TRGState::dump(const string& msg,
205  const string& pre) const
206  {
207 
208 // bool bin = true;
209  bool large = (_size > 60) || msg.find("large") != string::npos;
210 
211  if (! large) {
212  cout << pre << "size=" << _size << ",";
213  for (unsigned i = 0; i < _size; i++) {
214  const unsigned j = _size - i - 1;
215  if ((j % 8) == 7)
216  cout << "_";
217  if ((* this)[j])
218  cout << "1";
219  else
220  cout << "0";
221  }
222  cout << dec << endl;
223  } else {
224  cout << pre << "size=" << _size << endl;
225 
226  const unsigned nPerLines = 64;
227  const unsigned lines = _size / nPerLines + 1;
228  const unsigned rem = _size % nPerLines;
229 
230  cout << "TRGState" <<
231  " +56 +48 +40 +32 +24 +16 +8"
232  << " +0" << endl;
233 
234  bool skipLast = false;
235  for (unsigned i = 0; i < lines; i++) {
236  const unsigned n0 = (i == 0) ? rem - 1 : nPerLines - 1;
237  const int n1 = 0;
238  const int os = (lines - i - 1) * nPerLines;
239 
240  const string b = TRGUtilities::itostring(os);
241 
242  TRGState s = subset(n1 + os, n0 - n1 + 1);
243 
244 // s.dump("", "*** ");
245 
246  bool skip = false;
247  if (! s.active())
248  skip = true;
249 
250  if (skip && (! skipLast)) {
251  cout << "... (all zero)" << endl;
252  skipLast = true;
253  }
254 
255  if (skip) {
256  skipLast = true;
257  continue;
258  }
259 
260  skipLast = false;
261 
262  cout.width(5);
263  cout << b;
264  cout << " ";
265 
266  if (i == 0) {
267  unsigned n = nPerLines - rem + (nPerLines - rem) / 8;
268  if (rem % 8) ++n;
269  for (unsigned j = 0; j < n; j++)
270  cout << " ";
271  }
272 
273  for (int j = n0; j >= n1; --j) {
274  const unsigned v = (* this)[j + os];
275 
276  if ((j % 8) == 7)
277  cout << "_";
278  if (v)
279  cout << "1";
280  else
281  cout << "0";
282  }
283  cout << endl;
284  }
285  }
286 
287  // else {
288  // cout << pre << "size=" << _size << ",0x";
289  // bool first = true;
290  // for (unsigned i = 0; i < _n; i++) {
291  // const unsigned j = _n - i - 1;
292  // if (((j % 4) == 3) && (! first))
293  // cout << "_";
294  // cout << hex << _state[j];
295  // first = false;
296  // }
297  // cout << dec << endl;
298 
299  // cout << pre << "size=" << _size << ",0x";
300  // bool first = true;
301  // for (unsigned i = 0; i < _n; i++) {
302  // const unsigned j = _n - i - 1;
303  // if (! first)
304  // cout << "_";
305  // cout << hex << _state[j];
306  // cout << "(";
307  // for (unsigned k = 0; k < 4; k++) {
308  // unsigned c = ((_state[j] >> (4 - k + 1) * 8) & 0xff);
309  // if (c < 0x10)
310  // cout << ".";
311  // cout << c;
312  // }
313  // cout << ")";
314  // first = false;
315  // }
316  // cout << dec << endl;
317  // }
318  }
319 
320  TRGState&
322  {
323 
324  //...Check final size...
325  const unsigned sizeNew = _size + a.size();
326  const unsigned sizeMax = _n * _bsu;
327  const unsigned oldSize = _size;
328 
329  //...Necessary to extend...
330  if (sizeNew > sizeMax) {
331  unsigned nNew = sizeNew / _bsu;
332  if (sizeNew % _bsu) ++nNew;
333  unsigned* tmp = (unsigned*) calloc(nNew, _su);
334  for (unsigned i = 0; i < _n; i++) {
335  tmp[i] = _state[i];
336  }
337  if (_state)
338  free(_state);
339  _state = tmp;
340  _n = nNew;
341  }
342  _size = sizeNew;
343 
344  for (unsigned i = 0; i < a.size(); i++) {
345  unsigned j = i + oldSize;
346  const unsigned wp = j / _bsu;
347  const unsigned bp = j % _bsu;
348  if (a[i])
349  _state[wp] |= (1 << bp);
350  else
351  _state[wp] &= ~(1 << bp);
352 
353 // cout << "size,given,states=" << _size << "," << states[i] << ","
354 // << _state[wp] << endl;
355 
356  }
357 
358  return (* this);
359  }
360 
361  TRGState
362  TRGState::subset(unsigned s, unsigned n) const
363  {
364  vector<bool> stack;
365  for (unsigned i = s; i < s + n; i++) {
366  if ((* this)[i])
367  stack.push_back(true);
368  else
369  stack.push_back(false);
370  }
371  return TRGState(stack);
372  }
373 
374  TRGState&
376  {
377  if (_state)
378  free(_state);
379 
380  _size = a._size;
381  _n = a._n;
382  _state = (unsigned*) calloc(_n, _su);
383  for (unsigned i = 0; i < _n; i++) {
384  _state[i] = a._state[i];
385  }
386 
387  return * this;
388  }
389 
390  bool
392  {
393  const unsigned long long n0(* this);
394  const unsigned long long n1(a);
395  if (n0 < n1)
396  return true;
397  return false;
398  }
399 
401 } // namespace Belle2
402 
403 namespace std {
404 
405  ostream&
406  operator<<(ostream& out, const Belle2::TRGState& s)
407  {
408  for (unsigned i = 0; i < s.size(); i++) {
409  const unsigned j = s.size() - i - 1;
410  if (s.active(j))
411  out << "1";
412  else
413  out << "0";
414  }
415  return out;
416  }
417 
418 }
Belle2::TRGState::TRGState
TRGState(unsigned bitSize=0)
Default constructor.
Definition: State.cc:35
Belle2::TRGState::_size
unsigned _size
bit size.
Definition: State.h:140
Belle2::operator<<
std::ostream & operator<<(std::ostream &output, const IntervalOfValidity &iov)
Definition: IntervalOfValidity.cc:196
Belle2::TRGState::_n
unsigned _n
bit storage size.
Definition: State.h:143
Belle2::TRGState::subset
TRGState subset(unsigned i, unsigned n) const
returns subset from i with n bits.
Definition: State.cc:362
Belle2::TRGState
A class to represent a state of multi bits.
Definition: State.h:29
Belle2::TRGState::_su
static const unsigned _su
size of unsigned.
Definition: State.h:134
Belle2::TRGState::dump
void dump(const std::string &message="", const std::string &pre="") const
dumps contents.
Definition: State.cc:204
Belle2::TRGState::_bsu
static const unsigned _bsu
bit size of unsigned.
Definition: State.h:137
Belle2::TRGState::~TRGState
virtual ~TRGState()
Destructor.
Definition: State.cc:197
Belle2
Abstract base class for different kinds of events.
Definition: MillepedeAlgorithm.h:19
Belle2::TRGState::operator=
TRGState & operator=(const TRGState &)
Copy operator.
Definition: State.cc:375
Belle2::TRGUtilities::itostring
static std::string itostring(int i)
converts int to string. (Use boost::lexical_cast)
Belle2::TRGState::operator<
bool operator<(const TRGState &) const
Copy operator.
Definition: State.cc:391
Belle2::TRGState::_state
unsigned * _state
bit state.
Definition: State.h:146
Belle2::TRGState::operator+=
TRGState & operator+=(const TRGState &)
appends TRGState (as MSB).
Definition: State.cc:321