00001 /*! @file Landmark/density.C [put description here] */ 00002 00003 // $HeadURL: svn://isvn.usc.edu/software/invt/trunk/saliency/src/Landmark/density.C $ 00004 // $Id: density.C 6410 2006-04-01 22:12:24Z rjpeters $ 00005 00006 // find the density plot: treat each object as 1 pt in 2d space 00007 // not considering sigma yet 00008 00009 #include "Landmark/density.H" 00010 00011 #include "Image/FilterOps.H" 00012 #include "Image/Image.H" 00013 #include "Raster/Raster.H" 00014 00015 #include <fstream> 00016 #include <math.h> 00017 00018 Image<float> density(const char* filename, std::map<int, Object*>& list) 00019 { 00020 00021 // read features into image 00022 std::ifstream file(filename); 00023 LDEBUG("opening file %s", filename); 00024 if (file == 0) LFATAL("Couldn't open object file: '%s'", filename); 00025 std::string line; 00026 int count = 0; 00027 00028 while(getline(file, line)) 00029 { 00030 double mu1, sigma1; 00031 char name[256]; 00032 sscanf(line.c_str(), "%s\t%lf %lf", 00033 name, &mu1, &sigma1); 00034 //LDEBUG("read %s\t%lf %lf\t%lf %lf\n", 00035 // name, mu1, sigma1, mu2, sigma2); 00036 00037 Object* o = new Object(name, count, mu1, sigma1); 00038 list.insert(std::pair<int, Object*>(count, o)); 00039 count++; 00040 00041 } 00042 00043 // compute the inter-object distances 00044 int num = list.size(); 00045 double sum = 0.0; 00046 double min_w = -1.0, max_w = 0.0; 00047 double distance[num][num]; 00048 for(int i = 0; i < num; i++) 00049 { 00050 double min = 0.0; 00051 for(int j = i + 1; j < num; j++) 00052 { 00053 if(i == j) 00054 distance[i][j] = 0.0; 00055 else 00056 { 00057 // find the distance 00058 distance[i][j] = std::abs(list[i]->mu1 - list[j]->mu1); 00059 00060 // find the minimum of all distances to this object 00061 if(min == 0.0) 00062 min = distance[i][j]; 00063 else if(min > distance[i][j]) 00064 min = distance[i][j]; 00065 00066 // find the image width and height 00067 if(min_w == -1.0) 00068 min_w = list[i]->mu1; 00069 else if(min_w > list[i]->mu1) 00070 min_w = list[i]->mu1; 00071 00072 if(max_w == 0.0) 00073 max_w = list[i]->mu1; 00074 else if(max_w < list[i]->mu1) 00075 max_w = list[i]->mu1; 00076 00077 } 00078 } 00079 sum += min; 00080 } 00081 00082 // consider the last object in the list to find the image width and height 00083 if(min_w == -1.0) 00084 min_w = list[num-1]->mu1; 00085 else if(min_w > list[num-1]->mu1) 00086 min_w = list[num-1]->mu1; 00087 00088 if(max_w == 0.0) 00089 max_w = list[num-1]->mu1; 00090 else if(max_w < list[num-1]->mu1) 00091 max_w = list[num-1]->mu1; 00092 00093 // find the average min inter-object distance 00094 double avg = sum / num; 00095 LDEBUG(" average inter-object min. distance = %lf", avg); 00096 00097 // estimate image width and height 00098 LDEBUG(" width -- (%lf, %lf)", 00099 min_w, max_w); 00100 double w = max_w - min_w; 00101 00102 // scale the image size to 128 * 1 00103 Image<float> image(128, 1, NO_INIT); 00104 image.clear(0.0f); 00105 double scale_w = 125.0 / w; 00106 00107 // first plot the objects in the 1d space 00108 for(int i = 0; i < num; i++) 00109 { 00110 list[i]->mu1 = (list[i]->mu1 - min_w) * scale_w; 00111 int mu = (int)list[i]->mu1; 00112 // one more object yields the same feature response 00113 image.setVal(mu, image.getVal(mu)+1.0f); 00114 } 00115 00116 // use avg to estimate the gaussian convolution kernel 00117 //double sigma = avg * std::max(scale_w, scale_h); 00118 double sigma = avg * scale_w; // / 5; 00119 LDEBUG("sigma of gaussian = %lf", sigma); 00120 00121 Image<float> density = convGauss(image, sigma, 0, 1); 00122 LDEBUG("convolution over"); 00123 00124 Raster::WriteGray( image, "input.pgm"); 00125 LDEBUG("written input"); 00126 //Raster::WriteGray( density, "density.pgm"); 00127 00128 return density; 00129 00130 }