ndmspc  0.20250128.0
HnSparseStress.cxx
1 #include <TAxis.h>
2 #include <TRandom.h>
3 
4 #include "HnSparse.h"
5 #include "HnSparseStress.h"
6 
10 
11 namespace Ndmspc {
12 namespace Ndh {
13 
14 HnSparseStress::HnSparseStress() : TObject() {}
15 
16 Bool_t HnSparseStress::Generate(THnSparse * h, Long64_t size, Long64_t start)
17 {
21 
22  if (h == nullptr) return kFALSE;
23 
24  if (size == 0) fNFilledMax = kMaxLong64;
25 
26  fNFilledMax = size;
27  if (fDebugLevel > 0)
28  Printf("dimensions=%d chunkSize=%d nFillMax=%lld start=%lld", h->GetNdimensions(), h->GetChunkSize(), fNFilledMax,
29  start);
30 
31  Double_t cCenter[h->GetNdimensions()];
32  Int_t cStart[h->GetNdimensions()];
33 
34  if (start > 0) {
35  Long64_t allBins = 1;
36  for (Int_t i = 0; i < h->GetNdimensions(); ++i) {
37 
38  if (allBins > kMaxLong64 / h->GetAxis(i)->GetNbins()) {
39  Printf("Error: Product of all bins is higer then %lld !!! Do not use --start in this case !!!", kMaxLong64);
40  return kFALSE;
41  }
42  allBins *= h->GetAxis(i)->GetNbins();
43  }
44  if (fDebugLevel > 0) Printf("MaxNumberOfBins=%lld", allBins);
45 
46  Long64_t startIndex = start;
47  Int_t bx = 0;
48  for (Int_t i = h->GetNdimensions() - 1; i >= 0; --i) {
49  allBins /= h->GetAxis(i)->GetNbins();
50 
51  bx = startIndex / allBins;
52  startIndex -= (bx * allBins);
53  cStart[i] = bx;
54  if (fDebugLevel > 0)
55  Printf("i=%d x=%d startIndex=%lld allBins=%lld cStart[%d]=%d", i, bx, startIndex, allBins, i, cStart[i]);
56  }
57 
58  if (fDebugLevel > 0)
59  for (Int_t i = h->GetNdimensions() - 1; i >= 0; --i) {
60  Printf("i=%d %d", i, cStart[i]);
61  }
62  }
63  else {
64  for (Int_t i = 0; i < h->GetNdimensions(); ++i) {
65  cStart[i] = 0;
66  }
67  }
68 
69  fTimerTotal.Start();
70  fTimer.Start();
71  Printf("fNFilledMax=%lld filled=%lld", fNFilledMax, h->GetNbins());
72  GenerateRecursiveLoop(h, h->GetNdimensions() - 1, cCenter, cStart);
73  fTimer.Stop();
74  fTimerTotal.Stop();
75  fTimerTotal.Print("m");
76 
77  return kTRUE;
78 }
79 
80 bool HnSparseStress::GenerateRecursiveLoop(THnSparse * h, Int_t iDim, Double_t * coord, Int_t * start)
81 {
85 
86  if (iDim < 0) return true;
87  for (Int_t iBin = start[iDim] + 1; iBin <= h->GetAxis(iDim)->GetNbins(); iBin++) {
88  coord[iDim] = h->GetAxis(iDim)->GetBinCenter(iBin);
89  if (fDebugLevel > 1) Printf("iDim=%d iBin=%d center=%f", iDim, iBin, coord[iDim]);
90 
91  if (iDim == 0) {
92  if (fRandomFill) {
93  for (Int_t iAxis = 0; iAxis < h->GetNdimensions(); iAxis++) {
94  coord[iAxis] = gRandom->Uniform(h->GetAxis(iAxis)->GetXmin(), h->GetAxis(iAxis)->GetXmax());
95  }
96  }
97  h->Fill(coord);
98  Long64_t filled = h->GetNbins();
99  if (fPrintRefresh > 0 && filled % fPrintRefresh == 0)
100  PrintBin(h->GetNdimensions(), coord,
101  TString::Format("%03.2f MB filled=%e [chunkSize=%e nChunks=%d]",
102  sizeof(Double_t) * (Double_t)filled / (1024 * 1024), (Double_t)filled,
103  (Double_t)h->GetChunkSize(), h->GetNChunks())
104  .Data());
105  if (fNFilledMax > 0 && filled >= fNFilledMax) return true;
106  }
107  else {
108  if (fDebugLevel > 1) Printf("iDim=%d", iDim);
109  coord[iDim] = h->GetAxis(iDim)->GetBinCenter(iBin);
110  bool finished = GenerateRecursiveLoop(h, iDim - 1, coord, start);
111  if (finished) return true;
112  }
113 
114  if (iBin == h->GetAxis(iDim)->GetNbins()) start[iDim] = 0;
115  }
116 
117  return false;
118 }
119 
120 bool HnSparseStress::StressRecursiveLoop(HnSparse * h, Int_t & iDim, Int_t * coord)
121 {
125 
126  Long64_t nBinsSizeBytes = sizeof(Double_t) * h->GetNbins();
127  if (fNBytesMax > 0 && nBinsSizeBytes > fNBytesMax) return true;
128 
129  if (iDim >= h->GetNdimensions()) return true;
130  if (coord[h->GetNdimensions() - 1] > h->GetAxis(h->GetNdimensions() - 1)->GetNbins()) {
131  return true;
132  }
133 
134  if (nBinsSizeBytes > 0 && nBinsSizeBytes % (10 * 1024 * 1024) == 0) {
135  Printf("%03.2f MB [chunks=%d binsFilled=%lld]", (Double_t)nBinsSizeBytes / (1024 * 1024), h->GetNChunks(),
136  h->GetNbins());
137  fTimer.Stop();
138  fTimer.Print("m");
139  fTimer.Reset();
140  fTimer.Start();
141  }
142 
143  // Printf("iDim=%d nBins=%d", iDim, GetAxis(iDim)->GetNbins());
144  if (coord[iDim] < h->GetAxis(iDim)->GetNbins()) {
145  coord[iDim]++;
146  coord[iDim - 1] = 0;
147  iDim = 0;
148  return false;
149  }
150 
151  return StressRecursiveLoop(h, ++iDim, coord);
152 }
153 Bool_t HnSparseStress::Stress(HnSparse * h, Long64_t size, bool bytes)
154 {
158 
159  if (h == nullptr) return kFALSE;
160 
161  Long64_t nFill = size;
162  if (bytes) {
163  fNBytesMax = size;
164  nFill = kMaxLong64;
165  }
166  Printf("dimensions=%d chunkSize=%d nFill=%lld maxSize=%lld", h->GetNdimensions(), h->GetChunkSize(), nFill,
167  fNBytesMax);
168 
169  Int_t c[h->GetNdimensions()];
170  Double_t cCenter[h->GetNdimensions()];
171  for (Int_t i = 0; i < h->GetNdimensions(); ++i) {
172  c[i] = 100;
173  }
174 
175  fTimerTotal.Start();
176  fTimer.Start();
177  Bool_t finish = kFALSE;
178  Int_t dim;
179  for (Long64_t iFill = 0; iFill < nFill; ++iFill) {
180  dim = 0;
181  finish = StressRecursiveLoop(h, dim, c);
182  if (finish) break;
183 
184  PrintBin(h->GetNdimensions(), cCenter, "Hello");
185  h->GetBin(cCenter);
186  }
187  fTimer.Stop();
188  fTimerTotal.Stop();
189  fTimerTotal.Print("m");
190 
191  return kTRUE;
192 }
193 void HnSparseStress::PrintBin(Int_t n, Double_t * c, const char * msg)
194 {
198 
199  std::string s = "[";
200  for (Int_t i = 0; i < n; ++i) {
201  s.append(TString::Format("%.3f,", c[i]).Data());
202  }
203  s.resize(s.size() - 1);
204  s.append("] : ");
205  s.append(msg);
206 
207  Printf("%s", s.data());
208 }
209 
210 } // namespace Ndh
211 } // namespace Ndmspc
HnSparseStress object.
HnSparse object.
Definition: HnSparse.h:19