微分方程数值算法求解结构动力响应

对于如下的二自由度结构,采用不同的微分方程解法来求解结构动力响应。

在这里插入图片描述
通过牛顿第二定律,可以得到如下的动力学方程:
[ m 1 0 0 m 1 ] { x ¨ 1 x ¨ 2 } + [ c 1 + c 2 − c 2 − c 2 c 2 ] { x ˙ 1 x ˙ 2 } + [ k 1 + k 2 − k 2 − k 2 k 2 ] { x 1 x 2 } = { f 1 f 2 } \left[ \begin{matrix} m_1& 0\\ 0& m_1\\ \end{matrix} \right] \left\{ \begin{array}{c} \ddot{x}_1\\ \ddot{x}_2\\ \end{array} \right\} +\left[ \begin{matrix} c_1+c_2& -c_2\\ -c_2& c_2\\ \end{matrix} \right] \left\{ \begin{array}{c} \dot{x}_1\\ \dot{x}_2\\ \end{array} \right\} +\left[ \begin{matrix} k_1+k_2& -k_2\\ -k_2& k_2\\ \end{matrix} \right] \left\{ \begin{array}{c} x_1\\ x_2\\ \end{array} \right\} =\left\{ \begin{array}{c} f_1\\ f_2\\ \end{array} \right\} [m100m1]{x¨1x¨2}+[c1+c2c2c2c2]{x˙1x˙2}+[k1+k2k2k2k2]{x1x2}={f1f2}
简化为:
M X ¨ + C X ˙ + K X = F \mathbf{M\ddot{X}}+\mathbf{C\dot{X}}+\mathbf{KX}=\mathbf{F} MX¨+CX˙+KX=F
其中:
M = [ m 1 0 0 m 1 ] , C = [ c 1 + c 2 − c 2 − c 2 c 2 ] , K = [ k 1 + k 2 − k 2 − k 2 k 2 ] , X = { x 1    x 2 } \mathbf{M}=\left[ \begin{matrix} m_1& 0\\ 0& m_1\\ \end{matrix} \right] ,\mathbf{C}=\left[ \begin{matrix} c_1+c_2& -c_2\\ -c_2& c_2\\ \end{matrix} \right] ,\mathbf{K}=\left[ \begin{matrix} k_1+k_2& -k_2\\ -k_2& k_2\\ \end{matrix} \right] , \mathbf{X}=\left\{ \begin{array}{c} x_1\\ \,\,x_2\\ \end{array} \right\} M=[m100m1],C=[c1+c2c2c2c2],K=[k1+k2k2k2k2],X={x1x2}
写为状态空间方程,可得
{ X ˙ X ¨ } = [ 0 I − M − 1 C − M − 1 K ] { X X ¨ } + [ 0 M − 1 ] F \left\{ \begin{array}{c} \mathbf{\dot{X}}\\ \mathbf{\ddot{X}}\\ \end{array} \right\} =\left[ \begin{matrix} \mathbf{0}& \mathbf{I}\\ -\mathbf{M}^{-1}\mathbf{C}& -\mathbf{M}^{-1}\mathbf{K}\\ \end{matrix} \right] \left\{ \begin{array}{c} \mathbf{X}\\ \mathbf{\ddot{X}}\\ \end{array} \right\} +\left[ \begin{array}{c} \bf{0}\\ \mathbf{M}^{-1}\\ \end{array} \right] \mathbf{F} {X˙X¨}=[0M1CIM1K]{XX¨}+[0M1]F

简化为:
Z ˙ = A Z + B U \mathbf{\dot{Z}}=\mathbf{AZ}+\mathbf{BU} Z˙=AZ+BU
其中:

Z = { X X ˙ } , A = [ 0 I − M − 1 C − M − 1 K ] , B = [ 0 M − 1 ] , U = F \mathbf{Z}=\left\{ \begin{array}{c} \mathbf{X}\\ \mathbf{\dot{X}}\\ \end{array} \right\} \text{,}\mathbf{A}=\left[ \begin{matrix} \mathbf{0}& \mathbf{I}\\ -\mathbf{M}^{-1}\mathbf{C}& -\mathbf{M}^{-1}\mathbf{K}\\ \end{matrix} \right] \text{,}\mathbf{B}=\left[ \begin{array}{c} \mathbf{0}\\ \mathbf{M}^{-1}\\ \end{array} \right] \text{,}\mathbf{U}=\mathbf{F} Z={XX˙}A=[0M1CIM1K]B=[0M1]U=F

上式为一微分方程,可采用微分多种数值解法来进行求解,包括欧拉法、改进欧拉法、龙格-库塔法、亚当姆斯法、亚当姆斯预报-校正法等,以下是相应的MATLAB代码.


function Y = state_space_slover(A,B,C,D,U,t,Z0,method)


switch method
    case 1
        Y = Euler_method(A,B,C,D,Z0,U,t);
    case 2
        Y = Improved_Euler_method(A,B,C,D,Z0,U,t);
    case 3
        Y = Runge_kutta_method_4th(A,B,C,D,Z0,U,t);
    case 4
        Y = Adams_method_2nd(A,B,C,D,Z0,U,t);
    case 5
        Y = Adams_method_4th(A,B,C,D,Z0,U,t);
    case 6
        Y = Improver_Adams_method_4th(A,B,C,D,Z0,U,t);
end

end
function Y = Euler_method(A,B,C,D,Z0,U,t)
dt = t(2) - t(1);
Nt = length(t);
Z = zeros(size(A,1), Nt);
Z(:,1) = Z0;
Y = zeros(size(C,1), Nt);

for it = 1:Nt
    z0 = Z(:,it);
    Ui = U(:,it);
    zi = A*z0 + B*Ui;
    
    Z(:,it+1) = z0 + dt*zi;
    Y(:,it) = C*zi + D*Ui;
end

end
function Y = Improved_Euler_method(A,B,C,D,Z0,U,t)

dt = t(2) - t(1);
Nt = length(t);
Z = zeros(size(A,1), Nt);
Z(:,1) = Z0;
Y = zeros(size(C,1), Nt);

for it = 1:Nt
    z0 = Z(:,it);
    Ui = U(:,it);

    zp = z0 + dt*(A*z0 + B*Ui);
    zc = z0 + dt*(A*zp + B*Ui);
    zi = (zp + zc)/2;

    Z(:,it+1) = zi;
    Y(:,it) = C*zi + D*Ui;
end

end
function Y = Runge_kutta_method_4th(A,B,C,D,Z0,U,t)

dt = t(2) - t(1);
Nt = length(t);
Z = zeros(size(A,1), Nt);
Z(:,1) = Z0;
Y = zeros(size(C,1), Nt);

for it = 1:Nt
    z0 = Z(:,it);
    Ui = U(:,it);

    K1 = A*z0 + B*Ui;
    K2 = A*(z0 + K1*dt/2) + B*Ui;
    K3 = A*(z0 + K2*dt/2) + B*Ui;
    K4 = A*(z0 + K3*dt) + B*Ui;
    zi = z0 + dt/6*(K1 + 2*K2 + 2*K3 + K4);

    Z(:,it+1) = zi;
    Y(:,it) = C*zi + D*Ui;
end

end
function Y = Adams_method_2nd(A,B,C,D,Z0,U,t)

dt = t(2) - t(1);
Nt = length(t);
Z = zeros(size(A,1), Nt);
Z(:,1) = Z0;
Y = zeros(size(C,1), Nt);

for it = 1:Nt
    Ui = U(:,it);
    z0 = Z(:,it);
    if it == 1
        zi = A*Z(:,it) + B*Ui;
    else
        z1 = Z(:,it);
        z2 = Z(:,it-1);

        za = A*z1 + B*Ui;
        zb = A*z2 + B*Ui;
        zi = z0  + 0.5*dt*(3*za - zb);
    end

    Z(:,it+1) = zi;
    Y(:,it) = C*zi + D*Ui;

end

end
function Y = Adams_method_4th(A,B,C,D,Z0,U,t)

dt = t(2) - t(1);
Nt = length(t);
Z = zeros(size(A,1), Nt);
Z(:,1) = Z0;
Y = zeros(size(C,1), Nt);

for it = 1:Nt
    Ui = U(:,it);
    z0 = Z(:,it);
    if it <= 4
        K1 = A*z0 + B*Ui;
        K2 = A*(z0 + K1*dt/2) + B*Ui;
        K3 = A*(z0 + K2*dt/2) + B*Ui;
        K4 = A*(z0 + K3*dt) + B*Ui;
        zi = z0 + dt/6*(K1 + 2*K2 + 2*K3 + K4);
    else
        z1 = Z(:,it);
        z2 = Z(:,it-1);
        z3 = Z(:,it-2);
        z4 = Z(:,it-3);

        za = A*z1 + B*Ui;
        zb = A*z2 + B*Ui;
        zc = A*z3 + B*Ui;
        zd = A*z4 + B*Ui;

        zi = z0  + 1/24*dt*(9*za + 19*zb - 5*zc + zd);
    end
    Z(:,it+1) = zi;
    Y(:,it) = C*zi + D*Ui;
end
end
function Y = Improver_Adams_method_4th(A,B,C,D,Z0,U,t)

dt = t(2) - t(1);
Nt = length(t);
Z = zeros(size(A,1), Nt);
Z(:,1) = Z0;
Y = zeros(size(C,1), Nt);

for it = 1:Nt
    Ui = U(:,it);
    z0 = Z(:,it);
    if it <= 3
        K1 = A*z0 + B*Ui;
        K2 = A*(z0 + K1*dt/2) + B*Ui;
        K3 = A*(z0 + K2*dt/2) + B*Ui;
        K4 = A*(z0 + K3*dt) + B*Ui;
        zi = z0 + dt/6*(K1 + 2*K2 + 2*K3 + K4);
    else
        z1 = Z(:,it);
        z2 = Z(:,it-1);
        z3 = Z(:,it-2);
        z4 = Z(:,it-3);

        za = A*z1 + B*Ui;
        zb = A*z2 + B*Ui;
        zc = A*z3 + B*Ui;
        zd = A*z4 + B*Ui;

        ze = z0 + dt/24*(55*za - 59*zb + 37*zc - 9*zd);
        zp = A*ze + B*Ui;

        zi = z0 + dt/24*(9*zp + 19*za - 5*zb + zc);
    end

    Z(:,it+1) = zi;
    Y(:,it) = C*zi + D*Ui;

end

end

假设 m 1 m_1 m1 = 10 kg, m 2 m_2 m2 = 5kg, c 1 c_1 c1 = 3 N ⋅ s / m \text{N}\cdot \text{s}/\text{m} Ns/m, c 2 = 4 N ⋅ s / m c_2= 4 \text{N}\cdot \text{s}/\text{m} c2=4Ns/m, , k 1 = 10 N / m k_1 = 10 \text{N}/\text{m} k1=10N/m , k 2 k_2 k2 = 6 N / m \text{N}/\text{m} N/m, f 1 = 5 sin ⁡ ( t ) f_1 = 5\sin(t) f1=5sin(t), f 2 = 10 sin ⁡ ( t ) f_2 = 10\sin(t) f2=10sin(t)。若只考虑输出结构的位移和速度响应,则状态空间方程的数值为:

A = [ 0 0 1 0 0 0 0 1 − 1.6 0.6 − 0.7 0.4 1.2 − 1.2 0.8 − 0.8 ] , B = [ 0 0 0 0 0.1 0 0 0.2 ] , C = [ 1 0 0 0 0 1 0 0 0 0 1 0 0 0 0 1 ] , D = [ 0 0 0 0 0 0 0 0 ] \mathbf{A}=\left[ \begin{matrix} 0& 0& 1& 0\\ 0& 0& 0& 1\\ -1.6& 0.6& -0.7& 0.4\\ 1.2& -1.2& 0.8& -0.8\\ \end{matrix} \right] ,\mathbf{B}=\left[ \begin{matrix} 0& 0\\ 0& 0\\ 0.1& 0\\ 0& 0.2\\ \end{matrix} \right] ,\mathbf{C}=\left[ \begin{matrix} 1& 0& 0& 0\\ 0& 1& 0& 0\\ 0& 0& 1& 0\\ 0& 0& 0& 1\\ \end{matrix} \right] ,\mathbf{D}=\left[ \begin{matrix} 0& 0\\ 0& 0\\ 0& 0\\ 0& 0\\ \end{matrix} \right] A= 001.61.2000.61.2100.70.8010.40.8 ,B= 000.100000.2 ,C= 1000010000100001 ,D= 00000000

由此,采用以上方法,可得到结构的响应值,代码如下:


clear
clc

m1 = 10;
m2 = 5;
c1 = 3;
c2 = 4;
k1 = 10;
k2 = 6;

M = [m1, 0; 0, m2];
C = [c1+c2, -c2; -c2, c2];
K = [k1+k2, -k2; -k2, k2];

n = 2;
A = [zeros(n), eye(2); -M\K, -M\C];
B = [zeros(n); inv(M)];
C = eye(2*n);
D = zeros(2*n,n);

t = 0:0.01:10;
f1 = 5*sin(t);
f2 = 10*sin(t);
U = [f1; f2];
Z0 = [1,0.5,0,0]';

Y = cell(1,6);
for i = 1:6
    Y{i} = state_space_slover(A,B,C,D,U,t,Z0,i);
end

于此同时,可采用MATLAB中 lsim 命令求得此状态方程的精确值

Y0 = lsim(A,B,C,D,U,t,Z0);

不同计算方式的结果对比如下:

colors = {'#a9eee6', '#ffbd39', '#f38181', '#fccde2', '#5e63b6', '#685454'};
style = {'-','-.', '--', '.', '-.', '-.'};
ylabels = {'$x_1$', '$x_2$', '$\dot{x}_1$', '$\dot{x}_2$'};
figure(Color='w', Position=[200,200,800,600])
for i = 1:4
    subplot(2,2,i)

    plot(t,Y0(:,i),'b',linewidth = 1.5)
    hold on
    for j = 1:6
        plot(t, Y{j}(i,:), Color=colors{j}, linewidth = 1.5)
    end

    if i == 1
        legend('lsim', 'Euler', 'Improved Euler', '4th Runge kutta', '2nd Adams', ...
            '4th Adams','4th Improved Adams', ...
            'Location', 'NorthOutside', 'Orientation', 'horizontal','NumColumns',4) 
    end

    xlabel('Time (s)')
    ylabel(ylabels{i}, 'Interpreter','latex',FontSize=18)
end

不同计算方法响应结果
从上图可以看出,对于不同的方式,除欧拉和2阶的Adams外,其他的方法与lsim得到的精确结果相差不大。在实际计算过程中,推荐采用4阶的龙格-库塔方法,其计算效率和精度相对高。但在计算过程中需要注意时间步长的选择,若步长太大,则会引起计算的不稳定,致使结果发散。

参考书籍:数值计算方法及其程序实现(第二版),吴开腾。北京:科学出版社,2019.

  • 3
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值