CLHEP VERSION Reference Documentation
   
CLHEP Home Page     CLHEP Documentation     CLHEP Bug Reports

ZMinput.cc
Go to the documentation of this file.
1 #include "CLHEP/Vector/defs.h"
2 
3 #include <cctype>
4 #include <iostream>
5 
6 namespace {
7 
8 bool eatwhitespace ( std::istream & is ) {
9  // Will discard whitespace until it either encounters EOF or bad input
10  // (in which case it will return false) or it hits a non-whitespace.
11  // Will put that non whitespace character back so that after this routine
12  // returns true, is.get(c) should always work.
13  // If eatwhitespace returns false, is will always be in a fail or bad state.
14  char c;
15  bool avail = false; // avail stays false until we know there is a nonwhite
16  // character available.
17  while ( is.get(c) ) {
18  if ( !isspace(c) ) {
19  is.putback(c);
20  avail = true;
21  break;
22  }
23  }
24  return avail;
25 }
26 
27 void fouledup() {
28  std::cerr << "istream mysteriously lost a putback character!\n";
29 }
30 
31 
32 } // end of unnamed namespace
33 
34 
35 namespace CLHEP {
36 
37 void ZMinput3doubles ( std::istream & is, const char * type,
38  double & x, double & y, double & z ) {
39 
40 // Accepted formats are
41 // x y z
42 // x, y, z (each comma is optional, and whitespace ignored if comma present)
43 // ( x, y, z ) (commas optional)
44 
45  char c;
46  bool parenthesis = false;
47 
48  if ( !eatwhitespace(is) ) {
49  std::cerr << "istream ended before trying to input " << type << "\n";
50  return;
51  }
52 
53  if ( !is.get(c) ) { fouledup(); return; }
54  if ( c == '(' ) {
55  parenthesis = true;
56  if ( !eatwhitespace(is) ) {
57  std::cerr << "istream ended after ( trying to input " << type << "\n";
58  return;
59  }
60  } else {
61  is.putback(c);
62  }
63 
64  // At this point, parenthesis or not, the next item read is supposed to
65  // be the number x.
66 
67  if (!(is >> x)) {
68  std::cerr << "Could not read first value in input of " << type << "\n";
69  return;
70  }
71 
72  if ( !eatwhitespace(is) ) {
73  std::cerr << "istream ended before second value of " << type << "\n";
74  return;
75  }
76 
77  if ( !is.get(c) ) { fouledup(); return; }
78  if ( c == ',' ) {
79  if ( !eatwhitespace(is) ) {
80  std::cerr << "istream ended ater one value and comma in "
81  << type << "\n";
82  return;
83  }
84  } else {
85  is.putback(c);
86  }
87 
88  // At this point, comma or not, the next item read is supposed to
89  // be the number y.
90 
91  if (!(is >> y)) {
92  std::cerr << "Could not read second value in input of " << type << "\n";
93  return;
94  }
95 
96  if ( !eatwhitespace(is) ) {
97  std::cerr << "istream ended before third value of " << type << "\n";
98  return;
99  }
100 
101  if ( !is.get(c) ) { fouledup(); return; }
102  if ( c == ',' ) {
103  if ( !eatwhitespace(is) ) {
104  std::cerr << "istream ended ater two values and comma in "
105  << type << "\n";
106  return;
107  }
108  } else {
109  is.putback(c);
110  }
111 
112  // At this point, comma or not, the next item read is supposed to
113  // be the number z.
114 
115  if (!(is >> z)) {
116  std::cerr << "Could not read third value in input of " << type << "\n";
117  return;
118  }
119 
120  // Finally, check for the closing parenthesis if there was an open paren.
121 
122  if (parenthesis) {
123  if ( !eatwhitespace(is) ) {
124  std::cerr << "No closing parenthesis in input of " << type << "\n";
125  return;
126  }
127  if ( !is.get(c) ) { fouledup(); return; }
128  if ( c != ')' ) {
129  std::cerr << "Missing closing parenthesis in input of "
130  << type << "\n";
131  // Now a trick to do (as nearly as we can) what
132  // is.putback(c); is.setstate(std::ios_base::failbit);
133  // would do (because using ios_base will confuse old CLHEP compilers):
134  if ( isdigit(c) || (c=='-') || (c=='+') ) {
135  is.putback('@');
136  } else {
137  is.putback('c');
138  }
139  int m;
140  is >> m; // This fails, leaving the state bad, and the istream
141  // otherwise unchanged, except if the next char might
142  // have started a valid int, it turns to @
143  return;
144  }
145  }
146 
147  return;
148 
149 }
150 
151 
152 void ZMinputAxisAngle ( std::istream & is,
153  double & x, double & y, double & z,
154  double & delta ) {
155 // Accepted formats are
156 // parenthesis optional, then
157 // any acceptable format for a Hep3Vector, then
158 // optional comma, then
159 // delta, then
160 // close parenthesis if opened at start.
161 //
162 // But if there is an open parenthesis, it must be for the overall
163 // object. That is, if the axis has parentheses, the form must be
164 // ( (x,y,z) , delta )
165 
166  char c;
167  bool parenthesis = false;
168 
169  if ( !eatwhitespace(is) ) {
170  std::cerr << "istream ended before trying to input AxisAngle \n";
171  return;
172  }
173 
174  if ( !is.get(c) ) { fouledup(); return; }
175  if ( c == '(' ) {
176  parenthesis = true;
177  if ( !eatwhitespace(is) ) {
178  std::cerr << "istream ended after ( trying to input AxisAngle \n";
179  return;
180  }
181  } else {
182  is.putback(c);
183  }
184 
185  // At this point, parenthesis or not, the next item read is supposed to
186  // be a valid Hep3Vector axis.
187 
188  ZMinput3doubles ( is, "axis of AxisAngle", x, y, z );
189  if (!is) return;
190 
191  if ( !eatwhitespace(is) ) {
192  std::cerr << "istream ended before delta of AxisAngle \n";
193  return;
194  }
195 
196  if ( !is.get(c) ) { fouledup(); return; }
197  if ( c == ',' ) {
198  if ( !eatwhitespace(is) ) {
199  std::cerr << "istream ended ater axis and comma in AxisAngle \n";
200  return;
201  }
202  } else {
203  is.putback(c);
204  }
205 
206  // At this point, comma or not, the next item read is supposed to
207  // be the number delta.
208 
209  if (!(is >> delta)) {
210  std::cerr << "Could not delta value in input of AxisAngle \n";
211  return;
212  }
213 
214  // Finally, check for the closing parenthesis if there was an open paren.
215 
216  if (parenthesis) {
217  if ( !eatwhitespace(is) ) {
218  std::cerr << "No closing parenthesis in input of AxisAngle \n";
219  return;
220  }
221  if ( !is.get(c) ) { fouledup(); return; }
222  if ( c != ')' ) {
223  std::cerr << "Missing closing parenthesis in input of AxisAngle \n";
224  if ( isdigit(c) || (c=='-') || (c=='+') ) {
225  is.putback('@');
226  } else {
227  is.putback('c');
228  }
229  int m;
230  is >> m; // This fails, leaving the state bad.
231  return;
232  }
233  }
234 
235  return;
236 
237 }
238 
239 
240 void ZMinput2doubles ( std::istream & is, const char * type,
241  double & x, double & y ) {
242 
243 // Accepted formats are
244 // x y
245 // x, y (comma is optional, and whitespace ignored if comma present)
246 // ( x, y ) (comma optional)
247 
248  char c;
249  bool parenthesis = false;
250 
251  if ( !eatwhitespace(is) ) {
252  std::cerr << "istream ended before trying to input " << type << "\n";
253  return;
254  }
255 
256  if ( !is.get(c) ) { fouledup(); return; }
257  if ( c == '(' ) {
258  parenthesis = true;
259  if ( !eatwhitespace(is) ) {
260  std::cerr << "istream ended after ( trying to input " << type << "\n";
261  return;
262  }
263  } else {
264  is.putback(c);
265  }
266 
267  // At this point, parenthesis or not, the next item read is supposed to
268  // be the number x.
269 
270  if (!(is >> x)) {
271  std::cerr << "Could not read first value in input of " << type << "\n";
272  return;
273  }
274 
275  if ( !eatwhitespace(is) ) {
276  std::cerr << "istream ended before second value of " << type << "\n";
277  return;
278  }
279 
280  if ( !is.get(c) ) { fouledup(); return; }
281  if ( c == ',' ) {
282  if ( !eatwhitespace(is) ) {
283  std::cerr << "istream ended ater one value and comma in "
284  << type << "\n";
285  return;
286  }
287  } else {
288  is.putback(c);
289  }
290 
291  // At this point, comma or not, the next item read is supposed to
292  // be the number y.
293 
294  if (!(is >> y)) {
295  std::cerr << "Could not read second value in input of " << type << "\n";
296  return;
297  }
298 
299  // Finally, check for the closing parenthesis if there was an open paren.
300 
301  if (parenthesis) {
302  if ( !eatwhitespace(is) ) {
303  std::cerr << "No closing parenthesis in input of " << type << "\n";
304  return;
305  }
306  if ( !is.get(c) ) { fouledup(); return; }
307  if ( c != ')' ) {
308  std::cerr << "Missing closing parenthesis in input of "
309  << type << "\n";
310  // Now a trick to do (as nearly as we can) what
311  // is.putback(c); is.setstate(std::ios_base::failbit);
312  // would do (because using ios_base will confuse old CLHEP compilers):
313  if ( isdigit(c) || (c=='-') || (c=='+') ) {
314  is.putback('@');
315  } else {
316  is.putback('c');
317  }
318  int m;
319  is >> m; // This fails, leaving the state bad, and the istream
320  // otherwise unchanged, except if the next char might
321  // have started a valid int, it turns to @
322  return;
323  }
324  }
325 
326  return;
327 
328 }
329 
330 } // namespace CLHEP