47 double GLOBAL_elapsed_time;
55 double W=(double)T*(((
double)R/2.0)*((double)R/2.0)+1.0/4.0);
57 for(t=-T/2; t<T/2; t++)
59 for(r=-R/2; r<R/2; r++)
63 x[2*((t+T/2)*R+(r+R/2))+0] = (
double)r/R;
64 x[2*((t+T/2)*R+(r+R/2))+1] = (
double)4*(t+T/4)/T*r/R;
68 x[2*((t+T/2)*R+(r+R/2))+0] = -(
double)4*(t-T/4)/T*r/R;
69 x[2*((t+T/2)*R+(r+R/2))+1] = (
double)r/R;
72 w[(t+T/2)*R+(r+R/2)] = 1.0/4.0/W;
74 w[(t+T/2)*R+(r+R/2)] = fabs((
double)r)/W;
82 static int linogram_dft(fftw_complex *f_hat,
int NN, fftw_complex *f,
int T,
int R,
int m)
105 nfft_init_guru(&my_nfft_plan, 2, N, M, n, m,
106 PRE_PHI_HUT| PRE_PSI| MALLOC_X | MALLOC_F_HAT| MALLOC_F| FFTW_INIT | FFT_OUT_OF_PLACE,
107 FFTW_MEASURE| FFTW_DESTROY_INPUT);
111 for(j=0;j<my_nfft_plan.
M_total;j++)
113 my_nfft_plan.
x[2*j+0] = x[2*j+0];
114 my_nfft_plan.
x[2*j+1] = x[2*j+1];
119 for(k=0;k<my_nfft_plan.
N_total;k++)
120 my_nfft_plan.
f_hat[k] = f_hat[k];
124 nfft_trafo_direct(&my_nfft_plan);
126 GLOBAL_elapsed_time = nfft_elapsed_seconds(t1,t0);
129 for(j=0;j<my_nfft_plan.
M_total;j++)
130 f[j] = my_nfft_plan.
f[j];
133 nfft_finalize(&my_nfft_plan);
141 static int linogram_fft(fftw_complex *f_hat,
int NN, fftw_complex *f,
int T,
int R,
int m)
152 N[0]=NN; n[0]=2*N[0];
153 N[1]=NN; n[1]=2*N[1];
164 nfft_init_guru(&my_nfft_plan, 2, N, M, n, m,
165 PRE_PHI_HUT| PRE_PSI| MALLOC_X | MALLOC_F_HAT| MALLOC_F| FFTW_INIT | FFT_OUT_OF_PLACE,
166 FFTW_MEASURE| FFTW_DESTROY_INPUT);
170 for(j=0;j<my_nfft_plan.
M_total;j++)
172 my_nfft_plan.
x[2*j+0] = x[2*j+0];
173 my_nfft_plan.
x[2*j+1] = x[2*j+1];
181 nfft_precompute_psi(&my_nfft_plan);
184 nfft_precompute_full_psi(&my_nfft_plan);
187 for(k=0;k<my_nfft_plan.
N_total;k++)
188 my_nfft_plan.
f_hat[k] = f_hat[k];
194 GLOBAL_elapsed_time = nfft_elapsed_seconds(t1,t0);
197 for(j=0;j<my_nfft_plan.
M_total;j++)
198 f[j] = my_nfft_plan.
f[j];
201 nfft_finalize(&my_nfft_plan);
222 N[0]=NN; n[0]=2*N[0];
223 N[1]=NN; n[1]=2*N[1];
234 nfft_init_guru(&my_nfft_plan, 2, N, M, n, m,
235 PRE_PHI_HUT| PRE_PSI| MALLOC_X | MALLOC_F_HAT| MALLOC_F| FFTW_INIT | FFT_OUT_OF_PLACE,
236 FFTW_MEASURE| FFTW_DESTROY_INPUT);
239 solver_init_advanced_complex(&my_infft_plan,(
nfft_mv_plan_complex*)(&my_nfft_plan), CGNR | PRECOMPUTE_WEIGHT );
243 for(j=0;j<my_nfft_plan.
M_total;j++)
245 my_nfft_plan.
x[2*j+0] = x[2*j+0];
246 my_nfft_plan.
x[2*j+1] = x[2*j+1];
247 my_infft_plan.
y[j] = f[j];
248 my_infft_plan.
w[j] = w[j];
256 nfft_precompute_psi(&my_nfft_plan);
259 nfft_precompute_full_psi(&my_nfft_plan);
262 if(my_infft_plan.
flags & PRECOMPUTE_DAMP)
263 for(j=0;j<my_nfft_plan.
N[0];j++)
264 for(k=0;k<my_nfft_plan.
N[1];k++)
266 my_infft_plan.
w_hat[j*my_nfft_plan.
N[1]+k]=
267 (sqrt(pow(j-my_nfft_plan.
N[0]/2,2)+pow(k-my_nfft_plan.
N[1]/2,2))>(my_nfft_plan.
N[0]/2)?0:1);
271 for(k=0;k<my_nfft_plan.
N_total;k++)
272 my_infft_plan.
f_hat_iter[k] = 0.0 + _Complex_I*0.0;
276 solver_before_loop_complex(&my_infft_plan);
281 for(k=0;k<my_nfft_plan.
N_total;k++)
286 for(l=1;l<=
max_i;l++)
293 GLOBAL_elapsed_time = nfft_elapsed_seconds(t1,t0);
296 for(k=0;k<my_nfft_plan.
N_total;k++)
301 nfft_finalize(&my_nfft_plan);
312 fftw_plan my_fftw_plan;
313 fftw_complex *f_hat,*f;
315 double t_fft, t_dft_linogram;
317 f_hat = (fftw_complex *)
nfft_malloc(
sizeof(fftw_complex)*N*N);
318 f = (fftw_complex *)
nfft_malloc(
sizeof(fftw_complex)*(T*R/4)*5);
320 my_fftw_plan = fftw_plan_dft_2d(N,N,f_hat,f,FFTW_BACKWARD,FFTW_MEASURE);
323 f_hat[k] = (((
double)rand())/RAND_MAX) + _Complex_I* (((double)rand())/RAND_MAX);
326 for(m=0;m<65536/N;m++)
328 fftw_execute(my_fftw_plan);
333 GLOBAL_elapsed_time = nfft_elapsed_seconds(t1,t0);
334 t_fft=N*GLOBAL_elapsed_time/65536;
339 t_dft_linogram=GLOBAL_elapsed_time;
342 for (m=3; m<=9; m+=3)
345 fprintf(fp,
"%d\t&\t&\t%1.1e&\t%1.1e&\t%d\t",N,t_fft,t_dft_linogram,m);
348 fprintf(fp,
"%d\t&\t&\t%1.1e&\t &\t%d\t",N,t_fft,m);
350 fprintf(fp,
" \t&\t&\t &\t &\t%d\t",m);
352 printf(
"N=%d\tt_fft=%1.1e\tt_dft_linogram=%1.1e\tm=%d\t",N,t_fft,t_dft_linogram,m);
355 fprintf(fp,
"%1.1e&\t",GLOBAL_elapsed_time);
356 printf(
"t_linogram=%1.1e\t",GLOBAL_elapsed_time);
359 fprintf(fp,
"%1.1e\\\\\\hline\n",GLOBAL_elapsed_time);
361 fprintf(fp,
"%1.1e\\\\\n",GLOBAL_elapsed_time);
362 printf(
"t_ilinogram=%1.1e\n",GLOBAL_elapsed_time);
374 int main(
int argc,
char **argv)
380 fftw_complex *f_hat, *f, *f_direct, *f_tilde;
384 double temp1, temp2, E_max=0.0;
391 printf(
"linogram_fft_test N T R \n");
393 printf(
"N linogram FFT of size NxN \n");
394 printf(
"T number of slopes \n");
395 printf(
"R number of offsets \n");
398 printf(
"\nHence, comparison FFTW, linogram FFT and inverse linogram FFT\n");
399 fp1=fopen(
"linogram_comparison_fft.dat",
"w");
402 for (logN=4; logN<=8; logN++)
403 comparison_fft(fp1,(1U<< logN), 3*(1U<< logN), 3*(1U<< (logN-1)));
412 printf(
"N=%d, linogram grid with T=%d, R=%d => ",N,T,R);
414 x = (
double *)
nfft_malloc(5*T*R/2*(
sizeof(
double)));
415 w = (
double *)
nfft_malloc(5*T*R/4*(
sizeof(
double)));
417 f_hat = (fftw_complex *)
nfft_malloc(
sizeof(fftw_complex)*N*N);
418 f = (fftw_complex *)
nfft_malloc(
sizeof(fftw_complex)*5*T*R/4);
419 f_direct = (fftw_complex *)
nfft_malloc(
sizeof(fftw_complex)*5*T*R/4);
420 f_tilde = (fftw_complex *)
nfft_malloc(
sizeof(fftw_complex)*N*N);
426 fp1=fopen(
"input_data_r.dat",
"r");
427 fp2=fopen(
"input_data_i.dat",
"r");
428 if ((fp1==NULL) || (fp2==NULL))
432 fscanf(fp1,
"%le ",&temp1);
433 fscanf(fp2,
"%le ",&temp2);
434 f_hat[k]=temp1+_Complex_I*temp2;
444 printf(
"\nTest of the linogram FFT: \n");
445 fp1=fopen(
"linogram_fft_error.dat",
"w+");
446 for (m=1; m<=12; m++)
452 E_max=X(error_l_infty_complex)(f_direct,f,M);
455 printf(
"m=%2d: E_max = %e\n",m,E_max);
456 fprintf(fp1,
"%e\n",E_max);
461 for (m=3; m<=9; m+=3)
463 printf(
"\nTest of the inverse linogram FFT for m=%d: \n",m);
464 sprintf(filename,
"linogram_ifft_error%d.dat",m);
465 fp1=fopen(filename,
"w+");
466 for (max_i=0; max_i<=20; max_i+=2)
472 E_max=X(error_l_infty_complex)(f_hat,f_tilde,N*N);
473 printf(
"%3d iterations: E_max = %e\n",max_i,E_max);
474 fprintf(fp1,
"%e\n",E_max);