BTPerfIndicator.cpp
Go to the documentation of this file.
1 /* $Id: BTPerfIndicator.cpp 1004 2013-10-13 16:04:19Z pbelotti $
2  *
3  * Name: BTPerfIndicator.cpp
4  * Author: Pietro Belotti
5  * Purpose: Measures performance of BT in terms of shrunken bounds -- implementation
6  *
7  * (C) Pietro Belotti, 2011.
8  * This file is licensed under the Eclipse Public License (EPL)
9  */
10 
11 #include "CouenneTypes.hpp"
12 #include "CouennePrecisions.hpp"
13 #include "CouenneProblem.hpp"
14 #include "math.h"
16 
17 using namespace Couenne;
18 
20 void CouenneBTPerfIndicator::update (const CouNumber *lb, const CouNumber *ub, int depth) const {
21 
22  assert (oldLB_ != NULL &&
23  oldUB_ != NULL);
24 
25  double
26  curWei = 1. / CoinMax (1., (double) depth),
27  newWS = weightSum_ + curWei;
28 
29  // Compute improvement in bounds:
30 
31  int
32  nFixed = 0,
33  nShr = 0,
34  nShrDbl = 0,
35  nPrInf = 0;
36 
37  double ratio = 0.;
38 
39  CouNumber *optimum = problem_ -> bestSol ();
40 
41  for (int i=0; i<problem_ -> nVars (); ++i) {
42 
43  CouNumber
44  olb = oldLB_ [i], oub = oldUB_ [i],
45  nlb = lb [i], nub = ub [i];
46 
47  if (nlb < olb) nlb = olb;
48  if (nub > oub) nub = oub;
49 
50  // Check if optimal solution violated
51 
52  if (optimum &&
53  ((optimum [i] < nlb - COUENNE_EPS && optimum [i] >= olb) ||
54  (optimum [i] > nub + COUENNE_EPS && optimum [i] <= oub)))
55 
56  printf (" %30s cuts optimum at x_%d=%e: [%e,%e] --> [%e,%e], diff:%e\n",
57  name_.c_str (),
58  i, optimum [i],
59  olb, oub,
60  nlb, nub,
61  CoinMax (nlb - optimum [i],
62  optimum [i] - nub));
63 
64  // Check if bound has worsened rather than improved
65 
66  if ((((olb > -COUENNE_INFINITY / 1e4) && (nlb < olb - COUENNE_EPS)) ||
67  ((oub < COUENNE_INFINITY / 1e4) && (nub > oub + COUENNE_EPS))) &&
68  ((nlb >= nub + 2 - 1e-5) && i == 0)) // check this is not a wiping cut
69 
70  printf (" %30s makes bound worse (x%d): [%e,%e] --> [%e,%e], diff:%e\n",
71  name_.c_str (),
72  i,
73  olb, oub,
74  nlb, nub,
75  CoinMax (olb - nlb,
76  nub - oub));
77 
78  if (fabs (nlb - nub) < COUENNE_EPS) {
79 
80  if (fabs (olb - oub) > COUENNE_EPS)
81  ++nFixed;
82 
83  } else if (nlb >= nub + 1e2 * COUENNE_EPS) { // infeasible
84 
85  ++ nPrInf;
86  nFixed = nShr = nShrDbl = 0;
87  ratio = 0.;
88  break;
89 
90  } else if ((nlb > -COUENNE_INFINITY) &&
91  (nub < COUENNE_INFINITY)) { // finite bounds
92 
93  if (olb <= -COUENNE_INFINITY ||
94  oub >= COUENNE_INFINITY) {
95 
96  if ((olb <= -COUENNE_INFINITY) &&
97  (oub >= COUENNE_INFINITY)) // case 2a: actually it was [-inf,+inf]
98 
99  nShr += 2;
100 
101  else ++nShr;
102 
103  } else {
104 
105  // printf ("{%g}\t", ratio);
106 
107  ratio += (log (CoinMax (1e-6, oub - olb)) -
108  log (CoinMax (1e-6, nub - nlb)));
109 
110  // printf ("%g\tlog (%g-%g) - log (%g-%g) = log %g - log %g = %g - %g = %g ===> %g, %g [%g,%g,%g]\n",
111  // boundRatio_ * weightSum_,
112  // oub, olb, nub, nlb, oub - olb, nub - nlb,
113  // log (oub - olb), log (nub - nlb),
114  // log (oub - olb) - log (nub - nlb),
115  // ratio, boundRatio_, weightSum_, curWei, newWS);
116 
117  }
118  } else if ((olb <= -COUENNE_INFINITY) &&
119  (oub >= COUENNE_INFINITY))
120  ++nShrDbl;
121  }
122 
123  // Update
124 
125  ++nRuns_;
126 
127  ratio /= log ((double) 2.); // so that it is readable in terms of halvings of the bound interval
128 
129  boundRatio_ = (boundRatio_ * weightSum_ + curWei * ratio) / newWS;
130  shrunkInf_ = (shrunkInf_ * weightSum_ + curWei * nShr) / newWS;
131  shrunkDoubleInf_ = (shrunkDoubleInf_ * weightSum_ + curWei * nShrDbl) / newWS;
132  nFixed_ = (nFixed_ * weightSum_ + curWei * nFixed) / newWS;
133 
134  nProvedInfeas_ += nPrInf;
135 
136  weightSum_ = newWS;
137 
138  delete [] oldLB_;
139  delete [] oldUB_;
140 
141  oldLB_ = NULL;
142  oldUB_ = NULL;
143 }
double nFixed_
Whose performance is this?
CouExpr & log(CouExpr &e)
double * oldLB_
total weight (used to give an average indicator at the end of Couenne)
double boundRatio_
number of fixed variables
double shrunkInf_
average bound width shrinkage
int nRuns_
CPU time spent on this.
void fint fint fint real fint real real real real real real real real real * e
static double ratio(Bigint *a, Bigint *b)
Definition: OSdtoa.cpp:1460
#define COUENNE_EPS
double nProvedInfeas_
average # bounds that went from doubly infinite to infinite
double * oldUB_
old lower bounds (initial, i.e. before BT)
double shrunkDoubleInf_
average # bounds that went from infinite to finite (counts twice if [-inf,inf] to [a...
double CouNumber
main number type in Couenne
#define COUENNE_INFINITY
CouenneProblem * problem_
number of runs
void update(const CouNumber *lb, const CouNumber *ub, int depth) const
double weightSum_
average # proofs of infeasibility