Home || Architecture || Video Search || Visual Search || Scripts || Applications || Important Messages || OGL || Src

InterestPointProc.h

Go to the documentation of this file.
00001 #ifndef Impala_Core_ImageSet_InterestPointProc_h
00002 #define Impala_Core_ImageSet_InterestPointProc_h
00003 
00004 #include "Core/ImageSet/Reporter.h"
00005 #include "Core/ImageSet/MakeImageSet.h"
00006 #include "Core/Array/MakeFromValue.h"
00007 #include "Core/Array/ArrayListDelete.h"
00008 #include "Core/Array/WriteRaw.h"
00009 #include "Core/Feature/FeatureTable.h"
00010 #include "Core/Feature/InterestPointFeature.h"
00011 #include "Core/Feature/DumpFeatureTableHistogram.h"
00012 
00013 namespace Impala
00014 {
00015 namespace Core
00016 {
00017 namespace ImageSet
00018 {
00019 
00020 class InterestPointProc : public Listener
00021 {
00022 public:
00023 
00024     InterestPointProc(Reporter* reporter, CmdOptions& options) 
00025         : mInterestPointFeature(options), mOptions(options), mNoZIP(false),
00026           mSkipThisFolder(false)
00027     {
00028         mReporter = reporter;
00029         mNoZIP = options.GetBool("noZIP");
00030         mTableInfoString = "codebook=" + options.GetString("codebook");
00031         mCodebookSet = "";
00032         if (options.GetNrArg() > 2)
00033             mCodebookSet = options.GetArg(2);
00034         if(mNoZIP) {
00035             ILOG_INFO("NOT creating ZIP output files");
00036         } else {
00037             ILOG_INFO("Creating ZIP output files");
00038         }
00039     }
00040 
00041     static void
00042     AddCmdOptions()
00043     { 
00044         Feature::InterestPointFeature::AddCmdOptions();
00045 
00046         CmdOptions& options = CmdOptions::GetInstance();
00047         options.AddOption(0, "noZIP",                    "",            "0");
00048         options.AddOption(0, "interestPointPostProcess", "command",     "");
00049         options.AddOption(0, "useDetectorCache",         "name",        "");
00050     }
00051 
00052     virtual void
00053     HandleNewWalk(ImageSet* is)
00054     {
00055         if(!mOptions.GetString("codebook").empty())
00056         {
00057             Database::RawDataSet* bookSet = is;
00058             if (!mCodebookSet.empty())
00059             {
00060                 ILOG_INFO("Using separate codebook set: " << mCodebookSet);
00061                 bookSet = Database::MakeRawDataSet(mCodebookSet);
00062             }
00063 
00064             mInterestPointFeature.SetCodebook(mOptions.GetString("codebook"),
00065                                               bookSet->GetDatabase());
00066         }
00067     }
00068 
00069     virtual void
00070     HandleNewWalk(ImageSet* is, String walkType)
00071     {
00072         mWalkType = walkType;
00073     }
00074 
00075     virtual void
00076     HandleNewDir(ImageSet* is, int dirId)
00077     {
00078         // Make the feature data folder
00079         ILOG_INFO("HandleNewDir: " << dirId);
00080         int fileId = is->GetFirstFileId(dirId);
00081         is->MakeDirId("FeatureData", mInterestPointFeature.GetFeatureNameShort(),
00082                       fileId, false);
00083         mTempFilenames.clear();
00084         mSkipThisFolder = false;
00085         if(!CmdOptions::GetInstance().GetBool("override")) 
00086         {
00087             // only support skipping if override is off
00088             if(!mNoZIP) 
00089             {
00090                 // does the ZIP exist already?
00091                 String serverName = is->GetFilePathFeatureData
00092                     (mInterestPointFeature.GetFeatureName(), dirId, false, -1,
00093                      true, false) + ".zip";
00094                 String temp =
00095                     is->GetDatabase()->GetFilePath(serverName, false, true);
00096                 if(!temp.empty())
00097                 {
00098                     mSkipThisFolder = true;
00099                     ILOG_WARNING("Skipping folder " << dirId <<
00100                                  "; ZIP file already exists");
00101                 }
00102             }
00103             else
00104             {
00105                 if(mInterestPointFeature.mClusterInput)
00106                 {
00107                     // clusterInput mode
00108                     Feature::FeatureDefinition def = mInterestPointFeature.GetFeatureName();
00109                     def.AddParameter("clusterinput", "2");
00110                     String tableName = is->GetFilePathFeatureData
00111                         (def, dirId, false, -1, false, true);
00112                     if(!tableName.empty())
00113                     {
00114                         mSkipThisFolder = true;
00115                         ILOG_WARNING("Skipping folder " << dirId <<
00116                                      "; FeatureData:ClusterInput file already exists");
00117                     }
00118                 }
00119                 else
00120                 {
00121                     // does the featuretable exist already?
00122                     String tableName = is->GetFilePathFeatureData
00123                         (mInterestPointFeature.mFeatureDefinition, dirId, false,
00124                          -1, false, true);
00125                     if(!tableName.empty())
00126                     {
00127                         mSkipThisFolder = true;
00128                         ILOG_WARNING("Skipping folder " << dirId <<
00129                                      "; FeatureData file already exists");
00130                     }
00131                 }
00132             }
00133         }
00134     }
00135 
00136     virtual void
00137     HandleNewFile(ImageSet* is, int fileId, Array::Array2dVec3UInt8* im)
00138     {
00139         if(mSkipThisFolder)
00140             return;
00141         int dirId = is->GetDirIdOfFile(fileId);
00142         // silent failures - we might be reading from ImageArchives
00143         String fileName = is->GetAsPath(fileId);
00144         // create temporary output filename
00145         String outputFilename =
00146             PathJoin(GetTmpPath(), is->GetFileBase(fileId) + "." +
00147                      mInterestPointFeature.GetFeatureName());
00148         ILOG_DEBUG(" outputFilename=" << outputFilename  << "; fileId=" << fileId
00149                    << "; dirId=" << dirId);
00150         if (im == 0)
00151         {
00152             ILOG_ERROR("No image " << fileName);
00153             return;
00154         }
00155         
00156         String detectorCacheFilename = "";
00157         if(mOptions.GetString("useDetectorCache") != "")
00158         {
00159             detectorCacheFilename = is->GetFilePathId
00160                 ("FeatureData", mOptions.GetString("useDetectorCache"), fileId,
00161                  false, false, is->GetFileBase(fileId) + "." +
00162                  mOptions.GetString("useDetectorCache"), false);
00163             ILOG_INFO("detectorCacheFilename = " << detectorCacheFilename);
00164         }
00165         if(mNoZIP) {
00166             outputFilename = "";
00167         }
00168         mInterestPointFeature.mClusterInputImage =
00169             QuidObj(is->GetQuidImage(fileId)).ToString();
00170 
00171         if(!mInterestPointFeature.FindInterestPoints(mOptions, im, 
00172                                                      is->GetQuidImage(fileId),
00173                                                      outputFilename,
00174                                                      true, detectorCacheFilename))
00175         {
00176             ILOG_ERROR("Extracting interest points/descriptors failed: "<<fileName);
00177         }
00178 
00179         if(mInterestPointFeature.mLastCodebookVectors.size() != 0)
00180         {
00181             // we have a projected feature vector
00182             std::vector<Vector::VectorTem<Real64>*>& featureVectors =
00183                 mInterestPointFeature.mLastCodebookVectors;
00184             if(mFeatureTables.size() < featureVectors.size())
00185             {
00186                 // first valid vector: allocate the table
00187                 for(int i = mFeatureTables.size(); i < featureVectors.size(); i++)
00188                 {
00189                     String name = mInterestPointFeature.GetFeatureName();
00190                     Feature::FeatureTable* t = new Feature::FeatureTable(name, 500,
00191                                                   featureVectors[i]->Size());
00192                     mFeatureTables.push_back(t);
00193                 }
00194             }
00195             for(int i = 0; i < featureVectors.size(); i++)
00196             {
00197                 Quid quid = is->GetQuidImage(fileId);
00198                 mFeatureTables[i]->Add(quid, *featureVectors[i]);
00199             }
00200         }
00201         
00202         // post-processing functionality
00203         if(mOptions.GetString("interestPointPostProcess") != "")
00204         {
00205             String cmd = mOptions.GetString("interestPointPostProcess")
00206                 + " " + outputFilename;
00207             ILOG_DEBUG("Post-processing = " << cmd);
00208             system(cmd.c_str());
00209         }
00210         if(!mNoZIP)
00211         {
00212             mTempFilenames.push_back(outputFilename);
00213         }
00214     }
00215 
00217     virtual void
00218     HandleDoneDir(ImageSet* is, int dirId)
00219     {
00220         if(mSkipThisFolder) return;
00221         int fileId = is->GetFirstFileId(dirId);
00222 
00223         // Feature table logic
00224         Feature::FeatureDefinition fdef = mInterestPointFeature.mFeatureDefinition;
00225         String tableName = is->GetFilePathFeatureData
00226             (fdef, dirId, false, -1, true, false);
00227         if(mFeatureTables.size() != 0)
00228         {
00229             for(int i = 0; i < mFeatureTables.size(); i++)
00230             {
00231                 Feature::FeatureDefinition tempDef(fdef.AsString());
00232                 if(i != 0)
00233                     tempDef.AddParameter("sub", MakeString(i));
00234                 String tempTableName = is->GetFilePathFeatureData
00235                     (tempDef, dirId, false, -1, true, false);
00236                 mFeatureTables[i]->SetInfo(mTableInfoString);
00237                 Write(mFeatureTables[i], tempTableName, is->GetDatabase(), true);
00238                 //for debugging:
00239                 //Feature::DumpFeatureTableHistogram(mFeatureTables[i], tempDef, dirId);
00240                 delete mFeatureTables[i];
00241                 mFeatureTables[i] = 0;
00242             }
00243             mFeatureTables.clear();
00244         }
00245         
00246         // ZIP-file logic
00247         if(!mNoZIP)
00248         {
00249             String featureName = mInterestPointFeature.GetFeatureName();
00250             String fName = PathJoin(GetTmpPath(), "tmp-" + featureName +
00251                                          "-" + MakeString(dirId) + ".zip");
00252             String txtName = StringReplace(fName, ".zip", ".txt");
00253             String serverName = is->GetFilePathFeatureData
00254                 (featureName + ".zip", dirId, false, -1, true, false);
00255             if (fName == String(""))
00256             {
00257                 ILOG_ERROR("Empty file name");
00258             }
00259             serverName = StringReplace(serverName, ".zip.tab", ".tab.zip");
00260                         
00261             // put it all in fName
00262             std::ofstream fs(txtName.c_str());
00263             for(std::vector<String>::iterator iter = mTempFilenames.begin();
00264                 iter != mTempFilenames.end(); iter++)
00265             {
00266                 fs << (*iter) << std::endl;
00267             }
00268             fs.close();
00269     
00270             String cmd = "zip ";
00271             cmd += fName;
00272             cmd += " -@ <";
00273             cmd += txtName;
00274             //TODO: call toZip.py here? Instead of Shell scripting?
00275             if (serverName != String(""))
00276             {
00277                 // without override, fName will be empty if zip file already
00278                 // exists, so we cannot ZIP!
00279                 system(cmd.c_str());
00280             }
00281 
00282             // cleanup
00283             if(std::remove(txtName.c_str()) != 0) {
00284                 ILOG_WARN("Could not cleanup intermediate file: " << txtName);
00285             }
00286             
00287             // copy ZIP file to its final destination
00288             Util::IOBuffer* zip = new Util::IOBufferFile(fName, true, false);
00289             Util::Database* database = is->GetDatabase();
00290             Util::IOBuffer* destination = database->GetIOBuffer
00291                 (serverName, false, false, "tmp", 0, true);
00292             static const int bufSize = 1024 * 1024;
00293             static unsigned char buffer[bufSize];
00294             while(true)
00295             {
00296                 int bytesread = zip->Read(buffer, bufSize);
00297                 if(bytesread == 0)
00298                     break;
00299                 destination->Write(buffer, bytesread);
00300             }
00301             delete zip;
00302             delete destination; // this will force a write through a channel, if
00303                                 // needed
00304 
00305             // cleanup
00306             if(std::remove(fName.c_str()) != 0) {
00307                 ILOG_WARN("Could not cleanup temporary ZIP file: " << fName);
00308             }
00309         }
00310 
00311         // clusterInput mode
00312         if(mInterestPointFeature.mClusterInput &&
00313            mInterestPointFeature.mClusterInputData)
00314         {
00315             String tableName = is->GetFilePathFeatureData
00316                 (mInterestPointFeature.mClusterInputData->GetFeatureDefinition(),
00317                  dirId, false, -1, true, false);
00318             Write(mInterestPointFeature.mClusterInputData, tableName,
00319                   is->GetDatabase(), true);
00320             delete mInterestPointFeature.mClusterInputData;
00321             mInterestPointFeature.mClusterInputData = 0;
00322         }
00323         
00324         // cleanup
00325         for(std::vector<String>::iterator iter = mTempFilenames.begin();
00326             iter != mTempFilenames.end(); iter++)
00327         {
00328             if(std::remove((*iter).c_str()) != 0)
00329             {
00330                 ILOG_WARN("Could not cleanup intermediate file: " << (*iter));
00331             }
00332         }
00333         mTempFilenames.clear();
00334         ILOG_INFO("HandleDoneDir: " << dirId);
00335     }
00336 
00337 
00338 private:
00339 
00340     Reporter* mReporter;
00341     std::vector<Feature::FeatureTable*> mFeatureTables;
00342     Feature::InterestPointFeature mInterestPointFeature;
00343     CmdOptions& mOptions;
00344     String mCodebookSet;
00345     std::vector<String> mTempFilenames;
00346     bool mNoZIP;
00347     bool mSkipThisFolder;
00348     String mTableInfoString;
00349     String mWalkType;
00350     
00351     ILOG_VAR_DEC;
00352 
00353 };
00354 
00355 ILOG_VAR_INIT(InterestPointProc, Impala.Core.ImageSet);
00356 
00357 } // namespace ImageSet
00358 } // namespace Core
00359 } // namespace Impala
00360 
00361 #endif

Generated on Fri Mar 19 09:31:13 2010 for ImpalaSrc by  doxygen 1.5.1