Modifying trees while in memory

I have a TChain of data which I was hoping to use in a TMultiLayerPerceptron, but I (think I) need a 0/1 background/signal attribute for training. My first plan was to use AddFriend to add a TChain of the right length containing a single background/signal branch to the chain. Trying this I found you have to write code like this:

TChain * tc1 = new TChain("1","");
tc1->Add("1.root/1");

Int_t nEntries = tc1->GetEntries();
delete tc1;

 TFile fAddData("adddata.root","recreate");
TTree t1 ("addData","");
Double_t derivedValue;
t1.Branch("DerivedValue",&derivedValue,"DerivedValue/D");
for (Int_t jEntry=0; jEntry<nEntries;jEntry++) 
	{
	derivedValue = 0; 
	t1.Fill();
	}
t1.Write();
fAddData.Close();

tc1 = new TChain("1","");
tc1->Add("1.root/1");
	
	
TChain tc2("addData");
tc2.Add("adddata.root");

tc1->AddFriend("addData");

Which seems a very roundabout way of doing it, outputting a tree to disk and having to recreate tc1. I was wondering if there was a better way of doing this while the TChain is open (attempting to AddFriend after using any of tc1’s member functions causes AddFriend to not find tc2, and the size and complexity of the original TChain makes it even more of a hassle to follow the user guide example and recreate the data in a new Tree).

Thanks in advance (4.02/00)

Chris

Just a little update- I should really test my code better, the example given above works fine - but when I used the same technique on my data (made up of objects contiaing objects with SetMakeClass(1) ) it no longer works. However when I used a TTree for additional data instead of a TChain it seems to wokr fine. Frankly I’m very suspiciousof adding a tree to a chain. My previous example would become:

TChain * tc1 = new TChain("1","");
tc1->Add("1.root/1");

Int_t nEntries = tc1->GetEntries();
delete tc1;

TFile fAddData("adddata.root","recreate");
TTree t1 ("addData","");
Double_t derivedValue;
t1.Branch("DerivedValue",&derivedValue,"DerivedValue/D");
for (Int_t jEntry=0; jEntry<nEntries;jEntry++)
   {
   derivedValue = 0;
   t1.Fill();
   }
t1.Write();
fAddData.Close();

tc1->Reset();
tc1->Add("1.root/1");

tc1->AddFriend("addData","adddata.root");

Hi,
this should work:

TChain *tc1=new TChain("1",""); tc1->Add("1.root/1", -1); // we need the number of entries in 1.root Int_t nEntries = tc1->GetEntries(); TTree* t1=new TTree("addData",""); Double_t derivedValue; t1->Branch("DerivedValue",&derivedValue,"DerivedValue/D"); for (Int_t jEntry=0; jEntry<nEntries;jEntry++) { derivedValue = 0; t1->Fill(); } tc1->AddFriend(t1, "DerivedValue");You should also be able to specify pretty complex expressions for any neuron, as in “(Entry$%10)>4” instead of “DerivedValue” (for the expression syntax see http://root.cern.ch/root/html/src/TTree.cxx.html#TTree:Draw), though I’ve never tried that. Using that you might not have to create a friend tree at all (depends on how you determine the ANN target value of an entry in the chain).
Axel.

Thank you very much for your reply, that’s very useful information. So I can use any character string that I would use in a draw function as a neuron? That makes my life so much easier.

Chris