CouenneExprPow.hpp

Go to the documentation of this file.
00001 /* $Id: CouenneExprPow.hpp 940 2013-01-13 19:49:02Z pbelotti $
00002  *
00003  * Name:    CouenneExprPow.hpp
00004  * Author:  Pietro Belotti
00005  * Purpose: definition of powers, specifically with fractional
00006  *          exponent (odd/even/signed: see appropriate files)
00007  *
00008  * (C) Carnegie-Mellon University, 2006-11.
00009  * This file is licensed under the Eclipse Public License (EPL)
00010  */
00011 
00012 #ifndef COUENNE_EXPRPOW_HPP
00013 #define COUENNE_EXPRPOW_HPP
00014 
00015 #include <math.h>
00016 #include <stdio.h>
00017 
00018 #include "CouenneExprOp.hpp"
00019 #include "CouenneExprMul.hpp"
00020 #include "CouenneExprClone.hpp"
00021 #include "CouenneExprConst.hpp"
00022 
00023 namespace Couenne {
00024 
00025 class funtriplet;
00026 
00027 
00029 
00030 class exprPow: public exprOp {
00031 
00032  private:
00033 
00035   bool issignpower_;
00036 
00037  public:
00038 
00040   exprPow (expression **al, int n = 2, bool signpower = false): 
00041     exprOp (al, n), issignpower_ (signpower) {} //< non-leaf expression, with argument list
00042 
00044   exprPow (expression *arg0, expression *arg1, bool signpower = false):
00045     exprOp (arg0, arg1), issignpower_ (signpower) {}
00046 
00048   expression *clone (Domain *d = NULL) const
00049   {return new exprPow (clonearglist (d), nargs_, issignpower_);}
00050 
00052   virtual std::string printOp () const
00053   {return "^";}
00054 
00056   virtual CouNumber operator () ();
00057 
00059   virtual CouNumber gradientNorm (const double *x);
00060 
00062   virtual expression *differentiate (int index); 
00063 
00065   virtual expression *simplify ();
00066 
00068   virtual int Linearity ();
00069 
00071   virtual bool isInteger ();
00072 
00074   virtual void getBounds (expression *&, expression *&);
00075 
00077   virtual void getBounds (CouNumber &lb, CouNumber &ub);
00078 
00081   virtual exprAux *standardize (CouenneProblem *p, bool addAux = true);
00082 
00084   virtual void generateCuts (expression *w, //const OsiSolverInterface &si, 
00085                              OsiCuts &cs, const CouenneCutGenerator *cg, 
00086                              t_chg_bounds * = NULL, int = -1, 
00087                              CouNumber = -COUENNE_INFINITY, 
00088                              CouNumber =  COUENNE_INFINITY);
00089 
00092   virtual expression *getFixVar () 
00093   {return arglist_ [0];}
00094 
00096   virtual enum expr_type code () 
00097   {return (issignpower_ ? COU_EXPRSIGNPOW : COU_EXPRPOW);}
00098 
00100   virtual bool impliedBound (int, CouNumber *, CouNumber *, t_chg_bounds *, enum auxSign = expression::AUX_EQ);
00101 
00104   virtual CouNumber selectBranch (const CouenneObject *obj, 
00105                                   const OsiBranchingInformation *info,
00106                                   expression * &var, 
00107                                   double * &brpts, 
00108                                   double * &brDist, // distance of current LP
00109                                                     // point to new convexifications
00110                                   int &way);
00111 
00113   virtual void closestFeasible (expression *varind,
00114                                 expression *vardep, 
00115                                 CouNumber &left,
00116                                 CouNumber &right) const;
00117 
00120   virtual bool isCuttable (CouenneProblem *problem, int index) const;
00121 
00123   virtual bool isSignpower () const { return issignpower_; } 
00124 };
00125 
00126 
00128 
00129 inline CouNumber safe_pow (CouNumber base, 
00130                            CouNumber exponent, bool signpower = false) {
00131 
00132   double 
00133     lbase     = base,
00134     lexponent = exponent,
00135     retval    = 0.;
00136 
00137   if (lbase < 0.) {
00138 
00139     register int rndexp = COUENNE_round (lexponent);
00140 
00141     if (((fabs (lexponent - rndexp) < COUENNE_EPS) ||
00142          ((fabs (lexponent) > COUENNE_EPS) && 
00143           (fabs (1. / lexponent - (rndexp = COUENNE_round (1. / lexponent))) < COUENNE_EPS)))) {
00144       if ((rndexp % 2) || signpower)
00145         retval = (- pow (- lbase, lexponent)); // x^k, x negative, k odd  or signed power
00146       else retval = pow (- lbase, lexponent);  // x^k, x negative, k even or signed power
00147     }
00148     else retval =  0.; // this is incorrect but avoids nan's
00149   }
00150   else if (fabs (lbase) >= COUENNE_INFINITY) {
00151 
00152     if (lbase <= -COUENNE_INFINITY) {
00153 
00154       register int intk = COUENNE_round (lexponent);
00155 
00156       if ((fabs (lexponent - intk) < COUENNE_EPS) && (intk % 2 || signpower))
00157         retval = (lexponent < 0.) ? 0. : -COUENNE_INFINITY;
00158     }
00159     else retval = (lexponent < 0.) ? 0. : COUENNE_INFINITY;
00160   }
00161   else
00162     retval = (pow (lbase, lexponent));
00163 
00164   return (CouNumber) (retval);
00165 }
00166 
00167 
00169 inline CouNumber exprPow::operator () () {
00170   //  return (currValue_ = safe_pow (base, exponent));
00171   return safe_pow ((**arglist_) (), (*(arglist_ [1])) (), issignpower_);
00172 }
00173 
00174 
00176 void addPowEnvelope (const CouenneCutGenerator *, OsiCuts &, int, int,
00177                      CouNumber, CouNumber, CouNumber, CouNumber, CouNumber, int, bool = false);
00178 
00180 CouNumber powNewton (CouNumber, CouNumber, unary_function, unary_function, unary_function);
00181 
00183 CouNumber powNewton (CouNumber, CouNumber, funtriplet *);
00184 
00185 }
00186 
00187 #endif
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines

Generated on 17 Feb 2015 for Couenne by  doxygen 1.6.1