57 int fi, ret, n, to, from, to_min, from_min, orig_max_nr;
59 double kel, c0=0.0, *cx, *cy;
60 double slope, slope_sd, ic, ic_sd, r, f, adj_r2, adj_r2_max;
65 if(status!=NULL) sprintf(status,
"program error");
66 if(dft==NULL || ext==NULL)
return -1;
67 if(*min_nr<2) *min_nr=3;
68 if(max_nr>-1 && max_nr<*min_nr)
return -2;
74 while(dft->
x[fitNr-1]>*fittime && fitNr>0) fitNr--;
75 if(loginfo!=NULL) fprintf(loginfo,
"fitNr := %d\nTime range := %g - %g\n",
76 fitNr, dft->
x[0], dft->
x[fitNr-1]);
78 *fittime=dft->
x[fitNr-1];
81 if(status!=NULL) sprintf(status,
"too few samples for extrapolation");
87 fi=0;
while(dft->
x[fi]<(*fittime-mintime) && fi<fitNr) fi++;
89 if(status!=NULL) sprintf(status,
"required minimum fit range too large");
92 *min_nr=((fitNr-fi)>*min_nr?fitNr-fi:*min_nr);
94 if(loginfo!=NULL) fprintf(loginfo,
"final_min_nr := %d\n", *min_nr);
102 if(loginfo!=NULL) fprintf(loginfo,
"extr_sampl=%g\n", extr_sampl);
103 if(extr_sampl<1.0E-8) {
104 if(status!=NULL) sprintf(status,
"check sample times");
110 if(status!=NULL) sprintf(status,
"no extrapolation is needed");
113 n=ceil(f/extr_sampl);
114 if(loginfo!=NULL) fprintf(loginfo,
" extr_sampl=%g n=%d\n", extr_sampl, n);
119 if(status!=NULL) sprintf(status,
"error in memory allocation.\n");
124 for(fi=0; fi<dft->
frameNr; fi++) {
125 ext->
x[fi]=dft->
x[fi]; ext->
x1[fi]=dft->
x1[fi]; ext->
x2[fi]=dft->
x2[fi];}
128 ext->
x[fi]=ext->
x[fi-1]+extr_sampl;
129 ext->
x1[fi]=ext->
x2[fi-1]; ext->
x2[fi]=ext->
x[fi]+0.5*extr_sampl;
133 ext->
x1[fi]=ext->
x2[fi-1]; ext->
x2[fi]=ext->
x1[fi]+extr_sampl;
134 ext->
x[fi]=0.5*(ext->
x1[fi]+ext->
x2[fi]);
141 for(
int ri=0; ri<dft->
voiNr; ri++)
142 for(
int fi=0; fi<dft->
frameNr; fi++)
143 ext->
voi[ri].
y[fi]=dft->
voi[ri].
y[fi];
149 if(loginfo!=NULL) fprintf(loginfo,
"ln transformation\n");
150 for(
int ri=0; ri<dft->
voiNr; ri++)
151 for(
int fi=0; fi<dft->
frameNr; fi++) {
152 if(!isnan(dft->
voi[ri].
y[fi]) && dft->
voi[ri].
y[fi]>0.0)
153 dft->
voi[ri].
y2[fi]=log(dft->
voi[ri].
y[fi]);
155 dft->
voi[ri].
y2[fi]=nan(
"");
162 if(loginfo!=NULL) fprintf(loginfo,
"linear fitting\n");
163 cx=(
double*)malloc(2*fitNr*
sizeof(
double));
if(cx==NULL) {
164 if(status!=NULL) sprintf(status,
"out of memory");
168 for(
int ri=0; ri<dft->
voiNr; ri++) {
169 kel=0.0; max_nr=orig_max_nr;
171 if(dft->
voiNr>1 && loginfo!=NULL)
172 fprintf(loginfo,
"%s :\n", dft->
voi[ri].
name);
175 for(fi=n=0; fi<fitNr; fi++)
176 if(dft->
x[fi]>0.0 && !isnan(dft->
voi[ri].
y2[fi])) {
177 cx[n]=dft->
x[fi]; cy[n++]=dft->
voi[ri].
y2[fi];}
179 if(status!=NULL) sprintf(status,
"check the datafile (%d<%d)", n, *min_nr);
182 if(max_nr<=0) max_nr=n;
184 from_min=to_min=-1; adj_r2_max=-9.99E+99;
185 for(from=n-max_nr, to=n-1; from<1+n-*min_nr; from++) {
189 cx+from, cy+from, snr, &slope, &slope_sd, &ic, &ic_sd, &r, &f
192 adj_r2= 1.0 - ((1.0-r*r)*(double)(snr-1)) / (
double)(snr-2);
197 if(adj_r2>adj_r2_max+0.0001) {
198 adj_r2_max=adj_r2; from_min=from; to_min=to; kel=-slope; c0=exp(ic);
201 fprintf(loginfo,
" adj_r2=%g from=%d (%g)\n", adj_r2, from, *(cx+from) );
204 if(status!=NULL) sprintf(status,
"check the datafile");
211 fprintf(loginfo,
" k(el)=%g adj_r2=%g C(0)=%g; %d data points.\n",
212 kel, adj_r2_max, c0, (to_min-from_min)+1 );
214 for(fi=fitNr; fi<ext->
frameNr; fi++) {
215 ext->
voi[ri].
y[fi]=c0*exp(-kel*ext->
x[fi]);
219 for(fi=fitNr-1, f=0.0, n=0; fi>=0 && n<3; fi--)
220 if(!isnan(dft->
voi[ri].
y[fi])) {f+=dft->
voi[ri].
y[fi]; n++;}
221 if(n>0) f/=(double)n;
223 sprintf(status,
"curve end is not descending; extrapolation with horizontal line determined as avg of %d samples", n);
225 for(fi=fitNr; fi<ext->
frameNr; fi++) {
226 ext->
voi[ri].
y[fi]=f;
232 if(status!=NULL) sprintf(status,
"ok");
421 int ret, fi, fj, i, new_frameNr=0, new_voiNr=0;
425 printf(
"dftDivideFrames(*dft, %d, %d, *dft2)\n", voi_index, add_nr);
429 if(dft==NULL || dft2==NULL)
return 1;
431 if(add_nr<1 || add_nr>100)
return 3;
432 if(voi_index>=dft->
voiNr)
return 4;
436 else new_frameNr=(add_nr+1)*dft->
frameNr-1;
437 if(voi_index<0) new_voiNr=dft->
voiNr;
else new_voiNr=1;
439 printf(
"new_frameNr := %d\n", new_frameNr);
440 printf(
"new_voiNr := %d\n", new_voiNr);
445 if(new_frameNr>dft2->
frameNr || new_voiNr>dft2->_voidataNr) {
447 printf(
"deleting old data and allocating new\n"); fflush(stdout);}
457 for(
int ri=0; ri<dft->
voiNr; ri++) {
460 if(ret!=0)
return 13;
465 for(fi=0, fj=0; fi<dft->
frameNr; fi++) {
466 fdur=(dft->
x2[fi]-dft->
x1[fi])/(
double)(add_nr+1);
467 for(i=0; i<add_nr+1; i++) {
469 dft2->
x1[fj]=dft->
x1[fi]+fdur*(double)i;
470 dft2->
x2[fj]=dft2->
x1[fj]+fdur;
471 dft2->
x[fj]=0.5*(dft2->
x1[fj]+dft2->
x2[fj]);
473 dft2->
voi[0].
y[fj]=dft->
voi[voi_index].
y[fi];
475 for(
int ri=0; ri<dft->
voiNr; ri++) dft2->
voi[ri].
y[fj]=dft->
voi[ri].
y[fi];
480 dft2->
x[0]=dft->
x[0];
481 for(fi=1, fj=0; fi<dft->
frameNr; fi++) {
482 fdur=(dft->
x[fi]-dft->
x[fi-1])/(
double)(add_nr+1);
483 for(i=0; i<add_nr+1; i++) {
484 fj=(fi-1)*(add_nr+1) + i + 1;
485 dft2->
x[fj]=dft->
x[fi-1]+fdur*(double)(i+1);
493 for(
int ri=0; ri<dft->
voiNr; ri++) {
500 if(ret!=0)
return 21;
553 int fi, ret, n, to, from, to_min, from_min, orig_max_nr;
556 double adj_r2, slope, slope_sd, ic, ic_sd, r, f, ySD_min;
557 double adj_r2_max, adj_r2_prev=-10.0, ic_min, slope_min;
561 if(status!=NULL) sprintf(status,
"program error");
562 if(dft==NULL || fit==NULL)
return -1;
563 if(*min_nr<2) *min_nr=3;
564 if(max_nr>-1 && max_nr<*min_nr)
return -2;
570 while(dft->
x[fitNr-1]>*fittime && fitNr>0) fitNr--;
571 if(loginfo!=NULL) fprintf(loginfo,
"fitNr := %d\nTime range := %g - %g\n",
572 fitNr, dft->
x[0], dft->
x[fitNr-1]);
574 *fittime=dft->
x[fitNr-1];
577 if(status!=NULL) sprintf(status,
"too few samples for linear fit");
583 fi=0;
while(dft->
x[fi]<(*fittime-mintime) && fi<fitNr) fi++;
585 if(status!=NULL) sprintf(status,
"required minimum fit range too large");
588 *min_nr=((fitNr-fi)>*min_nr?fitNr-fi:*min_nr);
590 if(loginfo!=NULL) fprintf(loginfo,
"final_min_nr := %d\n", *min_nr);
594 if(loginfo!=NULL) fprintf(loginfo,
"Error %d: cannot allocate memory for fits.\n", ret);
595 if(status!=NULL) sprintf(status,
"cannot allocate memory for fits");
599 cx=(
double*)malloc(2*fitNr*
sizeof(
double));
if(cx==NULL) {
600 if(status!=NULL) sprintf(status,
"out of memory");
606 if(loginfo!=NULL) fprintf(loginfo,
"linear fitting\n");
607 for(
int ri=0; ri<dft->
voiNr; ri++) {
610 if(dft->
voiNr>1 && loginfo!=NULL)
611 fprintf(loginfo,
"%s :\n", dft->
voi[ri].
name);
616 for(fi=n=0; fi<fitNr; fi++)
617 if(dft->
x[fi]>0.0 && !isnan(dft->
voi[ri].
y[fi])) {
618 cx[n]=dft->
x[fi]; cy[n++]=dft->
voi[ri].
y[fi];}
620 if(status!=NULL) sprintf(status,
"check the datafile (%d<%d)", n, *min_nr);
623 if(max_nr<=0) max_nr=n;
625 from_min=to_min=-1; adj_r2_max=-9.99E+99; ic_min=slope_min=0.0; ySD_min=0.0;
626 for(from=n-*min_nr, to=n-1; from>=n-max_nr; from--) {
630 cx+from, cy+from, snr, &slope, &slope_sd, &ic, &ic_sd, &r, &f
633 adj_r2= 1.0 - ((1.0-r*r)*(double)(snr-1)) / (
double)(snr-2);
634 if(adj_r2<0.0 && loginfo!=NULL)
635 fprintf(loginfo,
" r=%g; snr=%d\n", r, snr);
639 if(adj_r2>adj_r2_max-0.0001) {
640 adj_r2_max=adj_r2; from_min=from; to_min=to;
641 ic_min=ic; slope_min=slope; ySD_min=f;
644 fprintf(loginfo,
" adj_r2=%g from=%d (%g)\n",
645 adj_r2, from, *(cx+from) );
647 if(check_impr!=0 && adj_r2_prev>-1.0 && adj_r2>0.0 && adj_r2<adj_r2_prev)
653 if(status!=NULL) sprintf(status,
"check the datafile");
656 if(loginfo!=NULL) fprintf(loginfo,
" adj_r2_max=%g.\n", adj_r2_max );
658 fit->
voi[ri].
p[0]=ic_min;
659 fit->
voi[ri].
p[1]=slope_min;
660 fit->
voi[ri].
p[2]=adj_r2_max;
668 if(status!=NULL) sprintf(status,
"ok");
int interpolate(double *x, double *y, int nr, double *newx, double *newy, double *newyi, double *newyii, int newnr)
Linear interpolation and integration.
int interpolate4pet(double *x, double *y, int nr, double *newx1, double *newx2, double *newy, double *newyi, double *newyii, int newnr)
Interpolate and integrate TAC to PET frames.
int pearson(double *x, double *y, int nr, double *k, double *kSD, double *b, double *bSD, double *r, double *ySD)