Decision Optimization

Decision Optimization

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

 View Only
  • 1.  How to warm-start with partial solution in Java API

    Posted Tue May 26, 2020 04:10 PM
    Edited by System Admin Fri January 20, 2023 04:16 PM
    Hi,

    I'd like to warm-start a MILP with multiple partial solutions. I am presenting a MWE below.

    int numNodes = 1000;
    
    IloIntVar[] x = new IloIntVar[numNodes];
    IloIntVar[] y = new IloIntVar[numNodes];
      
    for(int i=0; i< numNodes; i++) { 
      x[i] = cplex.boolVar("x_"+ i);   
      y[i] = cplex.boolVar("y_"+ i);
    }
    
    HashMap<Integer, Set<Integer>> candidateSolutions = new HashMap<Integer, Set<Integer>>();
    
    Path myFilePath = Paths.get(DATADIR).resolve(Paths.get("solutions.txt"));    	
    try {
         Files.lines(myFilePath).forEach(line -> {
         String[] columnValues = line.split("\\s+");
         Set<Integer> yVars= new HashSet<Integer>();
         for(int i =1 ; i < columnValues.length; i++) {
              yVars.add(Integer.valueOf(columnValues[i]));
          }
          candidateSolutions.put(Integer.valueOf(columnValues[0]),leaves );
           });
    } catch (IOException e) {
          e.printStackTrace();
    }
    
    // Suppose I have two different partial solutions. candidateSolutions are: 
    // 1) key = (x[1] = 1),  values = (y[10] = 1, y[62] =1) 
    // 2) key = (x[34] = 1), values =  (y[23] = 1, y[456] = 1, y[92] =1)​
    
    

    Before I have used warm-start when I have the full solution with multi-dimensional variables. However, I could not get away with the scenario shown above. I was wondering if someone could help me with this.

    Here is a CPLEX source for warm-star in Java API.






    ------------------------------
    Ser Giovio
    ------------------------------
    #DecisionOptimization


  • 2.  RE: How to warm-start with partial solution in Java API
    Best Answer

    Posted Wed May 27, 2020 01:17 AM
    If I understand correctly then an entry a => { b, c } in your map represents a solution x[a]=1, y[b]=1, y[c]=1.

    You have to convert this into a flat array of variables and values and then use IloCplex.addMIPStart as in this untested code:
    for (Map.Entry<Integer,Set<Integer>> e : candidateSolution) {
      IloNumVar[] vars = new IloNumVar[1 + e.getValue().getSize()];
      double[] val = new double[vars.length];
      int idx = 0;
      vars[idx] = x[e.getKey()];
      vals[idx++] = 1;
      for (Integer yIdx : e.getValue()) {
        vars[idx] = y[yIdx];
        vals[idx++] = 1;
      }
      cplex.addMIPStart(vars, vals);
    }
    Note that you may want to use a TreeMap instead of a HashMap for candidateSolution or may want to sort the candidate solutions before adding them as MIP starts.
    The order of MIP starts makes a difference and so you may want to have something that is guaranteed to be the same in every run.

    ------------------------------
    Daniel Junglas
    ------------------------------



  • 3.  RE: How to warm-start with partial solution in Java API

    Posted Wed May 27, 2020 04:46 AM
    Hi @Daniel Junglas,

    You're right that ​about "If I understand correctly then an entry a => { b, c } in your map represents a solution x[a]=1, y[b]=1, y[c]=1."

    Thanks for the help!  I started using TreeMap<Integer, Set<Integer>> candidateSolutions= new TreeMap<Integer, Set<Integer>>(); as you suggested. According to my preliminary tests, it seems like everything is working fine.


    ------------------------------
    Ser Giovio
    ------------------------------