我试图用最小二乘法解一个非线性方程组。我得到了一个结果,但不幸的是它不是很准确。主要问题是方程29至32必须被充满,但它们不是。有没有一种方法可以在非线性系统中对方程进行优先级排序?
下面是我的代码:
# Ethanol and 1_Propanol with 3 trays
from scipy.optimize import least_squares
import numpy as np
def equations(x):
eq1 = x[18] - x[16] * x[19] * x[11] * (x[21] / (x[19] * x[11] * x[13])) ** (2.0 / 3.0)
eq2 = x[19] - ((732.0 * x[10]) + (747.0 * x[9]))
eq3 = x[13] - ((1.25E-5 * x[10]) + (1.6E-6 * x[9]))
eq4 = x[2] - ((((((-6021.54) + (0.055134232180918 * (x[29] - 298.0))) + 2.61275786690816) * x[10])
+ ((((-6883.827) + (0.058471271259418 * (x[29] - 298.0))) + 2.38446400137128) * x[9])))
eq5 = x[11] - (((0.055134232180918 * (x[29])) + 2.61275786690816) * x[10] + ((0.058471271259418 * (x[29])) +
2.38446400137128) * x[9])
eq6 = x[21] - ((((((0.001318 * (x[29])) + 0.16762) * x[10])
+ (((-0.001075424413 * (x[29])) + 0.155701011727667) * x[9]))))
eq7 = x[24] - (1.746 * x[22] + 2.76 * x[20])
eq8 = x[15] - (1.0E-5 * x[22] + 6.5E-6 * x[20])
eq9 = x[12] - ((((((((-6021.54) + (0.015220202121093 * (x[26] - 298.0))) + 1.60395800121061) + 922.194)
* x[22]) + ((((((-6883.827) + (0.01847750929725 * (x[26] - 298.0))) + 1.43843773750579)
+ 1067.523)) * x[20]))))
eq10 = x[6] - ((((((((0.015220202121093 * (x[26])) + 1.60395800121061)
* x[22]) + (((0.01847750929725 * (x[26])) + 1.43843773750579)
* x[20]))))))
eq11 = x[5] - ((((((((5.07392141746E-4 * (x[29])) + 0.015070468544221)
* x[22]) + (((4.89248E-4 * (x[29])) + 0.014354384)
* x[20]))))))
eq12 = x[3] - (1.0 / (10.0 ** (5.24677 - 1598.673 / (x[28] + 46.424))))
eq13 = x[0] - (1.0 / (10.0 ** (5.31384 - 1690.864 / (x[28] + 51.804))))
eq14 = x[27] - (x[25] * x[24] * x[6] * ((x[5] / (x[24] * x[6] * x[15])) ** (2.0 / 3.0)))
eq15 = 0.0 - ((2.0 * 28000.0) - (x[23] * x[2]) + (x[17] * 0.002))
eq16 = 0.0 - ((0.2 * 30000.0) - (x[14] * x[12]) - (x[17] * 0.002))
eq17 = 0.0 - ((2.0 * 0.5) - (x[23] * x[10]) + (x[8] * 0.002))
eq18 = 0.0 - ((2.0 * 0.5) - (x[23] * x[9]) + (x[7] * 0.002))
eq19 = 0.0 - ((0.2 * 0.6) - (x[14] * x[22]) - (x[8] * 0.002))
eq20 = 0.0 - ((0.2 * 0.4) - (x[14] * x[20]) - (x[7] * 0.002))
eq21 = 0.0 - (x[31] - (x[3] * x[4]))
eq22 = 0.0 - (x[30] - (x[0] * x[1]))
eq23 = x[17] - (x[18] * (x[28] - x[29]) + (x[8] * (((-6021.54 + (0.055134232180918 * (x[29] - 298.0))) +
2.61275786690816) + (x[7] * (
(-6883.827 + (0.058471271259418 * (x[29] - 298.0))) + 2.38446400137128)))))
eq24 = x[17] - (x[27] * (x[26] - x[28]) + (x[8] * ((((-6021.54 + (0.015220202121093 * (x[26] - 298.0))) +
1.60395800121061) + 922.194) + (x[7] * (
((-6883.827 + (0.01847750929725 * (x[26] - 298.0))) + 1.43843773750579) + 1067.523)))))
eq25 = x[8] - (x[19] * x[16] * (x[4] - x[10]) + x[10] * (x[8] + x[7]))
eq26 = x[7] - (x[19] * x[16] * (x[1] - x[9]) + x[9] * (x[8] + x[7]))
eq27 = x[8] - (x[24] * x[25] * (x[22] - x[31]) + x[22] * (x[8] + x[7]))
eq28 = x[7] - (x[24] * x[25] * (x[20] - x[30]) + x[20] * (x[8] + x[7]))
eq29 = 1.0 - (x[10] + x[9])
eq30 = 1.0 - (x[4] + x[1])
eq31 = 1.0 - (x[22] + x[20])
eq32 = 1.0 - (x[31] + x[30])
return [eq1, eq2, eq3, eq4, eq5, eq6, eq7, eq8, eq9, eq10, eq11, eq12, eq13, eq14, eq15, eq16,
eq17, eq18, eq19, eq20, eq21, eq22, eq23, eq24, eq25, eq26, eq27, eq28, eq29, eq30,
eq31, eq32]
# Boundaries
# Upper bounds for specific variables
upper_bounds = np.ones(32) * np.inf
upper_bounds[1] = 1
upper_bounds[4] = 1
upper_bounds[9] = 1
upper_bounds[10] = 1
upper_bounds[20] = 1
upper_bounds[22] = 1
upper_bounds[30] = 1
upper_bounds[31] = 1
# Upper bounds for specific variables
bottom_bounds = np.zeros(32)
bottom_bounds[26] = 340
bottom_bounds[28] = 340
bottom_bounds[29] = 340
# Bounds array
bounds = (bottom_bounds, upper_bounds)
# bounds = (0, np.inf)
# Initial values
x0 = np.ones(32)
x0[1] = 0.5
x0[4] = 0.5
x0[9] = 0.5
x0[10] = 0.5
x0[20] = 0.5
x0[22] = 0.5
x0[30] = 0.5
x0[31] = 0.5
x0[26] = 370
x0[28] = 370
x0[29] = 370
# x0 = np.array([1, 1e-4, 1, 1, 1, 1, 1e-4, 1, 1, 1, 1, 1, 1, 1, 1, 1])
# Lösung des Gleichungssystems mit Variablengrenzen
res = least_squares(equations, x0, bounds=bounds, method='trf', ftol=1e-10, xtol=1e-10, gtol=1e-10)
print(res.x)
print('e0_K_tr1_c2 {0}'.format(res.x[0]))
print('e0_x_Lint_tr1_c2 {0}'.format(res.x[1]))
print('e0_h_L_tr1 {0}'.format(res.x[2]))
print('e0_K_tr1_c1 {0}'.format(res.x[3]))
print('e0_x_Lint_tr1_c1 {0}'.format(res.x[4]))
print('e0_greek_lambda_V_tr1 {0}'.format(res.x[5]))
print('e0_cp_V_tr1 {0}'.format(res.x[6]))
print('e0_f_int_tr1_c2 {0}'.format(res.x[7]))
print('e0_f_int_tr1_c1 {0}'.format(res.x[8]))
print('e0_x_L_tr1_c2 {0}'.format(res.x[9]))
print('e0_x_L_tr1_c1 {0}'.format(res.x[10]))
print('e0_cp_L_tr1 {0}'.format(res.x[11]))
print('e0_h_V_tr1 {0}'.format(res.x[12]))
print('e0_D_L_tr1 {0}'.format(res.x[13]))
print('e0_F_V_tr1 {0}'.format(res.x[14]))
print('e0_D_V_tr1 {0}'.format(res.x[15]))
print('e0_greek_beta_L_tr1 {0}'.format(res.x[16]))
print('e0_e_int_tr1 {0}'.format(res.x[17]))
print('e0_greek_alpha_L_tr1 {0}'.format(res.x[18]))
print('e0_greek_rho_L_tr1 {0}'.format(res.x[19]))
print('e0_x_V_tr1_c2 {0}'.format(res.x[20]))
print('e0_greek_lambda_L_tr1 {0}'.format(res.x[21]))
print('e0_x_V_tr1_c1 {0}'.format(res.x[22]))
print('e0_F_L_tr1 {0}'.format(res.x[23]))
print('e0_greek_rho_V_tr1 {0}'.format(res.x[24]))
print('e0_greek_beta_V_tr1 {0}'.format(res.x[25]))
print('e0_T_V_tr1 {0}'.format(res.x[26]))
print('e0_greek_alpha_V_tr1 {0}'.format(res.x[27]))
print('e0_T_int_tr1 {0}'.format(res.x[28]))
print('e0_T_L_tr1 {0}'.format(res.x[29]))
print('e0_x_Vint_tr1_c2 {0}'.format(res.x[30]))
print('e0_x_Vint_tr1_c1 {0}'.format(res.x[31]))
print('Zusammensetztungen:')
print('e0_x_Vint_tr1_c1 {0}'.format(res.x[31]))
print('e0_x_Vint_tr1_c2 {0}'.format(res.x[30]))
print('e0_x_V_tr1_c1 {0}'.format(res.x[22]))
print('e0_x_V_tr1_c2 {0}'.format(res.x[20]))
print('e0_x_Lint_tr1_c1 {0}'.format(res.x[4]))
print('e0_x_Lint_tr1_c2 {0}'.format(res.x[1]))
print('e0_x_L_tr1_c1 {0}'.format(res.x[10]))
print('e0_x_L_tr1_c2 {0}'.format(res.x[9]))
字符串
以及x[31]
、x[30]
、x[22]
、…为:
Zusammensetztungen:
e0_x_Vint_tr1_c1 0.5189962572539993
e0_x_Vint_tr1_c2 0.24082903753005624
e0_x_V_tr1_c1 2.3066615630447933e-32
e0_x_V_tr1_c2 1.246796204196686e-33
e0_x_Lint_tr1_c1 0.9999999999999999
e0_x_Lint_tr1_c2 0.01258253962013115
e0_x_L_tr1_c1 7.013309435002394e-33
e0_x_L_tr1_c2 3.0913699644636455e-33
型e0_x_Vint_tr1_c1 + e0_x_Vint_tr1_c2
应该是1,但不是。
1条答案
按热度按时间gopyfrb31#
删除多余的括号并重新设置公式的格式,以便更容易调试。
用命名变量替换索引变量。我展示了一种通过
NamedTuple
实现此目的的快速方法。不幸的是,尽管方法
lm
似乎可以改善您的结果-它声称找到的解决方案的成本(30.7)比trf
(399)低10倍-但它不可用,因为它不尊重您的边界。没有什么灵丹妙药可以提高准确性。了解领域问题是必要的。如果某些方程比其他方程对解决方案“更重要”,则可以简单地按其权重缩放这些方程。添加回归测试。对于我展示的结果,这些方程等价于你原来的方程。
始终检查
result.success
。第一遍看起来像
个字符