# Variable bin with same entries

Dear Rooter
I produce some plots with Ttree with bin fixed ,I want to create a variable bin Ttree with a binning such
that the entries per bin is about the same.

Sandra

A TTree itself has no bins. The histograms you produce using a given TTree has bins. When you use a command like.

``````tree->Draw("x");
``````

An histograming operation will be done on the `x` variable in the TTree `tree`. By default the histogram created (`htemp`) has equidistant bins. If you want non-equisitant bins you should create a such histogram (`h_neq`) before performing the `Draw` and then do it as follow:

``````tree->Draw("x>>h_neq");
``````

Exactly the TTree has no bin but when I want to read my TTree I create Histograms with bin fix.
you can find bellow what I did :

``````   TTree *t4 = (TTree*)f->Get("t4");

Double_t ,TST_Ntest,TST_Vtest;

TH1D *TST_N   = new TH1D("TST","",10, 0.0, 100.);

/////////////Create bin fix///////////////
Int_t nentries = 41967;
TST_N->FillRandom("gaus",nentries);
Double_t xbins;
Int_t k=0;
TAxis *axis = TST_N->GetXaxis();
for (Int_t i=1;i<=50;i++) {
Int_t y = (Int_t)TST_N->GetBinContent(i);
if (y <=0) continue;
Double_t dx = axis->GetBinWidth(i)/y;
Double_t xmin = axis->GetBinLowEdge(i);
for (Int_t j=0;j<y;j++) {
xbins[k] = xmin +j*dx;
k++;
}
}
xbins[k] = axis->GetXmax();
TH1F *hnew = new TH1F("hnew","rebinned",k,xbins);
hnew->FillRandom("gaus",10*nentries);

//rebin hnew keeping only 50% of the bins
Double_t xbins2;
Int_t kk=0;
for (Int_t j=0;j<k;j+=2) {
xbins2[kk] = xbins[j];
kk++;
}
xbins2[kk] = xbins[k];

TH1F *hnew2 = (TH1F*)hnew->Rebin(kk,"hnew2",xbins2);

//draw the 3 histograms
TCanvas *c1 = new TCanvas("c1","c1",800,1000);
c1->Divide(1,3);
c1->cd(1);
TST_N->Draw();
c1->cd(2);
hnew->Draw();
c1->cd(3);
hnew2->Draw();
``````

But I have got strang plot and the number of entry are increased .

Cheers,
Sandra

As far as can see, in your example `TST_N` and `h new` are filled with random numbers, `h_new2` is empty and you do not use the TTree `t4`

You are right. Could you please tell me what I can to do with this essue because I change TST_N with TST_Ntest but I got this error :
non class,struct,union object TST_Vtest used with . or -> macro.c:17:
*** Interpreter error recovered ***

What is the name of the variable you want to see in the `TTree` named `t4` ?

The name of the variable that I want to see is “TST_Ntest” and I use : t4->SetBranchAddress(“TST_Ntest”,&TST_Ntest); to read

Just do:

``````TTree *t4 = (TTree*)f->Get("t4");
t4->Draw("TST_Ntest");
``````
``````t4->Draw("TST_Ntest");
``````

this to draw TST_Ntest variable with bin fixed but for me I want variable bin with the same entry .

Example :

This is an Let’s assume we have a TST histogram from 0. to 100 GeV. with 1000 entrie. Let’s assume you have created this histograms with 50 bins

we want to have 5 bins… meaning each bin will have 200 entries. SO now we should find the intervals [TST_min,TST_max] corresponding to bin contents ofabout 200 entries each…

Then you define a (double or single) 5+1 vector like this:

``````Double_t TST_edges = {TST_min_1 , TST_max_1, TST_max_2, TST_max_3, TST_max_4, TST_max_5}
``````

So you an now create a new histograms as follow:

``````TH1* h_new = new TH1D("name", "title", 5, TST_edges);
``````

with 5 bins corresponding to TST_edges with each bin having about 200 entries…

But for me I have 41967 entry and Idon’t know what is criteria to transform the histogram bins from constant bin to variable bin.

Ok. So now you should create the variable bin size histogram using this constructor.
Let say you call this histogram `h1_neq`.

Then you do:

``````t4->Draw("TST_Ntest >> h1_neq");
``````

I imagine you could determine the bin edges as such:

``````#include <algorithm>
#include <vector>

//Set the number of bins
const int numBins = 10;

//Determine the number of counts per bin
int countsPerBin = tree->GetEntries() / numBins;

//Loop over all entries in the tree and store them in a vector
double value;
std::vector<double> values;
for (int entry=0; entry<tree->GetEntries(); ++entry) {
tree->GetEntry(entry);
values.push_back(value);
}

//Sort the vector of values
std::sort(values.begin(), values.end());

//Take the value every countsPerBin and use it as the bin edge.
std::vector<double> binEdges;
binEdges.push_back(values.front());
for (int edge=1; edge<numBins; edge++) {
binEdges.push_back(values.at(countsPerBin * edge));
}
binEdges.push_back(values.back());
``````

I use your algo but I have got this error :
Error: Function sort(values.begin(),values.end()) is not defined in current scope macro.c:19:
*** Interpreter error recovered ***

It is just an algorithm, not code for your specific case, it will need some modification. You will need to replace `"value"` with the name of the branch you are interested, the pointer `tree` with the pointer of your tree, and so on.

``````#include <algorithm>
``````

http://www.cplusplus.com/reference/algorithm/sort/

Hi smith,

Could you please explain me this instruction “(values.at(countsPerBin * edge)” because I have got an error in this line

Cheers,