#ifdef vxWorks #include #endif #include #include #include #define SMALL 1e-8 #define MAX(a,b) (a)>(b)?(a):(b) #define MIN(a,b) (a)<(b)?(a):(b) int pfit(double *x, double *y, int n, double *x0, double *x0_e, double *y0, double *y0_e, double *w, double *w_e, double *chisq, double *depth); int lfit(double *x, double *y, int n, double *m, double *m_e, double *b, double *b_e, double *chisq); int fitpoly(double *x, double *y, int n, double *c, double *b, double *a, double *mask); /* * Caller supplies x[], y[] arrays of n pts. * We return derivative in d. */ int nderiv(double *x, double *y, int n, double *d, int npts, double *lx) { int i, j, e, m; double c, b, a; m = 2*npts+1; /* first m/2+1 points */ e = fitpoly(x,y,m, &c, &b, &a, NULL); if (e) { printf("nderiv: error in fitpoly\n"); return(e); } /* * y[i] = c + b*x[i] + a*(x[i])^2 * dy/dx = b + 2*a*(x[i]) */ for (j=0; j= 2m+1, where m is 5th arg to nderiv() */ return(nderiv(x, y, n, d, 2, work)); } int invert3x3(double **aa, double **bb) { double a = aa[0][0], b = aa[0][1], c = aa[0][2]; double d = aa[1][0], e = aa[1][1], f = aa[1][2]; double g = aa[2][0], h = aa[2][1], i = aa[2][2]; double det = a*(e*i-h*f) + b*(f*g-i*d) + c*(d*h-g*e); if (fabs(det) < SMALL) return(-1); bb[0][0] = (e*i - f*h) / det; bb[0][1] = (c*h - b*i) / det; bb[0][2] = (b*f - c*e) / det; bb[1][0] = (f*g - d*i) / det; bb[1][1] = (a*i - c*g) / det; bb[1][2] = (c*d - a*f) / det; bb[2][0] = (d*h - e*g) / det; bb[2][1] = (b*g - a*h) / det; bb[2][2] = (a*e - b*d) / det; return(0); } int invert2x2(double **aa, double **bb) { double a = aa[0][0], b = aa[0][1]; double c = aa[1][0], d = aa[1][1]; double det = a*d - c*b; if (fabs(det) < SMALL) return(-1); bb[0][0] = d / det; bb[0][1] = -b / det; bb[1][0] = -c / det; bb[1][1] = a / det; return(0); } /* line: y = m*x +b */ int lfit(double *x, double *y /*, double *e*/, int n, double *m, double *m_e, double *b, double *b_e, double *chisq) { double beta[2], a[2], ea[2]; double aa[4], *alpha[2]; double ia[4], *ialpha[2]; double e2, q; int i; if (n<2) return(-1); alpha[0] = &aa[0]; alpha[1] = &aa[2]; ialpha[0] = &ia[0]; ialpha[1] = &ia[2]; beta[0] = beta[1] = 0; alpha[0][0] = alpha[0][1] = alpha[1][0] = alpha[1][1] = 0; for (i=0; i2) *chisq /= (n-2); /* per degree of freedom */ return(0); } /* parabola: y[i] = y0 + w*(x[i]-x0)*(x[i]-x0) */ int pfit(double *x, double *y /*, double *e */, int n, double *x0, double *x0_e, double *y0, double *y0_e, double *w, double *w_e, double *chisq, double *depth) { double beta[3], a[3], ea[3]; double aa[9], *alpha[3]; double ia[9], *ialpha[3]; double e1, e2, q, x2, q1; int i, j; if (n<3) return(-1); alpha[0] =&aa[0]; alpha[1] =&aa[3], alpha[2] =&aa[6]; ialpha[0]=&ia[0]; ialpha[1]=&ia[3], ialpha[2]=&ia[6]; for (i=0; i<3; i++) { beta[i] = 0; for (j=0; j<3; j++) {alpha[i][j] = 0;} } for (i=0, e1=0.; i3) *chisq /= (n-3); /* per degree of freedom */ *depth = *w * ((x[0] - *x0) * (x[0] - *x0) + (x[n-1] - *x0) * (x[n-1] - *x0)) / (2*e1); /* printf("pfit: x0=%7f(%7f); y0=%7f(%7f); w=%7f(%7f); chi=%7f; depth=%f\n", *x0, *x0_e, *y0, *y0_e, *w, *w_e, *chisq, *depth);*/ return(0); } /* fit: y[i] = c + b*(x[i]-x0) + a*(x[i]-x0)*(x[i]-x0) */ int fitpoly(double *x, double *y, int n, double *c, double *b, double *a, double *mask) { double beta[3]; double aa[9], *alpha[3]; double ia[9], *ialpha[3]; int i, j; if (n<3) return(-1); alpha[0] =&aa[0]; alpha[1] =&aa[3], alpha[2] =&aa[6]; ialpha[0]=&ia[0]; ialpha[1]=&ia[3], ialpha[2]=&ia[6]; for (i=0; i<3; i++) { beta[i] = 0; for (j=0; j<3; j++) {alpha[i][j] = 0;} } for (i=0; iSMALL)) { beta[0] += y[i]; beta[1] += y[i]*x[i]; beta[2] += (y[i]*x[i]*x[i]); alpha[0][0] += 1; alpha[0][1] += x[i]; alpha[1][1] += x[i]*x[i]; alpha[1][2] += x[i]*x[i]*x[i]; alpha[2][2] += x[i]*x[i]*x[i]*x[i]; } } alpha[1][0] = alpha[0][1]; alpha[2][0] = alpha[0][2] = alpha[1][1]; alpha[2][1] = alpha[1][2]; if (invert3x3(alpha, ialpha)) { printf("fitpoly: error in invert3x3\n"); return(-1); } *c = *b = *a = 0.; for (j=0; j<3; j++) { *c += beta[j]*ialpha[j][0]; *b += beta[j]*ialpha[j][1]; *a += beta[j]*ialpha[j][2]; } return(0); }