GestureRecognitionToolkit  Version: 0.2.5
The Gesture Recognition Toolkit (GRT) is a cross-platform, open-source, c++ machine learning library for real-time gesture recognition.
WeightedAverageFilter.cpp
1 /*
2 GRT MIT License
3 Copyright (c) <2012> <Nicholas Gillian, Media Lab, MIT>
4 
5 Permission is hereby granted, free of charge, to any person obtaining a copy of this software
6 and associated documentation files (the "Software"), to deal in the Software without restriction,
7 including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so,
9 subject to the following conditions:
10 
11 The above copyright notice and this permission notice shall be included in all copies or substantial
12 portions of the Software.
13 
14 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT
15 LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
16 IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
17 WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
18 SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
19 */
20 
21 #define GRT_DLL_EXPORTS
22 #include "WeightedAverageFilter.h"
23 
24 GRT_BEGIN_NAMESPACE
25 
26 //Define the string that will be used to identify the object
27 const std::string WeightedAverageFilter::id = "WeightedAverageFilter";
28 std::string WeightedAverageFilter::getId() { return WeightedAverageFilter::id; }
29 
30 //Register the WeightedAverageFilter module with the PreProcessing base class
32 
34 {
35  init(filterSize,numDimensions);
36 }
37 
39 {
40  //Zero this instance
41  this->filterSize = 0;
42  this->inputSampleCounter = 0;
43 
44  //Copy the settings from the rhs instance
45  *this = rhs;
46 }
47 
49 
50 }
51 
53  if(this!=&rhs){
54  //Clear this instance
55  this->filterSize = 0;
56  this->inputSampleCounter = 0;
57  this->dataBuffer.clear();
58  this->weights = rhs.weights;
59 
60  //Copy from the rhs instance
61  if( rhs.initialized ){
62  this->init( rhs.filterSize, rhs.numInputDimensions );
63  this->dataBuffer = rhs.dataBuffer;
64  }
65 
66  //Copy the preprocessing base variables
68  }
69  return *this;
70 }
71 
73 
74  if( preProcessing == NULL ) return false;
75 
76  if( this->getId() == preProcessing->getId() ){
77 
78  //Call the equals operator
79  *this = *dynamic_cast<const WeightedAverageFilter*>(preProcessing);
80 
81  return true;
82  }
83 
84  errorLog << "deepCopyFrom(const PreProcessing *preProcessing) - PreProcessing Types Do Not Match!" << std::endl;
85 
86  return false;
87 }
88 
89 
91 
92  if( !initialized ){
93  errorLog << "process(const VectorFloat &inputVector) - The filter has not been initialized!" << std::endl;
94  return false;
95  }
96 
97  if( inputVector.size() != numInputDimensions ){
98  errorLog << "process(const VectorFloat &inputVector) - The size of the inputVector (" << inputVector.size() << ") does not match that of the filter (" << numInputDimensions << ")!" << std::endl;
99  return false;
100  }
101 
102  filter( inputVector );
103 
104  if( processedData.size() == numOutputDimensions ) return true;
105 
106  return false;
107 }
108 
110  if( initialized ) return init(filterSize,numInputDimensions);
111  return false;
112 }
113 
114 bool WeightedAverageFilter::save( std::fstream &file ) const{
115 
116  if( !file.is_open() ){
117  errorLog << "save(fstream &file) - The file is not open!" << std::endl;
118  return false;
119  }
120 
121  file << "GRT_WEIGHTED_AVERAGE_FILTER_FILE_V1.0" << std::endl;
122 
123  file << "NumInputDimensions: " << numInputDimensions << std::endl;
124  file << "NumOutputDimensions: " << numOutputDimensions << std::endl;
125  file << "FilterSize: " << filterSize << std::endl;
126 
127  return true;
128 }
129 
130 bool WeightedAverageFilter::load( std::fstream &file ){
131 
132  if( !file.is_open() ){
133  errorLog << "load(fstream &file) - The file is not open!" << std::endl;
134  return false;
135  }
136 
137  std::string word;
138 
139  //Load the header
140  file >> word;
141 
142  if( word != "GRT_WEIGHTED_AVERAGE_FILTER_FILE_V1.0" ){
143  errorLog << "load(fstream &file) - Invalid file format!" << std::endl;
144  return false;
145  }
146 
147  //Load the number of input dimensions
148  file >> word;
149  if( word != "NumInputDimensions:" ){
150  errorLog << "load(fstream &file) - Failed to read NumInputDimensions header!" << std::endl;
151  return false;
152  }
153  file >> numInputDimensions;
154 
155  //Load the number of output dimensions
156  file >> word;
157  if( word != "NumOutputDimensions:" ){
158  errorLog << "load(fstream &file) - Failed to read NumOutputDimensions header!" << std::endl;
159  return false;
160  }
161  file >> numOutputDimensions;
162 
163  //Load the filter factor
164  file >> word;
165  if( word != "FilterSize:" ){
166  errorLog << "load(fstream &file) - Failed to read FilterSize header!" << std::endl;
167  return false;
168  }
169  file >> filterSize;
170 
171  //Init the filter module to ensure everything is initialized correctly
172  return init(filterSize,numInputDimensions);
173 }
174 
175 bool WeightedAverageFilter::init(const UINT filterSize,const UINT numDimensions){
176 
177  //Cleanup the old memory
178  initialized = false;
179  inputSampleCounter = 0;
180 
181  if( filterSize == 0 ){
182  errorLog << "init(UINT filterSize,UINT numDimensions) - Filter size can not be zero!" << std::endl;
183  return false;
184  }
185 
186  if( numDimensions == 0 ){
187  errorLog << "init(UINT filterSize,UINT numDimensions) - The number of dimensions must be greater than zero!" << std::endl;
188  return false;
189  }
190 
191  //Resize the filter
192  this->filterSize = filterSize;
193  this->numInputDimensions = numDimensions;
194  this->numOutputDimensions = numDimensions;
195  processedData.clear();
196  weights.clear();
197  processedData.resize(numDimensions,0);
198  weights.resize(filterSize);
199  initialized = dataBuffer.resize( filterSize, VectorFloat(numInputDimensions,0) );
200 
201  const Float norm = 1.0 / filterSize;
202  for(UINT i=0; i<filterSize; i++){
203  weights[i] = (i+1)*norm;
204  }
205 
206  if( !initialized ){
207  errorLog << "init(UINT filterSize,UINT numDimensions) - Failed to resize dataBuffer!" << std::endl;
208  }
209 
210  return initialized;
211 }
212 
213 Float WeightedAverageFilter::filter(const Float x){
214 
215  //If the filter has not been initialised then return 0, otherwise filter x and return y
216  if( !initialized ){
217  errorLog << "filter(const Float x) - The filter has not been initialized!" << std::endl;
218  return 0;
219  }
220 
221  VectorFloat y = filter(VectorFloat(1,x));
222 
223  if( y.size() == 0 ) return 0;
224  return y[0];
225 }
226 
228 
229  //If the filter has not been initialised then return 0, otherwise filter x and return y
230  if( !initialized ){
231  errorLog << "filter(const VectorFloat &x) - The filter has not been initialized!" << std::endl;
232  return VectorFloat();
233  }
234 
235  if( x.size() != numInputDimensions ){
236  errorLog << "filter(const VectorFloat &x) - The size of the input vector (" << x.size() << ") does not match that of the number of dimensions of the filter (" << numInputDimensions << ")!" << std::endl;
237  return VectorFloat();
238  }
239 
241 
242  //Add the new value to the buffer
243  dataBuffer.push_back( x );
244 
245  Float weightSum = 0;
246  for(unsigned int j=0; j<numInputDimensions; j++){
247  processedData[j] = 0;
248  weightSum = 0;
249  for(unsigned int i=0; i<inputSampleCounter; i++) {
250  processedData[j] += dataBuffer[i][j] * weights[i];
251  weightSum += weights[i];
252  }
253  if( weightSum != 0.0 ) processedData[j] /= weightSum;
254  }
255 
256  return processedData;
257 }
258 
260 
261 VectorFloat WeightedAverageFilter::getFilteredData() const { return processedData; }
262 
263 GRT_END_NAMESPACE
bool push_back(const T &value)
std::string getId() const
Definition: GRTBase.cpp:85
UINT inputSampleCounter
A counter to keep track of the number of input samples.
static std::string getId()
virtual bool resize(const unsigned int size)
Definition: Vector.h:133
WeightedAverageFilter & operator=(const WeightedAverageFilter &rhs)
CircularBuffer< VectorFloat > dataBuffer
A buffer to store the previous N values, N = filterSize.
virtual bool deepCopyFrom(const PreProcessing *preProcessing)
The WeightedAverageFilter implements a weighted average filter that gives a larger weight to more rec...
virtual bool process(const VectorFloat &inputVector)
virtual bool save(std::fstream &file) const
UINT filterSize
The size of the filter.
Float filter(const Float x)
bool copyBaseVariables(const PreProcessing *preProcessingModule)
WeightedAverageFilter(const UINT filterSize=5, const UINT numDimensions=1)
VectorFloat getFilteredData() const
virtual bool load(std::fstream &file)
VectorFloat weights
Stores the weights for each sample in the buffer, the size of this vector will match the filterSize...
bool resize(const unsigned int newBufferSize)