Scippy

SCIP

Solving Constraint Integer Programs

scip_solvingstats.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-2023 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 scip_solvingstats.c
26  * @ingroup OTHER_CFILES
27  * @brief public methods for querying solving statistics
28  * @author Tobias Achterberg
29  * @author Timo Berthold
30  * @author Gerald Gamrath
31  * @author Leona Gottwald
32  * @author Stefan Heinz
33  * @author Gregor Hendel
34  * @author Thorsten Koch
35  * @author Alexander Martin
36  * @author Marc Pfetsch
37  * @author Michael Winkler
38  * @author Kati Wolter
39  *
40  * @todo check all SCIP_STAGE_* switches, and include the new stages TRANSFORMED and INITSOLVE
41  */
42 
43 /*---+----1----+----2----+----3----+----4----+----5----+----6----+----7----+----8----+----9----+----0----+----1----+----2*/
44 
45 #include "blockmemshell/memory.h"
46 #include "scip/branch.h"
47 #include "scip/clock.h"
48 #include "scip/concsolver.h"
49 #include "scip/concurrent.h"
50 #include "scip/conflict.h"
51 #include "scip/conflictstore.h"
52 #include "scip/debug.h"
53 #include "scip/disp.h"
54 #include "scip/history.h"
55 #include "scip/implics.h"
56 #include "scip/pricestore.h"
57 #include "scip/primal.h"
58 #include "scip/prob.h"
59 #include "scip/pub_benderscut.h"
60 #include "scip/pub_benders.h"
61 #include "scip/pub_branch.h"
62 #include "scip/pub_compr.h"
63 #include "scip/pub_cons.h"
64 #include "scip/pub_cutpool.h"
65 #include "scip/pub_cutsel.h"
66 #include "scip/pub_expr.h"
67 #include "scip/pub_heur.h"
68 #include "scip/pub_history.h"
69 #include "scip/pub_message.h"
70 #include "scip/pub_misc.h"
71 #include "scip/pub_misc_sort.h"
72 #include "scip/pub_nlpi.h"
73 #include "scip/pub_presol.h"
74 #include "scip/pub_pricer.h"
75 #include "scip/pub_prop.h"
76 #include "scip/pub_reader.h"
77 #include "scip/pub_relax.h"
78 #include "scip/pub_reopt.h"
79 #include "scip/pub_sepa.h"
80 #include "scip/pub_sol.h"
81 #include "scip/pub_table.h"
82 #include "scip/pub_var.h"
83 #include "scip/reader.h"
84 #include "scip/reopt.h"
85 #include "scip/scip_benders.h"
86 #include "scip/scip_general.h"
87 #include "scip/scip_mem.h"
88 #include "scip/scip_message.h"
89 #include "scip/scip_numerics.h"
90 #include "scip/scip_sol.h"
91 #include "scip/scip_solvingstats.h"
92 #include "scip/scip_table.h"
93 #include "scip/scip_timing.h"
94 #include "scip/scip_var.h"
95 #include "scip/sepastore.h"
96 #include "scip/set.h"
97 #include "scip/sol.h"
98 #include "scip/stat.h"
99 #include "scip/struct_mem.h"
100 #include "scip/struct_primal.h"
101 #include "scip/struct_prob.h"
102 #include "scip/struct_scip.h"
103 #include "scip/struct_set.h"
104 #include "scip/struct_stat.h"
105 #include "scip/syncstore.h"
106 #include "scip/table.h"
107 #include "scip/tree.h"
108 #include "scip/var.h"
109 #include <string.h>
110 
111 /** gets number of branch and bound runs performed, including the current run
112  *
113  * @return the number of branch and bound runs performed, including the current run
114  *
115  * @pre This method can be called if SCIP is in one of the following stages:
116  * - \ref SCIP_STAGE_PROBLEM
117  * - \ref SCIP_STAGE_TRANSFORMING
118  * - \ref SCIP_STAGE_TRANSFORMED
119  * - \ref SCIP_STAGE_INITPRESOLVE
120  * - \ref SCIP_STAGE_PRESOLVING
121  * - \ref SCIP_STAGE_EXITPRESOLVE
122  * - \ref SCIP_STAGE_PRESOLVED
123  * - \ref SCIP_STAGE_INITSOLVE
124  * - \ref SCIP_STAGE_SOLVING
125  * - \ref SCIP_STAGE_SOLVED
126  * - \ref SCIP_STAGE_EXITSOLVE
127  * - \ref SCIP_STAGE_FREETRANS
128  */
130  SCIP* scip /**< SCIP data structure */
131  )
132 {
133  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNRuns", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
134 
135  return scip->stat->nruns;
136 }
137 
138 /** gets number of reoptimization runs performed, including the current run
139  *
140  * @return the number of reoptimization runs performed, including the current run
141  *
142  * @pre This method can be called if SCIP is in one of the following stages:
143  * - \ref SCIP_STAGE_PROBLEM
144  * - \ref SCIP_STAGE_TRANSFORMING
145  * - \ref SCIP_STAGE_TRANSFORMED
146  * - \ref SCIP_STAGE_INITPRESOLVE
147  * - \ref SCIP_STAGE_PRESOLVING
148  * - \ref SCIP_STAGE_EXITPRESOLVE
149  * - \ref SCIP_STAGE_PRESOLVED
150  * - \ref SCIP_STAGE_INITSOLVE
151  * - \ref SCIP_STAGE_SOLVING
152  * - \ref SCIP_STAGE_SOLVED
153  * - \ref SCIP_STAGE_EXITSOLVE
154  * - \ref SCIP_STAGE_FREETRANS
155  */
157  SCIP* scip /**< SCIP data structure */
158  )
159 {
160  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNReoptRuns", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
161 
162  return scip->stat->nreoptruns;
163 }
164 
165 /** add given number to the number of processed nodes in current run and in all runs, including the focus node
166  *
167  * @return the number of processed nodes in current run, including the focus node
168  *
169  * @pre This method can be called if SCIP is in one of the following stages:
170  * - \ref SCIP_STAGE_PROBLEM
171  * - \ref SCIP_STAGE_TRANSFORMING
172  * - \ref SCIP_STAGE_TRANSFORMED
173  * - \ref SCIP_STAGE_INITPRESOLVE
174  * - \ref SCIP_STAGE_PRESOLVING
175  * - \ref SCIP_STAGE_EXITPRESOLVE
176  * - \ref SCIP_STAGE_PRESOLVED
177  * - \ref SCIP_STAGE_INITSOLVE
178  * - \ref SCIP_STAGE_SOLVING
179  * - \ref SCIP_STAGE_SOLVED
180  * - \ref SCIP_STAGE_EXITSOLVE
181  * - \ref SCIP_STAGE_FREETRANS
182  */
184  SCIP* scip, /**< SCIP data structure */
185  SCIP_Longint nnodes /**< number of processed nodes to add to the statistics */
186  )
187 {
188  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPaddNNodes", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
189 
190  scip->stat->nnodes += nnodes;
191  scip->stat->ntotalnodes += nnodes;
192 }
193 
194 /** gets number of processed nodes in current run, including the focus node
195  *
196  * @return the number of processed nodes in current run, including the focus node
197  *
198  * @pre This method can be called if SCIP is in one of the following stages:
199  * - \ref SCIP_STAGE_PROBLEM
200  * - \ref SCIP_STAGE_TRANSFORMING
201  * - \ref SCIP_STAGE_TRANSFORMED
202  * - \ref SCIP_STAGE_INITPRESOLVE
203  * - \ref SCIP_STAGE_PRESOLVING
204  * - \ref SCIP_STAGE_EXITPRESOLVE
205  * - \ref SCIP_STAGE_PRESOLVED
206  * - \ref SCIP_STAGE_INITSOLVE
207  * - \ref SCIP_STAGE_SOLVING
208  * - \ref SCIP_STAGE_SOLVED
209  * - \ref SCIP_STAGE_EXITSOLVE
210  * - \ref SCIP_STAGE_FREETRANS
211  */
213  SCIP* scip /**< SCIP data structure */
214  )
215 {
216  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNNodes", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
217 
218  return scip->stat->nnodes;
219 }
220 
221 /** gets total number of processed nodes in all runs, including the focus node
222  *
223  * @return the total number of processed nodes in all runs, including the focus node
224  *
225  * @pre This method can be called if SCIP is in one of the following stages:
226  * - \ref SCIP_STAGE_PROBLEM
227  * - \ref SCIP_STAGE_TRANSFORMING
228  * - \ref SCIP_STAGE_TRANSFORMED
229  * - \ref SCIP_STAGE_INITPRESOLVE
230  * - \ref SCIP_STAGE_PRESOLVING
231  * - \ref SCIP_STAGE_EXITPRESOLVE
232  * - \ref SCIP_STAGE_PRESOLVED
233  * - \ref SCIP_STAGE_INITSOLVE
234  * - \ref SCIP_STAGE_SOLVING
235  * - \ref SCIP_STAGE_SOLVED
236  * - \ref SCIP_STAGE_EXITSOLVE
237  * - \ref SCIP_STAGE_FREETRANS
238  */
240  SCIP* scip /**< SCIP data structure */
241  )
242 {
243  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNTotalNodes", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
244 
245  return scip->stat->ntotalnodes;
246 }
247 
248 /** gets number of leaf nodes processed with feasible relaxation solution
249  *
250  * @return number of leaf nodes processed with feasible relaxation solution
251  *
252  * @pre This method can be called if SCIP is in one of the following stages:
253  * - \ref SCIP_STAGE_PROBLEM
254  * - \ref SCIP_STAGE_TRANSFORMING
255  * - \ref SCIP_STAGE_TRANSFORMED
256  * - \ref SCIP_STAGE_INITPRESOLVE
257  * - \ref SCIP_STAGE_PRESOLVING
258  * - \ref SCIP_STAGE_EXITPRESOLVE
259  * - \ref SCIP_STAGE_PRESOLVED
260  * - \ref SCIP_STAGE_INITSOLVE
261  * - \ref SCIP_STAGE_SOLVING
262  * - \ref SCIP_STAGE_SOLVED
263  * - \ref SCIP_STAGE_EXITSOLVE
264  * - \ref SCIP_STAGE_FREETRANS
265  */
267  SCIP* scip /**< SCIP data structure */
268  )
269 {
270  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNFeasibleLeaves", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
271 
272  return scip->stat->nfeasleaves;
273 }
274 
275 /** gets number of infeasible leaf nodes processed
276  *
277  * @return number of infeasible leaf nodes processed
278  *
279  * @pre This method can be called if SCIP is in one of the following stages:
280  * - \ref SCIP_STAGE_PROBLEM
281  * - \ref SCIP_STAGE_TRANSFORMING
282  * - \ref SCIP_STAGE_TRANSFORMED
283  * - \ref SCIP_STAGE_INITPRESOLVE
284  * - \ref SCIP_STAGE_PRESOLVING
285  * - \ref SCIP_STAGE_EXITPRESOLVE
286  * - \ref SCIP_STAGE_PRESOLVED
287  * - \ref SCIP_STAGE_INITSOLVE
288  * - \ref SCIP_STAGE_SOLVING
289  * - \ref SCIP_STAGE_SOLVED
290  * - \ref SCIP_STAGE_EXITSOLVE
291  * - \ref SCIP_STAGE_FREETRANS
292  */
294  SCIP* scip /**< SCIP data structure */
295  )
296 {
297  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNInfeasibleLeaves", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
298 
299  return scip->stat->ninfeasleaves;
300 }
301 
302 /** gets number of processed leaf nodes that hit LP objective limit
303  *
304  * @return number of processed leaf nodes that hit LP objective limit
305  *
306  * @pre This method can be called if SCIP is in one of the following stages:
307  * - \ref SCIP_STAGE_PROBLEM
308  * - \ref SCIP_STAGE_TRANSFORMING
309  * - \ref SCIP_STAGE_TRANSFORMED
310  * - \ref SCIP_STAGE_INITPRESOLVE
311  * - \ref SCIP_STAGE_PRESOLVING
312  * - \ref SCIP_STAGE_EXITPRESOLVE
313  * - \ref SCIP_STAGE_PRESOLVED
314  * - \ref SCIP_STAGE_INITSOLVE
315  * - \ref SCIP_STAGE_SOLVING
316  * - \ref SCIP_STAGE_SOLVED
317  * - \ref SCIP_STAGE_EXITSOLVE
318  * - \ref SCIP_STAGE_FREETRANS
319  */
321  SCIP* scip /**< Scip data structure */
322  )
323 {
324  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNObjlimLeaves", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
325 
326  return scip->stat->nobjleaves;
327 }
328 
329 /** gets number of global bound changes
330  *
331  * @return number of global bound changes
332  *
333  * @pre This method can be called if SCIP is in one of the following stages:
334  * - \ref SCIP_STAGE_PROBLEM
335  * - \ref SCIP_STAGE_TRANSFORMING
336  * - \ref SCIP_STAGE_TRANSFORMED
337  * - \ref SCIP_STAGE_INITPRESOLVE
338  * - \ref SCIP_STAGE_PRESOLVING
339  * - \ref SCIP_STAGE_EXITPRESOLVE
340  * - \ref SCIP_STAGE_PRESOLVED
341  * - \ref SCIP_STAGE_INITSOLVE
342  * - \ref SCIP_STAGE_SOLVING
343  * - \ref SCIP_STAGE_SOLVED
344  * - \ref SCIP_STAGE_EXITSOLVE
345  * - \ref SCIP_STAGE_FREETRANS
346  */
348  SCIP* scip /**< Scip data structure */
349  )
350 {
351  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNRootboundChgs", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
352 
353  return scip->stat->nrootboundchgs;
354 }
355 
356 /** gets number of global bound changes applied in the current run
357  *
358  * @return number of global bound changes
359  *
360  * @pre This method can be called if SCIP is in one of the following stages:
361  * - \ref SCIP_STAGE_PROBLEM
362  * - \ref SCIP_STAGE_TRANSFORMING
363  * - \ref SCIP_STAGE_TRANSFORMED
364  * - \ref SCIP_STAGE_INITPRESOLVE
365  * - \ref SCIP_STAGE_PRESOLVING
366  * - \ref SCIP_STAGE_EXITPRESOLVE
367  * - \ref SCIP_STAGE_PRESOLVED
368  * - \ref SCIP_STAGE_INITSOLVE
369  * - \ref SCIP_STAGE_SOLVING
370  * - \ref SCIP_STAGE_SOLVED
371  * - \ref SCIP_STAGE_EXITSOLVE
372  * - \ref SCIP_STAGE_FREETRANS
373  */
375  SCIP* scip /**< Scip data structure */
376  )
377 {
378  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNRootboundChgsRun", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
379 
380  return scip->stat->nrootboundchgsrun;
381 }
382 
383 /** gets number of times a selected node was from a cut off subtree
384  *
385  * @return number of times a selected node was from a cut off subtree
386  *
387  * @pre This method can be called if SCIP is in one of the following stages:
388  * - \ref SCIP_STAGE_PROBLEM
389  * - \ref SCIP_STAGE_TRANSFORMING
390  * - \ref SCIP_STAGE_TRANSFORMED
391  * - \ref SCIP_STAGE_INITPRESOLVE
392  * - \ref SCIP_STAGE_PRESOLVING
393  * - \ref SCIP_STAGE_EXITPRESOLVE
394  * - \ref SCIP_STAGE_PRESOLVED
395  * - \ref SCIP_STAGE_INITSOLVE
396  * - \ref SCIP_STAGE_SOLVING
397  * - \ref SCIP_STAGE_SOLVED
398  * - \ref SCIP_STAGE_EXITSOLVE
399  * - \ref SCIP_STAGE_FREETRANS
400  */
402  SCIP* scip /**< SCIP data structure */
403  )
404 {
405  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNDelayedCutoffs", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
406 
407  return scip->stat->ndelayedcutoffs;
408 }
409 
410 /** gets total number of LPs solved so far
411  *
412  * @return the total number of LPs solved so far
413  *
414  * @pre This method can be called if SCIP is in one of the following stages:
415  * - \ref SCIP_STAGE_PROBLEM
416  * - \ref SCIP_STAGE_TRANSFORMING
417  * - \ref SCIP_STAGE_TRANSFORMED
418  * - \ref SCIP_STAGE_INITPRESOLVE
419  * - \ref SCIP_STAGE_PRESOLVING
420  * - \ref SCIP_STAGE_EXITPRESOLVE
421  * - \ref SCIP_STAGE_PRESOLVED
422  * - \ref SCIP_STAGE_INITSOLVE
423  * - \ref SCIP_STAGE_SOLVING
424  * - \ref SCIP_STAGE_SOLVED
425  * - \ref SCIP_STAGE_EXITSOLVE
426  * - \ref SCIP_STAGE_FREETRANS
427  */
429  SCIP* scip /**< SCIP data structure */
430  )
431 {
432  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNLPs", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
433 
434  return scip->stat->nlps;
435 }
436 
437 /** gets total number of iterations used so far in primal and dual simplex and barrier algorithm
438  *
439  * @return the total number of iterations used so far in primal and dual simplex and barrier algorithm
440  *
441  * @pre This method can be called if SCIP is in one of the following stages:
442  * - \ref SCIP_STAGE_PRESOLVING
443  * - \ref SCIP_STAGE_PRESOLVED
444  * - \ref SCIP_STAGE_SOLVING
445  * - \ref SCIP_STAGE_SOLVED
446  */
448  SCIP* scip /**< SCIP data structure */
449  )
450 {
451  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
452 
453  return scip->stat->nlpiterations;
454 }
455 
456 /** gets number of active non-zeros in the current transformed problem
457  *
458  * @return the number of active non-zeros in the current transformed problem
459  *
460  * @pre This method can be called if SCIP is in one of the following stages:
461  * - \ref SCIP_STAGE_PROBLEM
462  * - \ref SCIP_STAGE_TRANSFORMING
463  * - \ref SCIP_STAGE_TRANSFORMED
464  * - \ref SCIP_STAGE_INITPRESOLVE
465  * - \ref SCIP_STAGE_PRESOLVING
466  * - \ref SCIP_STAGE_EXITPRESOLVE
467  * - \ref SCIP_STAGE_PRESOLVED
468  * - \ref SCIP_STAGE_INITSOLVE
469  * - \ref SCIP_STAGE_SOLVING
470  * - \ref SCIP_STAGE_SOLVED
471  * - \ref SCIP_STAGE_EXITSOLVE
472  */
474  SCIP* scip /**< SCIP data structure */
475  )
476 {
477  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNNZs", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
478 
479  return scip->stat->nnz;
480 }
481 
482 /** gets total number of iterations used so far in primal and dual simplex and barrier algorithm for the root node
483  *
484  * @return the total number of iterations used so far in primal and dual simplex and barrier algorithm for the root node
485  *
486  * @pre This method can be called if SCIP is in one of the following stages:
487  * - \ref SCIP_STAGE_PRESOLVED
488  * - \ref SCIP_STAGE_SOLVING
489  * - \ref SCIP_STAGE_SOLVED
490  */
492  SCIP* scip /**< SCIP data structure */
493  )
494 {
495  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNRootLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
496 
497  return scip->stat->nrootlpiterations;
498 }
499 
500 /** gets total number of iterations used in primal and dual simplex and barrier algorithm for the first LP at the root
501  * node
502  *
503  * @return the total number of iterations used in primal and dual simplex and barrier algorithm for the first root LP
504  *
505  * @pre This method can be called if SCIP is in one of the following stages:
506  * - \ref SCIP_STAGE_PRESOLVED
507  * - \ref SCIP_STAGE_SOLVING
508  * - \ref SCIP_STAGE_SOLVED
509  */
511  SCIP* scip /**< SCIP data structure */
512  )
513 {
514  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNRootFirstLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
515 
516  return scip->stat->nrootfirstlpiterations;
517 }
518 
519 /** gets total number of primal LPs solved so far
520  *
521  * @return the total number of primal LPs solved so far
522  *
523  * @pre This method can be called if SCIP is in one of the following stages:
524  * - \ref SCIP_STAGE_PRESOLVED
525  * - \ref SCIP_STAGE_SOLVING
526  * - \ref SCIP_STAGE_SOLVED
527  */
529  SCIP* scip /**< SCIP data structure */
530  )
531 {
532  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNPrimalLPs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
533 
534  return scip->stat->nprimallps;
535 }
536 
537 /** gets total number of iterations used so far in primal simplex
538  *
539  * @return total number of iterations used so far in primal simplex
540  *
541  * @pre This method can be called if SCIP is in one of the following stages:
542  * - \ref SCIP_STAGE_PRESOLVED
543  * - \ref SCIP_STAGE_SOLVING
544  * - \ref SCIP_STAGE_SOLVED
545  */
547  SCIP* scip /**< SCIP data structure */
548  )
549 {
550  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNPrimalLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
551 
552  return scip->stat->nprimallpiterations;
553 }
554 
555 /** gets total number of dual LPs solved so far
556  *
557  * @return the total number of dual LPs solved so far
558  *
559  * @pre This method can be called if SCIP is in one of the following stages:
560  * - \ref SCIP_STAGE_PRESOLVED
561  * - \ref SCIP_STAGE_SOLVING
562  * - \ref SCIP_STAGE_SOLVED
563  */
565  SCIP* scip /**< SCIP data structure */
566  )
567 {
568  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNDualLPs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
569 
570  return scip->stat->nduallps;
571 }
572 
573 /** gets total number of iterations used so far in dual simplex
574  *
575  * @return the total number of iterations used so far in dual simplex
576  *
577  * @pre This method can be called if SCIP is in one of the following stages:
578  * - \ref SCIP_STAGE_PRESOLVED
579  * - \ref SCIP_STAGE_SOLVING
580  * - \ref SCIP_STAGE_SOLVED
581  */
583  SCIP* scip /**< SCIP data structure */
584  )
585 {
586  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNDualLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
587 
588  return scip->stat->nduallpiterations;
589 }
590 
591 /** gets total number of barrier LPs solved so far
592  *
593  * @return the total number of barrier LPs solved so far
594  *
595  * @pre This method can be called if SCIP is in one of the following stages:
596  * - \ref SCIP_STAGE_PRESOLVED
597  * - \ref SCIP_STAGE_SOLVING
598  * - \ref SCIP_STAGE_SOLVED
599  */
601  SCIP* scip /**< SCIP data structure */
602  )
603 {
604  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNBarrierLPs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
605 
606  return scip->stat->nbarrierlps;
607 }
608 
609 /** gets total number of iterations used so far in barrier algorithm
610  *
611  * @return the total number of iterations used so far in barrier algorithm
612  *
613  * @pre This method can be called if SCIP is in one of the following stages:
614  * - \ref SCIP_STAGE_PRESOLVED
615  * - \ref SCIP_STAGE_SOLVING
616  * - \ref SCIP_STAGE_SOLVED
617  */
619  SCIP* scip /**< SCIP data structure */
620  )
621 {
622  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNBarrierLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
623 
624  return scip->stat->nbarrierlpiterations;
625 }
626 
627 /** gets total number of LPs solved so far that were resolved from an advanced start basis
628  *
629  * @return the total number of LPs solved so far that were resolved from an advanced start basis
630  *
631  * @pre This method can be called if SCIP is in one of the following stages:
632  * - \ref SCIP_STAGE_PRESOLVED
633  * - \ref SCIP_STAGE_SOLVING
634  * - \ref SCIP_STAGE_SOLVED
635  */
637  SCIP* scip /**< SCIP data structure */
638  )
639 {
640  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNResolveLPs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
641 
642  return scip->stat->nprimalresolvelps + scip->stat->ndualresolvelps;
643 }
644 
645 /** gets total number of simplex iterations used so far in primal and dual simplex calls where an advanced start basis
646  * was available
647  *
648  * @return the total number of simplex iterations used so far in primal and dual simplex calls where an advanced start
649  * basis was available
650  *
651  * @pre This method can be called if SCIP is in one of the following stages:
652  * - \ref SCIP_STAGE_PRESOLVED
653  * - \ref SCIP_STAGE_SOLVING
654  * - \ref SCIP_STAGE_SOLVED
655  */
657  SCIP* scip /**< SCIP data structure */
658  )
659 {
660  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNResolveLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
661 
663 }
664 
665 /** gets total number of primal LPs solved so far that were resolved from an advanced start basis
666  *
667  * @return the total number of primal LPs solved so far that were resolved from an advanced start basis
668  *
669  * @pre This method can be called if SCIP is in one of the following stages:
670  * - \ref SCIP_STAGE_PRESOLVED
671  * - \ref SCIP_STAGE_SOLVING
672  * - \ref SCIP_STAGE_SOLVED
673  */
675  SCIP* scip /**< SCIP data structure */
676  )
677 {
678  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNPrimalResolveLPs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
679 
680  return scip->stat->nprimalresolvelps;
681 }
682 
683 /** gets total number of simplex iterations used so far in primal simplex calls where an advanced start basis
684  * was available
685  *
686  * @return the total number of simplex iterations used so far in primal simplex calls where an advanced start
687  * basis was available
688  *
689  * @pre This method can be called if SCIP is in one of the following stages:
690  * - \ref SCIP_STAGE_PRESOLVED
691  * - \ref SCIP_STAGE_SOLVING
692  * - \ref SCIP_STAGE_SOLVED
693  */
695  SCIP* scip /**< SCIP data structure */
696  )
697 {
698  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNPrimalResolveLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
699 
700  return scip->stat->nprimalresolvelpiterations;
701 }
702 
703 /** gets total number of dual LPs solved so far that were resolved from an advanced start basis
704  *
705  * @return the total number of dual LPs solved so far that were resolved from an advanced start basis
706  *
707  * @pre This method can be called if SCIP is in one of the following stages:
708  * - \ref SCIP_STAGE_PRESOLVED
709  * - \ref SCIP_STAGE_SOLVING
710  * - \ref SCIP_STAGE_SOLVED
711  */
713  SCIP* scip /**< SCIP data structure */
714  )
715 {
716  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNDualResolveLPs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
717 
718  return scip->stat->ndualresolvelps;
719 }
720 
721 /** gets total number of simplex iterations used so far in dual simplex calls where an advanced start basis
722  * was available
723  *
724  * @return the total number of simplex iterations used so far in dual simplex calls where an advanced start
725  * basis was available
726  *
727  * @pre This method can be called if SCIP is in one of the following stages:
728  * - \ref SCIP_STAGE_PRESOLVED
729  * - \ref SCIP_STAGE_SOLVING
730  * - \ref SCIP_STAGE_SOLVED
731  */
733  SCIP* scip /**< SCIP data structure */
734  )
735 {
736  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNDualResolveLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
737 
738  return scip->stat->ndualresolvelpiterations;
739 }
740 
741 /** gets total number of LPs solved so far for node relaxations
742  *
743  * @return the total number of LPs solved so far for node relaxations
744  *
745  * @pre This method can be called if SCIP is in one of the following stages:
746  * - \ref SCIP_STAGE_PRESOLVED
747  * - \ref SCIP_STAGE_SOLVING
748  * - \ref SCIP_STAGE_SOLVED
749  */
751  SCIP* scip /**< SCIP data structure */
752  )
753 {
754  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNNodeLPs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
755 
756  return scip->stat->nnodelps;
757 }
758 
759 /** gets total number of LPs solved in 0 iterations for node relaxations
760  *
761  * @return the total number of LPs solved with 0 iteratins for node relaxations
762  *
763  * @pre This method can be called if SCIP is in one of the following stages:
764  * - \ref SCIP_STAGE_PRESOLVED
765  * - \ref SCIP_STAGE_SOLVING
766  * - \ref SCIP_STAGE_SOLVED
767  */
769  SCIP* scip /**< SCIP data structure */
770  )
771 {
772  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNNodeZeroIterationLPs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
773 
774  return scip->stat->nnodezeroitlps;
775 }
776 
777 /** gets total number of simplex iterations used so far for node relaxations
778  *
779  * @return the total number of simplex iterations used so far for node relaxations
780  *
781  * @pre This method can be called if SCIP is in one of the following stages:
782  * - \ref SCIP_STAGE_PRESOLVED
783  * - \ref SCIP_STAGE_SOLVING
784  * - \ref SCIP_STAGE_SOLVED
785  */
787  SCIP* scip /**< SCIP data structure */
788  )
789 {
790  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNNodeLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
791 
792  return scip->stat->nnodelpiterations;
793 }
794 
795 /** gets total number of LPs solved so far for initial LP in node relaxations
796  *
797  * @return the total number of LPs solved so far for initial LP in node relaxations
798  *
799  * @pre This method can be called if SCIP is in one of the following stages:
800  * - \ref SCIP_STAGE_PRESOLVED
801  * - \ref SCIP_STAGE_SOLVING
802  * - \ref SCIP_STAGE_SOLVED
803  */
805  SCIP* scip /**< SCIP data structure */
806  )
807 {
808  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNNodeInitLPs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
809 
810  return scip->stat->ninitlps;
811 }
812 
813 /** gets total number of simplex iterations used so far for initial LP in node relaxations
814  *
815  * @return the total number of simplex iterations used so far for initial LP in node relaxations
816  *
817  * @pre This method can be called if SCIP is in one of the following stages:
818  * - \ref SCIP_STAGE_PRESOLVED
819  * - \ref SCIP_STAGE_SOLVING
820  * - \ref SCIP_STAGE_SOLVED
821  */
823  SCIP* scip /**< SCIP data structure */
824  )
825 {
826  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNNodeInitLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
827 
828  return scip->stat->ninitlpiterations;
829 }
830 
831 /** gets total number of LPs solved so far during diving and probing
832  *
833  * @return total number of LPs solved so far during diving and probing
834  *
835  * @pre This method can be called if SCIP is in one of the following stages:
836  * - \ref SCIP_STAGE_PRESOLVED
837  * - \ref SCIP_STAGE_SOLVING
838  * - \ref SCIP_STAGE_SOLVED
839  */
841  SCIP* scip /**< SCIP data structure */
842  )
843 {
844  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNDivingLPs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
845 
846  return scip->stat->ndivinglps;
847 }
848 
849 /** gets total number of simplex iterations used so far during diving and probing
850  *
851  * @return the total number of simplex iterations used so far during diving and probing
852  *
853  * @pre This method can be called if SCIP is in one of the following stages:
854  * - \ref SCIP_STAGE_PRESOLVED
855  * - \ref SCIP_STAGE_SOLVING
856  * - \ref SCIP_STAGE_SOLVED
857  */
859  SCIP* scip /**< SCIP data structure */
860  )
861 {
862  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNDivingLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
863 
864  return scip->stat->ndivinglpiterations;
865 }
866 
867 /** gets total number of times, strong branching was called (each call represents solving two LPs)
868  *
869  * @return the total number of times, strong branching was called (each call represents solving two LPs)
870  *
871  * @pre This method can be called if SCIP is in one of the following stages:
872  * - \ref SCIP_STAGE_PRESOLVED
873  * - \ref SCIP_STAGE_SOLVING
874  * - \ref SCIP_STAGE_SOLVED
875  */
877  SCIP* scip /**< SCIP data structure */
878  )
879 {
880  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNStrongbranchs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
881 
882  return scip->stat->nstrongbranchs;
883 }
884 
885 /** gets total number of simplex iterations used so far in strong branching
886  *
887  * @return the total number of simplex iterations used so far in strong branching
888  *
889  * @pre This method can be called if SCIP is in one of the following stages:
890  * - \ref SCIP_STAGE_PRESOLVED
891  * - \ref SCIP_STAGE_SOLVING
892  * - \ref SCIP_STAGE_SOLVED
893  */
895  SCIP* scip /**< SCIP data structure */
896  )
897 {
898  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNStrongbranchLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
899 
900  return scip->stat->nsblpiterations;
901 }
902 
903 /** gets total number of times, strong branching was called at the root node (each call represents solving two LPs)
904  *
905  * @return the total number of times, strong branching was called at the root node (each call represents solving two LPs)
906  *
907  * @pre This method can be called if SCIP is in one of the following stages:
908  * - \ref SCIP_STAGE_PRESOLVED
909  * - \ref SCIP_STAGE_SOLVING
910  * - \ref SCIP_STAGE_SOLVED
911  */
913  SCIP* scip /**< SCIP data structure */
914  )
915 {
916  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNRootStrongbranchs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
917 
918  return scip->stat->nrootstrongbranchs;
919 }
920 
921 /** gets total number of simplex iterations used so far in strong branching at the root node
922  *
923  * @return the total number of simplex iterations used so far in strong branching at the root node
924  *
925  * @pre This method can be called if SCIP is in one of the following stages:
926  * - \ref SCIP_STAGE_PRESOLVED
927  * - \ref SCIP_STAGE_SOLVING
928  * - \ref SCIP_STAGE_SOLVED
929  */
931  SCIP* scip /**< SCIP data structure */
932  )
933 {
934  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNRootStrongbranchLPIterations", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
935 
936  return scip->stat->nrootsblpiterations;
937 }
938 
939 /** gets number of pricing rounds performed so far at the current node
940  *
941  * @return the number of pricing rounds performed so far at the current node
942  *
943  * @pre This method can be called if SCIP is in one of the following stages:
944  * - \ref SCIP_STAGE_SOLVING
945  */
947  SCIP* scip /**< SCIP data structure */
948  )
949 {
950  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNPriceRounds", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE) );
951 
952  return scip->stat->npricerounds;
953 }
954 
955 /** get current number of variables in the pricing store
956  *
957  * @return the current number of variables in the pricing store
958  *
959  * @pre This method can be called if SCIP is in one of the following stages:
960  * - \ref SCIP_STAGE_PRESOLVED
961  * - \ref SCIP_STAGE_SOLVING
962  * - \ref SCIP_STAGE_SOLVED
963  */
965  SCIP* scip /**< SCIP data structure */
966  )
967 {
968  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNPricevars", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
969 
970  return scip->pricestore == NULL ? 0 : SCIPpricestoreGetNVars(scip->pricestore);
971 }
972 
973 /** get total number of pricing variables found so far
974  *
975  * @return the total number of pricing variables found so far
976  *
977  * @pre This method can be called if SCIP is in one of the following stages:
978  * - \ref SCIP_STAGE_PRESOLVED
979  * - \ref SCIP_STAGE_SOLVING
980  * - \ref SCIP_STAGE_SOLVED
981  */
983  SCIP* scip /**< SCIP data structure */
984  )
985 {
986  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNPricevarsFound", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
987 
988  return scip->pricestore == NULL ? 0 : SCIPpricestoreGetNVarsFound(scip->pricestore);
989 }
990 
991 /** get total number of pricing variables applied to the LPs
992  *
993  * @return the total number of pricing variables applied to the LPs
994  *
995  * @pre This method can be called if SCIP is in one of the following stages:
996  * - \ref SCIP_STAGE_PRESOLVED
997  * - \ref SCIP_STAGE_SOLVING
998  * - \ref SCIP_STAGE_SOLVED
999  */
1001  SCIP* scip /**< SCIP data structure */
1002  )
1003 {
1004  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNPricevarsApplied", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1005 
1006  return scip->pricestore == NULL ? 0 : SCIPpricestoreGetNVarsApplied(scip->pricestore);
1007 }
1008 
1009 /** gets number of separation rounds performed so far at the current node
1010  *
1011  * @return the number of separation rounds performed so far at the current node
1012  *
1013  * @pre This method can be called if SCIP is in one of the following stages:
1014  * - \ref SCIP_STAGE_SOLVING
1015  */
1017  SCIP* scip /**< SCIP data structure */
1018  )
1019 {
1020  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNSepaRounds", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE) );
1021 
1022  return scip->stat->nseparounds;
1023 }
1024 
1025 /** get total number of cuts added to the sepastore so far; this includes global cuts from the cut pool as often as they are separated
1026  *
1027  * @return the total number of cuts added to the sepastore so far
1028  *
1029  * @pre This method can be called if SCIP is in one of the following stages:
1030  * - \ref SCIP_STAGE_PRESOLVED
1031  * - \ref SCIP_STAGE_SOLVING
1032  * - \ref SCIP_STAGE_SOLVED
1033  */
1035  SCIP* scip /**< SCIP data structure */
1036  )
1037 {
1038  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNCutsFound", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1039 
1040  return scip->sepastore == NULL ? 0 : SCIPsepastoreGetNCutsAdded(scip->sepastore);
1041 }
1042 
1043 /** get number of cuts found so far in current separation round
1044  *
1045  * @return the number of cuts found so far in current separation round
1046  *
1047  * @pre This method can be called if SCIP is in one of the following stages:
1048  * - \ref SCIP_STAGE_PRESOLVED
1049  * - \ref SCIP_STAGE_SOLVING
1050  * - \ref SCIP_STAGE_SOLVED
1051  */
1053  SCIP* scip /**< SCIP data structure */
1054  )
1055 {
1056  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNCutsFoundRound", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1057 
1058  return scip->sepastore == NULL ? 0 : SCIPsepastoreGetNCutsFoundRound(scip->sepastore);
1059 }
1060 
1061 /** get total number of cuts applied to the LPs
1062  *
1063  * @return the total number of cuts applied to the LPs
1064  *
1065  * @pre This method can be called if SCIP is in one of the following stages:
1066  * - \ref SCIP_STAGE_PRESOLVED
1067  * - \ref SCIP_STAGE_SOLVING
1068  * - \ref SCIP_STAGE_SOLVED
1069  */
1071  SCIP* scip /**< SCIP data structure */
1072  )
1073 {
1074  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNCutsApplied", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1075 
1076  return scip->sepastore == NULL ? 0 : SCIPsepastoreGetNCutsApplied(scip->sepastore);
1077 }
1078 
1079 /** get total number of constraints found in conflict analysis (conflict, reconvergence constraints, and dual proofs)
1080  *
1081  * @return the total number of constraints found in conflict analysis (conflict, reconvergence constraints, and dual proofs)
1082  *
1083  * @pre This method can be called if SCIP is in one of the following stages:
1084  * - \ref SCIP_STAGE_TRANSFORMED
1085  * - \ref SCIP_STAGE_INITPRESOLVE
1086  * - \ref SCIP_STAGE_PRESOLVING
1087  * - \ref SCIP_STAGE_EXITPRESOLVE
1088  * - \ref SCIP_STAGE_PRESOLVED
1089  * - \ref SCIP_STAGE_INITSOLVE
1090  * - \ref SCIP_STAGE_SOLVING
1091  * - \ref SCIP_STAGE_SOLVED
1092  * - \ref SCIP_STAGE_EXITSOLVE
1093  */
1095  SCIP* scip /**< SCIP data structure */
1096  )
1097 {
1098  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNConflictConssFound", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1099 
1100  return scip->conflict == NULL ? 0 : (SCIPconflictGetNPropConflictConss(scip->conflict)
1112 }
1113 
1114 /** get number of conflict constraints found so far at the current node
1115  *
1116  * @return the number of conflict constraints found so far at the current node
1117  *
1118  * @pre This method can be called if SCIP is in one of the following stages:
1119  * - \ref SCIP_STAGE_TRANSFORMED
1120  * - \ref SCIP_STAGE_INITPRESOLVE
1121  * - \ref SCIP_STAGE_PRESOLVING
1122  * - \ref SCIP_STAGE_EXITPRESOLVE
1123  * - \ref SCIP_STAGE_PRESOLVED
1124  * - \ref SCIP_STAGE_INITSOLVE
1125  * - \ref SCIP_STAGE_SOLVING
1126  * - \ref SCIP_STAGE_SOLVED
1127  * - \ref SCIP_STAGE_EXITSOLVE
1128  */
1130  SCIP* scip /**< SCIP data structure */
1131  )
1132 {
1133  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNConflictConssFoundNode", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1134 
1135  return scip->conflict == NULL ? 0 : SCIPconflictGetNConflicts(scip->conflict);
1136 }
1137 
1138 /** get total number of conflict constraints added to the problem
1139  *
1140  * @return the total number of conflict constraints added to the problem
1141  *
1142  * @pre This method can be called if SCIP is in one of the following stages:
1143  * - \ref SCIP_STAGE_TRANSFORMED
1144  * - \ref SCIP_STAGE_INITPRESOLVE
1145  * - \ref SCIP_STAGE_PRESOLVING
1146  * - \ref SCIP_STAGE_EXITPRESOLVE
1147  * - \ref SCIP_STAGE_PRESOLVED
1148  * - \ref SCIP_STAGE_INITSOLVE
1149  * - \ref SCIP_STAGE_SOLVING
1150  * - \ref SCIP_STAGE_SOLVED
1151  * - \ref SCIP_STAGE_EXITSOLVE
1152  */
1154  SCIP* scip /**< SCIP data structure */
1155  )
1156 {
1157  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNConflictConssApplied", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1158 
1159  return scip->conflict == NULL ? 0 : SCIPconflictGetNAppliedConss(scip->conflict);
1160 }
1161 
1162 /** get total number of dual proof constraints added to the problem
1163  *
1164  * @return the total number of dual proof constraints added to the problem
1165  *
1166  * @pre This method can be called if SCIP is in one of the following stages:
1167  * - \ref SCIP_STAGE_TRANSFORMED
1168  * - \ref SCIP_STAGE_INITPRESOLVE
1169  * - \ref SCIP_STAGE_PRESOLVING
1170  * - \ref SCIP_STAGE_EXITPRESOLVE
1171  * - \ref SCIP_STAGE_PRESOLVED
1172  * - \ref SCIP_STAGE_INITSOLVE
1173  * - \ref SCIP_STAGE_SOLVING
1174  * - \ref SCIP_STAGE_SOLVED
1175  * - \ref SCIP_STAGE_EXITSOLVE
1176  */
1178  SCIP* scip /**< SCIP data structure */
1179  )
1180 {
1181  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNConflictDualproofsApplied", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1182 
1183  return scip->conflict == NULL ? 0 : (SCIPconflictGetNDualproofsInfSuccess(scip->conflict) +
1185 }
1186 
1187 /** gets maximal depth of all processed nodes in current branch and bound run (excluding probing nodes)
1188  *
1189  * @return the maximal depth of all processed nodes in current branch and bound run (excluding probing nodes)
1190  *
1191  * @pre This method can be called if SCIP is in one of the following stages:
1192  * - \ref SCIP_STAGE_TRANSFORMED
1193  * - \ref SCIP_STAGE_INITPRESOLVE
1194  * - \ref SCIP_STAGE_PRESOLVING
1195  * - \ref SCIP_STAGE_EXITPRESOLVE
1196  * - \ref SCIP_STAGE_PRESOLVED
1197  * - \ref SCIP_STAGE_INITSOLVE
1198  * - \ref SCIP_STAGE_SOLVING
1199  * - \ref SCIP_STAGE_SOLVED
1200  * - \ref SCIP_STAGE_EXITSOLVE
1201  */
1203  SCIP* scip /**< SCIP data structure */
1204  )
1205 {
1206  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetMaxDepth", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1207 
1208  return scip->stat->maxdepth;
1209 }
1210 
1211 /** gets maximal depth of all processed nodes over all branch and bound runs
1212  *
1213  * @return the maximal depth of all processed nodes over all branch and bound runs
1214  *
1215  * @pre This method can be called if SCIP is in one of the following stages:
1216  * - \ref SCIP_STAGE_TRANSFORMED
1217  * - \ref SCIP_STAGE_INITPRESOLVE
1218  * - \ref SCIP_STAGE_PRESOLVING
1219  * - \ref SCIP_STAGE_EXITPRESOLVE
1220  * - \ref SCIP_STAGE_PRESOLVED
1221  * - \ref SCIP_STAGE_INITSOLVE
1222  * - \ref SCIP_STAGE_SOLVING
1223  * - \ref SCIP_STAGE_SOLVED
1224  * - \ref SCIP_STAGE_EXITSOLVE
1225  */
1227  SCIP* scip /**< SCIP data structure */
1228  )
1229 {
1230  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetMaxTotalDepth", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1231 
1232  return scip->stat->maxtotaldepth;
1233 }
1234 
1235 /** gets total number of backtracks, i.e. number of times, the new node was selected from the leaves queue
1236  *
1237  * @return the total number of backtracks, i.e. number of times, the new node was selected from the leaves queue
1238  *
1239  * @pre This method can be called if SCIP is in one of the following stages:
1240  * - \ref SCIP_STAGE_TRANSFORMED
1241  * - \ref SCIP_STAGE_INITPRESOLVE
1242  * - \ref SCIP_STAGE_PRESOLVING
1243  * - \ref SCIP_STAGE_EXITPRESOLVE
1244  * - \ref SCIP_STAGE_PRESOLVED
1245  * - \ref SCIP_STAGE_INITSOLVE
1246  * - \ref SCIP_STAGE_SOLVING
1247  * - \ref SCIP_STAGE_SOLVED
1248  * - \ref SCIP_STAGE_EXITSOLVE
1249  */
1251  SCIP* scip /**< SCIP data structure */
1252  )
1253 {
1254  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNBacktracks", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1255 
1256  return scip->stat->nbacktracks;
1257 }
1258 
1259 /** gets total number of active constraints at the current node
1260  *
1261  * @return the total number of active constraints at the current node
1262  *
1263  * @pre This method can be called if SCIP is in one of the following stages:
1264  * - \ref SCIP_STAGE_INITPRESOLVE
1265  * - \ref SCIP_STAGE_PRESOLVING
1266  * - \ref SCIP_STAGE_EXITPRESOLVE
1267  * - \ref SCIP_STAGE_PRESOLVED
1268  * - \ref SCIP_STAGE_SOLVING
1269  */
1271  SCIP* scip /**< SCIP data structure */
1272  )
1273 {
1274  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNActiveConss", FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE) );
1275 
1276  return scip->stat->nactiveconss;
1277 }
1278 
1279 /** gets total number of enabled constraints at the current node
1280  *
1281  * @return the total number of enabled constraints at the current node
1282  *
1283  * @pre This method can be called if SCIP is in one of the following stages:
1284  * - \ref SCIP_STAGE_PRESOLVED
1285  * - \ref SCIP_STAGE_SOLVING
1286  */
1288  SCIP* scip /**< SCIP data structure */
1289  )
1290 {
1291  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNEnabledConss", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, FALSE, FALSE, FALSE) );
1292 
1293  return scip->stat->nenabledconss;
1294 }
1295 
1296 /** gets average dual bound of all unprocessed nodes for original problem
1297  *
1298  * @return the average dual bound of all unprocessed nodes for original problem
1299  *
1300  * @pre This method can be called if SCIP is in one of the following stages:
1301  * - \ref SCIP_STAGE_PRESOLVED
1302  * - \ref SCIP_STAGE_SOLVING
1303  * - \ref SCIP_STAGE_SOLVED
1304  */
1306  SCIP* scip /**< SCIP data structure */
1307  )
1308 {
1309  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgDualbound", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1310 
1311  return SCIPprobExternObjval(scip->transprob, scip->origprob, scip->set,
1313 }
1314 
1315 /** gets average lower (dual) bound of all unprocessed nodes in transformed problem
1316  *
1317  * @return the average lower (dual) bound of all unprocessed nodes in transformed problem
1318  *
1319  * @pre This method can be called if SCIP is in one of the following stages:
1320  * - \ref SCIP_STAGE_PRESOLVED
1321  * - \ref SCIP_STAGE_SOLVING
1322  * - \ref SCIP_STAGE_SOLVED
1323  */
1325  SCIP* scip /**< SCIP data structure */
1326  )
1327 {
1328  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgLowerbound", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1329 
1330  return SCIPtreeGetAvgLowerbound(scip->tree, scip->primal->cutoffbound);
1331 }
1332 
1333 /** gets global dual bound
1334  *
1335  * @return the global dual bound
1336  *
1337  * @pre This method can be called if SCIP is in one of the following stages:
1338  * - \ref SCIP_STAGE_TRANSFORMED
1339  * - \ref SCIP_STAGE_INITPRESOLVE
1340  * - \ref SCIP_STAGE_PRESOLVING
1341  * - \ref SCIP_STAGE_EXITPRESOLVE
1342  * - \ref SCIP_STAGE_PRESOLVED
1343  * - \ref SCIP_STAGE_INITSOLVE
1344  * - \ref SCIP_STAGE_SOLVING
1345  * - \ref SCIP_STAGE_SOLVED
1346  * - \ref SCIP_STAGE_EXITSOLVE
1347  */
1349  SCIP* scip /**< SCIP data structure */
1350  )
1351 {
1352  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetDualbound", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1353 
1354  /* in case we are in presolving we use the stored dual bound if it exits */
1355  if( scip->set->stage <= SCIP_STAGE_INITSOLVE && scip->transprob->dualbound < SCIP_INVALID )
1356  return scip->transprob->dualbound;
1357 
1358  return SCIPprobExternObjval(scip->transprob, scip->origprob, scip->set, SCIPgetLowerbound(scip));
1359 }
1360 
1361 /** gets global lower (dual) bound in transformed problem
1362  *
1363  * @return the global lower (dual) bound in transformed problem
1364  *
1365  * @pre This method can be called if SCIP is in one of the following stages:
1366  * - \ref SCIP_STAGE_TRANSFORMED
1367  * - \ref SCIP_STAGE_INITPRESOLVE
1368  * - \ref SCIP_STAGE_PRESOLVING
1369  * - \ref SCIP_STAGE_EXITPRESOLVE
1370  * - \ref SCIP_STAGE_PRESOLVED
1371  * - \ref SCIP_STAGE_INITSOLVE
1372  * - \ref SCIP_STAGE_SOLVING
1373  * - \ref SCIP_STAGE_SOLVED
1374  */
1376  SCIP* scip /**< SCIP data structure */
1377  )
1378 {
1379  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetLowerbound", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1380 
1381  if( scip->set->stage <= SCIP_STAGE_INITSOLVE )
1382  return -SCIPinfinity(scip);
1384  {
1385  /* in case we could not prove whether the problem is unbounded or infeasible, we want to terminate with lower
1386  * bound = -inf instead of lower bound = upper bound = +inf also in case we prove that the problem is unbounded,
1387  * it seems to make sense to return with lower bound = -inf, since -infinity is the only valid lower bound
1388  */
1389  return -SCIPinfinity(scip);
1390  }
1391  else if( SCIPgetStatus(scip) == SCIP_STATUS_INFEASIBLE )
1392  {
1393  /* SCIPtreeGetLowerbound() should return +inf in the case of infeasibility, but when infeasibility is detected
1394  * during presolving this does not seem to be the case; hence, we treat this case explicitly
1395  */
1396  return SCIPinfinity(scip);
1397  }
1398  else
1399  {
1400  SCIP_Real treelowerbound;
1401 
1402  /* it may happen that the remaining tree is empty or all open nodes have a lower bound above the cutoff bound, but
1403  * have not yet been cut off, e.g., when the user calls SCIPgetDualbound() in some event handler; in this case,
1404  * the global lower bound is given by the upper bound value
1405  */
1406  treelowerbound = SCIPtreeGetLowerbound(scip->tree, scip->set);
1407 
1408  if( treelowerbound < scip->primal->upperbound)
1409  return treelowerbound;
1410  else
1411  return scip->primal->upperbound;
1412  }
1413 }
1414 
1415 /** gets dual bound of the root node for the original problem
1416  *
1417  * @return the dual bound of the root node for the original problem
1418  *
1419  * @pre This method can be called if SCIP is in one of the following stages:
1420  * - \ref SCIP_STAGE_PRESOLVING
1421  * - \ref SCIP_STAGE_EXITPRESOLVE
1422  * - \ref SCIP_STAGE_PRESOLVED
1423  * - \ref SCIP_STAGE_INITSOLVE
1424  * - \ref SCIP_STAGE_SOLVING
1425  * - \ref SCIP_STAGE_SOLVED
1426  */
1428  SCIP* scip /**< SCIP data structure */
1429  )
1430 {
1431  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetDualboundRoot", FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1432 
1433  if( SCIPsetIsInfinity(scip->set, scip->stat->rootlowerbound) )
1434  return SCIPgetPrimalbound(scip);
1435  else
1436  return SCIPprobExternObjval(scip->transprob, scip->origprob, scip->set, scip->stat->rootlowerbound);
1437 }
1438 
1439 /** gets lower (dual) bound in transformed problem of the root node
1440  *
1441  * @return the lower (dual) bound in transformed problem of the root node
1442  *
1443  * @pre This method can be called if SCIP is in one of the following stages:
1444  * - \ref SCIP_STAGE_PRESOLVING
1445  * - \ref SCIP_STAGE_EXITPRESOLVE
1446  * - \ref SCIP_STAGE_PRESOLVED
1447  * - \ref SCIP_STAGE_INITSOLVE
1448  * - \ref SCIP_STAGE_SOLVING
1449  * - \ref SCIP_STAGE_SOLVED
1450  */
1452  SCIP* scip /**< SCIP data structure */
1453  )
1454 {
1455  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetLowerboundRoot", FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1456 
1457  if( SCIPsetIsInfinity(scip->set, scip->stat->rootlowerbound) )
1458  return SCIPgetUpperbound(scip);
1459  else
1460  return scip->stat->rootlowerbound;
1461 }
1462 
1463 /** gets dual bound for the original problem obtained by the first LP solve at the root node
1464  *
1465  * @return the dual bound for the original problem of the first LP solve at the root node
1466  *
1467  * @pre This method can be called if SCIP is in one of the following stages:
1468  * - \ref SCIP_STAGE_PRESOLVING
1469  * - \ref SCIP_STAGE_EXITPRESOLVE
1470  * - \ref SCIP_STAGE_PRESOLVED
1471  * - \ref SCIP_STAGE_INITSOLVE
1472  * - \ref SCIP_STAGE_SOLVING
1473  * - \ref SCIP_STAGE_SOLVED
1474  */
1476  SCIP* scip /**< SCIP data structure */
1477  )
1478 {
1479  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetFirstLPDualboundRoot", FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1480 
1481  return scip->stat->firstlpdualbound;
1482 }
1483 
1484 /** gets lower (dual) bound in transformed problem obtained by the first LP solve at the root node
1485  *
1486  * @return the lower (dual) bound in transformed problem obtained by first LP solve at the root node
1487  *
1488  * @pre This method can be called if SCIP is in one of the following stages:
1489  * - \ref SCIP_STAGE_PRESOLVING
1490  * - \ref SCIP_STAGE_EXITPRESOLVE
1491  * - \ref SCIP_STAGE_PRESOLVED
1492  * - \ref SCIP_STAGE_INITSOLVE
1493  * - \ref SCIP_STAGE_SOLVING
1494  * - \ref SCIP_STAGE_SOLVED
1495  */
1497  SCIP* scip /**< SCIP data structure */
1498  )
1499 {
1500  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetFirstLPLowerboundRoot", FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1501 
1502  if( scip->stat->firstlpdualbound == SCIP_INVALID ) /*lint !e777*/
1503  return -SCIPinfinity(scip);
1504  else
1505  return SCIPprobInternObjval(scip->transprob, scip->origprob, scip->set, scip->stat->firstlpdualbound);
1506 }
1507 
1508 /** the primal bound of the very first solution */
1510  SCIP* scip /**< SCIP data structure */
1511  )
1512 {
1513  return scip->stat->firstprimalbound;
1514 }
1515 
1516 /** gets global primal bound (objective value of best solution or user objective limit) for the original problem
1517  *
1518  * @return the global primal bound (objective value of best solution or user objective limit) for the original problem
1519  *
1520  * @pre This method can be called if SCIP is in one of the following stages:
1521  * - \ref SCIP_STAGE_TRANSFORMED
1522  * - \ref SCIP_STAGE_INITPRESOLVE
1523  * - \ref SCIP_STAGE_PRESOLVING
1524  * - \ref SCIP_STAGE_EXITPRESOLVE
1525  * - \ref SCIP_STAGE_PRESOLVED
1526  * - \ref SCIP_STAGE_INITSOLVE
1527  * - \ref SCIP_STAGE_SOLVING
1528  * - \ref SCIP_STAGE_SOLVED
1529  * - \ref SCIP_STAGE_EXITSOLVE
1530  */
1532  SCIP* scip /**< SCIP data structure */
1533  )
1534 {
1535  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetPrimalbound", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1536 
1537  return SCIPprobExternObjval(scip->transprob, scip->origprob, scip->set, SCIPgetUpperbound(scip));
1538 }
1539 
1540 /** gets global upper (primal) bound in transformed problem (objective value of best solution or user objective limit)
1541  *
1542  * @return the global upper (primal) bound in transformed problem (objective value of best solution or user objective limit)
1543  *
1544  * @pre This method can be called if SCIP is in one of the following stages:
1545  * - \ref SCIP_STAGE_TRANSFORMED
1546  * - \ref SCIP_STAGE_INITPRESOLVE
1547  * - \ref SCIP_STAGE_PRESOLVING
1548  * - \ref SCIP_STAGE_EXITPRESOLVE
1549  * - \ref SCIP_STAGE_PRESOLVED
1550  * - \ref SCIP_STAGE_INITSOLVE
1551  * - \ref SCIP_STAGE_SOLVING
1552  * - \ref SCIP_STAGE_SOLVED
1553  * - \ref SCIP_STAGE_EXITSOLVE
1554  */
1556  SCIP* scip /**< SCIP data structure */
1557  )
1558 {
1559  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetUpperbound", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1560 
1561  if( SCIPgetStatus(scip) == SCIP_STATUS_UNBOUNDED )
1562  return -SCIPinfinity(scip);
1563  else
1564  return scip->primal->upperbound;
1565 }
1566 
1567 /** gets global cutoff bound in transformed problem: a sub problem with lower bound larger than the cutoff
1568  * cannot contain a better feasible solution; usually, this bound is equal to the upper bound, but if the
1569  * objective value is always integral, the cutoff bound is (nearly) one less than the upper bound;
1570  * additionally, due to objective function domain propagation, the cutoff bound can be further reduced
1571  *
1572  * @return global cutoff bound in transformed problem
1573  *
1574  * @pre This method can be called if SCIP is in one of the following stages:
1575  * - \ref SCIP_STAGE_TRANSFORMED
1576  * - \ref SCIP_STAGE_INITPRESOLVE
1577  * - \ref SCIP_STAGE_PRESOLVING
1578  * - \ref SCIP_STAGE_EXITPRESOLVE
1579  * - \ref SCIP_STAGE_PRESOLVED
1580  * - \ref SCIP_STAGE_INITSOLVE
1581  * - \ref SCIP_STAGE_SOLVING
1582  * - \ref SCIP_STAGE_SOLVED
1583  * - \ref SCIP_STAGE_EXITSOLVE
1584  */
1586  SCIP* scip /**< SCIP data structure */
1587  )
1588 {
1589  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetCutoffbound", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1590 
1591  return scip->primal->cutoffbound;
1592 }
1593 
1594 /** updates the cutoff bound
1595  *
1596  * @return \ref SCIP_OKAY is returned if everything worked. Otherwise a suitable error code is passed. See \ref
1597  * SCIP_Retcode "SCIP_RETCODE" for a complete list of error codes.
1598  *
1599  * @note using this method in the solving stage can lead to an erroneous SCIP solving status; in particular,
1600  * if a solution not respecting the cutoff bound was found before installing a cutoff bound which
1601  * renders the remaining problem infeasible, this solution may be reported as optimal
1602  *
1603  * @pre This method can be called if SCIP is in one of the following stages:
1604  * - \ref SCIP_STAGE_TRANSFORMED
1605  * - \ref SCIP_STAGE_PRESOLVING
1606  * - \ref SCIP_STAGE_PRESOLVED
1607  * - \ref SCIP_STAGE_INITSOLVE
1608  * - \ref SCIP_STAGE_SOLVING
1609  *
1610  * @note the given cutoff bound has to better or equal to known one (SCIPgetCutoffbound())
1611  * @note a given cutoff bound is also used for updating the objective limit, if possible
1612  */
1614  SCIP* scip, /**< SCIP data structure */
1615  SCIP_Real cutoffbound /**< new cutoff bound */
1616  )
1617 {
1618  SCIP_CALL( SCIPcheckStage(scip, "SCIPupdateCutoffbound", FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, FALSE, FALSE, FALSE, FALSE) );
1619 
1620  assert(cutoffbound <= SCIPgetCutoffbound(scip));
1621 
1622  SCIP_CALL( SCIPprimalSetCutoffbound(scip->primal, scip->mem->probmem, scip->set, scip->stat, scip->eventfilter,
1623  scip->eventqueue, scip->transprob, scip->origprob, scip->tree, scip->reopt, scip->lp, cutoffbound, FALSE) );
1624 
1625  return SCIP_OKAY;
1626 }
1627 
1628 
1629 /** returns whether the current primal bound is justified with a feasible primal solution; if not, the primal bound
1630  * was set from the user as objective limit
1631  *
1632  * @return TRUE if the current primal bound is justified with a feasible primal solution, otherwise FALSE
1633  *
1634  * @pre This method can be called if SCIP is in one of the following stages:
1635  * - \ref SCIP_STAGE_TRANSFORMED
1636  * - \ref SCIP_STAGE_INITPRESOLVE
1637  * - \ref SCIP_STAGE_PRESOLVING
1638  * - \ref SCIP_STAGE_EXITPRESOLVE
1639  * - \ref SCIP_STAGE_PRESOLVED
1640  * - \ref SCIP_STAGE_INITSOLVE
1641  * - \ref SCIP_STAGE_SOLVING
1642  * - \ref SCIP_STAGE_SOLVED
1643  * - \ref SCIP_STAGE_EXITSOLVE
1644  */
1646  SCIP* scip /**< SCIP data structure */
1647  )
1648 {
1649  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPisPrimalboundSol", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1650 
1651  return SCIPprimalUpperboundIsSol(scip->primal, scip->set, scip->transprob, scip->origprob);
1652 }
1653 
1654 /** gets current gap |(primalbound - dualbound)/min(|primalbound|,|dualbound|)| if both bounds have same sign,
1655  * or infinity, if they have opposite sign
1656  *
1657  * @return the current gap |(primalbound - dualbound)/min(|primalbound|,|dualbound|)| if both bounds have same sign,
1658  * or infinity, if they have opposite sign
1659  *
1660  * @pre This method can be called if SCIP is in one of the following stages:
1661  * - \ref SCIP_STAGE_PRESOLVING
1662  * - \ref SCIP_STAGE_EXITPRESOLVE
1663  * - \ref SCIP_STAGE_PRESOLVED
1664  * - \ref SCIP_STAGE_INITSOLVE
1665  * - \ref SCIP_STAGE_SOLVING
1666  * - \ref SCIP_STAGE_SOLVED
1667  */
1669  SCIP* scip /**< SCIP data structure */
1670  )
1671 {
1673 
1674  /* in case we could not prove whether the problem is unbounded or infeasible, we want to terminate with gap = +inf;
1675  * if the problem was proven to be unbounded or proven to be infeasible we return gap = 0
1676  */
1677  if( SCIPgetStatus(scip) == SCIP_STATUS_INFORUNBD )
1678  return SCIPsetInfinity(scip->set);
1680  return 0.0;
1681 
1682  /* the lowerbound is infinity, but SCIP may not have updated the status; in this case, the problem was already solved
1683  * so we return gap = 0
1684  */
1685  if( SCIPsetIsInfinity(scip->set, SCIPgetLowerbound(scip)) )
1686  return 0.0;
1687 
1689 }
1690 
1691 /** gets current gap |(upperbound - lowerbound)/min(|upperbound|,|lowerbound|)| in transformed problem if both bounds
1692  * have same sign, or infinity, if they have opposite sign
1693  *
1694  * @return current gap |(upperbound - lowerbound)/min(|upperbound|,|lowerbound|)| in transformed problem if both bounds
1695  * have same sign, or infinity, if they have opposite sign
1696  *
1697  * @pre This method can be called if SCIP is in one of the following stages:
1698  * - \ref SCIP_STAGE_PRESOLVED
1699  * - \ref SCIP_STAGE_SOLVING
1700  * - \ref SCIP_STAGE_SOLVED
1701  */
1703  SCIP* scip /**< SCIP data structure */
1704  )
1705 {
1706  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetTransGap", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1707 
1708  /* in case we could not prove whether the problem is unbounded or infeasible, we want to terminate with gap = +inf;
1709  * if the problem was proven to be unbounded or proven to be infeasible we return gap = 0
1710  */
1711  if( SCIPgetStatus(scip) == SCIP_STATUS_INFORUNBD )
1712  return SCIPsetInfinity(scip->set);
1714  return 0.0;
1715 
1716  /* the lowerbound is infinity, but SCIP may not have updated the status; in this case, the problem was already solved
1717  * so we return gap = 0
1718  */
1719  if( SCIPsetIsInfinity(scip->set, SCIPgetLowerbound(scip)) )
1720  return 0.0;
1721 
1723 }
1724 
1725 /** gets number of feasible primal solutions found so far
1726  *
1727  * @return the number of feasible primal solutions found so far
1728  *
1729  * @pre This method can be called if SCIP is in one of the following stages:
1730  * - \ref SCIP_STAGE_TRANSFORMED
1731  * - \ref SCIP_STAGE_INITPRESOLVE
1732  * - \ref SCIP_STAGE_PRESOLVING
1733  * - \ref SCIP_STAGE_EXITPRESOLVE
1734  * - \ref SCIP_STAGE_PRESOLVED
1735  * - \ref SCIP_STAGE_INITSOLVE
1736  * - \ref SCIP_STAGE_SOLVING
1737  * - \ref SCIP_STAGE_SOLVED
1738  * - \ref SCIP_STAGE_EXITSOLVE
1739  */
1741  SCIP* scip /**< SCIP data structure */
1742  )
1743 {
1744  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNSolsFound", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1745 
1746  return scip->primal->nsolsfound;
1747 }
1748 
1749 /** gets number of feasible primal solutions respecting the objective limit found so far
1750  *
1751  * @return the number of feasible primal solutions respecting the objective limit found so far
1752  *
1753  * @pre This method can be called if SCIP is in one of the following stages:
1754  * - \ref SCIP_STAGE_INIT
1755  * - \ref SCIP_STAGE_PROBLEM
1756  * - \ref SCIP_STAGE_TRANSFORMING
1757  * - \ref SCIP_STAGE_TRANSFORMED
1758  * - \ref SCIP_STAGE_INITPRESOLVE
1759  * - \ref SCIP_STAGE_PRESOLVING
1760  * - \ref SCIP_STAGE_EXITPRESOLVE
1761  * - \ref SCIP_STAGE_PRESOLVED
1762  * - \ref SCIP_STAGE_INITSOLVE
1763  * - \ref SCIP_STAGE_SOLVING
1764  * - \ref SCIP_STAGE_SOLVED
1765  * - \ref SCIP_STAGE_EXITSOLVE
1766  */
1768  SCIP* scip /**< SCIP data structure */
1769  )
1770 {
1772  return 0;
1773 
1774  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNLimSolsFound", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1775 
1776  return scip->primal->nlimsolsfound;
1777 }
1778 
1779 /** gets number of feasible primal solutions found so far, that improved the primal bound at the time they were found
1780  *
1781  * @return the number of feasible primal solutions found so far, that improved the primal bound at the time they were found
1782  *
1783  * @pre This method can be called if SCIP is in one of the following stages:
1784  * - \ref SCIP_STAGE_TRANSFORMED
1785  * - \ref SCIP_STAGE_INITPRESOLVE
1786  * - \ref SCIP_STAGE_PRESOLVING
1787  * - \ref SCIP_STAGE_EXITPRESOLVE
1788  * - \ref SCIP_STAGE_PRESOLVED
1789  * - \ref SCIP_STAGE_INITSOLVE
1790  * - \ref SCIP_STAGE_SOLVING
1791  * - \ref SCIP_STAGE_SOLVED
1792  * - \ref SCIP_STAGE_EXITSOLVE
1793  */
1795  SCIP* scip /**< SCIP data structure */
1796  )
1797 {
1798  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetNBestSolsFound", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, FALSE) );
1799 
1800  return scip->primal->nbestsolsfound;
1801 }
1802 
1803 /** gets the average pseudo cost value for the given direction over all variables
1804  *
1805  * @return the average pseudo cost value for the given direction over all variables
1806  *
1807  * @pre This method can be called if SCIP is in one of the following stages:
1808  * - \ref SCIP_STAGE_SOLVING
1809  * - \ref SCIP_STAGE_SOLVED
1810  */
1812  SCIP* scip, /**< SCIP data structure */
1813  SCIP_Real solvaldelta /**< difference of variable's new LP value - old LP value */
1814  )
1815 {
1816  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgPseudocost", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1817 
1818  return SCIPhistoryGetPseudocost(scip->stat->glbhistory, solvaldelta);
1819 }
1820 
1821 /** gets the average pseudo cost value for the given direction over all variables,
1822  * only using the pseudo cost information of the current run
1823  *
1824  * @return the average pseudo cost value for the given direction over all variables,
1825  * only using the pseudo cost information of the current run
1826  *
1827  * @pre This method can be called if SCIP is in one of the following stages:
1828  * - \ref SCIP_STAGE_SOLVING
1829  * - \ref SCIP_STAGE_SOLVED
1830  */
1832  SCIP* scip, /**< SCIP data structure */
1833  SCIP_Real solvaldelta /**< difference of variable's new LP value - old LP value */
1834  )
1835 {
1836  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgPseudocostCurrentRun", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1837 
1838  return SCIPhistoryGetPseudocost(scip->stat->glbhistorycrun, solvaldelta);
1839 }
1840 
1841 /** gets the average number of pseudo cost updates for the given direction over all variables
1842  *
1843  * @return the average number of pseudo cost updates for the given direction over all variables
1844  *
1845  * @pre This method can be called if SCIP is in one of the following stages:
1846  * - \ref SCIP_STAGE_SOLVING
1847  * - \ref SCIP_STAGE_SOLVED
1848  */
1850  SCIP* scip, /**< SCIP data structure */
1851  SCIP_BRANCHDIR dir /**< branching direction (downwards, or upwards) */
1852  )
1853 {
1854  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgPseudocostCount", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1855 
1856  return SCIPhistoryGetPseudocostCount(scip->stat->glbhistory, dir)
1857  / MAX(scip->transprob->nbinvars + scip->transprob->nintvars, 1);
1858 }
1859 
1860 /** gets the average number of pseudo cost updates for the given direction over all variables,
1861  * only using the pseudo cost information of the current run
1862  *
1863  * @return the average number of pseudo cost updates for the given direction over all variables,
1864  * only using the pseudo cost information of the current run
1865  *
1866  * @pre This method can be called if SCIP is in one of the following stages:
1867  * - \ref SCIP_STAGE_SOLVING
1868  * - \ref SCIP_STAGE_SOLVED
1869  */
1871  SCIP* scip, /**< SCIP data structure */
1872  SCIP_BRANCHDIR dir /**< branching direction (downwards, or upwards) */
1873  )
1874 {
1875  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgPseudocostCountCurrentRun", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1876 
1878  / MAX(scip->transprob->nbinvars + scip->transprob->nintvars, 1);
1879 }
1880 
1881 /** gets the average pseudo cost score value over all variables, assuming a fractionality of 0.5
1882  *
1883  * @return the average pseudo cost score value over all variables, assuming a fractionality of 0.5
1884  *
1885  * @pre This method can be called if SCIP is in one of the following stages:
1886  * - \ref SCIP_STAGE_SOLVING
1887  * - \ref SCIP_STAGE_SOLVED
1888  */
1890  SCIP* scip /**< SCIP data structure */
1891  )
1892 {
1893  SCIP_Real pscostdown;
1894  SCIP_Real pscostup;
1895 
1896  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgPseudocostScore", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1897 
1898  pscostdown = SCIPhistoryGetPseudocost(scip->stat->glbhistory, -0.5);
1899  pscostup = SCIPhistoryGetPseudocost(scip->stat->glbhistory, +0.5);
1900 
1901  return SCIPbranchGetScore(scip->set, NULL, pscostdown, pscostup);
1902 }
1903 
1904 /** returns the variance of pseudo costs for all variables in the requested direction
1905  *
1906  * @return the variance of pseudo costs for all variables in the requested direction
1907  *
1908  * @pre This method can be called if SCIP is in one of the following stages:
1909  * - \ref SCIP_STAGE_SOLVING
1910  * - \ref SCIP_STAGE_SOLVED
1911  */
1913  SCIP* scip, /**< SCIP data structure */
1914  SCIP_BRANCHDIR branchdir, /**< the branching direction, up or down */
1915  SCIP_Bool onlycurrentrun /**< use only history of current run? */
1916  )
1917 {
1918  SCIP_HISTORY* history;
1919 
1920  assert(scip != NULL);
1921  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetPseudocostVariance", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1922 
1923  history = (onlycurrentrun ? scip->stat->glbhistorycrun : scip->stat->glbhistory);
1924  assert(history != NULL);
1925 
1926  return SCIPhistoryGetPseudocostVariance(history, branchdir);
1927 }
1928 
1929 /** gets the number of pseudo cost updates for the given direction over all variables
1930  *
1931  * @return the number of pseudo cost updates for the given direction over all variables
1932  *
1933  * @pre This method can be called if SCIP is in one of the following stages:
1934  * - \ref SCIP_STAGE_SOLVING
1935  * - \ref SCIP_STAGE_SOLVED
1936  */
1938  SCIP* scip, /**< SCIP data structure */
1939  SCIP_BRANCHDIR dir, /**< branching direction (downwards, or upwards) */
1940  SCIP_Bool onlycurrentrun /**< use only history of current run? */
1941  )
1942 {
1943  SCIP_HISTORY* history;
1944 
1945  assert(scip != NULL);
1946  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetPseudocostCount", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1947 
1948  history = (onlycurrentrun ? scip->stat->glbhistorycrun : scip->stat->glbhistory);
1949 
1950  return SCIPhistoryGetPseudocostCount(history, dir);
1951 }
1952 
1953 /** gets the average pseudo cost score value over all variables, assuming a fractionality of 0.5,
1954  * only using the pseudo cost information of the current run
1955  *
1956  * @return the average pseudo cost score value over all variables, assuming a fractionality of 0.5,
1957  * only using the pseudo cost information of the current run
1958  *
1959  * @pre This method can be called if SCIP is in one of the following stages:
1960  * - \ref SCIP_STAGE_SOLVING
1961  * - \ref SCIP_STAGE_SOLVED
1962  */
1964  SCIP* scip /**< SCIP data structure */
1965  )
1966 {
1967  SCIP_Real pscostdown;
1968  SCIP_Real pscostup;
1969 
1970  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgPseudocostScoreCurrentRun", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1971 
1972  pscostdown = SCIPhistoryGetPseudocost(scip->stat->glbhistorycrun, -0.5);
1973  pscostup = SCIPhistoryGetPseudocost(scip->stat->glbhistorycrun, +0.5);
1974 
1975  return SCIPbranchGetScore(scip->set, NULL, pscostdown, pscostup);
1976 }
1977 
1978 /** gets the average conflict score value over all variables
1979  *
1980  * @return the average conflict score value over all variables
1981  *
1982  * @pre This method can be called if SCIP is in one of the following stages:
1983  * - \ref SCIP_STAGE_SOLVING
1984  * - \ref SCIP_STAGE_SOLVED
1985  */
1987  SCIP* scip /**< SCIP data structure */
1988  )
1989 {
1990  SCIP_Real conflictscoredown;
1991  SCIP_Real conflictscoreup;
1992  SCIP_Real scale;
1993 
1994  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgConflictScore", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
1995 
1996  scale = scip->transprob->nvars * scip->stat->vsidsweight;
1997  conflictscoredown = SCIPhistoryGetVSIDS(scip->stat->glbhistory, SCIP_BRANCHDIR_DOWNWARDS) / scale;
1998  conflictscoreup = SCIPhistoryGetVSIDS(scip->stat->glbhistory, SCIP_BRANCHDIR_UPWARDS) / scale;
1999 
2000  return SCIPbranchGetScore(scip->set, NULL, conflictscoredown, conflictscoreup);
2001 }
2002 
2003 /** gets the average conflict score value over all variables, only using the conflict score information of the current run
2004  *
2005  * @return the average conflict score value over all variables, only using the conflict score information of the current run
2006  *
2007  * @pre This method can be called if SCIP is in one of the following stages:
2008  * - \ref SCIP_STAGE_SOLVING
2009  * - \ref SCIP_STAGE_SOLVED
2010  */
2012  SCIP* scip /**< SCIP data structure */
2013  )
2014 {
2015  SCIP_Real conflictscoredown;
2016  SCIP_Real conflictscoreup;
2017  SCIP_Real scale;
2018 
2019  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgConflictScoreCurrentRun", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2020 
2021  scale = scip->transprob->nvars * scip->stat->vsidsweight;
2022  conflictscoredown = SCIPhistoryGetVSIDS(scip->stat->glbhistorycrun, SCIP_BRANCHDIR_DOWNWARDS) / scale;
2023  conflictscoreup = SCIPhistoryGetVSIDS(scip->stat->glbhistorycrun, SCIP_BRANCHDIR_UPWARDS) / scale;
2024 
2025  return SCIPbranchGetScore(scip->set, NULL, conflictscoredown, conflictscoreup);
2026 }
2027 
2028 /** gets the average inference score value over all variables
2029  *
2030  * @return the average inference score value over all variables
2031  *
2032  * @pre This method can be called if SCIP is in one of the following stages:
2033  * - \ref SCIP_STAGE_SOLVING
2034  * - \ref SCIP_STAGE_SOLVED
2035  */
2037  SCIP* scip /**< SCIP data structure */
2038  )
2039 {
2040  SCIP_Real conflictlengthdown;
2041  SCIP_Real conflictlengthup;
2042 
2043  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgConflictlengthScore", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2044 
2047 
2048  return SCIPbranchGetScore(scip->set, NULL, conflictlengthdown, conflictlengthup);
2049 }
2050 
2051 /** gets the average conflictlength score value over all variables, only using the conflictlength information of the
2052  * current run
2053  *
2054  * @return the average conflictlength score value over all variables, only using the conflictlength information of the
2055  * current run
2056  *
2057  * @pre This method can be called if SCIP is in one of the following stages:
2058  * - \ref SCIP_STAGE_SOLVING
2059  * - \ref SCIP_STAGE_SOLVED
2060  */
2062  SCIP* scip /**< SCIP data structure */
2063  )
2064 {
2065  SCIP_Real conflictlengthdown;
2066  SCIP_Real conflictlengthup;
2067 
2068  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgConflictlengthScoreCurrentRun", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2069 
2072 
2073  return SCIPbranchGetScore(scip->set, NULL, conflictlengthdown, conflictlengthup);
2074 }
2075 
2076 /** returns the average number of inferences found after branching in given direction over all variables
2077  *
2078  * @return the average number of inferences found after branching in given direction over all variables
2079  *
2080  * @pre This method can be called if SCIP is in one of the following stages:
2081  * - \ref SCIP_STAGE_SOLVING
2082  * - \ref SCIP_STAGE_SOLVED
2083  */
2085  SCIP* scip, /**< SCIP data structure */
2086  SCIP_BRANCHDIR dir /**< branching direction (downwards, or upwards) */
2087  )
2088 {
2089  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgInferences", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2090 
2091  return SCIPhistoryGetAvgInferences(scip->stat->glbhistory, dir);
2092 }
2093 
2094 /** returns the average number of inferences found after branching in given direction over all variables,
2095  * only using the inference information of the current run
2096  *
2097  * @return the average number of inferences found after branching in given direction over all variables,
2098  * only using the inference information of the current run
2099  *
2100  * @pre This method can be called if SCIP is in one of the following stages:
2101  * - \ref SCIP_STAGE_SOLVING
2102  * - \ref SCIP_STAGE_SOLVED
2103  */
2105  SCIP* scip, /**< SCIP data structure */
2106  SCIP_BRANCHDIR dir /**< branching direction (downwards, or upwards) */
2107  )
2108 {
2109  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgInferencesCurrentRun", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2110 
2111  return SCIPhistoryGetAvgInferences(scip->stat->glbhistorycrun, dir);
2112 }
2113 
2114 /** gets the average inference score value over all variables
2115  *
2116  * @return the average inference score value over all variables
2117  *
2118  * @pre This method can be called if SCIP is in one of the following stages:
2119  * - \ref SCIP_STAGE_SOLVING
2120  * - \ref SCIP_STAGE_SOLVED
2121  */
2123  SCIP* scip /**< SCIP data structure */
2124  )
2125 {
2126  SCIP_Real inferencesdown;
2127  SCIP_Real inferencesup;
2128 
2129  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgInferenceScore", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2130 
2133 
2134  return SCIPbranchGetScore(scip->set, NULL, inferencesdown, inferencesup);
2135 }
2136 
2137 /** gets the average inference score value over all variables, only using the inference information of the
2138  * current run
2139  *
2140  * @return the average inference score value over all variables, only using the inference information of the
2141  * current run
2142  *
2143  * @pre This method can be called if SCIP is in one of the following stages:
2144  * - \ref SCIP_STAGE_SOLVING
2145  * - \ref SCIP_STAGE_SOLVED
2146  */
2148  SCIP* scip /**< SCIP data structure */
2149  )
2150 {
2151  SCIP_Real inferencesdown;
2152  SCIP_Real inferencesup;
2153 
2154  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgInferenceScoreCurrentRun", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2155 
2158 
2159  return SCIPbranchGetScore(scip->set, NULL, inferencesdown, inferencesup);
2160 }
2161 
2162 /** returns the average number of cutoffs found after branching in given direction over all variables
2163  *
2164  * @return the average number of cutoffs found after branching in given direction over all variables
2165  *
2166  * @pre This method can be called if SCIP is in one of the following stages:
2167  * - \ref SCIP_STAGE_SOLVING
2168  * - \ref SCIP_STAGE_SOLVED
2169  */
2171  SCIP* scip, /**< SCIP data structure */
2172  SCIP_BRANCHDIR dir /**< branching direction (downwards, or upwards) */
2173  )
2174 {
2175  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgCutoffs", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2176 
2177  return SCIPhistoryGetAvgCutoffs(scip->stat->glbhistory, dir);
2178 }
2179 
2180 /** returns the average number of cutoffs found after branching in given direction over all variables,
2181  * only using the cutoff information of the current run
2182  *
2183  * @return the average number of cutoffs found after branching in given direction over all variables,
2184  * only using the cutoff information of the current run
2185  *
2186  * @pre This method can be called if SCIP is in one of the following stages:
2187  * - \ref SCIP_STAGE_SOLVING
2188  * - \ref SCIP_STAGE_SOLVED
2189  */
2191  SCIP* scip, /**< SCIP data structure */
2192  SCIP_BRANCHDIR dir /**< branching direction (downwards, or upwards) */
2193  )
2194 {
2195  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgCutoffsCurrentRun", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2196 
2197  return SCIPhistoryGetAvgCutoffs(scip->stat->glbhistorycrun, dir);
2198 }
2199 
2200 /** gets the average cutoff score value over all variables
2201  *
2202  * @return the average cutoff score value over all variables
2203  *
2204  * @pre This method can be called if SCIP is in one of the following stages:
2205  * - \ref SCIP_STAGE_SOLVING
2206  * - \ref SCIP_STAGE_SOLVED
2207  */
2209  SCIP* scip /**< SCIP data structure */
2210  )
2211 {
2212  SCIP_Real cutoffsdown;
2213  SCIP_Real cutoffsup;
2214 
2215  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgCutoffScore", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2216 
2219 
2220  return SCIPbranchGetScore(scip->set, NULL, cutoffsdown, cutoffsup);
2221 }
2222 
2223 /** gets the average cutoff score value over all variables, only using the cutoff score information of the current run
2224  *
2225  * @return the average cutoff score value over all variables, only using the cutoff score information of the current run
2226  *
2227  * @pre This method can be called if SCIP is in one of the following stages:
2228  * - \ref SCIP_STAGE_SOLVING
2229  * - \ref SCIP_STAGE_SOLVED
2230  */
2232  SCIP* scip /**< SCIP data structure */
2233  )
2234 {
2235  SCIP_Real cutoffsdown;
2236  SCIP_Real cutoffsup;
2237 
2238  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetAvgCutoffScoreCurrentRun", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2239 
2242 
2243  return SCIPbranchGetScore(scip->set, NULL, cutoffsdown, cutoffsup);
2244 }
2245 
2246 /** computes a deterministic measure of time from statistics
2247  *
2248  * @return the deterministic time
2249  *
2250  * @pre This method can be called if SCIP is in one of the following stages:
2251  * - \ref SCIP_STAGE_PRESOLVING
2252  * - \ref SCIP_STAGE_PRESOLVED
2253  * - \ref SCIP_STAGE_SOLVING
2254  * - \ref SCIP_STAGE_SOLVED
2255  */
2257  SCIP* scip /**< SCIP data structure */
2258  )
2259 {
2260 /* TODO: SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPgetDeterministicTime", FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, FALSE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) ); */
2261  if(scip->stat == NULL)
2262  return 0.0;
2263 
2264  return 1e-6 * scip->stat->nnz * (
2265  0.00328285264101 * scip->stat->nprimalresolvelpiterations +
2266  0.00531625104146 * scip->stat->ndualresolvelpiterations +
2267  0.000738719124051 * scip->stat->nprobboundchgs +
2268  0.0011123144764 * scip->stat->nisstoppedcalls );
2269 }
2270 
2271 /** outputs problem to file stream */
2272 static
2274  SCIP* scip, /**< SCIP data structure */
2275  SCIP_PROB* prob, /**< problem data */
2276  FILE* file, /**< output file (or NULL for standard output) */
2277  const char* extension, /**< file format (or NULL for default CIP format) */
2278  SCIP_Bool genericnames /**< using generic variable and constraint names? */
2279  )
2280 {
2281  SCIP_RESULT result;
2282  int i;
2283  assert(scip != NULL);
2284  assert(prob != NULL);
2285 
2286  /* try all readers until one could read the file */
2287  result = SCIP_DIDNOTRUN;
2288  for( i = 0; i < scip->set->nreaders && result == SCIP_DIDNOTRUN; ++i )
2289  {
2290  SCIP_RETCODE retcode;
2291 
2292  if( extension != NULL )
2293  retcode = SCIPreaderWrite(scip->set->readers[i], prob, scip->set, file, extension, genericnames, &result);
2294  else
2295  retcode = SCIPreaderWrite(scip->set->readers[i], prob, scip->set, file, "cip", genericnames, &result);
2296 
2297  /* check for reader errors */
2298  if( retcode == SCIP_WRITEERROR )
2299  return retcode;
2300 
2301  SCIP_CALL( retcode );
2302  }
2303 
2304  switch( result )
2305  {
2306  case SCIP_DIDNOTRUN:
2307  return SCIP_PLUGINNOTFOUND;
2308 
2309  case SCIP_SUCCESS:
2310  return SCIP_OKAY;
2311 
2312  default:
2313  assert(i < scip->set->nreaders);
2314  SCIPerrorMessage("invalid result code <%d> from reader <%s> writing <%s> format\n",
2315  result, SCIPreaderGetName(scip->set->readers[i]), extension);
2316  return SCIP_READERROR;
2317  } /*lint !e788*/
2318 }
2319 
2320 /** outputs original problem to file stream
2321  *
2322  * @return \ref SCIP_OKAY is returned if everything worked. Otherwise a suitable error code is passed. See \ref
2323  * SCIP_Retcode "SCIP_RETCODE" for a complete list of error codes.
2324  *
2325  * @pre This method can be called if SCIP is in one of the following stages:
2326  * - \ref SCIP_STAGE_PROBLEM
2327  * - \ref SCIP_STAGE_TRANSFORMING
2328  * - \ref SCIP_STAGE_TRANSFORMED
2329  * - \ref SCIP_STAGE_INITPRESOLVE
2330  * - \ref SCIP_STAGE_PRESOLVING
2331  * - \ref SCIP_STAGE_EXITPRESOLVE
2332  * - \ref SCIP_STAGE_PRESOLVED
2333  * - \ref SCIP_STAGE_INITSOLVE
2334  * - \ref SCIP_STAGE_SOLVING
2335  * - \ref SCIP_STAGE_SOLVED
2336  * - \ref SCIP_STAGE_EXITSOLVE
2337  * - \ref SCIP_STAGE_FREETRANS
2338  */
2340  SCIP* scip, /**< SCIP data structure */
2341  FILE* file, /**< output file (or NULL for standard output) */
2342  const char* extension, /**< file format (or NULL for default CIP format)*/
2343  SCIP_Bool genericnames /**< using generic variable and constraint names? */
2344  )
2345 {
2346  SCIP_RETCODE retcode;
2347 
2348  SCIP_CALL( SCIPcheckStage(scip, "SCIPprintOrigProblem", FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
2349 
2350  assert(scip != NULL);
2351  assert( scip->origprob != NULL );
2352 
2353  retcode = printProblem(scip, scip->origprob, file, extension, genericnames);
2354 
2355  /* check for write errors */
2356  if( retcode == SCIP_WRITEERROR || retcode == SCIP_PLUGINNOTFOUND )
2357  return retcode;
2358  else
2359  {
2360  SCIP_CALL( retcode );
2361  }
2362 
2363  return SCIP_OKAY;
2364 }
2365 
2366 /** outputs transformed problem of the current node to file stream
2367  *
2368  * @return \ref SCIP_OKAY is returned if everything worked. Otherwise a suitable error code is passed. See \ref
2369  * SCIP_Retcode "SCIP_RETCODE" for a complete list of error codes.
2370  *
2371  * @pre This method can be called if SCIP is in one of the following stages:
2372  * - \ref SCIP_STAGE_TRANSFORMED
2373  * - \ref SCIP_STAGE_INITPRESOLVE
2374  * - \ref SCIP_STAGE_PRESOLVING
2375  * - \ref SCIP_STAGE_EXITPRESOLVE
2376  * - \ref SCIP_STAGE_PRESOLVED
2377  * - \ref SCIP_STAGE_INITSOLVE
2378  * - \ref SCIP_STAGE_SOLVING
2379  * - \ref SCIP_STAGE_SOLVED
2380  * - \ref SCIP_STAGE_EXITSOLVE
2381  * - \ref SCIP_STAGE_FREETRANS
2382  */
2384  SCIP* scip, /**< SCIP data structure */
2385  FILE* file, /**< output file (or NULL for standard output) */
2386  const char* extension, /**< file format (or NULL for default CIP format)*/
2387  SCIP_Bool genericnames /**< using generic variable and constraint names? */
2388  )
2389 {
2390  SCIP_RETCODE retcode;
2391 
2392  SCIP_CALL( SCIPcheckStage(scip, "SCIPprintTransProblem", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE) );
2393 
2394  assert(scip != NULL);
2395  assert(scip->transprob != NULL );
2396 
2397  retcode = printProblem(scip, scip->transprob, file, extension, genericnames);
2398 
2399  /* check for write errors */
2400  if( retcode == SCIP_WRITEERROR || retcode == SCIP_PLUGINNOTFOUND )
2401  return retcode;
2402  else
2403  {
2404  SCIP_CALL( retcode );
2405  }
2406 
2407  return SCIP_OKAY;
2408 }
2409 
2410 /** outputs status statistics
2411  *
2412  * @note If limits have been changed between the solution and the call to this function, the status is recomputed and
2413  * thus may to correspond to the original status.
2414  *
2415  * @pre This method can be called if SCIP is in one of the following stages:
2416  * - \ref SCIP_STAGE_INIT
2417  * - \ref SCIP_STAGE_PROBLEM
2418  * - \ref SCIP_STAGE_TRANSFORMED
2419  * - \ref SCIP_STAGE_INITPRESOLVE
2420  * - \ref SCIP_STAGE_PRESOLVING
2421  * - \ref SCIP_STAGE_EXITPRESOLVE
2422  * - \ref SCIP_STAGE_PRESOLVED
2423  * - \ref SCIP_STAGE_SOLVING
2424  * - \ref SCIP_STAGE_SOLVED
2425  */
2427  SCIP* scip, /**< SCIP data structure */
2428  FILE* file /**< output file */
2429  )
2430 {
2431  assert(scip != NULL);
2432  assert(scip->set != NULL);
2433 
2434  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintStatusStatistics", TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2435 
2436  SCIPmessageFPrintInfo(scip->messagehdlr, file, "SCIP Status : ");
2437  SCIP_CALL_ABORT( SCIPprintStage(scip, file) );
2438  SCIPmessageFPrintInfo(scip->messagehdlr, file, "\n");
2439 }
2440 
2441 /** outputs statistics for original problem
2442  *
2443  * @pre This method can be called if SCIP is in one of the following stages:
2444  * - \ref SCIP_STAGE_PROBLEM
2445  * - \ref SCIP_STAGE_TRANSFORMED
2446  * - \ref SCIP_STAGE_INITPRESOLVE
2447  * - \ref SCIP_STAGE_PRESOLVING
2448  * - \ref SCIP_STAGE_EXITPRESOLVE
2449  * - \ref SCIP_STAGE_PRESOLVED
2450  * - \ref SCIP_STAGE_SOLVING
2451  * - \ref SCIP_STAGE_SOLVED
2452  */
2454  SCIP* scip, /**< SCIP data structure */
2455  FILE* file /**< output file */
2456  )
2457 {
2458  assert(scip != NULL);
2459  assert(scip->set != NULL);
2460 
2461  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintOrigProblemStatistics", FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2462 
2463  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Original Problem :\n");
2464  SCIPprobPrintStatistics(scip->origprob, scip->set, scip->messagehdlr, file);
2465 }
2466 
2467 /** outputs statistics for transformed problem
2468  *
2469  * @pre This method can be called if SCIP is in one of the following stages:
2470  * - \ref SCIP_STAGE_PROBLEM
2471  * - \ref SCIP_STAGE_TRANSFORMED
2472  * - \ref SCIP_STAGE_INITPRESOLVE
2473  * - \ref SCIP_STAGE_PRESOLVING
2474  * - \ref SCIP_STAGE_EXITPRESOLVE
2475  * - \ref SCIP_STAGE_PRESOLVED
2476  * - \ref SCIP_STAGE_SOLVING
2477  * - \ref SCIP_STAGE_SOLVED
2478  */
2480  SCIP* scip, /**< SCIP data structure */
2481  FILE* file /**< output file */
2482  )
2483 {
2484  assert(scip != NULL);
2485  assert(scip->set != NULL);
2486 
2487  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintTransProblemStatistics", FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2488 
2489  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Presolved Problem :\n");
2490  SCIPprobPrintStatistics(scip->transprob, scip->set, scip->messagehdlr, file);
2491  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Nonzeros : %" SCIP_LONGINT_FORMAT " constraint, %" SCIP_LONGINT_FORMAT " clique table\n",
2493 }
2494 
2495 /** outputs presolver statistics
2496  *
2497  * @pre This method can be called if SCIP is in one of the following stages:
2498  * - \ref SCIP_STAGE_TRANSFORMED
2499  * - \ref SCIP_STAGE_INITPRESOLVE
2500  * - \ref SCIP_STAGE_PRESOLVING
2501  * - \ref SCIP_STAGE_EXITPRESOLVE
2502  * - \ref SCIP_STAGE_PRESOLVED
2503  * - \ref SCIP_STAGE_SOLVING
2504  * - \ref SCIP_STAGE_SOLVED
2505  */
2507  SCIP* scip, /**< SCIP data structure */
2508  FILE* file /**< output file */
2509  )
2510 {
2511  int i;
2512 
2513  assert(scip != NULL);
2514  assert(scip->set != NULL);
2515 
2516  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintPresolverStatistics", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2517 
2518  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Presolvers : ExecTime SetupTime Calls FixedVars AggrVars ChgTypes ChgBounds AddHoles DelCons AddCons ChgSides ChgCoefs\n");
2519 
2520  /* sort presolvers w.r.t. their name */
2521  SCIPsetSortPresolsName(scip->set);
2522 
2523  /* presolver statistics */
2524  for( i = 0; i < scip->set->npresols; ++i )
2525  {
2526  SCIP_PRESOL* presol;
2527  presol = scip->set->presols[i];
2528  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s:", SCIPpresolGetName(presol));
2529  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f %10.2f %6d %10d %10d %10d %10d %10d %10d %10d %10d %10d\n",
2530  SCIPpresolGetTime(presol),
2531  SCIPpresolGetSetupTime(presol),
2532  SCIPpresolGetNCalls(presol),
2533  SCIPpresolGetNFixedVars(presol),
2534  SCIPpresolGetNAggrVars(presol),
2535  SCIPpresolGetNChgVarTypes(presol),
2536  SCIPpresolGetNChgBds(presol),
2537  SCIPpresolGetNAddHoles(presol),
2538  SCIPpresolGetNDelConss(presol),
2539  SCIPpresolGetNAddConss(presol),
2540  SCIPpresolGetNChgSides(presol),
2541  SCIPpresolGetNChgCoefs(presol));
2542  }
2543 
2544  /* sort propagators w.r.t. their name */
2545  SCIPsetSortPropsName(scip->set);
2546 
2547  for( i = 0; i < scip->set->nprops; ++i )
2548  {
2549  SCIP_PROP* prop;
2550  prop = scip->set->props[i];
2551  if( SCIPpropDoesPresolve(prop) )
2552  {
2553  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s:", SCIPpropGetName(prop));
2554  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f %10.2f %6d %10d %10d %10d %10d %10d %10d %10d %10d %10d\n",
2555  SCIPpropGetPresolTime(prop),
2556  SCIPpropGetSetupTime(prop),
2558  SCIPpropGetNFixedVars(prop),
2559  SCIPpropGetNAggrVars(prop),
2561  SCIPpropGetNChgBds(prop),
2562  SCIPpropGetNAddHoles(prop),
2563  SCIPpropGetNDelConss(prop),
2564  SCIPpropGetNAddConss(prop),
2565  SCIPpropGetNChgSides(prop),
2566  SCIPpropGetNChgCoefs(prop));
2567  }
2568  }
2569 
2570  /* constraint handler presolving methods statistics */
2571  for( i = 0; i < scip->set->nconshdlrs; ++i )
2572  {
2573  SCIP_CONSHDLR* conshdlr;
2574  int maxnactiveconss;
2575 
2576  conshdlr = scip->set->conshdlrs[i];
2577  maxnactiveconss = SCIPconshdlrGetMaxNActiveConss(conshdlr);
2578  if( SCIPconshdlrDoesPresolve(conshdlr)
2579  && (maxnactiveconss > 0 || !SCIPconshdlrNeedsCons(conshdlr)
2580  || SCIPconshdlrGetNFixedVars(conshdlr) > 0
2581  || SCIPconshdlrGetNAggrVars(conshdlr) > 0
2582  || SCIPconshdlrGetNChgVarTypes(conshdlr) > 0
2583  || SCIPconshdlrGetNChgBds(conshdlr) > 0
2584  || SCIPconshdlrGetNAddHoles(conshdlr) > 0
2585  || SCIPconshdlrGetNDelConss(conshdlr) > 0
2586  || SCIPconshdlrGetNAddConss(conshdlr) > 0
2587  || SCIPconshdlrGetNChgSides(conshdlr) > 0
2588  || SCIPconshdlrGetNChgCoefs(conshdlr) > 0
2589  || SCIPconshdlrGetNUpgdConss(conshdlr) > 0) )
2590  {
2591  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s:", SCIPconshdlrGetName(conshdlr));
2592  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f %10.2f %6d %10d %10d %10d %10d %10d %10d %10d %10d %10d\n",
2593  SCIPconshdlrGetPresolTime(conshdlr),
2594  SCIPconshdlrGetSetupTime(conshdlr),
2595  SCIPconshdlrGetNPresolCalls(conshdlr),
2596  SCIPconshdlrGetNFixedVars(conshdlr),
2597  SCIPconshdlrGetNAggrVars(conshdlr),
2598  SCIPconshdlrGetNChgVarTypes(conshdlr),
2599  SCIPconshdlrGetNChgBds(conshdlr),
2600  SCIPconshdlrGetNAddHoles(conshdlr),
2601  SCIPconshdlrGetNDelConss(conshdlr),
2602  SCIPconshdlrGetNAddConss(conshdlr),
2603  SCIPconshdlrGetNChgSides(conshdlr),
2604  SCIPconshdlrGetNChgCoefs(conshdlr));
2605  }
2606  }
2607 
2608  /* root node bound changes */
2609  SCIPmessageFPrintInfo(scip->messagehdlr, file, " root node : - - - %10d - - %10d - - - - -\n",
2610  scip->stat->nrootintfixings, scip->stat->nrootboundchgs);
2611 }
2612 
2613 /** outputs constraint statistics
2614  *
2615  * @pre This method can be called if SCIP is in one of the following stages:
2616  * - \ref SCIP_STAGE_TRANSFORMED
2617  * - \ref SCIP_STAGE_INITPRESOLVE
2618  * - \ref SCIP_STAGE_PRESOLVING
2619  * - \ref SCIP_STAGE_EXITPRESOLVE
2620  * - \ref SCIP_STAGE_PRESOLVED
2621  * - \ref SCIP_STAGE_SOLVING
2622  * - \ref SCIP_STAGE_SOLVED
2623  */
2625  SCIP* scip, /**< SCIP data structure */
2626  FILE* file /**< output file */
2627  )
2628 {
2629  int i;
2630 
2631  assert(scip != NULL);
2632  assert(scip->set != NULL);
2633 
2634  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintConstraintStatistics", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2635 
2636  /* Add maximal number of constraints of the same type? So far this information is not added because of lack of space. */
2637  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Constraints : Number MaxNumber #Separate #Propagate #EnfoLP #EnfoRelax #EnfoPS #Check #ResProp Cutoffs DomReds Cuts Applied Conss Children\n");
2638 
2639  for( i = 0; i < scip->set->nconshdlrs; ++i )
2640  {
2641  SCIP_CONSHDLR* conshdlr;
2642  int startnactiveconss;
2643  int maxnactiveconss;
2644 
2645  conshdlr = scip->set->conshdlrs[i];
2646  startnactiveconss = SCIPconshdlrGetStartNActiveConss(conshdlr);
2647  maxnactiveconss = SCIPconshdlrGetMaxNActiveConss(conshdlr);
2648  if( maxnactiveconss > 0 || !SCIPconshdlrNeedsCons(conshdlr) )
2649  {
2650  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s:", SCIPconshdlrGetName(conshdlr));
2651  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10d%c%10d %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT "\n",
2652  startnactiveconss,
2653  maxnactiveconss > startnactiveconss ? '+' : ' ',
2654  maxnactiveconss,
2655  SCIPconshdlrGetNSepaCalls(conshdlr),
2656  SCIPconshdlrGetNPropCalls(conshdlr),
2657  SCIPconshdlrGetNEnfoLPCalls(conshdlr),
2659  SCIPconshdlrGetNEnfoPSCalls(conshdlr),
2660  SCIPconshdlrGetNCheckCalls(conshdlr),
2661  SCIPconshdlrGetNRespropCalls(conshdlr),
2662  SCIPconshdlrGetNCutoffs(conshdlr),
2663  SCIPconshdlrGetNDomredsFound(conshdlr),
2664  SCIPconshdlrGetNCutsFound(conshdlr),
2665  SCIPconshdlrGetNCutsApplied(conshdlr),
2666  SCIPconshdlrGetNConssFound(conshdlr),
2667  SCIPconshdlrGetNChildren(conshdlr));
2668  }
2669  }
2670 }
2671 
2672 /** outputs constraint timing statistics
2673  *
2674  * @pre This method can be called if SCIP is in one of the following stages:
2675  * - \ref SCIP_STAGE_TRANSFORMED
2676  * - \ref SCIP_STAGE_INITPRESOLVE
2677  * - \ref SCIP_STAGE_PRESOLVING
2678  * - \ref SCIP_STAGE_EXITPRESOLVE
2679  * - \ref SCIP_STAGE_PRESOLVED
2680  * - \ref SCIP_STAGE_SOLVING
2681  * - \ref SCIP_STAGE_SOLVED
2682  */
2684  SCIP* scip, /**< SCIP data structure */
2685  FILE* file /**< output file */
2686  )
2687 {
2688  int i;
2689 
2690  assert(scip != NULL);
2691  assert(scip->set != NULL);
2692 
2693  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintConstraintTimingStatistics", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2694 
2695  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Constraint Timings : TotalTime SetupTime Separate Propagate EnfoLP EnfoPS EnfoRelax Check ResProp SB-Prop\n");
2696 
2697  for( i = 0; i < scip->set->nconshdlrs; ++i )
2698  {
2699  SCIP_CONSHDLR* conshdlr;
2700  int maxnactiveconss;
2701 
2702  conshdlr = scip->set->conshdlrs[i];
2703  maxnactiveconss = SCIPconshdlrGetMaxNActiveConss(conshdlr);
2704  if( maxnactiveconss > 0 || !SCIPconshdlrNeedsCons(conshdlr) )
2705  {
2706  SCIP_Real totaltime;
2707 
2708  totaltime = SCIPconshdlrGetSepaTime(conshdlr) + SCIPconshdlrGetPropTime(conshdlr)
2710  + SCIPconshdlrGetEnfoLPTime(conshdlr)
2711  + SCIPconshdlrGetEnfoPSTime(conshdlr)
2712  + SCIPconshdlrGetEnfoRelaxTime(conshdlr)
2713  + SCIPconshdlrGetCheckTime(conshdlr)
2714  + SCIPconshdlrGetRespropTime(conshdlr)
2715  + SCIPconshdlrGetSetupTime(conshdlr);
2716 
2717  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s:", SCIPconshdlrGetName(conshdlr));
2718  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f %10.2f %10.2f %10.2f %10.2f %10.2f %10.2f %10.2f %10.2f %10.2f\n",
2719  totaltime,
2720  SCIPconshdlrGetSetupTime(conshdlr),
2721  SCIPconshdlrGetSepaTime(conshdlr),
2722  SCIPconshdlrGetPropTime(conshdlr),
2723  SCIPconshdlrGetEnfoLPTime(conshdlr),
2724  SCIPconshdlrGetEnfoPSTime(conshdlr),
2725  SCIPconshdlrGetEnfoRelaxTime(conshdlr),
2726  SCIPconshdlrGetCheckTime(conshdlr),
2727  SCIPconshdlrGetRespropTime(conshdlr),
2729  }
2730  }
2731 }
2732 
2733 /** outputs propagator statistics
2734  *
2735  * @pre This method can be called if SCIP is in one of the following stages:
2736  * - \ref SCIP_STAGE_TRANSFORMED
2737  * - \ref SCIP_STAGE_INITPRESOLVE
2738  * - \ref SCIP_STAGE_PRESOLVING
2739  * - \ref SCIP_STAGE_EXITPRESOLVE
2740  * - \ref SCIP_STAGE_PRESOLVED
2741  * - \ref SCIP_STAGE_SOLVING
2742  * - \ref SCIP_STAGE_SOLVED
2743  */
2745  SCIP* scip, /**< SCIP data structure */
2746  FILE* file /**< output file */
2747  )
2748 {
2749  int i;
2750 
2751  assert(scip != NULL);
2752  assert(scip->set != NULL);
2753 
2754  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintPropagatorStatistics", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2755 
2756  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Propagators : #Propagate #ResProp Cutoffs DomReds\n");
2757 
2758  /* sort propagaters w.r.t. their name */
2759  SCIPsetSortPropsName(scip->set);
2760 
2761  for( i = 0; i < scip->set->nprops; ++i )
2762  {
2763  SCIP_PROP* prop;
2764  prop = scip->set->props[i];
2765 
2766  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s: %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT "\n",
2767  SCIPpropGetName(prop),
2768  SCIPpropGetNCalls(prop),
2770  SCIPpropGetNCutoffs(prop),
2771  SCIPpropGetNDomredsFound(prop));
2772  }
2773 
2774  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Propagator Timings : TotalTime SetupTime Presolve Propagate ResProp SB-Prop\n");
2775 
2776  for( i = 0; i < scip->set->nprops; ++i )
2777  {
2778  SCIP_PROP* prop;
2779  SCIP_Real totaltime;
2780 
2781  prop = scip->set->props[i];
2782  totaltime = SCIPpropGetPresolTime(prop) + SCIPpropGetTime(prop) + SCIPpropGetRespropTime(prop)
2784 
2785  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s:", SCIPpropGetName(prop));
2786  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f %10.2f %10.2f %10.2f %10.2f %10.2f\n",
2787  totaltime,
2788  SCIPpropGetSetupTime(prop),
2789  SCIPpropGetPresolTime(prop),
2790  SCIPpropGetTime(prop),
2791  SCIPpropGetRespropTime(prop),
2793  }
2794 }
2795 
2796 /** outputs conflict statistics
2797  *
2798  * @pre This method can be called if SCIP is in one of the following stages:
2799  * - \ref SCIP_STAGE_TRANSFORMED
2800  * - \ref SCIP_STAGE_INITPRESOLVE
2801  * - \ref SCIP_STAGE_PRESOLVING
2802  * - \ref SCIP_STAGE_EXITPRESOLVE
2803  * - \ref SCIP_STAGE_PRESOLVED
2804  * - \ref SCIP_STAGE_SOLVING
2805  * - \ref SCIP_STAGE_SOLVED
2806  */
2808  SCIP* scip, /**< SCIP data structure */
2809  FILE* file /**< output file */
2810  )
2811 {
2812  char initstoresize[SCIP_MAXSTRLEN];
2813  char maxstoresize[SCIP_MAXSTRLEN];
2814 
2815  assert(scip != NULL);
2816  assert(scip->set != NULL);
2817 
2818  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintConflictStatistics", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2819 
2820  if( scip->set->conf_maxstoresize == 0 )
2821  {
2822  (void)SCIPsnprintf(initstoresize, SCIP_MAXSTRLEN, "inf");
2823  (void)SCIPsnprintf(maxstoresize, SCIP_MAXSTRLEN, "inf");
2824  }
2825  else
2826  {
2827  int initsize = SCIPconflictstoreGetInitPoolSize(scip->conflictstore);
2828  int maxsize = SCIPconflictstoreGetMaxPoolSize(scip->conflictstore);
2829 
2830  if( maxsize == -1 )
2831  {
2832  (void)SCIPsnprintf(initstoresize, SCIP_MAXSTRLEN, "--");
2833  (void)SCIPsnprintf(maxstoresize, SCIP_MAXSTRLEN, "--");
2834  }
2835  else
2836  {
2837  assert(initsize >= 0);
2838  assert(maxsize >= 0);
2839 
2840  (void)SCIPsnprintf(initstoresize, SCIP_MAXSTRLEN, "%d", initsize);
2841  (void)SCIPsnprintf(maxstoresize, SCIP_MAXSTRLEN, "%d", maxsize);
2842  }
2843  }
2844  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Conflict Analysis : Time Calls Success DomReds Conflicts Literals Reconvs ReconvLits Dualrays Nonzeros LP Iters (pool size: [%s,%s])\n", initstoresize, maxstoresize);
2845  SCIPmessageFPrintInfo(scip->messagehdlr, file, " propagation : %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " - %10" SCIP_LONGINT_FORMAT " %10.1f %10" SCIP_LONGINT_FORMAT " %10.1f - - -\n",
2857  SCIPmessageFPrintInfo(scip->messagehdlr, file, " infeasible LP : %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " - %10" SCIP_LONGINT_FORMAT " %10.1f %10" SCIP_LONGINT_FORMAT " %10.1f %10" SCIP_LONGINT_FORMAT " %10.1f %10" SCIP_LONGINT_FORMAT "\n",
2874  SCIPmessageFPrintInfo(scip->messagehdlr, file, " bound exceed. LP : %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " - %10" SCIP_LONGINT_FORMAT " %10.1f %10" SCIP_LONGINT_FORMAT " %10.1f %10" SCIP_LONGINT_FORMAT " %10.1f %10" SCIP_LONGINT_FORMAT "\n",
2891  SCIPmessageFPrintInfo(scip->messagehdlr, file, " strong branching : %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " - %10" SCIP_LONGINT_FORMAT " %10.1f %10" SCIP_LONGINT_FORMAT " %10.1f - - %10" SCIP_LONGINT_FORMAT "\n",
2904  SCIPmessageFPrintInfo(scip->messagehdlr, file, " pseudo solution : %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " - %10" SCIP_LONGINT_FORMAT " %10.1f %10" SCIP_LONGINT_FORMAT " %10.1f - - -\n",
2916  SCIPmessageFPrintInfo(scip->messagehdlr, file, " applied globally : %10.2f - - %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10.1f - - %10" SCIP_LONGINT_FORMAT " - -\n",
2924  SCIPmessageFPrintInfo(scip->messagehdlr, file, " applied locally : - - - %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10.1f - - %10" SCIP_LONGINT_FORMAT " - -\n",
2931 }
2932 
2933 /** outputs separator statistics
2934  *
2935  * Columns:
2936  * - RootCalls: The number of calls that happened at the root.
2937  * - FoundCuts: The total number of cuts generated by the separators.
2938  * Note: Cutpool-FoundCuts \f$= \sum_{i=1}^nsepas ( Foundcuts_i - DirectAdd_i )\f$.
2939  * - ViaPoolAdd: The total number of cuts added to the sepastore from the cutpool.
2940  * - DirectAdd: The total number of cuts added directly to the sepastore from the separator.
2941  * - Applied: The sum of all cuts from the separator that were applied to the LP.
2942  * - ViaPoolApp: The number of cuts that entered the sepastore from the cutpool that were applied to the LP.
2943  * - DirectApp: The number of cuts that entered the sepastore directly and were applied to the LP.
2944  *
2945  * The number of cuts ViaPoolAdd + Directly should be equal to the number of cuts Filtered + Forced + Selected in the
2946  * cutselector statistics.
2947  *
2948  * @note The following edge case may lead to over or undercounting of statistics: When SCIPapplyCutsProbing() is
2949  * called, cuts are counted for the cut selection statistics, but not for the separator statistics. This
2950  * happens, e.g., in the default plugin prop_obbt.c.
2951  *
2952  * @pre This method can be called if SCIP is in one of the following stages:
2953  * - \ref SCIP_STAGE_SOLVING
2954  * - \ref SCIP_STAGE_SOLVED
2955  */
2957  SCIP* scip, /**< SCIP data structure */
2958  FILE* file /**< output file */
2959  )
2960 {
2961  int i;
2962 
2963  assert(scip != NULL);
2964  assert(scip->set != NULL);
2965 
2966  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintSeparatorStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
2967 
2968  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Separators : ExecTime SetupTime Calls RootCalls Cutoffs DomReds FoundCuts ViaPoolAdd DirectAdd Applied ViaPoolApp DirectApp Conss\n");
2969  SCIPmessageFPrintInfo(scip->messagehdlr, file, " cut pool : %10.2f - %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " - - %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " - - - - - (maximal pool size: %10" SCIP_LONGINT_FORMAT")\n",
2970  SCIPcutpoolGetTime(scip->cutpool),
2976 
2977  /* sort separators w.r.t. their name */
2978  SCIPsetSortSepasName(scip->set);
2979 
2980  for( i = 0; i < scip->set->nsepas; ++i )
2981  {
2982  SCIP_SEPA* sepa;
2983 
2984  sepa = scip->set->sepas[i];
2985 
2986  /* only output data for separators without parent separator */
2987  if( SCIPsepaGetParentsepa(sepa) == NULL )
2988  {
2989 
2990  /* output data */
2991  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s: %10.2f %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT "\n",
2992  SCIPsepaGetName(sepa),
2993  SCIPsepaGetTime(sepa),
2994  SCIPsepaGetSetupTime(sepa),
2995  SCIPsepaGetNCalls(sepa),
2996  SCIPsepaGetNRootCalls(sepa),
2997  SCIPsepaGetNCutoffs(sepa),
2999  SCIPsepaGetNCutsFound(sepa),
3005  SCIPsepaGetNConssFound(sepa));
3006 
3007  /* for parent separators search for dependent separators */
3008  if( SCIPsepaIsParentsepa(sepa) )
3009  {
3010  SCIP_SEPA* parentsepa;
3011  int k;
3012 
3013  for( k = 0; k < scip->set->nsepas; ++k )
3014  {
3015  if( k == i )
3016  continue;
3017 
3018  parentsepa = SCIPsepaGetParentsepa(scip->set->sepas[k]);
3019  if( parentsepa != sepa )
3020  continue;
3021 
3022  SCIPmessageFPrintInfo(scip->messagehdlr, file, " > %-15.17s: %10s %10s %10s %10s %10s %10s %10s %10" SCIP_LONGINT_FORMAT" %10" SCIP_LONGINT_FORMAT" %10" SCIP_LONGINT_FORMAT" %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10s\n",
3023  SCIPsepaGetName(scip->set->sepas[k]), "-", "-", "-", "-", "-", "-", "-",
3026  SCIPsepaGetNCutsApplied(scip->set->sepas[k]),
3028  SCIPsepaGetNCutsAppliedDirect(scip->set->sepas[k]), "-");
3029  }
3030  }
3031  }
3032  }
3033 }
3034 
3035 /** outputs cutselector statistics
3036  *
3037  * Filtered = ViaPoolAdd(Separators) + DirectAdd(Separators) - Selected - Cuts(Constraints)
3038  * Selected = Applied(Separators) + Applied(Constraints)
3039  *
3040  * @pre This method can be called if SCIP is in one of the following stages:
3041  * - \ref SCIP_STAGE_SOLVING
3042  * - \ref SCIP_STAGE_SOLVED
3043  */
3045  SCIP* scip, /**< SCIP data structure */
3046  FILE* file /**< output file */
3047  )
3048 {
3049  int i;
3050 
3051  assert(scip != NULL);
3052  assert(scip->set != NULL);
3053 
3054  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintCutselectorStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3055 
3056  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Cutselectors : ExecTime SetupTime Calls RootCalls Selected Forced Filtered RootSelec RootForc RootFilt \n");
3057 
3058  /* sort cutsels w.r.t. their priority */
3059  SCIPsetSortCutsels(scip->set);
3060 
3061  for( i = 0; i < scip->set->ncutsels; ++i )
3062  {
3063  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s: %10.2f %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT "\n",
3064  SCIPcutselGetName(scip->set->cutsels[i]),
3065  SCIPcutselGetTime(scip->set->cutsels[i]),
3066  SCIPcutselGetSetupTime(scip->set->cutsels[i]),
3067  SCIPcutselGetNCalls(scip->set->cutsels[i]),
3068  SCIPcutselGetNRootCalls(scip->set->cutsels[i]),
3072  SCIPcutselGetNRootCuts(scip->set->cutsels[i]),
3075  );
3076  }
3077 }
3078 
3079 /** outputs pricer statistics
3080  *
3081  * @pre This method can be called if SCIP is in one of the following stages:
3082  * - \ref SCIP_STAGE_SOLVING
3083  * - \ref SCIP_STAGE_SOLVED
3084  */
3086  SCIP* scip, /**< SCIP data structure */
3087  FILE* file /**< output file */
3088  )
3089 {
3090  int i;
3091 
3092  assert(scip != NULL);
3093  assert(scip->set != NULL);
3094 
3095  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintPricerStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3096 
3097  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Pricers : ExecTime SetupTime Calls Vars\n");
3098  SCIPmessageFPrintInfo(scip->messagehdlr, file, " problem variables: %10.2f - %10d %10d\n",
3102 
3103  /* sort pricers w.r.t. their name */
3104  SCIPsetSortPricersName(scip->set);
3105 
3106  for( i = 0; i < scip->set->nactivepricers; ++i )
3107  {
3108  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s: %10.2f %10.2f %10d %10d\n",
3109  SCIPpricerGetName(scip->set->pricers[i]),
3110  SCIPpricerGetTime(scip->set->pricers[i]),
3111  SCIPpricerGetSetupTime(scip->set->pricers[i]),
3112  SCIPpricerGetNCalls(scip->set->pricers[i]),
3113  SCIPpricerGetNVarsFound(scip->set->pricers[i]));
3114  }
3115 }
3116 
3117 /** outputs branching rule statistics
3118  *
3119  * @pre This method can be called if SCIP is in one of the following stages:
3120  * - \ref SCIP_STAGE_SOLVING
3121  * - \ref SCIP_STAGE_SOLVED
3122  */
3124  SCIP* scip, /**< SCIP data structure */
3125  FILE* file /**< output file */
3126  )
3127 {
3128  int i;
3129 
3130  assert(scip != NULL);
3131  assert(scip->set != NULL);
3132 
3133  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintBranchruleStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3134 
3135  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Branching Rules : ExecTime SetupTime BranchLP BranchExt BranchPS Cutoffs DomReds Cuts Conss Children\n");
3136 
3137  /* sort branching rules w.r.t. their name */
3139 
3140  for( i = 0; i < scip->set->nbranchrules; ++i )
3141  {
3142  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s: %10.2f %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT "\n",
3154  }
3155 }
3156 
3157 /** outputs heuristics statistics
3158  *
3159  * @pre This method can be called if SCIP is in one of the following stages:
3160  * - \ref SCIP_STAGE_PRESOLVING
3161  * - \ref SCIP_STAGE_EXITPRESOLVE
3162  * - \ref SCIP_STAGE_PRESOLVED
3163  * - \ref SCIP_STAGE_SOLVING
3164  * - \ref SCIP_STAGE_SOLVED
3165  */
3167  SCIP* scip, /**< SCIP data structure */
3168  FILE* file /**< output file */
3169  )
3170 {
3171  int ndivesets = 0;
3172  int i;
3173 
3174  assert(scip != NULL);
3175  assert(scip->set != NULL);
3176  assert(scip->tree != NULL);
3177 
3178  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintHeuristicStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3179 
3180  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Primal Heuristics : ExecTime SetupTime Calls Found Best\n");
3181  SCIPmessageFPrintInfo(scip->messagehdlr, file, " LP solutions : %10.2f - - %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT "\n",
3183  scip->stat->nlpsolsfound, scip->stat->nlpbestsolsfound);
3184  SCIPmessageFPrintInfo(scip->messagehdlr, file, " relax solutions : %10.2f - - %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT "\n",
3186  scip->stat->nrelaxsolsfound, scip->stat->nrelaxbestsolsfound);
3187  SCIPmessageFPrintInfo(scip->messagehdlr, file, " pseudo solutions : %10.2f - - %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT "\n",
3189  scip->stat->npssolsfound, scip->stat->npsbestsolsfound);
3190  SCIPmessageFPrintInfo(scip->messagehdlr, file, " strong branching : %10.2f - - %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT "\n",
3192  scip->stat->nsbsolsfound, scip->stat->nsbbestsolsfound);
3193 
3194  /* sort heuristics w.r.t. their names */
3195  SCIPsetSortHeursName(scip->set);
3196 
3197  for( i = 0; i < scip->set->nheurs; ++i )
3198  {
3199  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s: %10.2f %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT "\n",
3200  SCIPheurGetName(scip->set->heurs[i]),
3201  SCIPheurGetTime(scip->set->heurs[i]),
3202  SCIPheurGetSetupTime(scip->set->heurs[i]),
3203  SCIPheurGetNCalls(scip->set->heurs[i]),
3204  SCIPheurGetNSolsFound(scip->set->heurs[i]),
3205  SCIPheurGetNBestSolsFound(scip->set->heurs[i]));
3206 
3207  /* count heuristics that use diving; needed to determine output later */
3208  ndivesets += SCIPheurGetNDivesets(scip->set->heurs[i]);
3209  }
3210 
3211  SCIPmessageFPrintInfo(scip->messagehdlr, file, " other solutions : - - - %10" SCIP_LONGINT_FORMAT " -\n",
3212  scip->stat->nexternalsolsfound);
3213 
3214  if ( ndivesets > 0 && scip->set->misc_showdivingstats )
3215  {
3216  int c;
3218 
3219  /* print statistics for both contexts individually */
3220  for( c = 0; c < 2; ++c )
3221  {
3222  SCIP_DIVECONTEXT divecontext = divecontexts[c];
3223  SCIPmessageFPrintInfo(scip->messagehdlr, file,
3224  "Diving %-12s: Calls Nodes LP Iters Backtracks Conflicts MinDepth MaxDepth AvgDepth RoundSols NLeafSols MinSolDpt MaxSolDpt AvgSolDpt\n",
3225  divecontext == SCIP_DIVECONTEXT_SINGLE ? "(single)" : "(adaptive)");
3226 
3227  for( i = 0; i < scip->set->nheurs; ++i )
3228  {
3229  int s;
3230  for( s = 0; s < SCIPheurGetNDivesets(scip->set->heurs[i]); ++s )
3231  {
3232  SCIP_DIVESET* diveset = SCIPheurGetDivesets(scip->set->heurs[i])[s];
3233 
3234  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s: %10d",
3235  SCIPdivesetGetName(diveset),
3236  SCIPdivesetGetNCalls(diveset, divecontext));
3237  if( SCIPdivesetGetNCalls(diveset, divecontext) > 0 )
3238  {
3239  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10d %10d %10.1f %10" SCIP_LONGINT_FORMAT,
3240  SCIPdivesetGetNProbingNodes(diveset, divecontext),
3241  SCIPdivesetGetNLPIterations(diveset, divecontext),
3242  SCIPdivesetGetNBacktracks(diveset, divecontext),
3243  SCIPdivesetGetNConflicts(diveset, divecontext),
3244  SCIPdivesetGetMinDepth(diveset, divecontext),
3245  SCIPdivesetGetMaxDepth(diveset, divecontext),
3246  SCIPdivesetGetAvgDepth(diveset, divecontext),
3247  SCIPdivesetGetNSols(diveset, divecontext) - SCIPdivesetGetNSolutionCalls(diveset, divecontext));
3248 
3249  if( SCIPdivesetGetNSolutionCalls(diveset, divecontext) > 0 )
3250  {
3251  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10d %10d %10d %10.1f\n",
3252  SCIPdivesetGetNSolutionCalls(diveset, divecontext),
3253  SCIPdivesetGetMinSolutionDepth(diveset, divecontext),
3254  SCIPdivesetGetMaxSolutionDepth(diveset, divecontext),
3255  SCIPdivesetGetAvgSolutionDepth(diveset, divecontext));
3256  }
3257  else
3258  SCIPmessageFPrintInfo(scip->messagehdlr, file, " - - - -\n");
3259  }
3260  else
3261  SCIPmessageFPrintInfo(scip->messagehdlr, file, " - - - - - - - - - - - -\n");
3262  }
3263  }
3264  }
3265  }
3266 }
3267 
3268 /** outputs compression statistics
3269  *
3270  * @pre This method can be called if SCIP is in one of the following stages:
3271  * - \ref SCIP_STAGE_PRESOLVING
3272  * - \ref SCIP_STAGE_EXITPRESOLVE
3273  * - \ref SCIP_STAGE_PRESOLVED
3274  * - \ref SCIP_STAGE_SOLVING
3275  * - \ref SCIP_STAGE_SOLVED
3276  */
3278  SCIP* scip, /**< SCIP data structure */
3279  FILE* file /**< output file */
3280  )
3281 {
3282  int i;
3283 
3284  assert(scip != NULL);
3285 
3286  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintCompressionStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3287 
3288  /* only print compression statistics if tree reoptimization is enabled */
3289  if( !scip->set->reopt_enable )
3290  return;
3291 
3292  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Tree Compressions : ExecTime SetupTime Calls Found\n");
3293 
3294  /* sort compressions w.r.t. their names */
3295  SCIPsetSortComprsName(scip->set);
3296 
3297  for( i = 0; i < scip->set->ncomprs; ++i )
3298  {
3299  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s: %10.2f %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT "\n",
3300  SCIPcomprGetName(scip->set->comprs[i]),
3301  SCIPcomprGetTime(scip->set->comprs[i]),
3302  SCIPcomprGetSetupTime(scip->set->comprs[i]),
3303  SCIPcomprGetNCalls(scip->set->comprs[i]),
3304  SCIPcomprGetNFound(scip->set->comprs[i]));
3305  }
3306 }
3307 
3308 /** outputs LP statistics
3309  *
3310  * @pre This method can be called if SCIP is in one of the following stages:
3311  * - \ref SCIP_STAGE_SOLVING
3312  * - \ref SCIP_STAGE_SOLVED
3313  */
3315  SCIP* scip, /**< SCIP data structure */
3316  FILE* file /**< output file */
3317  )
3318 {
3319  assert(scip != NULL);
3320  assert(scip->stat != NULL);
3321  assert(scip->lp != NULL);
3322 
3323  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintLPStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3324 
3325  SCIPmessageFPrintInfo(scip->messagehdlr, file, "LP : Time Calls Iterations Iter/call Iter/sec Time-0-It Calls-0-It ItLimit\n");
3326 
3327  SCIPmessageFPrintInfo(scip->messagehdlr, file, " primal LP : %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10.2f",
3329  scip->stat->nprimallps + scip->stat->nprimalzeroitlps,
3330  scip->stat->nprimallpiterations,
3331  scip->stat->nprimallps > 0 ? (SCIP_Real)scip->stat->nprimallpiterations/(SCIP_Real)scip->stat->nprimallps : 0.0);
3332  if( SCIPclockGetTime(scip->stat->primallptime) >= 0.01 )
3334  else
3335  SCIPmessageFPrintInfo(scip->messagehdlr, file, " -");
3336  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f %10" SCIP_LONGINT_FORMAT "\n",
3337  scip->stat->primalzeroittime,
3338  scip->stat->nprimalzeroitlps);
3339 
3340  SCIPmessageFPrintInfo(scip->messagehdlr, file, " dual LP : %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10.2f",
3342  scip->stat->nduallps + scip->stat->ndualzeroitlps,
3343  scip->stat->nduallpiterations,
3344  scip->stat->nduallps > 0 ? (SCIP_Real)scip->stat->nduallpiterations/(SCIP_Real)scip->stat->nduallps : 0.0);
3345  if( SCIPclockGetTime(scip->stat->duallptime) >= 0.01 )
3347  else
3348  SCIPmessageFPrintInfo(scip->messagehdlr, file, " -");
3349  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f %10" SCIP_LONGINT_FORMAT "\n",
3350  scip->stat->dualzeroittime,
3351  scip->stat->ndualzeroitlps);
3352 
3353  SCIPmessageFPrintInfo(scip->messagehdlr, file, " lex dual LP : %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10.2f",
3355  scip->stat->nlexduallps,
3356  scip->stat->nlexduallpiterations,
3357  scip->stat->nlexduallps > 0 ? (SCIP_Real)scip->stat->nlexduallpiterations/(SCIP_Real)scip->stat->nlexduallps : 0.0);
3358  if( SCIPclockGetTime(scip->stat->lexduallptime) >= 0.01 )
3360  else
3361  SCIPmessageFPrintInfo(scip->messagehdlr, file, " -\n");
3362 
3363  SCIPmessageFPrintInfo(scip->messagehdlr, file, " barrier LP : %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10.2f",
3365  scip->stat->nbarrierlps,
3366  scip->stat->nbarrierlpiterations,
3367  scip->stat->nbarrierlps > 0 ? (SCIP_Real)scip->stat->nbarrierlpiterations/(SCIP_Real)scip->stat->nbarrierlps : 0.0);
3368  if( SCIPclockGetTime(scip->stat->barrierlptime) >= 0.01 )
3370  else
3371  SCIPmessageFPrintInfo(scip->messagehdlr, file, " -");
3372  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f %10" SCIP_LONGINT_FORMAT "\n",
3373  scip->stat->barrierzeroittime,
3374  scip->stat->nbarrierzeroitlps);
3375 
3376  SCIPmessageFPrintInfo(scip->messagehdlr, file, " resolve instable : %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10.2f",
3378  scip->stat->nresolveinstablelps,
3381  if( SCIPclockGetTime(scip->stat->resolveinstablelptime) >= 0.01 )
3383  else
3384  SCIPmessageFPrintInfo(scip->messagehdlr, file, " -\n");
3385 
3386  SCIPmessageFPrintInfo(scip->messagehdlr, file, " diving/probing LP: %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10.2f",
3388  scip->stat->ndivinglps,
3389  scip->stat->ndivinglpiterations,
3390  scip->stat->ndivinglps > 0 ? (SCIP_Real)scip->stat->ndivinglpiterations/(SCIP_Real)scip->stat->ndivinglps : 0.0);
3391  if( SCIPclockGetTime(scip->stat->divinglptime) >= 0.01 )
3393  else
3394  SCIPmessageFPrintInfo(scip->messagehdlr, file, " -\n");
3395 
3396  SCIPmessageFPrintInfo(scip->messagehdlr, file, " strong branching : %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10.2f",
3398  scip->stat->nstrongbranchs,
3399  scip->stat->nsblpiterations,
3400  scip->stat->nstrongbranchs > 0 ? (SCIP_Real)scip->stat->nsblpiterations/(SCIP_Real)scip->stat->nstrongbranchs : 0.0);
3401  if( SCIPclockGetTime(scip->stat->strongbranchtime) >= 0.01 )
3403  else
3404  SCIPmessageFPrintInfo(scip->messagehdlr, file, " -");
3405  SCIPmessageFPrintInfo(scip->messagehdlr, file, " - - %10" SCIP_LONGINT_FORMAT "\n", scip->stat->nsbtimesiterlimhit);
3406 
3407  SCIPmessageFPrintInfo(scip->messagehdlr, file, " (at root node) : - %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10.2f -\n",
3408  scip->stat->nrootstrongbranchs,
3409  scip->stat->nrootsblpiterations,
3410  scip->stat->nrootstrongbranchs > 0
3412 
3413  SCIPmessageFPrintInfo(scip->messagehdlr, file, " conflict analysis: %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10.2f",
3415  scip->stat->nconflictlps,
3416  scip->stat->nconflictlpiterations,
3417  scip->stat->nconflictlps > 0 ? (SCIP_Real)scip->stat->nconflictlpiterations/(SCIP_Real)scip->stat->nconflictlps : 0.0);
3418  if( SCIPclockGetTime(scip->stat->conflictlptime) >= 0.01 )
3420  else
3421  SCIPmessageFPrintInfo(scip->messagehdlr, file, " -\n");
3422 }
3423 
3424 /** outputs NLP statistics
3425  *
3426  * @pre This method can be called if SCIP is in one of the following stages:
3427  * - \ref SCIP_STAGE_SOLVING
3428  * - \ref SCIP_STAGE_SOLVED
3429  */
3431  SCIP* scip, /**< SCIP data structure */
3432  FILE* file /**< output file */
3433  )
3434 {
3435  assert(scip != NULL);
3436  assert(scip->stat != NULL);
3437 
3438  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintNLPStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3439 
3440  if( scip->nlp == NULL )
3441  return;
3442 
3443  SCIPmessageFPrintInfo(scip->messagehdlr, file, "NLP : Time Calls\n");
3444 
3445  SCIPmessageFPrintInfo(scip->messagehdlr, file, " all NLPs : %10.2f %10" SCIP_LONGINT_FORMAT "\n",
3447  scip->stat->nnlps);
3448 }
3449 
3450 /** outputs relaxator statistics
3451  *
3452  * @pre This method can be called if SCIP is in one of the following stages:
3453  * - \ref SCIP_STAGE_SOLVING
3454  * - \ref SCIP_STAGE_SOLVED
3455  */
3457  SCIP* scip, /**< SCIP data structure */
3458  FILE* file /**< output file */
3459  )
3460 {
3461  int i;
3462 
3463  assert(scip != NULL);
3464  assert(scip->set != NULL);
3465 
3466  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintRelaxatorStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3467 
3468  if( scip->set->nrelaxs == 0 )
3469  return;
3470 
3471  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Relaxators : Time Calls Cutoffs ImprBounds ImprTime ReducedDom Separated AddedConss\n");
3472 
3473  /* sort relaxators w.r.t. their name */
3474  SCIPsetSortRelaxsName(scip->set);
3475 
3476  for( i = 0; i < scip->set->nrelaxs; ++i )
3477  {
3478  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s: %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT "\n",
3479  SCIPrelaxGetName(scip->set->relaxs[i]),
3480  SCIPrelaxGetTime(scip->set->relaxs[i]),
3481  SCIPrelaxGetNCalls(scip->set->relaxs[i]),
3482  SCIPrelaxGetNCutoffs(scip->set->relaxs[i]),
3488  );
3489  }
3490 }
3491 
3492 /** outputs tree statistics
3493  *
3494  * @pre This method can be called if SCIP is in one of the following stages:
3495  * - \ref SCIP_STAGE_SOLVING
3496  * - \ref SCIP_STAGE_SOLVED
3497  */
3499  SCIP* scip, /**< SCIP data structure */
3500  FILE* file /**< output file */
3501  )
3502 {
3503  assert(scip != NULL);
3504  assert(scip->stat != NULL);
3505  assert(scip->tree != NULL);
3506 
3507  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintTreeStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3508 
3509  SCIPmessageFPrintInfo(scip->messagehdlr, file, "B&B Tree :\n");
3510  SCIPmessageFPrintInfo(scip->messagehdlr, file, " number of runs : %10d\n", scip->stat->nruns);
3511  SCIPmessageFPrintInfo(scip->messagehdlr, file,
3512  " nodes : %10" SCIP_LONGINT_FORMAT " (%" SCIP_LONGINT_FORMAT " internal, %" SCIP_LONGINT_FORMAT " leaves)\n",
3513  scip->stat->nnodes, scip->stat->ninternalnodes, scip->stat->nnodes - scip->stat->ninternalnodes );
3514  SCIPmessageFPrintInfo(scip->messagehdlr, file, " feasible leaves : %10" SCIP_LONGINT_FORMAT "\n", scip->stat->nfeasleaves);
3515  SCIPmessageFPrintInfo(scip->messagehdlr, file, " infeas. leaves : %10" SCIP_LONGINT_FORMAT "\n", scip->stat->ninfeasleaves);
3516  SCIPmessageFPrintInfo(scip->messagehdlr, file, " objective leaves : %10" SCIP_LONGINT_FORMAT "\n", scip->stat->nobjleaves);
3517  SCIPmessageFPrintInfo(scip->messagehdlr, file,
3518  " nodes (total) : %10" SCIP_LONGINT_FORMAT " (%" SCIP_LONGINT_FORMAT " internal, %" SCIP_LONGINT_FORMAT " leaves)\n",
3520  SCIPmessageFPrintInfo(scip->messagehdlr, file, " nodes left : %10d\n", SCIPtreeGetNNodes(scip->tree));
3521  SCIPmessageFPrintInfo(scip->messagehdlr, file, " max depth : %10d\n", scip->stat->maxdepth);
3522  SCIPmessageFPrintInfo(scip->messagehdlr, file, " max depth (total): %10d\n", scip->stat->maxtotaldepth);
3523  SCIPmessageFPrintInfo(scip->messagehdlr, file, " backtracks : %10" SCIP_LONGINT_FORMAT " (%.1f%%)\n", scip->stat->nbacktracks,
3524  scip->stat->nnodes > 0 ? 100.0 * (SCIP_Real)scip->stat->nbacktracks / (SCIP_Real)scip->stat->nnodes : 0.0);
3525  SCIPmessageFPrintInfo(scip->messagehdlr, file, " early backtracks : %10" SCIP_LONGINT_FORMAT " (%.1f%%)\n", scip->stat->nearlybacktracks,
3526  scip->stat->nbacktracks > 0 ? 100.0 * (SCIP_Real)scip->stat->nearlybacktracks / (SCIP_Real)scip->stat->nbacktracks : 0.0);
3527  SCIPmessageFPrintInfo(scip->messagehdlr, file, " nodes exc. ref. : %10" SCIP_LONGINT_FORMAT " (%.1f%%)\n", scip->stat->nnodesaboverefbound,
3528  scip->stat->nnodes > 0 ? 100.0 * (SCIP_Real)scip->stat->nnodesaboverefbound / (SCIP_Real)scip->stat->nnodes : 0.0);
3529 
3530  SCIPmessageFPrintInfo(scip->messagehdlr, file, " delayed cutoffs : %10" SCIP_LONGINT_FORMAT "\n", scip->stat->ndelayedcutoffs);
3531  SCIPmessageFPrintInfo(scip->messagehdlr, file, " repropagations : %10" SCIP_LONGINT_FORMAT " (%" SCIP_LONGINT_FORMAT " domain reductions, %" SCIP_LONGINT_FORMAT " cutoffs)\n",
3532  scip->stat->nreprops, scip->stat->nrepropboundchgs, scip->stat->nrepropcutoffs);
3533  SCIPmessageFPrintInfo(scip->messagehdlr, file, " avg switch length: %10.2f\n",
3534  scip->stat->nnodes > 0
3535  ? (SCIP_Real)(scip->stat->nactivatednodes + scip->stat->ndeactivatednodes) / (SCIP_Real)scip->stat->nnodes : 0.0);
3536  SCIPmessageFPrintInfo(scip->messagehdlr, file, " switching time : %10.2f\n", SCIPclockGetTime(scip->stat->nodeactivationtime));
3537 }
3538 
3539 /** outputs solution statistics
3540  *
3541  * @pre This method can be called if SCIP is in one of the following stages:
3542  * - \ref SCIP_STAGE_PRESOLVING
3543  * - \ref SCIP_STAGE_EXITPRESOLVE
3544  * - \ref SCIP_STAGE_PRESOLVED
3545  * - \ref SCIP_STAGE_SOLVING
3546  * - \ref SCIP_STAGE_SOLVED
3547  */
3549  SCIP* scip, /**< SCIP data structure */
3550  FILE* file /**< output file */
3551  )
3552 {
3553  SCIP_Real primalbound;
3554  SCIP_Real dualbound;
3555  SCIP_Real gap;
3556  SCIP_Real firstprimalbound;
3557  SCIP_Bool objlimitreached;
3558  char limsolstring[SCIP_MAXSTRLEN];
3559 
3560  assert(scip != NULL);
3561  assert(scip->stat != NULL);
3562  assert(scip->primal != NULL);
3563 
3564  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintSolutionStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3565 
3566  primalbound = SCIPgetPrimalbound(scip);
3567  dualbound = SCIPgetDualbound(scip);
3568  gap = SCIPgetGap(scip);
3569 
3570  /* We output that the objective limit has been reached if the problem has been solved, no solution respecting the
3571  * objective limit has been found (nlimsolsfound == 0) and the primal bound is finite. Note that it still might be
3572  * that the original problem is infeasible, even without the objective limit, i.e., we cannot be sure that we
3573  * actually reached the objective limit. */
3574  objlimitreached = FALSE;
3575  if( SCIPgetStage(scip) == SCIP_STAGE_SOLVED && scip->primal->nlimsolsfound == 0
3576  && !SCIPisInfinity(scip, primalbound) && SCIPgetStatus(scip) != SCIP_STATUS_INFORUNBD )
3577  objlimitreached = TRUE;
3578 
3579  if( scip->primal->nsolsfound != scip->primal->nlimsolsfound )
3580  (void) SCIPsnprintf(limsolstring, SCIP_MAXSTRLEN, ", %" SCIP_LONGINT_FORMAT " respecting the objective limit", scip->primal->nlimsolsfound);
3581  else
3582  limsolstring[0] = '\0';
3583 
3584  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Solution :\n");
3585  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Solutions found : %10" SCIP_LONGINT_FORMAT " (%" SCIP_LONGINT_FORMAT " improvements%s)\n",
3586  scip->primal->nsolsfound, scip->primal->nbestsolsfound, limsolstring);
3587 
3588  if( SCIPsetIsInfinity(scip->set, REALABS(primalbound)) )
3589  {
3590  if( scip->set->stage == SCIP_STAGE_SOLVED )
3591  {
3592  if( scip->primal->nlimsolsfound == 0 )
3593  {
3594  if( SCIPgetStatus(scip) == SCIP_STATUS_INFORUNBD )
3595  {
3596  assert(!objlimitreached);
3597  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Primal Bound : infeasible or unbounded\n");
3598  }
3599  else
3600  {
3601  assert(SCIPgetStatus(scip) == SCIP_STATUS_INFEASIBLE);
3602  if( objlimitreached )
3603  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Primal Bound : infeasible (objective limit reached)\n");
3604  else
3605  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Primal Bound : infeasible\n");
3606  }
3607  }
3608  else
3609  {
3610  assert(!objlimitreached);
3611  assert(SCIPgetStatus(scip) == SCIP_STATUS_UNBOUNDED);
3612  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Primal Bound : unbounded\n");
3613  }
3614  }
3615  else
3616  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Primal Bound : -\n");
3617  }
3618  else
3619  {
3620  if( scip->primal->nlimsolsfound == 0 )
3621  {
3622  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Primal Bound : %+21.14e (objective limit)\n", primalbound);
3623 
3624  /* display (best) primal bound */
3625  if( scip->primal->nsolsfound > 0 )
3626  {
3627  SCIP_Real bestsol;
3628  bestsol = SCIPsolGetObj(scip->primal->sols[0], scip->set, scip->transprob, scip->origprob);
3629  bestsol = SCIPretransformObj(scip, bestsol);
3630 
3631  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Best Solution : %+21.14e\n", bestsol);
3632  }
3633  }
3634  else
3635  {
3636  /* display first primal bound line */
3637  firstprimalbound = scip->stat->firstprimalbound;
3638  SCIPmessageFPrintInfo(scip->messagehdlr, file, " First Solution : %+21.14e", firstprimalbound);
3639 
3640  SCIPmessageFPrintInfo(scip->messagehdlr, file, " (in run %d, after %" SCIP_LONGINT_FORMAT " nodes, %.2f seconds, depth %d, found by <%s>)\n",
3641  scip->stat->nrunsbeforefirst,
3642  scip->stat->nnodesbeforefirst,
3643  scip->stat->firstprimaltime,
3644  scip->stat->firstprimaldepth,
3645  ( scip->stat->firstprimalheur != NULL )
3646  ? ( SCIPheurGetName(scip->stat->firstprimalheur) )
3647  : (( scip->stat->nrunsbeforefirst == 0 ) ? "initial" : "relaxation"));
3648 
3649  if( SCIPisInfinity(scip, scip->stat->firstsolgap) )
3650  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Gap First Sol. : infinite\n");
3651  else
3652  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Gap First Sol. : %10.2f %%\n", 100.0 * scip->stat->firstsolgap);
3653 
3654  if( SCIPisInfinity(scip, scip->stat->lastsolgap) )
3655  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Gap Last Sol. : infinite\n");
3656  else
3657  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Gap Last Sol. : %10.2f %%\n", 100.0 * scip->stat->lastsolgap);
3658 
3659  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Primal Bound : %+21.14e", primalbound);
3660 
3661  SCIPmessageFPrintInfo(scip->messagehdlr, file, " (in run %d, after %" SCIP_LONGINT_FORMAT " nodes, %.2f seconds, depth %d, found by <%s>)\n",
3662  SCIPsolGetRunnum(scip->primal->sols[0]),
3663  SCIPsolGetNodenum(scip->primal->sols[0]),
3664  SCIPsolGetTime(scip->primal->sols[0]),
3665  SCIPsolGetDepth(scip->primal->sols[0]),
3666  SCIPsolGetHeur(scip->primal->sols[0]) != NULL
3668  : (SCIPsolGetRunnum(scip->primal->sols[0]) == 0 ? "initial" : "relaxation"));
3669  }
3670  }
3671 
3672  if( SCIPsetIsInfinity(scip->set, REALABS(dualbound)) )
3673  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Dual Bound : -\n");
3674  else
3675  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Dual Bound : %+21.14e\n", dualbound);
3676 
3677  if( SCIPsetIsInfinity(scip->set, gap) )
3678  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Gap : infinite\n");
3679  else
3680  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Gap : %10.2f %%\n", 100.0 * gap);
3681 
3682  if( scip->set->misc_calcintegral )
3683  {
3684  int s;
3685  const char* names[] = {
3686  "primal-dual",
3687  "primal-ref",
3688  "dual-ref"
3689  };
3690  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Integrals : Total Avg%%\n");
3691  if( SCIPgetStatus(scip) == SCIP_STATUS_INFEASIBLE && ! objlimitreached )
3692  {
3693  for( s = 0; s < 3; ++s )
3694  {
3695  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17s: %10s %10s (problem infeasible)\n",
3696  names[s], "-", "-");
3697  }
3698  }
3699  else
3700  {
3701  SCIP_Real integrals[3];
3702  SCIP_Real solvingtime = SCIPgetSolvingTime(scip);
3703 
3704  if( !SCIPisFeasZero(scip, solvingtime) )
3705  {
3706  integrals[0] = SCIPstatGetPrimalDualIntegral(scip->stat, scip->set, scip->transprob, scip->origprob, TRUE);
3707 
3708  if( scip->set->misc_referencevalue != SCIP_INVALID ) /*lint !e777*/
3709  {
3710  integrals[1] = SCIPstatGetPrimalReferenceIntegral(scip->stat, scip->set, scip->transprob, scip->origprob, FALSE);
3711  integrals[2] = SCIPstatGetDualReferenceIntegral(scip->stat, scip->set, scip->transprob, scip->origprob, FALSE);
3712  }
3713  else
3714  integrals[1] = integrals[2] = SCIP_INVALID;
3715  }
3716  else
3717  {
3718  BMSclearMemoryArray(integrals, 3);
3719  }
3720 
3721  /* print integrals, if computed */
3722  for( s = 0; s < 3; ++s )
3723  {
3724  if( integrals[s] == SCIP_INVALID ) /*lint !e777*/
3725  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17s: - - (not evaluated)\n", names[s]);
3726  else
3727  {
3728  SCIP_Real avg = integrals[s] / MAX(solvingtime,1e-6);
3729 
3730  /* caution: this assert is non-deterministic since it depends on the solving time */
3731  assert(0.0 <= avg && SCIPisLE(scip, avg, 100.0));
3732  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17s: %10.2f %10.2f\n", names[s], integrals[s], avg);
3733  }
3734  }
3735  }
3736  }
3737 }
3738 
3739 /** outputs concurrent solver statistics
3740  *
3741  * @pre This method can be called if SCIP is in one of the following stages:
3742  * - \ref SCIP_STAGE_TRANSFORMED
3743  * - \ref SCIP_STAGE_INITPRESOLVE
3744  * - \ref SCIP_STAGE_PRESOLVING
3745  * - \ref SCIP_STAGE_EXITPRESOLVE
3746  * - \ref SCIP_STAGE_PRESOLVED
3747  * - \ref SCIP_STAGE_SOLVING
3748  * - \ref SCIP_STAGE_SOLVED
3749  */
3751  SCIP* scip, /**< SCIP data structure */
3752  FILE* file /**< output file */
3753  )
3754 {
3755  SCIP_CONCSOLVER** concsolvers;
3756  int nconcsolvers;
3757  int i;
3758  int winner;
3759 
3760  assert(scip != NULL);
3761  assert(scip->set != NULL);
3762 
3763  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintConcsolverStatistics", FALSE, FALSE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3764 
3766  return;
3767 
3768  nconcsolvers = SCIPgetNConcurrentSolvers(scip);
3769  concsolvers = SCIPgetConcurrentSolvers(scip);
3770  winner = SCIPsyncstoreGetWinner(scip->syncstore);
3771 
3772  if( nconcsolvers > 0 )
3773  {
3774  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Concurrent Solvers : SolvingTime SyncTime Nodes LP Iters SolsShared SolsRecvd TighterBnds TighterIntBnds\n");
3775  for( i = 0; i < nconcsolvers; ++i )
3776  {
3777  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %c%-16s: %11.2f %11.2f %11" SCIP_LONGINT_FORMAT " %11" SCIP_LONGINT_FORMAT "%11" SCIP_LONGINT_FORMAT " %11" SCIP_LONGINT_FORMAT " %11" SCIP_LONGINT_FORMAT " %14" SCIP_LONGINT_FORMAT "\n",
3778  winner == i ? '*' : ' ',
3779  SCIPconcsolverGetName(concsolvers[i]),
3780  SCIPconcsolverGetSolvingTime(concsolvers[i]),
3781  SCIPconcsolverGetSyncTime(concsolvers[i]),
3782  SCIPconcsolverGetNNodes(concsolvers[i]),
3783  SCIPconcsolverGetNLPIterations(concsolvers[i]),
3784  SCIPconcsolverGetNSolsShared(concsolvers[i]),
3785  SCIPconcsolverGetNSolsRecvd(concsolvers[i]),
3786  SCIPconcsolverGetNTighterBnds(concsolvers[i]),
3787  SCIPconcsolverGetNTighterIntBnds(concsolvers[i])
3788  );
3789  }
3790  }
3791 }
3792 
3793 /** display Benders' decomposition statistics */
3795  SCIP* scip, /**< SCIP data structure */
3796  FILE* file /**< output file */
3797  )
3798 {
3799  SCIP_BENDERS** benders;
3800  int nbenders;
3801  int i;
3802 
3803  assert(scip != NULL);
3804  assert(scip->set != NULL);
3805 
3806  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintBendersStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3807 
3808  if( SCIPgetNActiveBenders(scip) == 0 )
3809  return;
3810 
3811  nbenders = SCIPgetNBenders(scip);
3812  benders = SCIPgetBenders(scip);
3813 
3814  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Benders Decomp : ExecTime SetupTime Calls Found Transfer StrCalls StrFails StrCuts\n");
3815  for( i = 0; i < nbenders; ++i )
3816  {
3817  if( SCIPbendersIsActive(benders[i]) )
3818  {
3819  SCIP_BENDERSCUT** benderscuts;
3820  int nbenderscuts;
3821  int j;
3822 
3823  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17.17s: %10.2f %10.2f %10d %10d %10d %10d %10d %10d\n",
3824  SCIPbendersGetName(scip->set->benders[i]),
3825  SCIPbendersGetTime(scip->set->benders[i]),
3826  SCIPbendersGetSetupTime(scip->set->benders[i]),
3827  SCIPbendersGetNCalls(scip->set->benders[i]),
3833 
3834  nbenderscuts = SCIPbendersGetNBenderscuts(scip->set->benders[i]);
3835  benderscuts = SCIPbendersGetBenderscuts(scip->set->benders[i]);
3836 
3837  for( j = 0; j < nbenderscuts; j++ )
3838  {
3839  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-15.17s: %10.2f %10.2f %10" SCIP_LONGINT_FORMAT " %10" SCIP_LONGINT_FORMAT " -\n",
3840  SCIPbenderscutGetName(benderscuts[j]),
3841  SCIPbenderscutGetTime(benderscuts[j]),
3842  SCIPbenderscutGetSetupTime(benderscuts[j]),
3843  SCIPbenderscutGetNCalls(benderscuts[j]),
3844  SCIPbenderscutGetNFound(benderscuts[j]));
3845  }
3846  }
3847  }
3848 }
3849 
3850 /** outputs root statistics
3851  *
3852  * @pre This method can be called if SCIP is in one of the following stages:
3853  * - \ref SCIP_STAGE_SOLVING
3854  * - \ref SCIP_STAGE_SOLVED
3855  */
3857  SCIP* scip, /**< SCIP data structure */
3858  FILE* file /**< output file */
3859  )
3860 {
3861  SCIP_Real dualboundroot;
3862  SCIP_Real firstdualboundroot;
3863  SCIP_Real firstlptime;
3864  SCIP_Real firstlpspeed;
3865 
3866  assert(scip != NULL);
3867  assert(scip->stat != NULL);
3868  assert(scip->primal != NULL);
3869 
3870  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintRootStatistics", FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3871 
3872  dualboundroot = SCIPgetDualboundRoot(scip);
3873  firstdualboundroot = SCIPgetFirstLPDualboundRoot(scip);
3874  firstlptime = SCIPgetFirstLPTime(scip);
3875 
3876  if( firstlptime > 0.0 )
3877  firstlpspeed = (SCIP_Real)scip->stat->nrootfirstlpiterations/firstlptime;
3878  else
3879  firstlpspeed = 0.0;
3880 
3881  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Root Node :\n");
3882  if( SCIPsetIsInfinity(scip->set, REALABS(firstdualboundroot)) )
3883  SCIPmessageFPrintInfo(scip->messagehdlr, file, " First LP value : -\n");
3884  else
3885  SCIPmessageFPrintInfo(scip->messagehdlr, file, " First LP value : %+21.14e\n", firstdualboundroot);
3886  if( firstlpspeed > 0.0 )
3887  SCIPmessageFPrintInfo(scip->messagehdlr, file, " First LP Iters : %10" SCIP_LONGINT_FORMAT " (%.2f Iter/sec)\n",
3889  (SCIP_Real)scip->stat->nrootfirstlpiterations/firstlptime);
3890  else
3891  SCIPmessageFPrintInfo(scip->messagehdlr, file, " First LP Iters : %10" SCIP_LONGINT_FORMAT "\n", scip->stat->nrootfirstlpiterations);
3892  SCIPmessageFPrintInfo(scip->messagehdlr, file, " First LP Time : %10.2f\n", firstlptime);
3893 
3894  if( SCIPsetIsInfinity(scip->set, REALABS(dualboundroot)) )
3895  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Final Dual Bound : -\n");
3896  else
3897  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Final Dual Bound : %+21.14e\n", dualboundroot);
3898  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Final Root Iters : %10" SCIP_LONGINT_FORMAT "\n", scip->stat->nrootlpiterations);
3899 
3900  SCIPmessageFPrintInfo(scip->messagehdlr, file, " Root LP Estimate : ");
3901  if( scip->stat->rootlpbestestimate != SCIP_INVALID ) /*lint !e777*/
3902  {
3903  SCIPmessageFPrintInfo(scip->messagehdlr, file, "%+21.14e\n", SCIPretransformObj(scip, scip->stat->rootlpbestestimate));
3904  }
3905  else
3906  SCIPmessageFPrintInfo(scip->messagehdlr, file, "%21s\n","-");
3907 }
3908 
3909 /** outputs timing statistics
3910  *
3911  * @pre This method can be called if SCIP is in one of the following stages:
3912  * - \ref SCIP_STAGE_PROBLEM
3913  * - \ref SCIP_STAGE_TRANSFORMED
3914  * - \ref SCIP_STAGE_INITPRESOLVE
3915  * - \ref SCIP_STAGE_PRESOLVING
3916  * - \ref SCIP_STAGE_EXITPRESOLVE
3917  * - \ref SCIP_STAGE_PRESOLVED
3918  * - \ref SCIP_STAGE_SOLVING
3919  * - \ref SCIP_STAGE_SOLVED
3920  */
3922  SCIP* scip, /**< SCIP data structure */
3923  FILE* file /**< output file */
3924  )
3925 {
3926  SCIP_Real readingtime;
3927 
3928  assert(scip != NULL);
3929  assert(scip->set != NULL);
3930 
3931  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintTimingStatistics", FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3932 
3933  readingtime = SCIPgetReadingTime(scip);
3934 
3935  if( SCIPgetStage(scip) == SCIP_STAGE_PROBLEM )
3936  {
3937  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Total Time : %10.2f\n", readingtime);
3938  SCIPmessageFPrintInfo(scip->messagehdlr, file, " reading : %10.2f\n", readingtime);
3939  }
3940  else
3941  {
3942  SCIP_Real totaltime;
3943  SCIP_Real solvingtime;
3944 
3945  solvingtime = SCIPclockGetTime(scip->stat->solvingtime);
3946 
3947  if( scip->set->time_reading )
3948  totaltime = solvingtime;
3949  else
3950  totaltime = solvingtime + readingtime;
3951 
3952  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Total Time : %10.2f\n", totaltime);
3953  SCIPmessageFPrintInfo(scip->messagehdlr, file, " solving : %10.2f\n", solvingtime);
3954  SCIPmessageFPrintInfo(scip->messagehdlr, file, " presolving : %10.2f (included in solving)\n", SCIPclockGetTime(scip->stat->presolvingtime));
3955  SCIPmessageFPrintInfo(scip->messagehdlr, file, " reading : %10.2f%s\n", readingtime, scip->set->time_reading ? " (included in solving)" : "");
3956 
3957  if( scip->stat->ncopies > 0 )
3958  {
3959  SCIP_Real copytime;
3960 
3961  copytime = SCIPclockGetTime(scip->stat->copyclock);
3962 
3963  SCIPmessageFPrintInfo(scip->messagehdlr, file, " copying : %10.2f (%d #copies) (minimal %.2f, maximal %.2f, average %.2f)\n",
3964  copytime, scip->stat->ncopies, scip->stat->mincopytime, scip->stat->maxcopytime, copytime / scip->stat->ncopies);
3965  }
3966  else
3967  SCIPmessageFPrintInfo(scip->messagehdlr, file, " copying : %10.2f %s\n", 0.0, "(0 times copied the problem)");
3968  }
3969 }
3970 
3971 /** outputs expression handler statistics
3972  *
3973  * @pre This method can be called if SCIP is in one of the following stages:
3974  * - \ref SCIP_STAGE_PROBLEM
3975  * - \ref SCIP_STAGE_TRANSFORMED
3976  * - \ref SCIP_STAGE_INITPRESOLVE
3977  * - \ref SCIP_STAGE_PRESOLVING
3978  * - \ref SCIP_STAGE_EXITPRESOLVE
3979  * - \ref SCIP_STAGE_PRESOLVED
3980  * - \ref SCIP_STAGE_SOLVING
3981  * - \ref SCIP_STAGE_SOLVED
3982  */
3984  SCIP* scip, /**< SCIP data structure */
3985  FILE* file /**< output file */
3986  )
3987 {
3988  SCIP_Bool headerprinted = FALSE;
3989  int i;
3990 
3991  assert(scip != NULL);
3992  assert(scip->set != NULL);
3993 
3994  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintExpressionHandlerStatistics", FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
3995 
3996  for( i = 0; i < scip->set->nexprhdlrs; ++i )
3997  {
3998  SCIP_EXPRHDLR* exprhdlr = scip->set->exprhdlrs[i];
3999  assert(exprhdlr != NULL);
4000 
4001  /* skip unused expression handler */
4002  if( SCIPexprhdlrGetNCreated(exprhdlr) == 0 )
4003  continue;
4004 
4005  if( !headerprinted )
4006  {
4007  SCIPmessageFPrintInfo(scip->messagehdlr, file,
4008  "Expressions : %10s %10s %10s %10s %10s %10s %10s %10s %10s %10s %10s %10s\n",
4009  "#IntEval", "IntEvalTi", "#RevProp", "RevPropTi", "DomReds", "Cutoffs", "#Estimate", "EstimTime", "Branching", "#Simplify", "SimplifyTi", "Simplified");
4010  headerprinted = TRUE;
4011  }
4012 
4013  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17s:", SCIPexprhdlrGetName(exprhdlr));
4014  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10lld", SCIPexprhdlrGetNIntevalCalls(exprhdlr));
4015  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f", SCIPexprhdlrGetIntevalTime(exprhdlr));
4016  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10lld", SCIPexprhdlrGetNReversepropCalls(exprhdlr));
4017  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f", SCIPexprhdlrGetReversepropTime(exprhdlr));
4018  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10lld", SCIPexprhdlrGetNDomainReductions(exprhdlr));
4019  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10lld", SCIPexprhdlrGetNCutoffs(exprhdlr));
4020  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10lld", SCIPexprhdlrGetNEstimateCalls(exprhdlr));
4021  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f", SCIPexprhdlrGetEstimateTime(exprhdlr));
4022  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10lld", SCIPexprhdlrGetNBranchings(exprhdlr));
4023  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10lld", SCIPexprhdlrGetNSimplifyCalls(exprhdlr));
4024  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f", SCIPexprhdlrGetSimplifyTime(exprhdlr));
4025  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10lld", SCIPexprhdlrGetNSimplifications(exprhdlr));
4026  SCIPmessageFPrintInfo(scip->messagehdlr, file, "\n");
4027  }
4028 }
4029 
4030 /** outputs NLPI statistics
4031  *
4032  * @pre This method can be called if SCIP is in one of the following stages:
4033  * - \ref SCIP_STAGE_PROBLEM
4034  * - \ref SCIP_STAGE_TRANSFORMED
4035  * - \ref SCIP_STAGE_INITPRESOLVE
4036  * - \ref SCIP_STAGE_PRESOLVING
4037  * - \ref SCIP_STAGE_EXITPRESOLVE
4038  * - \ref SCIP_STAGE_PRESOLVED
4039  * - \ref SCIP_STAGE_SOLVING
4040  * - \ref SCIP_STAGE_SOLVED
4041  */
4043  SCIP* scip, /**< SCIP data structure */
4044  FILE* file /**< output file */
4045  )
4046 {
4047  SCIP_Bool printedheader = FALSE;
4048  int i;
4049 
4050  assert(scip != NULL);
4051  assert(scip->set != NULL);
4052 
4053  SCIP_CALL_ABORT( SCIPcheckStage(scip, "SCIPprintNLPIStatistics", FALSE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
4054 
4055  for( i = 0; i < scip->set->nnlpis; ++i )
4056  {
4057  SCIP_Real solvetime;
4058  SCIP_Real evaltime = 0.0;
4059  SCIP_Longint niter;
4060  SCIP_NLPI* nlpi;
4061  int j;
4062 
4063  nlpi = scip->set->nlpis[i];
4064  assert(nlpi != NULL);
4065 
4066  /* skip unused NLP solver */
4067  if( SCIPnlpiGetNProblems(nlpi) == 0 )
4068  continue;
4069 
4070  if( !printedheader )
4071  {
4072  SCIPmessageFPrintInfo(scip->messagehdlr, file,
4073  "NLP Solvers : %10s %10s %10s %10s %s%10s %10s"
4074  " %10s %10s %10s %10s %10s %10s %10s %10s %10s %10s"
4075  " %10s %10s %10s %10s %10s %10s %10s\n",
4076  "#Problems", "ProblemTi", "#Solves", "SolveTime",
4077  scip->set->time_nlpieval ? " EvalTime%" : "",
4078  "#Iter", "Time/Iter",
4079  "#Okay", "#TimeLimit", "#IterLimit", "#LObjLimit", "#Interrupt", "#NumError", "#EvalError", "#OutOfMem", "#LicenseEr", "#OtherTerm",
4080  "#GlobOpt", "#LocOpt", "#Feasible", "#LocInfeas", "#GlobInfea", "#Unbounded", "#Unknown"
4081  );
4082  printedheader = TRUE;
4083  }
4084 
4085  solvetime = SCIPnlpiGetSolveTime(nlpi);
4086  if( scip->set->time_nlpieval )
4087  evaltime = SCIPnlpiGetEvalTime(nlpi);
4088  niter = SCIPnlpiGetNIterations(nlpi);
4089 
4090  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %-17s:", SCIPnlpiGetName(nlpi));
4091  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10d", SCIPnlpiGetNProblems(nlpi));
4092  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f", SCIPnlpiGetProblemTime(nlpi));
4093  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10d", SCIPnlpiGetNSolves(nlpi));
4094  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f", solvetime);
4095  if( scip->set->time_nlpieval )
4096  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f", solvetime > 0.0 ? 100.0 * evaltime / solvetime : 0.0);
4097  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10" SCIP_LONGINT_FORMAT, niter);
4098  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10.2f", niter > 0 ? solvetime / niter : 0.0);
4099 
4100  for( j = (int)SCIP_NLPTERMSTAT_OKAY; j <= (int)SCIP_NLPTERMSTAT_OTHER; ++j )
4102 
4103  for( j = (int)SCIP_NLPSOLSTAT_GLOBOPT; j <= (int)SCIP_NLPSOLSTAT_UNKNOWN; ++j )
4104  SCIPmessageFPrintInfo(scip->messagehdlr, file, " %10d", SCIPnlpiGetNSolStat(nlpi, (SCIP_NLPSOLSTAT)j));
4105 
4106  SCIPmessageFPrintInfo(scip->messagehdlr, file, "\n");
4107  }
4108 }
4109 
4110 /** comparison method for statistics tables */
4111 static
4113 { /*lint --e{715}*/
4114  return (SCIPtableGetPosition((SCIP_TABLE*)elem1) - (SCIPtableGetPosition((SCIP_TABLE*)elem2)));
4115 }
4116 
4117 /** outputs solving statistics
4118  *
4119  * @return \ref SCIP_OKAY is returned if everything worked. Otherwise a suitable error code is passed. See \ref
4120  * SCIP_Retcode "SCIP_RETCODE" for a complete list of error codes.
4121  *
4122  * @note If limits have been changed between the solution and the call to this function, the status is recomputed and
4123  * thus may to correspond to the original status.
4124  *
4125  * @pre This method can be called if SCIP is in one of the following stages:
4126  * - \ref SCIP_STAGE_INIT
4127  * - \ref SCIP_STAGE_PROBLEM
4128  * - \ref SCIP_STAGE_TRANSFORMED
4129  * - \ref SCIP_STAGE_INITPRESOLVE
4130  * - \ref SCIP_STAGE_PRESOLVING
4131  * - \ref SCIP_STAGE_EXITPRESOLVE
4132  * - \ref SCIP_STAGE_PRESOLVED
4133  * - \ref SCIP_STAGE_SOLVING
4134  * - \ref SCIP_STAGE_SOLVED
4135  */
4137  SCIP* scip, /**< SCIP data structure */
4138  FILE* file /**< output file (or NULL for standard output) */
4139  )
4140 {
4141  SCIP_TABLE** tables;
4142  int ntables;
4143  int i;
4144 
4145  assert(scip != NULL);
4146  assert(scip->set != NULL);
4147 
4148  SCIP_CALL( SCIPcheckStage(scip, "SCIPprintStatistics", TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
4149 
4150  ntables = SCIPgetNTables(scip);
4151  tables = SCIPgetTables(scip);
4152 
4153  /* sort all tables by position unless this has already been done */
4154  if( ! scip->set->tablessorted )
4155  {
4156  SCIPsortPtr((void**)tables, tablePosComp, ntables);
4157 
4158  scip->set->tablessorted = TRUE;
4159  }
4160 
4161  for( i = 0; i < ntables; ++i )
4162  {
4163  /* skip tables which are not active or only used in later stages */
4164  if( ( ! SCIPtableIsActive(tables[i]) ) || SCIPtableGetEarliestStage(tables[i]) > SCIPgetStage(scip) )
4165  continue;
4166 
4167  SCIP_CALL( SCIPtableOutput(tables[i], scip->set, file) );
4168  }
4169 
4170  return SCIP_OKAY;
4171 }
4172 
4173 /** outputs reoptimization statistics
4174  *
4175  * @return \ref SCIP_OKAY is returned if everything worked. Otherwise a suitable error code is passed. See \ref
4176  * SCIP_Retcode "SCIP_RETCODE" for a complete list of error codes.
4177  *
4178  * @pre This method can be called if SCIP is in one of the following stages:
4179  * - \ref SCIP_STAGE_INIT
4180  * - \ref SCIP_STAGE_PROBLEM
4181  * - \ref SCIP_STAGE_TRANSFORMED
4182  * - \ref SCIP_STAGE_INITPRESOLVE
4183  * - \ref SCIP_STAGE_PRESOLVING
4184  * - \ref SCIP_STAGE_EXITPRESOLVE
4185  * - \ref SCIP_STAGE_PRESOLVED
4186  * - \ref SCIP_STAGE_SOLVING
4187  * - \ref SCIP_STAGE_SOLVED
4188  */
4190  SCIP* scip, /**< SCIP data structure */
4191  FILE* file /**< output file (or NULL for standard output) */
4192  )
4193 {
4194  SCIP_Real solving;
4195  SCIP_Real presolving;
4196  SCIP_Real updatetime;
4197 
4198  SCIP_CALL( SCIPcheckStage(scip, "SCIPprintReoptStatistics", TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
4199 
4200  assert(scip != NULL);
4201 
4202  /* skip if reoptimization is disabled */
4203  if( !scip->set->reopt_enable )
4204  return SCIP_OKAY;
4205 
4206  /* skip if not problem yet */
4207  if( scip->stat == NULL )
4208  return SCIP_OKAY;
4209 
4210  solving = SCIPclockGetTime(scip->stat->solvingtimeoverall);
4211  presolving = SCIPclockGetTime(scip->stat->presolvingtimeoverall);
4212  updatetime = SCIPclockGetTime(scip->stat->reoptupdatetime);
4213 
4214  SCIPmessageFPrintInfo(scip->messagehdlr, file, "SCIP Reopt Status : finished after %d runs.\n", scip->stat->nreoptruns);
4215  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Time (sec) :\n");
4216  SCIPmessageFPrintInfo(scip->messagehdlr, file, " solving : %10.2f\n", solving);
4217  SCIPmessageFPrintInfo(scip->messagehdlr, file, " presolving : %10.2f (included in solving)\n", presolving);
4218  SCIPmessageFPrintInfo(scip->messagehdlr, file, " save time : %10.2f\n", SCIPreoptGetSavingtime(scip->reopt));
4219  SCIPmessageFPrintInfo(scip->messagehdlr, file, " update time : %10.2f\n", updatetime);
4220  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Nodes : feas infeas pruned cutoff\n");
4221  SCIPmessageFPrintInfo(scip->messagehdlr, file, " total : %10d %10d %10d %10d\n",
4224  if( scip->stat->nreoptruns > 0 )
4225  {
4226  SCIPmessageFPrintInfo(scip->messagehdlr, file, " avg : %10.2f %10.2f %10.2f %10.2f\n",
4231  }
4232  else
4233  {
4234  SCIPmessageFPrintInfo(scip->messagehdlr, file, " avg : %10s %10s %10s %10s\n", "--", "--", "--", "--");
4235  }
4236  SCIPmessageFPrintInfo(scip->messagehdlr, file, "Restarts : global local\n");
4237  SCIPmessageFPrintInfo(scip->messagehdlr, file, " first : %10d --\n", SCIPreoptGetFirstRestarts(scip->reopt));
4238  SCIPmessageFPrintInfo(scip->messagehdlr, file, " last : %10d --\n", SCIPreoptGetLastRestarts(scip->reopt));
4239  SCIPmessageFPrintInfo(scip->messagehdlr, file, " total : %10d %10d\n", SCIPreoptGetNRestartsGlobal(scip->reopt),
4241  if( scip->stat->nreoptruns > 0 )
4242  {
4243  SCIPmessageFPrintInfo(scip->messagehdlr, file, " avg : -- %10.2f\n",
4245  }
4246  else
4247  {
4248  SCIPmessageFPrintInfo(scip->messagehdlr, file, " avg : -- %10s\n", "--");
4249  }
4250 
4251  return SCIP_OKAY;
4252 }
4253 
4254 /** outputs history statistics about branchings on variables
4255  *
4256  * @return \ref SCIP_OKAY is returned if everything worked. Otherwise a suitable error code is passed. See \ref
4257  * SCIP_Retcode "SCIP_RETCODE" for a complete list of error codes.
4258  *
4259  * @pre This method can be called if SCIP is in one of the following stages:
4260  * - \ref SCIP_STAGE_INIT
4261  * - \ref SCIP_STAGE_PROBLEM
4262  * - \ref SCIP_STAGE_TRANSFORMED
4263  * - \ref SCIP_STAGE_INITPRESOLVE
4264  * - \ref SCIP_STAGE_PRESOLVING
4265  * - \ref SCIP_STAGE_EXITPRESOLVE
4266  * - \ref SCIP_STAGE_PRESOLVED
4267  * - \ref SCIP_STAGE_SOLVING
4268  * - \ref SCIP_STAGE_SOLVED
4269  */
4271  SCIP* scip, /**< SCIP data structure */
4272  FILE* file /**< output file (or NULL for standard output) */
4273  )
4274 {
4275  SCIP_VAR** vars;
4276  int totalnstrongbranchs;
4277  int v;
4278 
4279  SCIP_CALL( SCIPcheckStage(scip, "SCIPprintBranchingStatistics", TRUE, TRUE, FALSE, TRUE, TRUE, TRUE, TRUE, TRUE, FALSE, TRUE, TRUE, FALSE, FALSE, FALSE) );
4280 
4281  switch( scip->set->stage )
4282  {
4283  case SCIP_STAGE_INIT:
4284  case SCIP_STAGE_PROBLEM:
4285  SCIPmessageFPrintInfo(scip->messagehdlr, file, "problem not yet solved. branching statistics not available.\n");
4286  return SCIP_OKAY;
4287 
4290  case SCIP_STAGE_PRESOLVING:
4292  case SCIP_STAGE_PRESOLVED:
4293  case SCIP_STAGE_SOLVING:
4294  case SCIP_STAGE_SOLVED:
4295  SCIP_CALL( SCIPallocBufferArray(scip, &vars, scip->transprob->nvars) );
4296  for( v = 0; v < scip->transprob->nvars; ++v )
4297  {
4298  SCIP_VAR* var;
4299  int i;
4300 
4301  var = scip->transprob->vars[v];
4302  for( i = v; i > 0 && strcmp(SCIPvarGetName(var), SCIPvarGetName(vars[i-1])) < 0; i-- )
4303  vars[i] = vars[i-1];
4304  vars[i] = var;
4305  }
4306 
4307  SCIPmessageFPrintInfo(scip->messagehdlr, file, " locks branchings inferences cutoffs LP gain pscostcount gain variance \n");
4308  SCIPmessageFPrintInfo(scip->messagehdlr, file, "variable prio factor down up depth down up sb down up down up down up down up down up\n");
4309 
4310  totalnstrongbranchs = 0;
4311  for( v = 0; v < scip->transprob->nvars; ++v )
4312  {
4315  || SCIPgetVarNStrongbranchs(scip, vars[v]) > 0 )
4316  {
4317  int nstrongbranchs;
4318 
4319  nstrongbranchs = SCIPgetVarNStrongbranchs(scip, vars[v]);
4320  totalnstrongbranchs += nstrongbranchs;
4321  SCIPmessageFPrintInfo(scip->messagehdlr, file, "%-16s %5d %8.1f %6d %6d %6.1f %7" SCIP_LONGINT_FORMAT " %7" SCIP_LONGINT_FORMAT " %5d %8.1f %8.1f %5.1f%% %5.1f%% %15.4f %15.4f %7.1f %7.1f %15.2f %15.2f\n",
4322  SCIPvarGetName(vars[v]),
4323  SCIPvarGetBranchPriority(vars[v]),
4324  SCIPvarGetBranchFactor(vars[v]),
4328  + SCIPvarGetAvgBranchdepth(vars[v], SCIP_BRANCHDIR_UPWARDS))/2.0 - 1.0,
4330