changeset 463:35bb388d0eac api-inversion

audioDB::query_loop and audioDB::query_loop_points are no more. Be a little bit careful about deleting the exact_evaluation_queue in error conditions, but otherwise this was simple (If you ignore the work of the previous $N$ commits, that is). The inversion work in query.cpp is now complete, apart from physically teasing apart the API function from the body of audioDB::query and then moving the two remaining audioDB:: methods elsewhere. Unfortunately, we're still not quite done, because we have to deal with audioDB::index_query_loop too, which is still a little bit tangled. Still, we're nearly there...
author mas01cr
date Tue, 30 Dec 2008 15:38:59 +0000
parents f689510baaf4
children 1030664df98c
files audioDB-internals.h audioDB.h index.cpp query.cpp
diffstat 4 files changed, 38 insertions(+), 46 deletions(-) [+]
line wrap: on
line diff
--- a/audioDB-internals.h	Tue Dec 30 15:38:55 2008 +0000
+++ b/audioDB-internals.h	Tue Dec 30 15:38:59 2008 +0000
@@ -16,6 +16,23 @@
   void *power;
 } adb_datum_internal_t;
 
+/* this struct is to collect together a bunch of information about a
+ * query (or, in fact, a single database entry, or even a whole
+ * database).  The _data pointers are immutable (hey, FIXME: should
+ * they be constified in some way?) so that free() can work on them
+ * later, while the ones without the suffix are mutable to maintain
+ * the "current" position in some way.  mean_duration points to a
+ * (possibly single-element) array of mean durations for each track.
+ */
+typedef struct adb_qpointers_internal {
+  uint32_t nvectors;
+  double *l2norm_data;
+  double *l2norm;
+  double *power_data;
+  double *power;
+  double *mean_duration;
+} adb_qpointers_internal_t;
+
 /* this struct is for maintaining per-query state.  We don't want to
  * store this stuff in the adb struct itself, because (a) it doesn't
  * belong there and (b) in principle people might do two queries in
@@ -225,5 +242,7 @@
 int audiodb_free_datum(adb_datum_t *);
 int audiodb_datum_qpointers(adb_datum_t *, uint32_t, double **, double **, adb_qpointers_internal_t *);
 int audiodb_query_spec_qpointers(adb_t *, adb_query_spec_t *, double **, double **, adb_qpointers_internal_t *);
+int audiodb_query_queue_loop(adb_t *, adb_query_spec_t *, adb_qstate_internal_t *, double *, adb_qpointers_internal_t *);
+int audiodb_query_loop(adb_t *, adb_query_spec_t *, adb_qstate_internal_t *);
 char *audiodb_index_get_name(const char *, double, uint32_t);
 bool audiodb_index_exists(const char *, double, uint32_t);
--- a/audioDB.h	Tue Dec 30 15:38:55 2008 +0000
+++ b/audioDB.h	Tue Dec 30 15:38:59 2008 +0000
@@ -43,15 +43,6 @@
 bool operator<(const PointPair& a, const PointPair& b);
 
 // should be in -internals.h
-typedef struct adb_qpointers_internal {
-  uint32_t nvectors;
-  double *l2norm_data;
-  double *l2norm;
-  double *power_data;
-  double *power;
-  double *mean_duration;
-} adb_qpointers_internal_t;
-
 typedef struct adb_qstate_internal {
   Accumulator *accumulator;
   std::set<std::string> *allowed_keys;
@@ -94,13 +85,6 @@
 #define COM_EXHAUSTIVE "--exhaustive"
 #define COM_LSH_EXACT "--lsh_exact"
 
-// Because LSH returns NN with P(1)<1 we want to return exact
-// points above this boundary. 
-// Because we work in Radius^2 units,
-// The sqrt of this number is the multiplier on the radius
-
-#define O2_LSH_EXACT_MULT 9
-
 #define O2_OLD_MAGIC ('O'|'2'<<8|'D'<<16|'B'<<24)
 #define O2_MAGIC ('o'|'2'<<8|'d'<<16|'b'<<24)
 #define O2_FORMAT_VERSION (4U)
@@ -328,8 +312,6 @@
   void error(const char* a, const char* b = "", const char *sysFunc = 0);
 
   void insertTimeStamps(unsigned n, std::ifstream* timesFile, double* timesdata);
-  int query_loop(adb_t *adb, adb_query_spec_t *spec, adb_qstate_internal_t *qstate);
-  void query_loop_points(adb_t *adb, adb_query_spec_t *spec, adb_qstate_internal_t *qstate, double *query, adb_qpointers_internal_t *qpointers);
   void initRNG();
   void initDBHeader(const char *dbName);
   void initInputFile(const char *inFile);
--- a/index.cpp	Tue Dec 30 15:38:55 2008 +0000
+++ b/index.cpp	Tue Dec 30 15:38:59 2008 +0000
@@ -577,8 +577,8 @@
   }
 }
 
-// Maintain a queue of points to pass to query_loop_points() for exact
-// evaluation
+// Maintain a queue of points to pass to audiodb_query_queue_loop()
+// for exact evaluation
 void audiodb_index_add_point_exact(void *user_data, Uns32T pointID, Uns32T qpos, float dist) {
   adb_qcallback_t *data = (adb_qcallback_t *) user_data;
   adb_t *adb = data->adb;
@@ -667,7 +667,7 @@
 
   if(lsh_exact)
     // Perform exact distance computation on point pairs in exact_evaluation_queue
-    query_loop_points(adb, spec, qstate, query, &qpointers);
+    audiodb_query_queue_loop(adb, spec, qstate, query, &qpointers);
   
   // Close the index file
   close(lshfid);
--- a/query.cpp	Tue Dec 30 15:38:55 2008 +0000
+++ b/query.cpp	Tue Dec 30 15:38:59 2008 +0000
@@ -240,10 +240,10 @@
     VERB_LOG(1, "Calling indexed query on database %s, radius=%f, sequence_length=%d\n", adb->path, qspec.refine.radius, qspec.qid.sequence_length);
     index_query_loop(adb, &qspec, &qstate);
   }
-  else{
+  else {
     VERB_LOG(1, "Calling brute-force query on database %s\n", dbName);
-    if(query_loop(adb, &qspec, &qstate)) {
-      error("query_loop failed");
+    if(audiodb_query_loop(adb, &qspec, &qstate)) {
+      error("audiodb_query_loop failed");
     }
   }
 
@@ -628,35 +628,22 @@
   
 }
 
-// query_points()
-//
-// using PointPairs held in the exact_evaluation_queue compute squared distance for each PointPair
-// and insert result into the current reporter.
-//
-// Preconditions:
-// A query inFile has been opened with setup_query(...) and query pointers initialized
-// The database contains some points
-// An exact_evaluation_queue has been allocated and populated
-// A reporter has been allocated
-//
-// Postconditions:
-// reporter contains the points and distances that meet the reporter constraints 
-
-void audioDB::query_loop_points(adb_t *adb, adb_query_spec_t *spec, adb_qstate_internal_t *qstate, double *query, adb_qpointers_internal_t *qpointers) {
+int audiodb_query_queue_loop(adb_t *adb, adb_query_spec_t *spec, adb_qstate_internal_t *qstate, double *query, adb_qpointers_internal_t *qpointers) {
   adb_qpointers_internal_t dbpointers = {0};
 
   uint32_t sequence_length = spec->qid.sequence_length;
   bool power_refine = spec->refine.flags & (ADB_REFINE_ABSOLUTE_THRESHOLD|ADB_REFINE_RELATIVE_THRESHOLD);
 
   if(qstate->exact_evaluation_queue->size() == 0) {
-    return;
+    return 0;
   }
 
   /* We are guaranteed that the order of points is sorted by:
    * {trackID, spos, qpos} so we can be relatively efficient in
    * initialization of track data.  We assume that points usually
    * don't overlap, so we will use exhaustive dot product evaluation
-   * (instead of memoization of partial sums, as in query_loop()). */
+   * (instead of memoization of partial sums, as in query_loop()).
+   */
   double dist;
   double *dbdata = 0, *dbdata_pointer;
   Uns32T currentTrack = 0x80000000; // KLUDGE: Initialize with a value outside of track index range
@@ -671,15 +658,17 @@
       currentTrack = pp.trackID;
       adb_datum_t d = {0};
       if(audiodb_track_id_datum(adb, pp.trackID, &d)) {
-        error("failed to get datum");
+        delete qstate->exact_evaluation_queue;
+        return 1;
       }
       if(audiodb_datum_qpointers(&d, sequence_length, &dbdata, &dbdata_pointer, &dbpointers)) {
+        delete qstate->exact_evaluation_queue;
         audiodb_free_datum(&d);
-        error("failed to get dbpointers");
+        return 1;
       }
       audiodb_free_datum(&d);
     }
-    Uns32T qPos = usingQueryPoint?0:pp.qpos;// index for query point
+    Uns32T qPos = (spec->qid.flags & ADB_QUERY_ID_FLAG_EXHAUSTIVE) ? pp.qpos : 0;
     Uns32T sPos = pp.spos; // index into l2norm table
     // Test power thresholds before computing distance
     if( ( (!power_refine) || audiodb_powers_acceptable(&spec->refine, qpointers->power[qPos], dbpointers.power[sPos])) &&
@@ -696,7 +685,8 @@
         dist = qn*qn + sn*sn - 2*dist;
         break;
       }
-      if((!radius) || dist <= (O2_LSH_EXACT_MULT*radius+O2_DISTANCE_TOLERANCE)) {
+      if((!(spec->refine.flags & ADB_REFINE_RADIUS)) || 
+         dist <= (spec->refine.radius+O2_DISTANCE_TOLERANCE)) {
         adb_result_t r;
         r.key = (*adb->keys)[pp.trackID].c_str();
         r.dist = dist;
@@ -713,9 +703,10 @@
   SAFE_DELETE_ARRAY(dbpointers.power_data);
   SAFE_DELETE_ARRAY(dbpointers.mean_duration);
   delete qstate->exact_evaluation_queue;
+  return 0;
 }
 
-int audioDB::query_loop(adb_t *adb, adb_query_spec_t *spec, adb_qstate_internal_t *qstate) {
+int audiodb_query_loop(adb_t *adb, adb_query_spec_t *spec, adb_qstate_internal_t *qstate) {
   
   double *query, *query_data;
   adb_qpointers_internal_t qpointers = {0}, dbpointers = {0};