00001
00002
00003
00004
00005
00006
00007
00008
00009 #include <sstream>
00010 #include "MP_expression.hpp"
00011 #include "MP_constant.hpp"
00012 #include "MP_boolean.hpp"
00013 #include "MP_constraint.hpp"
00014 #include "MP_set.hpp"
00015 #include "MP_variable.hpp"
00016
00017 using namespace std;
00018
00019 namespace flopc {
00020
00021 class Expression_constant : public TerminalExpression {
00022 friend class MP_expression;
00023
00024 private:
00025 Expression_constant(const Constant& c) : C(c) {}
00026 double level() const {
00027 return C->evaluate();
00028 }
00029 double getValue() const {
00030 return C->evaluate();
00031 }
00032 int getColumn() const {
00033 return -1;
00034 }
00035 int getStage() const {
00036 return C->getStage();
00037 }
00038 void generate(const MP_domain& domain,
00039 vector<Constant> multiplicators,
00040 GenerateFunctor& f,
00041 double m) const {
00042 f.setMultiplicator(multiplicators,m);
00043 f.setTerminalExpression(this);
00044 domain.Forall(&f);
00045 }
00046 void insertVariables(set<MP_variable*>& v) const {}
00047
00048 Constant C;
00049 };
00050
00051 class Expression_plus : public Expression_operator {
00052 friend MP_expression operator+(const MP_expression& e1, const MP_expression& e2);
00053 friend MP_expression operator+(const MP_expression& e1, const Constant& e2);
00054 friend MP_expression operator+(const Constant& e1, const MP_expression& e2);
00055 private:
00056 Expression_plus(const MP_expression& e1, const MP_expression& e2) :
00057 Expression_operator(e1,e2) {}
00058 double level() const {
00059 return left->level()+right->level();
00060 }
00061 void generate(const MP_domain& domain,
00062 vector<Constant> multiplicators,
00063 GenerateFunctor& f,
00064 double m) const {
00065 left->generate(domain, multiplicators,f,m);
00066 right->generate(domain, multiplicators,f,m);
00067 }
00068 };
00069
00070 class Expression_minus : public Expression_operator {
00071 friend MP_expression operator-(const MP_expression& e1, const MP_expression& e2);
00072 friend MP_expression operator-(const MP_expression& e1, const Constant& e2);
00073 friend MP_expression operator-(const Constant& e1, const MP_expression& e2);
00074 private:
00075 Expression_minus(const MP_expression& e1, const MP_expression& e2) :
00076 Expression_operator(e1,e2) {}
00077 double level() const {
00078 return left->level()-right->level();
00079 }
00080 void generate(const MP_domain& domain,
00081 vector<Constant> multiplicators,
00082 GenerateFunctor& f,
00083 double m) const {
00084 left->generate(domain, multiplicators,f,m);
00085 right->generate(domain, multiplicators,f,-m);
00086 }
00087 };
00088
00089 class Expression_mult : public MP_expression_base {
00090 friend MP_expression operator*(const Constant& e1, const MP_expression& e2);
00091 friend MP_expression operator*(const MP_expression& e1, const Constant& e2);
00092
00093 private:
00094 Expression_mult(const Constant& e1, const MP_expression& e2) :
00095 left(e1), right(e2) {}
00096 double level() const {
00097 return left->evaluate()*right->level();
00098 }
00099 void generate(const MP_domain& domain,
00100 vector<Constant> multiplicators,
00101 GenerateFunctor& f,
00102 double m) const {
00103 multiplicators.push_back(left);
00104 right->generate(domain, multiplicators, f, m);
00105 }
00106 void insertVariables(set<MP_variable*>& v) const {
00107 right->insertVariables(v);
00108 }
00109 Constant left;
00110 MP_expression right;
00111 };
00112
00113 class Expression_sum : public MP_expression_base, public Functor {
00114 friend MP_expression sum(const MP_domain& d, const MP_expression& e);
00115 private:
00116 Expression_sum(const MP_domain& d, const MP_expression& e) :
00117 D(d), exp(e) {}
00118 void operator()() const {
00119 the_sum += exp->level();
00120 }
00121 double level() const {
00122 the_sum = 0;
00123 D.Forall(this);
00124 return the_sum;
00125 }
00126 void generate(const MP_domain& domain,
00127 vector<Constant> multiplicators,
00128 GenerateFunctor& f,
00129 double m) const {
00130
00131 exp->generate(D*domain, multiplicators, f, m);
00132 }
00133 void insertVariables(set<MP_variable*>& v) const {
00134 exp->insertVariables(v);
00135 }
00136
00137 mutable double the_sum;
00138 MP_domain D;
00139 MP_expression exp;
00140 };
00141
00142
00143 MP_expression operator+(const MP_expression& e1, const MP_expression& e2) {
00144 return new Expression_plus(e1, e2);
00145 }
00146 MP_expression operator+(const MP_expression& e1, const Constant& e2) {
00147 return new Expression_plus(e1, e2);
00148 }
00149 MP_expression operator+(const Constant& e1, const MP_expression& e2) {
00150 return new Expression_plus(e1, e2);
00151 }
00152
00153 MP_expression operator-(const MP_expression& e1,
00154 const MP_expression& e2) {
00155 return new Expression_minus(e1, e2);
00156 }
00157 MP_expression operator-(const MP_expression& e1,
00158 const Constant& e2) {
00159 return new Expression_minus(e1, e2);
00160 }
00161 MP_expression operator-(const Constant& e1,
00162 const MP_expression& e2) {
00163 return new Expression_minus(e1, e2);
00164 }
00165
00166 MP_expression operator*(const Constant& e1, const MP_expression& e2) {
00167 return new Expression_mult(e1, e2);
00168 }
00169 MP_expression operator*(const MP_expression& e1, const Constant& e2) {
00170 return new Expression_mult(e2, e1);
00171 }
00172
00173 MP_expression sum(const MP_domain& d, const MP_expression& e) {
00174 return new Expression_sum(d, e);
00175 }
00176
00177 }
00178
00179 using namespace flopc;
00180
00181
00182 MP_expression::MP_expression(const Constant &c) :
00183 Handle<MP_expression_base*>(new Expression_constant(c)) {}
00184
00185 MP_expression::MP_expression(const VariableRef &v) :
00186 Handle<MP_expression_base*>(const_cast<VariableRef*>(&v)) {}
00187
00188 int GenerateFunctor::row_number() const {
00189 return R->row_number();
00190 }
00191
00192 void GenerateFunctor::operator()() const {
00193 double multiplicator = m_;
00194 int stage = 0;
00195 for (unsigned int i=0; i<multiplicators.size(); i++) {
00196 multiplicator *= multiplicators[i]->evaluate();
00197 if (multiplicators[i]->getStage() > stage) {
00198 stage = multiplicators[i]->getStage();
00199 }
00200 }
00201 int rowNumber = row_number();
00202 if (rowNumber != outOfBound) {
00203 int colNumber = C->getColumn();
00204 if ( colNumber != outOfBound ) {
00205 double val = multiplicator*C->getValue();
00206 int tstage = C->getStage();
00207 if (tstage > stage) {
00208 stage = tstage;
00209 }
00210
00211
00212 Coefs.push_back(Coef(colNumber, rowNumber, val, stage));
00213
00214 }
00215 }
00216 }