MaCh3  2.5.1
Reference Guide
histutils.h
Go to the documentation of this file.
1 #pragma once
2 
3 #include "TH1.h"
4 #include "TH2.h"
5 #include "TH2Poly.h"
6 
7 #include <pybind11/numpy.h>
8 
13 
14 namespace py = pybind11;
15 
16 using HistTuple = std::tuple<py::array_t<M3::float_t>, py::array_t<M3::float_t>, py::array_t<M3::float_t>>;
17 
18 void FillEdgesPointer(py::array_t<M3::float_t> edges_buf, TAxis* axis, int nbins) {
19  auto edges_ptr = static_cast<M3::float_t*>(edges_buf.request().ptr);
20  for (int i = 0; i <= nbins; ++i) {
21  edges_ptr[i] = axis->GetBinLowEdge(i + 1);
22  }
23  edges_ptr[nbins] = axis->GetBinLowEdge(nbins + 1) + axis->GetBinWidth(nbins + 1);
24 }
25 
26 HistTuple THNToNumpy(std::unique_ptr<TH1>& hist){
27  int nbinsX = hist->GetNbinsX();
28 
29 
30  py::array_t<M3::float_t> edgesX(nbinsX + 1);
31  FillEdgesPointer(edgesX, hist->GetXaxis(), nbinsX);
32 
33  py::array_t<M3::float_t> edgesY;
34 
35  // If we need to get the contents as a 2D array, we need to check if the histogram is actually 2D
36  int nbinsY = hist->GetNbinsY();
37  if(nbinsY > 1){
38  edgesY = py::array_t<M3::float_t>(nbinsY + 1);
39  FillEdgesPointer(edgesY, hist->GetYaxis(), nbinsY);
40  }
41 
42  // Now we fill the contents
43  py::array_t<M3::float_t> contents({nbinsY, nbinsX});
44  auto contents_buf = contents.request();
45  M3::float_t* contents_ptr = static_cast<M3::float_t*>(contents_buf.ptr);
46 
47  for(int iy=0; iy<nbinsY; ++iy){
48  for(int ix=0; ix<nbinsX; ++ix){
49  contents_ptr[iy * nbinsX + ix] = hist->GetBinContent(ix + 1, iy + 1);
50  }
51  }
52 
53  return std::make_tuple(contents, edgesX, edgesY);
54 }
55 
56 inline py::tuple HistToNumpy(std::unique_ptr<TH1>& hist)
57 {
58  if(dynamic_cast<TH2Poly*>(hist.get())){
59  throw std::runtime_error("TH2Poly is not supported for conversion to numpy arrays");
60  }
61 
62  return py::cast(THNToNumpy(hist));
63 }
HistTuple THNToNumpy(std::unique_ptr< TH1 > &hist)
Definition: histutils.h:26
std::tuple< py::array_t< M3::float_t >, py::array_t< M3::float_t >, py::array_t< M3::float_t > > HistTuple
Definition: histutils.h:16
py::tuple HistToNumpy(std::unique_ptr< TH1 > &hist)
Definition: histutils.h:56
void FillEdgesPointer(py::array_t< M3::float_t > edges_buf, TAxis *axis, int nbins)
Definition: histutils.h:18
double float_t
Definition: Core.h:37