Simultaneous fit of 2 equations

I have two data sets that I wish to simultaneously fit with two equations of the form:


Notice that both have the same pedestal and L, but different heights. Is there a simple way to constrain two independent 1-d fits in this way? The other option is to do a 2-D fit, with one data set on the x-axis and the other on the y-axis. I’ve tried to do this with a sample macro, but MIGRAD fails to converge (despite very good initial parameter values obtained from a 1-D fit of each data set). I’m feeling very green, so any assistance would be greatly appreciated. Thanks in advance.


Hi Nick,

This can be done in a fairly straightforward way by creating an additional controlled variable that assigns to each data point the correct
height variable .
Reformulate your problem slightly:


par[0]+par[int(x[1])] * TMath::Exp(x[0]/L)

x[0] : your original x variable
x[1] : variable that has either value 1 or 2 !!

par[0] : pedestal
par[1] : H_1
par[2] : H_2

Either code directly with Minuit, see test/minexam.cxx example
or use a TF2/TGraph2D where the function is defined according to
case C in the TF1 class desciption.


I tried your idea. It didn’t help convergence, but it did get me thinking in the right direction. I “overloaded” the x and z axis, so that x[j+10]=x[j] and z[j+10]=y[j]. Then I told the fit function myfunction() how to handle the situation with an if statement. Seems to have worked. I’ve attached the code in case anyone else ever wants to do the same thing.


[quote]Double_t myfunction(Double_t *x, Double_t *par)
Double_t f;
if (x[0] < 10) f = par[2]+par[0]*TMath::Exp(x[0]/par[3]);
if (x[0]>=10 && x[0]<20) f=par[2]+par[1]*TMath::Exp(x[0]/par[3]);
return f;

void myfunc()
TF1 *f1 = new TF1(“myfunc”,myfunction,0,10,4);
f1->SetParNames(“HeightX”,“HeightY”,“Pedestal”,“Atten Len”);

void test_fit()
Double_t x[20] = {1,2,3,4,5,6,7,8,9,10,1,2,3,4,5,6,7,8,9,10};
Double_t z[20] = {0,3,5,7,12,16,27,39,50,64,1,3,5,7,10,16,25,35,47,60};
Double_t err = 0.1;

TGraphErrors *gr1 = new TGraphErrors(20,x,z);

TF1 *f1=gROOT->GetFunction(“myfunc”);
f1->SetParNames(“Ped”,“Atten Length”,“HeightX”,“HeightY”);