|
Go to the documentation of this file.
44 #define PRESOL_NAME "dualinfer"
45 #define PRESOL_DESC "exploit dual informations for variable fixings"
46 #define PRESOL_PRIORITY 20010000
47 #define PRESOL_MAXROUNDS 0
48 #define PRESOL_DELAY TRUE
71 struct ConstraintMatrix
97 int* minactivityneginf;
98 int* minactivityposinf;
99 int* maxactivityneginf;
100 int* maxactivityposinf;
116 assert(scip != NULL);
117 assert(vars != NULL);
118 assert(scalars != NULL);
119 assert(*vars != NULL);
120 assert(*scalars != NULL);
121 assert(nvars != NULL);
122 assert(constant != NULL);
126 if( requiredsize > *nvars )
133 assert(requiredsize <= *nvars);
159 assert(vars != NULL);
160 assert(vals != NULL);
162 rowidx = matrix->nrows;
167 matrix->lhs[rowidx] = -rhs;
169 matrix->isrhsinfinite[rowidx] = TRUE;
174 matrix->lhs[rowidx] = lhs;
175 matrix->rhs[rowidx] = rhs;
176 matrix->isrhsinfinite[rowidx] = SCIPisInfinity(scip, matrix->rhs[rowidx]);
182 matrix->rowname[rowidx] = name;
185 matrix->rowmatbeg[rowidx] = matrix->nnonzs;
187 for( j = 0; j < nvars; j++ )
189 matrix->rowmatval[matrix->nnonzs] = factor * vals[j];
191 assert(matrix->vars[probindex] == vars[j]);
193 assert(0 <= probindex && probindex < matrix->ncols);
194 matrix->rowmatind[matrix->nnonzs] = probindex;
198 matrix->rowmatcnt[rowidx] = matrix->nnonzs - matrix->rowmatbeg[rowidx];
226 assert(scip != NULL);
227 assert(matrix != NULL);
228 assert(vars != NULL || nvars == 0);
242 activeconstant = 0.0;
254 for( v = 0; v < nactivevars; v++ )
263 lhs -= activeconstant;
265 rhs -= activeconstant;
268 if( nactivevars > 0 )
271 SCIP_CALL( addRow(scip, matrix, name, activevars, activevals, nactivevars, lhs, rhs) );
273 SCIP_CALL( addRow(scip, matrix, activevars, activevals, nactivevars, lhs, rhs) );
298 assert(scip != NULL);
299 assert(matrix != NULL);
300 assert(matrix->colmatval != NULL);
301 assert(matrix->colmatind != NULL);
302 assert(matrix->colmatbeg != NULL);
303 assert(matrix->colmatcnt != NULL);
304 assert(matrix->rowmatval != NULL);
305 assert(matrix->rowmatind != NULL);
306 assert(matrix->rowmatbeg != NULL);
307 assert(matrix->rowmatcnt != NULL);
313 for( i = 0; i < matrix->nrows; i++ )
315 rowpnt = matrix->rowmatind + matrix->rowmatbeg[i];
316 rowend = rowpnt + matrix->rowmatcnt[i];
317 for( ; rowpnt < rowend; rowpnt++ )
320 (matrix->colmatcnt[colidx])++;
324 matrix->colmatbeg[0] = 0;
325 for( i = 0; i < matrix->ncols-1; i++ )
327 matrix->colmatbeg[i+1] = matrix->colmatbeg[i] + matrix->colmatcnt[i];
330 for( i = 0; i < matrix->nrows; i++ )
332 rowpnt = matrix->rowmatind + matrix->rowmatbeg[i];
333 rowend = rowpnt + matrix->rowmatcnt[i];
334 valpnt = matrix->rowmatval + matrix->rowmatbeg[i];
336 for( ; rowpnt < rowend; rowpnt++, valpnt++ )
338 assert(*rowpnt < matrix->ncols);
340 matrix->colmatval[matrix->colmatbeg[colidx] + fillidx[colidx]] = *valpnt;
341 matrix->colmatind[matrix->colmatbeg[colidx] + fillidx[colidx]] = i;
365 assert(scip != NULL);
366 assert(matrix != NULL);
368 for( row = 0; row < matrix->nrows; row++ )
370 matrix->minactivity[row] = 0;
371 matrix->maxactivity[row] = 0;
372 matrix->minactivityneginf[row] = 0;
373 matrix->minactivityposinf[row] = 0;
374 matrix->maxactivityneginf[row] = 0;
375 matrix->maxactivityposinf[row] = 0;
377 rowpnt = matrix->rowmatind + matrix->rowmatbeg[row];
378 rowend = rowpnt + matrix->rowmatcnt[row];
379 valpnt = matrix->rowmatval + matrix->rowmatbeg[row];
381 for( ; rowpnt < rowend; rowpnt++, valpnt++ )
389 assert(matrix->ncols > col);
397 matrix->maxactivityposinf[row]++;
399 matrix->maxactivity[row] += val * matrix->ub[col];
402 matrix->minactivityneginf[row]++;
404 matrix->minactivity[row] += val * matrix->lb[col];
409 matrix->maxactivityneginf[row]++;
411 matrix->maxactivity[row] += val * matrix->lb[col];
414 matrix->minactivityposinf[row]++;
416 matrix->minactivity[row] += val * matrix->ub[col];
420 if( (matrix->minactivityneginf[row] + matrix->minactivityposinf[row]) > 0 )
422 if( (matrix->maxactivityneginf[row] + matrix->maxactivityposinf[row]) > 0 )
439 const char* conshdlrname;
454 assert(scip != NULL);
455 assert(matrixptr != NULL);
456 assert(initialized != NULL);
458 *initialized = FALSE;
469 for( i = 0; i < nconshdlrs; ++i )
475 if( nconshdlrconss > 0 )
479 if( (strcmp(conshdlrname, "linear") != 0) && (strcmp(conshdlrname, "setppc") != 0)
480 && (strcmp(conshdlrname, "logicor") != 0) && (strcmp(conshdlrname, "knapsack") != 0)
481 && (strcmp(conshdlrname, "varbound") != 0) )
483 SCIPdebugMessage( "unsupported constraint type <%s>: aborting domcol presolver\n", conshdlrname);
488 nconss += nconshdlrconss;
492 if( i < nconshdlrs || nconss == 0 )
503 for( i = nvars - 1; i >= 0; --i )
519 matrix->ncols = nvars;
532 for( v = 0; v < matrix->ncols; v++ )
534 var = matrix->vars[v];
564 for( i = 0; i < nconshdlrs; ++i )
579 if( strcmp(conshdlrname, "linear") == 0 )
581 for( c = 0; c < nconshdlrconss && (c % 1000 != 0 || ! SCIPisStopped(scip)); ++c )
583 cons = conshdlrconss[c];
597 else if( strcmp(conshdlrname, "setppc") == 0 )
599 for( c = 0; c < nconshdlrconss && (c % 1000 != 0 || ! SCIPisStopped(scip)); ++c )
604 cons = conshdlrconss[c];
634 else if( strcmp(conshdlrname, "logicor") == 0 )
636 for( c = 0; c < nconshdlrconss && (c % 1000 != 0 || ! SCIPisStopped(scip)); ++c )
638 cons = conshdlrconss[c];
650 else if( strcmp(conshdlrname, "knapsack") == 0 )
652 if( nconshdlrconss > 0 )
660 for( c = 0; c < nconshdlrconss && (c % 1000 != 0 || ! SCIPisStopped(scip)); ++c )
664 cons = conshdlrconss[c];
670 if( nvars > valssize )
672 valssize = (int) (1.5 * nvars);
676 for( v = 0; v < nvars; v++ )
693 else if( strcmp(conshdlrname, "varbound") == 0 )
695 if( nconshdlrconss > 0 )
704 for( c = 0; c < nconshdlrconss && (c % 1000 != 0 || ! SCIPisStopped(scip)); ++c )
706 cons = conshdlrconss[c];
730 assert(nconshdlrconss == 0);
734 assert(matrix->nrows <= nconss);
735 assert(matrix->nnonzs <= nnonzstmp);
759 assert(scip != NULL);
760 assert(matrix != NULL);
762 if( (*matrix) != NULL )
764 assert((*matrix)->colmatval != NULL);
765 assert((*matrix)->colmatind != NULL);
766 assert((*matrix)->colmatbeg != NULL);
767 assert((*matrix)->colmatcnt != NULL);
768 assert((*matrix)->lb != NULL);
769 assert((*matrix)->ub != NULL);
771 assert((*matrix)->rowmatval != NULL);
772 assert((*matrix)->rowmatind != NULL);
773 assert((*matrix)->rowmatbeg != NULL);
774 assert((*matrix)->rowmatcnt != NULL);
775 assert((*matrix)->lhs != NULL);
776 assert((*matrix)->rhs != NULL);
778 assert((*matrix)->rowname != NULL);
808 (*matrix)->nrows = 0;
809 (*matrix)->ncols = 0;
810 (*matrix)->nnonzs = 0;
835 assert(scip != NULL);
836 assert(matrix != NULL);
837 assert(0 <= row && row < matrix->nrows);
839 return SCIPisFeasLE(scip, matrix->lhs[row], matrix->minactivity[row])
840 && SCIPisFeasLE(scip, matrix->maxactivity[row], matrix->rhs[row]);
854 assert(scip != NULL);
855 assert(matrix != NULL);
856 assert(lowershadow != NULL);
857 assert(uppershadow != NULL);
859 for( r = 0; r < matrix->nrows; r++ )
862 uppershadow[r] = matrix->isrhsinfinite[r] ? 0 : SCIPinfinity(scip);
878 assert(scip != NULL);
879 assert(matrix != NULL);
880 assert(lowershadow != NULL);
881 assert(uppershadow != NULL);
882 assert(nfitsinglecols != NULL);
884 for( c = 0; c < matrix->ncols; c++ )
892 row = *(matrix->colmatind + matrix->colmatbeg[c]);
894 if( matrix->isrhsinfinite[row] )
899 val = *(matrix->colmatval + matrix->colmatbeg[c]);
906 if( tmp > lowershadow[row] )
907 lowershadow[row] = tmp;
913 if( tmp < uppershadow[row] )
914 uppershadow[row] = tmp;
943 assert(scip != NULL);
944 assert(matrix != NULL);
945 assert(lowershadow != NULL);
946 assert(uppershadow != NULL);
947 assert(lowercosts != NULL);
948 assert(uppercosts != NULL);
950 for( c = 0; c < matrix->ncols; c++)
957 colpnt = matrix->colmatind + matrix->colmatbeg[c];
958 colend = colpnt + matrix->colmatcnt[c];
959 valpnt = matrix->colmatval + matrix->colmatbeg[c];
961 for( ; (colpnt < colend) && (!mininfinite || !maxinfinite); colpnt++, valpnt++ )
970 mininfinite = mininfinite || SCIPisInfinity(scip, -lowershadow[row]);
971 maxinfinite = maxinfinite || SCIPisInfinity(scip, uppershadow[row]);
975 lowercosts[c] += val * lowershadow[row];
979 uppercosts[c] += val * uppershadow[row];
984 mininfinite = mininfinite || SCIPisInfinity(scip, uppershadow[row]);
985 maxinfinite = maxinfinite || SCIPisInfinity(scip, -lowershadow[row]);
989 lowercosts[c] += val * uppershadow[row];
993 uppercosts[c] += val * lowershadow[row];
1013 int* npossiblefixings,
1019 assert(scip != NULL);
1020 assert(matrix != NULL);
1021 assert(lowercosts != NULL);
1022 assert(uppercosts != NULL);
1023 assert(npossiblefixings != NULL);
1024 assert(varstofix != NULL);
1026 for( c = 0; c < matrix->ncols; c++ )
1034 if( lowercosts[c] > objval )
1039 (*npossiblefixings)++;
1045 if( uppercosts[c] < objval )
1050 (*npossiblefixings)++;
1063 int* nfitsinglecols,
1064 int* npossiblefixings
1072 assert(scip != NULL);
1073 assert(matrix != NULL);
1074 assert(varstofix != NULL);
1075 assert(nfitsinglecols != NULL);
1076 assert(npossiblefixings != NULL);
1087 costCalculation(scip, matrix, lowershadow, uppershadow, lowercosts, uppercosts);
1089 fixColumns(scip, matrix, lowercosts, uppercosts, npossiblefixings, varstofix);
1117 assert(scip != NULL);
1118 assert(matrix != NULL);
1119 assert(0 <= col && col < matrix->ncols);
1120 assert(0 <= withoutrow && withoutrow < matrix->nrows);
1121 assert(lbdual != NULL);
1122 assert(ubdual != NULL);
1127 colpnt = matrix->colmatind + matrix->colmatbeg[col];
1128 colend = colpnt + matrix->colmatcnt[col];
1129 valpnt = matrix->colmatval + matrix->colmatbeg[col];
1131 for(; (colpnt < colend); colpnt++, valpnt++ )
1136 assert(matrix->isrhsinfinite[row]);
1138 if( row == withoutrow )
1144 maxcolactivity += val * ubdual[row];
1146 else if( val < 0.0 )
1149 maxcolactivity += val * lbdual[row];
1152 return maxcolactivity;
1173 assert(scip != NULL);
1174 assert(matrix != NULL);
1175 assert(0 <= col && col < matrix->ncols);
1176 assert(0 <= withoutrow && withoutrow < matrix->nrows);
1177 assert(lbdual != NULL);
1178 assert(ubdual != NULL);
1183 colpnt = matrix->colmatind + matrix->colmatbeg[col];
1184 colend = colpnt + matrix->colmatcnt[col];
1185 valpnt = matrix->colmatval + matrix->colmatbeg[col];
1187 for(; (colpnt < colend); colpnt++, valpnt++ )
1192 assert(matrix->isrhsinfinite[row]);
1194 if( row == withoutrow )
1200 mincolactivity += val * lbdual[row];
1202 else if( val < 0.0 )
1205 mincolactivity += val * ubdual[row];
1208 return mincolactivity;
1229 assert(scip != NULL);
1230 assert(matrix != NULL);
1231 assert(0 <= col && col < matrix->ncols);
1232 assert(0 <= row && row < matrix->nrows);
1233 assert(lbdual != NULL);
1234 assert(ubdual != NULL);
1235 assert(mincolact != NULL);
1236 assert(maxcolact != NULL);
1237 assert(maxcolactinf != NULL);
1238 assert(mincolactinf != NULL);
1239 assert(mincolresact != NULL);
1240 assert(maxcolresact != NULL);
1241 assert(matrix->isrhsinfinite[row]);
1248 assert(maxcolactinf[col] >= 1);
1249 if( maxcolactinf[col] == 1 )
1256 if( maxcolactinf[col] > 0 )
1259 *maxcolresact = maxcolact[col] - val * ubdual[row];
1264 assert(mincolactinf[col] >= 1);
1265 if( mincolactinf[col] == 1 )
1272 if( mincolactinf[col] > 0 )
1275 *mincolresact = mincolact[col] - val * lbdual[row];
1278 else if( val < 0.0 )
1282 assert(maxcolactinf[col] >= 1);
1283 if( maxcolactinf[col] == 1 )
1290 if( maxcolactinf[col] > 0 )
1293 *maxcolresact = maxcolact[col] - val * lbdual[row];
1298 assert(mincolactinf[col] >= 1);
1299 if( mincolactinf[col] == 1 )
1306 if( mincolactinf[col] > 0 )
1309 *mincolresact = mincolact[col] - val * ubdual[row];
1337 assert(scip != NULL);
1338 assert(matrix != NULL);
1339 assert(lbdual != NULL);
1340 assert(ubdual != NULL);
1341 assert(0 <= startcol && startcol < matrix->ncols);
1342 assert(0 < stopcol && stopcol <= matrix->ncols);
1343 assert(excludevar != NULL);
1344 assert(mincolact != NULL);
1345 assert(maxcolact != NULL);
1346 assert(maxcolactinf != NULL);
1347 assert(mincolactinf != NULL);
1349 for( c = startcol; c < stopcol; c++ )
1351 excludevar[c] = FALSE;
1354 maxcolactinf[c] = 0;
1355 mincolactinf[c] = 0;
1361 colpnt = matrix->colmatind + matrix->colmatbeg[c];
1362 colend = colpnt + matrix->colmatcnt[c];
1363 valpnt = matrix->colmatval + matrix->colmatbeg[c];
1366 for(; (colpnt < colend); colpnt++, valpnt++ )
1371 if( matrix->isrhsinfinite[row] )
1378 maxcolact[c] += val * ubdual[row];
1383 mincolact[c] += val * lbdual[row];
1385 else if( val < 0.0 )
1390 maxcolact[c] += val * lbdual[row];
1395 mincolact[c] += val * ubdual[row];
1398 else if( !matrix->isrhsinfinite[row] )
1400 excludevar[c] = TRUE;
1405 if( !excludevar[c] )
1416 if( mincolactinf[c] > 0 )
1418 if( maxcolactinf[c] > 0 )
1443 assert(scip != NULL);
1444 assert(matrix != NULL);
1445 assert(lbdual != NULL);
1446 assert(ubdual != NULL);
1447 assert(boundchanges != NULL);
1448 assert(updateinfcnt != NULL);
1449 assert(matrix->isrhsinfinite[row]);
1451 *updateinfcnt = FALSE;
1459 newubdual = (objval - mincolresact) / val;
1460 if( newubdual < ubdual[row] )
1463 *updateinfcnt = TRUE;
1465 ubdual[row] = newubdual;
1476 newlbdual = (objval - mincolresact) / val;
1477 if( newlbdual > lbdual[row] )
1480 *updateinfcnt = TRUE;
1482 lbdual[row] = newlbdual;
1511 assert(scip != NULL);
1512 assert(matrix != NULL);
1513 assert(0 <= row && row < matrix->nrows);
1514 assert(lbdual != NULL);
1515 assert(ubdual != NULL);
1516 assert(excludevar != NULL);
1517 assert(mincolact != NULL);
1518 assert(maxcolact != NULL);
1519 assert(maxcolactinf != NULL);
1520 assert(mincolactinf != NULL);
1521 assert(matrix->isrhsinfinite[row]);
1523 rowpnt = matrix->rowmatind + matrix->rowmatbeg[row];
1524 rowend = rowpnt + matrix->rowmatcnt[row];
1525 valpnt = matrix->rowmatval + matrix->rowmatbeg[row];
1534 for(; (rowpnt < rowend); rowpnt++, valpnt++ )
1544 assert(maxcolactinf[c] > 0);
1547 if( maxcolactinf[c] == 0 )
1549 calcColActivity(scip, matrix, lbdual, ubdual, c, c+1, excludevar, mincolact, maxcolact,
1550 maxcolactinf, mincolactinf);
1555 assert(mincolactinf[c] > 0);
1558 if( mincolactinf[c] == 0 )
1560 calcColActivity(scip, matrix, lbdual, ubdual, c, c+1, excludevar, mincolact, maxcolact,
1561 maxcolactinf, mincolactinf);
1569 for(; (rowpnt < rowend); rowpnt++, valpnt++ )
1579 assert(mincolactinf[c] > 0);
1582 if( mincolactinf[c] == 0 )
1583 calcColActivity(scip, matrix, lbdual, ubdual, c, c+1, excludevar, mincolact, maxcolact,
1584 maxcolactinf, mincolactinf);
1588 assert(maxcolactinf[c] > 0);
1591 if( maxcolactinf[c] == 0 )
1592 calcColActivity(scip, matrix, lbdual, ubdual, c, c+1, excludevar, mincolact, maxcolact,
1593 maxcolactinf, mincolactinf);
1605 int* nfitsinglecols,
1606 int* npossiblefixings
1626 assert(scip != NULL);
1627 assert(matrix != NULL);
1628 assert(varstofix != NULL);
1629 assert(nfitsinglecols != NULL);
1630 assert(npossiblefixings != NULL);
1633 for( c = 0; c < matrix->ncols; c++ )
1648 for( r = 0; r < matrix->nrows; r++ )
1657 for( c = 0; c < matrix->ncols; c++ )
1661 row = *(matrix->colmatind + matrix->colmatbeg[c]);
1662 varissingcol[c] = FALSE;
1664 if( matrix->colmatcnt[c] == 1 && matrix->isrhsinfinite[row] )
1666 varissingcol[c] = TRUE;
1678 val = *(matrix->colmatval + matrix->colmatbeg[c]);
1682 newubdual = objval/val;
1683 if( newubdual < ubdual[row] )
1685 ubdual[row] = newubdual;
1691 newlbdual = objval/val;
1692 if( newlbdual > lbdual[row] )
1694 lbdual[row] = newlbdual;
1701 (*nfitsinglecols) = cnt;
1712 while( boundchanges && loops < MAX_LOOPS )
1718 calcColActivity(scip, matrix, lbdual, ubdual, 0, matrix->ncols, excludevar, mincolact, maxcolact,
1719 maxcolactinf, mincolactinf);
1721 for( c = 0 ; c < matrix->ncols; c++ )
1733 colpnt = matrix->colmatind + matrix->colmatbeg[c];
1734 colend = colpnt + matrix->colmatcnt[c];
1735 valpnt = matrix->colmatval + matrix->colmatbeg[c];
1737 for(; (colpnt < colend); colpnt++, valpnt++ )
1749 updateinfcnt = FALSE;
1753 maxcolactinf, mincolactinf, &mincolresact, &maxcolresact);
1757 lbdual, ubdual, &boundchanges, &updateinfcnt);
1761 infCounterUpdate(scip, matrix, val, row, lbdual, ubdual, excludevar, mincolact, maxcolact,
1762 maxcolactinf, mincolactinf);
1767 if( boundchanges > 0 )
1770 calcColActivity(scip, matrix, lbdual, ubdual, 0, matrix->ncols, excludevar, mincolact, maxcolact,
1771 maxcolactinf, mincolactinf);
1774 for( c = 0; c < matrix->ncols; c++ )
1785 if( SCIPisLT(scip, maxcolact[c], objval) && varstofix[c] == NOFIX )
1788 (*npossiblefixings)++;
1813 assert(scip != NULL);
1814 assert(presol != NULL);
1830 assert(result != NULL);
1840 initialized = FALSE;
1849 int npossiblefixings;
1856 npossiblefixings = 0;
1873 if( npossiblefixings > 0 )
1876 for( i = matrix->ncols - 1; i >= 0; --i )
1886 var = matrix->vars[i];
1909 else if( varstofix[i] == FIXATUB )
1913 var = matrix->vars[i];
1941 if( (*result) != SCIP_CUTOFF && (nconvarsfixed + nintvarsfixed + nbinvarsfixed) > 0 )
1943 SCIPdebugMessage( "### %d vars [%d column singletons] ===>>> fixed [cont: %d, int: %d, bin: %d]\n",
1944 matrix->ncols, nfitsinglecols, nconvarsfixed, nintvarsfixed, nbinvarsfixed);
|