noisegenerator.h

Go to the documentation of this file.
00001 /*************************************************************************** 00002 * Copyright (C) 2005 by Robot Group Leipzig * 00003 * martius@informatik.uni-leipzig.de * 00004 * fhesse@informatik.uni-leipzig.de * 00005 * der@informatik.uni-leipzig.de * 00006 * * 00007 * This program is free software; you can redistribute it and/or modify * 00008 * it under the terms of the GNU General Public License as published by * 00009 * the Free Software Foundation; either version 2 of the License, or * 00010 * (at your option) any later version. * 00011 * * 00012 * This program is distributed in the hope that it will be useful, * 00013 * but WITHOUT ANY WARRANTY; without even the implied warranty of * 00014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * 00015 * GNU General Public License for more details. * 00016 * * 00017 * You should have received a copy of the GNU General Public License * 00018 * along with this program; if not, write to the * 00019 * Free Software Foundation, Inc., * 00020 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * 00021 * * 00022 * $Log: noisegenerator.h,v $ 00023 * Revision 1.15 2006/12/11 14:00:09 martius 00024 * colornoise is more colorful (tau = 0.5) 00025 * variance for colornoise is invariant of tau now 00026 * 00027 * Revision 1.14 2006/10/09 12:37:54 martius 00028 * variance was wrong since it was sigma (std deviation) 00029 * 00030 * Revision 1.13 2006/08/04 15:16:13 martius 00031 * documentation 00032 * 00033 * Revision 1.12 2006/07/14 12:23:59 martius 00034 * selforg becomes HEAD 00035 * 00036 * Revision 1.10.6.1 2005/11/22 14:55:21 martius 00037 * added math.h 00038 * 00039 * Revision 1.10 2005/10/06 17:07:16 martius 00040 * removed MAXINT 00041 * 00042 * Revision 1.9 2005/09/11 11:20:21 martius 00043 * virtual destructors 00044 * 00045 * Revision 1.8 2005/08/22 20:32:29 martius 00046 * sine noise has phaseShift 00047 * 00048 * Revision 1.7 2005/08/06 20:47:54 martius 00049 * Commented 00050 * 00051 * Revision 1.6 2005/08/03 20:31:40 martius 00052 * sinenoise 00053 * no random initialisation anymore 00054 * 00055 * Revision 1.5 2005/07/21 15:11:19 martius 00056 * normalised noise strength for colored noise 00057 * 00058 * Revision 1.4 2005/07/14 16:07:12 fhesse 00059 * cmath included 00060 * 00061 * Revision 1.3 2005/07/06 16:05:34 martius 00062 * noise generator is splitted into sub classes with a common interface 00063 * 00064 * Revision 1.2 2005/06/15 16:04:56 martius 00065 * de-templatified 00066 * * 00067 ***************************************************************************/ 00068 #ifndef __NOISEGENERATOR_H 00069 #define __NOISEGENERATOR_H 00070 00071 #include <stdlib.h> 00072 #include <time.h> 00073 #include <math.h> 00074 00075 /** Interface and basic class for noise generator. 00076 It is suitable for single noise channels but also multidimensional noise. 00077 */ 00078 class NoiseGenerator{ 00079 public: 00080 NoiseGenerator() { 00081 dimension=0; 00082 }; 00083 00084 virtual ~NoiseGenerator(){} 00085 00086 /** initialization with the the given dimension for multidimensional noise 00087 @see add() 00088 */ 00089 virtual void init(unsigned int dimension) { 00090 this->dimension = dimension; 00091 }; 00092 00093 /** generate somehow distributed random number parameterized with min and max. 00094 valid only for ONE random number, use \ref add() for 00095 adding this kind of noise to several channels 00096 */ 00097 virtual double generate(double min, double max) = 0; 00098 00099 /** adds multidimensional noise to the value field. 00100 Generic implementation calls generate for each channel. 00101 Overload this if you need different behavior. 00102 @param value field where noise is added. Must have length dimension (\ref init()) 00103 @param p1 first parameter for random number distribution 00104 @param p2 second parameter for random number distribution 00105 */ 00106 virtual void add(double *value, double p1, double p2){ 00107 for (unsigned int i = 0; i < dimension; i++){ 00108 value[i]+=generate(p1,p2); 00109 } 00110 } 00111 00112 protected: 00113 //generates white (no averaging) uniformly distributed random number between "min" and "max" 00114 double uniform(double min=-0.1, double max=0.1){ 00115 return( (double(rand())/RAND_MAX)*(max-min)+min); 00116 } 00117 unsigned int dimension; 00118 }; 00119 00120 /// generates white (no averaging) uniformly distributed random number between "min" and "max" 00121 class WhiteUniformNoise : public NoiseGenerator{ 00122 public: 00123 WhiteUniformNoise(){} 00124 virtual ~WhiteUniformNoise(){} 00125 virtual double generate(double min, double max) { 00126 return uniform(min,max); 00127 }; 00128 }; 00129 00130 /// generates white and normal distributed random numbers. p1: mean, p2: standard deviation 00131 class WhiteNormalNoise : public NoiseGenerator{ 00132 public: 00133 WhiteNormalNoise(){} 00134 virtual ~WhiteNormalNoise(){} 00135 virtual double generate(double mean, double stddev) { 00136 double x1=uniform(0, 1); 00137 double x2=uniform(0, 1); 00138 return( (sqrt(-2*log(x1)) *cos(2*M_PI*x2)) * stddev + mean) ; 00139 }; 00140 }; 00141 00142 /// generated colored noise. This is obtained by using time average of uniform distributed noise. 00143 class ColorUniformNoise : public NoiseGenerator{ 00144 public: 00145 /** @param tau time averaging factor (1/window) 00146 (1: smoothing (white) 0.1: strong color, 0 no noise anymore 00147 */ 00148 ColorUniformNoise(double tau=0.05) 00149 : tau(tau){ 00150 sqrttau = sqrt(tau); 00151 mean1channel=0.0; 00152 mean=0; 00153 } 00154 virtual ~ColorUniformNoise(){ if(mean) free(mean);} 00155 virtual void init(unsigned int dimension){ 00156 NoiseGenerator::init(dimension); 00157 mean = (double*)malloc(sizeof(double) * dimension); 00158 for (unsigned int i=0; i<dimension; i++){ 00159 mean[i]=0.0; 00160 } 00161 } 00162 00163 virtual double generate(double min, double max) { 00164 mean1channel+= sqrttau * uniform(min, max) - tau * mean1channel; 00165 return(mean1channel); 00166 } 00167 00168 /** adds multidimensional noise to the value field. 00169 @param value field where noise is added. Must have length dimension (\ref init()) 00170 @param min lower bound of interval 00171 @param max upper bound of interval 00172 */ 00173 virtual void add(double *value, double min, double max){ 00174 for (unsigned int i = 0; i < dimension; i++){ 00175 mean[i]+= sqrttau * uniform(min, max) - tau * mean[i]; 00176 value[i]+=mean[i]; 00177 } 00178 } 00179 00180 protected: 00181 double tau; // smoothing paramter 00182 double sqrttau; // square root of smoothing parameter 00183 double* mean; 00184 double mean1channel; 00185 }; 00186 00187 /// like ColorUniformNoise but averaging over normal distributed noise instead. 00188 class ColorNormalNoise : public WhiteNormalNoise{ 00189 public: 00190 ColorNormalNoise(double tau=0.05) 00191 : tau(tau){ 00192 sqrttau = sqrt(tau); 00193 mean = 0; 00194 mean1channel=0.0; 00195 } 00196 00197 virtual ~ColorNormalNoise(){if(mean) free(mean);} 00198 00199 virtual void init(unsigned int dimension){ 00200 WhiteNormalNoise::init(dimension); 00201 mean = (double*)malloc(sizeof(double) * dimension); 00202 for (unsigned int i=0; i<dimension; i++){ 00203 mean[i]=0.0; 00204 } 00205 } 00206 00207 virtual double generate(double stddev, double meanvalue) { 00208 mean1channel += sqrttau * WhiteNormalNoise::generate(stddev, meanvalue) - tau*mean1channel; 00209 return(mean1channel); 00210 } 00211 00212 /** adds multidimensional noise to the value field. 00213 @param value field where noise is added. Must have length dimension (\ref init()) 00214 @param stddev stddev of normal distribution 00215 @param meanvalue mean value of normal distribution 00216 */ 00217 virtual void add(double *value, double stddev, double meanvalue){ 00218 for (unsigned int i = 0; i < dimension; i++){ 00219 mean[i]+=sqrttau * WhiteNormalNoise::generate(stddev*factor, meanvalue) - tau*mean[i]; 00220 value[i]+=mean[i]; 00221 } 00222 } 00223 00224 protected: 00225 double tau; // smoothing paramter 00226 double sqrttau; // square root of smoothing parameter 00227 double* mean; 00228 double mean1channel; 00229 double factor; 00230 }; 00231 00232 /// Sine wave noise. Produces a 90 degree phase shifted sine wave or white noise 00233 class SineWhiteNoise : public NoiseGenerator{ 00234 public: 00235 /** @param omega anglerate 00236 @param amplitude amplitude of the sine wave in respect to the noise strength 00237 @param phaseShift phase shift between channels in rad 00238 @param channels number of channel for sine noise (and the rest get white noise) 00239 */ 00240 SineWhiteNoise(double omega, double amplitude, double phaseShift = M_PI/2, 00241 unsigned int channels = 0xFFFF) 00242 : omega(omega), amplitude(amplitude) 00243 , channels(channels), phaseShift(phaseShift){ 00244 t=0; 00245 } 00246 00247 virtual ~SineWhiteNoise(){} 00248 00249 virtual double generate(double min, double max) { 00250 t ++; 00251 return uniform(min, max) + sin(t*omega)*amplitude*(max-min); 00252 } 00253 00254 /** adds multidimensional noise to the value field. 00255 @param value field where noise is added. Must have length dimension (\ref init()) 00256 @param min lower bound of interval 00257 @param max upper bound of interval 00258 */ 00259 virtual void add(double *value, double min, double max){ 00260 00261 for (unsigned int i = 0; i < dimension; i++){ 00262 if(i < channels) 00263 value[i]+=sin(t*omega+i*phaseShift)*amplitude*(max-min); 00264 value[i]+=uniform(min, max); 00265 } 00266 t ++; 00267 } 00268 void setOmega(double omega){ 00269 this->omega=omega; 00270 } 00271 void setPhaseShift(double phaseShift){ 00272 this->phaseShift=phaseShift; 00273 } 00274 00275 protected: 00276 long int t; // time 00277 double omega; // angle velocity 00278 double amplitude; // factor for noise strength 00279 unsigned int channels; // number of channels with sine 00280 double phaseShift; // phase shift 00281 00282 }; 00283 00284 00285 #endif 00286

Generated on Tue Jan 16 02:14:36 2007 for Robotsystem of the Robot Group Leipzig by doxygen 1.3.8