2D array of TH1F

Hello, I am using root v5.27/04 on SL5. I am using the attached script to create a 2d arrry of TH1F, It looks OK and I can acturally run it. But If I try to compile it, there is an error
root [5] .L totest.C+g
Info in : script has already been loaded in interpreted mode
Info in : unloading /export/home/has64/hepserv01_repos/BcJpsiPi/./totest.C and compiling it
Info in TUnixSystem::ACLiC: creating shared library /export/home/has64/hepserv01_repos/BcJpsiPi/./totest_C.so
/export/home/has64/hepserv01_repos/BcJpsiPi/./totest.C: In function ‘void totest()’:
/export/home/has64/hepserv01_repos/BcJpsiPi/./totest.C:20: error: no match for ‘operator=’ in ‘(((((TH1F**)(((unsigned int)i) * 4u)) + hist)) + ((TH1F*)(((unsigned int)k) * 588u))) = (test.TString::operator const char*(), (((TH1F*)TObject::operator new(588u)), (->TH1F::TH1F(, ((const char*)“1”), 100, 0.0, 1.0e+1), )))’
/export/home/has64/root/include/TH1.h:522: note: candidates are: TH1F& TH1F::operator=(const TH1F&)
g++: /export/home/has64/hepserv01_repos/BcJpsiPi/totest_C_ACLiC_dict.o: No such file or directory
Error in : Compilation failed!

I do not know what’s wrong with Line 20, any suggestion about calling constructor for this 2D array for TH1F? Thanks!totest.C (303 Bytes)

In your code:

hist is TH1F **
hist[i] is TH1F*
hist[i][k] is TH1F, object of type TH1F and you can not assign pointer to TH1F to object of type TH1F - TH1F does not have such an operator =.

Looks like you are a bit lost in “levels of indirection” :slight_smile:

TH1F **hist = new TH1F *[2];//array of pointers
//i-th element of this array now will point to an array of TH1F
for (i=0;i<2;i++)  
  hist[i]= new TH1F [2];

To initialize your histograms, you simply have to omit ‘new’ in the last loop. This is, of course, very ineffective way to “initialize” as soon as you’ll create temporary object (== will allocate a memory inside TArrayF for bins + TString : name|title + copy empty bins) just to pass bin size and range into you array element, but still, the simplest form. You can also do:

#include "TH1F.h"

void totest()
{
  int i,k;
  TString test = "name";

  TH1F **hist = new TH1F *[2];
  for (i=0;i<2;i++)
    hist[i]= new TH1F [2];
     
  for (i = 0; i < 2; i++)
  {
    for (k = 0; k < 2; k++)
    {
      test +=k;
      hist[i][k].SetName(test.Data());
      hist[i][k].SetTitle("1");
      hist[i][k].SetBins(100, 0., 10.);
    }
  }

  hist[1][1].Draw();
}

Thanks, it helps a lot. But why could it run if I just type .x totest.C?

This is one of weak spots of current version of CINT: not complete type-check and extensions. If I understand correctly, this expression (ill-formed) is not even calling assignment operator, it’s doing something else. So, simply do not rely on CINT too much, it’s not a complete C++ parser/analyzer. If you are not sure about some language constructs - compile them, instead of interpreting.

AFAIK in a bright, nice and happy future we’ll have something reliable and cool from Axel:)

Thans you for your help!