| Classes | Job Modules | Data Objects | Services | Algorithms | Tools | Packages | Directories | Tracs |

In This Package:

ConditionParser.cpp

Go to the documentation of this file.
00001 #include "ConditionParser.h"
00002 
00003 #include <boost/version.hpp>
00004 #if BOOST_VERSION >= 103800
00005 #define BOOST_SPIRIT_USE_OLD_NAMESPACE
00006 #include <boost/spirit/include/classic_core.hpp>
00007 #else
00008 #include <boost/spirit/core.hpp>
00009 #endif
00010 
00011 using namespace std;
00012 using namespace boost::spirit;
00013 
00014 namespace {
00015 
00017   struct TempParameter {
00018     TempParameter():name(),param(){}
00019     ~TempParameter() { }
00020     
00021     std::string name;
00022     BasicParam* param;
00023     
00025     template <class T>
00026     void setValue(T value){
00027       if (param) delete param;
00028       param = new Param<T>(value);
00029     }
00030 
00032     template <class T>
00033     void newVector(){
00034       if (param) delete param;
00035       param = new Param<std::vector<T> >();
00036     }
00037 
00039     struct SetName {
00040       SetName(TempParameter &par):temp(par){}
00041       TempParameter &temp;
00042       void operator () (char const*b, char const*e) const {
00043         temp.name = std::string(b,e);
00044         //std::cout << "SetName " << temp.name << std::endl;
00045       }
00046     };
00047 
00049     template <class T>
00050     struct SetValue {
00051       SetValue(TempParameter &par):temp(par){}
00052       TempParameter &temp;
00053       void operator () (T val) const {
00054         //std::cout << "SetValue " << val << std::endl;
00055         temp.setValue<T>(val);
00056       }
00057     };
00058 
00060     struct SetValueString {
00061       SetValueString(TempParameter &par):temp(par){}
00062       TempParameter &temp;
00063       void operator () (char const*b, char const*e) const {
00064         temp.setValue<std::string>(std::string(b,e));
00065         //std::cout << "SetValueString " << std::string(b,e) << std::endl;
00066       }
00067     };
00068 
00070     template <class T>
00071     struct AddVector {
00072       AddVector(TempParameter &par):temp(par){}
00073       TempParameter &temp;
00074       void operator () (char const*, char const*) const {
00075         //std::cout << "AddVector " << std::string(b,e) << std::endl;
00076         temp.newVector<T>();
00077       }
00078     };
00079 
00081     template <class T>
00082     struct PushBack {
00083       PushBack(TempParameter &par):temp(par){}
00084       TempParameter &temp;
00085       void operator () (T val) const {
00086         //std::cout << "PushBack " << val << std::endl;
00087         temp.param->template get<std::vector<T> >().push_back(val);
00088       }
00089     };
00090 
00092     struct PushBackString {
00093       PushBackString(TempParameter &par):temp(par){}
00094       TempParameter &temp;
00095       void operator () (char const*b, char const*e) const {
00096         //std::cout << "PushBack " << val << std::endl;
00097         temp.param->get<std::vector<std::string> >().push_back(std::string(b,e));
00098       }
00099     };
00100 
00102     struct AddParameter {
00103       AddParameter(ParamValidDataObject &c, TempParameter &par):temp(par),cond(c){}
00104       TempParameter &temp;
00105       ParamValidDataObject &cond;
00106       void operator () (char const*, char const*) const {
00107         //std::cout << "AddParam " << temp.name << " " << temp.param->toStr() << std::endl; 
00108         cond.addBasicParam(temp.name,temp.param);
00109       }
00110     };
00111 
00112   };
00113 
00115   struct SetString {
00116     SetString(std::string &s):temp(s){}
00117     std::string &temp;
00118     void operator () (char const*b, char const*e) const {
00119       temp = std::string(b,e);
00120       //std::cout << "SetString " << temp << std::endl;
00121     }
00122   };
00123   
00125   class ConditionGrammar : public grammar<ConditionGrammar> {
00126   public:
00127 
00128     ConditionGrammar() {}
00129 
00131     std::string name;
00133     ParamValidDataObject condition;
00134 
00135     
00137     template <class ScannerT>
00138     struct definition {
00139 
00141       enum Types {  
00142         Integer = 0,
00143         Double,
00144         String,
00145         IntegerVector,
00146         DoubleVector,
00147         StringVector,
00148         NTypes};
00149     
00151       ParamValidDataObject &cond;
00153       std::string &condition_name;
00155       TempParameter tmp;
00156     
00158       rule<ScannerT> identifier, name, parameter, type[NTypes], value[NTypes];
00159       rule<ScannerT> spaces, eq, sep;
00161       rule<ScannerT> condition;
00162       
00164       definition ( const ConditionGrammar &self ):
00165         cond(const_cast<ConditionGrammar &>(self).condition),
00166         condition_name(const_cast<ConditionGrammar &>(self).name)
00167       {
00168         // an identifier is a sequence of alphanumeric characters + '/' + '_' + '-'
00169         identifier = *(alnum_p | ch_p('/') | ch_p('_') | ch_p('-') | ch_p(':'));
00170         
00171         // name of a parameter
00172         name = identifier[TempParameter::SetName(tmp)];
00173 
00174         // I define the keyword used to identify the types
00175         // basic types:
00176         type[Integer]       = str_p("int");
00177         type[Double]        = (str_p("double") | str_p("dbl"));
00178         type[String]        = (str_p("string") | str_p("str"));
00179         // vectors: (vectors need a special action to create the container before parsing the values)
00180         type[IntegerVector] = str_p("int_v")
00181                               [TempParameter::AddVector<int>(tmp)];
00182         type[DoubleVector]  = (str_p("double_v") | str_p("dbl_v"))
00183                               [TempParameter::AddVector<double>(tmp)];
00184         type[StringVector]  = (str_p("string_v") | str_p("str_v"))
00185                               [TempParameter::AddVector<std::string>(tmp)];
00186       
00187         // just to simplify
00188         spaces = *space_p;
00189         eq = ch_p('=');
00190         sep = ch_p(';');
00191       
00192         // descriptions of the values and relative actions
00193         value[Integer]       = int_p
00194                                [TempParameter::SetValue<int>(tmp)];
00195         value[Double]        = real_p
00196                                [TempParameter::SetValue<double>(tmp)];
00197         value[String]        = ((+alnum_p) % spaces)
00198                                [TempParameter::SetValueString(tmp)];
00199         // vectors are space separated lists
00200         value[IntegerVector] = int_p[TempParameter::PushBack<int>(tmp)] % spaces;
00201         value[DoubleVector]  = real_p[TempParameter::PushBack<double>(tmp)] % spaces;
00202         value[StringVector]  = (+~space_p)[TempParameter::PushBackString(tmp)] % spaces;
00203       
00204         // Definition of the parameter
00205         parameter =
00206           (
00207            // vector<int>
00208            ( type[IntegerVector] >> spaces >> name >> spaces >> eq >> spaces >> value[IntegerVector] ) |
00209            // vector<double>
00210            ( type[DoubleVector] >> spaces >> name >> spaces >> eq >> spaces >> value[DoubleVector] ) |
00211            // vector<string>
00212            ( type[StringVector] >> spaces >> name >> spaces >> eq >> spaces >> value[StringVector] ) |
00213            // int
00214            ( type[Integer] >> spaces >> name >> spaces >> eq >> spaces >> value[Integer] ) |
00215            // double
00216            ( type[Double] >> spaces >> name >> spaces >> eq >> spaces >> value[Double] ) |
00217            // string
00218            ( type[String] >> spaces >> name >> spaces >> eq >> spaces >> value[String] )
00219            )
00220           // add the parameter to the condition
00221           [TempParameter::AddParameter(cond,tmp)];
00222       
00223         // the whole condition
00224         condition =
00225           // name (path) of the condition 
00226           identifier[SetString(condition_name)] >> spaces >>
00227           // assignment operator (from Pascal)
00228           str_p(":=") >> spaces >>
00229           // sequence of parameters separated by (regexp) ' *; *'
00230           ( parameter % ( spaces >> sep >> spaces ) ) >>
00231           // optional closing (regexp) ' *(; *)?'
00232           spaces >> !(sep >> spaces); 
00233       }
00234     
00236       rule<ScannerT> const& start() const { return condition; }
00237     };
00238   };
00239 }
00240 
00241 //======================================================================
00242 // function to parse the string describing a condition
00243 //======================================================================
00244 bool ConditionParser(const std::string &str, std::string &name, ParamValidDataObject &cond){
00245   ConditionGrammar g;
00246   // TODO: improve error messages
00247   if ( parse(str.c_str(),g).full ){
00248     name = g.name;
00249     cond.update(g.condition);
00250     return true;
00251   }
00252   return false;
00253 }
| Classes | Job Modules | Data Objects | Services | Algorithms | Tools | Packages | Directories | Tracs |

Generated on Mon Apr 11 20:02:42 2011 for DetDescSvc by doxygen 1.4.7