Defining function with general number of parameters

Hello, I got this macro.
Currently, the disang function is called by
W[n][k] = disang(X[k], a[n][1], a[n][2]), a[n][3];

is there a way to define a general double a[Npar], then definining a general disang function, something like

double disang(double x, double a[Npar]) {
double W = 1;
for (int j=1; j<=Npar; j++) {
W = W + a[j]*Legendre(j,x);
}
return W;
}

and call the function in a general way, something like

W[n][k] = disang(X[k], a[n][Npar]);

?
Thank you
dis.C (10.5 KB)

Hello! What you usually do here in C is to pass an array by pointer, plus an additional parameter for the size, just like it already happens for the Legendre function in your script. The disang function would then look like this:

double disang(double x, int nPar, double *a) {
  double W = 1.0;
  for (int j = 1; j <= nPar; j++) {
    W += a[j - 1] * Legendre(j, x);
  }
  return W;
}

And then you use it like this:

W[n][k] = disang(X[k], 2, a[n]);

If you can switch from C to C++, you might consider std::vector

#include <vector>

double disang(double x, const std::vector<double>& a) {
  double W = 1.0;
  int j = 1;
  for (auto v : a) {
    W += v * Legendre(j, x);
    j++;
  }
  return W;
}

Also note that arrays in C / C++ are zero based and not 1 based. So starting your loop at 1 and ending at nPar means that your array must have nPar+1 elements, and you’re ignoring the first element. In my C++ version I have left j starting at 1 so that Legendre is called with the same start value for the loop.

Hello, thank you the both @jonas and @ctacke !

Yes, I usually start my loops from 0. As I said the macro wasn’t written by me …I don’t know the reason beacause of the author started from 1…

Hello @jonas and @ctacke.
I realized that it is not enough changing the disang function to use the macro with a general number of fitting parameters. That’s because the fit function is

double fitfun(double *x, double *par) {
  	double xx = x[0];
	double Sum = 0;
	for (int k=1; k<Npar; k++) {
		Sum = Sum + par[k]*Legendre(k, xx);
	}
  	return par[0]*(1 + Sum);
}

and called as


fit[n] = new TF1("fit", fitfun, -1, 1, 3);

being Npar the gloabal variable

const int Npar = 3;

Then I’ve also pass the Npar value (that is now given by command line) to the fitfun function.
Do you know how to do please?
If I try to pass it in this way:

double fitfun(double *x, double *par, int Npar) {

fit[n] = new TF1("fit", fitfun(Npar), -1, 1, 3);

I get this error

error: no matching function for call to 'fitfun'
                fit[n] = new TF1("fit", fitfun(Npar), -1, 1, 3);
                                        ^~~~~~

note: candidate function not viable: requires 3 arguments, but 1 was provided
double fitfun(double *x, double *par, int Npar) {

because the fitfun already had double*x,double *par

Dis.C (10.6 KB)

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.