Decision Optimization

Decision Optimization

Delivers prescriptive analytics capabilities and decision intelligence to improve decision-making.


#Analytics
#DecisionOptimization
#DecisionOptimization
 View Only
  • 1.  Questions about the branchCallback CPLEX 11.2

    Posted 01/16/11 10:36 PM

    Originally posted by: SystemAdmin


    I am using CPLEX 11.2 Concert Technology C++ to branch by myself.

    However, I am a little bit confused about how the "makeBranch" method is implemented.
    in my code for a class derived from CallbackI, I did this way
    // take binary decision variable z for example 
             if ( z_vals[l_min][h_min][t_min] > 0.5 ){ //if the solution value of z_i_j_t to the LP relaxation problem is larger than 0.5
               bound[0] = 1;               //then branch at the bound of 1 in the direction of UP at first
               bound[1] = 0;               // branch at the bound of 0 in the direction of DOWN later.
               z_dir[0] = cplex.BranchUp;      
               z_dir[1] = cplex.BranchDown;    
               cout << "branch on " << z[l_min][h_min][t_min] << " on 1 at first" << endl;
             }
             else{         //if the solution value of z_i_j_t to the LP relaxation problem is smaller than 0.5
               z_dir[0] = cplex.BranchDown;     // branch at the bound of 0 in the direction of DOWN at first.
               z_dir[1] = cplex.BranchUp;        //then branch at the bound of 1 in the direction of UP later
               bound[0] = 0;
               bound[1] = 1;
               cout << "branch on " << z[l_min][h_min][t_min] << " on 0 at first" << endl;
             }
              
                 makeBranch(z[l_min][h_min][t_min], bound[0], z_dir[0], getObjValue()); //make the first branch 
                 makeBranch(z[l_min][h_min][t_min], bound[1], z_dir[1], getObjValue()); //make the second branch
              
          // I did the similar thing for binary variable of y_i_j_k_t and by some rule, I will choose to branch on z or y each time.
    


    And the resulted B&B tree is as follows:
    Tried aggregator 2 times.
    MIP Presolve eliminated 106771 rows and 31683 columns.
    MIP Presolve modified 19284 coefficients.
    Aggregator did 2755 substitutions.
    Reduced MIP has 27338 rows, 17443 columns, and 113900 nonzeros.
    Reduced MIP has 9102 binaries, 0 generals, 0 SOSs, and 0 indicators.
    Presolve time =    0.39 sec.
    Clique table members: 9187.
    MIP emphasis: balance optimality and feasibility.
    MIP search method: traditional branch-and-cut.
    Parallel mode: none, using 1 thread.
    Root relaxation solution time =    1.27 sec.
     
            Nodes                                         Cuts/ 
       Node  Left     Objective  IInf  Best Integer     Best Node    ItCnt     Gap         Variable B NodeID Parent  Depth
     
          0     0    10933.3801   183                  10933.3801     7684         
          0     0    10941.0054   646                   Cuts: 272    12203         
          0     0    10944.0997   210                   Cuts: 182    14060         
          0     0    10952.1677   444                    Cuts: 46    16250         
          0     0    10954.9100   369                    Cuts: 74    18438         
          0     0    10956.0782   386                    Cuts: 26    19183         
          0     0    10957.6825   500                    Cuts: 32    20337         
          0     0    10958.1474   338                    Cuts: 22    20501         
          0     0    10958.4589   521                    Cuts: 12    20728         
          0     0    10958.5293   467                    Cuts: 14    20800         
          0     0    10958.5357   477                     Cuts: 6    20809         
    branch on z_0_0_2[0..1]  on 0 at first
          0     2    10958.5357   477                  10958.5357    20809                                 0             0
    Elapsed time =  17.91 sec. (tree size =  0.00 MB, solutions = 0)
    branch on z_3_0_4[0..1]  on 0 at first
          1     3    10958.5411   360                  10958.5357    20845                  z_0_0_2 D      1      0      1
    branch on z_2_0_3[0..1]  on 0 at first
          2     4    10959.0596   314                  10958.5357    20940                  z_3_0_4 D      2      1      2
    branch on z_3_0_3[0..1]  on 0 at first
          3     5    10986.4547   298                  10958.5357    21766                  z_3_0_4 U      3      1      2
    branch on z_6_0_2[0..1]  on 0 at first
          4     6    10960.2118   361                  10958.5357    22455                  z_2_0_3 D      4      2      3
    branch on z_0_0_3[0..1]  on 0 at first
          5     7    10977.8945   278                  10958.5357    23213                  z_2_0_3 U      5      2      3
    branch on z_5_0_4[0..1]  on 0 at first
          6     8    10960.2119   330                  10958.5357    23215                  z_6_0_2 D      6      4      4
    branch on z_4_0_4[0..1]  on 0 at first
          7     9    10973.2998   414                  10958.5357    26229                  z_5_0_4 D      7      6      5
    branch on z_5_0_3[0..1]  on 0 at first
          8    10    10973.7960   281                  10958.5357    26887                  z_5_0_4 U      8      6      5
    branch on z_1_0_3[0..1]  on 1 at first
          9    11    10973.7332   399                  10958.5357    27081                  z_4_0_4 D      9      7      6
    branch on z_0_0_4[0..1]  on 1 at first
         10    12    11158.9533   207                  10958.5357    28923                  z_4_0_4 U     10      7      6
    branch on z_7_0_4[0..1]  on 0 at first
         11    13    10973.8161   412                  10958.5357    29220                  z_1_0_3 U     11      9      7
    branch on z_2_0_4[0..1]  on 1 at first
         12    14    11003.9091   446                  10958.5357    30418                  z_1_0_3 D     12      9      7
    branch on z_0_0_3[0..1]  on 1 at first
         13    15    10973.8501   403                  10958.5357    30590                  z_7_0_4 D     13     11      8
    branch on z_7_0_3[0..1]  on 0 at first
         14    16    11237.1843   165                  10958.5357    34589                  z_7_0_4 U     14     11      8
    branch on y_1_0_2_4[0..1]  on 0 first
         15    17    10976.9832   418                  10958.5357    34972                  z_0_0_3 U     15     13      9
    branch on z_2_0_4[0..1]  on 1 at first
         16    18    10989.8479   457                  10958.5357    36671                  z_0_0_3 D     16     13      9
    branch on y_1_0_2_3[0..1]  on 0 first
         17    19    10976.9832   418                  10958.5357    36671                y_1_0_2_4 D     17     15     10
    branch on y_1_0_2_2[0..1]  on 0 first
         18    20    10976.9832   418                  10958.5357    36671                y_1_0_2_3 D     18     17     11
    branch on y_1_0_2_0[0..1]  on 0 first
         19    21    10976.9832   418                  10958.5357    36671                y_1_0_2_2 D     19     18     12
    branch on y_9_0_2_2[0..1]  on 0 first
         20    22    10976.9832   418                  10958.5357    36671                y_1_0_2_0 D     20     19     13
    Elapsed time = 111.90 sec. (tree size =  0.16 MB, solutions = 0)
    branch on y_9_0_2_4[0..1]  on 0 first
         21    23    10976.9832   417                  10958.5357    36672                y_9_0_2_2 D     21     20     14
    branch on y_8_0_2_4[0..1]  on 0 first
         22    24    10976.9832   415                  10958.5357    36673                y_9_0_2_4 D     22     21     15
    branch on y_1_0_0_4[0..1]  on 0 first
         23    25    10976.9832   412                  10958.5357    36674                y_8_0_2_4 D     23     22     16
    branch on y_2_0_2_3[0..1]  on 0 first
         24    26    10976.9854   400                  10958.5357    37161                y_1_0_0_4 D     24     23     17
    branch on y_2_0_2_4[0..1]  on 0 first
         25    27    10976.9854   400                  10958.5357    37161                y_2_0_2_3 D     25     24     18
    branch on y_2_0_0_0[0..1]  on 0 first
         26    28    10976.9854   398                  10958.5357    37164                y_2_0_2_4 D     26     25     19
    branch on y_0_0_2_4[0..1]  on 0 first
         27    29    10976.9885   410                  10958.5357    37328                y_2_0_0_0 D     27     26     20
    


    What makes me surprised is that sometimes CPLEX will make 2 branches on the binary variable in both directions at a node (e.g at NodeID 1, it created NodeID 2 and 3), while sometimes it will only make one branch (e.g. at NodeID 4, it created only NodeID 6 and for all the y variables, it always created only one branch). Should it be supposed to make 2 branches each time according to my code?

    What is more, I am also confused about the order of investigating the 2 branches generated at the same parent node. I found sometimes CPLEX will investigate the branch at the bound of 1 in the direction of BranchUp at first, sometimes it will investigate the branch at the bound of 0 in the direction of BranchDown at first, even I create the branch at the bound of 1 in the direction of BranchUp first....Thanks for any help.
    #CPLEXOptimizers
    #DecisionOptimization


  • 2.  Re: Questions about the branchCallback CPLEX 11.2

    Posted 01/17/11 08:27 AM

    Originally posted by: SystemAdmin


    CPLEX is creating both children each time, but you don't see each child in the log until CPLEX visits it. Watch the depth indicator on the right. Early on, CPLEX is in a pattern where it creates two children, visits the left child, then doubles back to the right child (presumably due to a better bound, since the log indicates neither integer feasibility nor infeasibility at any of the early nodes). Starting at node 16, CPLEX goes on a dive, visiting consecutive left children. The right children will show up eventually, when CPLEX backtracks.

    /Paul

    Mathematicians are like Frenchmen: whenever you say something to them, they translate it into their own language, and at once it is something entirely different. (Goethe)
    #CPLEXOptimizers
    #DecisionOptimization


  • 3.  Re: Questions about the branchCallback CPLEX 11.2

    Posted 01/17/11 08:46 AM

    Originally posted by: SystemAdmin


    Paul, thanks for your reply. So if I would like CPLEX to visit the branch I created first ignoring the quality of the bound, what should I do? Using NodeCallback to impact the order of traversing? In the "Goal" of CPLEX, I know it generates a stack automatically following some rule like "first in first out". In the callback section, I did not find anything like this, so I guess, I need to propose something by myself to force CPLEX to visit the branch I create first? Thanks.
    #CPLEXOptimizers
    #DecisionOptimization


  • 4.  Re: Questions about the branchCallback CPLEX 11.2

    Posted 01/18/11 05:03 PM

    Originally posted by: SystemAdmin


    > jimzhang wrote:
    > Paul, thanks for your reply. So if I would like CPLEX to visit the branch I created first ignoring the quality of the bound, what should I do? Using NodeCallback to impact the order of traversing?

    Yes, you'll need to use a node callback to specify the order in which nodes are visited.

    /Paul

    Mathematicians are like Frenchmen: whenever you say something to them, they translate it into their own language, and at once it is something entirely different. (Goethe)
    #CPLEXOptimizers
    #DecisionOptimization


  • 5.  Re: Questions about the branchCallback CPLEX 11.2

    Posted 01/17/11 08:33 AM

    Originally posted by: SystemAdmin


    Creating the branches in a particular order does not instruct CPLEX to visit the branches in that order.
    If you want to visit the branches in a particular order then you have to use a node selection callback.
    #CPLEXOptimizers
    #DecisionOptimization


  • 6.  Re: Questions about the branchCallback CPLEX 11.2

    Posted 01/17/11 09:06 AM

    Originally posted by: SystemAdmin


    Hi, Daniel, thanks for your reply.

    In this case, is it good if I do as follows:
    I create a class derived from NodeData recording the index implying the creation order, And for each 2 nodes having the same depth, compare their the indices, the one telling that it is created first should be visited at first? Thanks.
    #CPLEXOptimizers
    #DecisionOptimization


  • 7.  Re: Questions about the branchCallback CPLEX 11.2

    Posted 01/24/11 01:36 AM

    Originally posted by: SystemAdmin


    You can also use the NodeId of a node directly (this should be available through the NodeCallback API). The smaller the node id the earlier the node was created. And using that you can of course tell which node was created earlier as you described.
    #CPLEXOptimizers
    #DecisionOptimization