00001 /*!@file Channels/IntegerComplexChannel.H */ 00002 00003 // //////////////////////////////////////////////////////////////////// // 00004 // The iLab Neuromorphic Vision C++ Toolkit - Copyright (C) 2000-2005 // 00005 // by the University of Southern California (USC) and the iLab at USC. // 00006 // See http://iLab.usc.edu for information about this project. // 00007 // //////////////////////////////////////////////////////////////////// // 00008 // Major portions of the iLab Neuromorphic Vision Toolkit are protected // 00009 // under the U.S. patent ``Computation of Intrinsic Perceptual Saliency // 00010 // in Visual Environments, and Applications'' by Christof Koch and // 00011 // Laurent Itti, California Institute of Technology, 2001 (patent // 00012 // pending; application number 09/912,225 filed July 23, 2001; see // 00013 // http://pair.uspto.gov/cgi-bin/final/home.pl for current status). // 00014 // //////////////////////////////////////////////////////////////////// // 00015 // This file is part of the iLab Neuromorphic Vision C++ Toolkit. // 00016 // // 00017 // The iLab Neuromorphic Vision C++ Toolkit is free software; you can // 00018 // redistribute it and/or modify it under the terms of the GNU General // 00019 // Public License as published by the Free Software Foundation; either // 00020 // version 2 of the License, or (at your option) any later version. // 00021 // // 00022 // The iLab Neuromorphic Vision C++ Toolkit is distributed in the hope // 00023 // that it will be useful, but WITHOUT ANY WARRANTY; without even the // 00024 // implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // 00025 // PURPOSE. See the GNU General Public License for more details. // 00026 // // 00027 // You should have received a copy of the GNU General Public License // 00028 // along with the iLab Neuromorphic Vision C++ Toolkit; if not, write // 00029 // to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, // 00030 // Boston, MA 02111-1307 USA. // 00031 // //////////////////////////////////////////////////////////////////// // 00032 // 00033 // Primary maintainer for this file: Rob Peters <rjpeters at usc dot edu> 00034 // $HeadURL: svn://isvn.usc.edu/software/invt/trunk/saliency/src/Channels/IntegerComplexChannel.H $ 00035 // $Id: IntegerComplexChannel.H 12820 2010-02-11 05:44:51Z itti $ 00036 // 00037 00038 #ifndef CHANNELS_INTEGERCOMPLEXCHANNEL_H_DEFINED 00039 #define CHANNELS_INTEGERCOMPLEXCHANNEL_H_DEFINED 00040 00041 #include "Channels/ChannelFacet.H" 00042 #include "Channels/IntegerChannel.H" 00043 #include "Image/Image.H" 00044 #include "Image/fancynorm.H" // for MaxNormType 00045 00046 // ###################################################################### 00047 //! Like ComplexChannel, but avoids floating-point arithmetic 00048 class IntegerComplexChannel : public IntegerChannel, public ChannelFacetMap 00049 { 00050 public: 00051 /// Refer to a subchannel by one of: its index, its tagname, its address 00052 /** Only one of the pieces of information will be valid. Inside the 00053 IntegerComplexChannel functions that use SubchanKey, we will determine 00054 which one of the keys is the valid one, and use that one to look 00055 up the subchannel itself. */ 00056 struct SubchanKey 00057 { 00058 /// Initialize with an integer index 00059 SubchanKey(uint i) : index(i), tag(0), addr(0) {} 00060 00061 /// Initialize with a tag name 00062 SubchanKey(const char* t) : index(uint(-1)), tag(t), addr(0) {} 00063 00064 /// Initialize with a channel reference 00065 SubchanKey(IntegerChannel& c): index(uint(-1)), tag(0), addr(&c) {} 00066 00067 uint index; 00068 const char* tag; 00069 IntegerChannel* addr; 00070 }; 00071 00072 //! Constructor. 00073 /*! @param mgr our ModelManager (see ModelManager.H) 00074 @param descrName descriptive name for human usage 00075 @param tagName name for ParamMap usage 00076 @param vs The VisualFeature implemented by the channel */ 00077 IntegerComplexChannel(OptionManager& mgr, 00078 const std::string& descrName, 00079 const std::string& tagName, 00080 const VisualFeature vs, 00081 nub::ref<IntegerMathEngine> eng); 00082 00083 //! Virtual destructor. 00084 virtual ~IntegerComplexChannel(); 00085 00086 //! Is the channel homogeneous? 00087 /*! A homogeneous channel is one whose subchannels (and their subs) 00088 have identical VisualFeatures, and those are also identical to our 00089 VisualFeature. Default implementation returns true. */ 00090 virtual bool isHomogeneous() const; 00091 00092 //! Get the number of subchannels. 00093 uint numChans() const; 00094 00095 //! Look up one of the subchannels by its integer index. 00096 nub::ref<IntegerChannel> subChan(const uint idx) const; 00097 00098 //! Look up one of the subchannels by its tagname 00099 nub::ref<IntegerChannel> subChan(const std::string& tagname) const; 00100 00101 //! Look up one of the subchannels by a submap number 00102 /*!@param oldIdx - the submap index (in the IntegerComplexChannel); 00103 @param newIdx - return value: the number of the submap within 00104 the subchannel*/ 00105 nub::ref<IntegerChannel> subChanFromSubmapNum(const uint oldIdx, 00106 uint& newIdx) const; 00107 00108 //! Add a subchannel 00109 /*! @param ch The channel to be added 00110 @param name If not null, the channel's tagName will be set to 00111 this value 00112 00113 The channel's tagName is used for associative lookup. 00114 00115 This is just a wrapper to ModelComponent::addSubComponent(), 00116 with some checking that the subcomponent indeed is a 00117 IntegerChannel derivative, and some adjustment of our 00118 homogeneity (if the newly added subchannel has a different 00119 VisualFeature from ours, then be become heterogeneous). */ 00120 void addSubChan(nub::ref<IntegerChannel> ch, const char* name = 0); 00121 00122 /// Remove a subchannel 00123 void removeSubChan(nub::ref<IntegerChannel> ch); 00124 00125 /// Remove all of our subchannels 00126 void removeAllSubChans(); 00127 00128 /// Check if we have a channel of given tagname 00129 bool hasSubChan(const char* name) const; 00130 00131 /// Install a visitor which will be applied to all newly-added subchannels. 00132 void setSubchanVisitor(rutz::shared_ptr<ChannelVisitor> v); 00133 00134 //! Set the total weight allocated to the specified subchannel. 00135 /*! This weight will be divided amongst any sub-subchannels managed 00136 by the specifed subchannel. So, for example, if the total weight 00137 is set to 2.0, and the subchannel has four sub-subchannels, then 00138 each sub-subchannel will get an effective weight of 0.5. The 00139 initial weight setting is 1.0. But, If you are handling b/w 00140 images, for instance, you may set the weight for the color 00141 channel to 0.0 and save computations. */ 00142 void setSubchanTotalWeight(SubchanKey key, const double wt); 00143 00144 //! Return the total weight allocated to the specified subchannel. 00145 double getSubchanTotalWeight(SubchanKey key) const; 00146 00147 /// Whether to sort subchannels by their number of submaps. 00148 /** If true, this may help in parallel-processing situations where 00149 we want to start the most CPU-intensive channels first. 00150 00151 Must be called before start(). 00152 */ 00153 void sortChannelsByNumSubmaps(bool dosort); 00154 00155 virtual void readFrom(const ParamMap& pmap); 00156 00157 virtual void writeTo(ParamMap& pmap) const; 00158 00159 virtual bool outputAvailable() const; 00160 00161 virtual Dims getMapDims() const; 00162 00163 virtual uint numSubmaps() const; 00164 00165 virtual Image<int> getSubmapInt(const uint index) const; 00166 00167 virtual Image<float> getSubmap(const uint index) const 00168 { return Image<float>(getSubmapInt(index)); } 00169 00170 virtual Image<int> getRawCSmapInt(const uint idx) const; 00171 00172 virtual Image<float> getRawCSmap(const uint idx) const 00173 { return Image<float>(getRawCSmap(idx)); } 00174 00175 virtual std::string getSubmapName(const uint index) const; 00176 00177 virtual std::string getSubmapNameShort(const uint index) const; 00178 00179 00180 virtual void getFeatures(const Point2D<int>& locn, 00181 std::vector<float>& mean) const; 00182 00183 virtual void getFeaturesBatch(std::vector<Point2D<int>*> *locn, 00184 std::vector<std::vector<float> > *mean, 00185 int *count) const; 00186 00187 virtual Image<int> getOutputInt(); 00188 00189 //! Form output by combining output of subchannels. 00190 /*! This function just provides a caching wrapper around 00191 combineOutputsInt(), where the real work is 00192 done. IntegerComplexChannel provides a default implementation of 00193 combineOutputsInt() that sums the outputs of the subchannels and 00194 then optionally maxNormalize()'s the result. */ 00195 virtual Image<float> getOutput() 00196 { return Image<float>(getOutputInt()); } 00197 00198 //! Save our various maps using a FrameOstream 00199 /*! By default, we save our output map (if itsSaveOutputMap is true) 00200 and propagate the call to our subchannels. Our output 00201 (conspicuity) map will be prefixed by "CO<tagname>-" */ 00202 virtual void saveResults(const nub::ref<FrameOstream>& ofs); 00203 00204 //! Clears the output cache. 00205 virtual void killCaches(); 00206 00207 protected: 00208 OModelParam<MaxNormType> itsNormType; //!< Normalization; see fancynorm.H 00209 OModelParam<bool> itsSaveOutputMap; //!< Save our output map? 00210 OModelParam<bool> itsUseOlderVersion; //!< use old version? see Visualcortex.H 00211 00212 //! Set a fixed range of values for the raw output 00213 /*! By default, the range is set to [MAXNORMMIN .. MAXNORMMAX] at 00214 construction. If non-zero values are provided here, in getOutput() 00215 we will cumulate our various submaps, apply the provided range, 00216 apply spatial competition for salience, apply our total weight, 00217 and return the result. If a range [0.0 .. 0.0] is provided here, 00218 only spatial competition and weights will be applied, but the 00219 first step of applying the range will be skipped. This must be 00220 called before start(). */ 00221 OModelParam<int> itsOutputRangeMin; 00222 OModelParam<int> itsOutputRangeMax; 00223 00224 //! Combines the outputs of subchannels. 00225 /*! The default implementation just sums the outputs of the 00226 subchannels and then maxNormalize()'s if requested by 00227 itsNormType. */ 00228 virtual Image<int> combineOutputsInt(); 00229 00230 //! get started 00231 virtual void start1(); 00232 00233 //! get started 00234 virtual void start2(); 00235 00236 //! stop 00237 virtual void stop2(); 00238 00239 private: 00240 IntegerComplexChannel(const IntegerComplexChannel&); // not allowed 00241 IntegerComplexChannel& operator=(const IntegerComplexChannel&); // not allowed 00242 00243 void lookupSubmap(const uint idx, uint& subchan, uint& subidx) const; 00244 00245 struct Impl; 00246 Impl* rep; 00247 }; 00248 00249 00250 // ###################################################################### 00251 /* So things look consistent in everyone's emacs... */ 00252 /* Local Variables: */ 00253 /* mode: c++ */ 00254 /* indent-tabs-mode: nil */ 00255 /* End: */ 00256 00257 #endif // CHANNELS_INTEGERCOMPLEXCHANNEL_H_DEFINED