Logo ROOT   6.14/05
Reference Guide
CpuBuffer.cxx
Go to the documentation of this file.
1 // @(#)root/tmva/tmva/dnn:$Id$
2 // Author: Simon Pfreundschuh 12/08/16
3 
4 /*************************************************************************
5  * Copyright (C) 2016, Simon Pfreundschuh *
6  * All rights reserved. *
7  * *
8  * For the licensing terms see $ROOTSYS/LICENSE. *
9  * For the list of contributors see $ROOTSYS/README/CREDITS. *
10  *************************************************************************/
11 
12 /////////////////////////////////////////////////////////////
13 // CPU Buffer interface class for the generic data loader. //
14 /////////////////////////////////////////////////////////////
15 
16 #include <vector>
17 #include <memory>
18 #include "TMVA/DataSetInfo.h"
19 #include "TMVA/DNN/DataLoader.h"
22 #include "Rtypes.h"
23 #include <iostream>
24 
25 namespace TMVA {
26 namespace DNN {
27 
28 //______________________________________________________________________________
29 template <typename AReal>
31 {
32  delete[] * pointer;
33  delete[] pointer;
34 }
35 
36 //______________________________________________________________________________
37 template <typename AReal>
38 TCpuBuffer<AReal>::TCpuBuffer(size_t size) : fSize(size), fOffset(0)
39 {
40  AReal **pointer = new AReal *[1];
41  *pointer = new AReal[size];
42  fBuffer = std::shared_ptr<AReal *>(pointer, fDestructor);
43 }
44 
45 //______________________________________________________________________________
46 template <typename AReal>
48 {
49  TCpuBuffer buffer = *this;
50  buffer.fOffset = offset;
51  buffer.fSize = size;
52  return buffer;
53 }
54 
55 //______________________________________________________________________________
56 template <typename AReal>
58 {
59  std::swap(*this->fBuffer, *other.fBuffer);
60 }
61 
62 //______________________________________________________________________________
63 template <typename AReal>
65 {
66  std::swap(*this->fBuffer, *other.fBuffer);
67 }
68 
69 //______________________________________________________________________________
70 template <>
72  size_t batchSize)
73 {
74  const TMatrixT<Real_t> &inputMatrix = std::get<0>(fData);
75  size_t n = inputMatrix.GetNcols();
76 
77  for (size_t i = 0; i < batchSize; i++) {
78  size_t sampleIndex = *sampleIterator;
79  for (size_t j = 0; j < n; j++) {
80  size_t bufferIndex = j * batchSize + i;
81  buffer[bufferIndex] = static_cast<Real_t>(inputMatrix(sampleIndex, j));
82  }
83  sampleIterator++;
84  }
85 }
86 
87 //______________________________________________________________________________
88 template <>
90  size_t batchSize)
91 {
92  const TMatrixT<Real_t> &outputMatrix = std::get<1>(fData);
93  size_t n = outputMatrix.GetNcols();
94 
95  for (size_t i = 0; i < batchSize; i++) {
96  size_t sampleIndex = *sampleIterator;
97  for (size_t j = 0; j < n; j++) {
98  size_t bufferIndex = j * batchSize + i;
99  buffer[bufferIndex] = static_cast<Real_t>(outputMatrix(sampleIndex, j));
100  }
101  sampleIterator++;
102  }
103 }
104 
105 //______________________________________________________________________________
106 template <>
108  size_t batchSize)
109 {
110  const TMatrixT<Real_t> &outputMatrix = std::get<2>(fData);
111 
112  for (size_t i = 0; i < batchSize; i++) {
113  size_t sampleIndex = *sampleIterator;
114  buffer[i] = static_cast<Real_t>(outputMatrix(sampleIndex, 0));
115  sampleIterator++;
116  }
117 }
118 
119 //______________________________________________________________________________
120 template <>
122  size_t batchSize)
123 {
124  const TMatrixT<Double_t> &inputMatrix = std::get<0>(fData);
125  size_t n = inputMatrix.GetNcols();
126 
127  for (size_t i = 0; i < batchSize; i++) {
128  size_t sampleIndex = *sampleIterator;
129  for (size_t j = 0; j < n; j++) {
130  size_t bufferIndex = j * batchSize + i;
131  buffer[bufferIndex] = inputMatrix(sampleIndex, j);
132  }
133  sampleIterator++;
134  }
135 }
136 
137 //______________________________________________________________________________
138 template <>
140  IndexIterator_t sampleIterator, size_t batchSize)
141 {
142  const TMatrixT<Double_t> &outputMatrix = std::get<1>(fData);
143  size_t n = outputMatrix.GetNcols();
144 
145  for (size_t i = 0; i < batchSize; i++) {
146  size_t sampleIndex = *sampleIterator;
147  for (size_t j = 0; j < n; j++) {
148  size_t bufferIndex = j * batchSize + i;
149  buffer[bufferIndex] = outputMatrix(sampleIndex, j);
150  }
151  sampleIterator++;
152  }
153 }
154 
155 //______________________________________________________________________________
156 template <>
158  IndexIterator_t sampleIterator, size_t batchSize)
159 {
160  const TMatrixT<Double_t> &outputMatrix = std::get<2>(fData);
161 
162  for (size_t i = 0; i < batchSize; i++) {
163  size_t sampleIndex = *sampleIterator;
164  buffer[i] = static_cast<Double_t>(outputMatrix(sampleIndex, 0));
165  sampleIterator++;
166  }
167 }
168 
169 //______________________________________________________________________________
170 template <>
172  size_t batchSize)
173 {
174  Event *event = std::get<0>(fData)[0];
175  size_t n = event->GetNVariables();
176  for (size_t i = 0; i < batchSize; i++) {
177  size_t sampleIndex = * sampleIterator++;
178  event = std::get<0>(fData)[sampleIndex];
179  for (size_t j = 0; j < n; j++) {
180  size_t bufferIndex = j * batchSize + i;
181  buffer[bufferIndex] = event->GetValue(j);
182  }
183  }
184 }
185 
186 //______________________________________________________________________________
187 template <>
189  size_t batchSize)
190 {
191  const DataSetInfo &info = std::get<1>(fData);
192  size_t n = buffer.GetSize() / batchSize;
193 
194  // Copy target(s).
195 
196  for (size_t i = 0; i < batchSize; i++) {
197  size_t sampleIndex = *sampleIterator++;
198  Event *event = std::get<0>(fData)[sampleIndex];
199  for (size_t j = 0; j < n; j++) {
200  // Copy output matrices.
201  size_t bufferIndex = j * batchSize + i;
202  // Classification
203  if (event->GetNTargets() == 0) {
204  if (n == 1) {
205  // Binary.
206  buffer[bufferIndex] = (info.IsSignal(event)) ? 1.0 : 0.0;
207  } else {
208  // Multiclass.
209  buffer[bufferIndex] = 0.0;
210  if (j == event->GetClass()) {
211  buffer[bufferIndex] = 1.0;
212  }
213  }
214  } else {
215  buffer[bufferIndex] = static_cast<Real_t>(event->GetTarget(j));
216  }
217  }
218  }
219 }
220 
221 //______________________________________________________________________________
222 template <>
224  size_t batchSize)
225 {
226  for (size_t i = 0; i < batchSize; i++) {
227  size_t sampleIndex = *sampleIterator++;
228  Event *event = std::get<0>(fData)[sampleIndex];
229  buffer[i] = event->GetWeight();
230  }
231 }
232 
233 //______________________________________________________________________________
234 template <>
236  size_t batchSize)
237 {
238  Event *event = std::get<0>(fData)[0];
239  size_t n = event->GetNVariables();
240  for (size_t i = 0; i < batchSize; i++) {
241  size_t sampleIndex = * sampleIterator++;
242  event = std::get<0>(fData)[sampleIndex];
243  for (size_t j = 0; j < n; j++) {
244  size_t bufferIndex = j * batchSize + i;
245  buffer[bufferIndex] = static_cast<Real_t>(event->GetValue(j));
246  }
247  }
248 }
249 
250 //______________________________________________________________________________
251 template <>
253  size_t batchSize)
254 {
255  const DataSetInfo &info = std::get<1>(fData);
256  size_t n = buffer.GetSize() / batchSize;
257 
258  // Copy target(s).
259 
260  for (size_t i = 0; i < batchSize; i++) {
261  size_t sampleIndex = *sampleIterator++;
262  Event *event = std::get<0>(fData)[sampleIndex];
263  for (size_t j = 0; j < n; j++) {
264  // Copy output matrices.
265  size_t bufferIndex = j * batchSize + i;
266  // Classification
267  if (event->GetNTargets() == 0) {
268  if (n == 1) {
269  // Binary.
270  buffer[bufferIndex] = (info.IsSignal(event)) ? 1.0 : 0.0;
271  } else {
272  // Multiclass.
273  buffer[bufferIndex] = 0.0;
274  if (j == event->GetClass()) {
275  buffer[bufferIndex] = 1.0;
276  }
277  }
278  } else {
279  buffer[bufferIndex] = static_cast<Real_t>(event->GetTarget(j));
280  }
281  }
282  }
283 }
284 
285 //______________________________________________________________________________
286 template <>
288  size_t batchSize)
289 {
290  for (size_t i = 0; i < batchSize; i++) {
291  size_t sampleIndex = *sampleIterator++;
292  Event *event = std::get<0>(fData)[sampleIndex];
293  buffer[i] = static_cast<Real_t>(event->GetWeight());
294  }
295 }
296 
297 //______________________________________________________________________________
298 template <>
300  IndexIterator_t sampleIterator)
301 {
302  const std::vector<TMatrixT<Double_t>> &inputTensor = std::get<0>(fData);
303 
304  if (fBatchDepth == 1) {
305  for (size_t i = 0; i < fBatchHeight; i++) {
306  size_t sampleIndex = *sampleIterator;
307  for (size_t j = 0; j < fBatchWidth; j++) {
308  size_t bufferIndex = j * fBatchHeight + i;
309  buffer[bufferIndex] = static_cast<Real_t>(inputTensor[0](sampleIndex, j));
310  }
311  sampleIterator++;
312  }
313  } else {
314  for (size_t i = 0; i < fBatchDepth; i++) {
315  size_t sampleIndex = *sampleIterator;
316  for (size_t j = 0; j < fBatchHeight; j++) {
317  for (size_t k = 0; k < fBatchWidth; k++) {
318  size_t bufferIndex = i * fBatchHeight * fBatchWidth + k * fBatchHeight + j;
319  buffer[bufferIndex] = static_cast<Real_t>(inputTensor[sampleIndex](j, k));
320  }
321  }
322  sampleIterator++;
323  }
324  }
325 }
326 
327 //______________________________________________________________________________
328 template <>
330  IndexIterator_t sampleIterator)
331 {
332  const TMatrixT<Double_t> &outputMatrix = std::get<1>(fData);
333  size_t n = outputMatrix.GetNcols();
334 
335  for (size_t i = 0; i < fBatchSize; i++) {
336  size_t sampleIndex = *sampleIterator;
337  for (size_t j = 0; j < n; j++) {
338  size_t bufferIndex = j * fBatchSize + i;
339  buffer[bufferIndex] = static_cast<Real_t>(outputMatrix(sampleIndex, j));
340  }
341  sampleIterator++;
342  }
343 }
344 
345 //______________________________________________________________________________
346 template <>
348  IndexIterator_t sampleIterator)
349 {
350  const TMatrixT<Double_t> &outputMatrix = std::get<2>(fData);
351 
352  for (size_t i = 0; i < fBatchSize; i++) {
353  size_t sampleIndex = *sampleIterator;
354  buffer[i] = static_cast<Real_t>(outputMatrix(sampleIndex, 0));
355  sampleIterator++;
356  }
357 }
358 
359 //______________________________________________________________________________
360 template <>
362  IndexIterator_t sampleIterator)
363 {
364  const std::vector<TMatrixT<Double_t>> &inputTensor = std::get<0>(fData);
365 
366  if (fBatchDepth == 1) {
367  for (size_t i = 0; i < fBatchHeight; i++) {
368  size_t sampleIndex = *sampleIterator;
369  for (size_t j = 0; j < fBatchWidth; j++) {
370  size_t bufferIndex = j * fBatchHeight + i;
371  buffer[bufferIndex] = inputTensor[0](sampleIndex, j);
372  }
373  sampleIterator++;
374  }
375  } else {
376  for (size_t i = 0; i < fBatchDepth; i++) {
377  size_t sampleIndex = *sampleIterator;
378  for (size_t j = 0; j < fBatchHeight; j++) {
379  for (size_t k = 0; k < fBatchWidth; k++) {
380  size_t bufferIndex = i * fBatchHeight * fBatchWidth + k * fBatchHeight + j;
381  buffer[bufferIndex] = inputTensor[sampleIndex](j, k);
382  }
383  }
384  sampleIterator++;
385  }
386  }
387 }
388 
389 //______________________________________________________________________________
390 template <>
392  IndexIterator_t sampleIterator)
393 {
394  const TMatrixT<Double_t> &outputMatrix = std::get<1>(fData);
395  size_t n = outputMatrix.GetNcols();
396 
397  for (size_t i = 0; i < fBatchSize; i++) {
398  size_t sampleIndex = *sampleIterator;
399  for (size_t j = 0; j < n; j++) {
400  size_t bufferIndex = j * fBatchSize + i;
401  buffer[bufferIndex] = outputMatrix(sampleIndex, j);
402  }
403  sampleIterator++;
404  }
405 }
406 
407 //______________________________________________________________________________
408 template <>
410  IndexIterator_t sampleIterator)
411 {
412  const TMatrixT<Double_t> &outputMatrix = std::get<2>(fData);
413 
414  for (size_t i = 0; i < fBatchSize; i++) {
415  size_t sampleIndex = *sampleIterator;
416  buffer[i] = static_cast<Double_t>(outputMatrix(sampleIndex, 0));
417  sampleIterator++;
418  }
419 }
420 
421 ///- re-implement specialization for Double_t
422 //______________________________________________________________________________
423 template <>
425  IndexIterator_t sampleIterator)
426 {
427  // one event, one example in the batch
428 
429  if (fBatchDepth == 1 && fBatchHeight == fBatchSize) {
430  for (size_t i = 0; i < fBatchHeight; i++) {
431  size_t sampleIndex = *sampleIterator;
432  Event * event = std::get<0>(fData)[sampleIndex];
433  for (size_t j = 0; j < fBatchWidth; j++) {
434  size_t bufferIndex = j * fBatchHeight + i;
435  buffer[bufferIndex] = event->GetValue(j);
436  }
437  sampleIterator++;
438  }
439  } else if (fBatchDepth == fBatchSize) {
440  // batchDepth is batch size
441  for (size_t i = 0; i < fBatchDepth; i++) {
442  size_t sampleIndex = *sampleIterator;
443  Event * event = std::get<0>(fData)[sampleIndex];
444  for (size_t j = 0; j < fBatchHeight; j++) {
445  for (size_t k = 0; k < fBatchWidth; k++) {
446  // because of the column-major ordering
447  size_t bufferIndex = i * fBatchHeight * fBatchWidth + k * fBatchHeight + j;
448  buffer[bufferIndex] = event->GetValue(j * fBatchWidth + k);
449  }
450  }
451  sampleIterator++;
452  }
453  }
454  else {
455  Error("TTensorDataLoader","Inconsistency between batch depth and batch size");
456  R__ASSERT(0); // one event, one example in the batch
457  }
458 }
459 
460 //______________________________________________________________________________
461 template <>
463  IndexIterator_t sampleIterator)
464 {
465  const DataSetInfo &info = std::get<1>(fData);
466  size_t n = buffer.GetSize() / fBatchSize;
467 
468  // Copy target(s).
469 
470  for (size_t i = 0; i < fBatchSize; i++) {
471  size_t sampleIndex = *sampleIterator++;
472  Event *event = std::get<0>(fData)[sampleIndex];
473  for (size_t j = 0; j < n; j++) {
474  // Copy output matrices.
475  size_t bufferIndex = j * fBatchSize + i;
476  // Classification
477  if (event->GetNTargets() == 0) {
478  if (n == 1) {
479  // Binary.
480  buffer[bufferIndex] = (info.IsSignal(event)) ? 1.0 : 0.0;
481  } else {
482  // Multiclass.
483  buffer[bufferIndex] = 0.0;
484  if (j == event->GetClass()) {
485  buffer[bufferIndex] = 1.0;
486  }
487  }
488  } else {
489  buffer[bufferIndex] = static_cast<Real_t>(event->GetTarget(j));
490  }
491  }
492  }
493 }
494 
495 //______________________________________________________________________________
496 template <>
498  IndexIterator_t sampleIterator)
499 {
500  for (size_t i = 0; i < fBatchSize; i++) {
501  size_t sampleIndex = *sampleIterator++;
502  Event *event = std::get<0>(fData)[sampleIndex];
503  buffer[i] = event->GetWeight();
504  }
505 }
506 
507 ///- re-implement specialization for Real_t
508 //______________________________________________________________________________
509 template <>
511  IndexIterator_t sampleIterator)
512 {
513  // one event, one example in the batch
514 
515  if (fBatchDepth == 1 && fBatchHeight == fBatchSize) {
516  for (size_t i = 0; i < fBatchHeight; i++) {
517  size_t sampleIndex = *sampleIterator;
518  Event * event = std::get<0>(fData)[sampleIndex];
519  for (size_t j = 0; j < fBatchWidth; j++) {
520  size_t bufferIndex = j * fBatchHeight + i;
521  buffer[bufferIndex] = event->GetValue(j);
522  }
523  sampleIterator++;
524  }
525  } else if (fBatchDepth == fBatchSize) {
526  // batchDepth is batch size
527  for (size_t i = 0; i < fBatchDepth; i++) {
528  size_t sampleIndex = *sampleIterator;
529  Event * event = std::get<0>(fData)[sampleIndex];
530  for (size_t j = 0; j < fBatchHeight; j++) {
531  for (size_t k = 0; k < fBatchWidth; k++) {
532  // because of the column-major ordering
533  size_t bufferIndex = i * fBatchHeight * fBatchWidth + k * fBatchHeight + j;
534  buffer[bufferIndex] = event->GetValue(j * fBatchWidth + k);
535  }
536  }
537  sampleIterator++;
538  }
539  }
540  else {
541  Error("TTensorDataLoader","Inconsistency between batch depth and batch size");
542  R__ASSERT(0);
543  }
544 }
545 
546 //______________________________________________________________________________
547 template <>
549  IndexIterator_t sampleIterator)
550 {
551  const DataSetInfo &info = std::get<1>(fData);
552  size_t n = buffer.GetSize() / fBatchSize;
553 
554  // Copy target(s).
555 
556  for (size_t i = 0; i < fBatchSize; i++) {
557  size_t sampleIndex = *sampleIterator++;
558  Event *event = std::get<0>(fData)[sampleIndex];
559  for (size_t j = 0; j < n; j++) {
560  // Copy output matrices.
561  size_t bufferIndex = j * fBatchSize + i;
562  // Classification
563  if (event->GetNTargets() == 0) {
564  if (n == 1) {
565  // Binary.
566  buffer[bufferIndex] = (info.IsSignal(event)) ? 1.0 : 0.0;
567  } else {
568  // Multiclass.
569  buffer[bufferIndex] = 0.0;
570  if (j == event->GetClass()) {
571  buffer[bufferIndex] = 1.0;
572  }
573  }
574  } else {
575  buffer[bufferIndex] = static_cast<Real_t>(event->GetTarget(j));
576  }
577  }
578  }
579 }
580 
581 //______________________________________________________________________________
582 template <>
584  IndexIterator_t sampleIterator)
585 {
586  for (size_t i = 0; i < fBatchSize; i++) {
587  size_t sampleIndex = *sampleIterator++;
588  Event *event = std::get<0>(fData)[sampleIndex];
589  buffer[i] = event->GetWeight();
590  }
591 }
592 
593 
594 // Explicit instantiations.
595 template class TCpuBuffer<Double_t>;
596 template class TCpuBuffer<Real_t>;
597 
598 } // namespace DNN
599 } // namespace TMVA
void swap(TDirectoryEntry &e1, TDirectoryEntry &e2) noexcept
void CopyTo(TCpuBuffer &)
Copy data to another buffer.
Definition: CpuBuffer.cxx:64
std::shared_ptr< AFloat * > fBuffer
Definition: CpuBuffer.h:49
Int_t GetNcols() const
Definition: TMatrixTBase.h:125
#define R__ASSERT(e)
Definition: TError.h:96
void operator()(AFloat **pointer)
Definition: CpuBuffer.cxx:30
TMatrixT.
Definition: TMatrixDfwd.h:22
Class that contains all the data information.
Definition: DataSetInfo.h:60
typename std::vector< size_t >::iterator IndexIterator_t
Definition: DataLoader.h:42
TCpuBuffer(size_t size)
Construct buffer to hold size numbers of type AFloat.
Definition: CpuBuffer.cxx:38
void Error(const char *location, const char *msgfmt,...)
TCpuBuffer.
Definition: CpuBuffer.h:43
TDataLoader.
Definition: DataLoader.h:79
double Double_t
Definition: RtypesCore.h:55
float Real_t
Definition: RtypesCore.h:64
Abstract ClassifierFactory template that handles arbitrary types.
void CopyFrom(TCpuBuffer &)
Copy data from another buffer.
Definition: CpuBuffer.cxx:57
Bool_t IsSignal(const Event *ev) const
TCpuBuffer GetSubBuffer(size_t offset, size_t start)
Return subbuffer of siez start starting at element offset.
Definition: CpuBuffer.cxx:47
size_t GetSize() const
Definition: CpuBuffer.h:81
struct TMVA::DNN::TCpuBuffer::TDestructor fDestructor
const Int_t n
Definition: legend1.C:16