Hello,
Unfortunately, there is no native way to relax SOS variable sets. However, you are right in that we could improve the linear relaxer by
replacing SOS by linear constraints in the relaxed model.
Note that for SOS2, the relaxation will be much weaker, as the constraint that only two adjacent variables can be equal to 1 cannot be enforced.
This will be fixed in the next version of DOcplex. Meanwhile, I can propose the code below to implement a relaxation of SOS: this code
saves SOS info, clears them, calls relaxer and then adds constraints for each SOS.
def relax_sos_sets(mdl):# 1. save sos infosaved_sos_sets = []for sos in mdl.iter_sos():saved_sos_sets.append((list(sos.iter_variables()), sos.sos_type))# 2. clear sos and relax model without sosmdl.clear_sos()relaxed_mdl = Lrx.make_relaxed_model(mdl)assert relaxed_mdl is not None# 3. add relaxation linear constraint for sosfor s, (sosvars, sostype) in enumerate(saved_sos_sets, start=1):relaxed_vars = [relaxed_mdl.get_var_by_index(dv.index) for dv in sosvars]sosval = sostype.valuerelaxed_mdl.add(relaxed_mdl.sum_vars(relaxed_vars) <= sosval, f"relaxed_sos{sosval}#{s}")# 4. restore sos in initial modelmdl.add_sos(sosvars, sostype)return relaxed_mdlSorry for the inconvenience, and don't hesitate to come back to us if this temp code is not sufficient.
Philippe.
------------------------------
Philippe Couronne
------------------------------