56#define NLHDLR_NAME "soc"
57#define NLHDLR_DESC "nonlinear handler for second-order cone structures"
58#define NLHDLR_DETECTPRIORITY 100
59#define NLHDLR_ENFOPRIORITY 100
60#define DEFAULT_MINCUTEFFICACY 1e-5
61#define DEFAULT_COMPEIGENVALUES TRUE
108struct SCIP_NlhdlrExprData
127struct SCIP_NlhdlrData
140void printNlhdlrExprData(
149 nterms = nlhdlrexprdata->nterms;
157 startidx = nlhdlrexprdata->termbegins[
i];
159 if( startidx == nlhdlrexprdata->termbegins[
i + 1] )
162 assert(nlhdlrexprdata->offsets[
i] != 0.0);
171 for( j = startidx; j < nlhdlrexprdata->termbegins[
i + 1]; ++j )
173 if( nlhdlrexprdata->transcoefs[j] != 1.0 )
185 if( nlhdlrexprdata->offsets[
i] != 0.0 )
197 for( j = nlhdlrexprdata->termbegins[
nterms-1]; j < nlhdlrexprdata->termbegins[
nterms]; ++j )
199 if( nlhdlrexprdata->transcoefs[j] != 1.0 )
208 if( nlhdlrexprdata->offsets[
nterms-1] != 0.0 )
229 ndisvars = nlhdlrexprdata->nterms - 1;
236 for(
i = 0;
i < ndisvars; ++
i )
262 if( nlhdlrexprdata->disvars ==
NULL )
265 ndisvars = nlhdlrexprdata->nterms - 1;
268 for(
i = 0;
i < ndisvars; ++
i )
301 nterms = nlhdlrexprdata->nterms;
302 beta = nlhdlrexprdata->offsets[
nterms - 1];
312 for(
i = 0;
i < ndisvars; ++
i )
326 coef = -nlhdlrexprdata->transcoefs[
i];
357 ntranscoefs = termbegins[
nterms];
365 (*nlhdlrexprdata)->nvars =
nvars;
366 (*nlhdlrexprdata)->nterms =
nterms;
368 (*nlhdlrexprdata)->disrow =
NULL;
369 (*nlhdlrexprdata)->disvars =
NULL;
371 (*nlhdlrexprdata)->varvals =
NULL;
372 (*nlhdlrexprdata)->disvarvals =
NULL;
375 SCIPdebugMsg(
scip,
"created nlhdlr data for the following soc expression:\n");
376 printNlhdlrExprData(
scip, *nlhdlrexprdata);
398 ntranscoefs = (*nlhdlrexprdata)->termbegins[(*nlhdlrexprdata)->nterms];
426 for(
i = 0;
i < nlhdlrexprdata->nvars; ++
i )
430 nlhdlrexprdata->varvals[
i] =
SCIPround(
scip, nlhdlrexprdata->varvals[
i]);
434 if( nlhdlrexprdata->disvarvals !=
NULL )
435 for(
i = 0;
i < nlhdlrexprdata->nterms - 1; ++
i )
439 nlhdlrexprdata->disvarvals[
i] =
SCIPround(
scip, nlhdlrexprdata->disvarvals[
i]);
458 result = nlhdlrexprdata->offsets[k];
461 result += nlhdlrexprdata->transcoefs[
i] * nlhdlrexprdata->varvals[nlhdlrexprdata->transcoefsidx[
i]];
524 vars = nlhdlrexprdata->vars;
525 transcoefs = nlhdlrexprdata->transcoefs;
526 transcoefsidx = nlhdlrexprdata->transcoefsidx;
527 termbegins = nlhdlrexprdata->termbegins;
528 nterms = nlhdlrexprdata->nterms;
538 fvalue +=
SQR( valterms[
i] );
539 if( nlhdlrexprdata->offsets[
i] != 0.0 )
542 fvalue = sqrt(fvalue);
547 if( fvalue - rhsval <= mincutviolation )
549 SCIPdebugMsg(
scip,
"do not generate cut: rhsval %g, fvalue %g violation is %g\n", rhsval, fvalue, fvalue - rhsval);
556 SCIPdebugMsg(
scip,
"do not generate cut for lhs=%g, cannot linearize at top of cone\n", fvalue);
569 cutrhs = nlhdlrexprdata->offsets[
nterms - 1];
574 for( j = 0; j <
nterms - 1; ++j )
576 for(
i = termbegins[j];
i < termbegins[j + 1]; ++
i )
581 cutcoef = transcoefs[
i] * valterms[j] / fvalue;
586 cutrhs += cutcoef * nlhdlrexprdata->varvals[transcoefsidx[
i]];
662 vars = nlhdlrexprdata->vars;
663 disvars = nlhdlrexprdata->disvars;
664 transcoefs = nlhdlrexprdata->transcoefs;
665 transcoefsidx = nlhdlrexprdata->transcoefsidx;
666 termbegins = nlhdlrexprdata->termbegins;
667 nterms = nlhdlrexprdata->nterms;
673 disvarval = nlhdlrexprdata->disvarvals[disaggidx];
677 denominator = sqrt(4.0 *
SQR(lhsval) +
SQR(rhsval - disvarval));
680 fvalue = denominator - rhsval - disvarval;
683 if( fvalue <= mincutviolation )
685 SCIPdebugMsg(
scip,
"skip cut on disaggregation index %d as violation=%g below minviolation %g\n", disaggidx,
686 fvalue, mincutviolation);
693 SCIPdebugMsg(
scip,
"skip cut on disaggregation index %d as we are on top of cone (denom=%g)\n", disaggidx, denominator);
698 ncutvars = (termbegins[
nterms] - termbegins[
nterms-1]) + (termbegins[disaggidx + 1] - termbegins[disaggidx]) + 1;
705 offsetzero = nlhdlrexprdata->offsets[disaggidx] == 0.0 && nlhdlrexprdata->offsets[
nterms-1] == 0.0;
713 for(
i = termbegins[disaggidx];
i < termbegins[disaggidx + 1]; ++
i )
719 cutcoef = 4.0 * lhsval * transcoefs[
i] / denominator;
724 constant += cutcoef * nlhdlrexprdata->varvals[transcoefsidx[
i]];
734 cutcoef = (rhsval - disvarval) * transcoefs[
i] / denominator - transcoefs[
i];
739 constant += cutcoef * nlhdlrexprdata->varvals[transcoefsidx[
i]];
743 cutcoef = (disvarval - rhsval) / denominator - 1.0;
744 cutvar = disvars[disaggidx];
750 constant += cutcoef * nlhdlrexprdata->disvarvals[disaggidx];
802 SCIPdebugMsg(
scip,
"generated row for SOC, efficacy=%g, minefficacy=%g, allowweakcuts=%u\n",
803 cutefficacy, nlhdlrdata->mincutefficacy, allowweakcuts);
812#ifdef SCIP_CONSNONLINEAR_ROWNOTREMOVABLE
814 if( addbranchscores )
902 for(
i = nchildren - 1;
i >= 0; --
i )
921 assert(*nexprs < 2 * nchildren);
922 occurringexprs[*nexprs] = childarg;
934 assert(*nexprs < 2 * nchildren);
935 occurringexprs[*nexprs] = child;
956 assert(*nexprs < 2 * nchildren);
957 occurringexprs[*nexprs] = childarg1;
967 assert(*nexprs < 2 * nchildren);
968 occurringexprs[*nexprs] = childarg2;
1016 for(
i = 0;
i < nchildren; ++
i )
1026 assert(0 <= varpos && varpos < nexprs);
1028 quadmatrix[varpos * nexprs + varpos] = childcoefs[
i];
1035 assert(0 <= varpos && varpos < nexprs);
1037 quadmatrix[varpos * nexprs + varpos] = childcoefs[
i];
1048 assert(0 <= varpos && varpos < nexprs);
1051 assert(0 <= varpos2 && varpos2 < nexprs);
1052 assert(varpos != varpos2);
1055 quadmatrix[
MIN(varpos, varpos2) * nexprs +
MAX(varpos, varpos2)] = childcoefs[
i] / 2.0;
1060 assert(0 <= varpos && varpos < nexprs);
1062 linvector[varpos] = childcoefs[
i];
1090 int nexttranscoef = 0;
1113 specialtermidx = -1;
1119 if( eigvals[
i] < 0.0 )
1121 assert(specialtermidx == -1);
1125 *lhsconstant -= bp[
i] * bp[
i] / (4.0 * eigvals[
i]);
1131 sqrteigval = sqrt(eigvals[
i]);
1133 termbegins[nextterm] = nexttranscoef;
1134 offsets[nextterm] = bp[
i] / (2.0 * sqrteigval);
1135 *lhsconstant -= bp[
i] * bp[
i] / (4.0 * eigvals[
i]);
1138 for( j = 0; j <
nvars; ++j )
1142 transcoefs[nexttranscoef] = sqrteigval * eigvecmatrix[
i *
nvars + j];
1143 transcoefsidx[nexttranscoef] = j;
1150 assert(specialtermidx > -1);
1157 if( *lhsconstant < 0.0 )
1161 if( *lhsconstant > 0.0 )
1163 termbegins[nextterm] = nexttranscoef;
1164 offsets[nextterm] = sqrt(*lhsconstant);
1174 assert(-eigvals[specialtermidx] > 0.0);
1175 sqrteigval = sqrt(-eigvals[specialtermidx]);
1177 termbegins[nextterm] = nexttranscoef;
1178 offsets[nextterm] = -bp[specialtermidx] / (2.0 * sqrteigval);
1183 rhstermlb = offsets[nextterm];
1184 for( j = 0; j <
nvars; ++j )
1195 if( eigvecmatrix[specialtermidx *
nvars + j] > 0.0 )
1212 rhstermlb += sqrteigval * eigvecmatrix[specialtermidx *
nvars + j] * aux;
1215 rhstermub = offsets[nextterm];
1216 for( j = 0; j <
nvars; ++j )
1227 if( eigvecmatrix[specialtermidx *
nvars + j] > 0.0 )
1244 rhstermub += sqrteigval * eigvecmatrix[specialtermidx *
nvars + j] * aux;
1251 if( rhstermub < rhstermlb )
1261 signfactor =
SCIPisLE(
scip, rhstermub, 0.0) ? -1.0 : 1.0;
1263 offsets[nextterm] *= signfactor;
1266 for( j = 0; j <
nvars; ++j )
1271 transcoefs[nexttranscoef] = signfactor * sqrteigval * eigvecmatrix[specialtermidx *
nvars + j];
1272 transcoefsidx[nexttranscoef] = j;
1278 assert(nexttranscoef > termbegins[nextterm]);
1287 termbegins[nextterm] = nexttranscoef;
1378 for(
i = 0;
i < nchildren; ++
i )
1390 if( childcoefs[
i] < 0.0 )
1395 transcoefs[
nterms] = sqrt(childcoefs[
i]);
1408 if( childcoefs[
i] < 0.0 )
1413 transcoefs[
nterms] = sqrt(childcoefs[
i]);
1441 for(
i = 0;
i < nchildren; ++
i )
1450 constant -=
SQR(0.5 * childcoefs[
i] / transcoefs[auxvarpos]);
1472 if( constant > 0.0 )
1484 transcoefsidx[
i] =
i;
1491 if( constant > 0.0 )
1495 offsets[
nterms - 2] = sqrt(constant);
1499 offsets[
nterms - 1] = 0.0;
1501 transcoefs[
nterms - 2] = 1.0;
1510 offsets[
nterms - 1] = 0.0;
1512 transcoefs[
nterms - 1] = 1.0;
1520 for(
i = 0;
i < nchildren; ++
i )
1531 vars[nextentry] = squarearg;
1538 vars[nextentry] = children[
i];
1550 offsets[auxvarpos] = 0.5 * childcoefs[
i] / transcoefs[auxvarpos];
1556 SCIPdebugMsg(
scip,
"found SOC structure for expression %p\n", (
void*)expr);
1602 int* transcoefsidx =
NULL;
1603 int* termbegins =
NULL;
1654 childcoefs[0] = 1.0;
1670 for(
i = 0;
i < nchildren; ++
i )
1674 if( childcoefs[
i] > 0.0 )
1687 if( childcoefs[
i] > 0.0 )
1700 if( childcoefs[
i] > 0.0 )
1717 if( nposquadterms > 1 && nnegquadterms > 1 )
1721 if( nposbilinterms + nnegbilinterms > 1 )
1725 if( nposbilinterms > 0 && nposquadterms > 0 )
1729 if( nnegbilinterms > 0 && nnegquadterms > 0 )
1733 if( nposquadterms == nchildren || nnegquadterms == nchildren )
1736 assert(nposquadterms <= 1 || nnegquadterms <= 1);
1737 assert(nposbilinterms + nnegbilinterms <= 1);
1738 assert(nposbilinterms == 0 || nposquadterms == 0);
1739 assert(nnegbilinterms == 0 || nnegquadterms == 0);
1742 ishyperbolic = (nposbilinterms + nnegbilinterms > 0);
1759 if( (ishyperbolic && nnegbilinterms > 0) || (!ishyperbolic && nnegquadterms < 2) )
1765 assert(nnegbilinterms == 1 || nnegquadterms == 1);
1775 specialtermidx = rhsidx;
1776 lhsconstant = constant - rhs;
1777 *enforcebelow =
TRUE;
1791 specialtermidx = lhsidx;
1792 lhsconstant = lhs - constant;
1795 for(
i = 0;
i < nchildren; ++
i )
1796 childcoefs[
i] = -childcoefs[
i];
1797 *enforcebelow =
FALSE;
1799 assert(childcoefs[specialtermidx] != 0.0);
1825 lhsconstant *= 4.0 / -childcoefs[specialtermidx];
1840 if( rhsactivity.
inf < 0.0 )
1843 if( rhsactivity.
sup > 0.0 )
1872 ntranscoefs = ishyperbolic ? nchildren + 3 : nchildren;
1873 nvars = ishyperbolic ? nchildren + 1 : nchildren;
1877 if( lhsconstant > 0.0 )
1892 for(
i = 0;
i < nchildren; ++
i )
1895 if(
i == specialtermidx )
1901 vars[nextentry] = children[
i];
1916 termbegins[nextentry] = nnzinterms;
1917 offsets[nextentry] = 0.0;
1919 transcoefsidx[nnzinterms] = nextentry;
1923 assert(4.0 * childcoefs[
i] / -childcoefs[specialtermidx] > 0.0);
1924 transcoefs[nnzinterms] = sqrt(4.0 * childcoefs[
i] / -childcoefs[specialtermidx]);
1929 transcoefs[nnzinterms] = sqrt(childcoefs[
i]);
1938 assert(nextentry == nchildren - 1);
1941 if( lhsconstant > 0.0 )
1943 termbegins[nextentry] = nnzinterms;
1944 offsets[nextentry] = sqrt(lhsconstant);
1957 vars[
nvars - 1] = children[specialtermidx];
1967 assert(childcoefs[specialtermidx] < 0.0);
1969 termbegins[nextentry] = nnzinterms;
1970 offsets[nextentry] = 0.0;
1971 transcoefs[nnzinterms] = rhssign * sqrt(-childcoefs[specialtermidx]);
1972 transcoefsidx[nnzinterms] =
nvars - 1;
1992 termbegins[nextentry] = nnzinterms;
1993 offsets[nextentry] = 0.0;
1996 transcoefsidx[nnzinterms] =
nvars - 2;
1997 transcoefs[nnzinterms] = 1.0;
2001 transcoefsidx[nnzinterms] =
nvars - 1;
2002 transcoefs[nnzinterms] = -1.0;
2009 termbegins[nextentry] = nnzinterms;
2010 offsets[nextentry] = 0.0;
2013 transcoefsidx[nnzinterms] =
nvars - 2;
2014 transcoefs[nnzinterms] = rhssign;
2018 transcoefsidx[nnzinterms] =
nvars - 1;
2019 transcoefs[nnzinterms] = rhssign;
2026 assert(nnzinterms == ntranscoefs);
2029 termbegins[nextentry] = nnzinterms;
2032 SCIPdebugMsg(
scip,
"found SOC structure for expression %p\n %g <= ", (
void*)expr, lhs);
2137 transcoefsidx =
NULL;
2179 SCIPdebugMsg(
scip,
"Failed to compute eigenvalues and eigenvectors for expression:\n");
2197 for( j = 0; j <
nvars; ++j )
2199 bp[
i] += lincoefs[j] * eigvecmatrix[
i *
nvars + j];
2215 else if( eigvals[
i] > 0.0 )
2222 if( npos + nneg < 2 )
2229 if( rhsissoc || lhsissoc )
2256 lhsconstant = lhs - constant;
2260 eigvals[
i] = -eigvals[
i];
2263 *enforcebelow =
FALSE;
2267 lhsconstant = constant - rhs;
2268 *enforcebelow =
TRUE;
2279 transcoefsidx, offsets, &lhsconstant, &
nterms, success) );
2298 SCIPdebugMsg(
scip,
"found SOC structure for expression %p\n%f <= ", (
void*)expr, lhs);
2377 *enforcebelow = *success;
2386 if( !(*success) && nlhdlrdata->compeigenvalues )
2460 SCIP_CALL(
detectSOC(
scip, nlhdlrdata, expr, conslhs, consrhs, nlhdlrexprdata, &enforcebelow, &success) );
2473 *enforcing |= *participating;
2475 else if( cons !=
NULL )
2483 *enforcing |= *participating;
2485 *enforcing |= *participating;
2503 assert(nlhdlrexprdata->transcoefsidx !=
NULL);
2504 assert(nlhdlrexprdata->nterms > 1);
2515 for(
i = 0;
i < nlhdlrexprdata->nterms - 1; ++
i )
2520 *auxvalue +=
SQR(termval);
2523 assert(*auxvalue >= 0.0);
2526 *auxvalue = sqrt(*auxvalue);
2543 for(
i = 0;
i < nchildren; ++
i )
2556 *auxvalue += childcoefs[
i] *
SQR( solval );
2617 if( nlhdlrexprdata->nterms > 3 )
2622#ifdef WITH_DEBUG_SOLUTION
2623 if( SCIPdebugIsMainscip(
scip) )
2632 for(
i = 0;
i < nlhdlrexprdata->nvars; ++
i )
2643 nterms = nlhdlrexprdata->nterms;
2649 ndisvars = nlhdlrexprdata->nterms - 1;
2653 for(
i = 0;
i < ndisvars; ++
i )
2661 for(
i = 0;
i < ndisvars; ++
i )
2665 disvarval =
SQR(lhsval) / rhsval;
2679 printNlhdlrExprData(
scip, nlhdlrexprdata);
2683 if( nlhdlrexprdata->nterms == 2 )
2698 norm +=
SQR(nlhdlrexprdata->transcoefs[
i]);
2703 for( plusminus1 = -1.0; plusminus1 <= 1.0; plusminus1 += 2.0 )
2707 nlhdlrexprdata->varvals[nlhdlrexprdata->transcoefsidx[
i]] = nlhdlrexprdata->transcoefs[
i] / norm * (plusminus1 - nlhdlrexprdata->offsets[0]);
2713 if( rowprep !=
NULL )
2733 else if( nlhdlrexprdata->nterms == 3 && nlhdlrexprdata->termbegins[0] != nlhdlrexprdata->termbegins[1] )
2760 static const SCIP_Real refpoints[3][2] = { {-1.0, 0.0}, {1.0, 1.0}, {1.0, -1.0} };
2769 i = nlhdlrexprdata->transcoefsidx[nlhdlrexprdata->termbegins[0]];
2770 v1i = nlhdlrexprdata->transcoefs[nlhdlrexprdata->termbegins[0]];
2773 v2zero = nlhdlrexprdata->termbegins[1] == nlhdlrexprdata->termbegins[2];
2777 if( !v2zero &&
SCIPsortedvecFindInt(nlhdlrexprdata->transcoefsidx + nlhdlrexprdata->termbegins[1],
i, nlhdlrexprdata->termbegins[2] - nlhdlrexprdata->termbegins[1], &pos) )
2779 assert(nlhdlrexprdata->transcoefsidx[nlhdlrexprdata->termbegins[1] + pos] ==
i);
2780 v2i = nlhdlrexprdata->transcoefs[nlhdlrexprdata->termbegins[1] + pos];
2784 for( k = nlhdlrexprdata->termbegins[1]; k < nlhdlrexprdata->termbegins[2]; ++k )
2788 if( nlhdlrexprdata->transcoefsidx[k] ==
i )
2793 if(
SCIPsortedvecFindInt(nlhdlrexprdata->transcoefsidx + nlhdlrexprdata->termbegins[0], nlhdlrexprdata->transcoefsidx[k], nlhdlrexprdata->termbegins[1] - nlhdlrexprdata->termbegins[0], &pos) )
2795 assert(nlhdlrexprdata->transcoefsidx[nlhdlrexprdata->termbegins[0] + pos] == nlhdlrexprdata->transcoefsidx[k]);
2796 v1j = nlhdlrexprdata->transcoefs[nlhdlrexprdata->termbegins[0] + pos];
2799 v2j = nlhdlrexprdata->transcoefs[k];
2804 j = nlhdlrexprdata->transcoefsidx[k];
2822 for( point = 0; point < (v2zero ? 2 : 3); ++point )
2824 c = refpoints[point][0] - nlhdlrexprdata->offsets[0];
2829 d = refpoints[point][1] - nlhdlrexprdata->offsets[1];
2830 nlhdlrexprdata->varvals[j] = (d - v2i/v1i*
c) / (v2j - v2i * v1j / v1i);
2831 nlhdlrexprdata->varvals[
i] = (
c - v1j * nlhdlrexprdata->varvals[j]) / v1i;
2840 nlhdlrexprdata->varvals[
i] =
c / v1i;
2852 if( rowprep !=
NULL )
2873 else if( nlhdlrexprdata->nterms == 3 )
2889 norm +=
SQR(nlhdlrexprdata->transcoefs[
i]);
2894 for( plusminus1 = -1.0; plusminus1 <= 1.0; plusminus1 += 2.0 )
2898 nlhdlrexprdata->varvals[nlhdlrexprdata->transcoefsidx[
i]] = nlhdlrexprdata->transcoefs[
i] / norm * (plusminus1 - nlhdlrexprdata->offsets[1]);
2904 if( rowprep !=
NULL )
2938 static const SCIP_Real refpoints[3][2] = { {-0.5, 0.0}, {0.5, 1.0}, {0.5, -1.0} };
2952 for( k = 0; k < nlhdlrexprdata->nterms - 1; ++k )
2954 vkzero = nlhdlrexprdata->termbegins[k+1] == nlhdlrexprdata->termbegins[k];
2955 assert(!vkzero || nlhdlrexprdata->offsets[k] != 0.0);
2960 norm +=
SQR(nlhdlrexprdata->transcoefs[
i]);
2961 assert(vkzero || norm > 0.0);
2965 for( point = vkzero ? 1 : 0; point < 3; ++point )
2969 nlhdlrexprdata->varvals[nlhdlrexprdata->transcoefsidx[
i]] = nlhdlrexprdata->transcoefs[
i] / norm * (refpoints[point][0] - nlhdlrexprdata->offsets[k]);
2974 nlhdlrexprdata->disvarvals[k] = rhsval + refpoints[point][1];
2979 if( rowprep !=
NULL )
3012 if( nlhdlrexprdata->disrow !=
NULL )
3034 assert(nlhdlrexprdata->nterms < 4 || nlhdlrexprdata->disrow !=
NULL);
3035 assert(nlhdlrexprdata->nterms > 1);
3039 if( branchcandonly )
3056 if( nlhdlrexprdata->nterms < 4 )
3063 if( rowprep !=
NULL )
3077 ndisaggrs = nlhdlrexprdata->nterms - 1;
3083 SCIPdebugMsg(
scip,
"added disaggregation row to LP, cutoff=%u\n", infeasible);
3101 if( rowprep !=
NULL )
3121 assert(nlhdlrexprdata->nterms < 4 || nlhdlrexprdata->disrow !=
NULL);
3122 assert(nlhdlrexprdata->nterms > 1);
3133 if( nlhdlrexprdata->nterms < 4 )
3140 if( rowprep !=
NULL )
3150 for( k = 0; k < nlhdlrexprdata->nterms - 1; ++k )
3157 if( rowprep !=
NULL )
3197 "Minimum efficacy which a cut needs in order to be added.",
3201 "Should Eigenvalue computations be done to detect complex cases in quadratic constraints?",
3240 int** transcoefsidx,
3259 nlhdlrdata.mincutefficacy = 0.0;
3260 nlhdlrdata.compeigenvalues = compeigenvalues;
3265 SCIP_CALL(
detectSOC(
scip, &nlhdlrdata, expr, conslhs, consrhs, &nlhdlrexprdata, &enforcebelow, success) );
3272 for(
i = 0;
i < nlhdlrexprdata->nvars; ++
i )
3287 for(
i = 0;
i < nlhdlrexprdata->nvars; ++
i )
3293 *offsets = nlhdlrexprdata->offsets;
3294 *transcoefs = nlhdlrexprdata->transcoefs;
3295 *transcoefsidx = nlhdlrexprdata->transcoefsidx;
3296 *termbegins = nlhdlrexprdata->termbegins;
3297 *
nvars = nlhdlrexprdata->nvars;
3298 *
nterms = nlhdlrexprdata->nterms;
3303 if( nlhdlrexprdata !=
NULL )
3310 *transcoefsidx =
NULL;
3325 int** transcoefsidx,
3342 ntranscoefs = (*termbegins)[
nterms];
constraint handler for nonlinear constraints specified by algebraic expressions
#define SCIPdebugGetSolVal(scip, var, val)
#define SCIPdebugAddSolVal(scip, var, val)
#define SCIP_LONGINT_FORMAT
power and signed power expression handlers
variable expression handler
unsigned int SCIPgetExprNAuxvarUsesNonlinear(SCIP_EXPR *expr)
int SCIPgetExprNLocksPosNonlinear(SCIP_EXPR *expr)
SCIP_VAR * SCIPgetExprAuxVarNonlinear(SCIP_EXPR *expr)
SCIP_EXPR * SCIPgetExprNonlinear(SCIP_CONS *cons)
SCIP_Real SCIPgetRhsNonlinear(SCIP_CONS *cons)
int SCIPgetExprNLocksNegNonlinear(SCIP_EXPR *expr)
SCIP_RETCODE SCIPregisterExprUsageNonlinear(SCIP *scip, SCIP_EXPR *expr, SCIP_Bool useauxvar, SCIP_Bool useactivityforprop, SCIP_Bool useactivityforsepabelow, SCIP_Bool useactivityforsepaabove)
SCIP_Real SCIPgetLhsNonlinear(SCIP_CONS *cons)
SCIP_RETCODE SCIPaddVar(SCIP *scip, SCIP_VAR *var)
void SCIPhashmapFree(SCIP_HASHMAP **hashmap)
int SCIPhashmapGetImageInt(SCIP_HASHMAP *hashmap, void *origin)
int SCIPhashmapGetNElements(SCIP_HASHMAP *hashmap)
SCIP_RETCODE SCIPhashmapCreate(SCIP_HASHMAP **hashmap, BMS_BLKMEM *blkmem, int mapsize)
SCIP_Bool SCIPhashmapExists(SCIP_HASHMAP *hashmap, void *origin)
SCIP_RETCODE SCIPhashmapInsertInt(SCIP_HASHMAP *hashmap, void *origin, int image)
void SCIPhashsetFree(SCIP_HASHSET **hashset, BMS_BLKMEM *blkmem)
SCIP_Bool SCIPhashsetExists(SCIP_HASHSET *hashset, void *element)
int SCIPhashsetGetNElements(SCIP_HASHSET *hashset)
SCIP_RETCODE SCIPhashsetInsert(SCIP_HASHSET *hashset, BMS_BLKMEM *blkmem, void *element)
SCIP_RETCODE SCIPhashsetCreate(SCIP_HASHSET **hashset, BMS_BLKMEM *blkmem, int size)
SCIP_RETCODE SCIPhashsetRemove(SCIP_HASHSET *hashset, void *element)
void SCIPinfoMessage(SCIP *scip, FILE *file, const char *formatstr,...)
void SCIPverbMessage(SCIP *scip, SCIP_VERBLEVEL msgverblevel, FILE *file, const char *formatstr,...)
void SCIPfreeSOCArraysNonlinear(SCIP *scip, SCIP_VAR ***vars, SCIP_Real **offsets, SCIP_Real **transcoefs, int **transcoefsidx, int **termbegins, int nvars, int nterms)
SCIP_RETCODE SCIPisSOCNonlinear(SCIP *scip, SCIP_CONS *cons, SCIP_Bool compeigenvalues, SCIP_Bool *success, SCIP_SIDETYPE *sidetype, SCIP_VAR ***vars, SCIP_Real **offsets, SCIP_Real **transcoefs, int **transcoefsidx, int **termbegins, int *nvars, int *nterms)
SCIP_RETCODE SCIPincludeNlhdlrSoc(SCIP *scip)
SCIP_RETCODE SCIPaddRealParam(SCIP *scip, const char *name, const char *desc, SCIP_Real *valueptr, SCIP_Bool isadvanced, SCIP_Real defaultvalue, SCIP_Real minvalue, SCIP_Real maxvalue, SCIP_DECL_PARAMCHGD((*paramchgd)), SCIP_PARAMDATA *paramdata)
SCIP_RETCODE SCIPaddBoolParam(SCIP *scip, const char *name, const char *desc, SCIP_Bool *valueptr, SCIP_Bool isadvanced, SCIP_Bool defaultvalue, SCIP_DECL_PARAMCHGD((*paramchgd)), SCIP_PARAMDATA *paramdata)
void SCIPswapReals(SCIP_Real *value1, SCIP_Real *value2)
SCIP_RETCODE SCIPaddPoolCut(SCIP *scip, SCIP_ROW *row)
SCIP_Real SCIPgetCutEfficacy(SCIP *scip, SCIP_SOL *sol, SCIP_ROW *cut)
SCIP_Bool SCIPisCutApplicable(SCIP *scip, SCIP_ROW *cut)
SCIP_RETCODE SCIPaddRow(SCIP *scip, SCIP_ROW *row, SCIP_Bool forcecut, SCIP_Bool *infeasible)
int SCIPexprGetNChildren(SCIP_EXPR *expr)
SCIP_Real SCIPgetExponentExprPow(SCIP_EXPR *expr)
SCIP_Bool SCIPisExprProduct(SCIP *scip, SCIP_EXPR *expr)
SCIP_Bool SCIPisExprSum(SCIP *scip, SCIP_EXPR *expr)
SCIP_Real * SCIPgetCoefsExprSum(SCIP_EXPR *expr)
SCIP_Bool SCIPisExprVar(SCIP *scip, SCIP_EXPR *expr)
SCIP_RETCODE SCIPprintExpr(SCIP *scip, SCIP_EXPR *expr, FILE *file)
SCIP_Bool SCIPisExprPower(SCIP *scip, SCIP_EXPR *expr)
SCIP_EXPR ** SCIPexprGetChildren(SCIP_EXPR *expr)
SCIP_Real SCIPgetConstantExprSum(SCIP_EXPR *expr)
SCIP_VAR * SCIPgetVarExprVar(SCIP_EXPR *expr)
SCIP_INTERVAL SCIPexprGetActivity(SCIP_EXPR *expr)
SCIP_RETCODE SCIPdismantleExpr(SCIP *scip, FILE *file, SCIP_EXPR *expr)
SCIP_RETCODE SCIPevalExprActivity(SCIP *scip, SCIP_EXPR *expr)
struct SCIP_Interval SCIP_INTERVAL
SCIP_Real SCIPgetLPFeastol(SCIP *scip)
#define SCIPfreeBlockMemoryArray(scip, ptr, num)
#define SCIPallocClearBlockMemory(scip, ptr)
BMS_BLKMEM * SCIPblkmem(SCIP *scip)
BMS_BUFMEM * SCIPbuffer(SCIP *scip)
#define SCIPallocClearBufferArray(scip, ptr, num)
#define SCIPallocBufferArray(scip, ptr, num)
#define SCIPfreeBufferArray(scip, ptr)
#define SCIPduplicateBufferArray(scip, ptr, source, num)
#define SCIPallocBlockMemoryArray(scip, ptr, num)
#define SCIPfreeBlockMemory(scip, ptr)
#define SCIPfreeBlockMemoryArrayNull(scip, ptr, num)
#define SCIPfreeBufferArrayNull(scip, ptr)
#define SCIPallocBlockMemory(scip, ptr)
#define SCIPduplicateBlockMemoryArray(scip, ptr, source, num)
SCIP_NLHDLRDATA * SCIPnlhdlrGetData(SCIP_NLHDLR *nlhdlr)
void SCIPnlhdlrSetFreeExprData(SCIP_NLHDLR *nlhdlr,)
const char * SCIPnlhdlrGetName(SCIP_NLHDLR *nlhdlr)
void SCIPnlhdlrSetSollinearize(SCIP_NLHDLR *nlhdlr,)
void SCIPnlhdlrSetSepa(SCIP_NLHDLR *nlhdlr, SCIP_DECL_NLHDLRINITSEPA((*initsepa)), SCIP_DECL_NLHDLRENFO((*enfo)), SCIP_DECL_NLHDLRESTIMATE((*estimate)),)
void SCIPnlhdlrSetFreeHdlrData(SCIP_NLHDLR *nlhdlr,)
void SCIPnlhdlrSetCopyHdlr(SCIP_NLHDLR *nlhdlr,)
SCIP_RETCODE SCIPincludeNlhdlrNonlinear(SCIP *scip, SCIP_NLHDLR **nlhdlr, const char *name, const char *desc, int detectpriority, int enfopriority, SCIP_DECL_NLHDLRDETECT((*detect)), SCIP_DECL_NLHDLREVALAUX((*evalaux)), SCIP_NLHDLRDATA *nlhdlrdata)
SCIP_RETCODE SCIPcreateEmptyRowConshdlr(SCIP *scip, SCIP_ROW **row, SCIP_CONSHDLR *conshdlr, const char *name, SCIP_Real lhs, SCIP_Real rhs, SCIP_Bool local, SCIP_Bool modifiable, SCIP_Bool removable)
SCIP_RETCODE SCIPaddVarToRow(SCIP *scip, SCIP_ROW *row, SCIP_VAR *var, SCIP_Real val)
SCIP_Real SCIPgetRowSolFeasibility(SCIP *scip, SCIP_ROW *row, SCIP_SOL *sol)
SCIP_RETCODE SCIPreleaseRow(SCIP *scip, SCIP_ROW **row)
void SCIPmarkRowNotRemovableLocal(SCIP *scip, SCIP_ROW *row)
SCIP_Bool SCIProwIsInLP(SCIP_ROW *row)
SCIP_Real SCIPgetSolVal(SCIP *scip, SCIP_SOL *sol, SCIP_VAR *var)
SCIP_Longint SCIPgetNLPs(SCIP *scip)
SCIP_Real SCIPinfinity(SCIP *scip)
SCIP_Bool SCIPisIntegral(SCIP *scip, SCIP_Real val)
SCIP_Bool SCIPisPositive(SCIP *scip, SCIP_Real val)
SCIP_Bool SCIPisLE(SCIP *scip, SCIP_Real val1, SCIP_Real val2)
SCIP_Bool SCIPisInfinity(SCIP *scip, SCIP_Real val)
SCIP_Real SCIPround(SCIP *scip, SCIP_Real val)
SCIP_Real SCIPgetHugeValue(SCIP *scip)
SCIP_Bool SCIPisGT(SCIP *scip, SCIP_Real val1, SCIP_Real val2)
SCIP_Bool SCIPisNegative(SCIP *scip, SCIP_Real val)
SCIP_Bool SCIPisEQ(SCIP *scip, SCIP_Real val1, SCIP_Real val2)
SCIP_Bool SCIPisZero(SCIP *scip, SCIP_Real val)
SCIP_Bool SCIPisLT(SCIP *scip, SCIP_Real val1, SCIP_Real val2)
SCIP_Bool SCIPvarIsBinary(SCIP_VAR *var)
void SCIPvarMarkRelaxationOnly(SCIP_VAR *var)
SCIP_RETCODE SCIPaddVarLocksType(SCIP *scip, SCIP_VAR *var, SCIP_LOCKTYPE locktype, int nlocksdown, int nlocksup)
const char * SCIPvarGetName(SCIP_VAR *var)
SCIP_RETCODE SCIPreleaseVar(SCIP *scip, SCIP_VAR **var)
SCIP_RETCODE SCIPcreateVarBasic(SCIP *scip, SCIP_VAR **var, const char *name, SCIP_Real lb, SCIP_Real ub, SCIP_Real obj, SCIP_VARTYPE vartype)
SCIP_RETCODE SCIPcleanupRowprep2(SCIP *scip, SCIP_ROWPREP *rowprep, SCIP_SOL *sol, SCIP_Real maxcoefbound, SCIP_Bool *success)
SCIP_RETCODE SCIPensureRowprepSize(SCIP *scip, SCIP_ROWPREP *rowprep, int size)
SCIP_Real SCIPgetRowprepViolation(SCIP *scip, SCIP_ROWPREP *rowprep, SCIP_SOL *sol, SCIP_Bool *reliable)
char * SCIProwprepGetName(SCIP_ROWPREP *rowprep)
SCIP_Bool SCIProwprepIsLocal(SCIP_ROWPREP *rowprep)
SCIP_RETCODE SCIPaddRowprepTerm(SCIP *scip, SCIP_ROWPREP *rowprep, SCIP_VAR *var, SCIP_Real coef)
SCIP_RETCODE SCIPgetRowprepRowCons(SCIP *scip, SCIP_ROW **row, SCIP_ROWPREP *rowprep, SCIP_CONS *cons)
SCIP_RETCODE SCIPcreateRowprep(SCIP *scip, SCIP_ROWPREP **rowprep, SCIP_SIDETYPE sidetype, SCIP_Bool local)
int SCIProwprepGetNVars(SCIP_ROWPREP *rowprep)
void SCIProwprepAddSide(SCIP_ROWPREP *rowprep, SCIP_Real side)
void SCIPfreeRowprep(SCIP *scip, SCIP_ROWPREP **rowprep)
SCIP_Bool SCIPsortedvecFindInt(int *intarray, int val, int len, int *pos)
int SCIPsnprintf(char *t, int len, const char *s,...)
assert(minobj< SCIPgetCutoffbound(scip))
static volatile int nterms
SCIP_Bool SCIPlapackIsAvailable(void)
SCIP_RETCODE SCIPlapackComputeEigenvalues(BMS_BUFMEM *bufmem, SCIP_Bool geteigenvectors, int N, SCIP_Real *a, SCIP_Real *w)
interface methods for lapack functions
#define BMSclearMemoryArray(ptr, num)
#define NLHDLR_DETECTPRIORITY
#define NLHDLR_ENFOPRIORITY
static SCIP_RETCODE addCutPool(SCIP *scip, SCIP_NLHDLRDATA *nlhdlrdata, SCIP_ROWPREP *rowprep, SCIP_SOL *sol, SCIP_CONS *cons)
static SCIP_RETCODE tryFillNlhdlrExprDataQuad(SCIP *scip, SCIP_EXPR **occurringexprs, SCIP_Real *eigvecmatrix, SCIP_Real *eigvals, SCIP_Real *bp, int nvars, int *termbegins, SCIP_Real *transcoefs, int *transcoefsidx, SCIP_Real *offsets, SCIP_Real *lhsconstant, int *nterms, SCIP_Bool *success)
static SCIP_RETCODE freeNlhdlrExprData(SCIP *scip, SCIP_NLHDLREXPRDATA **nlhdlrexprdata)
static void updateVarVals(SCIP *scip, SCIP_NLHDLREXPRDATA *nlhdlrexprdata, SCIP_SOL *sol, SCIP_Bool roundtinyfrac)
static SCIP_RETCODE generateCutSolSOC(SCIP *scip, SCIP_ROWPREP **rowprep, SCIP_EXPR *expr, SCIP_CONS *cons, SCIP_NLHDLREXPRDATA *nlhdlrexprdata, SCIP_Real mincutviolation, SCIP_Real rhsval)
static SCIP_RETCODE createDisaggrRow(SCIP *scip, SCIP_CONSHDLR *conshdlr, SCIP_EXPR *expr, SCIP_NLHDLREXPRDATA *nlhdlrexprdata)
static SCIP_RETCODE detectSocNorm(SCIP *scip, SCIP_EXPR *expr, SCIP_NLHDLREXPRDATA **nlhdlrexprdata, SCIP_Bool *success)
static SCIP_RETCODE detectSOC(SCIP *scip, SCIP_NLHDLRDATA *nlhdlrdata, SCIP_EXPR *expr, SCIP_Real conslhs, SCIP_Real consrhs, SCIP_NLHDLREXPRDATA **nlhdlrexprdata, SCIP_Bool *enforcebelow, SCIP_Bool *success)
static SCIP_RETCODE checkAndCollectQuadratic(SCIP *scip, SCIP_EXPR *quadexpr, SCIP_HASHMAP *expr2idx, SCIP_EXPR **occurringexprs, int *nexprs, SCIP_Bool *success)
#define DEFAULT_MINCUTEFFICACY
#define DEFAULT_COMPEIGENVALUES
static SCIP_RETCODE createDisaggrVars(SCIP *scip, SCIP_EXPR *expr, SCIP_NLHDLREXPRDATA *nlhdlrexprdata)
static SCIP_RETCODE detectSocQuadraticComplex(SCIP *scip, SCIP_EXPR *expr, SCIP_Real conslhs, SCIP_Real consrhs, SCIP_NLHDLREXPRDATA **nlhdlrexprdata, SCIP_Bool *enforcebelow, SCIP_Bool *success)
static SCIP_RETCODE createNlhdlrExprData(SCIP *scip, SCIP_EXPR **vars, SCIP_Real *offsets, SCIP_Real *transcoefs, int *transcoefsidx, int *termbegins, int nvars, int nterms, SCIP_NLHDLREXPRDATA **nlhdlrexprdata)
static void buildQuadExprMatrix(SCIP *scip, SCIP_EXPR *quadexpr, SCIP_HASHMAP *expr2idx, int nexprs, SCIP_Real *quadmatrix, SCIP_Real *linvector)
static SCIP_RETCODE addCut(SCIP *scip, SCIP_NLHDLRDATA *nlhdlrdata, SCIP_ROWPREP *rowprep, SCIP_SOL *sol, SCIP_CONS *cons, SCIP_Bool allowweakcuts, SCIP_RESULT *result)
static SCIP_RETCODE freeDisaggrVars(SCIP *scip, SCIP_NLHDLREXPRDATA *nlhdlrexprdata)
static SCIP_RETCODE generateCutSolDisagg(SCIP *scip, SCIP_ROWPREP **rowprep, SCIP_EXPR *expr, SCIP_CONS *cons, SCIP_NLHDLREXPRDATA *nlhdlrexprdata, int disaggidx, SCIP_Real mincutviolation, SCIP_Real rhsval)
static SCIP_Real evalSingleTerm(SCIP *scip, SCIP_NLHDLREXPRDATA *nlhdlrexprdata, int k)
static SCIP_RETCODE detectSocQuadraticSimple(SCIP *scip, SCIP_EXPR *expr, SCIP_Real conslhs, SCIP_Real consrhs, SCIP_NLHDLREXPRDATA **nlhdlrexprdata, SCIP_Bool *enforcebelow, SCIP_Bool *success)
public functions of nonlinear handlers of nonlinear constraints
struct SCIP_Cons SCIP_CONS
struct SCIP_Conshdlr SCIP_CONSHDLR
struct SCIP_Expr SCIP_EXPR
enum SCIP_SideType SCIP_SIDETYPE
struct SCIP_RowPrep SCIP_ROWPREP
struct SCIP_HashMap SCIP_HASHMAP
struct SCIP_HashSet SCIP_HASHSET
#define SCIP_NLHDLR_METHOD_SEPAABOVE
#define SCIP_DECL_NLHDLREVALAUX(x)
struct SCIP_NlhdlrData SCIP_NLHDLRDATA
#define SCIP_NLHDLR_METHOD_SEPABOTH
#define SCIP_DECL_NLHDLRCOPYHDLR(x)
#define SCIP_DECL_NLHDLRSOLLINEARIZE(x)
#define SCIP_DECL_NLHDLRFREEEXPRDATA(x)
#define SCIP_DECL_NLHDLRDETECT(x)
#define SCIP_DECL_NLHDLREXITSEPA(x)
struct SCIP_Nlhdlr SCIP_NLHDLR
#define SCIP_DECL_NLHDLRINITSEPA(x)
#define SCIP_DECL_NLHDLRFREEHDLRDATA(x)
struct SCIP_NlhdlrExprData SCIP_NLHDLREXPRDATA
#define SCIP_DECL_NLHDLRENFO(x)
#define SCIP_NLHDLR_METHOD_SEPABELOW
enum SCIP_Result SCIP_RESULT
enum SCIP_Retcode SCIP_RETCODE
@ SCIP_VARTYPE_CONTINUOUS