vq_lib.c
上传用户:luckfish
上传日期:2021-12-16
资源大小:77k
文件大小:12k
源码类别:

语音压缩

开发平台:

Visual C++

  1. /*
  2. 2.4 kbps MELP Proposed Federal Standard speech coder
  3. version 1.2
  4. Copyright (c) 1996, Texas Instruments, Inc.  
  5. Texas Instruments has intellectual property rights on the MELP
  6. algorithm.  The Texas Instruments contact for licensing issues for
  7. commercial and non-government use is William Gordon, Director,
  8. Government Contracts, Texas Instruments Incorporated, Semiconductor
  9. Group (phone 972 480 7442).
  10. */
  11. /*
  12.   vq_lib.c: vector quantization subroutines 
  13. */
  14. #include <stdio.h>
  15. #include <math.h>
  16. #include "spbstd.h"
  17. #include "vq.h"
  18. #include "mat.h"
  19. #include "lpc.h"
  20. #define BIGVAL 1E20
  21. /* VQ_LSPW- compute LSP weighting vector-
  22.     Atal's method:
  23.         From Atal and Paliwal (ICASSP 1991)
  24.         (Note: Paliwal and Atal used w(k)^2(u(k)-u_hat(k))^2,
  25.          and we use w(k)(u(k)-u_hat(k))^2 so our weights are different
  26.          but the method (i.e. the weighted MSE) is the same.
  27.                 */
  28. float *vq_lspw(float *w,float *lsp,float *a,int p)
  29. {
  30.     int j;
  31.         for(j=0; j < p; j++)
  32.         {
  33.             w[j] = (float)pow((double)lpc_aejw(a,lsp[j]*M_PI,p),(double)-0.3);
  34.             if (j == 8)
  35.                 w[j] *= 0.64;
  36.             else if (j == 9)
  37.                 w[j] *= 0.16;
  38.         }
  39.     return(w);
  40. } /* VQ_LSPW */
  41. /*
  42.     VQ_MS4-
  43.         Tree search multi-stage VQ encoder 
  44.     Synopsis: vq_ms4(cb,u,u_est,levels,ma,stages,p,w,u_hat,a_indices)
  45.         Input:
  46.             cb- one dimensional linear codebook array (codebook is structured 
  47.                 as [stages][levels for each stage][p])
  48.             u- dimension p, the parameters to be encoded (u[0..p-1])
  49.             u_est- dimension p, the estimated parameters or mean (if NULL, assume
  50.                estimate is the all zero vector) (u_est[0..p-1])
  51.             levels- the number of levels at each stage (levels[0..stages-1])
  52.             ma- the tree search size (keep ma candidates from one stage to the
  53.                next)
  54.             stages- the number of stages of msvq
  55.             p- the predictor order
  56.             w- the weighting vector (w[0..p-1])
  57.             max_inner- the maximum number of times the swapping procedure
  58.                        in the inner loop can be executed
  59.         Output:
  60.             u_hat-   the reconstruction vector (if non null)
  61.             a_indices- the codebook indices (for each stage) a_indices[0..stages-1]
  62.         Parameters:
  63. */
  64. #define P_SWAP(x,y,type) do{type u__p;u__p = x;x = y;y = u__p;}while(0)
  65. float vq_ms4(float *cb, float *u, float *u_est, int *levels, int ma, int stages, int p, float *w, float *u_hat, int *a_indices,int max_inner)
  66. {
  67.     float tmp,*u_tmp,*uhatw,uhatw_sq;
  68.     float d_cj,d_opt;
  69.     float *d,*p_d,*n_d,*p_distortion,*cb_currentstage,*cbp;
  70.     float *errors,*p_errors,*n_errors,*p_e;
  71.     int i,j,m,s,c,p_max,inner_counter;
  72.     int *indices,*p_indices,*n_indices;
  73.     int *parents,*p_parents,*n_parents;
  74.     /* allocate memory for the current node and
  75.        parent node (thus, the factors of two everywhere)
  76.        The parents and current nodes are allocated contiguously */
  77.     MEM_ALLOC(MALLOC,indices,2*ma*stages,int);
  78.     MEM_ALLOC(MALLOC,errors,2*ma*p,float);
  79.     MEM_ALLOC(MALLOC,uhatw,p,float);
  80.     MEM_ALLOC(MALLOC,d,2*ma,float);
  81.     MEM_ALLOC(MALLOC,parents,2*ma,int);
  82.     /* initialize memory */
  83.     v_zap_int(indices,2*stages*ma);
  84.     v_zap_int(parents,2*ma);
  85.     /* initialize inner loop counter */
  86.     inner_counter = 0;
  87.     /* set up memory */
  88.     p_indices = &indices[0];
  89.     n_indices = &indices[ma*stages];
  90.     p_errors = &errors[0];
  91.     n_errors = &errors[ma*p];
  92.     p_d = &d[0];
  93.     n_d = &d[ma];
  94.     p_parents = &parents[0];
  95.     n_parents = &parents[ma];
  96.     /* u_tmp is the input vector (i.e. if u_est is non-null, it
  97.        is subtracted off) */
  98.     MEM_ALLOC(MALLOC,u_tmp,p+1,float);
  99.     (void)v_equ(u_tmp,u,p);
  100.     if (u_est)
  101.     {
  102.         (void)v_sub(u_tmp,u_est,p);
  103.     }
  104.     for(j=0,tmp=0.0; j < p; j++)
  105.     {
  106.         tmp += u_tmp[j]*u_tmp[j]*w[j];
  107.     }
  108.     /* set up inital error vectors (i.e. error vectors = u_tmp) */
  109.     for(c=0; c < ma; c++)
  110.     {
  111.         (void)v_equ(&n_errors[c*p],u_tmp,p);
  112.         n_d[c] = tmp;
  113.     }
  114.     /* no longer need memory so free it here */
  115.     MEM_FREE(FREE,u_tmp);
  116.     /* codebook pointer is set to point to first stage */
  117.     cbp = cb;
  118.     /* set m to 1 for the first stage
  119.        and loop over all stages */
  120.     for(m=1,s=0; s < stages; s++)
  121.     {
  122.         /* Save the pointer to the beginning of the
  123.            current stage.  Note: cbp is only incremented in
  124.            one spot, and it is incremented all the way through
  125.            all the stages. */
  126.         cb_currentstage = cbp;
  127.         /* set up pointers to the parent and current nodes */
  128.         P_SWAP(p_indices,n_indices,int*);
  129.         P_SWAP(p_parents,n_parents,int*);
  130.         P_SWAP(p_errors,n_errors,float*);
  131.         P_SWAP(p_d,n_d,float*);
  132.         /* p_max is the pointer to the maximum distortion
  133.            node over all candidates.  The so-called worst
  134.            of the best. */
  135.         p_max = 0;
  136.         /* set the distortions to a large value */
  137.         for(c=0; c < ma; c++)
  138.             n_d[c] = BIGVAL;
  139.         for(j=0; j < levels[s]; j++)
  140.         {
  141.             /* compute weighted codebook element, increment codebook pointer */
  142.             for(i=0,uhatw_sq=0.0; i < p; i++,cbp++)
  143.             {
  144.                 uhatw_sq += *cbp * (tmp = *cbp * w[i]);
  145.                 uhatw[i] = -2.0*tmp;
  146.             }
  147.             /* p_e points to the error vectors and p_distortion
  148.                points to the node distortions.  Note: the error
  149.                vectors are contiguous in memory, as are the distortions.
  150.                Thus, the error vector for the 2nd node comes immediately
  151.                after the error for the first node.  (This saves on
  152.                repeated initializations) */
  153.             p_e = p_errors;
  154.             p_distortion = p_d;
  155.             /* iterate over all parent nodes */
  156.             for(c=0; c < m; c++)
  157.             {
  158.                 d_cj = *p_distortion++ + uhatw_sq;
  159.                 for(i=0; i < p; i++)
  160.                     d_cj += *p_e++ * uhatw[i];
  161.                 /* determine if d is less than the maximum candidate distortion                   i.e., is the distortion found better than the so-called
  162.                    worst of the best */
  163.                 if (d_cj <= n_d[p_max])
  164.                 {
  165.                     /* replace the worst with the values just found */
  166.                     n_d[p_max] = d_cj;
  167.                     n_indices[p_max*stages+s] = j;
  168.                     n_parents[p_max] = c;
  169.                     /* want to limit the number of times the inner loop
  170.                        is entered (to reduce the *maximum* complexity) */
  171.                     if (inner_counter < max_inner)
  172.                     {
  173.                         inner_counter++;
  174.         if (inner_counter < max_inner)
  175. {
  176.                             p_max = 0;
  177.                             /* find the new maximum */
  178.             for(i=1; i < ma; i++)
  179.                             {
  180.                                 if (n_d[i] > n_d[p_max])
  181.                                     p_max = i;
  182.             }
  183.         }
  184. else /* inner_counter == max_inner */
  185.                         {
  186.                                /* The inner loop counter now exceeds the
  187.                                maximum, and the inner loop will now not
  188.                                be entered.  Instead of quitting the search
  189.                                or doing something drastic, we simply keep
  190.                                track of the best candidate (rather than the
  191.                                M best) by setting p_max to equal the index
  192.                                of the minimum distortion
  193.                                i.e. only keep one candidate around
  194.                                 the MINIMUM distortion */
  195.             for(i=1; i < ma; i++)
  196.                             {
  197.                                 if (n_d[i] < n_d[p_max])
  198.                                     p_max = i;
  199.             }
  200.         }
  201.     }
  202.                 }
  203.             } /* for c */
  204.         } /* for j */
  205.         /* compute the error vectors for each node */
  206.         for(c=0; c < ma; c++)
  207.         {
  208.             /* get the error from the parent node and subtract off
  209.                the codebook value */
  210.             (void)v_equ(&n_errors[c*p],&p_errors[n_parents[c]*p],p);
  211.             (void)v_sub(&n_errors[c*p],&cb_currentstage[n_indices[c*stages+s]*p],p);
  212.             /* get the indices that were used for the parent node */
  213.             (void)v_equ_int(&n_indices[c*stages],&p_indices[n_parents[c]*stages],s);
  214.         }
  215.         m = (m*levels[s] > ma) ? ma : m*levels[s];
  216.     } /* for s */
  217.     /* find the optimum candidate c */
  218.     for(i=1,c=0; i < ma; i++)
  219.     {
  220.         if (n_d[i] < n_d[c])
  221.     c = i;
  222.     }
  223.     d_opt = n_d[c];
  224.     
  225.     if (a_indices)
  226.     {
  227.         (void)v_equ_int(a_indices,&n_indices[c*stages],stages);
  228.     }
  229.     if (u_hat)
  230.     {
  231.         if (u_est)
  232.             (void)v_equ(u_hat,u_est,p);
  233.         else
  234.             (void)v_zap(u_hat,p);
  235.         cb_currentstage = cb;
  236.         for(s=0; s < stages; s++)
  237.         {
  238.             (void)v_add(u_hat,&cb_currentstage[n_indices[c*stages+s]*p],p);
  239.             cb_currentstage += levels[s]*p;
  240.         }
  241.     }
  242.     MEM_FREE(FREE,parents);
  243.     MEM_FREE(FREE,d);
  244.     MEM_FREE(FREE,uhatw);
  245.     MEM_FREE(FREE,errors);
  246.     MEM_FREE(FREE,indices);
  247.     return(d_opt);
  248. }
  249. /*
  250.     VQ_MSD2-
  251.         Tree search multi-stage VQ decoder
  252.     Synopsis: vq_msd(cb,u,u_est,a,indices,levels,stages,p,conversion)
  253.         Input:
  254.             cb- one dimensional linear codebook array (codebook is structured 
  255.                 as [stages][levels for each stage][p])
  256.             indices- the codebook indices (for each stage) indices[0..stages-1]
  257.             levels- the number of levels (for each stage) levels[0..stages-1]
  258.             u_est- dimension p, the estimated parameters or mean (if NULL, assume
  259.                estimate is the all zero vector) (u_est[0..p-1])
  260.             stages- the number of stages of msvq
  261.             p- the predictor order
  262.             conversion- the conversion constant (see lpc.h, lpc_conv.c)
  263.         Output:
  264.             u- dimension p, the decoded parameters (if NULL, use alternate
  265.                temporary storage) (u[0..p-1])
  266.             a- predictor parameters (a[0..p]), if NULL, don't compute
  267.         Returns:
  268.             pointer to reconstruction vector (u)
  269.         Parameters:
  270. */
  271. float *vq_msd2(float *cb, float *u, float *u_est, float *a, int *indices, int *levels, int stages, int p, int conversion)
  272. {
  273.     float *u_hat,*cb_currentstage;
  274.     int i;
  275.     /* allocate memory (if required) */
  276.     if (u==(float*)NULL)
  277.     {
  278.         MEM_ALLOC(MALLOC,u_hat,p,float);
  279.     }
  280.     else
  281.         u_hat = u;
  282.     /* add estimate on (if non-null), or clear vector */
  283.     if (u_est)
  284.     {
  285.         (void)v_equ(u_hat,u_est,p);
  286.     }
  287.     else
  288.     {
  289.         (void)v_zap(u_hat,p);
  290.     }
  291.     /* add the contribution of each stage */
  292.     cb_currentstage = cb;
  293.     for(i=0; i < stages; i++)
  294.     {
  295.         (void)v_add(u_hat,&cb_currentstage[indices[i]*p],p);
  296.         cb_currentstage += levels[i]*p;
  297.     }
  298.     return(u);
  299. }
  300. /* VQ_ENC -
  301.    encode vector with full VQ using unweighted Euclidean distance
  302.     Synopsis: vq_enc(cb, u, levels, p, u_hat, indices)
  303.         Input:
  304.             cb- one dimensional linear codebook array
  305.             u- dimension p, the parameters to be encoded (u[0..p-1])
  306.             levels- the number of levels
  307.             p- the predictor order
  308.         Output:
  309.             u_hat-   the reconstruction vector (if non null)
  310.             a_indices- the codebook indices (for each stage) a_indices[0..stages-1]
  311.         Parameters:
  312. */
  313. float vq_enc(float *cb, float *u, int levels, int p, float *u_hat, int *indices)
  314. {
  315.     int i,j,index;
  316.     float d,dmin;
  317.     float *p_cb;
  318.     /* Search codebook for minimum distance */
  319.     index = 0;
  320.     dmin = BIGVAL;
  321.     p_cb = cb;
  322.     for (i = 0; i < levels; i++) {
  323. d = 0.0;
  324. for (j = 0; j < p; j++) {
  325.     d += SQR(u[j] - *p_cb);
  326.     p_cb++;
  327. }
  328. if (d < dmin) {
  329.     dmin = d;
  330.     index = i;
  331. }
  332.     }
  333.     /* Update index and quantized value, and return minimum distance */
  334.     *indices = index;
  335.     v_equ(u_hat,&cb[p*index],p);
  336.     return(dmin);
  337. }
  338. /* VQ_FSW - 
  339.    compute the weights for Euclidean distance of Fourier harmonics  */
  340. void vq_fsw(float *w_fs, int num_harm, float pitch)
  341. {
  342.     int j;
  343.     float w0;
  344.     /* Calculate fundamental frequency */
  345.     w0 = TWOPI/pitch;    
  346.     for(j=0; j < num_harm; j++) {
  347. /* Bark-scale weighting */
  348. w_fs[j] = 117.0 / (25.0 + 75.0*
  349.    pow(1.0 + 1.4*SQR(w0*(j+1)/(0.25*PI)),0.69));
  350.     }
  351. }