SCIP

    Solving Constraint Integer Programs

    branch_vanillafullstrong.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-2026 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 branch_vanillafullstrong.c
    26 * @ingroup DEFPLUGINS_BRANCH
    27 * @brief vanilla full strong LP branching rule
    28 * @author Tobias Achterberg
    29 * @author Maxime Gasse
    30 */
    31
    32/*---+----1----+----2----+----3----+----4----+----5----+----6----+----7----+----8----+----9----+----0----+----1----+----2*/
    33
    36#include "scip/pub_branch.h"
    37#include "scip/pub_message.h"
    38#include "scip/pub_tree.h"
    39#include "scip/pub_var.h"
    40#include "scip/scip_branch.h"
    41#include "scip/scip_exact.h"
    42#include "scip/scip_general.h"
    43#include "scip/scip_lp.h"
    44#include "scip/scip_mem.h"
    45#include "scip/scip_message.h"
    46#include "scip/scip_numerics.h"
    47#include "scip/scip_param.h"
    48#include "scip/scip_prob.h"
    50#include "scip/scip_tree.h"
    51#include "scip/scip_var.h"
    52
    53
    54#define BRANCHRULE_NAME "vanillafullstrong"
    55#define BRANCHRULE_DESC "vanilla full strong branching"
    56#define BRANCHRULE_PRIORITY -2000
    57#define BRANCHRULE_MAXDEPTH -1
    58#define BRANCHRULE_MAXBOUNDDIST 1.0
    59
    60#define DEFAULT_INTEGRALCANDS FALSE /**< should integral variables in the current LP solution be considered as
    61 * branching candidates ? */
    62#define DEFAULT_SCOREALL FALSE /**< should strong branching scores be computed for all candidates, or can
    63 * we early stop when a variable has infinite score ? */
    64#define DEFAULT_IDEMPOTENT FALSE /**< should strong branching side-effects be prevented (e.g., domain
    65 * changes, stat updates etc.) ? */
    66#define DEFAULT_COLLECTSCORES FALSE /**< should strong branching scores be collected ? */
    67#define DEFAULT_DONOTBRANCH FALSE /**< should branching be done ? */
    68
    69
    70/** branching rule data */
    71struct SCIP_BranchruleData
    72{
    73 SCIP_Bool integralcands; /**< should integral variables in the current LP solution be considered
    74 * as branching candidates ? */
    75 SCIP_Bool scoreall; /**< should strong branching scores be computed for all candidates, or
    76 * can we early stop when a node is detected infeasible ? */
    77 SCIP_Bool idempotent; /**< should strong branching side-effects be prevented (e.g., domain
    78 * changes, stat updates etc.) ? */
    79 SCIP_Bool collectscores; /**< should strong branching scores be collected ? */
    80 SCIP_Bool donotbranch; /**< should branching be done ? */
    81 SCIP_VAR** cands; /**< candidate variables */
    82 SCIP_Real* candscores; /**< candidate scores */
    83 int ncands; /**< number of candidates */
    84 int npriocands; /**< number of priority candidates */
    85 int bestcand; /**< best branching candidate */
    86 int candcapacity; /**< capacity of candidate arrays */
    87};
    88
    89
    90/*
    91 * local methods
    92 */
    93
    94
    95/** selects a variable from a set of candidates by strong branching */
    96static
    98 SCIP* scip, /**< SCIP data structure */
    99 SCIP_VAR** cands, /**< branching candidates */
    100 int ncands, /**< number of branching candidates */
    101 int npriocands, /**< number of branching candidates with highest priority */
    102 SCIP_Bool scoreall, /**< should strong branching scores be computed for all candidates, or can
    103 * we early stop when a node is detected infeasible ? */
    104 SCIP_Bool idempotent, /**< should strong branching side-effects be prevented (e.g., domain
    105 * changes, stat updates etc.) ? */
    106 SCIP_Real* scores, /**< candidate scores */
    107 int* bestcand, /**< best candidate for branching */
    108 SCIP_Real* bestdown, /**< objective value of the down branch for bestcand */
    109 SCIP_Real* bestup, /**< objective value of the up branch for bestcand */
    110 SCIP_Real* bestscore, /**< score for bestcand */
    111 SCIP_Bool* bestdownvalid, /**< is bestdown a valid dual bound for the down branch? */
    112 SCIP_Bool* bestupvalid, /**< is bestup a valid dual bound for the up branch? */
    113 SCIP_Real* provedbound /**< proved dual bound for current subtree */
    114 )
    115{ /*lint --e{715}*/
    116 SCIP_Real lpobjval;
    117 int nsbcalls;
    118 int c;
    119
    120 assert(scip != NULL);
    121 assert(cands != NULL);
    122 assert(bestcand != NULL);
    123 assert(bestdown != NULL);
    124 assert(bestup != NULL);
    125 assert(bestscore != NULL);
    126 assert(bestdownvalid != NULL);
    127 assert(bestupvalid != NULL);
    128 assert(provedbound != NULL);
    129 assert(ncands > 0);
    130
    131 /* get current LP objective bound of the local sub problem and global cutoff bound */
    132 lpobjval = SCIPgetLPObjval(scip);
    133 *provedbound = lpobjval;
    134
    135 *bestcand = 0;
    136 *bestdown = lpobjval;
    137 *bestup = lpobjval;
    138 *bestdownvalid = FALSE;
    139 *bestupvalid = FALSE;
    140 *bestscore = -SCIPinfinity(scip);
    141
    142 if( scores != NULL )
    143 for( c = 0; c < ncands; ++c )
    144 scores[c] = -SCIPinfinity(scip);
    145
    146 /* if only one candidate exists, choose this one without applying strong branching; also, when SCIP is about to be
    147 * stopped, all strongbranching evaluations will be aborted anyway, thus we can return immediately
    148 */
    149 if( (!scoreall && ncands == 1) || SCIPisStopped(scip) )
    150 return SCIP_OKAY;
    151
    152 /* this assert may not hold if SCIP is stopped, thus we only check it here */
    154
    155 /* initialize strong branching without propagation */
    157
    158 /* compute strong branching scores */
    159 nsbcalls = 0;
    160 for( c = 0; c < ncands ; ++c )
    161 {
    162 SCIP_VAR* var;
    163 SCIP_Real val;
    164 SCIP_Bool integral;
    165 SCIP_Real down, up;
    166 SCIP_Real downgain, upgain;
    167 SCIP_Bool downvalid, upvalid;
    168 SCIP_Bool downinf, upinf;
    169 SCIP_Bool downconflict, upconflict;
    170 SCIP_Bool lperror;
    171 SCIP_Real gains[3];
    172 SCIP_Real score;
    173
    174 var = cands[c];
    175 assert(var != NULL);
    176
    177 val = SCIPvarGetLPSol(var);
    178 integral = SCIPisFeasIntegral(scip, val);
    179
    180 up = -SCIPinfinity(scip);
    181 down = -SCIPinfinity(scip);
    182
    183 SCIPdebugMsg(scip, "applying vanilla strong branching on variable <%s> with solution %g\n",
    184 SCIPvarGetName(var), val);
    185
    186 /* apply strong branching */
    187 if( integral )
    188 {
    189 SCIP_CALL( SCIPgetVarStrongbranchInt(scip, cands[c], INT_MAX, idempotent,
    190 &down, &up, &downvalid, &upvalid, &downinf, &upinf, &downconflict, &upconflict, &lperror) );
    191 }
    192 else
    193 {
    194 SCIP_CALL( SCIPgetVarStrongbranchFrac(scip, cands[c], INT_MAX, idempotent,
    195 &down, &up, &downvalid, &upvalid, &downinf, &upinf, &downconflict, &upconflict, &lperror) );
    196 }
    197 nsbcalls++;
    198
    199 /* check for an error in strong branching */
    200 if( lperror )
    201 {
    203 "(node %" SCIP_LONGINT_FORMAT ") error in strong branching call for variable <%s> with solution %g\n",
    204 SCIPgetNNodes(scip), SCIPvarGetName(var), val);
    205 break;
    206 }
    207
    208 /* evaluate strong branching */
    209 down = MAX(down, lpobjval);
    210 up = MAX(up, lpobjval);
    211 downgain = down - lpobjval;
    212 upgain = up - lpobjval;
    213
    214 assert(!SCIPallColsInLP(scip) || SCIPisExact(scip) || !downvalid || downinf == SCIPisGE(scip, down, SCIPgetCutoffbound(scip)));
    215 assert(!SCIPallColsInLP(scip) || SCIPisExact(scip) || !upvalid || upinf == SCIPisGE(scip, up, SCIPgetCutoffbound(scip)));
    216 assert(downinf || !downconflict);
    217 assert(upinf || !upconflict);
    218
    219 if( !idempotent )
    220 {
    221 /* display node information line */
    222 if( SCIPgetDepth(scip) == 0 && nsbcalls % 100 == 0 )
    223 {
    225 }
    226 /* update variable pseudo cost values */
    227 if( !downinf && downvalid )
    228 {
    229 SCIP_CALL( SCIPupdateVarPseudocost(scip, var, integral ? -1.0 : 0.0 - SCIPfrac(scip, val), downgain, 1.0) );
    230 }
    231 if( !upinf && upvalid )
    232 {
    233 SCIP_CALL( SCIPupdateVarPseudocost(scip, var, integral ? +1.0 : 1.0 - SCIPfrac(scip, val), upgain, 1.0) );
    234 }
    235 }
    236
    237 /* compute strong branching score */
    238 gains[0] = downgain;
    239 gains[1] = upgain;
    240 gains[2] = 0.0;
    241 score = SCIPgetBranchScoreMultiple(scip, var, integral ? 3 : 2, gains);
    242
    243 /* collect scores if requested */
    244 if( scores != NULL )
    245 scores[c] = score;
    246
    247 /* check for a better score */
    248 if( score > *bestscore )
    249 {
    250 *bestcand = c;
    251 *bestdown = down;
    252 *bestup = up;
    253 *bestdownvalid = downvalid;
    254 *bestupvalid = upvalid;
    255 *bestscore = score;
    256 }
    257
    258 SCIPdebugMsg(scip, " -> cand %d/%d (prio:%d) var <%s> (solval=%g, downgain=%g, upgain=%g, score=%g) -- best: <%s> (%g)\n",
    259 c, ncands, npriocands, SCIPvarGetName(var), val, downgain, upgain, score,
    260 SCIPvarGetName(cands[*bestcand]), *bestscore);
    261
    262 /* node is infeasible -> early stopping (highest score) */
    263 if( !integral && !scoreall && downinf && upinf )
    264 {
    265 /* we should only detect infeasibility if the LP is a valid relaxation */
    266 assert(SCIPallColsInLP(scip));
    267 assert(!SCIPisExact(scip));
    268 assert(*bestcand == c);
    269
    270 SCIPdebugMsg(scip, " -> variable <%s> is infeasible in both directions\n", SCIPvarGetName(var));
    271 break;
    272 }
    273 }
    274
    275 /* end strong branching */
    277
    278 /* update proved bound */
    279 if( *bestdownvalid && *bestupvalid && !SCIPisFeasIntegral(scip, SCIPvarGetLPSol(cands[*bestcand])) )
    280 {
    281 SCIP_Real minbound = MIN(*bestdown, *bestup);
    282
    283 *provedbound = MAX(*provedbound, minbound);
    284 }
    285
    286 return SCIP_OKAY;
    287}
    288
    289/*
    290 * Callback methods
    291 */
    292
    293/** copy method for branchrule plugins (called when SCIP copies plugins) */
    294static
    295SCIP_DECL_BRANCHCOPY(branchCopyVanillafullstrong)
    296{ /*lint --e{715}*/
    297 assert(scip != NULL);
    298 assert(branchrule != NULL);
    299
    301
    302 /* call inclusion method of branchrule */
    304
    305 return SCIP_OKAY;
    306}
    307
    308/** destructor of branching rule to free user data (called when SCIP is exiting) */
    309static
    310SCIP_DECL_BRANCHFREE(branchFreeVanillafullstrong)
    311{ /*lint --e{715}*/
    312 SCIP_BRANCHRULEDATA* branchruledata;
    313
    314 /* free branching rule data */
    315 branchruledata = SCIPbranchruleGetData(branchrule);
    316 assert(branchruledata != NULL);
    317
    318 SCIPfreeBlockMemoryNull(scip, &branchruledata);
    319
    320 return SCIP_OKAY;
    321}
    322
    323/** initialization method of branching rule (called after problem was transformed) */
    324static
    325SCIP_DECL_BRANCHINIT(branchInitVanillafullstrong)
    326{ /*lint --e{715}*/
    327#ifndef NDEBUG
    328 SCIP_BRANCHRULEDATA* branchruledata;
    329
    330 /* initialize branching rule data */
    331 branchruledata = SCIPbranchruleGetData(branchrule);
    332#endif
    333 assert(branchruledata != NULL);
    334 assert(branchruledata->candscores == NULL);
    335 assert(branchruledata->cands == NULL);
    336
    337 return SCIP_OKAY;
    338}
    339
    340/** deinitialization method of branching rule (called before transformed problem is freed) */
    341static
    342SCIP_DECL_BRANCHEXIT(branchExitVanillafullstrong)
    343{ /*lint --e{715}*/
    344 SCIP_BRANCHRULEDATA* branchruledata;
    345
    346 /* initialize branching rule data */
    347 branchruledata = SCIPbranchruleGetData(branchrule);
    348 assert(branchruledata != NULL);
    349
    350 /* free candidate arrays if any */
    351 if( branchruledata->candscores != NULL )
    352 {
    353 SCIPfreeBlockMemoryArrayNull(scip, &branchruledata->candscores, branchruledata->candcapacity);
    354 }
    355 if( branchruledata->cands != NULL )
    356 {
    357 SCIPfreeBlockMemoryArrayNull(scip, &branchruledata->cands, branchruledata->candcapacity);
    358 }
    359
    360 branchruledata->candcapacity = -1;
    361 branchruledata->ncands = -1;
    362 branchruledata->npriocands = -1;
    363 branchruledata->bestcand = -1;
    364
    365 return SCIP_OKAY;
    366}
    367
    368/** branching execution method */
    369static
    370SCIP_DECL_BRANCHEXECLP(branchExeclpVanillafullstrong)
    371{ /*lint --e{715}*/
    372 SCIP_BRANCHRULEDATA* branchruledata;
    373 SCIP_Real bestdown;
    374 SCIP_Real bestup;
    375 SCIP_Real bestscore;
    376 SCIP_Real provedbound;
    377 SCIP_Bool bestdownvalid;
    378 SCIP_Bool bestupvalid;
    379 SCIP_VAR** cands;
    380 int ncands;
    381 int npriocands;
    382 int i;
    383
    384 assert(branchrule != NULL);
    385 assert(scip != NULL);
    386 assert(result != NULL);
    387
    389
    390 SCIPdebugMsg(scip, "Execlp method of vanilla fullstrong branching\n");
    391
    392 *result = SCIP_DIDNOTRUN;
    393
    394 /* get branching rule data */
    395 branchruledata = SCIPbranchruleGetData(branchrule);
    396 assert(branchruledata != NULL);
    397
    398 /* get branching candidates, either all non-fixed variables or only the
    399 * fractional ones */
    400 if( branchruledata->integralcands )
    401 {
    402 SCIP_CALL( SCIPgetPseudoBranchCands(scip, &cands, &ncands, &npriocands) );
    403 }
    404 else
    405 {
    406 SCIP_CALL( SCIPgetLPBranchCands(scip, &cands, NULL, NULL, &ncands, &npriocands, NULL) );
    407 }
    408
    409 assert(ncands > 0);
    410 assert(npriocands > 0);
    411
    412 /* increase candidate arrays capacity if needed */
    413 if( ncands > branchruledata->candcapacity )
    414 {
    415 /* free previously allocated arrays if any */
    416 if( branchruledata->candscores != NULL)
    417 {
    418 SCIPfreeBlockMemoryArrayNull(scip, &branchruledata->candscores, branchruledata->candcapacity);
    419 branchruledata->candscores = NULL;
    420 }
    421 if( branchruledata->cands != NULL)
    422 {
    423 SCIPfreeBlockMemoryArrayNull(scip, &branchruledata->cands, branchruledata->candcapacity);
    424 branchruledata->cands = NULL;
    425 }
    426
    427 /* update capacity */
    428 branchruledata->candcapacity = SCIPgetNBinVars(scip) + SCIPgetNIntVars(scip) + SCIPgetNImplVars(scip);
    429 }
    430 assert(branchruledata->candcapacity >= ncands);
    431
    432 /* allocate new candidate arrays if needed */
    433 if( branchruledata->cands == NULL )
    434 {
    435 SCIP_CALL( SCIPallocBlockMemoryArray(scip, &branchruledata->cands, branchruledata->candcapacity) );
    436 }
    437 if( branchruledata->candscores == NULL && branchruledata->collectscores )
    438 {
    439 SCIP_CALL( SCIPallocBlockMemoryArray(scip, &branchruledata->candscores, branchruledata->candcapacity) );
    440 }
    441
    442 /* copy candidates */
    443 branchruledata->ncands = ncands;
    444 branchruledata->npriocands = npriocands;
    445
    446 for( i = 0; i < ncands; i++ )
    447 branchruledata->cands[i] = cands[i];
    448
    449 SCIP_CALL( runVanillaStrongBranching(scip, branchruledata->cands, branchruledata->ncands, branchruledata->npriocands,
    450 branchruledata->scoreall, branchruledata->idempotent, branchruledata->candscores,
    451 &branchruledata->bestcand, &bestdown, &bestup, &bestscore, &bestdownvalid,
    452 &bestupvalid, &provedbound) );
    453
    454 if( !branchruledata->donotbranch )
    455 {
    456 assert(0 <= branchruledata->bestcand && branchruledata->bestcand < branchruledata->ncands);
    457
    458 if( SCIPisGE(scip, provedbound, SCIPgetCutoffbound(scip)) )
    459 {
    460 SCIPdebugMsg(scip, " -> variable <%s> is infeasible in both directions\n",
    461 SCIPvarGetName(branchruledata->cands[branchruledata->bestcand]));
    462
    463 *result = SCIP_CUTOFF;
    464 }
    465 else
    466 {
    467 SCIP_VAR* var;
    468 SCIP_Real val;
    469 SCIP_NODE* downchild;
    470 SCIP_NODE* eqchild;
    471 SCIP_NODE* upchild;
    472 SCIP_Bool allcolsinlp;
    473 SCIP_Bool exactsolve;
    474
    475 /* check, if we want to solve the problem exactly, meaning that strong branching information is not useful
    476 * for cutting off sub problems and improving lower bounds of children
    477 */
    478 exactsolve = SCIPisExact(scip);
    479
    480 /* check, if all existing columns are in LP, and thus the strong branching results give lower bounds */
    481 allcolsinlp = SCIPallColsInLP(scip);
    482
    483 if( !branchruledata->idempotent && allcolsinlp && !exactsolve )
    484 {
    486 }
    487
    488 assert(SCIPisLT(scip, provedbound, SCIPgetCutoffbound(scip)));
    489
    490 var = branchruledata->cands[branchruledata->bestcand];
    491 val = SCIPvarGetLPSol(var);
    492
    493 /* perform the branching */
    494 SCIPdebugMsg(scip, " -> %d candidates, selected candidate %d: variable <%s>[%g,%g] (solval=%g, down=%g, up=%g, score=%g)\n",
    495 branchruledata->ncands, branchruledata->bestcand, SCIPvarGetName(var), SCIPvarGetLbLocal(var),
    496 SCIPvarGetUbLocal(var), val, bestdown, bestup, bestscore);
    497 SCIP_CALL( SCIPbranchVarVal(scip, var, val, &downchild, &eqchild, &upchild) );
    498
    499 /* update the lower bounds in the children */
    500 if( !branchruledata->idempotent && allcolsinlp && !exactsolve )
    501 {
    502 if( downchild != NULL && bestdownvalid )
    503 {
    504 SCIP_CALL( SCIPupdateNodeLowerbound(scip, downchild, bestdown) );
    505 SCIPdebugMsg(scip, " -> down child's lowerbound: %g\n", SCIPnodeGetLowerbound(downchild));
    506 }
    507 if( upchild != NULL && bestupvalid )
    508 {
    509 SCIP_CALL( SCIPupdateNodeLowerbound(scip, upchild, bestup) );
    510 SCIPdebugMsg(scip, " -> up child's lowerbound: %g\n", SCIPnodeGetLowerbound(upchild));
    511 }
    512 }
    513
    514 *result = SCIP_BRANCHED;
    515 }
    516 }
    517
    518 return SCIP_OKAY;
    519}
    520
    521
    522/*
    523 * branching specific interface methods
    524 */
    525
    526/** creates the vanilla full strong LP branching rule and includes it in SCIP */
    528 SCIP* scip /**< SCIP data structure */
    529 )
    530{
    531 SCIP_BRANCHRULEDATA* branchruledata;
    532 SCIP_BRANCHRULE* branchrule;
    533
    534 /* create fullstrong branching rule data */
    535 SCIP_CALL( SCIPallocBlockMemory(scip, &branchruledata) );
    536 branchruledata->cands = NULL;
    537 branchruledata->candscores = NULL;
    538 branchruledata->candcapacity = -1;
    539 branchruledata->ncands = -1;
    540 branchruledata->npriocands = -1;
    541 branchruledata->bestcand = -1;
    542
    543 /* include branching rule */
    546
    547 assert(branchrule != NULL);
    548
    549 /* set non-fundamental callbacks via specific setter functions*/
    550 SCIP_CALL( SCIPsetBranchruleCopy(scip, branchrule, branchCopyVanillafullstrong) );
    551 SCIP_CALL( SCIPsetBranchruleFree(scip, branchrule, branchFreeVanillafullstrong) );
    552 SCIP_CALL( SCIPsetBranchruleInit(scip, branchrule, branchInitVanillafullstrong) );
    553 SCIP_CALL( SCIPsetBranchruleExit(scip, branchrule, branchExitVanillafullstrong) );
    554 SCIP_CALL( SCIPsetBranchruleExecLp(scip, branchrule, branchExeclpVanillafullstrong) );
    555
    556 /* fullstrong branching rule parameters */
    558 "branching/vanillafullstrong/integralcands",
    559 "should integral variables in the current LP solution be considered as branching candidates?",
    560 &branchruledata->integralcands, FALSE, DEFAULT_INTEGRALCANDS, NULL, NULL) );
    562 "branching/vanillafullstrong/idempotent",
    563 "should strong branching side-effects be prevented (e.g., domain changes, stat updates etc.)?",
    564 &branchruledata->idempotent, FALSE, DEFAULT_IDEMPOTENT, NULL, NULL) );
    566 "branching/vanillafullstrong/scoreall",
    567 "should strong branching scores be computed for all candidates, or can we early stop when a variable has infinite score?",
    568 &branchruledata->scoreall, TRUE, DEFAULT_SCOREALL, NULL, NULL) );
    570 "branching/vanillafullstrong/collectscores",
    571 "should strong branching scores be collected?",
    572 &branchruledata->collectscores, TRUE, DEFAULT_COLLECTSCORES, NULL, NULL) );
    574 "branching/vanillafullstrong/donotbranch",
    575 "should candidates only be scored, but no branching be performed?",
    576 &branchruledata->donotbranch, TRUE, DEFAULT_DONOTBRANCH, NULL, NULL) );
    577
    578 return SCIP_OKAY;
    579}
    580
    581
    582/** recovers candidate variables and their scores from last vanilla full strong branching call */
    584 SCIP* scip, /**< SCIP data structure */
    585 SCIP_VAR*** cands, /**< pointer to store candidate variables; or NULL */
    586 SCIP_Real** candscores, /**< pointer to store candidate scores; or NULL */
    587 int* ncands, /**< pointer to store number of candidates; or NULL */
    588 int* npriocands, /**< pointer to store number of priority candidates; or NULL */
    589 int* bestcand /**< pointer to store best branching candidate; or NULL */
    590 )
    591{
    592 SCIP_BRANCHRULEDATA* branchruledata;
    593 SCIP_BRANCHRULE* branchrule;
    594
    595 assert(scip != NULL);
    596
    598 assert( branchrule != NULL );
    599 branchruledata = SCIPbranchruleGetData(branchrule);
    600 assert( branchruledata != NULL );
    601
    602 if( cands )
    603 {
    604 *cands = branchruledata->cands;
    605 }
    606 if( candscores && branchruledata->collectscores )
    607 {
    608 *candscores = branchruledata->candscores;
    609 }
    610 if( ncands )
    611 {
    612 *ncands = branchruledata->ncands;
    613 }
    614 if( npriocands )
    615 {
    616 *npriocands = branchruledata->npriocands;
    617 }
    618 if( bestcand )
    619 {
    620 *bestcand = branchruledata->bestcand;
    621 }
    622
    623 return SCIP_OKAY;
    624}
    #define BRANCHRULE_DESC
    #define DEFAULT_IDEMPOTENT
    #define BRANCHRULE_PRIORITY
    SCIP_RETCODE SCIPgetVanillafullstrongData(SCIP *scip, SCIP_VAR ***cands, SCIP_Real **candscores, int *ncands, int *npriocands, int *bestcand)
    #define DEFAULT_SCOREALL
    #define BRANCHRULE_NAME
    static SCIP_DECL_BRANCHCOPY(branchCopyVanillafullstrong)
    static SCIP_RETCODE runVanillaStrongBranching(SCIP *scip, SCIP_VAR **cands, int ncands, int npriocands, SCIP_Bool scoreall, SCIP_Bool idempotent, SCIP_Real *scores, int *bestcand, SCIP_Real *bestdown, SCIP_Real *bestup, SCIP_Real *bestscore, SCIP_Bool *bestdownvalid, SCIP_Bool *bestupvalid, SCIP_Real *provedbound)
    #define DEFAULT_INTEGRALCANDS
    #define DEFAULT_DONOTBRANCH
    static SCIP_DECL_BRANCHFREE(branchFreeVanillafullstrong)
    static SCIP_DECL_BRANCHEXIT(branchExitVanillafullstrong)
    static SCIP_DECL_BRANCHEXECLP(branchExeclpVanillafullstrong)
    static SCIP_DECL_BRANCHINIT(branchInitVanillafullstrong)
    #define BRANCHRULE_MAXDEPTH
    #define DEFAULT_COLLECTSCORES
    #define BRANCHRULE_MAXBOUNDDIST
    vanilla full strong LP branching rule
    #define NULL
    Definition: def.h:257
    #define SCIP_Bool
    Definition: def.h:100
    #define MIN(x, y)
    Definition: def.h:233
    #define SCIP_STRINGEQ(name, reference, retcode)
    Definition: def.h:454
    #define SCIP_Real
    Definition: def.h:165
    #define TRUE
    Definition: def.h:102
    #define FALSE
    Definition: def.h:103
    #define MAX(x, y)
    Definition: def.h:229
    #define SCIP_LONGINT_FORMAT
    Definition: def.h:157
    #define SCIP_CALL(x)
    Definition: def.h:364
    SCIP_RETCODE SCIPincludeBranchruleVanillafullstrong(SCIP *scip)
    SCIP_Bool SCIPisStopped(SCIP *scip)
    Definition: scip_general.c:767
    int SCIPgetNIntVars(SCIP *scip)
    Definition: scip_prob.c:2340
    int SCIPgetNImplVars(SCIP *scip)
    Definition: scip_prob.c:2387
    int SCIPgetNBinVars(SCIP *scip)
    Definition: scip_prob.c:2293
    SCIP_RETCODE SCIPupdateNodeLowerbound(SCIP *scip, SCIP_NODE *node, SCIP_Real newbound)
    Definition: scip_prob.c:4354
    SCIP_RETCODE SCIPupdateLocalLowerbound(SCIP *scip, SCIP_Real newbound)
    Definition: scip_prob.c:4289
    void SCIPverbMessage(SCIP *scip, SCIP_VERBLEVEL msgverblevel, FILE *file, const char *formatstr,...)
    Definition: scip_message.c:225
    #define SCIPdebugMsg
    Definition: scip_message.h:78
    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 SCIPsetBranchruleExit(SCIP *scip, SCIP_BRANCHRULE *branchrule, SCIP_DECL_BRANCHEXIT((*branchexit)))
    Definition: scip_branch.c:208
    SCIP_RETCODE SCIPsetBranchruleExecLp(SCIP *scip, SCIP_BRANCHRULE *branchrule, SCIP_DECL_BRANCHEXECLP((*branchexeclp)))
    Definition: scip_branch.c:256
    SCIP_BRANCHRULE * SCIPfindBranchrule(SCIP *scip, const char *name)
    Definition: scip_branch.c:304
    SCIP_RETCODE SCIPsetBranchruleCopy(SCIP *scip, SCIP_BRANCHRULE *branchrule, SCIP_DECL_BRANCHCOPY((*branchcopy)))
    Definition: scip_branch.c:160
    SCIP_RETCODE SCIPincludeBranchruleBasic(SCIP *scip, SCIP_BRANCHRULE **branchruleptr, const char *name, const char *desc, int priority, int maxdepth, SCIP_Real maxbounddist, SCIP_BRANCHRULEDATA *branchruledata)
    Definition: scip_branch.c:123
    const char * SCIPbranchruleGetName(SCIP_BRANCHRULE *branchrule)
    Definition: branch.c:2018
    SCIP_BRANCHRULEDATA * SCIPbranchruleGetData(SCIP_BRANCHRULE *branchrule)
    Definition: branch.c:1886
    SCIP_RETCODE SCIPsetBranchruleFree(SCIP *scip, SCIP_BRANCHRULE *branchrule, SCIP_DECL_BRANCHFREE((*branchfree)))
    Definition: scip_branch.c:176
    SCIP_RETCODE SCIPsetBranchruleInit(SCIP *scip, SCIP_BRANCHRULE *branchrule, SCIP_DECL_BRANCHINIT((*branchinit)))
    Definition: scip_branch.c:192
    SCIP_RETCODE SCIPbranchVarVal(SCIP *scip, SCIP_VAR *var, SCIP_Real val, SCIP_NODE **downchild, SCIP_NODE **eqchild, SCIP_NODE **upchild)
    Definition: scip_branch.c:1134
    SCIP_RETCODE SCIPgetLPBranchCands(SCIP *scip, SCIP_VAR ***lpcands, SCIP_Real **lpcandssol, SCIP_Real **lpcandsfrac, int *nlpcands, int *npriolpcands, int *nfracimplvars)
    Definition: scip_branch.c:402
    SCIP_RETCODE SCIPgetPseudoBranchCands(SCIP *scip, SCIP_VAR ***pseudocands, int *npseudocands, int *npriopseudocands)
    Definition: scip_branch.c:741
    SCIP_Real SCIPgetBranchScoreMultiple(SCIP *scip, SCIP_VAR *var, int nchildren, SCIP_Real *gains)
    Definition: scip_branch.c:880
    SCIP_Bool SCIPisExact(SCIP *scip)
    Definition: scip_exact.c:193
    SCIP_LPSOLSTAT SCIPgetLPSolstat(SCIP *scip)
    Definition: scip_lp.c:174
    SCIP_Bool SCIPallColsInLP(SCIP *scip)
    Definition: scip_lp.c:655
    SCIP_Real SCIPgetLPObjval(SCIP *scip)
    Definition: scip_lp.c:253
    #define SCIPallocBlockMemoryArray(scip, ptr, num)
    Definition: scip_mem.h:93
    #define SCIPfreeBlockMemoryArrayNull(scip, ptr, num)
    Definition: scip_mem.h:111
    #define SCIPfreeBlockMemoryNull(scip, ptr)
    Definition: scip_mem.h:109
    #define SCIPallocBlockMemory(scip, ptr)
    Definition: scip_mem.h:89
    SCIP_Real SCIPnodeGetLowerbound(SCIP_NODE *node)
    Definition: tree.c:8533
    SCIP_Longint SCIPgetNNodes(SCIP *scip)
    SCIP_Real SCIPgetCutoffbound(SCIP *scip)
    SCIP_RETCODE SCIPprintDisplayLine(SCIP *scip, FILE *file, SCIP_VERBLEVEL verblevel, SCIP_Bool endline)
    SCIP_Real SCIPinfinity(SCIP *scip)
    SCIP_Bool SCIPisGE(SCIP *scip, SCIP_Real val1, SCIP_Real val2)
    SCIP_Bool SCIPisFeasIntegral(SCIP *scip, SCIP_Real val)
    SCIP_Real SCIPfrac(SCIP *scip, SCIP_Real val)
    SCIP_Bool SCIPisLT(SCIP *scip, SCIP_Real val1, SCIP_Real val2)
    int SCIPgetDepth(SCIP *scip)
    Definition: scip_tree.c:672
    SCIP_RETCODE SCIPgetVarStrongbranchFrac(SCIP *scip, SCIP_VAR *var, int itlim, SCIP_Bool idempotent, SCIP_Real *down, SCIP_Real *up, SCIP_Bool *downvalid, SCIP_Bool *upvalid, SCIP_Bool *downinf, SCIP_Bool *upinf, SCIP_Bool *downconflict, SCIP_Bool *upconflict, SCIP_Bool *lperror)
    Definition: scip_var.c:3664
    SCIP_RETCODE SCIPgetVarStrongbranchInt(SCIP *scip, SCIP_VAR *var, int itlim, SCIP_Bool idempotent, SCIP_Real *down, SCIP_Real *up, SCIP_Bool *downvalid, SCIP_Bool *upvalid, SCIP_Bool *downinf, SCIP_Bool *upinf, SCIP_Bool *downconflict, SCIP_Bool *upconflict, SCIP_Bool *lperror)
    Definition: scip_var.c:4478
    SCIP_RETCODE SCIPendStrongbranch(SCIP *scip)
    Definition: scip_var.c:3488
    SCIP_Real SCIPvarGetUbLocal(SCIP_VAR *var)
    Definition: var.c:24300
    const char * SCIPvarGetName(SCIP_VAR *var)
    Definition: var.c:23299
    SCIP_Real SCIPvarGetLPSol(SCIP_VAR *var)
    Definition: var.c:24696
    SCIP_Real SCIPvarGetLbLocal(SCIP_VAR *var)
    Definition: var.c:24266
    SCIP_RETCODE SCIPupdateVarPseudocost(SCIP *scip, SCIP_VAR *var, SCIP_Real solvaldelta, SCIP_Real objdelta, SCIP_Real weight)
    Definition: scip_var.c:11122
    SCIP_RETCODE SCIPstartStrongbranch(SCIP *scip, SCIP_Bool enablepropagation)
    Definition: scip_var.c:3430
    memory allocation routines
    public methods for branching rules
    public methods for message output
    public methods for branch and bound tree
    public methods for problem variables
    public methods for branching rule plugins and branching
    public methods for exact solving
    general public methods
    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 querying solving statistics
    public methods for the branch-and-bound tree
    public methods for SCIP variables
    struct SCIP_BranchruleData SCIP_BRANCHRULEDATA
    Definition: type_branch.h:57
    @ SCIP_LPSOLSTAT_OPTIMAL
    Definition: type_lp.h:44
    @ SCIP_VERBLEVEL_HIGH
    Definition: type_message.h:61
    @ SCIP_DIDNOTRUN
    Definition: type_result.h:42
    @ SCIP_CUTOFF
    Definition: type_result.h:48
    @ SCIP_BRANCHED
    Definition: type_result.h:54
    @ SCIP_OKAY
    Definition: type_retcode.h:42
    @ SCIP_INVALIDCALL
    Definition: type_retcode.h:51
    enum SCIP_Retcode SCIP_RETCODE
    Definition: type_retcode.h:63