Просмотр исходного кода

More modifations and commentations for Local Features and stuff

Alexander Freytag 12 лет назад
Родитель
Сommit
388132554e

+ 5 - 1
cbaselib/MultiDataset.cpp

@@ -42,8 +42,12 @@ void MultiDataset::selectExamples ( const std::string & examples_command,
     vector<string> parts;
     StringTools::split ( cmd, ' ', parts );
 
-    if ( (parts.size() != 3) && ((parts.size() != 2) || (parts[0] != "all")) )
+    if ( (parts.size() != 3) && ((parts.size() != 2) || (parts[0].compare("all") != 0)) )
+    {
+      std::cerr << "parts.size(): "<<parts.size()<<std::endl;
+      std::cerr << " parts[0]: " << parts[0] << std::endl;
       fthrow( Exception, "Syntax error " << examples_command );
+    }
 
     const std::string & mode = parts[0];
     const std::string & csel = parts[1];

+ 43 - 5
features/localfeatures/GenericLFSelection.h

@@ -135,27 +135,65 @@ class GenericLFSelection
         if ( writefeat )
         {
           // write the features to a file, if there isn't any to read
-          writeFeats = new LFWriteCache ( conf, lfrep );
-          lfrep = writeFeats;
+          
+          if ( useForTrainOrTest == TRAINING )
+          {
+            writeFeats = new LFWriteCache ( conf, lfrep, "cacheTrain" );
+            lfrep = writeFeats;
+          }
+          else if ( useForTrainOrTest == TESTING )
+          {
+            writeFeats = new LFWriteCache ( conf, lfrep, "cacheTest" );
+            lfrep = writeFeats;
+          }
+          else //not specified whether for training or testing, so we do not care about
+          {
+            writeFeats = new LFWriteCache ( conf, lfrep );
+            lfrep = writeFeats;
+          }              
+
         }
 
+//TODO add the section into constructor for readCache
         if ( readfeat )
         {
           int numFeatures = conf->gI(section, "localfeature_count", -1);
           // read the features from a file
           if ( writefeat )
           {
-            readFeats = new LFReadCache ( conf, writeFeats, numFeatures );
+            if ( useForTrainOrTest == TRAINING )
+            {
+              readFeats = new LFReadCache ( conf, writeFeats, numFeatures );
+            }
+            else if ( useForTrainOrTest == TESTING )
+            {
+              readFeats = new LFReadCache ( conf, writeFeats, numFeatures );
+            }
+            else //not specified whether for training or testing, so we do not care about
+            {
+              readFeats = new LFReadCache ( conf, writeFeats, numFeatures );
+            }                         
           }
           else
           {
-            readFeats = new LFReadCache (conf, lfrep, numFeatures );
+            if ( useForTrainOrTest == TRAINING )
+            {
+              readFeats = new LFReadCache (conf, lfrep, numFeatures );
+            }
+            else if ( useForTrainOrTest == TESTING )
+            {
+              readFeats = new LFReadCache (conf, lfrep, numFeatures );
+            }
+            else //not specified whether for training or testing, so we do not care about
+            {
+              readFeats = new LFReadCache (conf, lfrep, numFeatures );
+            }
           }
           lfrep = readFeats; 
         }  
           
         return lfrep;
-        }
+      }
 };
 
 }

+ 3 - 3
features/localfeatures/LFColorSande.cpp

@@ -45,7 +45,7 @@ LFColorSande::LFColorSande ( const Config *conf, std::string section )
   std::ostringstream temp;
   temp << g;
   gridsize = temp.str();
-
+  
   if ( descriptor_size <= 0 )
   {
     fprintf ( stderr, "LFColorSande::LFColorSande: No descriptor size found in config -> self test\n" );
@@ -60,11 +60,11 @@ LFColorSande::LFColorSande ( const Config *conf, std::string section )
 
     fprintf ( stderr, "LFColorSande::LFColorSande Self Test features:%d dimension:%d\n", ( int ) features.size(), descriptor_size );
   }
-
+  
   if ( descriptor_size != conf->gI ( "features", "descriptor_size", descriptor_size ) )
   {
     cerr << "Warning: LFColorSande: descriptor sizes do not match !!!" << endl;
-  }
+  }  
 }
 
 LFColorSande::~LFColorSande()

+ 2 - 0
features/localfeatures/LFReadCache.tcc

@@ -40,7 +40,9 @@ int LFReadCache::extractFeaturesTemplate ( const ImageClass & img,
     if ( lfrep == NULL )
       fthrow ( NICE::Exception, "LocalFeatureRepresentation not available, recovering is impossible!" );
 
+    std::cerr << "extract features with lfrep used in ReadCache" << std::endl;
     lfrep->extractFeatures ( img, features, positions );
+    std::cerr << "features extracted" << std::endl;
 
     features.save ( filename_desc, descFormat );
     positions.save ( filename_pos, NICE::VVector::FILEFORMAT_LINE );

+ 5 - 4
features/localfeatures/LFWriteCache.cpp

@@ -29,12 +29,13 @@ using namespace NICE;
 
 
 LFWriteCache::LFWriteCache ( const Config *conf,
-                             const LocalFeatureRepresentation *_lfrep ) : lfrep ( _lfrep )
+                             const LocalFeatureRepresentation *_lfrep,
+                             const std::string & _section ) : lfrep ( _lfrep )
 {
-  cachedir = conf->gS ( "cache", "root" );
-  cachemode = Globals::getCacheMode ( conf->gS ( "cache", "mode", "cat" ) );
+  cachedir = conf->gS ( _section, "root" );
+  cachemode = Globals::getCacheMode ( conf->gS ( _section, "mode", "cat" ) );
 
-  std::string descFormat_s = conf->gS ( "cache", "descriptor_format", "binary_double" );
+  std::string descFormat_s = conf->gS ( _section, "descriptor_format", "binary_double" );
   if ( descFormat_s == "binary_double" )
     descFormat = VVector::FILEFORMAT_BINARY_DOUBLE;
   else if ( descFormat_s == "binary_uchar" )

+ 3 - 1
features/localfeatures/LFWriteCache.h

@@ -38,7 +38,9 @@ namespace OBJREC {
     
         /** simple constructor */
         LFWriteCache( const NICE::Config *conf, 
-            const LocalFeatureRepresentation *lfrep ); 
+            const LocalFeatureRepresentation *lfrep,
+            const std::string & _section = "cache"
+                    ); 
         
         /** simple destructor */
         virtual ~LFWriteCache();

+ 39 - 14
progs/evaluateCompleteBoWPipeline.cpp

@@ -124,7 +124,7 @@ OBJREC::ClusterAlgorithm * setClusterAlgo( const Config * _conf )
 { 
  std::string section ( "clusteringStuff" );
   // define the initial number of clusters our codebook shall contain
-  int initialNumberOfClusters = _conf->gI(section, "initialNumberOfClusters", 10);
+  int noClusters = _conf->gI(section, "noClusters", 10);
   
   // define the clustering algorithm to be used
   std::string clusterAlgoString = _conf->gS(section, "clusterAlgo", "kmeans");  
@@ -133,15 +133,15 @@ OBJREC::ClusterAlgorithm * setClusterAlgo( const Config * _conf )
   
   if (clusterAlgoString.compare("kmeans") == 0)
   {
-    clusterAlgo = new OBJREC::KMeans(initialNumberOfClusters);
+    clusterAlgo = new OBJREC::KMeans(noClusters);
   }
   else if (clusterAlgoString.compare("kmedian") == 0)
   {
-    clusterAlgo = new OBJREC::KMedian(initialNumberOfClusters);
+    clusterAlgo = new OBJREC::KMedian(noClusters);
   }  
   else if (clusterAlgoString.compare("GMM") == 0) 
   {
-    clusterAlgo = new OBJREC::GMM( _conf, initialNumberOfClusters );
+    clusterAlgo = new OBJREC::GMM( _conf, noClusters );
   }
   else if ( clusterAlgoString.compare("RandomClustering") == 0 )   
   {
@@ -195,17 +195,36 @@ int main( int argc, char **argv )
   NICE::VVector featuresFromAllTrainingImages;  
   featuresFromAllTrainingImages.clear();
   
+  //determine how many training images we actually use to easily allocate the correct amount of memory afterwards
+  int numberOfTrainingImages ( 0 );
+  for(LabeledSet::const_iterator classIt = trainFiles->begin() ; classIt != trainFiles->end() ; classIt++)
+  {
+    numberOfTrainingImages += classIt->second.size();
+    std::cerr << "number of examples for this class: " << classIt->second.size() << std::endl;
+  }
+  
+  
   //okay, this is redundant - but I see no way to do it more easy right now...
-  std::vector<NICE::VVector> featuresOfImages ( trainFiles->size() );
+  std::vector<NICE::VVector> featuresOfImages ( numberOfTrainingImages );
   //this again is somehow redundant, but we need the labels lateron for easy access - change this to a better solution :)
-  NICE::VectorT<int> labelsTrain ( trainFiles->size(), 0 );
+  NICE::VectorT<int> labelsTrain ( numberOfTrainingImages, 0 );
   
   //TODO replace the nasty makro by a suitable for-loop to make it omp-ready (parallelization)
   int imgCnt ( 0 );
-  LOOP_ALL_S( *trainFiles )
+   
+  // the corresponding nasty makro: LOOP_ALL_S( *trainFiles )
+  for(LabeledSet::const_iterator classIt = trainFiles->begin() ; classIt != trainFiles->end() ; classIt++)
   {
-      EACH_INFO( classno, info );
-      std::string filename = info.img();  
+    for ( std::vector<ImageInfo *>::const_iterator imgIt = classIt->second.begin(); 
+          imgIt != classIt->second.end(); 
+          imgIt++, imgCnt++
+        ) 
+    {
+      // the corresponding nasty makro: EACH_INFO( classno, info );
+      int classno ( classIt->first );
+      const ImageInfo imgInfo = *(*imgIt);      
+      
+      std::string filename = imgInfo.img();      
       
       NICE::ColorImage img( filename );
   
@@ -217,7 +236,7 @@ int main( int argc, char **argv )
   
       Globals::setCurrentImgFN ( filename );
       featureExtractor->extractFeatures ( img, features, positions );  
-        
+              
       //normalization :)
       for ( NICE::VVector::iterator i = features.begin();
             i != features.end();
@@ -225,15 +244,16 @@ int main( int argc, char **argv )
       {              
         i->normalizeL1();
       }  
-      
+            
       //collect them all in a larger data structure
       featuresFromAllTrainingImages.append( features );
+      
       //and store it as well in the data struct that additionally keeps the information which features belong to which image
       //TODO this can be made more clever!
 //       featuresOfImages.push_back( features );
       featuresOfImages[imgCnt] = features;
       labelsTrain[imgCnt] = classno;
-      imgCnt++;
+    }
   }
   
   
@@ -252,9 +272,10 @@ int main( int argc, char **argv )
   std::vector<double> weights;
   std::vector<int> assignments;
   
+  std::cerr << "call cluster of cluster algo " << std::endl;
   clusterAlgo->cluster( featuresFromAllTrainingImages, prototypes, weights, assignments );
   
-  
+  std::cerr << "create new codebook with the computed prototypes" << std::endl;
   OBJREC::CodebookPrototypes * codebook = new OBJREC::CodebookPrototypes ( prototypes );
   
   
@@ -305,8 +326,11 @@ int main( int argc, char **argv )
   // ========================================================================
   
   const LabeledSet *testFiles = md["test"];
+
+  delete featureExtractor;
+  featureExtractor = OBJREC::GenericLFSelection::selectLocalFeatureRep ( conf, "features", OBJREC::GenericLFSelection::TESTING );  
   
-  NICE::Matrix confusionMat;
+  NICE::Matrix confusionMat ( trainFiles->size() /* number of classes in training */, testFiles->size() /* number of classes for testing*/, 0.0 );
   NICE::Timer t;
   
   ClassificationResults results;
@@ -364,6 +388,7 @@ int main( int argc, char **argv )
       ClassificationResult r = classifier->classify ( histogramOfCurrentImg );
       t.stop();
       uint classno_estimated = r.classno;
+      r.classno_groundtruth = classno_groundtruth;
 
       //if we like to store the classification results for external post processing, uncomment this
       if ( writeClassificationResults )