CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
ConfigFile.h
Go to the documentation of this file.
1 // ConfigFile.h
2 // Class for reading named values from configuration files
3 // Richard J. Wagner v2.1 24 May 2004 wagnerr@umich.edu
4 // Copyright (c) 2004 Richard J. Wagner
5 //
6 // Permission is hereby granted, free of charge, to any person obtaining a copy
7 // of this software and associated documentation files (the "Software"), to
8 // deal in the Software without restriction, including without limitation the
9 // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
10 // sell copies of the Software, and to permit persons to whom the Software is
11 // furnished to do so, subject to the following conditions:
12 //
13 // The above copyright notice and this permission notice shall be included in
14 // all copies or substantial portions of the Software.
15 //
16 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19 // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21 // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
22 // IN THE SOFTWARE.
23 
24 // Typical usage
25 // -------------
26 //
27 // Given a configuration file "settings.inp":
28 // atoms = 25
29 // length = 8.0 # nanometers
30 // name = Reece Surcher
31 //
32 // Named values are read in various ways, with or without default values:
33 // ConfigFile config( "settings.inp" );
34 // int atoms = config.read<int>( "atoms" );
35 // double length = config.read( "length", 10.0 );
36 // string author, title;
37 // config.readInto( author, "name" );
38 // config.readInto( title, "title", std::string("Untitled") );
39 //
40 // See file example.cpp for more examples.
41 
42 #ifndef CONFIGFILE_H
43 #define CONFIGFILE_H
44 
45 #include <string>
46 #include <map>
47 #include <iostream>
48 #include <fstream>
49 #include <sstream>
50 #include <vector>
51 
52 class ConfigFile {
53 // Data
54 protected:
55  std::string myDelimiter; // separator between key and value
56  std::string myComment; // separator between value and comments
57  std::string mySentry; // optional std::string to signal end of file
58  std::map<std::string,std::string> myContents; // extracted keys and values
59 
60  typedef std::map<std::string,std::string>::iterator mapi;
61  typedef std::map<std::string,std::string>::const_iterator mapci;
62 
63 // Methods
64 public:
65  ConfigFile( std::string filename,
66  std::string delimiter = "=",
67  std::string comment = "#",
68  std::string sentry = "EndConfigFile" );
69  ConfigFile();
70 
71  // Search for key and read value or optional default value
72  template<class T> T read( const std::string& key ) const; // call as read<T>
73  template<class T> T read( const std::string& key, const T& value ) const;
74  template<class T> bool readInto( T& var, const std::string& key ) const;
75  template<class T> bool readInto( T& var, const std::string& key, const T& value ) const;
76 
77 // template<class T> std::vector<T> readvec( const std::string& key ) const;
78 
79  // Modify keys and values
80  template<class T> void add( std::string key, const T& value );
81  void remove( const std::string& key );
82 
83  // Check whether key exists in configuration
84  bool keyExists( const std::string& key ) const;
85 
86  // Check or change configuration syntax
87  std::string getDelimiter() const { return myDelimiter; }
88  std::string getComment() const { return myComment; }
89  std::string getSentry() const { return mySentry; }
90  std::string setDelimiter( const std::string& s )
91  { std::string old = myDelimiter; myDelimiter = s; return old; }
92  std::string setComment( const std::string& s )
93  { std::string old = myComment; myComment = s; return old; }
94 
95  // Write or read configuration
96  friend std::ostream& operator<<( std::ostream& os, const ConfigFile& cf );
97  friend std::istream& operator>>( std::istream& is, ConfigFile& cf );
98 
99 protected:
100  template<class T> static std::string T_as_string( const T& t );
101  template<class T> static T string_as_T( const std::string& s );
102  static void trim( std::string& s );
103 
104 
105 // Exception types
106 public:
107  struct file_not_found {
108  std::string filename;
109  file_not_found( const std::string& filename_ = std::string() )
110  : filename(filename_) {} };
111  struct key_not_found { // thrown only by T read(key) variant of read()
112  std::string key;
113  key_not_found( const std::string& key_ = std::string() )
114  : key(key_) {} };
115 };
116 
117 
118 /* static */
119 template<class T>
120 std::string ConfigFile::T_as_string( const T& t )
121 {
122  // Convert from a T to a std::string
123  // Type T must support << operator
124  std::ostringstream ost;
125  ost << t;
126  return ost.str();
127 }
128 
129 
130 /* static */
131 template<class T>
132 T ConfigFile::string_as_T( const std::string& s )
133 {
134  // Convert from a std::string to a T
135  // Type T must support >> operator
136  T t;
137  std::istringstream ist(s);
138  ist >> t;
139  return t;
140 }
141 
142 
143 /* static */
144 template<>
145 inline std::string ConfigFile::string_as_T<std::string>( const std::string& s )
146 {
147  // Convert from a std::string to a std::string
148  // In other words, do nothing
149  return s;
150 }
151 
152 
153 /* static */
154 template<>
155 inline bool ConfigFile::string_as_T<bool>( const std::string& s )
156 {
157  // Convert from a std::string to a bool
158  // Interpret "false", "F", "no", "n", "0" as false
159  // Interpret "true", "T", "yes", "y", "1", "-1", or anything else as true
160  bool b = true;
161  std::string sup = s;
162  for( std::string::iterator p = sup.begin(); p != sup.end(); ++p )
163  *p = toupper(*p); // make std::string all caps
164  if( sup==std::string("FALSE") || sup==std::string("F") ||
165  sup==std::string("NO") || sup==std::string("N") ||
166  sup==std::string("0") || sup==std::string("NONE") )
167  b = false;
168  return b;
169 }
170 
171 
172 template<class T>
173 T ConfigFile::read( const std::string& key ) const
174 {
175  // Read the value corresponding to key
176  mapci p = myContents.find(key);
177  if( p == myContents.end() ) throw key_not_found(key);
178  return string_as_T<T>( p->second );
179 }
180 
181 
182 template<class T>
183 T ConfigFile::read( const std::string& key, const T& value ) const
184 {
185  // Return the value corresponding to key or given default value
186  // if key is not found
187  mapci p = myContents.find(key);
188  if( p == myContents.end() ) return value;
189  return string_as_T<T>( p->second );
190 }
191 
192 // CTA -------------------------------------------------------------------
193 //template<class T>
194 //std::vector<T> ConfigFile::readvec( const std::string& key ) const
195 //{
196 // std::vector<int> t;
197 // t.push_back(0);
198 // t.push_back(3);
199 // return t;
200 //}
201 // CTA -------------------------------------------------------------------
202 
203 template<class T>
204 bool ConfigFile::readInto( T& var, const std::string& key ) const
205 {
206  // Get the value corresponding to key and store in var
207  // Return true if key is found
208  // Otherwise leave var untouched
209  mapci p = myContents.find(key);
210  bool found = ( p != myContents.end() );
211  if( found ) var = string_as_T<T>( p->second );
212  return found;
213 }
214 
215 
216 template<class T>
217 bool ConfigFile::readInto( T& var, const std::string& key, const T& value ) const
218 {
219  // Get the value corresponding to key and store in var
220  // Return true if key is found
221  // Otherwise set var to given default
222  mapci p = myContents.find(key);
223  bool found = ( p != myContents.end() );
224  if( found )
225  var = string_as_T<T>( p->second );
226  else
227  var = value;
228  return found;
229 }
230 
231 
232 template<class T>
233 void ConfigFile::add( std::string key, const T& value )
234 {
235  // Add a key with given value
236  std::string v = T_as_string( value );
237  trim(key);
238  trim(v);
239  myContents[key] = v;
240  return;
241 }
242 
243 #endif // CONFIGFILE_H
244 
245 // Release notes:
246 // v1.0 21 May 1999
247 // + First release
248 // + Template read() access only through non-member readConfigFile()
249 // + ConfigurationFileBool is only built-in helper class
250 //
251 // v2.0 3 May 2002
252 // + Shortened name from ConfigurationFile to ConfigFile
253 // + Implemented template member functions
254 // + Changed default comment separator from % to #
255 // + Enabled reading of multiple-line values
256 //
257 // v2.1 24 May 2004
258 // + Made template specializations inline to avoid compiler-dependent linkage
259 // + Allowed comments within multiple-line values
260 // + Enabled blank line termination for multiple-line values
261 // + Added optional sentry to detect end of configuration file
262 // + Rewrote messy trimWhitespace() function as elegant trim()
std::string setComment(const std::string &s)
Definition: ConfigFile.h:92
T read(const std::string &key) const
Definition: ConfigFile.h:173
void add(std::string key, const T &value)
Definition: ConfigFile.h:233
static void trim(std::string &s)
Definition: ConfigFile.cc:45
friend std::istream & operator>>(std::istream &is, ConfigFile &cf)
Definition: ConfigFile.cc:68
std::map< std::string, std::string > myContents
Definition: ConfigFile.h:58
std::string getSentry() const
Definition: ConfigFile.h:89
static T string_as_T(const std::string &s)
Definition: ConfigFile.h:132
friend std::ostream & operator<<(std::ostream &os, const ConfigFile &cf)
Definition: ConfigFile.cc:54
std::string getDelimiter() const
Definition: ConfigFile.h:87
static std::string T_as_string(const T &t)
Definition: ConfigFile.h:120
bool keyExists(const std::string &key) const
Definition: ConfigFile.cc:36
std::map< std::string, std::string >::const_iterator mapci
Definition: ConfigFile.h:61
std::string getComment() const
Definition: ConfigFile.h:88
std::string mySentry
Definition: ConfigFile.h:57
std::string myComment
Definition: ConfigFile.h:56
double b
Definition: hdecay.h:120
std::map< std::string, std::string >::iterator mapi
Definition: ConfigFile.h:60
list key
Definition: combine.py:13
tuple filename
Definition: lut2db_cfg.py:20
std::string setDelimiter(const std::string &s)
Definition: ConfigFile.h:90
string s
Definition: asciidump.py:422
long double T
std::string myDelimiter
Definition: ConfigFile.h:55
bool readInto(T &var, const std::string &key) const
Definition: ConfigFile.h:204
mathSSE::Vec4< T > v
#define comment(par)
Definition: vmac.h:162