29 #define FREE_LHS_RHS 1 30 #define FREE_CONSTRAINT 1 31 #define EMPTY_CONSTRAINT 1 32 #define ROW_SINGLETON 1 33 #define FORCE_CONSTRAINT 1 36 #define EMPTY_COLUMN 1 37 #define FIX_VARIABLE 1 38 #define FREE_ZERO_OBJ_VARIABLE 1 39 #define ZERO_OBJ_COL_SINGLETON 1 40 #define DOUBLETON_EQUATION 1 41 #define FREE_COL_SINGLETON 1 43 #define DOMINATED_COLUMN 1 44 #define WEAKLY_DOMINATED_COLUMN 1 45 #define MULTI_AGGREGATE 1 47 #define TRIVIAL_HEURISTICS 1 56 #define DUPLICATE_ROWS 1 57 #define DUPLICATE_COLS 1 61 #define CHECK_BASIC_DIM 70 for(
int rs = 0; rs <
nRows; ++rs)
76 for(
int cs = 0; cs <
nCols; ++cs)
81 assert(numBasis == nRows);
82 return numBasis ==
nRows;
89 assert(
isZero(s[m_i], 1e-9));
96 MSG_DEBUG( std::cout <<
"RowObjPS: removing slack column " << m_j <<
" (" << cStatus[m_j] <<
") for row " << m_i <<
" (" << rStatus[m_i] <<
").\n" );
100 switch( cStatus[m_j] )
109 rStatus[m_i] = cStatus[m_j];
116 #ifdef CHECK_BASIC_DIM 132 rStatus[m_old_i] = rStatus[m_i];
137 for (
int k = 0; k < m_row.size(); ++k)
138 slack += m_row.value(k) * x[m_row.index(k)];
148 #ifdef CHECK_BASIC_DIM 163 rStatus[m_old_i] = rStatus[m_i];
174 #ifdef CHECK_BASIC_DIM 189 rStatus[m_old_i] = rStatus[m_i];
191 Real aij = m_col[m_i];
194 s[m_i] = aij * x[m_j];
199 for(
int k = 0; k < m_col.size(); ++k)
201 if (m_col.index(k) != m_i)
202 val -= m_col.value(k) * y[m_col.index(k)];
205 Real newLo = (aij > 0) ? m_lhs/aij : m_rhs/aij;
206 Real newUp = (aij > 0) ? m_rhs/aij : m_lhs/aij;
211 if(newLo <= m_oldLo && newUp >= m_oldUp)
220 assert(
EQrel(newLo, x[m_j],
eps()));
228 else if((
EQrel(m_oldLo, x[m_j],
eps()) && r[m_j] <= -
eps())
229 || (
EQrel(m_oldUp, x[m_j],
eps()) && r[m_j] >=
eps())
249 else if(
EQrel(newLo, m_oldUp,
eps()))
264 assert(
EQrel(m_oldUp, x[m_j],
eps()));
272 else if(
EQrel(newUp, m_oldLo,
eps()))
287 assert(
EQrel(m_oldLo, x[m_j],
eps()));
350 #ifdef CHECK_BASIC_DIM 365 rStatus[m_old_i] = rStatus[m_i];
371 int cBasisCandidate = -1;
372 Real maxViolation = -1.0;
375 for(
int k = 0; k < m_row.size(); ++k)
377 int cIdx = m_row.index(k);
378 Real aij = m_row.value(k);
379 Real oldLo = m_oldLowers[k];
380 Real oldUp = m_oldUppers[k];
382 switch(cStatus[cIdx])
393 if( violation > maxViolation && ( (
EQrel(oldLo, x[cIdx],
eps()) && r[cIdx] < -
eps()) || (
EQrel(oldUp, x[cIdx],
eps()) && r[cIdx] >
eps()) ) )
395 maxViolation = violation;
396 cBasisCandidate =
cIdx;
411 if(cBasisCandidate >= 0)
415 assert(cBasisCandidate == m_row.index(bas_k));
420 Real aij = m_row.value(bas_k);
421 Real multiplier = r[cBasisCandidate]/aij;
422 r[cBasisCandidate] = 0.0;
424 for(
int k = 0; k < m_row.size(); ++k)
430 r[m_row.index(k)] -= m_row.value(k) * multiplier;
434 Real val = m_objs[bas_k];
437 for(
int k = 0; k < basis_col.
size(); ++k)
439 if (basis_col.
index(k) != m_i)
440 val -= basis_col.
value(k) * y[basis_col.
index(k)];
451 #ifdef CHECK_BASIC_DIM 468 cStatus[m_old_j] = cStatus[m_j];
474 for(
int k = 0; k < m_col.size(); ++k)
475 s[m_col.index(k)] += m_col.value(k) * x[m_j];
480 for(
int k = 0; k < m_col.size(); ++k)
481 val -= m_col.value(k) * y[m_col.index(k)];
486 if( m_lower == m_upper )
488 assert(
EQrel(m_lower, m_val));
494 assert(
EQrel(m_val, m_lower) ||
EQrel(m_val, m_upper) || m_val == 0.0);
499 #ifdef CHECK_BASIC_DIM 515 cStatus[m_j] = m_status;
525 cStatus[m_old_j] = cStatus[m_j];
527 int rIdx = m_old_i - m_col.size() + 1;
529 for(
int k = 0; k < m_col.size(); ++k)
531 int rIdx_new = m_col.index(k);
532 s[
rIdx] = s[rIdx_new];
533 y[
rIdx] = y[rIdx_new];
534 rStatus[
rIdx] = rStatus[rIdx_new];
546 for(
int k = 0; k < m_rows.size(); ++k)
549 const SVector& row = m_rows[k];
551 for(
int l = 0; l < row.
size(); ++l)
553 if (row.
index(l) != m_j)
562 Real z = (m_lRhs[k] / scale) - (val / scale);
567 Real up = z * scale / row[m_j];
577 if (m_bnd < minRowUp)
589 for(
int k = 0; k < m_rows.size(); ++k)
592 const SVector& row = m_rows[k];
594 for(
int l = 0; l < row.
size(); ++l)
596 if (row.
index(l) != m_j)
605 Real z = (m_lRhs[k] / scale) - (val / scale);
610 Real lo = z * scale / row[m_j];
620 if (m_bnd > maxRowLo)
629 for(
int k = 0; k < m_col.size(); ++k)
630 s[m_col.index(k)] = slack[k] + m_col.value(k) * x[m_j];
635 for(
int k = 0; k < m_col.size(); ++k)
637 int idx = m_col.index(k);
638 y[idx] = m_rowObj[idx];
642 for(
int k = 0; k < m_col.size(); ++k)
664 #ifdef CHECK_BASIC_DIM 679 cStatus[m_old_j] = cStatus[m_j];
682 Real aij = m_row[m_j];
688 throw SPxException(
"Simplifier: infinite activities - aborting unsimplification");
698 Real z1 = (m_lhs / scale1) - (s[m_i] / scale1);
699 Real z2 = (m_rhs / scale2) - (s[m_i] / scale2);
706 Real lo = (aij > 0) ? z1 * scale1 / aij : z2 * scale2 / aij;
707 Real up = (aij > 0) ? z2 * scale2 / aij : z1 * scale1 / aij;
714 assert(
LErel(lo, up));
719 if ( m_lower == m_upper )
739 if ( m_lower == m_upper )
759 assert(
EQrel(m_lower, m_upper));
796 s[m_i] += aij * x[m_j];
799 r[m_j] = -1.0 * aij * y[m_i];
803 #ifdef CHECK_BASIC_DIM 819 rStatus[m_old_i] = rStatus[m_i];
824 cStatus[m_old_j] = cStatus[m_j];
828 Real aij = m_row[m_j];
830 for(
int k = 0; k < m_row.size(); ++k)
832 if (m_row.index(k) != m_j)
833 val += m_row.value(k) * x[m_row.index(k)];
841 Real z = (m_lRhs / scale) - (val / scale);
846 x[m_j] = z * scale / aij;
850 y[m_i] = m_obj / aij;
863 #ifdef CHECK_BASIC_DIM 880 (( m_maxSense && ((r[m_j] > 0 && m_strictUp) || (r[m_j] < 0 && m_strictLo))) ||
881 (!m_maxSense && ((r[m_j] > 0 && m_strictLo) || (r[m_j] < 0 && m_strictUp)))))))
884 Real aik = m_col[m_i];
886 for(
int _k = 0; _k < m_col.size(); ++_k)
888 if (m_col.index(_k) != m_i)
889 val -= m_col.value(_k) * y[m_col.index(_k)];
895 r[m_j] = m_jObj - val * m_aij / aik;
904 if(
GT(r[m_j], 0) || (
isZero(r[m_j]) &&
EQ(x[m_j], m_Lo_j)) )
913 #ifdef CHECK_BASIC_DIM 928 for(
int i = m_perm.size() - 1; i >= 0; --i)
932 int rIdx_new = m_perm[i];
934 s[
rIdx] = s[rIdx_new];
935 y[
rIdx] = y[rIdx_new];
936 rStatus[
rIdx] = rStatus[rIdx_new];
942 for(
int k = 0; k < m_scale.size(); ++k)
944 if (m_scale.index(k) != m_i)
945 s[m_scale.index(k)] = s[m_i] / m_scale.value(k);
949 bool haveSetBasis =
false;
951 for(
int k = 0; k < m_scale.size(); ++k)
953 int i = m_scale.index(k);
959 y[i] = m_rowObj.value(k);
966 if (rStatus[m_i] ==
SPxSolver::FIXED && (i == m_maxLhsIdx || i == m_minRhsIdx))
969 y[i] = y[m_i] * m_scale.value(k);
972 if(m_isLhsEqualRhs[k])
976 else if(i == m_maxLhsIdx)
982 assert(i == m_minRhsIdx);
993 y[i] = y[m_i] * m_scale.value(k);
1004 y[i] = y[m_i] * m_scale.value(k);
1005 y[m_i] = m_i_rowObj;
1010 haveSetBasis =
true;
1015 y[i] = m_rowObj.value(k);
1020 #ifdef CHECK_BASIC_DIM 1040 #ifdef CHECK_BASIC_DIM 1053 for(
int i = m_perm.size() - 1; i >= 0; --i)
1057 int cIdx_new = m_perm[i];
1059 x[
cIdx] = x[cIdx_new];
1060 r[
cIdx] = r[cIdx_new];
1061 cStatus[
cIdx] = cStatus[cIdx_new];
1110 assert(
LErel(m_loJ, 0.0));
1111 assert(
GErel(m_upJ, 0.0));
1112 assert(
LErel(m_loK, 0.0));
1113 assert(
GErel(m_upK, 0.0));
1121 else if (
LErel(m_loK, 0.0) &&
GErel(m_upK, 0.0))
1133 else if (
LErel(m_loJ, 0.0) &&
GErel(m_upJ, 0.0))
1148 Real z1 = (x[m_k] / scale1) - (m_loK / scale1);
1149 Real z2 = (x[m_k] / scale2) - (m_upK / scale2);
1156 if( m_loJ <= -infinity && m_upJ >=
infinity && m_loK <= -infinity && m_upK >=
infinity )
1161 else if( m_scale > 0.0 )
1163 if(
GErel(x[m_k], m_upK + m_scale * m_upJ) )
1168 x[m_k] -= m_scale * x[m_j];
1170 else if(
GErel(x[m_k], m_loK + m_scale * m_upJ) && m_upJ <
infinity )
1174 x[m_k] -= m_scale * x[m_j];
1176 else if(
GErel(x[m_k], m_upK + m_scale * m_loJ) && m_upK <
infinity )
1181 x[m_j] = z2 * scale2 / m_scale;
1183 else if(
GErel(x[m_k], m_loK + m_scale * m_loJ) && m_loJ > -
infinity )
1187 x[m_k] -= m_scale * x[m_j];
1189 else if(
GErel(x[m_k], m_loK + m_scale * m_loJ) && m_loK > -
infinity )
1194 x[m_j] = z1 * scale1 / m_scale;
1196 else if(
LTrel(x[m_k], m_loK + m_scale * m_loJ) )
1201 x[m_k] -= m_scale * x[m_j];
1210 assert(m_scale < 0.0);
1212 if(
GErel(x[m_k], m_upK + m_scale * m_loJ) )
1217 x[m_k] -= m_scale * x[m_j];
1219 else if(
GErel(x[m_k], m_loK + m_scale * m_loJ) && m_loJ > -
infinity )
1223 x[m_k] -= m_scale * x[m_j];
1225 else if(
GErel(x[m_k], m_upK + m_scale * m_upJ) && m_upK <
infinity )
1230 x[m_j] = z2 * scale2 / m_scale;
1232 else if(
GErel(x[m_k], m_loK + m_scale * m_upJ) && m_upJ <
infinity )
1236 x[m_k] -= m_scale * x[m_j];
1238 else if(
GErel(x[m_k], m_loK + m_scale * m_upJ) && m_loK > -
infinity )
1243 x[m_j] = z1 * scale1 / m_scale;
1245 else if(
LTrel(x[m_k], m_loK + m_scale * m_upJ) )
1250 x[m_k] -= m_scale * x[m_j];
1260 r[m_j] = m_scale * r[m_k];
1269 s[m_old_i] = s[m_i];
1270 y[m_old_i] = y[m_i];
1271 rStatus[m_old_i] = rStatus[m_i];
1274 x[m_old_j] = x[m_j];
1275 r[m_old_j] = r[m_j];
1276 cStatus[m_old_j] = cStatus[m_j];
1280 Real aij = m_row[m_j];
1282 for(
int k = 0; k < m_row.size(); ++k)
1284 if(m_row.index(k) != m_j)
1285 val += m_row.value(k) * x[m_row.index(k)];
1293 Real z = (m_const / scale) - (val / scale);
1298 x[m_j] = z * scale / aij;
1301 assert(!isOptimal || (
GE(x[m_j], m_lower) &&
LE(x[m_j], m_upper)));
1306 for(
int k = 0; k < m_col.size(); ++k)
1308 if(m_col.index(k) != m_i)
1309 dualVal += m_col.value(k) * y[m_col.index(k)];
1312 z = m_obj - dualVal;
1327 #ifdef CHECK_BASIC_DIM 1340 switch(cStatus[m_j])
1343 if(
LT(x[m_j], m_origupper,
eps()) &&
GT(x[m_j], m_origlower,
eps()))
1345 else if(
LT(x[m_j], m_origupper,
eps()))
1347 else if(
GT(x[m_j], m_origlower,
eps()))
1352 if(
GT(x[m_j], m_origlower,
eps()))
1357 if(
LT(x[m_j], m_origupper,
eps()))
1365 #ifdef CHECK_BASIC_DIM 1375 for(
int i = lp.
nRows() - 1; i >= 0; --i )
1407 for(
int i = lp.
nRows()-1; i >= 0; --i)
1417 else if (lhs > -
infinity && lhs < -maxVal)
1422 else if (lhs < infinity && lhs > maxVal)
1436 else if (rhs > -
infinity && rhs < -maxVal)
1441 else if (rhs < infinity && rhs > maxVal)
1460 for(
int j = 0; j < lp.
nCols(); ++j)
1470 else if (lo > -
infinity && lo < -maxVal)
1475 else if (lo < infinity && lo > maxVal)
1489 else if (up > -
infinity && up < -maxVal)
1494 else if (up < infinity && up > maxVal)
1506 Real absBnd = (lo > up) ? lo : up;
1515 while(i < col.
size())
1519 if (
isZero(aij * absBnd, tol))
1522 int row_j = row.
pos(j);
1530 <<
" removed, absBnd=" << absBnd
1540 else if(
isZero(aij, tol) )
1558 else if (obj > -
infinity && obj < -maxVal)
1563 else if (obj < infinity && obj > maxVal)
1570 if (remRows + remNzos + chgLRhs + chgBnds + objCnt > 0)
1578 << remRows <<
" rows, " 1579 << remNzos <<
" non-zeros, " 1580 << chgBnds <<
" col bounds, " 1581 << chgLRhs <<
" row bounds, " 1582 << objCnt <<
" objective coefficients" << std::endl; )
1591 bool minNegInfinite =
false;
1592 bool maxInfinite =
false;
1597 for (
int l = 0; l < row.
size(); ++l)
1599 if (colNumber < 0 || row.
index(l) != colNumber)
1605 minNegInfinite =
true;
1609 else if (
LT(row.
value(l), 0.0))
1612 minNegInfinite =
true;
1625 else if (
LT(row.
value(l), 0.0))
1656 minVal = (side - minRes)/val;
1661 maxVal = (side - maxRes)/val;
1663 else if(
GT(val, 0.0))
1668 minVal = (side - maxRes)/val;
1673 maxVal = (side - minRes)/val;
1694 bool zerovalid =
true;
1702 for(
int j = lp.
nCols()-1; j >= 0; --j)
1709 for(
int k = 0; k < col.
size(); ++k)
1740 lower =
MINIMUM(-largeValue, upper);
1752 lowersol[j] = lower;
1753 uppersol[j] = upper;
1755 if(downLocks[j] > upLocks[j])
1757 else if(downLocks[j] < upLocks[j])
1760 locksol[j] = (lower + upper)/2.0;
1762 lowerObj += lp.
maxObj(j)*lowersol[j];
1763 upperObj += lp.
maxObj(j)*uppersol[j];
1764 lockObj += lp.
maxObj(j)*locksol[j];
1800 for(
int i = lp.
nRows()-1; i >= 0; --i)
1805 for(
int k = 0; k < row.
size(); k++)
1822 for(
int j = lp.
nCols()-1; j >= 0; --j )
1829 pseudoObj += val*lp.
lower(j);
1835 pseudoObj += val*lp.
upper(j);
1844 for(
int j = lp.
nCols()-1; j >= 0; --j)
1863 else if(objval > 0.0)
1888 for(
int i = lp.
nRows()-1; i >= 0; --i)
1892 if (row.
size() == 0)
1900 <<
" rhs=" << lp.
rhs(i) << std::endl; )
1916 for(
int j = lp.
nCols()-1; j >= 0; --j)
1920 if (col.
size() == 0)
1923 <<
": empty -> maxObj=" << lp.
maxObj(j)
1924 <<
" lower=" << lp.
lower(j)
1925 <<
" upper=" << lp.
upper(j); )
1974 if (remRows + remCols > 0)
1980 << remRows <<
" rows, " 1981 << remCols <<
" cols" 1990 assert(row.
size() == 1);
1993 int j = row.
index(0);
1998 <<
": singleton -> val=" << aij
1999 <<
" lhs=" << lp.
lhs(i)
2000 <<
" rhs=" << lp.
rhs(i); )
2026 <<
" (" << lp.
lower(j)
2028 <<
" (" << lp.
upper(j)
2029 <<
")" << std::endl; )
2031 bool stricterUp =
false;
2032 bool stricterLo =
false;
2082 int oldRows = lp.
nRows();
2084 bool redundantLower;
2085 bool redundantUpper;
2089 for(
int i = lp.
nRows()-1; i >= 0; --i)
2100 for(
int k = 0; k < row.
size(); ++k)
2103 int j = row.
index(k);
2107 MSG_WARNING( (*
spxout), (*
spxout) <<
"Warning: tiny nonzero coefficient " << aij <<
" in row " << i <<
"\n" );
2115 lhsBnd += aij * lp.
lower(j);
2120 rhsBnd += aij * lp.
upper(j);
2127 rhsBnd += aij * lp.
lower(j);
2132 lhsBnd += aij * lp.
upper(j);
2138 if (rhsCnt <= 1 || lhsCnt <= 1)
2140 for(
int k = 0; k < row.
size(); ++k)
2143 int j = row.
index(k);
2145 redundantLower =
false;
2146 redundantUpper =
false;
2162 Real z = (lp.
lhs(i) / scale) - (rhsBnd / scale);
2170 lo = lp.
upper(j) + z * scale / aij;
2172 lo = z * scale / aij;
2180 <<
": redundant lower bound on x" << j
2181 <<
" -> lower=" << lo
2182 <<
" (" << lp.
lower(j)
2183 <<
")" << std::endl; )
2185 redundantLower =
true;
2199 Real z = (lp.
rhs(i) / scale) - (lhsBnd / scale);
2207 up = lp.
lower(j) + z * scale / aij;
2209 up = z * scale / aij;
2217 <<
": redundant upper bound on x" << j
2218 <<
" -> upper=" << up
2219 <<
" (" << lp.
upper(j)
2220 <<
")" << std::endl; )
2222 redundantUpper =
true;
2231 lhsBnd -= aij * lp.
lower(j);
2245 rhsBnd -= aij * lp.
upper(j);
2266 Real z = (lp.
lhs(i) / scale) - (rhsBnd / scale);
2274 up = lp.
lower(j) + z * scale / aij;
2276 up = z * scale / aij;
2284 <<
": redundant upper bound on x" << j
2285 <<
" -> upper=" << up
2286 <<
" (" << lp.
upper(j)
2287 <<
")" << std::endl; )
2289 redundantUpper =
true;
2302 Real z = (lp.
rhs(i) / scale) - (lhsBnd / scale);
2310 lo = lp.
upper(j) + z * scale / aij;
2312 lo = z * scale / aij;
2320 <<
": redundant lower bound on x" << j
2321 <<
" -> lower=" << lo
2322 <<
" (" << lp.
lower(j)
2323 <<
")" << std::endl; )
2325 redundantLower =
true;
2334 lhsBnd -= aij * lp.
upper(j);
2348 rhsBnd -= aij * lp.
lower(j);
2363 redundantLhs =
false;
2364 redundantRhs =
false;
2370 <<
": redundant lhs -> lhsBnd=" << lhsBnd
2371 <<
" lhs=" << lp.
lhs(i)
2374 redundantLhs =
true;
2379 <<
": redundant rhs -> rhsBnd=" << rhsBnd
2380 <<
" rhs=" << lp.
rhs(i)
2383 redundantRhs =
true;
2415 <<
": infeasible -> lhs=" << lp.
lhs(i)
2416 <<
" rhs=" << lp.
rhs(i)
2417 <<
" lhsBnd=" << lhsBnd
2418 <<
" rhsBnd=" << rhsBnd
2428 <<
": unconstrained -> removed" << std::endl; )
2435 remNzos += row.
size();
2444 #if EMPTY_CONSTRAINT 2446 if (row.
size() == 0)
2454 <<
" rhs=" << lp.
rhs(i) << std::endl; )
2474 if (row.
size() == 1)
2481 #if FORCE_CONSTRAINT 2487 <<
": forcing constraint fix on lhs ->" 2488 <<
" lhs=" << lp.
lhs(i)
2489 <<
" rhsBnd=" << rhsBnd
2496 for(
int k = 0; k < row.
size(); ++k)
2499 int j = row.
index(k);
2503 lowers[k] = lp.
lower(j);
2504 uppers[k] = lp.
upper(j);
2519 remNzos += row.
size();
2530 <<
": forcing constraint fix on rhs ->" 2531 <<
" rhs=" << lp.
rhs(i)
2532 <<
" lhsBnd=" << lhsBnd
2539 for(
int k = 0; k < row.
size(); ++k)
2542 int j = row.
index(k);
2546 lowers[k] = lp.
lower(j);
2547 uppers[k] = lp.
upper(j);
2562 remNzos += row.
size();
2572 assert(remRows > 0 || remNzos == 0);
2574 if (remRows + chgLRhs + chgBnds > 0)
2584 << remRows <<
" rows, " 2585 << remNzos <<
" non-zeros, " 2586 << chgBnds <<
" col bounds, " 2587 << chgLRhs <<
" row bounds; kept " 2588 << keptBnds <<
" column bounds, " 2589 << keptLRhs <<
" row bounds" 2617 int oldCols = lp.
nCols();
2618 int oldRows = lp.
nRows();
2620 for(
int j = lp.
nCols()-1; j >= 0; --j)
2628 <<
": infeasible bounds on x" << j
2629 <<
" -> lower=" << lp.
lower(j)
2630 <<
" upper=" << lp.
upper(j)
2636 if (col.
size() == 0)
2640 <<
": empty -> maxObj=" << lp.
maxObj(j)
2641 <<
" lower=" << lp.
lower(j)
2642 <<
" upper=" << lp.
upper(j); )
2700 for(
int k = 0; k < col.
size(); ++k)
2702 if (!loFree && !upFree)
2705 int i = col.
index(k);
2710 if (col.
value(k) > 0.0)
2718 else if (col.
value(k) < 0.0)
2736 <<
" unconstrained above ->"; )
2757 <<
" unconstrained below ->"; )
2775 #if FREE_ZERO_OBJ_VARIABLE 2776 bool unconstrained_below = loFree && lp.
lower(j) <= -
infinity;
2777 bool unconstrained_above = upFree && lp.
upper(j) >=
infinity;
2779 if (unconstrained_below || unconstrained_above)
2783 <<
" unconstrained " 2784 << (unconstrained_below ?
"below" :
"above")
2785 <<
" with zero objective (" << lp.
maxObj(j)
2786 <<
")" << std::endl; )
2792 SPxQuicksort(col_idx_sorted.mem(), col_idx_sorted.size(), compare);
2800 remRows += col.
size();
2801 for(
int k = col_idx_sorted.size()-1; k >= 0; --k)
2808 for(
int k = 0; k < col.
size(); ++k)
2810 int l = col.
index(k);
2829 <<
" fixed -> lower=" << lp.
lower(j)
2830 <<
" upper=" << lp.
upper(j) << std::endl; )
2835 remNzos += col.
size();
2845 if (col.
size() == 1)
2848 int i = col.
index(0);
2853 #if ZERO_OBJ_COL_SINGLETON 2855 <<
": singleton in row " << i
2856 <<
" with zero objective"; )
2864 lhs = lp.
lhs(i) - aij * lp.
upper(j);
2866 rhs = lp.
rhs(i) - aij * lp.
lower(j);
2871 lhs = lp.
lhs(i) - aij * lp.
lower(j);
2873 rhs = lp.
rhs(i) - aij * lp.
upper(j);
2887 <<
" (" << lp.
lhs(i)
2889 <<
" (" << lp.
rhs(i)
2890 <<
")" << std::endl; )
2925 #if DOUBLETON_EQUATION 2927 <<
": singleton in row " << i
2928 <<
" with doubleton equation ->"; )
2937 if (row.
index(0) == j)
2942 else if (row.
index(1) == j)
2964 Real z1 = (lhs / scale1) - (aij * lp.
upper(j) / scale1);
2965 Real z2 = (lhs / scale2) - (aij * lp.
lower(j) / scale2);
2992 <<
": lower=" << lp.
lower(k)
2994 <<
") upper=" << lp.
upper(k)
2996 <<
")" << std::endl; )
3024 #if FREE_COL_SINGLETON 3031 <<
": free singleton in inequality constraint" << std::endl; )
3078 <<
": free singleton removed" << std::endl; )
3082 for (
int h = 0; h < row.size(); ++h)
3084 int k = row.
index(h);
3088 Real new_obj = lp.
obj(k) - (lp.
obj(j) * row.value(h) / aij);
3095 remNzos += row.size();
3107 if (remCols + remRows > 0)
3115 << remRows <<
" rows, " 3116 << remCols <<
" cols, " 3117 << remNzos <<
" non-zeros, " 3118 << chgBnds <<
" col bounds" 3140 int oldRows = lp.
nRows();
3141 int oldCols = lp.
nCols();
3150 for(
int i = lp.
nRows()-1; i >= 0; --i)
3156 <<
": unconstrained" << std::endl; )
3177 for(
int j = 0; j < lp.
nCols(); ++j)
3191 dualVarUp[i] = bound;
3193 dualVarLo[i] = bound;
3198 dualVarLo[i] = bound;
3200 dualVarUp[i] = bound;
3207 for(
int j = 0; j < lp.
nCols(); ++j)
3209 dualConsLo[j] = dualConsUp[j] = 0.0;
3213 for(
int k = 0; k < col.
size(); ++k)
3219 int i = col.
index(k);
3228 dualConsLo[j] += aij * dualVarLo[i];
3233 dualConsUp[j] += aij * dualVarUp[i];
3240 dualConsUp[j] += aij * dualVarLo[i];
3245 dualConsLo[j] += aij * dualVarUp[i];
3250 for(
int j = lp.
nCols()-1; j >= 0; --j)
3256 if (
LTrel(dualConsUp[j], dualConsLo[j],
opttol()))
3259 <<
": dual infeasible -> dual lhs bound=" << dualConsLo[j]
3260 <<
" dual rhs bound=" << dualConsUp[j] << std::endl; )
3270 #if DOMINATED_COLUMN 3272 <<
": dominated -> maxObj=" << obj
3273 <<
" dual rhs bound=" << dualConsUp[j] << std::endl; )
3293 #if DOMINATED_COLUMN 3295 <<
": dominated -> maxObj=" << obj
3296 <<
" dual lhs bound=" << dualConsLo[j] << std::endl; )
3318 #if WEAKLY_DOMINATED_COLUMN 3320 <<
": weakly dominated -> maxObj=" << obj
3321 <<
" dual rhs bound=" << dualConsUp[j] << std::endl; )
3333 #if WEAKLY_DOMINATED_COLUMN 3335 <<
": weakly dominated -> maxObj=" << obj
3336 <<
" dual lhs bound=" << dualConsLo[j] << std::endl; )
3363 assert(remRows > 0 || remCols > 0 || remNzos == 0);
3365 if (remCols + remRows > 0)
3372 << remRows <<
" rows, " 3373 << remCols <<
" cols, " 3374 << remNzos <<
" non-zeros" 3392 int oldRows = lp.
nRows();
3393 int oldCols = lp.
nCols();
3398 for(
int j = lp.
nCols()-1; j >= 0; --j)
3408 for(
int k = 0; k < col.
size(); ++k)
3436 if (upLocks[j] == 1 || downLocks[j] == 1)
3442 bool bestislhs =
true;
3446 for(
int k = 0; k < col.
size(); ++k)
3458 rowNumber = col.
index(k);
3459 lhs = lp.
lhs(rowNumber);
3460 rhs = lp.
rhs(rowNumber);
3469 maxOtherLocks = INT_MAX;
3478 && ((col.
value(k) > 0.0 && lp.
maxObj(j) <= 0.0 && downLocks[j] == 1 && upLocks[j] <= maxOtherLocks)
3479 || (col.
value(k) < 0.0 && lp.
maxObj(j) >= 0.0 && upLocks[j] == 1 && downLocks[j] <= maxOtherLocks));
3481 && ((col.
value(k) > 0.0 && lp.
maxObj(j) >= 0.0 && upLocks[j] == 1 && downLocks[j] <= maxOtherLocks)
3482 || (col.
value(k) < 0.0 && lp.
maxObj(j) <= 0.0 && downLocks[j] == 1 && upLocks[j] <= maxOtherLocks));
3484 if (aggLhs || aggRhs)
3501 assert(
LE(minVal, maxVal));
3507 bestpos = col.
index(k);
3522 assert(
LE(minVal, maxVal));
3527 bestpos = col.
index(k);
3540 Real aggConstant = (bestislhs ? lp.
lhs(bestpos) : lp.
rhs(bestpos));
3541 Real aggAij = bestRow[j];
3544 (*
spxout) <<
"IMAISM51 col " << j
3545 <<
": Aggregating row: " << bestpos
3546 <<
" Aggregation Constant=" << aggConstant
3547 <<
" Coefficient of aggregated col=" << aggAij << std::endl;
3554 for(
int k = 0; k < col.
size(); ++k)
3556 if(col.
index(k) != bestpos)
3558 int rowNumber = col.
index(k);
3566 for(
int l = 0; l < bestRow.
size(); l++)
3568 if(bestRow.
index(l) != j)
3572 - updateRow[j]*bestRow.
value(l)/aggAij);
3580 lp.
changeRhs(rowNumber, updateRhs - updateRow[j]*aggConstant/aggAij);
3582 lp.
changeLhs(rowNumber, updateLhs - updateRow[j]*aggConstant/aggAij);
3584 assert(
LE(lp.
lhs(rowNumber), lp.
rhs(rowNumber)));
3588 for(
int l = 0; l < bestRow.
size(); l++)
3590 if(bestRow.
index(l) != j)
3607 assert(remRows > 0 || remCols > 0 || remNzos == 0);
3609 if (remCols + remRows > 0)
3616 << remRows <<
" rows, " 3617 << remCols <<
" cols, " 3618 << remNzos <<
" non-zeros" 3640 int oldRows = lp.
nRows();
3649 for (
int i = 0; i < lp.
nRows(); ++i)
3653 if (row.
size() == 1)
3663 << rs_remRows <<
" rows, " 3664 << rs_remRows <<
" non-zeros" 3692 classSize[0] = lp.
nRows();
3694 for(
int i = 1; i < lp.
nRows(); ++i)
3705 for(
int j = 0; j < lp.
nCols(); ++j)
3709 for(
int k = 0; k < col.
size(); ++k)
3712 int i = col.
index(k);
3714 if (scale[i] == 0.0)
3718 if (--classSize[pClass[i]] == 0)
3719 idxSet.addIdx(pClass[i]);
3723 for(
int m = 0; m < col.
size(); ++m)
3725 int k = pClass[col.
index(m)];
3736 int classIdx = idxSet.index(0);
3743 classIdx = idxSet.index(0);
3748 ++classSize[classIdx];
3750 oldVal = m_classSetRows[k].value(l);
3762 for(
int k = 0; k < lp.
nRows(); ++k )
3765 for(
int k = 0; k < lp.
nRows(); ++k)
3771 const int nRowsOld_tmp = lp.
nRows();
3775 for(
int j = 0; j < nRowsOld_tmp; ++j)
3780 int idxFirstDupRows = -1;
3781 int idxLastDupRows = -1;
3784 for(
int k = 0; k < lp.
nRows(); ++k)
3790 if(idxFirstDupRows < 0)
3792 idxFirstDupRows = k;
3795 for(
int l = 1; l <
m_dupRows[k].size(); ++l)
3806 int k_tmp, j_tmp = -1;
3807 for (k_tmp = j_tmp = 0; k_tmp < nRowsOld_tmp; ++k_tmp)
3809 if (perm_tmp[k_tmp] >= 0)
3810 perm_tmp[k_tmp] = j_tmp++;
3815 bool doChangeRanges =
false;
3819 for(
int k = 0; k < lp.
nRows(); ++k)
3824 <<
" duplicate rows found" << std::endl; )
3838 for(
int l = 0; l <
m_dupRows[k].size(); ++l)
3841 isLhsEqualRhs[l] = (lp.
lhs(i) == lp.
rhs(i));
3848 maxLhs = lp.
lhs(rowIdx);
3849 minRhs = lp.
rhs(rowIdx);
3853 Real scaledLhs, scaledRhs;
3854 Real factor = scale[rowIdx] / scale[i];
3866 if (scaledLhs > maxLhs)
3871 if (scaledRhs < minRhs)
3883 Real newLhs = (maxLhs > lp.
lhs(rowIdx)) ? maxLhs : lp.
lhs(rowIdx);
3884 Real newRhs = (minRhs < lp.
rhs(rowIdx)) ? minRhs : lp.
rhs(rowIdx);
3886 if(k == idxLastDupRows)
3889 for(
int j = 0; j < nRowsOld_tmp; ++j)
3891 da_perm[j] = perm_tmp[j];
3895 m_hist.append(
new (DuplicateRowsPSptr)
DuplicateRowsPS(lp, rowIdx, maxLhsIdx, minRhsIdx,
m_dupRows[k], scale, da_perm, isLhsEqualRhs,
true,
EQrel(newLhs, newRhs), k==idxFirstDupRows));
3902 m_hist.append(
new (DuplicateRowsPSptr)
DuplicateRowsPS(lp, rowIdx, maxLhsIdx, minRhsIdx,
m_dupRows[k], scale, da_perm_empty, isLhsEqualRhs,
false,
EQrel(newLhs, newRhs), k == idxFirstDupRows));
3905 if (maxLhs > lp.
lhs(rowIdx) || minRhs < lp.
rhs(rowIdx))
3908 doChangeRanges =
true;
3912 MSG_DEBUG( (*
spxout) <<
"IMAISM55 duplicate rows yield infeasible bounds:" 3913 <<
" lhs=" << newLhs
3914 <<
" rhs=" << newRhs << std::endl; )
3919 if( newRhs < newLhs )
3922 newLhsVec[rowIdx] = newLhs;
3923 newRhsVec[rowIdx] = newRhs;
3936 const int nRowsOld = lp.
nRows();
3940 for(
int i = 0; i < nRowsOld; ++i)
3953 for(
int i = 0; i < nRowsOld; ++i)
3956 assert(perm[i] == perm_tmp[i]);
3966 if (remRows + remNzos > 0)
3972 << remRows <<
" rows, " 3973 << remNzos <<
" non-zeros" 4019 classSize[0] = lp.
nCols();
4021 for(
int j = 1; j < lp.
nCols(); ++j)
4032 for(
int i = 0; i < lp.
nRows(); ++i)
4036 for(
int k = 0; k < row.
size(); ++k)
4039 int j = row.
index(k);
4041 if (scale[j] == 0.0)
4045 if (--classSize[pClass[j]] == 0)
4046 idxSet.addIdx(pClass[j]);
4050 for(
int m = 0; m < row.
size(); ++m)
4052 int k = pClass[row.
index(m)];
4063 int classIdx = idxSet.index(0);
4071 classIdx = idxSet.index(0);
4076 ++classSize[classIdx];
4078 oldVal = m_classSetCols[k].value(l);
4091 for(
int k = 0; k < lp.
nCols(); ++k )
4094 for(
int k = 0; k < lp.
nCols(); ++k)
4097 fixAndRemCol[k] =
false;
4101 bool hasDuplicateCol =
false;
4104 for(
int k = 0; k < lp.
nCols(); ++k)
4109 <<
" duplicate columns found" << std::endl; )
4111 if (!hasDuplicateCol)
4116 hasDuplicateCol =
true;
4119 for(
int l = 0; l <
m_dupCols[k].size(); ++l)
4121 for(
int m = 0; m <
m_dupCols[k].size(); ++m)
4126 if (l != m && !remCol[j1] && !remCol[j2])
4132 Real factor = scale[j1] / scale[j2];
4133 Real objDif = cj1 - cj2 * scale[j1] / scale[j2];
4164 else if (factor < 0)
4179 <<
" replaced by one" << std::endl; )
4187 MSG_DEBUG( (*
spxout) <<
"IMAISM80 not removing two duplicate columns " << j1
4189 <<
" because zero not contained in their bounds" << std::endl; )
4198 if (factor > 0 && objDif > 0)
4209 <<
" first one fixed at upper bound=" << lp.
upper(j1) << std::endl; )
4216 else if (factor < 0 && objDif < 0)
4227 <<
" first one fixed at lower bound=" << lp.
lower(j1) << std::endl; )
4238 if (factor < 0 && objDif > 0)
4249 <<
" first one fixed at upper bound=" << lp.
upper(j1) << std::endl; )
4258 else if (factor > 0 && objDif < 0)
4269 <<
" first one fixed at lower bound=" << lp.
lower(j1) << std::endl; )
4280 fixAndRemCol[j1] =
true;
4291 for(
int j = 0; j < lp.
nCols(); ++j)
4303 const int nColsOld = lp.
nCols();
4307 for(
int j = 0; j < nColsOld; ++j)
4320 for(
int j = 0; j < nColsOld; ++j)
4327 for(
int j = 0; j < nColsOld; ++j)
4329 da_perm[j] = perm[j];
4332 if (hasDuplicateCol)
4341 assert(remCols > 0 || remNzos == 0);
4349 << remCols <<
" cols, " 4350 << remNzos <<
" non-zeros" 4369 <<
": lower=" << lp.
lower(j)
4370 <<
" upper=" << lp.
upper(j)
4375 for(
int k = 0; k < col.
size(); ++k)
4377 int i = col.
index(k);
4387 Real rhs = (lp.
rhs(i) / scale) - (y / scale);
4396 <<
" (" << lp.
rhs(i)
4397 <<
") aij=" << col.
value(k)
4410 Real lhs = (lp.
lhs(i) / scale) - (y / scale);
4419 <<
" (" << lp.
lhs(i)
4420 <<
") aij=" << col.
value(k)
4425 assert(lp.
lhs(i) <= lp.
rhs(i));
4462 for(
int k = 0; k <
m_hist.size(); ++k)
4488 int numRangedRows = 0;
4489 int numBoxedCols = 0;
4491 for(
int i = 0; i < lp.
nRows(); ++i)
4494 for(
int j = 0; j < lp.
nCols(); ++j)
4498 (*spxout) <<
"LP has " 4499 << numRangedRows <<
" ranged rows, " 4500 << numBoxedCols <<
" boxed columns" 4528 for(
int i = 0; i < lp.
nRows(); ++i)
4531 for(
int j = 0; j < lp.
nCols(); ++j)
4571 #if TRIVIAL_HEURISTICS 4598 << m_remCols <<
" columns, " 4611 << lp.
nRows() <<
" rows " 4612 << lp.
nCols() <<
" columns " 4613 << lp.
nNzos() <<
" nonzeros" 4617 int numRangedRows = 0;
4618 int numBoxedCols = 0;
4620 for(
int i = 0; i < lp.
nRows(); ++i)
4624 for(
int j = 0; j < lp.
nCols(); ++j)
4628 (*spxout) <<
"Reduced LP has " 4629 << numRangedRows <<
" ranged rows, " 4630 << numBoxedCols <<
" boxed columns" 4670 assert(x.
dim() == r.
dim());
4671 assert(y.
dim() == s.
dim());
4676 for(
int j = 0; j < x.
dim(); ++j)
4682 for(
int i = 0; i < y.
dim(); ++i)
4690 for(
int k =
m_hist.size()-1; k >= 0; --k)
4728 #ifdef CHECK_BASIC_DIM 4764 os <<
"DUAL_INFEASIBLE";
const VectorBase< R > & rhs() const
Returns right hand side vector.
DVector m_prim
unsimplified primal solution vector.
Rational spxAbs(const Rational &r)
Absolute.
bool isNotZero(Real a, Real eps=Param::epsilon())
returns true iff |a| > eps
Real m_opttol
dual feasibility tolerance.
DataArray< PostStep * > m_hist
vector of presolve history.
Postsolves multi aggregation.
Exception class for things that should NEVER happen.This class is derived from the SoPlex exception b...
bool LTrel(Real a, Real b, Real eps=Param::epsilon())
returns true iff relDiff(a,b) <= -eps
free variable fixed to zero.
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
friend class FreeConstraintPS
Result removeRowSingleton(SPxLP &lp, const SVector &row, int &i)
remove row singletons.
DataArray< int > m_stat
preprocessing history.
bool GE(Real a, Real b, Real eps=Param::epsilon())
returns true iff a >= b + eps
void reDim(int newdim, const bool setZero=true)
Resets DVectorBase's dimension to newdim.
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
int m_keptLRhs
number of kept left- and right-hand sides
UnitVectorBase< Real > UnitVector
const VectorBase< R > & upper() const
Returns upper bound vector.
Real m_epsilon
epsilon zero.
THREADLOCAL const Real infinity
Postsolves variable bound fixing.
Result
Result of the simplification.
the problem was so much simplified that it vanished
Postsolves duplicate rows.
int m_remNzos
number of removed nonzero coefficients
int size() const
Number of used indices.
void computeMinMaxResidualActivity(SPxLP &lp, int rowNumber, int colNumber, Real &minAct, Real &maxAct)
computes the minimum and maximum residual activity for a given row and column. If colNumber is set to...
Real m_feastol
primal feasibility tolerance.
DataArray< SPxSolver::VarStatus > m_rBasisStat
basis status of rows.
Real maxAbs(Real a, Real b)
returns max(|a|,|b|)
virtual void removeCols(int perm[])
Removes multiple columns.
bool LE(Real a, Real b, Real eps=Param::epsilon())
returns true iff a <= b + eps
bool LT(Real a, Real b, Real eps=Param::epsilon())
returns true iff a < b + eps
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
SPxLP::SPxSense m_thesense
optimization sense.
bool NE(Real a, Real b, Real eps=Param::epsilon())
returns true iff |a-b| > eps
virtual Result simplify(SPxLP &lp, Real eps, Real delta)
simplify SPxLP lp with identical primal and dual feasibility tolerance.
friend class DuplicateRowsPS
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
int cIdx(int j) const
returns for a given column index of the (reduced) LP the corresponding column index in the unsimplifi...
variable fixed to identical bounds.
DVector m_dual
unsimplified dual solution vector.
R & value(int n)
Reference to value of n 'th nonzero.
General methods in LP preprocessing.
Postsolves empty constraints.
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
int m_keptBnds
number of kept bounds
#define ASSERT_WARN(prefix, expr)
Macro to turn some assertions into warnings.
Real m_minReduction
minimal reduction (sum of removed rows/cols) to continue simplification
void remove(int n, int m)
Remove nonzeros n thru m.
void handleExtremes(SPxLP &lp)
handles extreme values by setting them to zero or infinity.
bool m_postsolved
status of postsolving.
int rIdx(int i) const
returns for a given row index of the (reduced) LP the corresponding row index in the unsimplified LP...
virtual void unsimplify(const Vector &x, const Vector &y, const Vector &s, const Vector &r, const SPxSolver::VarStatus rows[], const SPxSolver::VarStatus cols[], bool isOptimal=true)
reconstructs an optimal solution for the unsimplified LP.
SVectorBase< R > & rowVector_w(int i)
virtual void removeRows(int perm[])
Removes multiple rows.
void fixColumn(SPxLP &lp, int i, bool correctIdx=true)
handles the fixing of a variable. correctIdx is true iff the index mapping has to be updated...
virtual const std::string what() const
returns exception message
Wrapper for different output streams and verbosity levels.
int nRows() const
Returns number of rows in LP.
Exception class for out of memory exceptions.This class is derived from the SoPlex exception base cla...
virtual void start()=0
start timer, resume accounting user, system and real time.
virtual Real stop()=0
stop timer, return accounted user time.
void spx_alloc(T &p, int n=1)
Allocate memory.
simplification could be done
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
Postsolves the case when constraints are removed due to a variable with zero objective that is free i...
int nNzos() const
Returns number of nonzeros in LP.
virtual const char * getName() const
get name of simplifying step.
friend class RowSingletonPS
Timer * m_timeUsed
user time used for simplification
nothing known about basis status (possibly due to a singular basis in transformed problem) ...
Array< DSVector > m_classSetCols
stores parallel classes with non-zero row entry
Result duplicateCols(SPxLP &lp, bool &again)
removes duplicate columns
void removeCol(SPxLP &lp, int j)
removes a column in the LP.
bool GT(Real a, Real b, Real eps=Param::epsilon())
returns true iff a > b + eps
SPxSense spxSense() const
Returns the optimization sense.
int & index(int n)
Reference to index of n 'th nonzero.
Postsolves row singletons.
virtual void changeMaxObj(const VectorBase< R > &newObj, bool scale=false)
Changes objective vector to newObj. scale determines whether the new data should be scaled...
std::ostream & operator<<(std::ostream &s, const VectorBase< R > &vec)
Output operator.
Result simplifyRows(SPxLP &lp, bool &again)
performs simplification steps on the rows of the LP.
bool checkSolution(SPxLP &lp, DVector sol)
checks a solution for feasibility
#define MSG_INFO2(spxout, x)
Prints out message x if the verbosity level is at least SPxOut::INFO2.
friend class DoubletonEquationPS
Postsolves doubleton equations combined with a column singleton.
Postsolves free column singletons.
virtual void changeLower(const VectorBase< R > &newLower, bool scale=false)
Changes vector of lower bounds to newLower. scale determines whether the new data should be scaled...
virtual void changeRhs(const VectorBase< R > &newRhs, bool scale=false)
Changes right hand side vector for constraints to newRhs. scale determines whether the new data shoul...
comparator for class SVector::Element: compare nonzeros according to value
R obj(int i) const
Returns objective value of column i.
const VectorBase< R > & lhs() const
Returns left hand side vector.
DataArray< int > m_cIdx
column index vector in original LP.
Result m_result
result of the simplification.
variable set to its upper bound.
bool GTrel(Real a, Real b, Real eps=Param::epsilon())
returns true iff relDiff(a,b) > eps
void SPxQuicksort(T *keys, int end, COMPARATOR &compare, int start=0, bool type=true)
Generic QuickSort implementation.
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
virtual void changeBounds(const VectorBase< R > &newLower, const VectorBase< R > &newUpper, bool scale=false)
Changes variable bounds to newLower and newUpper. scale determines whether the new data should be sca...
primal infeasibility was detected
const VectorBase< R > & maxRowObj() const
bool GErel(Real a, Real b, Real eps=Param::epsilon())
returns true iff relDiff(a,b) > -eps
variable set to its lower bound.
Generic QuickSort implementation.
Array< DSVector > m_dupCols
arrange duplicate columns w.r.t. their pClass values
int m_remRows
number of removed rows
void add(int i, const R &v)
Append one nonzero (i,v).
virtual void changeUpper(const VectorBase< R > &newUpper, bool scale=false)
Changes vector of upper bounds to newUpper. scale determines whether the new data should be scaled...
Postsolves row objectives.
bool EQ(Real a, Real b, Real eps=Param::epsilon())
returns true iff |a-b| <= eps
virtual void changeObj(const VectorBase< R > &newObj, bool scale=false)
Changes objective vector to newObj. scale determines whether the new data should be scaled...
DataArray< int > m_rIdx
row index vector in original LP.
Postsolves column singletons with zero objective.
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
virtual void addCol(const LPColBase< R > &col, bool scale=false)
int dim() const
Dimension of vector.
Exception base class.This class implements a base class for our SoPlex exceptions We provide a what()...
bool m_keepbounds
keep some bounds (for boundflipping)
Everything should be within this namespace.
virtual void changeRange(const VectorBase< R > &newLhs, const VectorBase< R > &newRhs, bool scale=false)
Changes left and right hand side vectors. scale determines whether the new data should be scaled...
bool EQrel(Real a, Real b, Real eps=Param::epsilon())
returns true iff |relDiff(a,b)| <= eps
virtual bool checkBasisDim(DataArray< SPxSolver::VarStatus > rows, DataArray< SPxSolver::VarStatus > cols) const
friend class ForceConstraintPS
void handleRowObjectives(SPxLP &lp)
handle row objectives
primal unboundedness was detected
#define MSG_WARNING(spxout, x)
Prints out message x if the verbosity level is at least SPxOut::WARNING.
Result duplicateRows(SPxLP &lp, bool &again)
removes duplicate rows.
Real m_cutoffbound
the cutoff bound that is found by heuristics
const VectorBase< R > & maxObj() const
Returns objective vector for maximization problem.
Exception class for incorrect usage of interface methods.
Result multiaggregation(SPxLP &lp, bool &again)
performs multi-aggregations of variable based upon constraint activitu.
Save arrays of arbitrary types.
Real m_objoffset
objective offset
friend class DuplicateColsPS
bool NErel(Real a, Real b, Real eps=Param::epsilon())
returns true iff |relDiff(a,b)| > eps
const SVectorBase< R > & rowVector(int i) const
Gets row vector of row i.
comparator for class SVector::Element: compare nonzeros according to index
virtual void changeRowObj(const VectorBase< R > &newRowObj, bool scale=false)
Changes row objective function vector to newRowObj. scale determines whether the new data should be s...
void trivialHeuristic(SPxLP &lp)
tries to find good lower bound solutions by applying some trivial heuristics
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
int m_chgBnds
number of changed bounds
Postsolves duplicate columns.
Result removeEmpty(SPxLP &lp)
removed empty rows and empty columns.
int size() const
return nr. of elements.
Postsolves forcing constraints.
Result simplifyDual(SPxLP &lp, bool &again)
performs simplification steps on the LP based on dual concepts.
Postsolves unconstraint constraints.
int pos(int i) const
Position of index i.
bool isConsistent() const
Consistency check.
Postsolves variable bound tightening from pseudo objective propagation.
#define MSG_INFO1(spxout, x)
Prints out message x if the verbosity level is at least SPxOut::INFO1.
int m_remCols
number of removed columns
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
const SVectorBase< R > & colVector(int i) const
Returns column vector of column i.
Postsolves variable fixing.
int nCols() const
Returns number of columns in LP.
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
virtual void changeElement(int i, int j, const R &val, bool scale=false)
Changes LP element (i, j) to val. scale determines whether the new data should be scaled...
friend class FreeColSingletonPS
bool LErel(Real a, Real b, Real eps=Param::epsilon())
returns true iff relDiff(a,b) <= eps
virtual void changeLhs(const VectorBase< R > &newLhs, bool scale=false)
Changes left hand side vector for constraints to newLhs. scale determines whether the new data should...
Real m_pseudoobj
the pseudo objective function value
friend class FreeZeroObjVariablePS
void computeMinMaxValues(SPxLP &lp, Real side, Real val, Real minRes, Real maxRes, Real &minVal, Real &maxVal)
calculate min/max value for the multi aggregated variables
int m_addedcols
columns added by handleRowObjectives()
friend class ZeroObjColSingletonPS
bool isZero(Real a, Real eps=Param::epsilon())
returns true iff |a| <= eps
void removeRow(SPxLP &lp, int i)
removes a row in the LP.
friend class EmptyConstraintPS
virtual void reset()=0
initialize timer, set timing accounts to zero.
SPxOut * spxout
message handler
Save arrays of data objects.
SVectorBase< R > & colVector_w(int i)
Returns the LP as an LPRowSet.
int m_chgLRhs
number of change right-hand sides
Result simplifyCols(SPxLP &lp, bool &again)
performs simplification steps on the columns of the LP.
Array< DSVector > m_dupRows
arrange duplicate rows using bucket sort w.r.t. their pClass values
void reSize(int newsize)
reset size to newsize.
DVector m_slack
unsimplified slack vector.
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
const VectorBase< R > & lower() const
Returns (internal and possibly scaled) lower bound vector.
virtual void execute(DVector &x, DVector &y, DVector &s, DVector &r, DataArray< SPxSolver::VarStatus > &cBasis, DataArray< SPxSolver::VarStatus > &rBasis, bool isOptimal) const
Set of indices.Class IdxSet provides a set of indices. At construction it must be given an array of i...
void spx_free(T &p)
Release memory.
DataArray< SPxSolver::VarStatus > m_cBasisStat
basis status of columns.
void propagatePseudoobj(SPxLP &lp)
tightens variable bounds by propagating the pseudo objective function value.
dual infeasibility was detected
Array< DSVector > m_classSetRows
stores parallel classes with non-zero colum entry
friend class FixVariablePS
DVector m_redCost
unsimplified reduced cost vector.