如何使用Sympy求解x1/A=x2/B=x3/C类型的多等号链式方程?
问题原因
- 错误构造链式等式:SymPy的
Eq不支持嵌套书写a = b = c的链式结构,你通过循环嵌套Eq生成的表达式无法被solve正确识别。 - 无依据硬设比值:你直接将公共比值设为Cost列表的最大值,这不是链式比例方程本身的约束,会直接导致结果不符合预期。
- 缺少返回值:函数计算完解
s后没有返回,调用后无法拿到计算结果。
修正方案
分两种场景实现:
场景1:求通解(保留公共常数为自由参数)
如果没有额外约束,链式比例方程本身有1个自由变量(即公共比值Constant),求解会得到用自由变量表示的通解:
from sympy import symbols, Eq, solve def _3covoit_prop(CostList): n = len(CostList) # 定义x变量 + 公共比值常数k varbs = symbols(f'x0:{n}') k = symbols('k') # 构造等式组:每个x_i / Cost_i = k eqs = [Eq(x / cost, k) for x, cost in zip(varbs, CostList)] # 求解 s = solve(eqs, varbs, dict=True) return s # 测试 print(_3covoit_prop([100., 450., 500., 1450.]))
运行输出为:[{x0: 100.0*k, x1: 450.0*k, x2: 500.0*k, x3: 1450.0*k}]
完全符合x_i = k * Cost_i的比例关系要求。
场景2:增加约束求特解
如果需要得到数值解,需要补充额外约束,比如要求所有x的和为固定值、或者最大的x等于对应Cost值等,以下示例补充约束所有x的总和=2500:
from sympy import symbols, Eq, solve def _3covoit_prop(CostList, sum_target=2500): n = len(CostList) varbs = symbols(f'x0:{n}') k = symbols('k') eqs = [Eq(x / cost, k) for x, cost in zip(varbs, CostList)] # 补充总和约束 eqs.append(Eq(sum(varbs), sum_target)) s = solve(eqs, [*varbs, k], dict=True) return s # 测试 print(_3covoit_prop([100., 450., 500., 1450.]))
运行输出为:[{k: 1.0, x0: 100.000000000000, x1: 450.000000000000, x2: 500.000000000000, x3: 1450.00000000000}]
内容的提问来源于stack exchange,提问作者Matthieu Akhavan
相关产品推荐
相关产品推荐

