/home/coin/SVN-release/OS-2.4.1/Couenne/src/convex/operators/conv-exprMul.cpp

Go to the documentation of this file.
00001 /* $Id: conv-exprMul.cpp 490 2011-01-14 16:07:12Z pbelotti $
00002  *
00003  * Name:    conv-exprMul.cpp
00004  * Author:  Pietro Belotti
00005  * Purpose: utility methods to convexify multiplications
00006  *
00007  * (C) Carnegie-Mellon University, 2006-10.
00008  * This file is licensed under the Eclipse Public License (EPL)
00009  */
00010 
00011 #include <queue>
00012 
00013 #include "CouenneTypes.hpp"
00014 #include "CouenneExprMul.hpp"
00015 #include "CouenneExprTrilinear.hpp"
00016 #include "CouenneExprBMul.hpp"
00017 #include "CouenneExprConst.hpp"
00018 #include "CouenneExprPow.hpp"
00019 #include "CouenneExprAux.hpp"
00020 #include "CouenneExprClone.hpp"
00021 #include "CouenneProblem.hpp"
00022 
00023 using namespace Couenne;
00024 
00025 
00027 
00028 void exprMul::getBounds (expression *&lb, expression *&ub) {
00029 
00030   int i;
00031 
00032   if ((arglist_ [i=0] -> Type () == CONST) ||
00033       (arglist_ [i=1] -> Type () == CONST)) {
00034 
00035     CouNumber c = arglist_ [i] -> Value ();
00036 
00037     if (!i && (arglist_ [1] -> Type () == CONST)) { 
00038 
00039       // !i means i==0, or the first is constant. If you are here,
00040       // both are constant, which should not happen...
00041 
00042       CouNumber prod = c * arglist_ [1] -> Value ();
00043 
00044       lb = new exprConst (prod);
00045       ub = new exprConst (prod);
00046 
00047       return;
00048     }
00049     else {
00050 
00051       // expression is of the type c*x
00052 
00053       expression *lbi, *ubi;
00054       arglist_ [1-i] -> getBounds (lbi, ubi);
00055 
00056       if (c >= 0) {
00057         lb = new exprMul (new exprConst (c), lbi);
00058         ub = new exprMul (new exprConst (c), ubi);
00059       } else {
00060         lb = new exprMul (new exprConst (c), ubi);
00061         ub = new exprMul (new exprConst (c), lbi);
00062       }
00063     }
00064   }
00065   else {
00066 
00067     // expression is of the type x*y
00068 
00069     expression **almin = new expression * [4];
00070     expression **almax = new expression * [4];
00071 
00072     arglist_ [0] -> getBounds (almin [0], almin [1]);
00073     arglist_ [1] -> getBounds (almin [2], almin [3]);
00074 
00075     almax [0] = new exprClone (almin [0]);
00076     almax [1] = new exprClone (almin [1]);
00077     almax [2] = new exprClone (almin [2]);
00078     almax [3] = new exprClone (almin [3]);
00079 
00080     lb = new exprLBMul (almin, 4);
00081     ub = new exprUBMul (almax, 4);
00082   }
00083 }
00084 
00085 
00087 
00088 void exprMul::getBounds (CouNumber &lb, CouNumber &ub) {
00089 
00090   CouNumber lb1, ub1, lb2, ub2;
00091 
00092   arglist_ [0] -> getBounds (lb1, ub1);
00093   arglist_ [1] -> getBounds (lb2, ub2);
00094 
00095   if (ub1 < 0) { // use lb1, dominant
00096     if      (ub2 < 0) {lb = safeProd(ub1,ub2); ub = safeProd(lb1,lb2);}
00097     else if (lb2 > 0) {lb = safeProd(lb1,ub2); ub = safeProd(ub1,lb2);}
00098     else              {lb = safeProd(lb1,ub2); ub = safeProd(lb1,lb2);}
00099   } else if (lb1 > 0) { // use ub1, dominant
00100     if      (ub2 < 0) {lb = safeProd(ub1,lb2); ub = safeProd(lb1,ub2);}
00101     else if (lb2 > 0) {lb = safeProd(lb1,lb2); ub = safeProd(ub1,ub2);}
00102     else              {lb = safeProd(ub1,lb2); ub = safeProd(ub1,ub2);}
00103   } else { // there is a zero to consider
00104     if      (ub2 < 0) {lb = safeProd(ub1,lb2); ub = safeProd(lb1,lb2);}
00105     else if (lb2 > 0) {lb = safeProd(lb1,ub2); ub = safeProd(ub1,ub2);}
00106     else              {lb = CoinMin (safeProd(lb1,ub2), safeProd(lb2,ub1));
00107                        ub = CoinMax (safeProd(lb1,lb2), safeProd(ub1,ub2));}
00108   }
00109 }

Generated on Thu Nov 10 03:05:43 2011 by  doxygen 1.4.7