8 static void make_sintbl(int n, double *sintbl)
11 double c, s, dc, ds, t;
13 n2 = n / 2; n4 = n / 4; n8 = n / 8;
16 dc = 2 * t * t; ds = sqrt(dc * (2 - dc));
17 t = 2 * dc; c = 1.0; s = 0.0;
20 for (i = 1; i < n8; i++) {
23 sintbl[i] = s; sintbl[n4 - i] = c;
25 if (n8 != 0) sintbl[n8] = sqrt(0.5);
29 for (i = 1; i < n4; i++)
30 sintbl[i] = sin( (double)i / n * ( 2 * PI ) );
32 for (i = 0; i < n4; i++)
33 sintbl[n2 - i] = sintbl[i];
34 for (i = 0; i < n2 + n4; i++)
35 sintbl[i + n2] = - sintbl[i];
39 fp = fopen( "sintbl", "w" );
41 fprintf( fp, "%d %f\n", i, sintbl[i] );
43 fp = fopen( "plot", "w" );
44 fprintf( fp, "plot 'sintbl'\npause 5" );
46 system( "gnuplot plot" );
53 static void make_bitrev(int n, int *bitrev)
57 n2 = n / 2; i = j = 0;
62 while (k <= j) { j -= k; k /= 2; }
69 int fft(int n, Fukusosuu *x)
71 static int last_n = 0; /* {\tt n} */
72 static int *bitrev = NULL; /* */
73 static float *sintbl = NULL; /* */
74 int i, j, k, ik, h, d, k2, n4, inverse;
75 float t, s, c, dR, dI;
79 n = -n; inverse = 1; /* */
82 if (n != last_n || n == 0) {
84 if (sintbl != NULL) free((void *)sintbl);
85 if (bitrev != NULL) free((void *)bitrev);
86 if (n == 0) return 0; /* */
87 sintbl = malloc((n + n4) * sizeof(float));
88 bitrev = malloc(n * sizeof(int));
89 if (sintbl == NULL || bitrev == NULL) {
90 fprintf(stderr, "\n"); return 1;
92 make_sintbl(n, sintbl);
93 make_bitrev(n, bitrev);
95 for (i = 0; i < n; i++) { /* */
98 t = x[i].R; x[i].R = x[j].R; x[j].R = t;
99 t = x[i].I; x[i].I = x[j].I; x[j].I = t;
102 for (k = 1; k < n; k = k2) { /* */
103 h = 0; k2 = k + k; d = n / k2;
104 for (j = 0; j < k; j++) {
106 if (inverse) s = - sintbl[h];
108 for (i = j; i < n; i += k2) {
110 dR = s * x[ik].I + c * x[ik].R;
111 dI = c * x[ik].I - s * x[ik].R;
112 x[ik].R = x[i].R - dR; x[i].R += dR;
113 x[ik].I = x[i].I - dI; x[i].I += dI;
118 if (! inverse) /* n */
119 for (i = 0; i < n; i++) { x[i].R /= (double)n; x[i].I /= (double)n; }
123 int fft(int n, Fukusosuu *x, int disp)
125 static int last_n = 0; /* {\tt n} */
126 static int *bitrev = NULL; /* */
127 static double *sintbl = NULL; /* */
128 int i, j, k, ik, h, d, k2, n4, inverse;
129 double t, s, c, dR, dI;
134 n = -n; inverse = 1; /* */
140 fp = fopen( "inputOfFft", "w" );
142 fprintf( fp, "%f %f\n", x[i].R, x[i].I );
144 system( "vi inputOfFft < /dev/tty > /dev/tty " );
148 if (n != last_n || n == 0) {
150 if (sintbl != NULL) free((void *)sintbl);
151 if (bitrev != NULL) free((void *)bitrev);
152 if (n == 0) return 0; /* */
153 sintbl = (double *)malloc((n + n4) * sizeof(double));
154 bitrev = (int *)malloc(n * sizeof(int));
155 if (sintbl == NULL || bitrev == NULL) {
156 fprintf(stderr, "\n"); return 1;
158 make_sintbl(n, sintbl);
159 make_bitrev(n, bitrev);
161 for (i = 0; i < n; i++) { /* */
164 t = x[i].R; x[i].R = x[j].R; x[j].R = t;
165 t = x[i].I; x[i].I = x[j].I; x[j].I = t;
169 if( disp ) gfp = fopen( "x", "w" );
170 if( disp ) for( i=0; i<n; i++ )
171 fprintf( gfp, "i=%d x=%f+i%f\n", i, x[i].R, x[i].I );
173 for (k = 1; k < n; k = k2) { /* */
174 h = 0; k2 = k + k; d = n / k2;
175 for (j = 0; j < k; j++) {
177 if (inverse) s = - sintbl[h];
179 for (i = j; i < n; i += k2) {
181 tmp1 = c * x[ik].I; tmp2 = s * x[ik].R;
183 tmp1 = s * x[ik].I; tmp2 = c * x[ik].R;
186 if( disp ) fprintf( gfp, "B k,j,i,ik=%d,%d,%d,s=%f,c=%f,x[%d]=%f+-i%f, dR=%f ? %f+%f \n", k, j, i, s, c, i, x[i].R, x[i].I, dR, s * x[ik].I, c * x[ik].R );
187 if( disp ) fprintf( gfp, "B k,j,i,ik=%d,%d,%d,s=%f,c=%f,x[%d]=%f+-i%f, dR=%f\n", k, j, i, s, c, ik, x[ik].R, x[ik].I, dR );
189 x[ik].R = x[i].R - dR; x[i].R += dR;
190 x[ik].I = x[i].I - dI; x[i].I += dI;
192 if( disp ) fprintf( gfp, "A k,j,i=%d,%d,%d,s=%f,c=%f,x[%d]=%f+-i%f, dR=%f\n", k, j, i, s, c, ik, x[ik].R, x[ik].I, dR );
198 if( disp ) fprintf( gfp, "ik=%d x=%f+i%f\n", ik, x[ik].R, x[ik].I );
201 if (! inverse) /* n */
202 for (i = 0; i < n; i++) { x[i].R /= (double)n; x[i].I /= (double)n; }
204 if( disp ) fclose( gfp );
205 if( disp ) system( "vi x < /dev/tty > /dev/tty " );
211 fp = fopen( "outputOfFft", "w" );
213 fprintf( fp, "%f %f\n", x[i].R, x[i].I );
215 system( "vi outputOfFft < /dev/tty > /dev/tty " );