00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011 #include <stdlib.h>
00012
00013 #include "CouenneExprSum.hpp"
00014 #include "CouenneExprCopy.hpp"
00015 #include "CouenneExprConst.hpp"
00016
00017 using namespace Couenne;
00018
00020 exprSum::exprSum (expression **al, int n):
00021 exprOp (al, n) {
00022
00023 if (al==NULL) {
00024 arglist_ = new expression * [1];
00025 *arglist_ = new exprConst (0);
00026 nargs_ = 1;
00027 }
00028
00029
00030 if (nargs_ > 1)
00031 qsort (arglist_, nargs_, sizeof (expression*), compareExpr);
00032 }
00033
00034
00036 exprSum::exprSum (expression *arg0, expression *arg1):
00037 exprOp (arg0, arg1) {
00038
00039
00040
00041 if (arg0 -> compare (*arg1) > 0) {
00042 expression *swap = arglist_ [0];
00043 arglist_ [0] = arglist_ [1];
00044 arglist_ [1] = swap;
00045 }
00046 }
00047
00048
00050
00051 expression *exprSum::simplify () {
00052
00053 exprOp:: simplify ();
00054
00055 if (nargs_ == 1) {
00056
00057 expression *ret = arglist_ [0];
00058 arglist_ [0] = NULL;
00059 return ret;
00060 }
00061
00062
00063
00064 CouNumber total = 0;
00065 bool found_one = false;
00066
00067 for (register int i=0; i<nargs_; i++) {
00068
00069
00070
00071 if (arglist_ [i] -> Type () == CONST) {
00072
00073 total += arglist_ [i] -> Value ();
00074 found_one = true;
00075 delete arglist_ [i];
00076 arglist_ [i] = NULL;
00077 }
00078 }
00079
00080
00081
00082
00083
00084
00085
00086 if (found_one && shrink_arglist (total, 0)) {
00087 expression *ret = arglist_ [0];
00088 arglist_ [0] = NULL;
00089 return ret;
00090 }
00091 else return NULL;
00092 }
00093
00094
00096
00097 expression *exprSum:: differentiate (int index) {
00098
00099
00100
00101 expression **arglist = new expression * [nargs_];
00102
00103 register int nonconst = 0;
00104
00105 for (int i = 0; i < nargs_; i++)
00106 if (arglist_ [i] -> dependsOn (index))
00107 arglist [nonconst++] = arglist_ [i] -> differentiate (index);
00108
00109 if (!nonconst) {
00110 delete [] arglist;
00111 return new exprConst (0.);
00112 }
00113 else return new exprSum (arglist, nonconst);
00114 }
00115
00116
00118 void exprSum::getBounds (expression *&lb, expression *&ub) {
00119
00120 expression **all = new expression * [nargs_];
00121 expression **alu = new expression * [nargs_];
00122
00123 for (int i=0; i<nargs_; i++)
00124 arglist_ [i] -> getBounds (all [i], alu [i]);
00125
00126 lb = new exprSum (all, nargs_);
00127 ub = new exprSum (alu, nargs_);
00128 }
00129
00130
00132 void exprSum::getBounds (CouNumber &lb, CouNumber &ub) {
00133
00134 CouNumber tlb, tub;
00135
00136 lb = ub = 0;
00137
00138 for (int i=0; i<nargs_; i++) {
00139 arglist_ [i] -> getBounds (tlb, tub);
00140 lb += tlb;
00141 ub += tub;
00142 }
00143 }
00144
00145
00147 int exprSum::Linearity () {
00148
00149 int linmax = arglist_ [0] -> Linearity ();
00150
00151 for (register int i=1; i<nargs_; i++) {
00152 register int lin = arglist_ [i] -> Linearity ();
00153 if (lin > linmax) linmax = lin;
00154 }
00155 return linmax;
00156 }