Using Solver Foundation and plug-in solvers in IronPython

Solver Foundation provides an easy-to-use and flexible plug-in infrastructure as an addition to its already rich set of solvers. Users can choose their favorite plugin solvers to solve the model, and yet leverage all features provided in Solver Foundation Services (SFS).

The key process is to register the plug-in solvers via an app.config file. A typical config file looks as follows:

<?xml version="1.0" encoding="utf-8" ?>

<configuration>

<configSections>

<section name="MsfConfig"

type="Microsoft.SolverFoundation.Services.MsfConfigSection, Microsoft.Solver.Foundation, Version=2.0.2.8632, Culture=neutral, PublicKeyToken=31bf3856ad364e35"

allowLocation="true"

allowDefinition="Everywhere"

allowExeDefinition="MachineToApplication"

restartOnExternalChanges="true"

requirePermission="true" />

</configSections>

<MsfConfig>

<MsfPluginSolvers>

<MsfPluginSolver

capability="<plug-in solver capability>"

assembly="<path\to\your\plug-in\solver\dll"

solverclass="<plug-in solver class name>"

directiveclass="<plug-in solver directive class name>"

parameterclass="<plug-in solver parameter class name>"/>

</MsfPluginSolvers>

</MsfConfig>

</configuration>

The information such as assembly name and solver class name can usually be found from the plug-in solver provider.

The config file then will co-exist with the compiled exe file of the user app. When, inside the app code, a Solve call is issued, SFS will pick a solver based on the model kind, directive instances passed in, and the solver registration.

The app code in this case can be written in any .NET compliant language such as C# or VB.NET.

IronPython is “an implementation of the Python programming language running under .NET …” So it is possible to use Solver Foundation, and with plug-in solvers, in IronPython code. However, one difficulty is that Python is an interpreted language. Therefore we cannot compile Python code to an exe file. So how do we register our plug-in solvers?

The trick is to register the plug-in solvers inside ipy.exe.config (or ipy64.exe.config). These two files must be put under the same folder with ipy.exe and ipy64.exe. We assume IronPython 2.6 RC2 in the following discussion.

There is IronPython sample code under <your document folder>\Microsoft Solver Foundation\Samples\SolverFoundationServices\IronPython if we install Solver Foundation v2.0. We will use the petrochem-sfs.py as the example. Let us again use Gurobi solver as our plug-in solver. Gurobi solver dlls are installed by default under C:\Program Files\Microsoft Solver Foundation\2.0.2.8632\Plugins (and C:\Program Files\Microsoft Solver Foundation\2.0.2.8632\Plugins(x86) if the target platform is 64bit). So the plug-in solver registration looks as follows:

ipy.exe.config

<?xml version="1.0" encoding="utf-8" ?>

<configuration>

<configSections>

<section name="MsfConfig"

type="Microsoft.SolverFoundation.Services.MsfConfigSection, Microsoft.Solver.Foundation, Version=2.0.2.8632, Culture=neutral, PublicKeyToken=31bf3856ad364e35"

allowLocation="true"

allowDefinition="Everywhere"

allowExeDefinition="MachineToApplication"

restartOnExternalChanges="true"

requirePermission="true" />

</configSections>

<MsfConfig>

<MsfPluginSolvers>

<MsfPluginSolver

capability="LP"

assembly="C:\Program Files\Microsoft Solver Foundation\2.0.2.8632\Plugins(x86)\GurobiPlugin.dll"

solverclass="SolverFoundation.Plugin.Gurobi.GurobiSolver"

directiveclass="SolverFoundation.Plugin.Gurobi.GurobiDirective"

parameterclass="SolverFoundation.Plugin.Gurobi.GurobiParams"/>

</MsfPluginSolvers>

</MsfConfig>

</configuration>

ipy64.exe.config

<?xml version="1.0" encoding="utf-8" ?>

<configuration>

<configSections>

<section name="MsfConfig"

type="Microsoft.SolverFoundation.Services.MsfConfigSection, Microsoft.Solver.Foundation, Version=2.0.2.8632, Culture=neutral, PublicKeyToken=31bf3856ad364e35"

allowLocation="true"

allowDefinition="Everywhere"

allowExeDefinition="MachineToApplication"

restartOnExternalChanges="true"

requirePermission="true" />

</configSections>

<MsfConfig>

<MsfPluginSolvers>

<MsfPluginSolver

capability="LP"

assembly="C:\Program Files\Microsoft Solver Foundation\2.0.2.8632\Plugins\GurobiPlugin.dll"

solverclass="SolverFoundation.Plugin.Gurobi.GurobiSolver"

directiveclass="SolverFoundation.Plugin.Gurobi.GurobiDirective"

parameterclass="SolverFoundation.Plugin.Gurobi.GurobiParams"/>

</MsfPluginSolvers>

</MsfConfig>

</configuration>

Now if we run the petrochem-sfs.py sample (ipy -O petrochem-sfs.py), we will see that Gurobi solver is used:

 

Lengning