[xiph-commits] r10730 - trunk/ghost/libghost

jm at svn.xiph.org jm at svn.xiph.org
Thu Jan 12 21:42:25 PST 2006


Author: jm
Date: 2006-01-12 21:42:22 -0800 (Thu, 12 Jan 2006)
New Revision: 10730

Modified:
   trunk/ghost/libghost/ghost.c
   trunk/ghost/libghost/sinusoids.c
   trunk/ghost/libghost/sinusoids.h
Log:
added variable number of sinusoids, finer frequency estimation, frequency
optimization and centered the analysis window (for now)


Modified: trunk/ghost/libghost/ghost.c
===================================================================
--- trunk/ghost/libghost/ghost.c	2006-01-12 09:57:02 UTC (rev 10729)
+++ trunk/ghost/libghost/ghost.c	2006-01-13 05:42:22 UTC (rev 10730)
@@ -32,7 +32,7 @@
 
 #define PCM_BUF_SIZE 2048
 
-#define SINUSOIDS 15
+#define SINUSOIDS 30
 
 GhostEncState *ghost_encoder_state_new(int sampling_rate)
 {
@@ -74,20 +74,15 @@
       st->pcm_buf[i] = st->pcm_buf[i+st->advance];
    for (i=0;i<st->advance;i++)
       st->current_pcm[i+st->overlap]=pcm[i];
-   find_pitch(st->current_pcm, &gain, &pitch, 100, 1024, st->length);
-   //fprintf (stderr,"%f %f\n", pitch, gain);
-   //pitch = 256;
-   w = 2*M_PI/pitch;
    {
       float wi[SINUSOIDS];
       float x[st->length];
       float y[st->length];
       float ai[SINUSOIDS], bi[SINUSOIDS];
+      float ci[SINUSOIDS], di[SINUSOIDS];
       float psd[PCM_BUF_SIZE];
+      int nb_sinusoids;
       
-      for (i=0;i<SINUSOIDS;i++)
-         wi[i] = w*(i+1);
-
       spx_fft_float(st->big_fft, st->pcm_buf, psd);
       for (i=1;i<(PCM_BUF_SIZE>>1);i++)
       {
@@ -95,15 +90,18 @@
       }
       psd[0] = 10*log10(1+psd[0]*psd[0]);
       psd[(PCM_BUF_SIZE>>1)-1] = 10*log10(1+psd[PCM_BUF_SIZE-1]*psd[PCM_BUF_SIZE-1]);
-      find_sinusoids(psd, wi, SINUSOIDS, (PCM_BUF_SIZE>>1)+1);
+      nb_sinusoids = SINUSOIDS;
+      find_sinusoids(psd, wi, &nb_sinusoids, (PCM_BUF_SIZE>>1)+1);
+      //printf ("%d\n", nb_sinusoids);
       /*for (i=0;i<SINUSOIDS;i++)
       {
          fprintf (stderr, "%f ", wi[i]);
       }
       fprintf (stderr, "\n");*/
       for (i=0;i<st->length;i++)
-         x[i] = st->window[i]*st->current_pcm[i];
-      extract_sinusoids(x, wi, st->window, ai, bi, y, SINUSOIDS, st->length);
+         x[i] = st->window[i]*st->current_pcm[i-896];
+      //extract_sinusoids(x, wi, st->window, ai, bi, y, SINUSOIDS, st->length);
+      extract_modulated_sinusoids(x, wi, st->window, ai, bi, ci, di, y, nb_sinusoids, st->length);
       /*for (i=0;i<st->length;i++)
       y[i] = x[i];*/
       short out[st->advance];

Modified: trunk/ghost/libghost/sinusoids.c
===================================================================
--- trunk/ghost/libghost/sinusoids.c	2006-01-12 09:57:02 UTC (rev 10729)
+++ trunk/ghost/libghost/sinusoids.c	2006-01-13 05:42:22 UTC (rev 10730)
@@ -28,7 +28,7 @@
 #define MIN(a,b) ((a)<(b) ? (a):(b))
 #define MAX(a,b) ((a)>(b) ? (a):(b))
 
-void find_sinusoids(float *psd, float *w, int N, int length)
+void find_sinusoids(float *psd, float *w, int *N, int length)
 {
    int i,j;
    float sinusoidism[length];
@@ -43,7 +43,7 @@
          float highlobe, lowlobe;
          highlobe = psd[i]-MIN(psd[i+1], psd[i+2]);
          lowlobe = psd[i]-MIN(psd[i-1], psd[i-2]);
-         sinusoidism[i] = psd[i] + .5*(highlobe + lowlobe - .5*MAX(lowlobe, highlobe));
+         sinusoidism[i] = 1*psd[i] + 1*(highlobe + lowlobe - .5*MAX(lowlobe, highlobe));
       } else {
          sinusoidism[i] = -1;
       }
@@ -53,7 +53,7 @@
       fprintf (stderr, "%f ", sinusoidism[i]);
    }
    fprintf (stderr, "\n");*/
-   for (i=0;i<N;i++)
+   for (i=0;i<*N;i++)
    {
       tmp_max = -2;
       for (j=0;j<length;j++)
@@ -64,9 +64,32 @@
             tmp_id = j;
          }
       }
+      //printf ("%f ", sinusoidism[tmp_id]);
+      if (sinusoidism[tmp_id]<50)
+      {
+         *N=i;
+         break;
+      }
       sinusoidism[tmp_id] = -3;
-      w[i] = M_PI*tmp_id/(length-1);
+      //w[i] = M_PI*tmp_id/(length-1);
+      float corr;
+      float side;
+      if (psd[tmp_id+1]> psd[tmp_id-1])
+         side=psd[tmp_id]-psd[tmp_id+1];
+      else
+         side=psd[tmp_id]-psd[tmp_id-1];
+      if (side>6)
+         corr = 0;
+      else if (side<0)
+         corr = 0;
+      else
+         corr = .5-.5*(side/6);
+      if (psd[tmp_id+1] < psd[tmp_id-1])
+         corr =- corr;
+      //printf ("%f\n",corr);
+      w[i] = M_PI*(tmp_id+corr)/(length-1);
    }
+   //printf ("\n");
 }
 
 void extract_sinusoids(float *x, float *w, float *window, float *ai, float *bi, float *y, int N, int len)
@@ -112,7 +135,89 @@
          }
          ai[i] += tmp1;
          bi[i] += tmp2;
+         if (iter==4)
+         {
+            printf ("%f %f ", w[i], (float)sqrt(ai[i]*ai[i] + bi[i]*bi[i]));
+         }
       }
    }
+   printf ("\n");
 }
 
+void extract_modulated_sinusoids(float *x, float *w, float *window, float *ai, float *bi, float *ci, float *di, float *y, int N, int len)
+{
+   float cos_table[N][len];
+   float sin_table[N][len];
+   float tcos_table[N][len];
+   float tsin_table[N][len];
+   float cosE[N], sinE[N];
+   float costE[N], sintE[N];
+   int i,j, iter;
+   for (i=0;i<N;i++)
+   {
+      float tmp1=0, tmp2=0;
+      float tmp3=0, tmp4=0;
+      for (j=0;j<len;j++)
+      {
+         cos_table[i][j] = cos(w[i]*j)*window[j];
+         sin_table[i][j] = sin(w[i]*j)*window[j];
+         tcos_table[i][j] = ((3./len)*(j-(len>>1)))*cos_table[i][j];
+         tsin_table[i][j] = ((3./len)*(j-(len>>1)))*sin_table[i][j];
+         tmp1 += cos_table[i][j]*cos_table[i][j];
+         tmp2 += sin_table[i][j]*sin_table[i][j];
+         tmp3 += tcos_table[i][j]*tcos_table[i][j];
+         tmp4 += tsin_table[i][j]*tsin_table[i][j];
+      }
+      cosE[i] = tmp1;
+      sinE[i] = tmp2;
+      costE[i] = tmp3;
+      sintE[i] = tmp4;
+   }
+   for (j=0;j<len;j++)
+      y[j] = 0;
+   for (i=0;i<N;i++)
+      ai[i] = bi[i] = ci[i] = di[i] = 0;
+   int tata=0;
+   for (iter=0;iter<5;iter++)
+   {
+      for (i=0;i<N;i++)
+      {
+         float tmp1=0, tmp2=0;
+         float tmp3=0, tmp4=0;
+         for (j=0;j<len;j++)
+         {
+            tmp1 += (x[j]-y[j])*cos_table[i][j];
+            tmp2 += (x[j]-y[j])*sin_table[i][j];
+            tmp3 += (x[j]-y[j])*tcos_table[i][j];
+            tmp4 += (x[j]-y[j])*tsin_table[i][j];
+         }
+         tmp1 /= cosE[i];
+         //Just in case it's a DC! Must fix that anyway
+         tmp2 /= (.0001+sinE[i]);
+         tmp3 /= (.0001+costE[i]);
+         tmp4 /= (.0001+sintE[i]);
+         //tmp3=tmp4 = 0;
+         for (j=0;j<len;j++)
+         {
+            y[j] += tmp1*cos_table[i][j] + tmp2*sin_table[i][j] + tmp3*tcos_table[i][j] + tmp4*tsin_table[i][j];
+         }
+         ai[i] += tmp1;
+         bi[i] += tmp2;
+         ci[i] += tmp3;
+         di[i] += tmp4;
+         if (iter==4)
+         {
+            if (w[i] > .49 && w[i] < .53 && !tata)
+            {
+               //printf ("%f %f %f %f %f\n", w[i], ai[i], bi[i], ci[i], di[i]);
+               tata = 1;
+            }
+            //printf ("%f %f ", w[i], (float)sqrt(ai[i]*ai[i] + bi[i]*bi[i]));
+         }
+      }
+   }
+   //if(!tata)
+      //printf ("0 0 0 0 0\n");
+
+   //printf ("\n");
+}

Modified: trunk/ghost/libghost/sinusoids.h
===================================================================
--- trunk/ghost/libghost/sinusoids.h	2006-01-12 09:57:02 UTC (rev 10729)
+++ trunk/ghost/libghost/sinusoids.h	2006-01-13 05:42:22 UTC (rev 10730)
@@ -23,8 +23,10 @@
 #ifndef _SINUSOIDS_H
 #define _SINUSOIDS_H
 
-void find_sinusoids(float *psd, float *w, int N, int length);
+void find_sinusoids(float *psd, float *w, int *N, int length);
 
 void extract_sinusoids(float *x, float *w, float *window, float *ai, float *bi, float *y, int N, int len);
 
+void extract_modulated_sinusoids(float *x, float *w, float *window, float *ai, float *bi, float *ci, float *di, float *y, int N, int len);
+
 #endif



More information about the commits mailing list