【问题标题】:Steady State parameter estimation for CSTR using GEKKO使用 GEKKO 的 CSTR 稳态参数估计
【发布时间】:2019-11-01 22:48:00
【问题描述】:

我想使用 CSTR 相对于反应器温度的稳态浓度数据来拟合反应常数(k0 和 EoverR)。 我只使用了一个简单的线性方程来生成要拟合的操作数据。 (Ca_data = -1.5*T_reactor/100 + 4.2)

因为这是稳态数据,所以不需要时间步长 (m.time)。请就如何将以下模拟代码转换为“Ca vs. T_reactor”的估计代码提供建议。

import numpy as np
import matplotlib.pyplot as plt
from gekko import GEKKO

# Feed Temperature (K)
Tf = 350
# Feed Concentration (mol/m^3)
Caf = 1

# Steady State Initial Conditions for the States
Ca_ss = 1
T_ss = 304

#%% GEKKO
m = GEKKO(remote=True)
m.time = np.linspace(0, 25, 251)

# Volumetric Flowrate (m^3/sec)
q = 100
# Volume of CSTR (m^3)
V = 100
# Density of A-B Mixture (kg/m^3)
rho = 1000
# Heat capacity of A-B Mixture (J/kg-K)
Cp = 0.239
# Heat of reaction for A->B (J/mol)
mdelH = 5e4
# E - Activation energy in the Arrhenius Equation (J/mol)
# R - Universal Gas Constant = 8.31451 J/mol-K
EoverR = 8700
# Pre-exponential factor (1/sec)
k0 = 3.2e15
# U - Overall Heat Transfer Coefficient (W/m^2-K)
# A - Area - this value is specific for the U calculation (m^2)
UA = 5e4

# initial conditions = 280
T0 = 304
Ca0 = 1.0

T = m.MV(value=T_ss)
rA = m.Var(value=0)
Ca = m.CV(value=Ca_ss)

m.Equation(rA == k0*m.exp(-EoverR/T)*Ca)
m.Equation(Ca.dt() == q/V*(Caf - Ca) - rA)

m.options.IMODE = 1
m.options.SOLVER = 3

T_reactor = np.linspace(220, 260, 11)
Ca_results = np.zeros(np.size(T_reactor))
for i in range(np.size(T_reactor)):
    T.Value = T_reactor[i]
    m.solve(disp=True)
    Ca_results[i] = Ca[-1]

Ca_data = -1.5*T_reactor/100 + 4.2 # for generating the operation data

# Plot the results
plt.plot(T_reactor,Ca_data,'bo',linewidth=3)
plt.plot(T_reactor,Ca_results,'r-',linewidth=3)
plt.ylabel('Ca (mol/L)')
plt.xlabel('Temperature (K)')
plt.legend(['Reactor Concentration'],loc='best')
plt.show()

【问题讨论】:

    标签: python gekko


    【解决方案1】:

    Gekko 中有一个steady state estimation mode (IMODE=2) 用于线性或非线性回归。两个例子是nonlinear regressionenergy price regression。对于发布的问题,这里有一些建议:

    • 通过一次求解而不是循环求解回归问题。这样一来,您选择的参数将适合整个范围,而不仅仅是某一点。
    • 确定应调整的参数,以最大限度地减少数据和模型预测之间的误差。对于只有一个值的参数,它们应该是 m.FV() 类型,对于每个时间点具有不同值的参数,它们应该是 m.MV()
    • 设置Ca.FSTATUS=1 告诉求解器它应该尝试将Ca 的预测与Ca.value 中加载的数据相匹配。
    • 设置kf.STATUS=1 告诉求解器它是一个应该调整的参数以最小化Ca 错误。
    • 可选:直接将kf 设为可调整参数而不是k0 以改进问题缩放。较大的值(例如 >1e10 或 kf 作为中间体,同时删除了一个额外的方程。

    import numpy as np
    import matplotlib.pyplot as plt
    from gekko import GEKKO
    m = GEKKO(remote=True)
    Tf = 350
    Caf = 1
    q = 100
    V = 100
    rho = 1000
    Cp = 0.239
    mdelH = 5e4
    EoverR = 8700
    k0 = 3.2e15
    UA = 5e4
    T = m.MV()
    Ca = m.CV()
    
    # new parameter to estimate
    kf = m.FV(1,lb=0.5,ub=2.0)
    kf.STATUS = 1
    
    rA = m.Intermediate(kf*k0*m.exp(-EoverR/T)*Ca)
    m.Equation(Ca.dt() == q/V*(Caf - Ca) - rA)
    
    m.options.IMODE = 2
    m.options.SOLVER = 3
    
    # generate data
    T_reactor = np.linspace(220, 260, 11)
    Ca_data = -1.5*T_reactor/100 + 4.2
    
    # insert data
    T.value = T_reactor
    Ca.value = Ca_data
    Ca.FSTATUS = 1 # fit Ca
    
    m.solve()
    
    print('kf = ' + str(kf.value[0]))
    print('k = ' + str(kf.value[0]*k0))
    
    # Plot the results
    plt.plot(T_reactor,Ca_data,'bo',linewidth=3)
    plt.plot(T_reactor,Ca.value,'r-',linewidth=3)
    plt.ylabel('Ca (mol/L)')
    plt.xlabel('Temperature (K)')
    plt.legend(['Reactor Concentration','Regression Fit'],loc='best')
    plt.show()
    

    您可以选择任意数量的参数进行估计以提高拟合度。它不需要仅限于kf。您的帖子提到EoverR 是另一个需要估计的潜在参数,但这可能不会显着改善拟合,因为k0EoverR 是共线的。这两个参数都可以增加或减少,并给出几乎相同的解决方案。需要注意的是,两者都需要有显着的温度变化。

    【讨论】:

      猜你喜欢
      • 2021-09-14
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-07-21
      • 1970-01-01
      • 1970-01-01
      • 2012-07-08
      相关资源
      最近更新 更多