Geant4 Cross Reference |
1 // 1 // 2 // ******************************************* 2 // ******************************************************************** 3 // * License and Disclaimer 3 // * License and Disclaimer * 4 // * 4 // * * 5 // * The Geant4 software is copyright of th 5 // * The Geant4 software is copyright of the Copyright Holders of * 6 // * the Geant4 Collaboration. It is provided 6 // * the Geant4 Collaboration. It is provided under the terms and * 7 // * conditions of the Geant4 Software License 7 // * conditions of the Geant4 Software License, included in the file * 8 // * LICENSE and available at http://cern.ch/ 8 // * LICENSE and available at http://cern.ch/geant4/license . These * 9 // * include a list of copyright holders. 9 // * include a list of copyright holders. * 10 // * 10 // * * 11 // * Neither the authors of this software syst 11 // * Neither the authors of this software system, nor their employing * 12 // * institutes,nor the agencies providing fin 12 // * institutes,nor the agencies providing financial support for this * 13 // * work make any representation or warran 13 // * work make any representation or warranty, express or implied, * 14 // * regarding this software system or assum 14 // * regarding this software system or assume any liability for its * 15 // * use. Please see the license in the file 15 // * use. Please see the license in the file LICENSE and URL above * 16 // * for the full disclaimer and the limitatio 16 // * for the full disclaimer and the limitation of liability. * 17 // * 17 // * * 18 // * This code implementation is the result 18 // * This code implementation is the result of the scientific and * 19 // * technical work of the GEANT4 collaboratio 19 // * technical work of the GEANT4 collaboration. * 20 // * By using, copying, modifying or distri 20 // * By using, copying, modifying or distributing the software (or * 21 // * any work based on the software) you ag 21 // * any work based on the software) you agree to acknowledge its * 22 // * use in resulting scientific publicati 22 // * use in resulting scientific publications, and indicate your * 23 // * acceptance of all terms of the Geant4 Sof 23 // * acceptance of all terms of the Geant4 Software license. * 24 // ******************************************* 24 // ******************************************************************** 25 // 25 // 26 // G4GDMLEvaluator implementation << 27 // 26 // 28 // Author: Zoltan Torzsok, November 2007 << 27 // $Id: G4GDMLEvaluator.cc,v 1.26 2010-11-04 11:33:49 gcosmo Exp $ >> 28 // GEANT4 tag $ Name:$ >> 29 // >> 30 // class G4GDMLEvaluator Implementation >> 31 // >> 32 // Original author: Zoltan Torzsok, November 2007 >> 33 // 29 // ------------------------------------------- 34 // -------------------------------------------------------------------- 30 35 31 #include <sstream> 36 #include <sstream> 32 37 33 #include "G4GDMLEvaluator.hh" 38 #include "G4GDMLEvaluator.hh" 34 #include "G4SystemOfUnits.hh" << 35 39 36 // ------------------------------------------- << 37 G4GDMLEvaluator::G4GDMLEvaluator() 40 G4GDMLEvaluator::G4GDMLEvaluator() 38 { 41 { 39 eval.clear(); << 42 eval.clear(); 40 eval.setStdMath(); << 43 eval.setStdMath(); 41 eval.setSystemOfUnits(meter, kilogram, secon << 44 eval.setSystemOfUnits(meter,kilogram,second,ampere,kelvin,mole,candela); 42 } 45 } 43 46 44 // ------------------------------------------- << 45 void G4GDMLEvaluator::Clear() 47 void G4GDMLEvaluator::Clear() 46 { 48 { 47 eval.clear(); 49 eval.clear(); 48 eval.setStdMath(); 50 eval.setStdMath(); 49 eval.setSystemOfUnits(meter, kilogram, secon << 51 eval.setSystemOfUnits(meter,kilogram,second,ampere,kelvin,mole,candela); 50 52 51 variableList.clear(); 53 variableList.clear(); 52 } 54 } 53 55 54 // ------------------------------------------- << 55 void G4GDMLEvaluator::DefineConstant(const G4S 56 void G4GDMLEvaluator::DefineConstant(const G4String& name, G4double value) 56 { 57 { 57 if(eval.findVariable(name)) << 58 if (eval.findVariable(name)) 58 { << 59 { 59 G4String error_msg = "Redefinition of cons << 60 G4String error_msg = "Redefinition of constant or variable: "+name; 60 G4Exception("G4GDMLEvaluator::DefineConsta << 61 G4Exception("G4GDMLEvaluator::DefineConstant()", "InvalidExpression", 61 FatalException, error_msg); << 62 FatalException, error_msg); 62 } << 63 } 63 eval.setVariable(name.c_str(), value); << 64 eval.setVariable(name.c_str(),value); 64 } << 65 } 65 << 66 66 // ------------------------------------------- << 67 void G4GDMLEvaluator::DefineVariable(const G4String& name,G4double value) 67 void G4GDMLEvaluator::DefineVariable(const G4S << 68 { 68 { << 69 if (eval.findVariable(name)) 69 if(eval.findVariable(name)) << 70 { 70 { << 71 G4String error_msg = "Redefinition of constant or variable: "+name; 71 G4String error_msg = "Redefinition of cons << 72 G4Exception("G4GDMLEvaluator::DefineVariable()", "InvalidExpression", 72 G4Exception("G4GDMLEvaluator::DefineVariab << 73 FatalException, error_msg); 73 FatalException, error_msg); << 74 } 74 } << 75 eval.setVariable(name.c_str(),value); 75 eval.setVariable(name.c_str(), value); << 76 variableList.push_back(name); 76 variableList.push_back(name); << 77 } 77 } << 78 78 << 79 void G4GDMLEvaluator::DefineMatrix(const G4String& name, 79 // ------------------------------------------- << 80 G4int coldim, 80 void G4GDMLEvaluator::DefineMatrix(const G4Str << 81 std::vector<G4double> valueList) 81 std::vector << 82 { 82 { << 83 const G4int size = valueList.size(); 83 const G4int size = (G4int)valueList.size(); << 84 >> 85 if (size == 0) >> 86 { >> 87 G4String error_msg = "Matrix '"+name+"' is empty!"; >> 88 G4Exception("G4GDMLEvaluator::DefineMatrix()", "InvalidSize", >> 89 FatalException, error_msg); >> 90 } >> 91 if (size == 1) >> 92 { >> 93 G4String error_msg = "Matrix '" + name >> 94 + "' has only one element! " >> 95 + "Define a constant instead!!"; >> 96 G4Exception("G4GDMLEvaluator::DefineMatrix()", "InvalidSize", >> 97 FatalException, error_msg); >> 98 } >> 99 if (size % coldim != 0) >> 100 { >> 101 G4String error_msg = "Matrix '" + name + "' is not filled correctly!"; >> 102 G4Exception("G4GDMLEvaluator::DefineMatrix()", "InvalidSize", >> 103 FatalException, error_msg); >> 104 } >> 105 >> 106 if ((size == coldim) || (coldim == 1)) // Row- or column matrix >> 107 { >> 108 for (G4int i=0;i<size;i++) >> 109 { >> 110 std::stringstream MatrixElementNameStream; >> 111 MatrixElementNameStream << name << "_" << i; >> 112 DefineConstant(MatrixElementNameStream.str(),valueList[i]); >> 113 } >> 114 } >> 115 else // Normal matrix >> 116 { >> 117 const G4int rowdim = size/coldim; 84 118 85 if(size == 0) << 119 for (G4int i=0;i<rowdim;i++) 86 { << 87 G4String error_msg = "Matrix '" + name + " << 88 G4Exception("G4GDMLEvaluator::DefineMatrix << 89 FatalException, error_msg); << 90 } << 91 /* << 92 if (size == 1) << 93 { << 94 G4String error_msg = "Matrix '" + name << 95 + "' has only one eleme << 96 + "Define a constant in << 97 G4Exception("G4GDMLEvaluator::DefineMatrix << 98 FatalException, error_msg); << 99 } << 100 */ << 101 << 102 if(size % coldim != 0) << 103 { << 104 G4String error_msg = "Matrix '" + name + " << 105 G4Exception("G4GDMLEvaluator::DefineMatrix << 106 FatalException, error_msg); << 107 } << 108 << 109 if((size == coldim) || (coldim == 1)) // Ro << 110 { << 111 for(G4int i = 0; i < size; ++i) << 112 { << 113 std::stringstream MatrixElementNameStrea << 114 MatrixElementNameStream << name << "_" < << 115 DefineConstant(MatrixElementNameStream.s << 116 } << 117 } << 118 else // Normal matrix << 119 { << 120 const G4int rowdim = size / coldim; << 121 << 122 for(G4int i = 0; i < rowdim; ++i) << 123 { << 124 for(G4int j = 0; j < coldim; ++j) << 125 { 120 { 126 std::stringstream MatrixElementNameStr << 121 for (G4int j=0;j<coldim;j++) 127 MatrixElementNameStream << name << "_" << 122 { 128 DefineConstant(MatrixElementNameStream << 123 std::stringstream MatrixElementNameStream; 129 valueList[coldim * i + << 124 MatrixElementNameStream << name << "_" << i << "_" << j; >> 125 DefineConstant(MatrixElementNameStream.str(),valueList[coldim*i+j]); >> 126 } 130 } 127 } 131 } << 128 } 132 } << 133 } 129 } 134 130 135 // ------------------------------------------- << 136 void G4GDMLEvaluator::SetVariable(const G4Stri 131 void G4GDMLEvaluator::SetVariable(const G4String& name, G4double value) 137 { 132 { 138 if(!IsVariable(name)) << 133 if (!IsVariable(name)) 139 { << 134 { 140 G4String error_msg = "Variable '" + name + << 135 G4String error_msg = "Variable '" + name + "' is not defined!"; 141 G4Exception("G4GDMLEvaluator::SetVariable( << 136 G4Exception("G4GDMLEvaluator::SetVariable()", "InvalidSetup", 142 FatalException, error_msg); << 137 FatalException, error_msg); 143 } << 138 } 144 eval.setVariable(name.c_str(), value); << 139 eval.setVariable(name.c_str(),value); 145 } 140 } 146 141 147 // ------------------------------------------- << 148 G4bool G4GDMLEvaluator::IsVariable(const G4Str 142 G4bool G4GDMLEvaluator::IsVariable(const G4String& name) const 149 { 143 { 150 const std::size_t variableCount = variableLi << 144 const size_t variableCount = variableList.size(); 151 145 152 for(std::size_t i = 0; i < variableCount; ++ << 146 for (size_t i=0;i<variableCount;i++) 153 { << 147 { 154 if(variableList[i] == name) << 148 if (variableList[i] == name) { return true; } 155 { << 149 } 156 return true; << 157 } << 158 } << 159 150 160 return false; << 151 return false; 161 } 152 } 162 153 163 // ------------------------------------------- << 164 G4String G4GDMLEvaluator::SolveBrackets(const 154 G4String G4GDMLEvaluator::SolveBrackets(const G4String& in) 165 { 155 { 166 std::string::size_type full = in.size(); << 156 std::string::size_type full = in.size(); 167 std::string::size_type open = in.find("[", << 157 std::string::size_type open = in.find("[",0); 168 std::string::size_type close = in.find("]", << 158 std::string::size_type close = in.find("]",0); 169 << 159 170 if(open == close) << 160 if (open==close) { return in; } 171 { << 161 172 return in; << 162 if ((open>close) || (open==std::string::npos) || (close==std::string::npos)) 173 } << 163 { 174 << 164 G4String error_msg = "Bracket mismatch: " + in; 175 if((open > close) || (open == std::string::n << 165 G4Exception("G4GDMLEvaluator::SolveBrackets()", "InvalidExpression", 176 (close == std::string::npos)) << 166 FatalException, error_msg); 177 { << 167 return in; 178 G4String error_msg = "Bracket mismatch: " << 168 } 179 G4Exception("G4GDMLEvaluator::SolveBracket << 169 180 FatalException, error_msg); << 170 std::string::size_type begin = open; 181 return in; << 171 std::string::size_type end = 0; 182 } << 172 std::string::size_type end1 = 0; 183 << 173 std::string out; 184 std::string::size_type begin = open; << 174 out.append(in,0,open); 185 std::string::size_type end = 0; << 175 186 std::string::size_type end1 = 0; << 176 do // Loop for all possible matrix elements in 'in' 187 std::string out; << 177 { 188 out.append(in, 0, open); << 178 do // SolveBrackets for one matrix element 189 << 179 { 190 do // Loop for all possible matrix elements << 180 end = in.find(",",begin+1); 191 { << 181 end1= in.find("]",begin+1); 192 do // SolveBrackets for one matrix elemen << 182 if (end>end1) { end = end1; } 193 { << 183 if (end==std::string::npos) { end = close;} 194 end = in.find(",", begin + 1); << 184 195 end1 = in.find("]", begin + 1); << 185 std::stringstream indexStream; 196 if(end > end1) << 186 indexStream << "_" << EvaluateInteger(in.substr(begin+1,end-begin-1))-1; 197 { << 187 198 end = end1; << 188 out.append(indexStream.str()); 199 } << 189 200 if(end == std::string::npos) << 190 begin = end; 201 { << 191 202 end = close; << 192 } while (end<close); 203 } << 193 204 << 194 if (full==close) { return out; } 205 std::stringstream indexStream; << 195 206 indexStream << "_" << 196 open = in.find("[",begin); 207 << EvaluateInteger(in.substr << 197 close = in.find("]",begin+1); 208 << 198 209 out.append(indexStream.str()); << 199 if (open==close) { out.append(in.substr(end+1,full-end-1)); return out; } 210 << 200 out.append(in.substr(end+1,open-end-1)); 211 begin = end; << 201 212 << 202 begin=open; 213 } while(end < close); << 203 214 << 204 } while (close<full); 215 if(full == close) << 205 216 { << 206 return out; 217 return out; << 218 } << 219 << 220 open = in.find("[", begin); << 221 close = in.find("]", begin + 1); << 222 << 223 if(open == close) << 224 { << 225 out.append(in.substr(end + 1, full - end << 226 return out; << 227 } << 228 out.append(in.substr(end + 1, open - end - << 229 << 230 begin = open; << 231 << 232 } while(close < full); << 233 << 234 return out; << 235 } 207 } 236 208 237 // ------------------------------------------- << 238 G4double G4GDMLEvaluator::Evaluate(const G4Str 209 G4double G4GDMLEvaluator::Evaluate(const G4String& in) 239 { 210 { 240 G4String expression = SolveBrackets(in); << 211 G4String expression = SolveBrackets(in); >> 212 >> 213 G4double value = 0.0; 241 214 242 G4double value = 0.0; << 215 if (!expression.empty()) >> 216 { >> 217 value = eval.evaluate(expression.c_str()); 243 218 244 if(!expression.empty()) << 219 if (eval.status() != G4Evaluator::OK) 245 { << 220 { 246 value = eval.evaluate(expression.c_str()); << 221 eval.print_error(); 247 << 222 G4String error_msg = "Error in expression: " + expression; 248 if(eval.status() != G4Evaluator::OK) << 223 G4Exception("G4GDMLEvaluator::Evaluate()", "InvalidExpression", 249 { << 224 FatalException, error_msg); 250 eval.print_error(); << 225 } 251 G4String error_msg = "Error in expressio << 226 } 252 G4Exception("G4GDMLEvaluator::Evaluate() << 227 return value; 253 FatalException, error_msg); << 254 } << 255 } << 256 return value; << 257 } 228 } 258 229 259 // ------------------------------------------- << 260 G4int G4GDMLEvaluator::EvaluateInteger(const G 230 G4int G4GDMLEvaluator::EvaluateInteger(const G4String& expression) 261 { 231 { 262 // This function is for evaluating integer e << 232 // This function is for evaluating integer expressions, 263 // like loop variables and matrix indices. << 233 // like loop variables and matrix indices. 264 // Complains if the evaluated expression has << 234 // Complains if the evaluated expression has a fractional 265 // part different from zero << 235 // part different from zero 266 << 236 267 G4double value = Evaluate(expression); << 237 G4double value = Evaluate(expression); 268 << 238 269 G4int whole = (G4int) value; << 239 G4int whole = (G4int)value; 270 G4double frac = value - (G4double) whole; << 240 G4double frac = value - (G4double)whole; 271 << 241 272 if(frac != 0.0) << 242 if (frac != 0.0) 273 { << 243 { 274 G4String error_msg = << 244 G4String error_msg = "Expression '" + expression 275 "Expression '" + expression + "' is expe << 245 + "' is expected to have an integer value!"; 276 G4Exception("G4GDMLEvaluator::EvaluateInte << 246 G4Exception("G4GDMLEvaluator::EvaluateInteger()", "InvalidExpression", 277 FatalException, error_msg); << 247 FatalException, error_msg); 278 } << 248 } 279 return whole; << 249 return whole; 280 } 250 } 281 251 282 // ------------------------------------------- << 283 G4double G4GDMLEvaluator::GetConstant(const G4 252 G4double G4GDMLEvaluator::GetConstant(const G4String& name) 284 { 253 { 285 if(IsVariable(name)) << 254 if (IsVariable(name)) 286 { << 255 { 287 G4String error_msg = << 256 G4String error_msg = "Constant '" + name 288 "Constant '" + name + "' is not defined! << 257 + "' is not defined! It is a variable!"; 289 G4Exception("G4GDMLEvaluator::GetConstant( << 258 G4Exception("G4GDMLEvaluator::GetConstant()", "InvalidSetup", 290 FatalException, error_msg); << 259 FatalException, error_msg); 291 } << 260 } 292 if(!eval.findVariable(name)) << 261 if (!eval.findVariable(name)) 293 { << 262 { 294 G4String error_msg = "Constant '" + name + << 263 G4String error_msg = "Constant '" + name + "' is not defined!"; 295 G4Exception("G4GDMLEvaluator::GetConstant( << 264 G4Exception("G4GDMLEvaluator::GetConstant()", "InvalidSetup", 296 FatalException, error_msg); << 265 FatalException, error_msg); 297 } << 266 } 298 return Evaluate(name); << 267 return Evaluate(name); 299 } 268 } 300 269 301 // ------------------------------------------- << 302 G4double G4GDMLEvaluator::GetVariable(const G4 270 G4double G4GDMLEvaluator::GetVariable(const G4String& name) 303 { 271 { 304 if(!IsVariable(name)) << 272 if (!IsVariable(name)) 305 { << 273 { 306 G4String error_msg = "Variable '" + name + << 274 G4String error_msg = "Variable '" + name + "' is not a defined!"; 307 G4Exception("G4GDMLEvaluator::GetVariable( << 275 G4Exception("G4GDMLEvaluator::GetVariable()", "InvalidSetup", 308 FatalException, error_msg); << 276 FatalException, error_msg); 309 } << 277 } 310 return Evaluate(name); << 278 return Evaluate(name); 311 } << 312 << 313 // ------------------------------------------- << 314 G4String G4GDMLEvaluator::ConvertToString(G4in << 315 { << 316 std::ostringstream os; << 317 os << ival; << 318 G4String vl = os.str(); << 319 return vl; << 320 } << 321 << 322 // ------------------------------------------- << 323 G4String G4GDMLEvaluator::ConvertToString(G4do << 324 { << 325 std::ostringstream os; << 326 os << dval; << 327 G4String vl = os.str(); << 328 return vl; << 329 } 279 } 330 280