Scipy中设置浮点精度方法及线性规划可行性异常求助
解决Scipy linprog循环调用中的精度与不可行问题
核心问题分析
Scipy的linprog默认采用双精度(64位浮点数)计算,不存在单独设置决策变量精度的选项——你遇到的问题本质是循环迭代中的数值精度累积,导致约束条件被微小误差破坏,而非变量精度不足。
针对性解决方案
1. 调整求解器参数提升稳定性
Scipy默认使用HiGHS求解器,可通过以下参数优化数值表现:
- 显式开启
presolve=True,让求解器预处理矩阵,降低数值病态性 - 微调
tol参数(默认1e-9),比如设为tol=1e-8,平衡精度要求与计算稳定性 - 尝试切换求解器,比如使用
solver='interior-point',不同求解器对病态矩阵的处理逻辑存在差异
示例调用代码:
from scipy.optimize import linprog result = linprog(c, A_ub=A_ub, b_ub=b_ub, method='highs', options={'presolve': True, 'tol': 1e-8})
2. 截断结果误差避免累积
每次LP求解完成后,对决策变量r进行合理精度截断,比如用numpy.round(r, 8)替代原生round(),保留足够有效数字的同时消除微小浮点误差,避免误差在循环中被放大。
3. 改写约束减少计算误差
针对你给出的约束,可通过数学改写降低浮点运算损失:
- 将第一个约束
∑(r_{ij} - r_{ji}) ≤ V_i - D_i拆分为∑r_{ij} - ∑r_{ji} ≤ V_i - D_i,构建约束矩阵时分别处理r_{ij}和r_{ji}的系数,避免直接计算差值带来的精度抵消问题
4. 调试定位误差节点
在每次LP调用前后,验证约束满足情况:
- 计算
∑(r_ij - r_ji) - (V_i - D_i)等关键值,确认是否因微小误差(如1e-10级的正数)触发不可行判定 - 对比CPLEX与Scipy的输出结果,定位误差累积的关键环节
关键提示
Scipylinprog本身已使用双精度计算,无需额外设置变量精度。你遇到的不可行问题源于循环迭代的误差累积,通过上述参数调整、结果截断、约束改写方式可有效缓解。
内容的提问来源于stack exchange,提问作者Mra Abs
相关产品推荐
相关产品推荐

