Scippy

    SCIP

    Solving Constraint Integer Programs

    heur_repair.c
    Go to the documentation of this file.
    1/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
    2/* */
    3/* This file is part of the program and library */
    4/* SCIP --- Solving Constraint Integer Programs */
    5/* */
    6/* Copyright (c) 2002-2025 Zuse Institute Berlin (ZIB) */
    7/* */
    8/* Licensed under the Apache License, Version 2.0 (the "License"); */
    9/* you may not use this file except in compliance with the License. */
    10/* You may obtain a copy of the License at */
    11/* */
    12/* http://www.apache.org/licenses/LICENSE-2.0 */
    13/* */
    14/* Unless required by applicable law or agreed to in writing, software */
    15/* distributed under the License is distributed on an "AS IS" BASIS, */
    16/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. */
    17/* See the License for the specific language governing permissions and */
    18/* limitations under the License. */
    19/* */
    20/* You should have received a copy of the Apache-2.0 license */
    21/* along with SCIP; see the file LICENSE. If not visit scipopt.org. */
    22/* */
    23/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
    24
    25/**@file heur_repair.c
    26 * @ingroup DEFPLUGINS_HEUR
    27 * @brief repair primal heuristic
    28 * @author Gregor Hendel
    29 * @author Thomas Nagel
    30 *
    31 */
    32
    33/* This heuristic takes an infeasible solution and tries to repair it.
    34 * This can happen by variable fixing as long as the sum of all potential possible shiftings
    35 * is higher than alpha*slack or slack variables with a strong penalty on the objective function.
    36 * This heuristic cannot run if variable fixing and slack variables are turned off.
    37 */
    38
    39/*---+----1----+----2----+----3----+----4----+----5----+----6----+----7----+----8----+----9----+----0----+----1----+----2*/
    40
    42#include "scip/cons_linear.h"
    43#include "scip/cons_varbound.h"
    44#include "scip/heur_repair.h"
    45#include "scip/pub_heur.h"
    46#include "scip/pub_lp.h"
    47#include "scip/pub_message.h"
    48#include "scip/pub_misc.h"
    49#include "scip/pub_misc_sort.h"
    50#include "scip/pub_var.h"
    51#include "scip/scip_branch.h"
    53#include "scip/scip_cons.h"
    54#include "scip/scip_copy.h"
    55#include "scip/scip_exact.h"
    56#include "scip/scip_general.h"
    57#include "scip/scip_heur.h"
    58#include "scip/scip_lp.h"
    59#include "scip/scip_mem.h"
    60#include "scip/scip_message.h"
    61#include "scip/scip_numerics.h"
    62#include "scip/scip_param.h"
    63#include "scip/scip_prob.h"
    64#include "scip/scip_sol.h"
    65#include "scip/scip_solve.h"
    67#include "scip/scip_timing.h"
    68#include "scip/scip_tree.h"
    69#include "scip/scip_var.h"
    70#include "scip/scipdefplugins.h"
    71#include <string.h>
    72
    73#define HEUR_NAME "repair"
    74#define HEUR_DESC "tries to repair a primal infeasible solution"
    75#define HEUR_DISPCHAR SCIP_HEURDISPCHAR_LNS
    76#define HEUR_PRIORITY -20
    77#define HEUR_FREQ -1
    78#define HEUR_FREQOFS 0
    79#define HEUR_MAXDEPTH -1
    80#define HEUR_TIMING SCIP_HEURTIMING_AFTERNODE
    81#define HEUR_USESSUBSCIP TRUE /**< does the heuristic use a secondary SCIP instance? */
    82#define DEFAULT_MINFIXINGRATE 0.3 /* minimum percentage of integer variables that have to be fixed */
    83
    84#define DEFAULT_NODESOFS 500 /* number of nodes added to the contingent of the total nodes */
    85#define DEFAULT_MAXNODES 5000 /* maximum number of nodes to regard in the subproblem */
    86#define DEFAULT_MINNODES 50 /* minimum number of nodes to regard in the subproblem */
    87#define DEFAULT_NODESQUOT 0.1 /* subproblem nodes in relation to nodes of the original problem */
    88
    89#define DEFAULT_FILENAME "-" /**< file name of a solution to be used as infeasible starting point */
    90#define DEFAULT_ROUNDIT TRUE /**< if it is TRUE : fractional variables which are not fractional in the given
    91 * solution are rounded, if it is FALSE : solving process of this heuristic
    92 * is stopped
    93 */
    94#define DEFAULT_USEOBJFACTOR FALSE /**< should a scaled objective function for original variables be used in repair
    95 * subproblem?
    96 */
    97#define DEFAULT_USEVARFIX TRUE /**< should variable fixings be used in repair subproblem? */
    98#define DEFAULT_USESLACKVARS FALSE /**< should slack variables be used in repair subproblem? */
    99#define DEFAULT_ALPHA 2.0 /**< how many times the potential should be bigger than the slack? */
    100
    101/*
    102 * Data structures
    103 */
    104
    105
    106/** primal heuristic data */
    107struct SCIP_HeurData
    108{
    109 SCIP_SOL* infsol; /**< infeasible solution to start with */
    110 char* filename; /**< file name of a solution to be used as infeasible starting point */
    111 SCIP_Longint usednodes; /**< number of already used nodes by repair */
    112 SCIP_Longint subnodes; /**< number of nodes which were necessary to solve the sub-SCIP */
    113 SCIP_Longint subiters; /**< contains total number of iterations used in primal and dual simplex
    114 * and barrier algorithm to solve the sub-SCIP
    115 */
    116 SCIP_Real relvarfixed; /**< relative number of fixed variables */
    117 SCIP_Real alpha; /**< how many times the potential should be bigger than the slack? */
    118 SCIP_Real nodesquot; /**< subproblem nodes in relation to nodes of the original problem */
    119 SCIP_Real minfixingrate; /**< minimum percentage of integer variables that have to be fixed */
    120#ifdef SCIP_STATISTIC
    121 SCIP_Real relviolatedvars; /**< relative number of violated variables */
    122 SCIP_Real subpresoltime; /**< time for presolving the sub-SCIP */
    123 SCIP_Real relviolatedcons; /**< relative number of violated cons */
    124 SCIP_Real originalsolval; /**< value of the solution find by repair, in the original Problem*/
    125 SCIP_Real improvedoldsol; /**< value of the given solution after being improved by SCIP */
    126 int nviolatedvars; /**< number of violated variables in the given solution */
    127 int norigvars; /**< number of all variables in the given problem */
    128 int nviolatedcons; /**< number of violated cons in the given solution */
    129 int norcons; /**< number of all cons in the given problem */
    130#endif
    131 int nvarfixed; /**< number of all variables fixed in the sub problem */
    132 int runs; /**< number of branch and bound runs performed to solve the sub-SCIP */
    133 int nodesofs; /**< number of nodes added to the contingent of the total nodes */
    134 int maxnodes; /**< maximum number of nodes to regard in the subproblem */
    135 int minnodes; /**< minimum number of nodes to regard in the subproblem */
    136 SCIP_Bool roundit; /**< if it is TRUE : fractional variables which are not fractional in the
    137 * given solution are rounded, if it is FALSE : solving process of this
    138 * heuristic is stopped.
    139 */
    140 SCIP_Bool useobjfactor; /**< should a scaled objective function for original variables be used in
    141 * repair subproblem?
    142 */
    143 SCIP_Bool usevarfix; /**< should variable fixings be used in repair subproblem? */
    144 SCIP_Bool useslackvars; /**< should slack variables be used in repair subproblem? */
    145};
    146
    147
    148/*
    149 * Local methods
    150 */
    151
    152/** computes a factor, so that (factor) * (original objective upper bound) <= 1.*/
    153static
    155 SCIP* scip, /**< SCIP data structure */
    156 SCIP* subscip, /**< SCIP data structure */
    157 SCIP_Real* factor, /**< SCIP_Real to save the factor for the old objective function*/
    158 SCIP_Bool* success /**< SCIP_Bool: Is the factor real?*/
    159 )
    160{
    161 SCIP_VAR** vars;
    162 SCIP_Real lprelaxobj;
    163 SCIP_Real upperbound;
    164 SCIP_Real objoffset;
    165 int nvars;
    166 int i;
    167
    168 *success = TRUE;
    169 *factor = 0.0;
    170 upperbound = 0.0;
    171
    172 lprelaxobj = SCIPgetLowerbound(scip);
    173
    174 if( SCIPisInfinity(scip, -lprelaxobj) )
    175 {
    176 return SCIP_OKAY;
    177 }
    178
    180 {
    181 upperbound = SCIPgetUpperbound(scip);
    182 }
    183 else
    184 {
    185 SCIP_CALL( SCIPgetVarsData(scip, &vars, &nvars, NULL, NULL, NULL, NULL) );
    186
    187 /* tries to find an upper bound for the original objective function, by compute the worst objective value of the
    188 * LP-relaxation, which holds all variable bounds
    189 */
    190 for (i = 0; i < nvars; ++i)
    191 {
    192 upperbound = SCIPvarGetObj(vars[i]);
    193 if( SCIPisInfinity(scip, upperbound) || SCIPisInfinity(scip, -upperbound) )
    194 {
    195 /* TODO fancy diving function to find a solution for the max problem */
    196 *factor = 1 / SCIPinfinity(scip);
    197 return SCIP_OKAY;
    198 }
    199 else if( SCIPisZero(scip, upperbound) )
    200 {
    201 continue;
    202 }
    203 else if( SCIPisGT(scip, 0.0, upperbound) )
    204 {
    205 *factor += upperbound * SCIPvarGetLbGlobal(vars[i]);
    206 }
    207 else
    208 {
    209 *factor += upperbound * SCIPvarGetUbGlobal(vars[i]);
    210 }
    211 }
    212 }
    213
    214 /* Ending-sequence */
    215 *factor = upperbound - lprelaxobj;
    216 if( !SCIPisZero(scip, *factor) )
    217 {
    218 *factor = 1.0 / *factor;
    219 }
    220
    221 /* set an offset which guarantees positive objective values */
    222 objoffset = -lprelaxobj * (*factor);
    223 SCIP_CALL( SCIPaddOrigObjoffset(subscip, -objoffset) );
    224
    225 return SCIP_OKAY;
    226}
    227
    228/** returns the contributed potential for a variable */
    229static
    231 SCIP* scip, /**< SCIP data structure */
    232 SCIP_SOL* sol, /**< infeasible solution */
    233 SCIP_VAR* var, /**< variable, which potential should be returned */
    234 SCIP_Real coefficient, /**< variables coefficient in corresponding row */
    235 int sgn /**< sign of the slack */
    236 )
    237{
    238 SCIP_Real potential;
    239
    240 assert(NULL != scip);
    241 assert(NULL != var);
    242
    243 if( 0 > sgn * coefficient )
    244 {
    246 {
    247 potential = SCIPinfinity(scip);
    248 }
    249 else
    250 {
    251 potential = coefficient * (SCIPgetSolVal(scip, sol, var) - SCIPvarGetLbGlobal(var));
    252 }
    253 }
    254 else
    255 {
    257 {
    258 potential = -SCIPinfinity(scip);
    259 }
    260 else
    261 {
    262 potential = coefficient * (SCIPgetSolVal(scip, sol, var) - SCIPvarGetUbGlobal(var));
    263 }
    264 }
    265
    266 if( SCIPisZero(scip, potential) )
    267 {
    268 potential = 0.0;
    269 }
    270 return potential;
    271}
    272
    273/** finds out if a variable can be fixed with respect to the potentials of all rows, if it is possible, the potentials
    274 * of rows are adapted and TRUE is returned.
    275 */
    276static
    278 SCIP* scip, /**< SCIP data structure */
    279 SCIP* subscip, /**< sub-SCIP data structure */
    280 SCIP_SOL* sol, /**< solution data structure */
    281 SCIP_Real* potential, /**< array with all potential values */
    282 SCIP_Real* slack, /**< array with all slack values */
    283 SCIP_VAR* var, /**< variable to be fixed? */
    284 SCIP_VAR* subvar, /**< representative variable for var in the sub-SCIP */
    285 int* inftycounter, /**< counters how many variables have an infinity potential in a row */
    286 SCIP_HEURDATA* heurdata, /**< repairs heuristic data */
    287 SCIP_Bool* fixed /**< pointer to store whether the fixing was performed (variable was unfixed) */
    288 )
    289{
    290 SCIP_ROW** rows;
    291 SCIP_COL* col;
    292 SCIP_Real* vals;
    293 SCIP_Real alpha;
    294 SCIP_Real solval;
    295 SCIP_Bool infeasible;
    296 int nrows;
    297 int i;
    298 int sgn;
    299 int rowindex;
    300
    301 assert(NULL != scip);
    302 assert(NULL != potential);
    303 assert(NULL != slack);
    304 assert(NULL != var);
    305 assert(NULL != inftycounter);
    306 assert(NULL != heurdata);
    307
    308 alpha = heurdata->alpha;
    309 infeasible = TRUE;
    310 *fixed = FALSE;
    311
    312 solval = SCIPgetSolVal(scip, sol, var);
    313
    314 if( SCIPisFeasLT(scip, solval, SCIPvarGetLbGlobal(var)) )
    315 {
    316 return SCIP_OKAY;
    317 }
    318 if( SCIPisFeasGT(scip, solval, SCIPvarGetUbGlobal(var)) )
    319 {
    320 return SCIP_OKAY;
    321 }
    322
    323 col = SCIPvarGetCol(var);
    324 rows = SCIPcolGetRows(col);
    325 nrows = SCIPcolGetNLPNonz(col);
    326 vals = SCIPcolGetVals(col);
    327
    328 if( NULL == rows )
    329 {
    330 SCIP_CALL( SCIPfixVar(subscip, subvar, solval,
    331 &infeasible, fixed) );
    332 assert(!infeasible && *fixed);
    333 heurdata->nvarfixed++;
    334 SCIPdebugMsg(scip,"Variable %s is fixed to %g\n",SCIPvarGetName(var), solval);
    335 return SCIP_OKAY;
    336 }
    337 assert(NULL != rows);
    338
    339 /* iterate over rows, where the variable coefficient is nonzero */
    340 for( i = 0; i < nrows; ++i )
    341 {
    342 SCIP_Real contribution;
    343 rowindex = SCIProwGetLPPos(rows[i]);
    344 assert(rowindex >= 0);
    345
    346 sgn = 1;
    347
    348 if( SCIPisFeasZero(scip, slack[rowindex]) )
    349 {
    350 continue;
    351 }
    352 else if( SCIPisFeasGT(scip, 0.0 , slack[rowindex]) )
    353 {
    354 sgn = -1;
    355 }
    356
    357 contribution = getPotentialContributed(scip, sol, var, vals[i], sgn);
    358
    359 if( !SCIPisInfinity(scip, REALABS(contribution)) )
    360 {
    361 potential[rowindex] -= contribution;
    362 }
    363 else
    364 {
    365 inftycounter[rowindex]--;
    366 }
    367
    368 assert(0 <= inftycounter[rowindex]);
    369 if( 0 == inftycounter[rowindex] && REALABS(potential[rowindex]) < alpha * REALABS(slack[rowindex]) )
    370 {
    371 /* revert the changes before */
    372 int j = i;
    373 for( ; j >= 0; --j )
    374 {
    375 sgn = 1;
    376 if( 0 == slack[rowindex] )
    377 {
    378 continue;
    379 }
    380 rowindex = SCIProwGetLPPos(rows[j]);
    381 if( 0 > slack[rowindex])
    382 {
    383 sgn = -1;
    384 }
    385 contribution = getPotentialContributed(scip, sol, var, vals[j], sgn);
    386 if( !SCIPisInfinity(scip, REALABS(contribution)) )
    387 {
    388 potential[rowindex] += contribution;
    389 }
    390 else
    391 {
    392 inftycounter[rowindex]++;
    393 }
    394 }
    395 return SCIP_OKAY;
    396 }
    397 }
    398
    399 SCIP_CALL( SCIPfixVar(subscip, subvar, solval, &infeasible, fixed) );
    400 assert(!infeasible && *fixed);
    401 heurdata->nvarfixed++;
    402 SCIPdebugMsg(scip,"Variable %s is fixed to %g\n",SCIPvarGetName(var),
    403 SCIPgetSolVal(scip, sol, var));
    404
    405 return SCIP_OKAY;
    406}
    407
    408/** checks if all integral variables in the given solution are integral. */
    409static
    411 SCIP* scip, /**< SCIP data structure */
    412 SCIP_SOL* sol, /**< solution pointer to the to be checked solution */
    413 SCIP_Bool roundit, /**< round fractional solution values of integer variables */
    414 SCIP_Bool* success /**< pointer to store if all integral variables are integral or could
    415 * be rounded
    416 */
    417 )
    418{
    419 SCIP_VAR** vars;
    420 int nvars;
    421 int nfracvars;
    422 int nbinvars;
    423 int nintvars;
    424 int i;
    425
    426 assert(NULL != success);
    427 assert(NULL != sol);
    428
    429 *success = TRUE;
    430
    431 /* get variable data */
    432 SCIP_CALL( SCIPgetVarsData(scip, &vars, &nvars, &nbinvars, &nintvars, NULL, NULL) );
    433
    434 /* check if the candidates are fractional and round them if necessary */
    435 nfracvars = nbinvars + nintvars;
    436 for( i = 0; i < nfracvars; ++i)
    437 {
    438 SCIP_Real value = SCIPgetSolVal(scip, sol, vars[i]);
    439
    440 if( SCIPisInfinity(scip, REALABS(value)) )
    441 {
    442 *success = FALSE;
    443 SCIPdebugMsg(scip, "Variable with infinite solution value");
    444
    445 return SCIP_OKAY;
    446 }
    447 if( !SCIPisFeasIntegral(scip, value) )
    448 {
    449 if( roundit )
    450 {
    451 SCIP_Real roundedvalue;
    452
    454 {
    455 roundedvalue = SCIPceil(scip, value - 1.0);
    456 }
    457 else
    458 {
    459 roundedvalue = SCIPfloor(scip, value + 1.0);
    460 }
    461
    462 SCIP_CALL( SCIPsetSolVal(scip, sol, vars[i], roundedvalue) );
    463 }
    464 else
    465 {
    466 *success = FALSE;
    467 SCIPdebugMsg(scip, "Repair: All variables are integral.\n");
    468 return SCIP_OKAY;
    469 }
    470 }
    471 }
    472
    473 /* ensure that no other variables have infinite LP solution values */
    474 for( ; i < nvars; ++i )
    475 {
    476 if( SCIPisInfinity(scip, REALABS(SCIPgetSolVal(scip, sol, vars[i]))) )
    477 {
    478 *success = FALSE;
    479 SCIPdebugMsg(scip, "Variable with infinite solution value");
    480
    481 return SCIP_OKAY;
    482 }
    483 }
    484
    485 SCIPdebugMsg(scip, "All variables rounded.\n");
    486 return SCIP_OKAY;
    487}
    488
    489/** creates a new solution for the original problem by copying the solution of the subproblem */
    490static
    492 SCIP* scip, /**< original SCIP data structure */
    493 SCIP* subscip, /**< SCIP structure of the subproblem */
    494 SCIP_VAR** subvars, /**< the variables of the subproblem */
    495 SCIP_HEUR* heur, /**< Repair heuristic structure */
    496 SCIP_SOL* subsol, /**< solution of the subproblem */
    497 SCIP_Bool* success /**< used to store whether new solution was found or not */
    498 )
    499{
    500 SCIP_SOL* newsol; /* solution to be created for the original problem */
    501
    502 assert(scip != NULL);
    503 assert(subscip != NULL);
    504 assert(subvars != NULL);
    505 assert(subsol != NULL);
    506
    507 SCIP_CALL( SCIPtranslateSubSol(scip, subscip, subsol, heur, subvars, &newsol) );
    508
    509 /* try to add new solution to SCIP and free it immediately */
    510 SCIP_CALL( SCIPtrySolFree(scip, &newsol, FALSE, FALSE, TRUE, TRUE, TRUE, success) );
    511
    512#ifdef SCIP_STATISTIC
    513 {
    514 SCIP_HEURDATA* heurdata;
    515 heurdata = SCIPheurGetData(heur);
    516
    517 if( *success )
    518 {
    519 heurdata->originalsolval = SCIPgetSolOrigObj(scip, newsol);
    520 }
    521 }
    522#endif
    523
    524 return SCIP_OKAY;
    525}
    526
    527/** tries to fix variables as an approach to repair a solution. */
    528static
    530 SCIP* scip, /**< SCIP data structure of the problem */
    531 SCIP_HEUR* heur, /**< pointer to this heuristic instance */
    532 SCIP_RESULT* result, /**< pointer to return the result status */
    533 SCIP_Longint nnodes /**< nodelimit for sub-SCIP */
    534 )
    535{
    536 SCIP* subscip = NULL;
    537 SCIP_VAR** vars = NULL;
    538 SCIP_VAR** subvars = NULL;
    539 SCIP_ROW** rows;
    540 SCIP_CONS** subcons = NULL;
    541 int* nviolatedrows = NULL;
    542 int* permutation = NULL;
    543 int* inftycounter = NULL;
    544 SCIP_SOL* sol;
    545 SCIP_SOL* subsol = NULL;
    546 SCIP_HEURDATA* heurdata;
    547 SCIP_Real* potential = NULL;
    548 SCIP_Real* slacks = NULL;
    549 SCIP_RETCODE retcode = SCIP_OKAY;
    550 SCIP_Real timelimit;
    551 SCIP_Real memorylimit;
    552 SCIP_Real factor;
    553 char probname[SCIP_MAXSTRLEN];
    554 int i;
    555 int nbinvars;
    556 int nintvars;
    557 int nvars;
    558 int nrows;
    559 int ndiscvars;
    560 int nfixeddiscvars;
    561 SCIP_Bool success;
    562 SCIP_Bool avoidmemout;
    563
    564 heurdata = SCIPheurGetData(heur);
    565 sol = heurdata->infsol;
    566
    567 /* initializes the sub-SCIP */
    568 SCIP_CALL( SCIPcreate(&subscip) );
    571
    572 /* even when solving exactly, sub-SCIP heuristics should be run in floating-point mode, since the exactsol constraint
    573 * handler is in place to perform a final repair step
    574 */
    576
    577 /* use inference branching */
    578 if( SCIPfindBranchrule(subscip, "inference") != NULL && !SCIPisParamFixed(subscip, "branching/inference/priority") )
    579 {
    580 SCIP_CALL( SCIPsetIntParam(subscip, "branching/inference/priority", INT_MAX/4) );
    581 }
    582
    583 /* get name of the original problem and add the string "_repairsub" */
    584 (void) SCIPsnprintf(probname, SCIP_MAXSTRLEN, "%s_repairsub", SCIPgetProbName(scip));
    585
    586 SCIP_CALL( SCIPcreateProb(subscip, probname, NULL, NULL, NULL, NULL, NULL, NULL, NULL) );
    587 assert(!SCIPisExact(subscip));
    588
    589 /* a trivial feasible solution can be constructed if violations are modeled with slack variables */
    590 if( heurdata->useslackvars )
    591 {
    592 SCIP_CALL( SCIPcreateSol(subscip, &subsol, heur) );
    593 }
    594
    595 /* gets all original variables */
    596 SCIP_CALL( SCIPgetVarsData(scip, &vars, &nvars, &nbinvars, &nintvars, NULL, NULL) );
    597 SCIP_CALL( SCIPallocBufferArray(scip, &subvars, nvars) );
    598 SCIP_CALL( SCIPallocBufferArray(scip, &nviolatedrows, nvars) );
    599 SCIP_CALL( SCIPallocBufferArray(scip, &permutation, nvars) );
    600
    601 SCIPdebugMsg(scip,"\n\n Calling objective factor calculation \n\n");
    602 if( heurdata->useobjfactor )
    603 {
    604 SCIP_CALL( getObjectiveFactor(scip, subscip, &factor, &success) );
    605 }
    606 else
    607 {
    608 factor = 0.0;
    609 }
    610
    611 /* adds all original variables */
    612 ndiscvars = 0;
    613 for( i = 0; i < nvars; ++i )
    614 {
    615 SCIP_CONS* cons;
    616 SCIP_Real lb;
    617 SCIP_Real ub;
    618 SCIP_Real lborig;
    619 SCIP_Real uborig;
    620 SCIP_Real varslack;
    621 SCIP_Real objval;
    622 SCIP_Real value;
    623 SCIP_VARTYPE vartype;
    624 SCIP_Bool varimplint;
    625 char varname[SCIP_MAXSTRLEN];
    626 char slackvarname[SCIP_MAXSTRLEN];
    627 char consvarname[SCIP_MAXSTRLEN];
    628
    629#ifdef SCIP_STATISTIC
    630 heurdata->norigvars++;
    631#endif
    632
    633 varslack = 0.0;
    634 lborig = SCIPvarGetLbGlobal(vars[i]);
    635 uborig = SCIPvarGetUbGlobal(vars[i]);
    636 value = SCIPgetSolVal(scip, sol, vars[i]);
    637 vartype = SCIPvarGetType(vars[i]);
    638 varimplint = SCIPvarIsImpliedIntegral(vars[i]);
    639
    640 nviolatedrows[i] = 0;
    641
    642 /* if the value of x is lower than the variables lower bound, sets the slack to a correcting value */
    643 if( heurdata->useslackvars && SCIPisFeasLT(scip, value, lborig) )
    644 {
    645 lb = value;
    646 varslack = lborig - value;
    647 }
    648 else
    649 {
    650 lb = lborig;
    651 }
    652
    653 /* if the value of x is bigger than the variables upper bound, sets the slack to a correcting value */
    654 if( heurdata->useslackvars && SCIPisFeasGT(scip, value, uborig) )
    655 {
    656 ub = value;
    657 varslack = uborig - value;
    658 }
    659 else
    660 {
    661 ub = uborig;
    662 }
    663
    664 if( heurdata->useobjfactor )
    665 {
    666 objval = SCIPvarGetObj(vars[i])*factor;
    667
    668 if( SCIPisZero(scip, objval) )
    669 {
    670 objval = 0.0;
    671 }
    672 }
    673 else
    674 {
    675 objval = SCIPvarGetObj(vars[i]);
    676 }
    677
    678 /* if a binary variable is out of bound, generalize it to an integer variable */
    679 if( !SCIPisFeasZero(scip, varslack) && vartype == SCIP_VARTYPE_BINARY && !varimplint )
    680 {
    681 vartype = SCIP_VARTYPE_INTEGER;
    682 }
    683
    684 (void) SCIPsnprintf(varname, SCIP_MAXSTRLEN, "sub_%s", SCIPvarGetName(vars[i]));
    685
    686 /* Adds the sub representing variable to the sub-SCIP. */
    687 SCIP_CALL( SCIPcreateVarBasic(subscip, &subvars[i], varname, lb, ub, objval, vartype) );
    688 SCIP_CALL( SCIPaddVar(subscip, subvars[i]) );
    689
    690 /* a trivial feasible solution can be constructed if violations are modeled with slack variables */
    691 if( heurdata->useslackvars )
    692 {
    693 SCIP_CALL( SCIPsetSolVal(subscip, subsol, subvars[i], value) );
    694 }
    695
    696 /* if necessary adds a constraint to represent the original bounds of x.*/
    697 if( !SCIPisFeasEQ(scip, varslack, 0.0) )
    698 {
    699 SCIP_VAR* newvar;
    700 (void) SCIPsnprintf(slackvarname, SCIP_MAXSTRLEN, "artificialslack_%s", SCIPvarGetName(vars[i]));
    701 (void) SCIPsnprintf(consvarname, SCIP_MAXSTRLEN, "boundcons_%s", SCIPvarGetName(vars[i]));
    702
    703 /* initialize and add an artificial slack variable */
    704 if( heurdata->useobjfactor )
    705 {
    706 SCIP_CALL( SCIPcreateVarBasic(subscip, &newvar, slackvarname, 0.0, 1.0, 1.0, SCIP_VARTYPE_CONTINUOUS) );
    707 }
    708 else
    709 {
    710 SCIP_CALL( SCIPcreateVarBasic(subscip, &newvar, slackvarname, 0.0, 1.0, 1.0, SCIP_VARTYPE_BINARY) );
    711 }
    712 SCIP_CALL( SCIPaddVar(subscip, newvar) );
    713
    714 /* set the value of the slack variable to 1 to punish the use of it.
    715 * note that a trivial feasible solution can be only constructed if violations are modeled with slack variables
    716 */
    717 if( heurdata->useslackvars )
    718 {
    719 SCIP_CALL( SCIPsetSolVal(subscip, subsol, newvar, 1.0) );
    720 }
    721
    722 /* adds a linear constraint to represent the old bounds */
    723 SCIP_CALL( SCIPcreateConsBasicVarbound(subscip, &cons, consvarname, subvars[i], newvar, varslack, lb, ub) );
    724 SCIP_CALL( SCIPaddCons(subscip, cons) );
    725 SCIP_CALL( SCIPreleaseVar(subscip, &newvar) );
    726 SCIP_CALL( SCIPreleaseCons(subscip, &cons) );
    727
    728 /* increases the counter for violated vars */
    729#ifdef SCIP_STATISTIC
    730 heurdata->nviolatedvars++;
    731#endif
    732 }
    733
    734#ifdef SCIP_STATISTIC
    735 if( SCIPisFeasLT(scip, value, lb) || SCIPisFeasGT(scip, value, ub) )
    736 {
    737 heurdata->nviolatedvars++;
    738 }
    739#endif
    740 if( vartype != SCIP_VARTYPE_CONTINUOUS && !varimplint )
    741 {
    742 ndiscvars++;
    743 }
    744 }
    745
    746 /* check solution for feasibility regarding the LP rows (SCIPgetRowSolActivity()) */
    747 rows = SCIPgetLPRows(scip);
    748 nrows = SCIPgetNLPRows(scip);
    749
    750 SCIP_CALL( SCIPallocBufferArray(scip, &potential, nrows) );
    751 SCIP_CALL( SCIPallocBufferArray(scip, &slacks, nrows) );
    752 SCIP_CALL( SCIPallocBufferArray(scip, &subcons, nrows) );
    753 SCIP_CALL( SCIPallocBufferArray(scip, &inftycounter, nrows) );
    754
    755 /* Adds all original constraints and computes potentials and slacks */
    756 for (i = 0; i < nrows; ++i)
    757 {
    758 SCIP_COL** cols;
    759 SCIP_VAR** consvars;
    760 SCIP_Real* vals;
    761 SCIP_Real constant;
    762 SCIP_Real lhs;
    763 SCIP_Real rhs;
    764 SCIP_Real rowsolact;
    765 int nnonz;
    766 int j;
    767
    768#ifdef SCIP_STATISTIC
    769 heurdata->norcons++;
    770#endif
    771
    772 /* gets the values to check the constraint */
    773 constant = SCIProwGetConstant(rows[i]);
    774 lhs = SCIPisInfinity(scip, -SCIProwGetLhs(rows[i])) ? SCIProwGetLhs(rows[i]) : SCIProwGetLhs(rows[i]) - constant;
    775 rhs = SCIPisInfinity(scip, SCIProwGetRhs(rows[i])) ? SCIProwGetRhs(rows[i]) : SCIProwGetRhs(rows[i]) - constant;
    776 rowsolact = SCIPgetRowSolActivity(scip, rows[i], sol) - constant;
    777 vals = SCIProwGetVals(rows[i]);
    778 potential[i] = 0.0;
    779 inftycounter[i] = 0;
    780
    781 assert(SCIPisFeasLE(scip, lhs, rhs));
    782
    783 nnonz = SCIProwGetNNonz(rows[i]);
    784 cols = SCIProwGetCols(rows[i]);
    785 SCIP_CALL( SCIPallocBufferArray(subscip, &consvars, nnonz) );
    786
    787 /* sets the slack if its necessary */
    788 if( SCIPisFeasLT(scip, rowsolact, lhs) )
    789 {
    790 slacks[i] = lhs - rowsolact;
    791#ifdef SCIP_STATISTIC
    792 heurdata->nviolatedcons++;
    793#endif
    794 }
    795 else if( SCIPisFeasGT(scip, rowsolact, rhs) )
    796 {
    797 slacks[i] = rhs - rowsolact;
    798#ifdef SCIP_STATISTIC
    799 heurdata->nviolatedcons++;
    800#endif
    801 }
    802 else
    803 {
    804 slacks[i] = 0.0;
    805 }
    806
    807 /* translate all variables from the original SCIP to the sub-SCIP with sub-SCIP variables. */
    808 for( j = 0; j < nnonz; ++j )
    809 {
    810 SCIP_Real contribution;
    811 int pos;
    812 int sgn = 1;
    813
    814 /* negative slack represents a right hand side violation */
    815 if( SCIPisFeasGT(scip, 0.0, slacks[i]) )
    816 {
    817 assert(!SCIPisInfinity(scip, rhs));
    818 sgn = -1;
    819 }
    820 #ifndef NDEBUG
    821 else
    822 assert(!SCIPisInfinity(scip, lhs));
    823 #endif
    824
    825 pos = SCIPvarGetProbindex(SCIPcolGetVar(cols[j]));
    826 consvars[j] = subvars[pos];
    827 assert(pos >= 0);
    828
    829 /* compute potentials */
    830 contribution = getPotentialContributed(scip, sol, vars[pos], vals[j], sgn);
    831 if( !SCIPisInfinity(scip, REALABS(contribution)) )
    832 {
    833 potential[i] += contribution;
    834 }
    835 else
    836 {
    837 inftycounter[i]++;
    838 }
    839
    840 if( !SCIPisZero(scip, slacks[i]) )
    841 {
    842 nviolatedrows[pos]++;
    843 }
    844 }
    845
    846 /* create a new linear constraint, representing the old one */
    847 SCIP_CALL( SCIPcreateConsBasicLinear(subscip, &subcons[i], SCIProwGetName(rows[i]),
    848 nnonz, consvars, vals, lhs, rhs) );
    849
    850 if( heurdata->useslackvars )
    851 {
    852 SCIP_VAR* newvar;
    853 char varname[SCIP_MAXSTRLEN];
    854
    855 /*if necessary adds a new artificial slack variable*/
    856 if( !SCIPisFeasEQ(subscip, slacks[i], 0.0) )
    857 {
    858 (void) SCIPsnprintf(varname, SCIP_MAXSTRLEN, "artificialslack_%s", SCIProwGetName(rows[i]));
    859 SCIP_CALL( SCIPcreateVarBasic(subscip, &newvar, varname, 0.0, 1.0, 1.0, SCIP_VARTYPE_CONTINUOUS) );
    860 SCIP_CALL( SCIPaddVar(subscip, newvar) );
    861
    862 /* a trivial feasible solution can be constructed if violations are modeled with slack variables */
    863 SCIP_CALL( SCIPsetSolVal(subscip, subsol, newvar, 1.0) );
    864 SCIP_CALL( SCIPaddCoefLinear(subscip, subcons[i], newvar, slacks[i]) );
    865 SCIP_CALL( SCIPreleaseVar(subscip, &newvar) );
    866 }
    867 }
    868
    869 /*Adds the Constraint and release it.*/
    870 SCIP_CALL( SCIPaddCons(subscip, subcons[i]) );
    871 SCIP_CALL( SCIPreleaseCons(subscip, &subcons[i]) );
    872 SCIPfreeBufferArray(subscip, &consvars);
    873 }
    874
    875 if( heurdata->usevarfix )
    876 {
    877 /* get the greedy order */
    878 for( i = 0; i < nvars; ++i )
    879 {
    880 permutation[i] = i;
    881 }
    882 SCIPsortIntInt(nviolatedrows, permutation, nvars);
    883
    884 /* loops over variables and greedily fix variables, but preserve the cover property that enough slack is given to
    885 * violated rows
    886 */
    887 nfixeddiscvars = 0;
    888 heurdata->nvarfixed = 0;
    889 for( i = 0; i < nvars; ++i )
    890 {
    891 SCIP_Bool fixed;
    892
    893 /* continue if we have a loose variable */
    894 if( SCIPvarGetStatus(vars[permutation[i]]) != SCIP_VARSTATUS_COLUMN )
    895 continue;
    896
    897 SCIP_CALL( tryFixVar(scip, subscip, sol, potential, slacks, vars[permutation[i]], subvars[permutation[i]], inftycounter, heurdata, &fixed) );
    898
    899 if( fixed && SCIPvarIsNonimpliedIntegral(subvars[permutation[i]]) )
    900 {
    901 nfixeddiscvars++;
    902 }
    903 }
    904 SCIPdebugMsg(scip,"fixings finished\n\n");
    905 if( heurdata->minfixingrate > ((SCIP_Real)nfixeddiscvars/MAX((SCIP_Real)ndiscvars,1.0)) )
    906 {
    907 goto TERMINATE;
    908 }
    909 }
    910
    911 /* a trivial feasible solution can be constructed if violations are modeled with slack variables */
    912 if( heurdata->useslackvars )
    913 {
    914 SCIP_CALL( SCIPaddSolFree(subscip, &subsol, &success) );
    915
    916 if( !success )
    917 {
    918 SCIPdebugMsg(scip, "Initial repair solution was not accepted.\n");
    919 }
    920
    921#ifdef SCIP_STATISTIC
    922 heurdata->improvedoldsol = SCIPgetSolOrigObj(subscip, subsol);
    923#endif
    924 }
    925
    926 /* check whether there is enough time and memory left */
    927 SCIP_CALL( SCIPgetRealParam(scip, "limits/time", &timelimit) );
    928 if( !SCIPisInfinity(scip, timelimit) )
    929 timelimit -= SCIPgetSolvingTime(scip);
    930 SCIP_CALL( SCIPgetRealParam(scip, "limits/memory", &memorylimit) );
    931 SCIP_CALL( SCIPgetBoolParam(scip, "misc/avoidmemout", &avoidmemout) );
    932
    933 /* subtract the memory already used by the main SCIP and the estimated memory usage of external software */
    934 if( !SCIPisInfinity(scip, memorylimit) )
    935 {
    936 memorylimit -= SCIPgetMemUsed(scip) / 1048576.0;
    937 memorylimit -= SCIPgetMemExternEstim(scip) / 1048576.0;
    938 }
    939
    940 /* abort if no time is left or not enough memory (we don't abort in this case if misc_avoidmemout == FALSE)
    941 * to create a copy of SCIP, including external memory usage */
    942 if( timelimit <= 0.0 || (avoidmemout && memorylimit <= 2.0 * SCIPgetMemExternEstim(scip) / 1048576.0) )
    943 goto TERMINATE;
    944
    945 /* set limits for the subproblem */
    946 SCIP_CALL( SCIPsetLongintParam(subscip, "limits/nodes", nnodes) );
    947 SCIP_CALL( SCIPsetRealParam(subscip, "limits/time", timelimit) );
    948 SCIP_CALL( SCIPsetRealParam(subscip, "limits/memory", memorylimit) );
    949 SCIP_CALL( SCIPsetObjlimit(subscip, 1.0) );
    950
    951 /* disable bound limits */
    952 SCIP_CALL( SCIPsetRealParam(subscip, "limits/primal", SCIP_INVALID) );
    953 SCIP_CALL( SCIPsetRealParam(subscip, "limits/dual", SCIP_INVALID) );
    954
    955 /* forbid recursive call of heuristics and separators solving sub-SCIPs */
    956 SCIP_CALL( SCIPsetSubscipsOff(subscip, TRUE) );
    957
    958 /* disable output to console */
    959 SCIP_CALL( SCIPsetIntParam(subscip, "display/verblevel", (int)SCIP_VERBLEVEL_NONE) );
    960
    961#ifdef SCIP_DEBUG
    962 /* for debugging Repair, enable MIP output */
    963 SCIP_CALL( SCIPsetIntParam(subscip, "display/verblevel", (int)SCIP_VERBLEVEL_FULL) );
    964 SCIP_CALL( SCIPsetIntParam(subscip, "display/freq", -1) );
    965#endif
    966
    967 /* solve the subproblem */
    968 retcode = SCIPsolve(subscip);
    969
    970 /* errors in sub-SCIPs should not kill the overall solving process. Hence, we print a warning message. Only
    971 * in debug mode, SCIP will stop
    972 */
    973 if( retcode != SCIP_OKAY )
    974 {
    975 SCIPwarningMessage(scip, "Error while solving subproblem in REPAIR heuristic; sub-SCIP terminated with code <%d>\n", retcode);
    976 SCIPABORT(); /*lint --e{527}*/
    977 goto TERMINATE;
    978 }
    979
    980 success = FALSE;
    981
    982 /* if a solution is found, save its value and create a new solution instance for the original SCIP */
    983 if( SCIPgetBestSol(subscip) != NULL )
    984 {
    985#ifdef SCIP_STATISTIC
    986 heurdata->improvedoldsol = SCIPgetSolOrigObj(subscip, SCIPgetBestSol(subscip));
    987#endif
    988 /* print solving statistics of subproblem if we are in SCIP's debug mode */
    990
    991 assert(SCIPgetNSols(subscip) > 0);
    992 SCIP_CALL( createNewSol(scip, subscip, subvars, heur, SCIPgetBestSol(subscip), &success) );
    993
    994 if( success )
    995 {
    996 *result = SCIP_FOUNDSOL;
    997 }
    998 }
    999 else
    1000 {
    1001 SCIPdebugMsg(scip,"No solution found!\n");
    1002 }
    1003
    1004 if( SCIPgetStage(subscip) >= SCIP_STAGE_SOLVED )
    1005 {
    1006 heurdata->subiters = SCIPgetNLPIterations(subscip);
    1007 heurdata->subnodes = SCIPgetNTotalNodes(subscip);
    1008#ifdef SCIP_STATISTIC
    1009 heurdata->subpresoltime = SCIPgetPresolvingTime(subscip);
    1010#endif
    1011 heurdata->runs = SCIPgetNRuns(subscip);
    1012 }
    1013
    1014 /* terminates the solving process */
    1015TERMINATE:
    1016 if( NULL != sol )
    1017 {
    1018 SCIP_CALL( SCIPfreeSol(scip, &sol) );
    1019 }
    1020 SCIPfreeBufferArrayNull(scip, &nviolatedrows);
    1021 for( i = 0; i < nvars; ++i )
    1022 {
    1023 SCIP_CALL( SCIPreleaseVar(subscip, &subvars[i]) );
    1024 }
    1025 SCIPfreeBufferArrayNull(scip, &inftycounter);
    1026 SCIPfreeBufferArrayNull(scip, &subcons);
    1027 SCIPfreeBufferArrayNull(scip, &slacks);
    1028 SCIPfreeBufferArrayNull(scip, &potential);
    1029 SCIPfreeBufferArrayNull(scip, &permutation);
    1030 SCIPfreeBufferArrayNull(scip, &subvars);
    1031
    1032 if( NULL != subsol )
    1033 {
    1034 SCIP_CALL( SCIPfreeSol(subscip, &subsol) );
    1035 }
    1036
    1037 SCIP_CALL( SCIPfree(&subscip) );
    1038
    1039 SCIPdebugMsg(scip, "repair finished\n");
    1040 return SCIP_OKAY;
    1041}
    1042
    1043/*
    1044 * Callback methods of primal heuristic
    1045 */
    1046
    1047/** copy method for primal heuristic plugins (called when SCIP copies plugins) */
    1048static
    1049SCIP_DECL_HEURCOPY(heurCopyRepair)
    1050{ /*lint --e{715}*/
    1051 assert(scip != NULL);
    1052 assert(heur != NULL);
    1053 assert(strcmp(SCIPheurGetName(heur), HEUR_NAME) == 0);
    1054
    1055 /* call inclusion method of primal heuristic */
    1057
    1058 return SCIP_OKAY;
    1059}
    1060
    1061/** destructor of primal heuristic to free user data (called when SCIP is exiting) */
    1062static
    1063SCIP_DECL_HEURFREE(heurFreeRepair)
    1064{ /*lint --e{715}*/
    1065 SCIP_HEURDATA* heurdata;
    1066
    1067 heurdata = SCIPheurGetData(heur);
    1068
    1069 assert(heurdata != NULL);
    1070 SCIPfreeMemory(scip, &heurdata);
    1071
    1072 SCIPheurSetData(heur, NULL);
    1073
    1074 return SCIP_OKAY;
    1075}
    1076
    1077
    1078/** initialization method of primal heuristic (called after problem was transformed) */
    1079static
    1080SCIP_DECL_HEURINIT(heurInitRepair)
    1081{ /*lint --e{715}*/
    1082 SCIP_HEURDATA* heurdata;
    1083
    1084 heurdata = SCIPheurGetData(heur);
    1085
    1086 heurdata->subiters = -1;
    1087 heurdata->subnodes = -1;
    1088 heurdata->runs = 0;
    1089
    1090 heurdata->nvarfixed = 0;
    1091 heurdata->relvarfixed = -1;
    1092
    1093#ifdef SCIP_STATISTIC
    1094 heurdata->subpresoltime = 0;
    1095
    1096 heurdata->nviolatedvars = 0;
    1097 heurdata->norigvars = 0;
    1098 heurdata->relviolatedvars = 0;
    1099 heurdata->nviolatedcons = 0;
    1100 heurdata->norcons = 0;
    1101 heurdata->relviolatedcons = 0;
    1102
    1103 heurdata->originalsolval = SCIP_INVALID;
    1104
    1105 heurdata->improvedoldsol = SCIP_UNKNOWN;
    1106#endif
    1107
    1108 heurdata->usednodes = 0;
    1109
    1110 return SCIP_OKAY;
    1111}
    1112
    1113
    1114/** deinitialization method of primal heuristic (called before transformed problem is freed) */
    1115static
    1116SCIP_DECL_HEUREXIT(heurExitRepair)
    1117{ /*lint --e{715}*/
    1118#ifdef SCIP_STATISTIC
    1119 SCIP_HEURDATA* heurdata;
    1120 SCIP_Real time;
    1121 SCIP_Real relvars;
    1122 SCIP_Real relcons;
    1123 SCIP_Real relfixed;
    1124 char solval[SCIP_MAXSTRLEN];
    1125 int violateds;
    1126 int ninvars;
    1127 int ninvcons;
    1128 int nvars;
    1129 int ncons;
    1130 int iterations;
    1131 int nodes;
    1132 int runs;
    1133
    1134 heurdata = SCIPheurGetData(heur);
    1135 violateds = heurdata->nviolatedvars+heurdata->nviolatedcons;
    1136 ninvars = heurdata->nviolatedvars;
    1137 ninvcons = heurdata->nviolatedcons;
    1138 nvars = heurdata->norigvars;
    1139 ncons = heurdata->norcons;
    1140 iterations = heurdata->subiters;
    1141 nodes = heurdata->subnodes;
    1142 time = heurdata->subpresoltime;
    1143 runs = heurdata->runs;
    1144
    1145 if( SCIP_INVALID == heurdata->originalsolval )
    1146 {
    1147 (void) SCIPsnprintf(solval, SCIP_MAXSTRLEN ,"--");
    1148 }
    1149 else
    1150 {
    1151 (void) SCIPsnprintf(solval, SCIP_MAXSTRLEN, "%15.9g", heurdata->originalsolval);
    1152 }
    1153
    1154 heurdata->relviolatedvars = MAX((SCIP_Real)heurdata->norigvars, 1.0);
    1155 heurdata->relviolatedvars = heurdata->nviolatedvars/heurdata->relviolatedvars;
    1156 heurdata->relviolatedcons = MAX((SCIP_Real)heurdata->norcons, 1.0);
    1157 heurdata->relviolatedcons = heurdata->nviolatedcons/heurdata->relviolatedcons;
    1158
    1159 heurdata->relvarfixed = MAX((SCIP_Real)heurdata->norigvars, 1.0);
    1160 heurdata->relvarfixed = heurdata->nvarfixed/heurdata->relvarfixed;
    1161 relvars = heurdata->relviolatedvars;
    1162 relcons = heurdata->relviolatedcons;
    1163 relfixed = heurdata->relvarfixed;
    1164
    1165 /* prints all statistic data for a user*/
    1167 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, "<repair> \n total violations : %10d\n", violateds);
    1168 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " violated variables : %10d\n", ninvars);
    1169 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " total variables : %10d\n", nvars);
    1170 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " relative violated variables : %10.2f%%\n", 100 * relvars);
    1171 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " violated constraints : %10d\n", ninvcons);
    1172 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " total constraints : %10d\n", ncons);
    1173 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " relative violated constraints: %10.2f%%\n", 100* relcons);
    1174 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " fixed variables : %10d\n", heurdata->nvarfixed);
    1175 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " relative fixed variables : %10.2f%%\n\n", 100* relfixed);
    1176 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " iterations : %10d\n", iterations);
    1177 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " nodes : %10d\n", nodes);
    1178 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " number of runs : %10d\n", runs);
    1179 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " presolve time : %10.2f\n", time);
    1180 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, "</repair>\n\n");
    1181 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " value of best solution : %10g\n", solval);
    1182 SCIPverbMessage(scip, SCIP_VERBLEVEL_HIGH, NULL, " improved orig. solval : %10g\n", heurdata->improvedoldsol);
    1183 )
    1184
    1185#endif
    1186 return SCIP_OKAY;
    1187}
    1188
    1189/** execution method of primal heuristic. Repair needs an incorrect solution, in which all variables are in their bound. */
    1190static
    1191SCIP_DECL_HEUREXEC(heurExecRepair)
    1192{ /*lint --e{715}*/
    1193 SCIP_HEURDATA* heurdata;
    1194 SCIP_RETCODE retcode;
    1195 SCIP_Bool success;
    1196 SCIP_Bool error;
    1198
    1199 heurdata = SCIPheurGetData(heur);
    1200 SCIPdebugMsg(scip, "%s\n", heurdata->filename);
    1201
    1202 /* checks the result pointer */
    1203 assert(result != NULL);
    1204 *result = SCIP_DIDNOTRUN;
    1205
    1206 /* if repair already ran or neither variable fixing nor slack variables are enabled, stop */
    1207 if( 0 < SCIPheurGetNCalls(heur) || !(heurdata->usevarfix || heurdata->useslackvars) )
    1208 return SCIP_OKAY;
    1209
    1210 /* do not run if the neither the LP is constructed nor a user given solution exists */
    1211 if( SCIPgetLPSolstat(scip) != SCIP_LPSOLSTAT_OPTIMAL && strcmp(heurdata->filename, DEFAULT_FILENAME) == 0 )
    1212 return SCIP_OKAY;
    1213
    1214 /* calculate the maximal number of branching nodes until heuristic is aborted */
    1215 nnodes = (SCIP_Longint)(heurdata->nodesquot * SCIPgetNNodes(scip));
    1216
    1217 /* reward REPAIR if it succeeded often */
    1218 nnodes = (SCIP_Longint)(nnodes * 3.0 * (SCIPheurGetNBestSolsFound(heur)+1.0)/(SCIPheurGetNCalls(heur) + 1.0));
    1219 nnodes -= (SCIP_Longint)(100.0 * SCIPheurGetNCalls(heur)); /* count the setup costs for the sub-MIP as 100 nodes */
    1220 nnodes += heurdata->nodesofs;
    1221
    1222 /* determine the node limit for the current process */
    1223 nnodes -= heurdata->usednodes;
    1224 nnodes = MIN(nnodes, heurdata->maxnodes);
    1225
    1226 /* check whether we have enough nodes left to call subproblem solving */
    1227 if( nnodes < heurdata->minnodes )
    1228 return SCIP_OKAY;
    1229
    1231 return SCIP_OKAY;
    1232
    1234 {
    1235 SCIP_Bool cutoff;
    1236
    1237 SCIP_CALL( SCIPconstructLP(scip, &cutoff) );
    1238
    1239 /* manually cut off the node if the LP construction detected infeasibility (heuristics cannot return such a
    1240 * result); the cutoff result is safe to use in exact solving mode, but we don't have enough information to
    1241 * give a certificate for the cutoff
    1242 */
    1243 if( cutoff && !SCIPisCertified(scip) )
    1244 {
    1246 return SCIP_OKAY;
    1247 }
    1248 }
    1249
    1250 /* create original solution */
    1251 SCIP_CALL( SCIPcreateOrigSol(scip, &(heurdata->infsol), heur) );
    1252
    1253 /* use read method to enter solution from a file */
    1254 if( strcmp(heurdata->filename, DEFAULT_FILENAME) == 0 )
    1255 {
    1256 retcode = SCIPlinkLPSol(scip, heurdata->infsol);
    1257 }
    1258 else
    1259 {
    1260 error = FALSE;
    1261 retcode = SCIPreadSolFile(scip, heurdata->filename, heurdata->infsol, FALSE, NULL, &error);
    1262 }
    1263
    1264 if( SCIP_NOFILE == retcode )
    1265 {
    1266 assert(strcmp(heurdata->filename, DEFAULT_FILENAME) != 0);
    1267 SCIPwarningMessage(scip, "cannot open file <%s> for reading\n", heurdata->filename);
    1268
    1269 SCIP_CALL( SCIPfreeSol(scip, &(heurdata->infsol)) );
    1270 return SCIP_OKAY;
    1271 }
    1272 else if( retcode != SCIP_OKAY )
    1273 {
    1274 SCIPwarningMessage(scip, "cannot run repair, unknown return status <%d>\n", retcode);
    1275 SCIP_CALL( SCIPfreeSol(scip, &(heurdata->infsol)) );
    1276 return SCIP_OKAY;
    1277 }
    1278 SCIPdebugMsg(scip, "Repair: Solution file read.\n");
    1279
    1280 /* checks the integrality of all discrete variable */
    1281 SCIP_CALL( checkCands(scip, heurdata->infsol, heurdata->roundit, &success) );
    1282 if( !success )
    1283 {
    1284 SCIPdebugMsg(scip,"Given solution is not integral, repair terminates.\n");
    1285 SCIP_CALL( SCIPfreeSol(scip, &(heurdata->infsol)) );
    1286 return SCIP_OKAY;
    1287 }
    1288
    1289 *result = SCIP_DIDNOTFIND;
    1290
    1291 SCIP_CALL( SCIPtrySol(scip, heurdata->infsol, FALSE, FALSE, TRUE, TRUE, TRUE, &success) );
    1292
    1293 /* the solution is not feasible for the original problem; we will try to repair it */
    1294 if( !success )
    1295 {
    1296 assert(NULL != heurdata->infsol);
    1297 assert(heurdata->usevarfix || heurdata->useslackvars);
    1298 SCIP_CALL( applyRepair(scip, heur, result, nnodes) );
    1299 }
    1300 else
    1301 {
    1302 SCIP_CALL( SCIPfreeSol(scip, &(heurdata->infsol)) );
    1303 }
    1304
    1305 return SCIP_OKAY;
    1306}
    1307
    1308/* primal heuristic specific interface methods */
    1309
    1310/** creates the repair primal heuristic and includes it in SCIP */
    1312 SCIP* scip /**< SCIP data structure */
    1313 )
    1314{
    1315 SCIP_HEURDATA* heurdata;
    1316 SCIP_HEUR* heur;
    1317
    1318 /* create repair primal heuristic data */
    1319 heurdata = NULL;
    1320
    1321 SCIP_CALL( SCIPallocMemory(scip ,&heurdata) );
    1322
    1323 heur = NULL;
    1324
    1325 /* include primal heuristic */
    1328 HEUR_MAXDEPTH, HEUR_TIMING, HEUR_USESSUBSCIP, heurExecRepair, heurdata) );
    1329
    1330 assert(heur != NULL);
    1331 assert(heurdata != NULL);
    1332
    1333 /* primal heuristic is safe to use in exact solving mode */
    1334 SCIPheurMarkExact(heur);
    1335
    1336 /* set non fundamental callbacks via setter functions */
    1337 SCIP_CALL( SCIPsetHeurCopy(scip, heur, heurCopyRepair) );
    1338 SCIP_CALL( SCIPsetHeurFree(scip, heur, heurFreeRepair) );
    1339 SCIP_CALL( SCIPsetHeurInit(scip, heur, heurInitRepair) );
    1340 SCIP_CALL( SCIPsetHeurExit(scip, heur, heurExitRepair) );
    1341
    1342 /* add repair primal heuristic parameters */
    1343
    1344 heurdata->filename = NULL;
    1345 /* add string parameter for filename containing a solution */
    1346 SCIP_CALL( SCIPaddStringParam(scip, "heuristics/" HEUR_NAME "/filename",
    1347 "file name of a solution to be used as infeasible starting point, [-] if not available",
    1348 &heurdata->filename, FALSE, DEFAULT_FILENAME, NULL, NULL) );
    1349
    1350 /* add bool parameter for decision how to deal with unfractional cands */
    1351 SCIP_CALL( SCIPaddBoolParam(scip, "heuristics/" HEUR_NAME "/roundit",
    1352 "True : fractional variables which are not fractional in the given solution are rounded, "
    1353 "FALSE : solving process of this heuristic is stopped. ",
    1354 &heurdata->roundit, FALSE, DEFAULT_ROUNDIT, NULL, NULL));
    1355
    1356 /* add bool parameter for decision how the objective function should be */
    1357 SCIP_CALL( SCIPaddBoolParam(scip, "heuristics/" HEUR_NAME "/useobjfactor",
    1358 "should a scaled objective function for original variables be used in repair subproblem?",
    1359 &heurdata->useobjfactor, FALSE, DEFAULT_USEOBJFACTOR, NULL, NULL));
    1360
    1361 /* add bool parameter for decision if variable fixings should be used */
    1362 SCIP_CALL( SCIPaddBoolParam(scip, "heuristics/" HEUR_NAME "/usevarfix",
    1363 "should variable fixings be used in repair subproblem?",
    1364 &heurdata->usevarfix, FALSE, DEFAULT_USEVARFIX, NULL, NULL));
    1365
    1366 /* add bool parameter for decision how the objective function should be */
    1367 SCIP_CALL( SCIPaddBoolParam(scip, "heuristics/" HEUR_NAME "/useslackvars",
    1368 "should slack variables be used in repair subproblem?",
    1369 &heurdata->useslackvars, FALSE, DEFAULT_USESLACKVARS, NULL, NULL));
    1370
    1371 SCIP_CALL( SCIPaddRealParam(scip, "heuristics/" HEUR_NAME "/alpha", "factor for the potential of var fixings",
    1372 &heurdata->alpha, TRUE, DEFAULT_ALPHA, 0.0, 100.00, NULL, NULL) );
    1373
    1374 SCIP_CALL( SCIPaddIntParam(scip, "heuristics/" HEUR_NAME "/nodesofs",
    1375 "number of nodes added to the contingent of the total nodes",
    1376 &heurdata->nodesofs, FALSE, DEFAULT_NODESOFS, 0, INT_MAX, NULL, NULL) );
    1377
    1378 SCIP_CALL( SCIPaddIntParam(scip, "heuristics/" HEUR_NAME "/maxnodes",
    1379 "maximum number of nodes to regard in the subproblem",
    1380 &heurdata->maxnodes, TRUE, DEFAULT_MAXNODES, 0, INT_MAX, NULL, NULL) );
    1381
    1382 SCIP_CALL( SCIPaddIntParam(scip, "heuristics/" HEUR_NAME "/minnodes",
    1383 "minimum number of nodes required to start the subproblem",
    1384 &heurdata->minnodes, TRUE, DEFAULT_MINNODES, 0, INT_MAX, NULL, NULL) );
    1385
    1386 SCIP_CALL( SCIPaddRealParam(scip, "heuristics/" HEUR_NAME "/nodesquot",
    1387 "contingent of sub problem nodes in relation to the number of nodes of the original problem",
    1388 &heurdata->nodesquot, FALSE, DEFAULT_NODESQUOT, 0.0, 1.0, NULL, NULL) );
    1389
    1390 SCIP_CALL( SCIPaddRealParam(scip, "heuristics/" HEUR_NAME "/minfixingrate",
    1391 "minimum percentage of integer variables that have to be fixed",
    1392 &heurdata->minfixingrate, FALSE, DEFAULT_MINFIXINGRATE, 0.0, 1.0, NULL, NULL) );
    1393
    1394 return SCIP_OKAY;
    1395}
    Constraint handler for linear constraints in their most general form, .
    Constraint handler for variable bound constraints .
    #define NULL
    Definition: def.h:248
    #define SCIP_MAXSTRLEN
    Definition: def.h:269
    #define SCIP_Longint
    Definition: def.h:141
    #define SCIP_INVALID
    Definition: def.h:178
    #define SCIP_Bool
    Definition: def.h:91
    #define MIN(x, y)
    Definition: def.h:224
    #define SCIP_Real
    Definition: def.h:156
    #define SCIP_UNKNOWN
    Definition: def.h:179
    #define TRUE
    Definition: def.h:93
    #define FALSE
    Definition: def.h:94
    #define MAX(x, y)
    Definition: def.h:220
    #define SCIPABORT()
    Definition: def.h:327
    #define REALABS(x)
    Definition: def.h:182
    #define SCIP_CALL(x)
    Definition: def.h:355
    #define nnodes
    Definition: gastrans.c:74
    SCIP_RETCODE SCIPaddCoefLinear(SCIP *scip, SCIP_CONS *cons, SCIP_VAR *var, SCIP_Real val)
    SCIP_RETCODE SCIPcreateConsBasicVarbound(SCIP *scip, SCIP_CONS **cons, const char *name, SCIP_VAR *var, SCIP_VAR *vbdvar, SCIP_Real vbdcoef, SCIP_Real lhs, SCIP_Real rhs)
    SCIP_RETCODE SCIPcreateConsBasicLinear(SCIP *scip, SCIP_CONS **cons, const char *name, int nvars, SCIP_VAR **vars, SCIP_Real *vals, SCIP_Real lhs, SCIP_Real rhs)
    SCIP_RETCODE SCIPtranslateSubSol(SCIP *scip, SCIP *subscip, SCIP_SOL *subsol, SCIP_HEUR *heur, SCIP_VAR **subvars, SCIP_SOL **newsol)
    Definition: scip_copy.c:1397
    SCIP_RETCODE SCIPcopyParamSettings(SCIP *sourcescip, SCIP *targetscip)
    Definition: scip_copy.c:2547
    SCIP_RETCODE SCIPfree(SCIP **scip)
    Definition: scip_general.c:402
    SCIP_RETCODE SCIPcreate(SCIP **scip)
    Definition: scip_general.c:370
    SCIP_STAGE SCIPgetStage(SCIP *scip)
    Definition: scip_general.c:444
    SCIP_RETCODE SCIPaddVar(SCIP *scip, SCIP_VAR *var)
    Definition: scip_prob.c:1907
    const char * SCIPgetProbName(SCIP *scip)
    Definition: scip_prob.c:1242
    SCIP_RETCODE SCIPsetObjlimit(SCIP *scip, SCIP_Real objlimit)
    Definition: scip_prob.c:1661
    SCIP_RETCODE SCIPgetVarsData(SCIP *scip, SCIP_VAR ***vars, int *nvars, int *nbinvars, int *nintvars, int *nimplvars, int *ncontvars)
    Definition: scip_prob.c:2115
    SCIP_RETCODE SCIPaddCons(SCIP *scip, SCIP_CONS *cons)
    Definition: scip_prob.c:3274
    SCIP_RETCODE SCIPaddOrigObjoffset(SCIP *scip, SCIP_Real addval)
    Definition: scip_prob.c:1486
    SCIP_RETCODE SCIPcreateProb(SCIP *scip, const char *name, SCIP_DECL_PROBDELORIG((*probdelorig)), SCIP_DECL_PROBTRANS((*probtrans)), SCIP_DECL_PROBDELTRANS((*probdeltrans)), SCIP_DECL_PROBINITSOL((*probinitsol)), SCIP_DECL_PROBEXITSOL((*probexitsol)), SCIP_DECL_PROBCOPY((*probcopy)), SCIP_PROBDATA *probdata)
    Definition: scip_prob.c:119
    void SCIPverbMessage(SCIP *scip, SCIP_VERBLEVEL msgverblevel, FILE *file, const char *formatstr,...)
    Definition: scip_message.c:225
    #define SCIPdebugMsg
    Definition: scip_message.h:78
    void SCIPwarningMessage(SCIP *scip, const char *formatstr,...)
    Definition: scip_message.c:120
    SCIP_RETCODE SCIPgetBoolParam(SCIP *scip, const char *name, SCIP_Bool *value)
    Definition: scip_param.c:250
    SCIP_Bool SCIPisParamFixed(SCIP *scip, const char *name)
    Definition: scip_param.c:219
    SCIP_RETCODE SCIPaddIntParam(SCIP *scip, const char *name, const char *desc, int *valueptr, SCIP_Bool isadvanced, int defaultvalue, int minvalue, int maxvalue, SCIP_DECL_PARAMCHGD((*paramchgd)), SCIP_PARAMDATA *paramdata)
    Definition: scip_param.c:83
    SCIP_RETCODE SCIPaddStringParam(SCIP *scip, const char *name, const char *desc, char **valueptr, SCIP_Bool isadvanced, const char *defaultvalue, SCIP_DECL_PARAMCHGD((*paramchgd)), SCIP_PARAMDATA *paramdata)
    Definition: scip_param.c:194
    SCIP_RETCODE SCIPsetLongintParam(SCIP *scip, const char *name, SCIP_Longint value)
    Definition: scip_param.c:545
    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)
    Definition: scip_param.c:139
    SCIP_RETCODE SCIPsetIntParam(SCIP *scip, const char *name, int value)
    Definition: scip_param.c:487
    SCIP_RETCODE SCIPsetSubscipsOff(SCIP *scip, SCIP_Bool quiet)
    Definition: scip_param.c:904
    SCIP_RETCODE SCIPgetRealParam(SCIP *scip, const char *name, SCIP_Real *value)
    Definition: scip_param.c:307
    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)
    Definition: scip_param.c:57
    SCIP_RETCODE SCIPsetRealParam(SCIP *scip, const char *name, SCIP_Real value)
    Definition: scip_param.c:603
    SCIP_RETCODE SCIPincludeHeurRepair(SCIP *scip)
    Definition: heur_repair.c:1311
    SCIP_BRANCHRULE * SCIPfindBranchrule(SCIP *scip, const char *name)
    Definition: scip_branch.c:304
    SCIP_Bool SCIPisCertified(SCIP *scip)
    SCIP_VAR * SCIPcolGetVar(SCIP_COL *col)
    Definition: lp.c:17425
    SCIP_Real * SCIPcolGetVals(SCIP_COL *col)
    Definition: lp.c:17555
    SCIP_ROW ** SCIPcolGetRows(SCIP_COL *col)
    Definition: lp.c:17545
    int SCIPcolGetNLPNonz(SCIP_COL *col)
    Definition: lp.c:17534
    SCIP_RETCODE SCIPreleaseCons(SCIP *scip, SCIP_CONS **cons)
    Definition: scip_cons.c:1173
    SCIP_Bool SCIPisExact(SCIP *scip)
    Definition: scip_exact.c:193
    SCIP_RETCODE SCIPenableExactSolving(SCIP *scip, SCIP_Bool enable)
    Definition: scip_exact.c:151
    SCIP_RETCODE SCIPsetHeurCopy(SCIP *scip, SCIP_HEUR *heur, SCIP_DECL_HEURCOPY((*heurcopy)))
    Definition: scip_heur.c:167
    SCIP_HEURDATA * SCIPheurGetData(SCIP_HEUR *heur)
    Definition: heur.c:1368
    SCIP_RETCODE SCIPincludeHeurBasic(SCIP *scip, SCIP_HEUR **heur, const char *name, const char *desc, char dispchar, int priority, int freq, int freqofs, int maxdepth, SCIP_HEURTIMING timingmask, SCIP_Bool usessubscip, SCIP_DECL_HEUREXEC((*heurexec)), SCIP_HEURDATA *heurdata)
    Definition: scip_heur.c:122
    SCIP_RETCODE SCIPsetHeurFree(SCIP *scip, SCIP_HEUR *heur, SCIP_DECL_HEURFREE((*heurfree)))
    Definition: scip_heur.c:183
    SCIP_RETCODE SCIPsetHeurExit(SCIP *scip, SCIP_HEUR *heur, SCIP_DECL_HEUREXIT((*heurexit)))
    Definition: scip_heur.c:215
    SCIP_Longint SCIPheurGetNBestSolsFound(SCIP_HEUR *heur)
    Definition: heur.c:1613
    SCIP_Longint SCIPheurGetNCalls(SCIP_HEUR *heur)
    Definition: heur.c:1593
    void SCIPheurMarkExact(SCIP_HEUR *heur)
    Definition: heur.c:1457
    SCIP_RETCODE SCIPsetHeurInit(SCIP *scip, SCIP_HEUR *heur, SCIP_DECL_HEURINIT((*heurinit)))
    Definition: scip_heur.c:199
    const char * SCIPheurGetName(SCIP_HEUR *heur)
    Definition: heur.c:1467
    void SCIPheurSetData(SCIP_HEUR *heur, SCIP_HEURDATA *heurdata)
    Definition: heur.c:1378
    SCIP_Bool SCIPhasCurrentNodeLP(SCIP *scip)
    Definition: scip_lp.c:87
    SCIP_RETCODE SCIPconstructLP(SCIP *scip, SCIP_Bool *cutoff)
    Definition: scip_lp.c:130
    SCIP_Bool SCIPisLPConstructed(SCIP *scip)
    Definition: scip_lp.c:105
    SCIP_ROW ** SCIPgetLPRows(SCIP *scip)
    Definition: scip_lp.c:611
    int SCIPgetNLPRows(SCIP *scip)
    Definition: scip_lp.c:632
    SCIP_LPSOLSTAT SCIPgetLPSolstat(SCIP *scip)
    Definition: scip_lp.c:174
    SCIP_Longint SCIPgetMemExternEstim(SCIP *scip)
    Definition: scip_mem.c:126
    SCIP_Longint SCIPgetMemUsed(SCIP *scip)
    Definition: scip_mem.c:100
    #define SCIPallocBufferArray(scip, ptr, num)
    Definition: scip_mem.h:124
    #define SCIPallocMemory(scip, ptr)
    Definition: scip_mem.h:60
    #define SCIPfreeBufferArray(scip, ptr)
    Definition: scip_mem.h:136
    #define SCIPfreeMemory(scip, ptr)
    Definition: scip_mem.h:78
    #define SCIPfreeBufferArrayNull(scip, ptr)
    Definition: scip_mem.h:137
    SCIP_Real SCIProwGetLhs(SCIP_ROW *row)
    Definition: lp.c:17686
    int SCIProwGetNNonz(SCIP_ROW *row)
    Definition: lp.c:17607
    SCIP_COL ** SCIProwGetCols(SCIP_ROW *row)
    Definition: lp.c:17632
    SCIP_Real SCIProwGetRhs(SCIP_ROW *row)
    Definition: lp.c:17696
    int SCIProwGetLPPos(SCIP_ROW *row)
    Definition: lp.c:17895
    const char * SCIProwGetName(SCIP_ROW *row)
    Definition: lp.c:17745
    SCIP_Real SCIProwGetConstant(SCIP_ROW *row)
    Definition: lp.c:17652
    SCIP_Real * SCIProwGetVals(SCIP_ROW *row)
    Definition: lp.c:17642
    SCIP_Real SCIPgetRowSolActivity(SCIP *scip, SCIP_ROW *row, SCIP_SOL *sol)
    Definition: scip_lp.c:2108
    SCIP_SOL * SCIPgetBestSol(SCIP *scip)
    Definition: scip_sol.c:2981
    SCIP_RETCODE SCIPcreateSol(SCIP *scip, SCIP_SOL **sol, SCIP_HEUR *heur)
    Definition: scip_sol.c:516
    SCIP_RETCODE SCIPreadSolFile(SCIP *scip, const char *filename, SCIP_SOL *sol, SCIP_Bool xml, SCIP_Bool *partial, SCIP_Bool *error)
    Definition: scip_sol.c:3802
    SCIP_RETCODE SCIPfreeSol(SCIP *scip, SCIP_SOL **sol)
    Definition: scip_sol.c:1252
    SCIP_RETCODE SCIPaddSolFree(SCIP *scip, SCIP_SOL **sol, SCIP_Bool *stored)
    Definition: scip_sol.c:3909
    int SCIPgetNSols(SCIP *scip)
    Definition: scip_sol.c:2882
    SCIP_RETCODE SCIPcreateOrigSol(SCIP *scip, SCIP_SOL **sol, SCIP_HEUR *heur)
    Definition: scip_sol.c:831
    SCIP_RETCODE SCIPtrySol(SCIP *scip, SCIP_SOL *sol, SCIP_Bool printreason, SCIP_Bool completely, SCIP_Bool checkbounds, SCIP_Bool checkintegrality, SCIP_Bool checklprows, SCIP_Bool *stored)
    Definition: scip_sol.c:4012
    SCIP_RETCODE SCIPtrySolFree(SCIP *scip, SCIP_SOL **sol, SCIP_Bool printreason, SCIP_Bool completely, SCIP_Bool checkbounds, SCIP_Bool checkintegrality, SCIP_Bool checklprows, SCIP_Bool *stored)
    Definition: scip_sol.c:4109
    SCIP_RETCODE SCIPlinkLPSol(SCIP *scip, SCIP_SOL *sol)
    Definition: scip_sol.c:1295
    SCIP_Real SCIPgetSolOrigObj(SCIP *scip, SCIP_SOL *sol)
    Definition: scip_sol.c:1892
    SCIP_RETCODE SCIPsetSolVal(SCIP *scip, SCIP_SOL *sol, SCIP_VAR *var, SCIP_Real val)
    Definition: scip_sol.c:1571
    SCIP_Real SCIPgetSolVal(SCIP *scip, SCIP_SOL *sol, SCIP_VAR *var)
    Definition: scip_sol.c:1765
    SCIP_RETCODE SCIPsolve(SCIP *scip)
    Definition: scip_solve.c:2635
    SCIP_Real SCIPgetUpperbound(SCIP *scip)
    SCIP_Longint SCIPgetNNodes(SCIP *scip)
    SCIP_RETCODE SCIPprintStatistics(SCIP *scip, FILE *file)
    SCIP_Real SCIPgetLowerbound(SCIP *scip)
    SCIP_Longint SCIPgetNTotalNodes(SCIP *scip)
    int SCIPgetNRuns(SCIP *scip)
    SCIP_Longint SCIPgetNLPIterations(SCIP *scip)
    SCIP_Real SCIPgetSolvingTime(SCIP *scip)
    Definition: scip_timing.c:378
    SCIP_Real SCIPgetPresolvingTime(SCIP *scip)
    Definition: scip_timing.c:442
    SCIP_Real SCIPinfinity(SCIP *scip)
    SCIP_Bool SCIPisFeasEQ(SCIP *scip, SCIP_Real val1, SCIP_Real val2)
    SCIP_Bool SCIPisFeasZero(SCIP *scip, SCIP_Real val)
    SCIP_Real SCIPfloor(SCIP *scip, SCIP_Real val)
    SCIP_Bool SCIPisInfinity(SCIP *scip, SCIP_Real val)
    SCIP_Bool SCIPisFeasLT(SCIP *scip, SCIP_Real val1, SCIP_Real val2)
    SCIP_Bool SCIPisFeasLE(SCIP *scip, SCIP_Real val1, SCIP_Real val2)
    SCIP_Bool SCIPisFeasIntegral(SCIP *scip, SCIP_Real val)
    SCIP_Bool SCIPisGT(SCIP *scip, SCIP_Real val1, SCIP_Real val2)
    SCIP_Real SCIPceil(SCIP *scip, SCIP_Real val)
    SCIP_Bool SCIPisFeasGT(SCIP *scip, SCIP_Real val1, SCIP_Real val2)
    SCIP_Bool SCIPisZero(SCIP *scip, SCIP_Real val)
    SCIP_RETCODE SCIPcutoffNode(SCIP *scip, SCIP_NODE *node)
    Definition: scip_tree.c:436
    SCIP_NODE * SCIPgetCurrentNode(SCIP *scip)
    Definition: scip_tree.c:91
    SCIP_COL * SCIPvarGetCol(SCIP_VAR *var)
    Definition: var.c:23683
    SCIP_VARSTATUS SCIPvarGetStatus(SCIP_VAR *var)
    Definition: var.c:23386
    int SCIPvarGetNLocksUpType(SCIP_VAR *var, SCIP_LOCKTYPE locktype)
    Definition: var.c:4386
    SCIP_Bool SCIPvarIsImpliedIntegral(SCIP_VAR *var)
    Definition: var.c:23498
    SCIP_Bool SCIPvarIsNonimpliedIntegral(SCIP_VAR *var)
    Definition: var.c:23506
    SCIP_Real SCIPvarGetObj(SCIP_VAR *var)
    Definition: var.c:23900
    SCIP_VARTYPE SCIPvarGetType(SCIP_VAR *var)
    Definition: var.c:23453
    SCIP_Real SCIPvarGetUbGlobal(SCIP_VAR *var)
    Definition: var.c:24142
    int SCIPvarGetProbindex(SCIP_VAR *var)
    Definition: var.c:23662
    const char * SCIPvarGetName(SCIP_VAR *var)
    Definition: var.c:23267
    SCIP_RETCODE SCIPreleaseVar(SCIP *scip, SCIP_VAR **var)
    Definition: scip_var.c:1887
    SCIP_Real SCIPvarGetLbGlobal(SCIP_VAR *var)
    Definition: var.c:24120
    SCIP_RETCODE SCIPfixVar(SCIP *scip, SCIP_VAR *var, SCIP_Real fixedval, SCIP_Bool *infeasible, SCIP_Bool *fixed)
    Definition: scip_var.c:10318
    SCIP_RETCODE SCIPcreateVarBasic(SCIP *scip, SCIP_VAR **var, const char *name, SCIP_Real lb, SCIP_Real ub, SCIP_Real obj, SCIP_VARTYPE vartype)
    Definition: scip_var.c:184
    int SCIPvarGetNLocksDownType(SCIP_VAR *var, SCIP_LOCKTYPE locktype)
    Definition: var.c:4328
    void SCIPsortIntInt(int *intarray1, int *intarray2, int len)
    int SCIPsnprintf(char *t, int len, const char *s,...)
    Definition: misc.c:10827
    #define DEFAULT_USEOBJFACTOR
    Definition: heur_repair.c:94
    static SCIP_Real getPotentialContributed(SCIP *scip, SCIP_SOL *sol, SCIP_VAR *var, SCIP_Real coefficient, int sgn)
    Definition: heur_repair.c:230
    #define DEFAULT_NODESQUOT
    Definition: heur_repair.c:87
    #define DEFAULT_FILENAME
    Definition: heur_repair.c:89
    static SCIP_DECL_HEUREXEC(heurExecRepair)
    Definition: heur_repair.c:1191
    #define DEFAULT_NODESOFS
    Definition: heur_repair.c:84
    #define DEFAULT_USEVARFIX
    Definition: heur_repair.c:97
    #define DEFAULT_MAXNODES
    Definition: heur_repair.c:85
    #define HEUR_TIMING
    Definition: heur_repair.c:80
    #define DEFAULT_MINNODES
    Definition: heur_repair.c:86
    #define HEUR_FREQOFS
    Definition: heur_repair.c:78
    #define HEUR_DESC
    Definition: heur_repair.c:74
    static SCIP_RETCODE applyRepair(SCIP *scip, SCIP_HEUR *heur, SCIP_RESULT *result, SCIP_Longint nnodes)
    Definition: heur_repair.c:529
    static SCIP_DECL_HEUREXIT(heurExitRepair)
    Definition: heur_repair.c:1116
    static SCIP_RETCODE tryFixVar(SCIP *scip, SCIP *subscip, SCIP_SOL *sol, SCIP_Real *potential, SCIP_Real *slack, SCIP_VAR *var, SCIP_VAR *subvar, int *inftycounter, SCIP_HEURDATA *heurdata, SCIP_Bool *fixed)
    Definition: heur_repair.c:277
    #define DEFAULT_MINFIXINGRATE
    Definition: heur_repair.c:82
    static SCIP_DECL_HEURFREE(heurFreeRepair)
    Definition: heur_repair.c:1063
    #define HEUR_DISPCHAR
    Definition: heur_repair.c:75
    #define HEUR_MAXDEPTH
    Definition: heur_repair.c:79
    #define HEUR_PRIORITY
    Definition: heur_repair.c:76
    static SCIP_RETCODE checkCands(SCIP *scip, SCIP_SOL *sol, SCIP_Bool roundit, SCIP_Bool *success)
    Definition: heur_repair.c:410
    #define HEUR_NAME
    Definition: heur_repair.c:73
    static SCIP_DECL_HEURCOPY(heurCopyRepair)
    Definition: heur_repair.c:1049
    #define DEFAULT_ALPHA
    Definition: heur_repair.c:99
    static SCIP_RETCODE getObjectiveFactor(SCIP *scip, SCIP *subscip, SCIP_Real *factor, SCIP_Bool *success)
    Definition: heur_repair.c:154
    #define HEUR_FREQ
    Definition: heur_repair.c:77
    #define DEFAULT_USESLACKVARS
    Definition: heur_repair.c:98
    #define HEUR_USESSUBSCIP
    Definition: heur_repair.c:81
    #define DEFAULT_ROUNDIT
    Definition: heur_repair.c:90
    static SCIP_RETCODE createNewSol(SCIP *scip, SCIP *subscip, SCIP_VAR **subvars, SCIP_HEUR *heur, SCIP_SOL *subsol, SCIP_Bool *success)
    Definition: heur_repair.c:491
    static SCIP_DECL_HEURINIT(heurInitRepair)
    Definition: heur_repair.c:1080
    repair primal heuristic
    memory allocation routines
    public methods for primal heuristics
    public methods for LP management
    public methods for message output
    #define SCIPdebug(x)
    Definition: pub_message.h:93
    #define SCIPstatistic(x)
    Definition: pub_message.h:120
    public data structures and miscellaneous methods
    methods for sorting joint arrays of various types
    public methods for problem variables
    public methods for branching rule plugins and branching
    public methods for certified solving
    public methods for constraint handler plugins and constraints
    public methods for problem copies
    public methods for exact solving
    general public methods
    public methods for primal heuristic plugins and divesets
    public methods for the LP relaxation, rows and columns
    public methods for memory management
    public methods for message handling
    public methods for numerical tolerances
    public methods for SCIP parameter handling
    public methods for global and local (sub)problems
    public methods for solutions
    public solving methods
    public methods for querying solving statistics
    public methods for timing
    public methods for the branch-and-bound tree
    public methods for SCIP variables
    SCIP_RETCODE SCIPincludeDefaultPlugins(SCIP *scip)
    default SCIP plugins
    struct SCIP_HeurData SCIP_HEURDATA
    Definition: type_heur.h:77
    @ SCIP_LPSOLSTAT_OPTIMAL
    Definition: type_lp.h:44
    @ SCIP_VERBLEVEL_NONE
    Definition: type_message.h:57
    @ SCIP_VERBLEVEL_HIGH
    Definition: type_message.h:61
    @ SCIP_VERBLEVEL_FULL
    Definition: type_message.h:62
    @ SCIP_DIDNOTRUN
    Definition: type_result.h:42
    @ SCIP_DIDNOTFIND
    Definition: type_result.h:44
    @ SCIP_FOUNDSOL
    Definition: type_result.h:56
    enum SCIP_Result SCIP_RESULT
    Definition: type_result.h:61
    @ SCIP_NOFILE
    Definition: type_retcode.h:47
    @ SCIP_OKAY
    Definition: type_retcode.h:42
    enum SCIP_Retcode SCIP_RETCODE
    Definition: type_retcode.h:63
    @ SCIP_STAGE_SOLVED
    Definition: type_set.h:54
    @ SCIP_VARTYPE_INTEGER
    Definition: type_var.h:65
    @ SCIP_VARTYPE_CONTINUOUS
    Definition: type_var.h:71
    @ SCIP_VARTYPE_BINARY
    Definition: type_var.h:64
    @ SCIP_VARSTATUS_COLUMN
    Definition: type_var.h:53
    @ SCIP_LOCKTYPE_MODEL
    Definition: type_var.h:141
    enum SCIP_Vartype SCIP_VARTYPE
    Definition: type_var.h:73