System Modeling

English translation

Execution setup

The Python option uses python-control. If the module is missing, run %pip install control==0.10.2 in a Colab or Jupyter code cell.

Learning objectives

Use the model to determine whether changing mass or resistance affects the transient response, the steady-state value, or both.

Cruise model and units

Starting conditions

m=1000m=1000 kg, b=50b=50 N·s/m, force 500 N. The state and output are velocity [m/s].

Procedure

  1. Build a model using A=−b/mA=-b/m, B=1/mB=1/m, C=1C=1, and D=0D=0, and plot the response over 0≤t≤1500\le t\le150 s to a constant force of 500 N.
  2. Change only m∈{500,1000,1500}m\in\{500,1000,1500\} and apply the same force. Substitute v̇=0\dot v=0 into mv̇+bv=500m\dot v+bv=500 to obtain steady-state velocity, and match the coefficients of v̇+(b/m)v=500/m\dot v+(b/m)v=500/m to the standard 1st-order form to obtain the time constant.
  3. For each mass, record the calculated steady-state velocity alongside the final simulation sample v(150)v(150). Find when the curve reaches approximately 63.2% of the calculated steady-state velocity, and compare this time with the calculated time constant.

Results to retain

import numpy as np
import matplotlib.pyplot as plt
import control as ctl
s = ctl.tf('s')
m=1000.; b=50.; force=500.
G=ctl.ss([[-b/m]],[[1/m]],[[1]],[[0]])
t=np.linspace(0,150,1501)
t,v=ctl.step_response(force*G,t)
plt.plot(t,v); plt.xlabel('Time [s]'); plt.ylabel('Speed [m/s]'); plt.grid()
# TODO: Compare the 3 mass conditions with the values predicted by the equations.

Record results and self-check

m [kg]:

Predicted final velocity [m/s]:

Measured velocity [m/s]:

Time Constant [s]:

Points to check

Comparing motor-model coefficients

Starting conditions

J=.01J=.01, b=.1b=.1, K=.01K=.01, L=.5L=.5. Compare R∈{.5,1,2}R\in\{.5,1,2\} Ω with an input of 1 V.

Procedure

  1. Construct G(s)=K(Js+b)(Ls+R)+K2G(s)=\frac K{(Js+b)(Ls+R)+K^2} and calculate its response over 0≤t≤100\le t\le 10 s.
  2. Tabulate the poles, DC gain, and final output for each R.
  3. Explain which terms in the equation change with electrical resistance and inertia.

Results to retain

import numpy as np
import matplotlib.pyplot as plt
import control as ctl
s = ctl.tf('s')
J=.01; b=.1; K=.01; L=.5
for R in [.5,1.,2.]:
    G=K/((J*s+b)*(L*s+R)+K**2)
    print(R,ctl.poles(G),ctl.dcgain(G))
# TODO: Add responses on the same time axis.

Record results and self-check

R [Ω]:

Pole:

DC Gain:

Final velocity [rad/s]:

Points to check

Estimating a model from a measured response

Starting conditions

Synthetic sensor step record: y=1.8(1−e−t/3)+noisey=1.8(1-e^{-t/3})+\text{noise}. 0≤t≤150\le t\le 15 s, 151 points, noise standard deviation .03, seed=7.

Procedure

  1. Use the supplied measurement array as the target values for curve_fit, and estimate K,τK,\tau of K(1−e−t/τ)K(1-e^{-t/\tau}).
  2. Apply the same estimation separately to the full 00–1515 s record and the first 00–33 s. Tabulate the sample count and estimated K,τK,\tau for each interval.
  3. Plot each fitted curve on the same time axis as the measurements, and plot residuals as measured minus estimated values. Based on the final values and residual patterns, choose one time interval where you would like more measurements and explain why.

Results to retain

from scipy.optimize import curve_fit
rng=np.random.default_rng(7); tm=np.linspace(0,15,151)
measured=1.8*(1-np.exp(-tm/3))+rng.normal(0,.03,len(tm))
def response(t,gain,tau):return gain*(1-np.exp(-t/tau))
for end in [3,15]:
    select=tm<=end
    parameters,_=curve_fit(response,tm[select],measured[select],p0=[1,2],bounds=(0,np.inf))
    print(end,parameters)
# TODO: Compare curves and residuals on the same time axis.

Record results and self-check

Recording interval [s]:

Estimated gain:

Estimated time constant [s]:

RMSE:

Points to check

Official examples and data