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