从 gurobipy 获取矩阵格式的约束
Get constraints in matrix format from gurobipy
我在 gurobipy 中编写了我的模型,我想获得约束矩阵和成本向量。
有什么方法可以访问这些吗?
Gurobi 9.0 之前
从pythonAPI来看,没有一个函数可以从Gurobi模型中获取矩阵系数,但是自己写一个并不难。
拥有变量和约束列表很方便。如果您在变量 m
中有一个 gurobi 模型
dvars = m.getVars()
constrs = m.getConstrs()
将为您提供变量和约束列表。然后,您可以使用 m.getAttr 检索与变量相关的属性。要获取 objective 函数系数,请查询 'Obj' 属性
obj_coeffs = m.getAttr('Obj', dvars)
这将为您提供模型中每个变量的 objective 系数列表。对于约束矩阵,您可能只想存储非零值。我将以 COOrdinate 格式
存储它们
- 行索引
- 列索引
- 系数
在这个例子中,有每个变量和约束对象的索引是很方便的。我将创建将对象映射到索引的字典
var_index = {v: i for i, v in enumerate(dvars)}
constr_index= {c: i for i, c in enumerate(constrs)}
constrs
列表中的每个约束对象对应于模型中的一个约束。每个约束都有一个
- 左侧表达式
- 意义(<=、==、>=)
- 右侧常量
对于约束矩阵,您只需要左侧。它由模型上的 LinExpr object which you can obtain with the getRow 方法表示。从Gurobi 6.x开始,获取列索引列表,系数元组需要如下函数
def get_expr_coos(expr, var_indices):
for i in range(expr.size()):
dvar = expr.getVar(i)
yield expr.getCoeff(i), var_indices[dvar]
要获取矩阵,您需要为每个约束应用此函数。
def get_matrix_coos(m):
dvars = m.getVars()
constrs = m.getConstrs()
var_indices = {v: i for i, v in enumerate(dvars)}
for row_idx, constr in enumerate(constrs):
for coeff, col_idx in get_expr_coos(m.getRow(constr), var_indices):
yield row_idx, col_idx, coeff
使用此函数,您可以将矩阵存储为类似 pandas dataframe
的结构
nzs = pd.DataFrame(get_matrix_coos(m),
columns=['row_idx', 'col_idx', 'coeff'])
根据这个结构,您可以绘制非零模式的基本图。使用来自 miplib aflow40b 基准问题的问题。
import matplotlib.pyplot as plt
import pandas as pd
import gurobipy as grb
m = grb.read("miplib/instances/miplib2010/aflow40b.mps.gz")
nzs = pd.DataFrame(get_matrix_coos(m),
columns=['row_idx', 'col_idx', 'coeff'])
plt.scatter(nzs.col_idx, nzs.row_idx,
marker='.', lw=0)
Gurobi 9.0 更新 19/06/20
您可以通过.getA()
查询系数矩阵作为<class 'scipy.sparse.csr.csr_matrix'>
。
import matplotlib.pyplot as plt
import gurobipy as grb
m = grb.read("miplib/instances/miplib2010/aflow40b.mps.gz")
A = m.getA()
plt.spy(A) # different options, e.g. markersize=0.5
plt.show()
还可以使用 betterspy 查看矩阵图。
由于声誉不足,无法评论@david-nehme 的回答,请随时将此添加到他的回答并删除我的。
从 Gurobi 9.0 开始,您可以通过 .getA()
作为 <class 'scipy.sparse.csr.csr_matrix'>
.
查询系数矩阵
import matplotlib.pyplot as plt
import gurobipy as grb
m = grb.read("miplib/instances/miplib2010/aflow40b.mps.gz")
A = m.getA()
plt.spy(A) # different options, e.g. markersize=0.5
plt.show()
还可以使用 betterspy 查看矩阵图。
我在 gurobipy 中编写了我的模型,我想获得约束矩阵和成本向量。 有什么方法可以访问这些吗?
Gurobi 9.0 之前
从pythonAPI来看,没有一个函数可以从Gurobi模型中获取矩阵系数,但是自己写一个并不难。
拥有变量和约束列表很方便。如果您在变量 m
dvars = m.getVars()
constrs = m.getConstrs()
将为您提供变量和约束列表。然后,您可以使用 m.getAttr 检索与变量相关的属性。要获取 objective 函数系数,请查询 'Obj' 属性
obj_coeffs = m.getAttr('Obj', dvars)
这将为您提供模型中每个变量的 objective 系数列表。对于约束矩阵,您可能只想存储非零值。我将以 COOrdinate 格式
存储它们- 行索引
- 列索引
- 系数
在这个例子中,有每个变量和约束对象的索引是很方便的。我将创建将对象映射到索引的字典
var_index = {v: i for i, v in enumerate(dvars)}
constr_index= {c: i for i, c in enumerate(constrs)}
constrs
列表中的每个约束对象对应于模型中的一个约束。每个约束都有一个
- 左侧表达式
- 意义(<=、==、>=)
- 右侧常量
对于约束矩阵,您只需要左侧。它由模型上的 LinExpr object which you can obtain with the getRow 方法表示。从Gurobi 6.x开始,获取列索引列表,系数元组需要如下函数
def get_expr_coos(expr, var_indices):
for i in range(expr.size()):
dvar = expr.getVar(i)
yield expr.getCoeff(i), var_indices[dvar]
要获取矩阵,您需要为每个约束应用此函数。
def get_matrix_coos(m):
dvars = m.getVars()
constrs = m.getConstrs()
var_indices = {v: i for i, v in enumerate(dvars)}
for row_idx, constr in enumerate(constrs):
for coeff, col_idx in get_expr_coos(m.getRow(constr), var_indices):
yield row_idx, col_idx, coeff
使用此函数,您可以将矩阵存储为类似 pandas dataframe
的结构 nzs = pd.DataFrame(get_matrix_coos(m),
columns=['row_idx', 'col_idx', 'coeff'])
根据这个结构,您可以绘制非零模式的基本图。使用来自 miplib aflow40b 基准问题的问题。
import matplotlib.pyplot as plt
import pandas as pd
import gurobipy as grb
m = grb.read("miplib/instances/miplib2010/aflow40b.mps.gz")
nzs = pd.DataFrame(get_matrix_coos(m),
columns=['row_idx', 'col_idx', 'coeff'])
plt.scatter(nzs.col_idx, nzs.row_idx,
marker='.', lw=0)
Gurobi 9.0 更新 19/06/20
您可以通过.getA()
查询系数矩阵作为<class 'scipy.sparse.csr.csr_matrix'>
。
import matplotlib.pyplot as plt
import gurobipy as grb
m = grb.read("miplib/instances/miplib2010/aflow40b.mps.gz")
A = m.getA()
plt.spy(A) # different options, e.g. markersize=0.5
plt.show()
还可以使用 betterspy 查看矩阵图。
由于声誉不足,无法评论@david-nehme 的回答,请随时将此添加到他的回答并删除我的。
从 Gurobi 9.0 开始,您可以通过 .getA()
作为 <class 'scipy.sparse.csr.csr_matrix'>
.
import matplotlib.pyplot as plt
import gurobipy as grb
m = grb.read("miplib/instances/miplib2010/aflow40b.mps.gz")
A = m.getA()
plt.spy(A) # different options, e.g. markersize=0.5
plt.show()
还可以使用 betterspy 查看矩阵图。