1 // This is mul/mbl/mbl_parse_tuple.h
2 #ifndef mbl_parse_tuple_h_
3 #define mbl_parse_tuple_h_
4 //:
5 // \file
6 // \author Ian Scott
7 // \date 6-Feb-2008
8 // \brief Convenience function a tuple of PODs from a config file.
9
10 #include <iostream>
11 #include <istream>
12 #include <sstream>
13 #ifdef _MSC_VER
14 # include <vcl_msvc_warnings.h>
15 #endif
16 #include <mbl/mbl_exception.h>
17
18 //: Read a 2-tuple of PODs from a config file.
19 // This function will read through a stream, and store the text found to a string.
20 // The function reads 2 elements. If there was an opening brace it will also consume the closing brace.
21 // Other conditions will cause an exception to be thrown, and the stream's fail bit to be set
22 //
23 // \throws mbl_exception_parse_error if unrecoverable parse error.
24 //
25 // Example:
26 // \code
27 // std::istringstream ss("{ 1.0 4 }");
28 // float a;
29 // int b;
30 // mbl_parse_tuple(ss, a, b)
31 // \endcode
32 //
33 template <class T, class U>
mbl_parse_tuple(std::istream & afs,T & a,U & b)34 inline void mbl_parse_tuple(std::istream &afs, T& a, U& b)
35 {
36 if (!afs) return;
37 char brace1, brace2;
38 afs >> std::ws >> brace1;
39 if (afs.eof())
40 throw mbl_exception_parse_error("mbl_parse_tuple failed unexpected eof");
41 if ( brace1 == '{')
42 {
43 afs >> std::ws >> a >> std::ws >> b >> std::ws >> brace2;
44 if (!afs)
45 throw mbl_exception_parse_error("mbl_parse_tuple failed with stream error");
46 if (brace2 != '}')
47 {
48 afs.putback(brace2);
49 afs.clear(std::ios::failbit); // Set a recoverable IO error on stream
50
51 throw mbl_exception_parse_error("mbl_parse_tuple failed to find closing brace");
52 }
53 }
54 else
55 {
56 afs.putback(brace1);
57 afs >> std::ws >> a >> std::ws >> b;
58 if (!afs)
59 throw mbl_exception_parse_error("mbl_parse_tuple failed with stream error");
60 }
61 }
62
63 //: Read a 3-tuple of PODs from a config file.
64 // This function will read through a stream, and store the text found to a string.
65 // The function reads 3 elements. If there was an opening brace it will also consume the closing brace.
66 // Other conditions will cause an exception to be thrown, and the stream's fail bit to be set
67 //
68 // \throws mbl_exception_parse_error if unrecoverable parse error.
69 //
70 // \verbatim
71 // Example:
72 // std::istringstream ss("{ 1.0 -5 4 }");
73 // float a;
74 // int b;
75 // unsigned c;
76 // mbl_parse_tuple(ss, a, b, c)
77 // \endverbatim
78 template <class T, class U, class V>
mbl_parse_tuple(std::istream & afs,T & a,U & b,V & c)79 inline void mbl_parse_tuple(std::istream &afs, T& a, U& b, V& c)
80 {
81 if (!afs) return;
82 char brace1, brace2;
83 afs >> std::ws >> brace1;
84 if (afs.eof())
85 throw mbl_exception_parse_error("mbl_parse_tuple failed unexpected eof");
86 if ( brace1 == '{')
87 {
88 afs >> std::ws >> a >> std::ws >> b >> std::ws >> c >> std::ws >> brace2;
89 if (!afs)
90 throw mbl_exception_parse_error("mbl_parse_tuple failed with stream error");
91 if (brace2 != '}')
92 {
93 afs.putback(brace2);
94 afs.clear(std::ios::failbit); // Set a recoverable IO error on stream
95
96 throw mbl_exception_parse_error("mbl_parse_tuple failed to find closing brace");
97 }
98 }
99 else
100 {
101 afs.putback(brace1);
102 afs >> std::ws >> a >> std::ws >> b >> std::ws >> c;
103 if (!afs)
104 throw mbl_exception_parse_error("mbl_parse_tuple failed with stream error");
105 }
106 }
107
108
109 //: Read a 4-tuple of PODs from a config file.
110 // This function will read through a stream, and store the text found to a string.
111 // The function reads 4 elements. If there was an opening brace it will also consume the closing brace.
112 // Other conditions will cause an exception to be thrown, and the stream's fail bit to be set
113 //
114 // \throws mbl_exception_parse_error if unrecoverable parse error.
115 //
116 // \verbatim
117 // Example:
118 // std::istringstream ss("{ 1.0 -5 4 a }");
119 // float a;
120 // int b;
121 // unsigned c;
122 // char d;
123 // mbl_parse_tuple(ss, a, b, c, d)
124 // \endverbatim
125 template <class T, class U, class V, class W>
mbl_parse_tuple(std::istream & afs,T & a,U & b,V & c,W & d)126 inline void mbl_parse_tuple(std::istream &afs, T& a, U& b, V& c, W& d)
127 {
128 if (!afs) return;
129 char brace1, brace2;
130 afs >> std::ws >> brace1;
131 if (afs.eof())
132 throw mbl_exception_parse_error("mbl_parse_tuple failed unexpected eof");
133 if ( brace1 == '{')
134 {
135 afs >> std::ws >> a >> std::ws >> b >> std::ws >> c >> std::ws >> d >> std::ws >> brace2;
136 if (!afs)
137 throw mbl_exception_parse_error("mbl_parse_tuple failed with stream error");
138 if (brace2 != '}')
139 {
140 afs.putback(brace2);
141 afs.clear(std::ios::failbit); // Set a recoverable IO error on stream
142
143 throw mbl_exception_parse_error("mbl_parse_tuple failed to find closing brace");
144 }
145 }
146 else
147 {
148 afs.putback(brace1);
149 afs >> std::ws >> a >> std::ws >> b >> std::ws >> c >> std::ws >> d;
150 if (!afs)
151 throw mbl_exception_parse_error("mbl_parse_tuple failed with stream error");
152 }
153 }
154
155
156 //: Read a 5-tuple of PODs from a config file.
157 // This function will read through a stream, and store the text found to a string.
158 // The function reads 5 elements. If there was an opening brace it will also consume the closing brace.
159 // Other conditions will cause an exception to be thrown, and the stream's fail bit to be set
160 //
161 // \throws mbl_exception_parse_error if unrecoverable parse error.
162 //
163 // \verbatim
164 // Example:
165 // std::istringstream ss("{ 1.0 -5 4 k l }");
166 // float a;
167 // int b;
168 // unsigned c;
169 // char d, e;
170 // mbl_parse_tuple(ss, a, b, c, d, e)
171 // \endverbatim
172 template <class T, class U, class V, class W, class X>
mbl_parse_tuple(std::istream & afs,T & a,U & b,V & c,W & d,X & e)173 inline void mbl_parse_tuple(std::istream &afs, T& a, U& b, V& c, W& d, X& e)
174 {
175 if (!afs) return;
176 char brace1, brace2;
177 afs >> std::ws >> brace1;
178 if (afs.eof())
179 throw mbl_exception_parse_error("mbl_parse_tuple failed unexpected eof");
180 if ( brace1 == '{')
181 {
182 afs >> std::ws >> a >> std::ws >> b >> std::ws >> c >> std::ws >> d >> std::ws >> e >> std::ws >> brace2;
183 if (!afs)
184 throw mbl_exception_parse_error("mbl_parse_tuple failed with stream error");
185 if (brace2 != '}')
186 {
187 afs.putback(brace2);
188 afs.clear(std::ios::failbit); // Set a recoverable IO error on stream
189
190 throw mbl_exception_parse_error("mbl_parse_tuple failed to find closing brace");
191 }
192 }
193 else
194 {
195 afs.putback(brace1);
196 afs >> std::ws >> a >> std::ws >> b >> std::ws >> c >> std::ws >> d >> std::ws >> e;
197 if (!afs)
198 throw mbl_exception_parse_error("mbl_parse_tuple failed with stream error");
199 }
200 }
201
202
203 //: Read a 6-tuple of PODs from a config file.
204 // This function will read through a stream, and store the text found to a string.
205 // The function reads 6 elements. If there was an opening brace it will also consume the closing brace.
206 // Other conditions will cause an exception to be thrown, and the stream's fail bit to be set
207 //
208 // \throws mbl_exception_parse_error if unrecoverable parse error.
209 //
210 // \verbatim
211 // Example:
212 // std::istringstream ss("{ 1.0 -3.4 -5 4 k l }");
213 // float a;
214 // double b;
215 // int c;
216 // unsigned d;
217 // char e, f;
218 // mbl_parse_tuple(ss, a, b, c, d, e, f)
219 // \endverbatim
220 template <class T, class U, class V, class W, class X, class Y>
mbl_parse_tuple(std::istream & afs,T & a,U & b,V & c,W & d,X & e,Y & f)221 inline void mbl_parse_tuple(std::istream &afs, T& a, U& b, V& c, W& d, X& e, Y& f)
222 {
223 if (!afs) return;
224 char brace1, brace2;
225 afs >> std::ws >> brace1;
226 if (afs.eof())
227 throw mbl_exception_parse_error("mbl_parse_tuple failed unexpected eof");
228 if ( brace1 == '{')
229 {
230 afs >> std::ws >> a >> std::ws >> b >> std::ws >> c >> std::ws >> d >> std::ws >>
231 e >> std::ws >> f >> std::ws >> brace2;
232 if (!afs)
233 throw mbl_exception_parse_error("mbl_parse_tuple failed with stream error");
234 if (brace2 != '}')
235 {
236 afs.putback(brace2);
237 afs.clear(std::ios::failbit); // Set a recoverable IO error on stream
238
239 throw mbl_exception_parse_error("mbl_parse_tuple failed to find closing brace");
240 }
241 }
242 else
243 {
244 afs.putback(brace1);
245 afs >> std::ws >> a >> std::ws >> b >> std::ws >> c >> std::ws >> d >>
246 std::ws >> e >> std::ws >> f;
247 if (!afs)
248 throw mbl_exception_parse_error("mbl_parse_tuple failed with stream error");
249 }
250 }
251 #endif // mbl_parse_tuple_h_
252