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 * guettler@informatik.uni-leipzig.de * 00007 * * 00008 * This program is free software; you can redistribute it and/or modify * 00009 * it under the terms of the GNU General Public License as published by * 00010 * the Free Software Foundation; either version 2 of the License, or * 00011 * (at your option) any later version. * 00012 * * 00013 * This program is distributed in the hope that it will be useful, * 00014 * but WITHOUT ANY WARRANTY; without even the implied warranty of * 00015 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * 00016 * GNU General Public License for more details. * 00017 * * 00018 * You should have received a copy of the GNU General Public License * 00019 * along with this program; if not, write to the * 00020 * Free Software Foundation, Inc., * 00021 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * 00022 *************************************************************************** 00023 * * 00024 * DESCRIPTION * 00025 * * 00026 * $Log: configurable.h,v $ 00027 * Revision 1.8 2009/08/05 22:47:10 martius 00028 * added support for integer variables and 00029 * proper display for bool and int 00030 * 00031 * Revision 1.7 2009/08/05 08:36:22 guettler 00032 * added support for boolean variables 00033 * 00034 * Revision 1.6 2009/03/27 06:16:57 guettler 00035 * support for gcc 4.3 compatibility (has to be checked), StatisticTools moves from utils to statistictools 00036 * 00037 * Revision 1.5 2008/11/14 09:16:15 martius 00038 * small things 00039 * 00040 * Revision 1.4 2008/08/14 08:06:02 robot1 00041 * fixed compile bug 00042 * 00043 * Revision 1.3 2008/08/01 14:42:03 guettler 00044 * we try the trip to hell! make selforg AVR compatible...good luck (first changes) 00045 * 00046 * Revision 1.2 2008/04/29 07:41:40 guettler 00047 * added GPL and revision tag 00048 * 00049 * Revision 1.1 2008/04/29 07:39:54 guettler 00050 * interfaces moved to selforg/utils directory 00051 * 00052 * Revision 1.7 2008/04/11 14:12:30 martius 00053 * comments paramter in storeCfg 00054 * 00055 * Revision 1.6 2007/06/08 15:44:32 martius 00056 * termination string -> more robust parsing 00057 * 00058 * Revision 1.5 2007/03/26 13:13:47 martius 00059 * store and restore with params 00060 * 00061 * Revision 1.4 2007/01/24 14:38:35 martius 00062 * new implementation with a map from key to reference. 00063 * addParameter and addParameterDef are used for registration of a parameter 00064 * the old style is still supported 00065 * 00066 * Revision 1.3 2006/07/14 12:23:57 martius 00067 * selforg becomes HEAD 00068 * 00069 * Revision 1.1.2.7 2006/06/25 21:56:07 martius 00070 * configureable has name and revision 00071 * 00072 * Revision 1.1.2.6 2006/02/08 16:17:40 martius 00073 * no namespace using 00074 * 00075 * Revision 1.1.2.5 2006/01/18 16:48:10 martius 00076 * configurables can be stored and reloaded 00077 * 00078 * Revision 1.1.2.4 2006/01/18 10:45:32 martius 00079 * *** empty log message *** 00080 * 00081 * Revision 1.1.2.3 2006/01/18 10:44:49 martius 00082 * (re)storeCfg 00083 * 00084 * Revision 1.1.2.2 2006/01/16 17:40:13 martius 00085 * parsing works 00086 * 00087 * Revision 1.1.2.1 2006/01/16 17:27:17 martius 00088 * *** empty log message *** 00089 * 00090 * * 00091 ***************************************************************************/ 00092 #ifndef __CONFIGURABLE_H 00093 #define __CONFIGURABLE_H 00094 00095 #include <iostream> 00096 #include <cstdlib> 00097 00098 #include <list> 00099 #include <utility> 00100 #include <string> 00101 #include <map> 00102 #include "stl_adds.h" 00103 00104 /** 00105 Abstact class for configurable objects. Sort of Hashmap interface. Parameters are double values 00106 00107 The Configurator is a (planned) external tool that can be used for changing the values of configurable objects. 00108 00109 * Protocoll for Configurator: 00110 \code 00111 To Configurator (BNF notation): 00112 Conf := <Comp>* 00113 Comp := <CompName> <Pair>* 00114 CompName := [<string>][<int>]<newline> 00115 Pair := <alphanum>=<double><newline> 00116 \endcode 00117 the remaining tags are self explanatory 00118 00119 Example 00120 \code 00121 [Component name which can contain spaces and digits and .,- ][ID1] 00122 key1 = value1 00123 key2 = value2 00124 . 00125 . 00126 [Other Component name which can contain spaces and digits and .,- ][ID2] 00127 key3 = value3 00128 \endcode 00129 00130 Answer: (from Communicator to Simulation environment)\n 00131 1. On change of a parameter: 00132 \code 00133 [ID] key=newvalue 00134 \endcode 00135 or 00136 \code 00137 key=newvalue 00138 \endcode 00139 the latter one means that the parameter is changed in all components 00140 00141 2. Request of the description as defined above. 00142 \code 00143 #Something I don\'t care 00144 \endcode 00145 */ 00146 00147 class Configurable 00148 { 00149 public: 00150 00151 typedef std::string paramkey; 00152 typedef double paramval; 00153 typedef std::list<std::pair<paramkey, paramval> > paramlist; 00154 typedef std::map<paramkey, paramval*> parammap; 00155 00156 // params of type bool 00157 typedef bool parambool; 00158 typedef std::list<std::pair<paramkey, parambool> > paramboollist; 00159 typedef std::map<paramkey, parambool*> paramboolmap; 00160 00161 // params of type int 00162 typedef int paramint; 00163 typedef std::list<std::pair<paramkey, paramint> > paramintlist; 00164 typedef std::map<paramkey, paramint*> paramintmap; 00165 00166 /// nice predicate function for finding by ID 00167 struct matchId : public std::unary_function<Configurable*, bool> 00168 { 00169 matchId(int id) : 00170 id(id) 00171 { 00172 } 00173 int id; 00174 bool operator()(Configurable* c) 00175 { 00176 return c->id == id; 00177 } 00178 }; 00179 00180 Configurable() 00181 { 00182 id = rand(); 00183 } 00184 /// intialise with name and revision (use "$ID$") 00185 Configurable(const std::string& name, const std::string& revision) : 00186 name(name), revision(revision) 00187 { 00188 id = rand(); 00189 } 00190 00191 // Configurable(const Configurable& copy) 00192 // :id(copy.id), name(copy.name), revision(revision), 00193 // mapOfValues(mapOfValues), mapOfBoolean(mapOfBoolean), mapOfInteger(mapOfInteger) 00194 // { 00195 // } 00196 00197 00198 virtual ~Configurable() 00199 { 00200 } 00201 00202 /// return the id of the configurable objects, which is created by random on initialisation 00203 int getId() const { 00204 return id; 00205 } 00206 00207 /// return the name of the object 00208 virtual paramkey getName() const { 00209 return name; 00210 } 00211 00212 /// returns the revision of the object 00213 virtual paramkey getRevision() const { 00214 return revision; 00215 } 00216 00217 /// stes the name of the object 00218 virtual void setName(const paramkey& name){ 00219 this->name = name; 00220 } 00221 /// sets the revision Hint: { return "$ID$"; } 00222 virtual void setRevision(const paramkey& revision) { 00223 this->revision = revision; 00224 } 00225 00226 /** returns the value of the requested parameter 00227 or 0 (+ error message to stderr) if unknown. 00228 */ 00229 virtual paramval getParam(const paramkey& key) const; 00230 00231 /** sets the value of the given parameter 00232 or does nothing if unknown. 00233 */ 00234 virtual bool setParam(const paramkey& key, paramval val); 00235 00236 /** The list of all parameters with there value as allocated lists. 00237 Note that these are only parameters that are managed manually (with setParam, getParam) 00238 @see getAllParamNames() 00239 @return list of key-value pairs 00240 */ 00241 virtual paramlist getParamList() const { 00242 return paramlist(); // return an empty list 00243 } 00244 00245 /// returns all names that are configureable 00246 virtual std::list<paramkey> getAllParamNames(); 00247 00248 /** 00249 This is the new style for adding configurable parameters. Just call this function 00250 for each parameter and you are done. 00251 If you need to do some special treatment for setting (or getting) of the parameter 00252 you can handle this by overloading getParam and setParam 00253 */ 00254 virtual void addParameter(const paramkey& key, paramval* val) { 00255 mapOfValues[key] = val; 00256 } 00257 00258 /** 00259 See addParameter(const paramkey& key, paramval* val) but for bool values 00260 */ 00261 virtual void addParameter(const paramkey& key, parambool* val) { 00262 mapOfBoolean[key] = val; 00263 } 00264 00265 /** 00266 See addParameter(const paramkey& key, paramval* val) but for int values 00267 */ 00268 virtual void addParameter(const paramkey& key, paramint* val) { 00269 mapOfInteger[key] = val; 00270 } 00271 00272 /** 00273 This function is only provided for convenience. It does the same as addParameter but set the 00274 variable to the default value 00275 */ 00276 virtual void addParameterDef(const paramkey& key, paramval* val, paramval def){ 00277 *val = def; 00278 mapOfValues[key] = val; 00279 } 00280 00281 /** 00282 This function is only provided for convenience. It does the same as addParameter but set the 00283 variable to the default value 00284 */ 00285 virtual void addParameterDef(const paramkey& key, parambool* val, parambool def) 00286 { 00287 *val = def; 00288 mapOfBoolean[key] = val; 00289 } 00290 /** 00291 This function is only provided for convenience. It does the same as addParameter but set the 00292 variable to the default value 00293 */ 00294 virtual void addParameterDef(const paramkey& key, paramint* val, paramint def) 00295 { 00296 *val = def; 00297 mapOfInteger[key] = val; 00298 } 00299 00300 /** This is a utility function for inserting the filename and the revision number 00301 at the beginning of the given string buffer str and terminates it. 00302 @param str buffer (call by reference) 00303 that should have space for file+revision+2 characters 00304 @param file filename given by CVS i.e. $RCSfile: configurable.h,v $ 00305 @param revision revision number given by CVS i.e. $Revision: 1.8 $ 00306 */ 00307 static void insertCVSInfo(paramkey& str, const char* file, const char* revision); 00308 00309 /** stores the key values paires into the file : filenamestem.cfg 00310 including the comments given in the list 00311 */ 00312 virtual bool storeCfg(const char* filenamestem, const std::list<std::string>& comments = std::list<std::string>()); 00313 /** restores the key values paires from the file : filenamestem.cfg */ 00314 virtual bool restoreCfg(const char* filenamestem); 00315 void print(FILE* f, const char* prefix) const; 00316 void parse(FILE* f); 00317 00318 private: 00319 int id; 00320 paramkey name; 00321 paramkey revision; 00322 00323 parammap mapOfValues; 00324 paramboolmap mapOfBoolean; 00325 paramintmap mapOfInteger; 00326 }; 00327 00328 #endif // __CONFIGURABLE_H