The Machine Perception Toolbox

[Introduction]- [News]- [Download]- [Screenshots]- [Manual (pdf)]- [Forums]- [API Reference]- [Repository ]

 

Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Namespace Members | Class Members | File Members | Related Pages

probColorSearch.h

Go to the documentation of this file.
00001 /*
00002  *  probColorSearch.h
00003  *  
00004  *
00005  *  Created by Bret Fortenberry 2003.
00006  *  Copyright (c) 2003 Machine Perception Laboratory
00007  *  University of California San Diego.
00008  *  Please read the disclaimer and notes about redistribution
00009  *  at the end of this file.
00010  *
00011  *  Authors: Bret Fortenberry, Ian Fasel, Josh Susskind
00012  */
00013 #ifndef _PROBCOLORSEARCH_H_
00014 #define _PROBCOLORSEARCH_H_
00015 
00016 // #ifdef __APPLE_CC__
00017 // #include <mpisearch/mpisearch.h>
00018 // #include <mpisearch/square.h>
00019 // #include <mpisearch/featuredata.h>
00020 // #include <mpisearch/rimage.h>
00021 // #else
00022 #include "mpisearch.h"
00023 #include "square.h"
00024 #include "featuredata.h"
00025 #include "rimage.h" 
00026 // #endif
00027 
00028 // #include "ffcommon.h"
00029 
00030 #include <math.h>
00031 #include <string>
00032 #include <list>
00033 
00034 template < class T >
00035 class ProbColorSearch : MPISearchObjectDetector<T> {
00036  public:
00037     enum SearchType {
00038         Max, 
00039         Mean
00040     };
00041 
00042         ProbColorSearch();
00043         ~ProbColorSearch();
00044         int CreateData(int width, int height, int searchWidth, int searchHeight); // create a rectangle in data
00045         double probSearch(SearchType type, RImage<T> &pixels, int size, TSquare<double>& win, TSquare<double>& var, 
00046                       double thresh, int LaplacianPrior);
00047 
00048  private:
00049         int set_width, set_height;
00050  
00051         double logPrior(int x, int y, double d, TSquare<double> &win, TSquare<double>& var, int LaplacianPrior); 
00052 };
00053 
00054 template < class T >
00055 ProbColorSearch<T>::ProbColorSearch(){};
00056 
00057 template < class T >
00058 ProbColorSearch<T>::~ProbColorSearch(){};
00059 
00060 
00061 template < class T >
00062 int ProbColorSearch<T>::CreateData(int width, int height, int searchWidth, int searchHeight){
00063         const int origin = 0;
00064         data.features = new Feature;
00065         data.features[0].numcorners = 4;
00066         data.numStdAdjusts = 0;
00067         data.numfeatures = 1;
00068         data.numcascades = 0;
00069         data.features[0].corners = new Corner[4]; 
00070         data.features[0].corners[0].x = origin;                                                 data.features[0].corners[0].y = origin;                                                         data.features[0].corners[0].value =   1;
00071         data.features[0].corners[1].x = origin+searchWidth; data.features[0].corners[1].y = origin;                                                     data.features[0].corners[1].value =  -1;
00072         data.features[0].corners[2].x = origin;                                                 data.features[0].corners[2].y = origin+searchHeight; data.features[0].corners[2].value =  -1;
00073         data.features[0].corners[3].x = origin+searchWidth; data.features[0].corners[3].y = origin+searchHeight; data.features[0].corners[3].value =   1;
00074         
00075         data.patch_width = searchWidth + 1;
00076         data.patch_height = searchHeight + 1;
00077         set_width = width; 
00078         set_height = height;
00079         stream.init(width, height, data, 1);
00080 
00081         return 1;
00082 }
00083 
00084 template < class T >
00085 double ProbColorSearch<T>::logPrior(int x, int y, double d, TSquare<double> &win, TSquare<double>& var, int LaplacianPrior) 
00086 {                       
00087         if (LaplacianPrior == 1){
00088                 // Laplacian prior is the default
00089                 const double c = 3*log(2.0) + log(var.x * var.y*var.size);
00090                 double zscore = fabs(x-win.x)*var.x + fabs(y-win.y)*var.y + fabs(d-win.size)*var.size;
00091                 return ( -c - zscore);
00092         }
00093         else{ // Gaussian prior
00094                 const double c = 1.5 * log(2*PI); // log(sqrt(cube(2*PI)))
00095                 return (- sqr(x - win.x)*var.x 
00096                                 - sqr(y - win.y)*var.y 
00097                                 - sqr(d - win.size)*var.size
00098                                 - c - 0.5 * (var.x + var.y + var.size));
00099         }
00100 }
00101 
00102 template < class T >
00103 double ProbColorSearch<T>::probSearch(SearchType type, RImage<T> &pixels, int size, TSquare<double>& win, TSquare<double>& var, double thresh, int LaplacianPrior){
00104          // Cache the corners
00105         
00106         if(pixels.width != set_width || pixels.height != set_height || !stream.allocated) {
00107         stream.reset(pixels.width, pixels.height, data, 1);
00108                 set_width = pixels.width; set_height = pixels.height;
00109         }
00110   
00111         
00112         // Integrate the image
00113   static_cast<RIntegral< T >* >(stream.images[0])->integrate(pixels);
00114   //stream.images[0]->print();
00115         
00116   bool bPrior = var.x > 0 && var.y > 0 && var.size > 0;
00117   bool firstTime = true;
00118 
00119   double lpostbest = 0;
00120   double max_llike = 0, llike = 0;
00121   double lprior = 0; // log prior
00122   double ptot = 0;
00123         double d1;
00124 
00125   double mx = 0;
00126   double my = 0;
00127   double md = 0;
00128 
00129   double sx = 0;
00130   double sy = 0;
00131   double sd = 0;
00132 
00133         // Do the search
00134   int scale_index;
00135   float scale_factor;
00136   int x, y;
00137   int numWindows = 0;
00138 
00139   MPIImagePyramid<T>::const_iterator scale = stream.mpi->begin();
00140   MPIImagePyramid<T>::const_iterator last_scale = stream.mpi->end();
00141 
00142         scale_factor = 0;
00143         while ( scale_factor*size < .092*pixels.width) {
00144                 scale_index = scale.getScale(scale_factor);
00145                 scale++;
00146         }
00147   for( ; scale != last_scale; ++scale){
00148     // get pointers to cached values for this scale
00149     scale_index = scale.getScale(scale_factor);
00150     //T sf2 = scale_factor * scale_factor;
00151     CornerCache< T > **corners = stream.corners[scale_index];
00152     CornerCache< T > *feature_corners = corners[0];
00153     //T *fns = stream.fns[scale_index];
00154     d1 = scale_factor * size ;
00155     T a,b,c,d;
00156     MPIScaledImage<T>::const_iterator window = (*scale).begin(), last_window = (*scale).end();
00157     for( ; window != last_window; ++window, ++numWindows){
00158       // Do the per window computation 
00159         llike = 0;
00160         for(int corner = 0; corner < data.features[0].numcorners; corner+=4) {
00161             a = window.getPixel0( feature_corners[corner].scaledIndex ) * feature_corners[corner].value;
00162             b = window.getPixel0( feature_corners[corner+1].scaledIndex ) * feature_corners[corner+1].value;
00163             c = window.getPixel0( feature_corners[corner+2].scaledIndex ) * feature_corners[corner+2].value;
00164             d = window.getPixel0( feature_corners[corner+3].scaledIndex ) * feature_corners[corner+3].value;
00165         llike += a + b + c + d; // this is the result of getFeat
00166         }
00167 
00168         if (llike < thresh) {
00169             continue;
00170         }
00171 
00172         window.getCoords(x,y);
00173         if (bPrior){
00174             lprior = logPrior(x,y,d1,win,var,LaplacianPrior);
00175         }
00176                 
00177         double lpost;
00178         lpost = llike + lprior;
00179   
00180  
00181                 double p = exp(lpost);
00182         ptot += p;
00183                 
00184                 switch(type) {
00185                  case Max:
00186                         if (firstTime || (lpost > lpostbest)){
00187                                 firstTime = false;
00188                                   mx = x;
00189                                   my = y;
00190                                   md = d1;
00191                                   lpostbest = lpost;
00192                                         max_llike = llike;
00193                                         
00194                         } // end if max
00195                         break;
00196                    case Mean:
00197                           {
00198                                   // do mean here
00199                                   mx += p*x;
00200                                 my += p*y;
00201                                 md += p * d1;
00202                                 
00203                                 sx += p*(x*x);
00204                                 sy += p*(y*y);
00205                                 sd += p*(d1*d1);
00206                         }
00207                         break;
00208                    default:
00209                           break;
00210         }
00211                         
00212     } // End window loop
00213   } // End scale loop
00214   switch(type) {
00215     case Max:
00216       break;
00217         case Mean:
00218         {
00219                 mx /= ptot;
00220                 my /= ptot;
00221                 md /= ptot;
00222 
00223                 sx = sx/ptot - mx*mx;
00224                 sy = sy/ptot - mx*mx;
00225                 sd = sd/ptot - mx*mx;
00226         }
00227                 break;
00228         default:
00229                 break;
00230   }
00231   win = TSquare<double>(md,mx,my,0);
00232   var = TSquare<double>(sd,sx,sy,0);
00233 
00234   if(type == Max) {
00235     return max_llike;
00236   }
00237                 
00238   //get value of mean feature  need to update fimage to random access x,y before implement
00239   /*int scale = (int) (md/size);        
00240   int a = static_cast<int>((mx - 1));
00241   int b = static_cast<int>((my - 1));
00242         double f = 0;
00243 
00244         for(int corner = 0; corner < data.feature[0].numcorners; corner++) {
00245 
00246                         f+= ii.getPixel(a + scale * data.feature[0].corners[corner].x,
00247                                                      b + scale * data.feature[0].corners[corner].y) 
00248                                         * data.feature[0].corners[corner].value;
00249 
00250         } // end feature loop
00251         return f;*/
00252         return -1;
00253         
00254 }
00255 
00256 #endif
00257 
00258 
00259 /*
00260  * 
00261  * Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
00262  * 
00263  *    1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
00264  *    2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
00265  *    3. The name of the author may not be used to endorse or promote products derived from this software without specific prior written permission.
00266  * 
00267  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00268  * 
00269  */

Generated on Mon Nov 8 17:07:46 2004 for MPT by  doxygen 1.3.9.1