5.6.10. MISOCP Modeling and Optimization in Java

In this chapter, we will use MindOpt JAVA API to model and solve the mixed-integer second-order cone program in MIQCP Example II.

Import the MindOpt package:

25 */

Create an optimization environment and model:

29    public static void main(String[] args) {
30        // Create environment and model.
31        MDOEnv env = new MDOEnv();

Next, we set the model name and optimization sense. Then, we call MDOModel.addVar to add five variables. Their lower bounds, upper bounds, types, names, and linear objective coefficients are all passed directly as arguments.

Note

To mark a variable as integer, set its type to 'I' in the call to MDOModel.addVar.

35            // Step 1. Input model.
36            model.set(MDO.StringAttr.ModelName, "MISOCPEx1");
37
38            // Change to minimization problem.
39            model.set(MDO.IntAttr.ModelSense, MDO.MINIMIZE);
40
41            // Add variables. The linear objective coefficients are specified directly.
42            MDOVar[] x = new MDOVar[5];
43            x[0] = model.addVar(0.0, 10.0, 1.0, 'I', "x0");
44            x[1] = model.addVar(0.0, MDO.INFINITY, 2.0, 'I', "x1");
45            x[2] = model.addVar(0.0, MDO.INFINITY, 1.0, 'I', "x2");
46            x[3] = model.addVar(0.0, MDO.INFINITY, 1.0, 'C', "x3");

Note

Since the linear objective coefficients are passed directly during variable creation, there is no separate call to MDOModel.setObjective.

We now add the linear constraints. For the Java API, this involves creating an MDOExpr object for each constraint and adding terms to it.

  • Constraint c0: \(x_0 + x_1 + 2x_2 + 3x_3 \geq 1\)

  • Constraint c1: \(x_0 - x_2 + 6x_3 = 1\)

These are added to the model using MDOModel.addConstr:

48            // Add linear constraint c0: 1 x0 + 1 x1 + 2 x2 + 3 x3 >= 1
49            MDOExpr c0_expr = new MDOExpr();
50            c0_expr.addTerms(new double[] { 1.0, 1.0, 2.0, 3.0 }, new MDOVar[] { x[0], x[1], x[2], x[3] });
51            model.addConstr(c0_expr, MDO.GREATER_EQUAL, 1.0, "c0");
52
53            // Add linear constraint c1: 1 x0 - 1 x2 + 6 x3 = 1
54            MDOExpr c1_expr = new MDOExpr();
55            c1_expr.addTerms(new double[] { 1.0, -1.0, 6.0 }, new MDOVar[] { x[0], x[2], x[3] });

Finally, we add the quadratic (second-order cone) constraint:

  • c2: \(x_1^2 + x_2^2 - x_4^2 \leq 0\)

This is done by creating an MDOQuadExpr object and adding the quadratic terms. The constraint is then added to the model using MDOModel.addQConstr.

58            // Add second-order cone constraint c2: x_1^2 + x_2^2 - x_4^2 <= 0
59            MDOQuadExpr c2_expr = new MDOQuadExpr();
60            // This constraint has no linear part. We only add the quadratic terms.
61            c2_expr.addTerms(
62                    new double[] { 1.0, 1.0, -1.0 },      // values
63                    new MDOVar[] { x[1], x[2], x[4] },     // first variable indices
64                    new MDOVar[] { x[1], x[2], x[4] }      // second variable indices
65            );

Once the model is fully constructed, we solve it by calling MDOModel.optimize:

69            // Step 2. Solve the problem.

After solving, we check the solution status and retrieve the optimal objective value and variable values.

77            // exist, making it necessary to check the SolCount property.
78            if (model.get(MDO.IntAttr.Status) == MDO.OPTIMAL || model.get(MDO.IntAttr.Status) == MDO.SUB_OPTIMAL
79                    || model.get(MDO.IntAttr.SolCount) > 0) {
80                System.out.println("Optimal objective value is: " + model.get(MDO.DoubleAttr.ObjVal));
81                System.out.println("Decision variables: ");
82                for (int i = 0; i < 5; i++) {
83                    System.out.println("x[" + i + "] = " + x[i].get(MDO.DoubleAttr.X));
84                }
85            } else {
86                System.out.println("No feasible solution.");

Finally, we dispose of the model and environment to free up resources.

95        } finally {
96            // Step 4. Free the model.
97            model.dispose();

The complete example code is shown in MdoMISOCPEx1.java:

  1/**
  2 *  Description
  3 *  -----------
  4 *
  5 *  Formulation
  6 *  -----------
  7 *
  8 Minimize
  9 *    obj: 1 x0 + 2 x1 + 1 x2 + 1 x3 + 0.5 x_4
 10 *
 11 *
 12 *  Subject To
 13 *   c0 : 1 x0 + 1 x1 + 2 x2 + 3 x3 >= 1
 14 *   c1 : 1 x0 - 1 x2 + 6 x3  = 1
 15 *   c2 : x_1^2 + x_2^2 - x_4^2 <= 0
 16 *  Bounds
 17 *    0 <= x0 <= 10
 18 *    0 <= x1
 19 *    0 <= x2
 20 *    0 <= x3
 21 *    0 <= x4
 22 *  Integer
 23 *  x0, x1, x2
 24 *  End
 25 */
 26import com.alibaba.damo.mindopt.*;
 27
 28public class MdoMISOCPEx1 {
 29    public static void main(String[] args) {
 30        // Create environment and model.
 31        MDOEnv env = new MDOEnv();
 32        MDOModel model = new MDOModel(env);
 33
 34        try {
 35            // Step 1. Input model.
 36            model.set(MDO.StringAttr.ModelName, "MISOCPEx1");
 37
 38            // Change to minimization problem.
 39            model.set(MDO.IntAttr.ModelSense, MDO.MINIMIZE);
 40
 41            // Add variables. The linear objective coefficients are specified directly.
 42            MDOVar[] x = new MDOVar[5];
 43            x[0] = model.addVar(0.0, 10.0, 1.0, 'I', "x0");
 44            x[1] = model.addVar(0.0, MDO.INFINITY, 2.0, 'I', "x1");
 45            x[2] = model.addVar(0.0, MDO.INFINITY, 1.0, 'I', "x2");
 46            x[3] = model.addVar(0.0, MDO.INFINITY, 1.0, 'C', "x3");
 47            x[4] = model.addVar(0.0, MDO.INFINITY, 0.5, 'C', "x4");
 48
 49            // Add linear constraint c0: 1 x0 + 1 x1 + 2 x2 + 3 x3 >= 1
 50            MDOExpr c0_expr = new MDOExpr();
 51            c0_expr.addTerms(new double[] { 1.0, 1.0, 2.0, 3.0 }, new MDOVar[] { x[0], x[1], x[2], x[3] });
 52            model.addConstr(c0_expr, MDO.GREATER_EQUAL, 1.0, "c0");
 53
 54            // Add linear constraint c1: 1 x0 - 1 x2 + 6 x3 = 1
 55            MDOExpr c1_expr = new MDOExpr();
 56            c1_expr.addTerms(new double[] { 1.0, -1.0, 6.0 }, new MDOVar[] { x[0], x[2], x[3] });
 57            model.addConstr(c1_expr, MDO.EQUAL, 1.0, "c1");
 58
 59            // Add second-order cone constraint c2: x_1^2 + x_2^2 - x_4^2 <= 0
 60            MDOQuadExpr c2_expr = new MDOQuadExpr();
 61            // This constraint has no linear part. We only add the quadratic terms.
 62            c2_expr.addTerms(
 63                    new double[] { 1.0, 1.0, -1.0 },      // values
 64                    new MDOVar[] { x[1], x[2], x[4] },     // first variable indices
 65                    new MDOVar[] { x[1], x[2], x[4] }      // second variable indices
 66            );
 67            model.addQConstr(c2_expr, MDO.LESS_EQUAL, 0.0, "c2");
 68
 69            // Step 2. Solve the problem.
 70            model.optimize();
 71
 72            // Step 3. Retrieve model status and solution.
 73            // For MIP(MILP,MIQP, MIQCP) problems, if the solving process
 74            // terminates early due to reasons such as timeout or interruption,
 75            // the model status will indicate termination by timeout (or
 76            // interruption, etc.). However, suboptimal solutions may still
 77            // exist, making it necessary to check the SolCount property.
 78            if (model.get(MDO.IntAttr.Status) == MDO.OPTIMAL || model.get(MDO.IntAttr.Status) == MDO.SUB_OPTIMAL
 79                    || model.get(MDO.IntAttr.SolCount) > 0) {
 80                System.out.println("Optimal objective value is: " + model.get(MDO.DoubleAttr.ObjVal));
 81                System.out.println("Decision variables: ");
 82                for (int i = 0; i < 5; i++) {
 83                    System.out.println("x[" + i + "] = " + x[i].get(MDO.DoubleAttr.X));
 84                }
 85            } else {
 86                System.out.println("No feasible solution.");
 87            }
 88        } catch (MDOException e) {
 89            System.out.println("Received Mindopt exception.");
 90            System.out.println(" - Code          : " + e.getErrorCode());
 91            System.out.println(" - Reason        : " + e.getMessage());
 92        } catch (Exception e) {
 93            System.out.println("Received exception.");
 94            System.out.println(" - Reason        : " + e.getMessage());
 95        } finally {
 96            // Step 4. Free the model.
 97            model.dispose();
 98            env.dispose();
 99        }
100    }
101}