# CPLEX Indicator Constraints in Java API

I'm using the Java API of CPLEX (12.6.1 version) to solve a MILP problem.

This is how I create 'normal' constraints:

public void charge_discharge_constraints() throws IloException {

for (int k = 0; k < periods; k++) {
for (int p = 0; p < num_p; p++) {
IloLinearNumExpr exp = model.linearNumExpr();
for (int n = 0; n < num_n; n++)
exp.addTerm(1, bc_p[n][p][k]);
exp.addTerm(1.0, bd_p[p][k]);
IloRange constr = model.addGe(1, exp, "Non simultaneous charge discharge");
}
}
}


Now, I'm trying to add an 'indicator constraint' such as:

if bd_p[p][k] == 1, -> (then) h_p[p][k] >= 4800.0


for every p and k indices.

I tried to achieve this by doing:

public void indicator_constraints() throws IloException {

for (int p = 0; p < num_p; p++) {
for (int k = 0; k < periods; k++) {
IloLinearNumExpr exp = model.linearNumExpr();
exp.addTerm(1, h_p[p][k]);
model.add(model.ifThen(model.eq(bd_p[p][k], 1.0), model.ge(exp, 4800.0)));
}
}
}


But, after having observed the generated ".lp" file, I noticed that the indicator constraints I created use the double-arrow simbol (<->), while my aim is to use the right-arrow symbol (->).

How could I achieve this?

EDIT (to add more details):

I can confirm that I have previously assigned a name to variables bd_p and h_p. Indeed, inside the LP file:

• both of them are present in the Binaries section (the section which lists the binary variables of the problem);
• they're correctly bounded between 0 and 1.

Anyway, while I was expecting that the indicator constraints which I generated should have used variables bd_p and h_p, actually (after a further investigation of the LP file) I can say that only the h_p variable is involved in the indicator constraints.

Indeed, the LP file contains indicator constraints formulated as:

IloI785: x38223#36652 = 1 <-> h_p(27,17)#34158 >= 4800


So, while h_p variable compares, bd_p variable is not present. In place of bd_p there's another variable called x followed by a progressive number.

bd_p is a binary variable, I previously assigned a name to it, it is correctly defined/bounded in the LP file, and it is used in many other "normal" (linear) constraints without any problem.

I also tried to do this small change:

public void indicator_constraints() throws IloException {
for (int p = 0; p < num_p; p++) {
for (int k = 0; k < periods; k++) {
IloLinearNumExpr exp_if = model.linearNumExpr();
IloLinearNumExpr exp_then = model.linearNumExpr();
exp_if.addTerm(1, bd_p[p][k]);
exp_then.addTerm(1, h_p[p][k]);
model.add(model.ifThen(model.eq(exp_if, 1.0), model.ge(exp_then, 4800.0)));
}
}
}


or, this other alternative:

public void indicator_constraints() throws IloException {
for (int p = 0; p < num_p; p++) {
for (int k = 0; k < periods; k++) {
IloLinearNumExpr exp_if = model.linearNumExpr();
IloLinearNumExpr exp_then = model.linearNumExpr();
exp_if.addTerm(1, bd_p[p][k]);
exp_then.addTerm(1, h_p[p][k]);
IloRange constr_if = model.addEq(1.0, exp_if);
IloRange constr_then = model.addLe(4800.0, exp_then);
model.add(model.ifThen(constr_if, constr_then));
}
}
}


but with no improvement.

So, I can't understand why in the LP file, the binary variable h_p is replaced by a unnamed variable.

Which could be the problem?

## 1 Answer

I suspect you have not assigned names to your variables. Try doing that and then exporting the .lp file, and I think you will discover that the bidirectional constraint involves a variable that CPLEX added.

As a small example, I created a model with a single binary variable "x", a single continuous variable "y" (domain [0, 10]), and a single constraint that x = 1 -> y <= 5. CPLEX added binary variables x1 and x3 and converted the one constraint I had to two constraints: x3 = 1 <-> y =< 5 and x = 1 -> x3 = 1. I'm not sure why it does that, but I presume the programmers had their reasons.

• Thank you for your suggestions, very interesting! Actually, I have correctly previoulsy assigned a name to all my variables, but you gave me the intuition to notice that, while the h_p variable is present in the indicator constraints in the LP file, the binary variable bd_p doesn't compare (in place of bd_p there's a generic variable called x followed by a progressive number). Its strange to me; anyway, I edited my original post to add some details which can be useful to you in order to help me to solve this problem. Commented Jun 8, 2021 at 22:09
• IloI785 is as I would expect. There should also be another constraint somewhere saying bd_p(27,17)#<whatever> = 1 -> x38223#36652 = 1. Are you saying that it is not present anywhere in the .lp file?
– prubin
Commented Jun 9, 2021 at 23:09