ParserGrammar.hh
4.93 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
#ifndef PARSERGRAMMAR_HH_
#define PARSERGRAMMAR_HH_
#include <boost/spirit/include/qi.hpp>
#include <boost/spirit/include/phoenix.hpp>
#include "ExpressionContainer.hh"
#include "CustomFoldDirective.hh"
#include "ParserToolbox.hh"
#include "Properties.hh"
namespace AMDA {
namespace parser {
namespace qi = boost::spirit::qi;
using namespace qi;
using namespace Expression;
template <typename It, typename Skipper = boost::spirit::standard_wide::space_type>
class ParserGrammar : public qi::grammar<It, Expression::ExpressionContainer(), Skipper>
{
public:
ParserGrammar(AMDA::helpers::Properties& lProperties) : ParserGrammar::base_type(expr_)
{
expr_ = or_.alias();
// Logical Operators
or_ = fold<binop<op_or> >(xor_.alias())[orOperator_ >> xor_];
xor_ = fold<binop<op_xor> >(and_.alias())[xorOperator_ >> and_];
and_ = fold<binop<op_and> >(equal_.alias())[andOperator_ >> equal_];
equal_ = fold<binop<op_equal> >(unequal_.alias())[equalOperator_ >> unequal_];
unequal_ = fold<binop<op_unequal> >(greaterOrEqual_.alias())[unequalOperator_ >>greaterOrEqual_];
greaterOrEqual_ = fold<binop<op_greaterOrEqual> >(lowerOrEqual_.alias())[greaterOrEqualOperator_ >> lowerOrEqual_];
lowerOrEqual_ = fold<binop<op_lowerOrEqual> >(plusSign_.alias())[lowerOrEqualOperator_ >> plusSign_];
plusSign_ = ((sumOperator_ >>-*sumOperator_)> minusSign_ ) [_val = boost::phoenix::construct<Expression::unop <op_plusSign>>(_1)] ||
((differenceOperator_ >>differenceOperator_)> minusSign_ ) [_val = boost::phoenix::construct<Expression::unop <op_plusSign>>(_1)] |minusSign_ [_val = _1];
minusSign_ = (-*sumOperator_>>differenceOperator_ >>-*sumOperator_> sum_) [_val = boost::phoenix::construct<Expression::unop <op_minusSign>>(_1)] | sum_[_val = _1];
// Numerical Operators
sum_ = fold<binop<op_sum> >(difference_.alias())[sumOperator_ >> difference_];
difference_ = fold<binop<op_difference> >(factor_.alias())[differenceOperator_ >> factor_];
factor_ = fold<binop<op_factor> >(division_.alias())[factorOperator_ >> division_];
division_ = fold<binop<op_division> >(greater_.alias())[divisionOperator_ >> greater_];
greater_= fold<comop<op_greater> >(lower_.alias())[greaterOperator_ >> lower_];
lower_ = fold<comop<op_lower> >( not_.alias())[lowerOperator_ >> not_];
// UNARY OPERATIONS
not_ = (notOperator_ > simple) [_val = boost::phoenix::construct<Expression::unop <op_not>>(_1)] | const_[_val = _1];
const_ = (definedFunctions ) [_val = boost::phoenix::construct<Expression::unop <op_const>>(_1)] | simple[_val = _1];
simple = (('(' > expr_ > ')') | var_);
var_ = qi::lexeme[+alnum];
notOperator_ = qi::char_('!');
andOperator_ = qi::string("&");
orOperator_ = qi::string("|");
xorOperator_ = qi::char_("^");
equalOperator_ = qi::string("=");
unequalOperator_ = qi::string("!=");
sumOperator_ = qi::char_("+");
differenceOperator_ = qi::char_("-");
factorOperator_ = qi::char_("*");
divisionOperator_ = qi::char_("/");
greaterOperator_ = qi::char_(">");
greaterOrEqualOperator_ = qi::string(">=");
lowerOrEqualOperator_ = qi::string("<=");
lowerOperator_ = qi::char_("<");
// Define available constants
std::map<std::string, std::string> existingConstants = ParserToolbox::getConstants(lProperties);
for(std::map<std::string, std::string>::iterator it = existingConstants.begin(); it != existingConstants.end(); ++it) {
definedFunctions.add (it->first, it->second);
}
BOOST_SPIRIT_DEBUG_NODES((expr_)(or_)(xor_)(and_)(equal_)(unequal_)(greaterOrEqual_)(lowerOrEqual_)(lower_)(sum_)
(difference_)(factor_)(division_)(simple)(notOperator_)(andOperator_)(orOperator_)(xorOperator_)(equalOperator_)(unequalOperator_)
(sumOperator_)(differenceOperator_)(factorOperator_)(divisionOperator_)(greater_)(lower_));
}
private:
qi::rule<It, Expression::var(), Skipper> var_;
qi::rule<It, Expression::ExpressionContainer(), Skipper> not_
, and_
, xor_
, or_
, equal_
, unequal_
, sum_
, difference_
, factor_
, division_
, simple
, expr_
,plusSign_
,minusSign_
,greater_
,greaterOrEqual_
,lowerOrEqual_
,lower_
,const_;
qi::rule<It, Skipper> notOperator_
, andOperator_
, orOperator_
, xorOperator_
, equalOperator_
, unequalOperator_
, sumOperator_
, differenceOperator_
, factorOperator_
, divisionOperator_
, greaterOperator_
, greaterOrEqualOperator_
,lowerOrEqualOperator_
,lowerOperator_ ;
qi::symbols<char, std::string> definedFunctions;
};
}
}
#endif