/home/coin/SVN-release/OS-2.4.0/Couenne/src/expression/operators/exprSum.cpp

Go to the documentation of this file.
00001 /* $Id: exprSum.cpp 490 2011-01-14 16:07:12Z pbelotti $
00002  *
00003  * Name:    exprSum.cpp
00004  * Author:  Pietro Belotti
00005  * Purpose: definition of sum expressions
00006  *
00007  * (C) Carnegie-Mellon University, 2006-07. 
00008  * This file is licensed under the Eclipse Public License (EPL)
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) { //< non-leaf expression, with argument list
00022 
00023   if (al==NULL) {
00024     arglist_ = new expression * [1];
00025     *arglist_ = new exprConst (0);
00026     nargs_ = 1;    
00027   }
00028 
00029   // commutative operator, sort elements
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   //  qsort (arglist_, nargs_, sizeof (expression*), compareExpr); // useless...
00040 
00041   if (arg0 -> compare (*arg1) > 0) { // swap elements
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   // from here on we assume the operands have been simplified
00063 
00064   CouNumber total     = 0;
00065   bool      found_one = false;
00066 
00067   for (register int i=0; i<nargs_; i++) {
00068 
00069     // check for constant operands in multiplications
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   if (found_one && shrink_arglist (total, 0))
00082     return new exprConst (arglist_ [0] -> Value ());
00083   else return NULL;
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   //  exprOp::differentiate (index); // FIX IT: why is it called?
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 }

Generated on Thu Sep 22 03:05:58 2011 by  doxygen 1.4.7