infeasibility.cpp
Go to the documentation of this file.
1 /* $Id: infeasibility.cpp 875 2012-07-31 13:02:43Z pbelotti $
2  *
3  * Name: infeasibility.cpp
4  * Authors: Pietro Belotti, Carnegie Mellon University
5  * Purpose: Compute infeasibility of a variable, looking at all expressions it appears in
6  *
7  * (C) Carnegie-Mellon University, 2008-10.
8  * This file is licensed under the Eclipse Public License (EPL)
9  */
10 
11 #include "CoinHelperFunctions.hpp"
12 
13 #include "CouenneProblem.hpp"
14 #include "CouenneVarObject.hpp"
15 
16 using namespace Ipopt;
17 using namespace Couenne;
18 
20 const CouNumber weiMin = 0.8; // for minimum of infeasibilities of nonlinear objects
21 const CouNumber weiMax = 1.3; // maximum
22 const CouNumber weiSum = 0.1; // sum
23 const CouNumber weiAvg = 0.0; // average
24 
25 
29 double CouenneVarObject::infeasibility (const OsiBranchingInformation *info, int &way) const {
30 
31  assert (reference_);
32  int index = reference_ -> Index ();
33 
34  /*printf ("===INFEAS %d = %g [%g,%g]\n",
35  index,
36  info -> solution_ [index],
37  info -> lower_ [index],
38  info -> upper_ [index]);*/
39 
40  /*if (info -> lower_ [index] >=
41  info -> upper_ [index] - CoinMin (COUENNE_EPS, feas_tolerance_))
42  return (reference_ -> isInteger ()) ?
43  intInfeasibility (info -> solution_ [index]) : 0.;*/
44 
45  problem_ -> domain () -> push
46  (problem_ -> nVars (),
47  info -> solution_,
48  info -> lower_,
49  info -> upper_,
50  false); // point is not copied, only its pointer
51 
53 
54  CouNumber retval = checkInfeasibility (info);
55 
57 
58  if (//(retval > CoinMin (COUENNE_EPS, feas_tolerance_)) &&
59  (jnlst_ -> ProduceOutput (J_DETAILED, J_BRANCHING))) {
60 
61  const std::set <int> &dependence = problem_ -> Dependence () [index];
62 
63  printf ("infeasVar x%d %-10g [", reference_ -> Index (), retval);
64  reference_ -> print ();
65  if ((dependence.size () == 0) && (reference_ -> Image ())) { // if no list, print image
66  printf (" := ");
67  reference_ -> Image () -> print ();
68  }
69  printf ("]\n");
70  }
71 
72  // add term to stop branching on very tiny intervals
73 
74  // Compute the up and down estimates here
75  // TODO: We probably only have to do that if pseudo costs option has
76  // been chosen
77 
78  const CouenneObject *obj_ignored = NULL; // only care about it in CouenneVarObject.cpp
79 
80  CouNumber brkPt = computeBranchingPoint (info, way, obj_ignored);
81 
82  if (fabs (brkPt) > 1e27) // why 1e27? Check ClpModel.cpp:613
83 
84  retval = 1e-4; // set infeasibility to a small value hoping it
85  // will be beaten by another variable
86  else {
87 
88  if (pseudoMultType_ != PROJECTDIST)
89  setEstimates (info, &retval, &brkPt);
90 
91  if (jnlst_ -> ProduceOutput (J_DETAILED, J_BRANCHING)) {
92  printf("index = %d up = %e down = %e bounds [%e,%e] brpt = %e inf = %e\n",
93  index, upEstimate_, downEstimate_,
94  info -> lower_ [index],
95  info -> upper_ [index], brkPt, retval);
96  }
97 
98  if (retval <= CoinMin (COUENNE_EPS, feas_tolerance_))
99  retval = 0;
100  }
101 
102  problem_ -> domain () -> pop (); // domain not used below
103 
104  int refInd = reference_ -> Index ();
105 
106  if (reference_ -> isInteger ()) {
107  CouNumber intinfeas = intInfeasibility (info -> solution_ [refInd],
108  info -> lower_ [refInd],
109  info -> upper_ [refInd]);
110  if ((intinfeas > retval) &&
111  (intinfeas > info -> integerTolerance_))
112  retval = intinfeas;
113  }
114 
115  //printf ("infVar x%d ==> returning %g\n", reference_ -> Index (), (reference_ -> isInteger ()) ?
116  //CoinMax (retval, intInfeasibility (info -> solution_ [reference_ -> Index ()])) :
117  //retval);
118 
119  jnlst_ -> Printf (J_DETAILED, J_BRANCHING,
120  "infVar x%d ==> returning %e\n", reference_ -> Index (), (reference_ -> isInteger ()) ?
121  CoinMax (retval, intInfeasibility (info -> solution_ [refInd],
122  info -> lower_ [refInd],
123  info -> upper_ [refInd])) :
124  retval);
125 
126  return retval;
127 
128  // (reference_ -> isInteger ()) ?
129  // CoinMax (retval, intInfeasibility (info -> solution_ [reference_ -> Index ()])) :
130  // retval;
131 }
132 
133 
136 double CouenneVarObject::checkInfeasibility (const OsiBranchingInformation * info) const {
137 
138  int indexVar = reference_ -> Index ();
139 
140  const std::set <int> &dependence = problem_ -> Dependence () [indexVar];
141 
142  if (dependence.size () == 0) { // this is a top level auxiliary,
143  // nowhere an independent
144 
145  // check first if this variable is fixed. If so, it's useless to branch on it
146  if (fabs (info -> upper_ [indexVar] -
147  info -> lower_ [indexVar]) /
148  (1. + fabs (info -> solution_ [indexVar])) < COUENNE_EPS)
149 
150  return (reference_ -> isInteger ()) ?
151  intInfeasibility (info -> solution_ [indexVar],
152  info -> lower_ [indexVar],
153  info -> upper_ [indexVar]) : 0;
154 
155  // otherwise, return a nonzero infeasibility, if necessary. It
156  // might make sense to branch on it
157  const CouenneObject *obj = problem_ -> Objects () [reference_ -> Index ()];
158 
159  double retval = (obj -> Reference ()) ?
160  (1. - 1. / (1. + info -> upper_ [indexVar] - info -> lower_ [indexVar])) *
161  weiSum * obj -> checkInfeasibility (info) : 0.;
162 
163  //return retval;
164 
165  return (reference_ -> isInteger ()) ?
166  CoinMax (retval, intInfeasibility (info -> solution_ [indexVar],
167  info -> lower_ [indexVar],
168  info -> upper_ [indexVar])) :
169  retval;
170 
171  } else {
172 
173  CouNumber
174  infsum = 0.,
175  infmax = 0.,
176  infmin = COIN_DBL_MAX;
177 
178  for (std::set <int>::const_iterator i = dependence.begin ();
179  i != dependence.end (); ++i) {
180 
181  // *i is the index of an auxiliary that depends on reference_
182 
183  const CouenneObject *obj = problem_ -> Objects () [*i];
184  CouNumber infeas = (obj -> Reference ()) ? obj -> checkInfeasibility (info) : 0.;
185 
186  if (infeas > infmax) infmax = infeas;
187  if (infeas < infmin) infmin = infeas;
188  infsum += infeas;
189  }
190 
191  double retval =
192  ((infmax < 1.e20) ? // avoid returning zero infeasibility in
193  // almost fixed variables that are at some
194  // denominator (see example triv1.nl from
195  // Stefano Coniglio)
196 
197  // 1e20 is probably too optimistic, expect
198  // instances that fail (i.e. give -9.99e+12)
199  // for much smaller values
200 
201  // neglect it if variable has small bound interval (check
202  // x84=x83/x5 in csched1.nl)
203  (1. - 1. / (1. + info -> upper_ [indexVar] - info -> lower_ [indexVar])) : 1.) *
204  // to consider maximum, minimum, and sum/avg of the infeasibilities
205  (weiSum * infsum +
206  weiAvg * (infsum / CoinMax (1., (CouNumber) dependence.size ())) +
207  weiMin * infmin +
208  weiMax * infmax);
209 
210  //return retval;
211 
212  return (reference_ -> isInteger ()) ?
213  CoinMax (retval, intInfeasibility (info -> solution_ [indexVar],
214  info -> lower_ [indexVar],
215  info -> upper_ [indexVar])) :
216  retval;
217  }
218 }
void fint fint fint real fint real real real real real real real real real fint real fint fint fint real fint fint fint fint * info
OsiObject for auxiliary variables $w=f(x)$.
const Ipopt::EJournalCategory J_BRANCHING(Ipopt::J_USER1)
const CouNumber weiMin
weights for computing infeasibility
const CouNumber weiSum
void fint fint fint real fint real real real real real real real real real * e
#define COUENNE_EPS
double CouNumber
main number type in Couenne
const CouNumber weiAvg
const CouNumber weiMax
bool isInteger(CouNumber x)
is this number integer?