summaryrefslogtreecommitdiff
path: root/mbest.c
diff options
context:
space:
mode:
authorerdgeist <erdgeist@erdgeist.org>2025-08-15 12:42:40 +0200
committererdgeist <erdgeist@erdgeist.org>2025-08-15 12:42:40 +0200
commit30325d24d107dbf133da39f7c96d1510fd1c9449 (patch)
tree932baa5b2a4475821f16dccf9e3e05011daa6d92 /mbest.c
parent9022d768021bbe15c7815cc6f8b64218b46f0e10 (diff)
Bump to codec2 version 1.2.0erdgeist-bump-to-1.2.0
Diffstat (limited to 'mbest.c')
-rw-r--r--mbest.c194
1 files changed, 106 insertions, 88 deletions
diff --git a/mbest.c b/mbest.c
index 6216b77..9c1a6c5 100644
--- a/mbest.c
+++ b/mbest.c
@@ -27,42 +27,48 @@
27 27
28*/ 28*/
29 29
30#include "mbest.h"
31
30#include <assert.h> 32#include <assert.h>
31#include <math.h> 33#include <math.h>
32#include <stdio.h> 34#include <stdio.h>
33#include <stdlib.h> 35#include <stdlib.h>
34#include <string.h> 36#include <string.h>
35 37
36#include "mbest.h"
37
38struct MBEST *mbest_create(int entries) { 38struct MBEST *mbest_create(int entries) {
39 int i,j; 39 int i, j;
40 struct MBEST *mbest; 40 struct MBEST *mbest;
41 41
42 assert(entries > 0); 42 assert(entries > 0);
43 mbest = (struct MBEST *)malloc(sizeof(struct MBEST)); 43 mbest = (struct MBEST *)malloc(sizeof(struct MBEST));
44 assert(mbest != NULL); 44 assert(mbest != NULL);
45 45
46 mbest->entries = entries; 46 mbest->entries = entries;
47 mbest->list = (struct MBEST_LIST *)malloc(entries*sizeof(struct MBEST_LIST)); 47 mbest->list =
48 assert(mbest->list != NULL); 48 (struct MBEST_LIST *)malloc(entries * sizeof(struct MBEST_LIST));
49 assert(mbest->list != NULL);
49 50
50 for(i=0; i<mbest->entries; i++) { 51 for (i = 0; i < mbest->entries; i++) {
51 for(j=0; j<MBEST_STAGES; j++) 52 for (j = 0; j < MBEST_STAGES; j++) mbest->list[i].index[j] = 0;
52 mbest->list[i].index[j] = 0; 53 mbest->list[i].error = 1E32;
53 mbest->list[i].error = 1E32; 54 }
54 }
55 55
56 return mbest; 56 return mbest;
57} 57}
58 58
59
60void mbest_destroy(struct MBEST *mbest) { 59void mbest_destroy(struct MBEST *mbest) {
61 assert(mbest != NULL); 60 assert(mbest != NULL);
62 free(mbest->list); 61 free(mbest->list);
63 free(mbest); 62 free(mbest);
64} 63}
65 64
65/* apply weighting to VQ for efficient VQ search */
66
67void mbest_precompute_weight(float cb[], float w[], int k, int m) {
68 for (int j = 0; j < m; j++) {
69 for (int i = 0; i < k; i++) cb[k * j + i] *= w[i];
70 }
71}
66 72
67/*---------------------------------------------------------------------------*\ 73/*---------------------------------------------------------------------------*\
68 74
@@ -75,36 +81,31 @@ void mbest_destroy(struct MBEST *mbest) {
75\*---------------------------------------------------------------------------*/ 81\*---------------------------------------------------------------------------*/
76 82
77void mbest_insert(struct MBEST *mbest, int index[], float error) { 83void mbest_insert(struct MBEST *mbest, int index[], float error) {
78 int i, j, found; 84 int i, found;
79 struct MBEST_LIST *list = mbest->list; 85 struct MBEST_LIST *list = mbest->list;
80 int entries = mbest->entries; 86 int entries = mbest->entries;
81 87
82 found = 0; 88 found = 0;
83 for(i=0; i<entries && !found; i++) 89 for (i = 0; i < entries && !found; i++)
84 if (error < list[i].error) { 90 if (error < list[i].error) {
85 found = 1; 91 found = 1;
86 for(j=entries-1; j>i; j--) 92 memmove(&list[i + 1], &list[i],
87 list[j] = list[j-1]; 93 sizeof(struct MBEST_LIST) * (entries - i - 1));
88 for(j=0; j<MBEST_STAGES; j++) 94 memcpy(&list[i].index[0], &index[0], sizeof(int) * MBEST_STAGES);
89 list[i].index[j] = index[j]; 95 list[i].error = error;
90 list[i].error = error; 96 }
91 }
92} 97}
93 98
99void mbest_print(char title[], struct MBEST *mbest) {
100 int i, j;
94 101
95#ifdef MBEST_PRINT_OUT 102 fprintf(stderr, "%s\n", title);
96static void mbest_print(char title[], struct MBEST *mbest) { 103 for (i = 0; i < mbest->entries; i++) {
97 int i,j; 104 for (j = 0; j < MBEST_STAGES; j++)
98 105 fprintf(stderr, " %4d ", mbest->list[i].index[j]);
99 fprintf(stderr, "%s\n", title); 106 fprintf(stderr, " %f\n", (double)mbest->list[i].error);
100 for(i=0; i<mbest->entries; i++) { 107 }
101 for(j=0; j<MBEST_STAGES; j++)
102 fprintf(stderr, " %4d ", mbest->list[i].index[j]);
103 fprintf(stderr, " %f\n", mbest->list[i].error);
104 }
105} 108}
106#endif
107
108 109
109/*---------------------------------------------------------------------------*\ 110/*---------------------------------------------------------------------------*\
110 111
@@ -115,31 +116,48 @@ static void mbest_print(char title[], struct MBEST *mbest) {
115 116
116\*---------------------------------------------------------------------------*/ 117\*---------------------------------------------------------------------------*/
117 118
118void mbest_search( 119void mbest_search(const float *cb, /* VQ codebook to search */
119 const float *cb, /* VQ codebook to search */ 120 float vec[], /* target vector */
120 float vec[], /* target vector */ 121 int k, /* dimension of vector */
121 float w[], /* weighting vector */ 122 int m, /* number on entries in codebook */
122 int k, /* dimension of vector */ 123 struct MBEST *mbest, /* list of closest matches */
123 int m, /* number on entries in codebook */ 124 int index[] /* indexes that lead us here */
124 struct MBEST *mbest, /* list of closest matches */ 125) {
125 int index[] /* indexes that lead us here */ 126 int j;
126) 127
127{ 128 /* note weighting can be applied externally by modifying cb[] and vec:
128 float e; 129
129 int i,j; 130 float e = 0.0;
130 float diff; 131 for(i=0; i<k; i++)
131 132 e += pow(w[i]*(cb[j*k+i] - vec[i]),2.0)
132 for(j=0; j<m; j++) { 133
133 e = 0.0; 134 |
134 for(i=0; i<k; i++) { 135 \|/
135 diff = cb[j*k+i]-vec[i]; 136
136 e += diff*w[i]*diff*w[i]; 137 for(i=0; i<k; i++)
137 } 138 e += pow(w[i]*cb[j*k+i] - w[i]*vec[i]),2.0)
138 index[0] = j; 139
139 mbest_insert(mbest, index, e); 140 |
140 } 141 \|/
141}
142 142
143 for(i=0; i<k; i++)
144 e += pow(cb1[j*k+i] - vec1[i]),2.0)
145
146 where cb1[j*k+i] = w[i]*cb[j*k+i], and vec1[i] = w[i]*vec[i]
147 */
148
149 for (j = 0; j < m; j++) {
150 float e = 0.0;
151 for (int i = 0; i < k; i++) {
152 float diff = *cb++ - vec[i];
153 e += diff * diff;
154 }
155
156 index[0] = j;
157 if (e < mbest->list[mbest->entries - 1].error)
158 mbest_insert(mbest, index, e);
159 }
160}
143 161
144/*---------------------------------------------------------------------------*\ 162/*---------------------------------------------------------------------------*\
145 163
@@ -148,26 +166,26 @@ void mbest_search(
148 Searches vec[] to a codebbook of vectors, and maintains a list of the mbest 166 Searches vec[] to a codebbook of vectors, and maintains a list of the mbest
149 closest matches. Only searches the first NewAmp2_K Vectors 167 closest matches. Only searches the first NewAmp2_K Vectors
150 168
151 \*---------------------------------------------------------------------------*/ 169\*---------------------------------------------------------------------------*/
152 170
153void mbest_search450(const float *cb, float vec[], float w[], int k,int shorterK, int m, struct MBEST *mbest, int index[]) 171void mbest_search450(const float *cb, float vec[], float w[], int k,
172 int shorterK, int m, struct MBEST *mbest, int index[])
154 173
155{ 174{
156 float e; 175 float e;
157 int i,j; 176 int i, j;
158 float diff; 177 float diff;
159 178
160 for(j=0; j<m; j++) { 179 for (j = 0; j < m; j++) {
161 e = 0.0; 180 e = 0.0;
162 for(i=0; i<k; i++) { 181 for (i = 0; i < k; i++) {
163 //Only search first NEWAMP2_K Vectors 182 // Only search first NEWAMP2_K Vectors
164 if(i<shorterK){ 183 if (i < shorterK) {
165 diff = cb[j*k+i]-vec[i]; 184 diff = cb[j * k + i] - vec[i];
166 e += diff*w[i] * diff*w[i]; 185 e += diff * w[i] * diff * w[i];
167 } 186 }
168 }
169 index[0] = j;
170 mbest_insert(mbest, index, e);
171 } 187 }
188 index[0] = j;
189 mbest_insert(mbest, index, e);
190 }
172} 191}
173