为了使用GEKKO软件包模拟FOPDT模型中的死区时间,我使用了GEKKO“cspline”函数使时间转移操作更加平滑。
当输入在死区时间长度之后发生变化时,它工作得很好。(例如,当死区时间=10时,输入在t=15时变化)
然而,当输入在死区时间长度之前发生变化时(例如,死区时间=10时,输入在t=5时发生变化),cspline函数似乎过度外推了输入值。请给出一些避免此问题的建议。
from gekko import GEKKO
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
tf = 50
npt = 51
t = np.linspace(0,tf,npt)
u1 = np.zeros(npt)
u1[5:] = 5
m = GEKKO(remote=True)
m.time = t
time = m.Var(0)
m.Equation(time.dt()==1)
K1 = m.FV(1,lb=0,ub=1); K1.STATUS=1
tau1 = m.FV(5, lb=1,ub=300); tau1.STATUS=1
theta1 = m.FV(10, lb=2,ub=30); theta1.STATUS=1
uc1 = m.Var(u1)
tc1 = m.Var(t)
m.Equation(tc1==time-theta1)
m.cspline(tc1,uc1,t,u1,bound_x=False)
yp1 = m.Var()
m.Equation(yp1.dt() == -yp1/tau1 + K1*uc1/tau1)
m.options.IMODE=4
m.solve()
print('K1: ', K1.value[0])
print('tau1: ', tau1.value[0])
print('theta1: ', theta1.value[0])
print('')
plt.figure()
plt.subplot(2,1,1)
plt.plot(t,u1)
plt.legend([r'u1'])
plt.ylabel('Input')
plt.subplot(2,1,2)
plt.plot(t,yp1)
plt.legend([r'y1'])
plt.ylabel('Output')
plt.xlabel('Time')
plt.savefig('sysid.png')
plt.show()
cspline对象被提供范围为
t=0
到t=50
的数据,但它访问t=-10
到t=40
的值。误差是由三次样条曲线的外推造成的。可以生成范围为t=-theta_ub
到t=50
的样条曲线数据,以避免外推问题相关问题 更多 >
编程相关推荐