123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350 |
- /**
- * @file testFeatureLearning.cpp
- * @brief test the feature learning routines to incrementally increase / adapt the codebook currently used
- * @author Alexander Freytag
- * @date 11-04-2013
- */
- //STL
- #include <iostream>
- #include <limits>
- //core
- #include <core/basics/Config.h>
- #include <core/basics/ResourceStatistics.h>
- #include <core/image/Convert.h>
- #include <core/vector/VectorT.h>
- //vislearning
- #include <vislearning/baselib/Globals.h>
- #include <vislearning/baselib/ICETools.h>
- #include <vislearning/cbaselib/MultiDataset.h>
- #include <vislearning/cbaselib/Example.h>
- //
- #include "vislearning/featureLearning/FeatureLearningGeneric.h"
- #include "vislearning/featureLearning/FeatureLearningClusterBased.h"
- #include "vislearning/featureLearning/FeatureLearningRegionBased.h"
- //
- #include "vislearning/noveltyDetection/NDCodebookLevelImagePooling.h"
- using namespace std;
- using namespace NICE;
- using namespace OBJREC;
- /**
- test feature learning routines
- */
- int main( int argc, char **argv )
- {
- #ifndef __clang__
- #ifndef __llvm__
- std::set_terminate( __gnu_cxx::__verbose_terminate_handler );
- #endif
- #endif
- Config * conf = new Config ( argc, argv );
-
- bool showTrainingImages = conf->gB( "featureLearning", "showTrainingImages", false );
- bool showTestImages = conf->gB( "featureLearning", "showTestImages", false );
- bool showResults = conf->gB( "featureLearning", "showResults", false );
-
- ResourceStatistics rs;
- std::string resultdir;
- resultdir = conf->gS( "featureLearning", "resultdir", "/tmp/");
-
-
- NICE::ImageT<int> noveltyScale ( 20, 100 );
- for (int j = 0; j < 100; j++)
- {
- for (int i = 0; i < 20; i++)
- noveltyScale(i,j) = 99-j;
- }
-
- NICE::ColorImage noveltyScaleRGB (noveltyScale.width(), noveltyScale.height() );
- imageToPseudoColor( noveltyScale, noveltyScaleRGB );
-
- std::string destinationNoveltyScale ( resultdir + "_" + "_noveltyScale.ppm");
- noveltyScaleRGB.writePPM( destinationNoveltyScale );
-
-
-
- //**********************************************
- //
- // READ INITIAL TRAINING SET TO COMPUTE
- // AN INITIAL CODEBOOK
- //
- //**********************************************
-
- std::cerr << " READ INITIAL TRAINING SET TO COMPUTE AN INITIAL CODEBOOK" << std::endl;
-
- MultiDataset md( conf );
- const LabeledSet *trainFiles = md["train"];
-
- //**********************************************
- //
- // SET UP THE FEATURE LEARNING ALGO
- //
- //**********************************************
-
- OBJREC::FeatureLearningGeneric * featureLearning;
-
- std::string featureLearningMethod = conf->gS( "featureLearning", "featureLearningMethod", "clusterBased" );
-
- if (featureLearningMethod.compare("clusterBased") == 0)
- {
- featureLearning = new OBJREC::FeatureLearningClusterBased( conf, &md );
- }
- else if (featureLearningMethod.compare("regionBased") == 0)
- {
- featureLearning = new OBJREC::FeatureLearningRegionBased( conf, &md );
- }
- else
- {
- std::cerr << "Unknown feature learning algorithm selected, use cluster based instead" << std::endl;
- featureLearning = new OBJREC::FeatureLearningClusterBased( conf, &md );
- }
-
- //**********************************************
- //
- // SET UP THE NOVELTY DECTION ALGO
- //
- //**********************************************
-
- OBJREC::NDCodebookLevelImagePooling * novDetector;
- novDetector = new OBJREC::NDCodebookLevelImagePooling( conf, &md, "featureLearning" );
-
- //evaluate how well the training images are covered with our initial codebook
- //that is, compute these nice "novelty maps" per feature
-
- //NOTE we skip this currently
- LOOP_ALL_S( *trainFiles )
- {
- EACH_INFO( classno, info );
- std::string filename = info.img();
- //
- // featureLearning->evaluateCurrentCodebook( filename , true /* beforeComputingNewFeatures */);
-
- NICE::ImageT< int > imgClusterAssignments;
- imgClusterAssignments = featureLearning->evaluateCurrentCodebookByAssignments(filename , false /* beforeComputingNewFeatures */, false /* _binaryShowLatestPrototype*/ );
-
- std::cerr << "now do image To pseude color and show the initial cluster assignments" << std::endl;
- NICE::ColorImage imgClusterAssignmentsRGB (imgClusterAssignments.width(), imgClusterAssignments.height() );
- imageToPseudoColor( imgClusterAssignments, imgClusterAssignmentsRGB );
-
- if ( showResults )
- showImage(imgClusterAssignmentsRGB, "cluster Assignments" ) ;
- else
- {
- std::vector< std::string > list2;
- StringTools::split ( filename, '/', list2 );
- std::string destination ( resultdir + NICE::intToString(0) + "_" + list2.back() + "_00_initialClusterAssignments.ppm");
- imgClusterAssignmentsRGB.writePPM( destination );
- }
- }
-
- //**********************************************
- //
- // EVALUATE INITIAL CLUSTER
- //
- // COMPUTE A NICE CONFUSION MATRIX
- // FOR OUR INITIAL CODEBOOK
- //
- //**********************************************
- NICE::Matrix confusionMatInitial;
- featureLearning->evaluateCurrentCodebookByConfusionMatrix( confusionMatInitial );
- std::cerr << "initial Confusion matrix: " << std::endl << confusionMatInitial << std::endl;
-
- //set the initially computed codebook to the novelty detection mechanism
- //TODO this should be done, but currently we do not care about
- // novDetector->setCodebook( featureLearning->getCurrentCodebook() );
-
- //**********************************************
- //
- // FOR-LOOP OVER UNSEEN IMAGES
- //
- // EXTRACT FEATURES, CLUSTER THEM, TAKE
- // MOST "VALUABLE" CLUSTERS AS NEW
- // REPRESENTATIVES IN AN INCREASED CODEBOK
- //
- //**********************************************
- const LabeledSet *testFiles = md["test"];
-
- std::cerr << "start looping over all files" << std::endl;
- int imageCnt ( 0 );
- LOOP_ALL_S( *testFiles )
- {
- EACH_INFO( classno, info );
- std::string filename = info.img();
-
- NICE::ColorImage orig( filename );
-
- NICE::ImageT< int > imgClusterAssignments;
- imgClusterAssignments = featureLearning->evaluateCurrentCodebookByAssignments(filename , false /* beforeComputingNewFeatures */, false /* _binaryShowLatestPrototype*/ );
-
- NICE::ColorImage imgClusterAssignmentsRGB (imgClusterAssignments.width(), imgClusterAssignments.height() );
- imageToPseudoColor( imgClusterAssignments, imgClusterAssignmentsRGB );
-
- NICE::FloatImage noveltyImageBefore;
- noveltyImageBefore = featureLearning->evaluateCurrentCodebookByDistance( filename , true /* beforeComputingNewFeatures */ );
-
- NICE::ColorImage noveltyImageBeforeRGB (noveltyImageBefore.width(), noveltyImageBefore.height() );
- imageToPseudoColor( noveltyImageBefore, noveltyImageBeforeRGB );
-
- if ( showResults )
- showImage(imgClusterAssignmentsRGB, "cluster Assignments" ) ;
- else
- {
- std::vector< std::string > list2;
- StringTools::split ( filename, '/', list2 );
- std::string destination ( resultdir + NICE::intToString(0) + "_" + list2.back() + "_00_initialClusterAssignments.ppm");
- imgClusterAssignmentsRGB.writePPM( destination );
-
- std::string destinationNovelty ( resultdir + NICE::intToString(0) + "_" + list2.back() + "_01_initialClusterDistances.ppm");
- noveltyImageBeforeRGB.writePPM( destinationNovelty );
- }
-
- //**********************************************
- //
- // IS THIS IMAGE NOVEL?
- //
- // IF NOT, GO TO THE NEXT ONE
- //
- //**********************************************
-
- bool b_isImageNovel ( novDetector->evaluateNoveltyOfImage( noveltyImageBefore ) );
-
- if ( ! b_isImageNovel )
- {
- std::cerr << " --- NOT NOVEL --- " << std::endl << std::endl;
- continue;
- }
- else
- {
- std::cerr << " --- NOVEL --- " << std::endl;
- }
-
- while ( b_isImageNovel )
- {
-
- //**********************************************
- //
- // LEARN NEW FEATURE FOR A NOVEL IMAGE
- //
- //**********************************************
-
- featureLearning->learnNewFeatures( filename );
-
- //and update the codebook pointer within our novelty detection algorithm
- //TODO this should be done, but currently we do not care about
- // novDetector->setCodebook( featureLearning->getCurrentCodebook() );
-
- //**********************************************
- //
- // EVALUATE HOW WELL THE CURRENT IMAGE
- // CAN BE EXPLAINED AFTER
- // COMPUTING A NEW FEATURE
- //
- // SHOULD WE REPEAT THIS UNTIL THE IMAGE
- // IS NOT CLASSIFIED AS "NOVEL" ANYMORE?
- //
- //**********************************************
-
- NICE::FloatImage noveltyImageAfter;
- noveltyImageAfter = featureLearning->evaluateCurrentCodebookByDistance( filename , false /* beforeComputingNewFeatures */ );
-
- NICE::FloatImage noveltyImageDifference ( noveltyImageAfter.width(), noveltyImageAfter.height());
- for ( uint y = 0 ; y < ( uint ) noveltyImageAfter.height() ; y++ )
- {
- for ( uint x = 0 ; x < ( uint ) noveltyImageAfter.width(); x++ )
- {
- noveltyImageDifference(x,y) = fabs ( noveltyImageBefore(x,y) - noveltyImageAfter(x,y) );
- }
- }
-
- std::cerr << "min diff: " << noveltyImageDifference.min() << " and max diff: " << noveltyImageDifference.max() << std::endl;
-
- NICE::ColorImage noveltyImageDifferenceRGB (noveltyImageAfter.width(), noveltyImageAfter.height() );
- imageToPseudoColor( noveltyImageDifference, noveltyImageDifferenceRGB );
-
- std::vector< std::string > list2;
- StringTools::split ( filename, '/', list2 );
- if ( showResults )
- {
- showImage( noveltyImageDifferenceRGB, "Difference of novelty images" );
- }
- else
- {
- std::string destination ( resultdir + NICE::intToString(imageCnt) + "_" + list2.back() + "_02_initialLoopClusterAssignments.ppm");
- imgClusterAssignmentsRGB.writePPM( destination );
- std::string destinationNoveltyDifference ( resultdir + NICE::intToString(imageCnt) + "_" + list2.back() + "_03_noveltyDifferences.ppm");
- noveltyImageDifferenceRGB.writePPM( destinationNoveltyDifference );
- }
- NICE::ImageT< int > imgClusterAssignmentsBinary;
- imgClusterAssignmentsBinary = featureLearning->evaluateCurrentCodebookByAssignments(filename , true, true /* _binaryShowLatestPrototype*/ );
-
- NICE::ImageT< int > imgClusterAssignments;
- imgClusterAssignments = featureLearning->evaluateCurrentCodebookByAssignments(filename , true, false /* _binaryShowLatestPrototype*/ );
-
- NICE::ColorImage imgClusterAssignmentsBinaryRGB (imgClusterAssignmentsBinary.width(), imgClusterAssignmentsBinary.height() );
- imageToPseudoColor( imgClusterAssignmentsBinary, imgClusterAssignmentsBinaryRGB );
-
- NICE::ColorImage imgClusterAssignmentsRGB (imgClusterAssignments.width(), imgClusterAssignments.height() );
- imageToPseudoColor( imgClusterAssignments, imgClusterAssignmentsRGB );
-
- if ( showResults )
- {
- showImage(imgClusterAssignmentsBinaryRGB, "cluster Assignments Binary (latest prototype)" ) ;
- showImage(imgClusterAssignmentsRGB, "cluster Assignments" ) ;
- }
- else
- {
- std::string destination ( resultdir + NICE::intToString(imageCnt) + "_" + list2.back() + "_5_clusterAssignments.ppm");
- std::string destinationBinary ( resultdir + NICE::intToString(imageCnt) + "_" + list2.back() + "_6_clusterAssignmentsBinary.ppm");
-
- imgClusterAssignmentsRGB.writePPM( destination );
- imgClusterAssignmentsBinaryRGB.writePPM( destinationBinary );
- }
-
- //check, whether the image will still be seen as novel or not
- // i.e., are we able to "explain" the image with the lately computed codebook entry?
- b_isImageNovel = novDetector->evaluateNoveltyOfImage( noveltyImageAfter ) ;
-
- if ( ! b_isImageNovel )
- {
- std::cerr << " --- NOT NOVEL ANYMORE --- " << std::endl << std::endl;
- }
- else
- {
- std::cerr << " --- STILL NOVEL --- " << std::endl;
- noveltyImageBefore = noveltyImageAfter;
- }
-
- //artifial break for the moment
- break;
- }
-
- imageCnt++;
- } //Loop over all test images
-
-
- //don't waste memory
- std::cerr << "don't waste memory - cleaning up" << std::endl;
- // if (trainFiles != NULL)
- // delete trainFiles;
- if (featureLearning != NULL)
- delete featureLearning;
- if (novDetector != NULL)
- delete novDetector;
- if (conf != NULL)
- delete conf;
-
- return 0;
- }
|