1 /********************************************************************
3 * THIS FILE IS PART OF THE OggVorbis SOFTWARE CODEC SOURCE CODE. *
4 * USE, DISTRIBUTION AND REPRODUCTION OF THIS LIBRARY SOURCE IS *
5 * GOVERNED BY A BSD-STYLE SOURCE LICENSE INCLUDED WITH THIS SOURCE *
6 * IN 'COPYING'. PLEASE READ THESE TERMS BEFORE DISTRIBUTING. *
8 * THE OggVorbis SOURCE CODE IS (C) COPYRIGHT 1994-2001 *
9 * by the Xiph.Org Foundation http://www.xiph.org/ *
11 ********************************************************************
13 function: function calls to collect codebook metrics
16 ********************************************************************/
24 /* collect the following metrics:
26 mean and mean squared amplitude
27 mean and mean squared error
28 mean and mean squared error (per sample) by entry
29 worst case fit by entry
34 (average bits per sample)*/
39 float meanamplitude_acc=0.f;
40 float meanamplitudesq_acc=0.f;
41 float meanerror_acc=0.f;
42 float meanerrorsq_acc=0.f;
44 float **histogram=NULL;
45 float **histogram_error=NULL;
46 float **histogram_errorsq=NULL;
47 float **histogram_hi=NULL;
48 float **histogram_lo=NULL;
52 static float *_now(codebook *c, int i){
53 return c->valuelist+i*c->c->dim;
58 void process_preprocess(codebook **bs,char *basename){
60 while(bs[books])books++;
63 histogram=_ogg_calloc(books,sizeof(float *));
64 histogram_error=_ogg_calloc(books,sizeof(float *));
65 histogram_errorsq=_ogg_calloc(books,sizeof(float *));
66 histogram_hi=_ogg_calloc(books,sizeof(float *));
67 histogram_lo=_ogg_calloc(books,sizeof(float *));
69 fprintf(stderr,"Specify at least one codebook\n");
75 histogram[i]=_ogg_calloc(b->entries,sizeof(float));
76 histogram_error[i]=_ogg_calloc(b->entries*b->dim,sizeof(float));
77 histogram_errorsq[i]=_ogg_calloc(b->entries*b->dim,sizeof(float));
78 histogram_hi[i]=_ogg_calloc(b->entries*b->dim,sizeof(float));
79 histogram_lo[i]=_ogg_calloc(b->entries*b->dim,sizeof(float));
83 static float _dist(int el,float *a, float *b){
87 float val=(a[i]-b[i]);
93 void cell_spacing(codebook *c){
95 float min=-1.f,max=-1.f,mean=0.f,meansq=0.f;
98 /* minimum, maximum, mean, ms cell spacing */
99 for(j=0;j<c->c->entries;j++){
100 if(c->c->lengthlist[j]>0){
102 for(k=0;k<c->c->entries;k++){
103 if(c->c->lengthlist[k]>0){
104 float this=_dist(c->c->dim,_now(c,j),_now(c,k));
106 (localmin==-1 || this<localmin))
111 if(min==-1 || localmin<min)min=localmin;
112 if(max==-1 || localmin>max)max=localmin;
113 mean+=sqrt(localmin);
119 fprintf(stderr,"\tminimum cell spacing (closest side): %g\n",sqrt(min));
120 fprintf(stderr,"\tmaximum cell spacing (closest side): %g\n",sqrt(max));
121 fprintf(stderr,"\tmean closest side spacing: %g\n",mean/total);
122 fprintf(stderr,"\tmean sq closest side spacing: %g\n",sqrt(meansq/total));
125 void process_postprocess(codebook **bs,char *basename){
127 char *buffer=alloca(strlen(basename)+80);
129 fprintf(stderr,"Done. Processed %ld data points:\n\n",
132 fprintf(stderr,"Global statistics:******************\n\n");
134 fprintf(stderr,"\ttotal samples: %ld\n",(long)count);
135 fprintf(stderr,"\ttotal bits required to code: %ld\n",(long)bits);
136 fprintf(stderr,"\taverage bits per sample: %g\n\n",bits/count);
138 fprintf(stderr,"\tmean sample amplitude: %g\n",
139 meanamplitude_acc/count);
140 fprintf(stderr,"\tmean squared sample amplitude: %g\n\n",
141 sqrt(meanamplitudesq_acc/count));
143 fprintf(stderr,"\tmean code error: %g\n",
144 meanerror_acc/count);
145 fprintf(stderr,"\tmean squared code error: %g\n\n",
146 sqrt(meanerrorsq_acc/count));
148 for(book=0;book<books;book++){
150 codebook *b=bs[book];
154 fprintf(stderr,"Book %d statistics:------------------\n",book);
158 sprintf(buffer,"%s-%d-mse.m",basename,book);
159 out=fopen(buffer,"w");
161 fprintf(stderr,"Could not open file %s for writing\n",buffer);
167 fprintf(out,"%d, %g, %g\n",
168 i*dim+k,(b->valuelist+i*dim)[k],
169 sqrt((histogram_errorsq[book]+i*dim)[k]/histogram[book][i]));
174 sprintf(buffer,"%s-%d-me.m",basename,book);
175 out=fopen(buffer,"w");
177 fprintf(stderr,"Could not open file %s for writing\n",buffer);
183 fprintf(out,"%d, %g, %g\n",
184 i*dim+k,(b->valuelist+i*dim)[k],
185 (histogram_error[book]+i*dim)[k]/histogram[book][i]);
190 sprintf(buffer,"%s-%d-worst.m",basename,book);
191 out=fopen(buffer,"w");
193 fprintf(stderr,"Could not open file %s for writing\n",buffer);
199 fprintf(out,"%d, %g, %g, %g\n",
200 i*dim+k,(b->valuelist+i*dim)[k],
201 (b->valuelist+i*dim)[k]+(histogram_lo[book]+i*dim)[k],
202 (b->valuelist+i*dim)[k]+(histogram_hi[book]+i*dim)[k]);
209 float process_one(codebook *b,int book,float *a,int dim,int step,int addmul,
217 amplitude=a[j*step]-(b->c->q_sequencep?last:0);
218 meanamplitude_acc+=fabs(amplitude);
219 meanamplitudesq_acc+=amplitude*amplitude;
225 if(b->c->q_sequencep){
234 entry=vorbis_book_besterror(b,a,step,addmul);
237 fprintf(stderr,"Internal error: _best returned -1.\n");
241 histogram[book][entry]++;
242 bits+=vorbis_book_codelen(b,entry);
245 float error=a[j*step];
248 meanerror_acc+=fabs(error);
249 meanerrorsq_acc+=error*error;
251 histogram_errorsq[book][entry*dim+j]+=error*error;
252 histogram_error[book][entry*dim+j]+=fabs(error);
253 if(histogram[book][entry]==0 || histogram_hi[book][entry*dim+j]<error)
254 histogram_hi[book][entry*dim+j]=error;
255 if(histogram[book][entry]==0 || histogram_lo[book][entry*dim+j]>error)
256 histogram_lo[book][entry*dim+j]=error;
262 void process_vector(codebook **bs,int *addmul,int inter,float *a,int n){
266 for(bi=0;bi<books;bi++){
273 base=process_one(b,bi,a+i,dim,n/dim,addmul[bi],base);
275 for(i=0;i<=n-dim;i+=dim)
276 base=process_one(b,bi,a+i,dim,1,addmul[bi],base);
280 if((long)(count)%100)spinnit("working.... samples: ",count);
283 void process_usage(void){
285 "usage: vqmetrics [-i] +|*<codebook>.vqh [ +|*<codebook.vqh> ]... \n"
286 " datafile.vqd [datafile.vqd]...\n\n"
287 " data can be taken on stdin. -i indicates interleaved coding.\n"
288 " Output goes to output files:\n"
289 " basename-me.m: gnuplot: mean error by entry value\n"
290 " basename-mse.m: gnuplot: mean square error by entry value\n"
291 " basename-worst.m: gnuplot: worst error by entry value\n"
292 " basename-distance.m: gnuplot file showing distance probability\n"