comparison audioDB.cpp @ 155:b251c49379d1 powertable

Implement power thresholding for radius search. (Also clean up a bit more after oneself, deleting power vectors if appropriate)
author mas01cr
date Thu, 01 Nov 2007 14:37:08 +0000
parents 97f704a32bf2
children d241a22593bb
comparison
equal deleted inserted replaced
154:97f704a32bf2 155:b251c49379d1
1692 // Copy the L2 norm values to core to avoid disk random access later on 1692 // Copy the L2 norm values to core to avoid disk random access later on
1693 memcpy(sNorm, l2normTable, dbVectors*sizeof(double)); 1693 memcpy(sNorm, l2normTable, dbVectors*sizeof(double));
1694 double* qnPtr = qNorm; 1694 double* qnPtr = qNorm;
1695 double* snPtr = sNorm; 1695 double* snPtr = sNorm;
1696 1696
1697 double *sPower = 0, *qPower; 1697 double *sPower = 0, *qPower = 0;
1698 double *spPtr = 0, *qpPtr = 0; 1698 double *spPtr = 0, *qpPtr = 0;
1699 1699
1700 if (usingPower) { 1700 if (usingPower) {
1701 if (!(dbH->flags & O2_FLAG_POWER)) { 1701 if (!(dbH->flags & O2_FLAG_POWER)) {
1702 error("database not power-enabled", dbName); 1702 error("database not power-enabled", dbName);
2123 delete[] queryCopy; 2123 delete[] queryCopy;
2124 if(qNorm) 2124 if(qNorm)
2125 delete[] qNorm; 2125 delete[] qNorm;
2126 if(sNorm) 2126 if(sNorm)
2127 delete[] sNorm; 2127 delete[] sNorm;
2128 if(qPower)
2129 delete[] qPower;
2130 if(sPower)
2131 delete[] sPower;
2128 if(D) 2132 if(D)
2129 delete[] D; 2133 delete[] D;
2130 if(DD) 2134 if(DD)
2131 delete[] DD; 2135 delete[] DD;
2132 if(timesdata) 2136 if(timesdata)
2147 // we use stdout in this stub version 2151 // we use stdout in this stub version
2148 unsigned numVectors = (statbuf.st_size-sizeof(int))/(sizeof(double)*dbH->dim); 2152 unsigned numVectors = (statbuf.st_size-sizeof(int))/(sizeof(double)*dbH->dim);
2149 double* query = (double*)(indata+sizeof(int)); 2153 double* query = (double*)(indata+sizeof(int));
2150 double* queryCopy = 0; 2154 double* queryCopy = 0;
2151 2155
2152 double qMeanL2;
2153 double* sMeanL2;
2154
2155 unsigned USE_THRESH=0;
2156 double SILENCE_THRESH=0;
2157 double DIFF_THRESH=0;
2158
2159 if(!(dbH->flags & O2_FLAG_L2NORM) ) 2156 if(!(dbH->flags & O2_FLAG_L2NORM) )
2160 error("Database must be L2 normed for sequence query","use -l2norm"); 2157 error("Database must be L2 normed for sequence query","use -l2norm");
2161 2158
2162 if(verbosity>1) { 2159 if(verbosity>1) {
2163 cerr << "performing norms ... "; cerr.flush(); 2160 cerr << "performing norms ... "; cerr.flush();
2167 // Make a copy of the query 2164 // Make a copy of the query
2168 queryCopy = new double[numVectors*dbH->dim]; 2165 queryCopy = new double[numVectors*dbH->dim];
2169 memcpy(queryCopy, query, numVectors*dbH->dim*sizeof(double)); 2166 memcpy(queryCopy, query, numVectors*dbH->dim*sizeof(double));
2170 qNorm = new double[numVectors]; 2167 qNorm = new double[numVectors];
2171 sNorm = new double[dbVectors]; 2168 sNorm = new double[dbVectors];
2172 sMeanL2=new double[dbH->numFiles]; 2169 assert(qNorm&&sNorm&&queryCopy&&sequenceLength);
2173 assert(qNorm&&sNorm&&queryCopy&&sMeanL2&&sequenceLength);
2174 unitNorm(queryCopy, dbH->dim, numVectors, qNorm); 2170 unitNorm(queryCopy, dbH->dim, numVectors, qNorm);
2175 query = queryCopy; 2171 query = queryCopy;
2176 2172
2177 // Make norm measurements relative to sequenceLength 2173 // Make norm measurements relative to sequenceLength
2178 unsigned w = sequenceLength-1; 2174 unsigned w = sequenceLength-1;
2181 2177
2182 // Copy the L2 norm values to core to avoid disk random access later on 2178 // Copy the L2 norm values to core to avoid disk random access later on
2183 memcpy(sNorm, l2normTable, dbVectors*sizeof(double)); 2179 memcpy(sNorm, l2normTable, dbVectors*sizeof(double));
2184 double* snPtr = sNorm; 2180 double* snPtr = sNorm;
2185 double* qnPtr = qNorm; 2181 double* qnPtr = qNorm;
2182
2183 double *sPower = 0, *qPower = 0;
2184 double *spPtr = 0, *qpPtr = 0;
2185
2186 if (usingPower) {
2187 if(!(dbH->flags & O2_FLAG_POWER)) {
2188 error("database not power-enabled", dbName);
2189 }
2190 sPower = new double[dbVectors];
2191 spPtr = sPower;
2192 memcpy(sPower, powerTable, dbVectors * sizeof(double));
2193 }
2194
2186 for(i=0; i<dbH->numFiles; i++){ 2195 for(i=0; i<dbH->numFiles; i++){
2187 if(trackTable[i]>=sequenceLength){ 2196 if(trackTable[i]>=sequenceLength) {
2188 sequence_sum(snPtr, trackTable[i], sequenceLength); 2197 sequence_sum(snPtr, trackTable[i], sequenceLength);
2198 if (usingPower) {
2199 sequence_sum(spPtr, trackTable[i], sequenceLength);
2200 }
2189 2201
2190 ps = snPtr; 2202 ps = snPtr;
2191 w=trackTable[i]-sequenceLength+1; 2203 w=trackTable[i]-sequenceLength+1;
2192 while(w--){ 2204 while(w--){
2193 *ps=sqrt(*ps); 2205 *ps=sqrt(*ps);
2194 ps++; 2206 ps++;
2195 } 2207 }
2196 } 2208 if (usingPower) {
2197 snPtr+=trackTable[i]; 2209 ps = spPtr;
2198 } 2210 w = trackTable[i] - sequenceLength + 1;
2199 2211 while(w--) {
2200 double* pn = sMeanL2; 2212 *ps = *ps / sequenceLength;
2201 w=dbH->numFiles; 2213 ps++;
2202 while(w--) 2214 }
2203 *pn++=0.0; 2215 }
2204 ps=sNorm; 2216 }
2205 unsigned processedTracks=0; 2217 snPtr += trackTable[i];
2206 for(i=0; i<dbH->numFiles; i++){ 2218 if (usingPower) {
2207 if(trackTable[i]>sequenceLength-1){ 2219 spPtr += trackTable[i];
2208 w = trackTable[i]-sequenceLength+1; 2220 }
2209 pn = sMeanL2+i; 2221 }
2210 *pn=0; 2222
2211 while(w--)
2212 if(*ps>0)
2213 *pn+=*ps++;
2214 *pn/=trackTable[i]-sequenceLength+1;
2215 SILENCE_THRESH+=*pn;
2216 processedTracks++;
2217 }
2218 ps = sNorm + trackTable[i];
2219 }
2220 if(verbosity>1) {
2221 cerr << "processedTracks: " << processedTracks << endl;
2222 }
2223
2224 SILENCE_THRESH/=processedTracks;
2225 USE_THRESH=1; // Turn thresholding on
2226 DIFF_THRESH=SILENCE_THRESH; // mean shingle power
2227 SILENCE_THRESH/=5; // 20% of the mean shingle power is SILENCE
2228 if(verbosity>4) {
2229 cerr << "silence thresh: " << SILENCE_THRESH;
2230 }
2231
2232 sequence_sum(qnPtr, numVectors, sequenceLength); 2223 sequence_sum(qnPtr, numVectors, sequenceLength);
2224 if (usingPower) {
2225 qPower = new double[numVectors];
2226 qpPtr = qPower;
2227 if (lseek(powerfd, sizeof(int), SEEK_SET) == (off_t) -1) {
2228 error("error seeking to data", powerFileName, "lseek");
2229 }
2230 int count = read(powerfd, qPower, numVectors * sizeof(double));
2231 if (count == -1) {
2232 error("error reading data", powerFileName, "read");
2233 }
2234 if ((unsigned) count != numVectors * sizeof(double)) {
2235 error("short read", powerFileName);
2236 }
2237
2238 sequence_sum(qpPtr, numVectors, sequenceLength);
2239 ps = qpPtr;
2240 w = numVectors - sequenceLength + 1;
2241 while(w--) {
2242 *ps = *ps / sequenceLength;
2243 ps++;
2244 }
2245 }
2233 2246
2234 ps = qnPtr; 2247 ps = qnPtr;
2235 qMeanL2 = 0; 2248 w = numVectors - sequenceLength + 1;
2236 w=numVectors-sequenceLength+1;
2237 while(w--){ 2249 while(w--){
2238 *ps=sqrt(*ps); 2250 *ps=sqrt(*ps);
2239 qMeanL2+=*ps++; 2251 }
2240 }
2241 qMeanL2 /= numVectors-sequenceLength+1;
2242 2252
2243 if(verbosity>1) { 2253 if(verbosity>1) {
2244 cerr << "done." << endl; 2254 cerr << "done." << endl;
2245 } 2255 }
2246 2256
2333 assert(D); 2343 assert(D);
2334 DD = new double*[numVectors]; 2344 DD = new double*[numVectors];
2335 assert(DD); 2345 assert(DD);
2336 2346
2337 gettimeofday(&tv1, NULL); 2347 gettimeofday(&tv1, NULL);
2338 processedTracks=0; 2348 unsigned processedTracks = 0;
2339 unsigned successfulTracks=0; 2349 unsigned successfulTracks=0;
2340 2350
2341 double* qp; 2351 double* qp;
2342 double* sp; 2352 double* sp;
2343 double* dp; 2353 double* dp;
2451 2461
2452 // Search for minimum distance by shingles (concatenated vectors) 2462 // Search for minimum distance by shingles (concatenated vectors)
2453 for(j=0;j<=numVectors-wL;j+=HOP_SIZE) 2463 for(j=0;j<=numVectors-wL;j+=HOP_SIZE)
2454 for(k=0;k<=trackTable[track]-wL;k+=HOP_SIZE){ 2464 for(k=0;k<=trackTable[track]-wL;k+=HOP_SIZE){
2455 thisDist=2-(2/(qnPtr[j]*sNorm[trackIndexOffset+k]))*DD[j][k]; 2465 thisDist=2-(2/(qnPtr[j]*sNorm[trackIndexOffset+k]))*DD[j][k];
2456 if(verbosity>10) { 2466 if(verbosity>9) {
2457 cerr << thisDist << " " << qnPtr[j] << " " << sNorm[trackIndexOffset+k] << endl; 2467 cerr << thisDist << " " << qnPtr[j] << " " << sNorm[trackIndexOffset+k] << endl;
2458 } 2468 }
2459 // Gather chi^2 statistics 2469 // Gather chi^2 statistics
2460 if(thisDist<minSample) 2470 if(thisDist<minSample)
2461 minSample=thisDist; 2471 minSample=thisDist;
2467 logSampleSum+=log(thisDist); 2477 logSampleSum+=log(thisDist);
2468 } 2478 }
2469 2479
2470 // diffL2 = fabs(qnPtr[j] - sNorm[trackIndexOffset+k]); 2480 // diffL2 = fabs(qnPtr[j] - sNorm[trackIndexOffset+k]);
2471 // Power test 2481 // Power test
2472 if(!USE_THRESH || 2482 if (usingPower) {
2473 // Threshold on mean L2 of Q and S sequences 2483 if (!(powers_acceptable(qpPtr[j], sPower[trackIndexOffset + k]))) {
2474 (USE_THRESH && qnPtr[j]>SILENCE_THRESH && sNorm[trackIndexOffset+k]>SILENCE_THRESH && 2484 thisDist = 1000000.0;
2475 // Are both query and target windows above mean energy? 2485 }
2476 (qnPtr[j]>qMeanL2*.25 && sNorm[trackIndexOffset+k]>sMeanL2[track]*.25))) // && diffL2 < DIFF_THRESH ))) 2486 }
2477 thisDist=thisDist; // Computed above 2487
2478 else
2479 thisDist=1000000.0;
2480 if(thisDist>=0 && thisDist<=radius){ 2488 if(thisDist>=0 && thisDist<=radius){
2481 distances[0]++; // increment count 2489 distances[0]++; // increment count
2482 break; // only need one track point per query point 2490 break; // only need one track point per query point
2483 } 2491 }
2484 } 2492 }
2577 delete[] queryCopy; 2585 delete[] queryCopy;
2578 if(qNorm) 2586 if(qNorm)
2579 delete[] qNorm; 2587 delete[] qNorm;
2580 if(sNorm) 2588 if(sNorm)
2581 delete[] sNorm; 2589 delete[] sNorm;
2582 if(sMeanL2) 2590 if(qPower)
2583 delete[] sMeanL2; 2591 delete[] qPower;
2592 if(sPower)
2593 delete[] sPower;
2584 if(D) 2594 if(D)
2585 delete[] D; 2595 delete[] D;
2586 if(DD) 2596 if(DD)
2587 delete[] DD; 2597 delete[] DD;
2588 if(timesdata) 2598 if(timesdata)
2589 delete[] timesdata; 2599 delete[] timesdata;
2590 if(meanDBdur) 2600 if(meanDBdur)
2591 delete[] meanDBdur; 2601 delete[] meanDBdur;
2592
2593
2594 } 2602 }
2595 2603
2596 // Unit norm block of features 2604 // Unit norm block of features
2597 void audioDB::unitNorm(double* X, unsigned dim, unsigned n, double* qNorm){ 2605 void audioDB::unitNorm(double* X, unsigned dim, unsigned n, double* qNorm){
2598 unsigned d; 2606 unsigned d;