Hi,
I used ampl.setOption(‘cplex_options’,‘poolstub savesol’)to generate feasible solution, but I do not know how to open this files and see the generated solutions
Could you please help? Thanks
Hi,
I used ampl.setOption(‘cplex_options’,‘poolstub savesol’)to generate feasible solution, but I do not know how to open this files and see the generated solutions
Could you please help? Thanks
CPLEX organizes the solutions as follows:
solution savesol<n>.sol
where is replaced by the solution number – for example, “solution savesol2.sol;” to read the second solution file. Here is an example of a loop that reads through all of the solutions:
for {k in 1..Total_Cost.npool} {
solution ("savesol" & k & ".sol");
display Trans;
};
(Replace Total_Cost by the name of your objective, and “display Trans;” by the commands you want to use to view or process each solution.)
Thanks a lot, it works well in AMPL. Is there a link to show how to do that in python as I am using amplpy?
Using amplpy, you can do that as follows:
from amplpy import AMPL
ampl = AMPL()
ampl.eval(
r"“”
set I := 1…1000000;
var x{I} integer >= 0 <= 1;
param v{i in I} := 10 + Irand224() mod 200;
param w{i in I} := v[i] + Irand224() mod 200;
maximize profit: sum{i in I} v[i] * x[i];
s.t. capacity: sum{i in I} x[i] <= 200;
“”"
)
ampl.option[“solver”] = “cplex”
ampl.option[“cplex_options”] = “poolstub savesol”
ampl.solve()
for i in range(1, ampl.get_value(“profit.npool”) + 1):
ampl.eval(f"solution savesol{i}.sol;“) # load the solution
print(i, ampl.get_data(r”{i in I: x[i] > 0} x[i]").to_dict()) # display the non-zero variables
Thanks a lot for your reply. I changed the name of the objective function from profit to cost, I tried the following :
for i in range(1, ampl.get_value(“cost.npool”) + 1):
ampl.eval(f"solution savesol{i}.sol;“)
print(i, ampl.get_data(r"x”).to_dict())
But it gives me this error
File “C:\Users\enhan\PycharmProjects\strategiesHM\scripts\get_AMPL_solution.py”, line 53, in main
for i in range(1, ampl.get_value(“cost.npool”) + 1):
^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File “C:\Users\enhan\AppData\Local\Programs\Python\Python311\Lib\site-packages\amplpy\ampl.py”, line 437, in get_value
return self._impl.getValue(scalar_expression)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
RuntimeError: file -
line 1 offset 33
Bad suffix .npool for cost
Any idea about resolving this error? thanks
Did you set CPLEX options with ampl.option[“cplex_options”] = “poolstub savesol”? Please send us the output from cplex, it should indicate that it exported that suffix if poolstub was set.
Here is my script in python
def main(argc, argv):
#os.chdir(os.path.dirname(file) or os.curdir)
ampl.set_option(“solver”, “cplex”)
ampl.setOption(‘cplex_options’,‘poolstub savesol’)
if argc > 1:
ampl.set_option(“solver”, argv[1])
ampl.read(“C:/bin/lin_strategies.mod”)
ampl.read_data(“C:/bin/strategies_1.txt”)
ampl.solve()
for i in range(1, ampl.get_value(“cost.npool”) + 1):
ampl.eval(f"solution savesol{i}.sol;“) # load the solution
data_x = ampl.get_data(r"x”).to_dict() # store the value of variable x
print(data_x)
if name == “main”:
try:
main(len(sys.argv), sys.argv)
except Exception as e:
print(e)
raise
Now it gives me this output. It doesn’t print data_x
CPLEX 12.6.0.1: poolstub savesol
CPLEX 12.6.0.1: optimal integer solution within mipgap or absmipgap; objective 43723.26731
6645 MIP simplex iterations
0 branch-and-bound nodes
absmipgap = 3, relmipgap = 6.86134e-05
Wrote 12 solutions in solution pool
to files savesol1.sol … savesol12.sol.
suffix npool OUT;
How to save x in a new variable, then print it?
Also, I want to do something similar using Gurobi because it is faster. I used the following to set the option: ampl.setOption(‘gurobi_options’, ‘ams_stub=allopt ams_mode=2 ams_epsabs=0.5’)
and the following loop to access the solution pool
for i in range(1, ampl.get_value(“cost.npool”) + 1):
ampl.eval(f"solution allopt{i}.sol;“) # load the solution
data_x = ampl.get_data(r"x”).to_dict() # store the value of variable x
print(data_x)
but it doesn’t work, and gives me this error
Gurobi 5.6.3: ams_stub=allopt
Gurobi 5.6.3: optimal solution; objective 43723.26731
56105 simplex iterations
plus 74 simplex iterations for intbasis
absmipgap = 3, relmipgap = 6.86e-05
Alternative MIP solution 1, objective = 44973.26731
Alternative MIP solution 2, objective = 45571.76731
Alternative MIP solution 3, objective = 49931.26731
Alternative MIP solution 4, objective = 52515.26731
4 alternative MIP solutions written to allopt1.sol
allopt4.sol
“option abs_boundtol 2.220446049250313e-16;”
or “option rel_boundtol 2.220446049250313e-16;”
will change deduced dual values.
file -
line 1 offset 33
Bad suffix .npool for cost
Traceback (most recent call last):
File “C:\Program Files\JetBrains\PyCharm 2023.1\plugins\python\helpers\pydev\pydevconsole.py”, line 364, in runcode
coro = func()
^^^^^^
File “”, line 1, in
File “C:\Program Files\JetBrains\PyCharm 2023.1\plugins\python\helpers\pydev_pydev_bundle\pydev_umd.py”, line 198, in runfile
pydev_imports.execfile(filename, global_vars, local_vars) # execute the script
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File “C:\Program Files\JetBrains\PyCharm 2023.1\plugins\python\helpers\pydev_pydev_imps_pydev_execfile.py”, line 18, in execfile
exec(compile(contents+“\n”, file, ‘exec’), glob, loc)
File “C:\Users\enhan\PycharmProjects\strategiesHM\scripts\get_AMPL_solution.py”, line 109, in
main(len(sys.argv), sys.argv)
File “C:\Users\enhan\PycharmProjects\strategiesHM\scripts\get_AMPL_solution.py”, line 58, in main
for i in range(1, ampl.get_value(“cost.npool”) + 1):
^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File “C:\Users\enhan\AppData\Local\Programs\Python\Python311\Lib\site-packages\amplpy\ampl.py”, line 437, in get_value
return self._impl.getValue(scalar_expression)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
RuntimeError: file -
line 1 offset 33
Bad suffix .npool for cost
Thanks a lot for your support
You have Gurobi 5.6.3 and CPLEX 12.6.0.1, which are extremely old versions of both solvers (release in 2014). By upgrading to the latest version, with Gurobi 10, you can do that as follows:
from amplpy import AMPL
ampl = AMPL()
ampl.eval(
r"“”
set I := 1…10000;
var x{I} integer >= 0 <= 1;
param v{i in I} := 10 + Irand224() mod 200;
param w{i in I} := v[i] + Irand224() mod 200;
maximize profit: sum{i in I} v[i] * x[i];
s.t. capacity: sum{i in I} x[i] <= 200;
“”"
)
ampl.option[“solver”] = “gurobi”
ampl.option[“gurobi_options”] = “solstub=savesol”
ampl.solve()
for i in range(1, ampl.get_value(“profit.npool”) + 1):
ampl.eval(f"solution savesol{i}.sol;“)
print(
ampl.get_data(r”{i in 1…_nvars: _var[i] != 0} (_varname[i], _var[i])").to_list(
skip_index=True
),
)
In the code example from the previous message I retrieved the values for variable x, but you need to adjust the code to the variable names in your models. In the code example above, it retrieves the values for all non-zero variables in a list of pairs (variable, value).
It works fine with the latest Cplex, but still I have the same problem with Groubi 10, please see below. Thanks
PyDev console: starting.
Python 3.11.4 (tags/v3.11.4:d2340ef, Jun 7 2023, 05:45:37) [MSC v.1934 64 bit (AMD64)] on win32
runfile(‘C:\Users\enhan\PycharmProjects\strategiesHM\scripts\get_AMPL_solution.py’, wdir=‘C:\Users\enhan\PycharmProjects\strategiesHM’)
Gurobi 10.0.2: sol:poolgapabs = 150
Gurobi 10.0.2: optimal solution; objective 43723.26731
6793 simplex iterations
1 branching nodes
absmipgap=3, relmipgap=6.86134e-05
file -
line 1 offset 33
Bad suffix .npool for cost
Traceback (most recent call last):
File “C:\Program Files\JetBrains\PyCharm 2023.1\plugins\python\helpers\pydev\pydevconsole.py”, line 364, in runcode
coro = func()
^^^^^^
File “”, line 1, in
File “C:\Program Files\JetBrains\PyCharm 2023.1\plugins\python\helpers\pydev_pydev_bundle\pydev_umd.py”, line 198, in runfile
pydev_imports.execfile(filename, global_vars, local_vars) # execute the script
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File “C:\Program Files\JetBrains\PyCharm 2023.1\plugins\python\helpers\pydev_pydev_imps_pydev_execfile.py”, line 18, in execfile
exec(compile(contents+“\n”, file, ‘exec’), glob, loc)
File “C:\Users\enhan\PycharmProjects\strategiesHM\scripts\get_AMPL_solution.py”, line 109, in
main(len(sys.argv), sys.argv)
File “C:\Users\enhan\PycharmProjects\strategiesHM\scripts\get_AMPL_solution.py”, line 58, in main
for i in range(1, ampl.get_value(“cost.npool”) + 1):
^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File “C:\Users\enhan\AppData\Local\Programs\Python\Python311\Lib\site-packages\amplpy\ampl.py”, line 437, in get_value
return self._impl.getValue(scalar_expression)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
RuntimeError: file -
line 1 offset 33
Bad suffix .npool for cost
Could you please send us the line where you set Gurobi options?
It should be something like ampl.option[“gurobi_options”] = “solstub=savesol” but the solver output only shows “sol:poolgapabs = 150”. You can combine the two options as follows:
…
ampl.option[“gurobi_options”] = “solstub=savesol sol:poolgapabs = 150”
…
Thanks for the support, it works fine with Groubi. Now, using Cplex, if I set this option ampl.setOption(‘cplex_options’, “mipsearch = 2”) to change the search method it gives an error. Please see below
import sys
from amplpy import AMPL, Environment
ampl = AMPL(Environment(r’C:/bin’))
def main(argc, argv):
#os.chdir(os.path.dirname(file) or os.curdir)
ampl.set_option(“solver”, “cplex”)
ampl.setOption(‘cplex_options’,‘poolstub savesol’)
ampl.setOption(‘cplex_options’, “mipsearch = 2”)
if argc > 1:
ampl.set_option(“solver”, argv[1])
ampl.read(“C:/bin/lin_strategies.mod”)
ampl.read_data(“C:/bin/strategies_1.txt”)
ampl.solve()
for i in range(1, ampl.get_value(“cost.npool”) + 1):
ampl.eval(f"solution savesol{i}.sol;“) # load the solution
data_x = ampl.get_data(r"x”).to_dict() # store the value of variable x
print(data_x)
if name == “main”:
try:
main(len(sys.argv), sys.argv)
except Exception as e:
print(e)
raise
it gives this error
CPLEX 22.1.1.0: mipsearch = 2
CPLEX 22.1.1.0: optimal integer solution within mipgap or absmipgap; objective 43723.26731
498571 MIP simplex iterations
4377 branch-and-bound nodes
absmipgap = 4.25, relmipgap = 9.72023e-05
file -
line 1 offset 33
Bad suffix .npool for cost
Traceback (most recent call last):
File “C:\Program Files\JetBrains\PyCharm 2023.1\plugins\python\helpers\pydev\pydevconsole.py”, line 364, in runcode
coro = func()
^^^^^^
File “”, line 1, in
File “C:\Program Files\JetBrains\PyCharm 2023.1\plugins\python\helpers\pydev_pydev_bundle\pydev_umd.py”, line 198, in runfile
pydev_imports.execfile(filename, global_vars, local_vars) # execute the script
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File “C:\Program Files\JetBrains\PyCharm 2023.1\plugins\python\helpers\pydev_pydev_imps_pydev_execfile.py”, line 18, in execfile
exec(compile(contents+“\n”, file, ‘exec’), glob, loc)
File “C:\Users\enhan\PycharmProjects\strategiesHM\scripts\try_solver.py”, line 30, in
main(len(sys.argv), sys.argv)
File “C:\Users\enhan\PycharmProjects\strategiesHM\scripts\try_solver.py”, line 23, in main
for i in range(1, ampl.get_value(“cost.npool”) + 1):
^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File “C:\Users\enhan\AppData\Local\Programs\Python\Python311\Lib\site-packages\amplpy\ampl.py”, line 437, in get_value
return self._impl.getValue(scalar_expression)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
RuntimeError: file -
line 1 offset 33
Bad suffix .npool for cost
When you set the same option multiple times only the last value is kept. For instance:
ampl.setOption(‘cplex_options’,‘poolstub savesol’)
ampl.setOption(‘cplex_options’, “mipsearch = 2”)
is equivalent to just:
ampl.setOption(‘cplex_options’, “mipsearch = 2”)
In order to set both options you need to set them as follows:
ampl.setOption(‘cplex_options’,‘poolstub savesol mipsearch = 2’)
it works perfect now, thanks a lot.
I have another issue, I set this option ampl.setOption(‘cplex_options’,‘poolstub savesol mipsearch = 2 nodesel = 3’) , and solved the model 10 times using looping. The pool of the first iteration contains 28 solutions, but afterwards the pool of at any other iteration contains only two solutions. Is there a reason for that? I am trying to generate as much feasible solutions as passible
Also, how to add a new seed to this option ampl.setOption(‘cplex_options’,‘poolstub savesol mipsearch = 2 nodesel = 3’)
I tried this, but doesn’t work
random_num = round((random.uniform(0.0, 10000)),0)
seed_value = f’seed=random_num’
ampl.setOption(‘cplex_options’,“poolstub savesol mipsearch = 2 nodesel = 3 seed_value”)
Regarding the number of solutions found, there are options like poolintensity that may help (see all options for CPLEX at https://dev.ampl.com/solvers/cplex/options.html).
Regarding seed, you can do it as follows:
random_num = round((random.uniform(0.0, 10000)),0)
ampl.setOption('cplex_options", f"poolstub savesol mipsearch = 2 nodesel = 3 seed={random_num}")
Thanks,
I used this
random_num = round((random.uniform(0, 10000)), 0)
ampl.setOption(“cplex_options”, f"poolstub savesol mipsearch = 2 nodesel = 3 seed={random_num}")
still gives an error, I do not know where “.0” comes from
CPLEX 22.1.1.0: poolstub savesol
mipsearch = 2
nodesel = 3
seed=4629
Unknown keyword “.0”
CPLEX 22.1.1.0: Error in $cplex_options.
file -
line 1 offset 33
Bad suffix .npool for cost
Even after rounding random_num is still a float so there is still a “.0” in formated string . You can cast it it int or format the f-string with 0 decimal points as follows:
ampl.setOption(“cplex_options”, f"poolstub savesol mipsearch = 2 nodesel = 3 seed={random_num:.0}")
Sorry, missed the f in the previous reply:
ampl.setOption(“cplex_options”, f"poolstub savesol mipsearch = 2 nodesel = 3 seed={random_num:.0f}")