工学生にとって避けられない科目が工業数学です。特に常微分方程式(ODE: Ordinary Differential Equation)は、電子回路解析、制御システム設計、機械振動解析など、ほぼすべての工学分野の数学的基盤となります。この記事では、ODEの基礎概念からラプラス変換まで、工学応用例を中心に体系的に説明します。
微分方程式は、未知関数とその導関数の関係を表す方程式です。例えば:
dxdy=2x,y′′+3y′+2y=0,∂t∂u=k∂x2∂2u
微分方程式は、自然現象や工学システムを数学的にモデル化する核心的なツールです。
常微分方程式(ODE): 一つの独立変数に関する導関数のみを含みます。
dt2d2x+2dtdx+x=0
偏微分方程式(PDE): 二つ以上の独立変数に関する偏微分を含みます。
∂t∂u=c2∂x2∂2u
この記事ではODEに焦点を当てます。
階数は方程式に現れる最高次の導関数の階数です。
- 1階ODE: y′+y=x (最高導関数は y′)
- 2階ODE: y′′+2y′+y=0 (最高導関数は y′′)
次数は最高階導関数の指数です。ほとんどの工学問題では次数は1です。
線形ODE: 未知関数とその導関数が1次の項のみで現れます。
an(x)y(n)+an−1(x)y(n−1)+⋯+a1(x)y′+a0(x)y=f(x)
非線形ODE: y2、y⋅y′、sin(y) などの非線形項を含みます。
y′′+sin(y)=0(振り子方程式)
- 一般解: 任意定数を含む完全な解
- 特殊解: 初期条件を適用して定数を決定した解
- 特異解: 一般解から得られない特別な解
工学システムのほとんどはODEで記述されます。
RC充電回路:
RCdtdv+v=Vs
バネ-質量-ダンパーシステム:
mx¨+cx˙+kx=F(t)
人口成長モデル:
dtdP=kP
RL回路:
Ldtdi+Ri=E(t)
これらすべてがODEです。解法を学ぶことで、工学システムの動的挙動を完全に解析できます。
形式: dxdy=f(x)g(y)
解法手順:
g(y)dy=f(x)dx
両辺を積分します:
∫g(y)dy=∫f(x)dx+C
例題:RC充電回路
回路方程式:
dtdv=RCVs−v
変数分離:
Vs−vdv=RCdt
積分:
−ln∣Vs−v∣=RCt+C1
初期条件 v(0)=0 を適用:
Vs−v=Vse−t/(RC)
v(t)=Vs(1−e−t/(RC))
この結果はRC回路の過渡応答を表します。時定数 τ=RC で決まる速度で電圧が Vs に収束します。
物理的意味:
- t=τ のとき: v≈0.632Vs (63.2% 充電)
- t=5τ のとき: v≈0.993Vs (ほぼ完全充電)
1階線形ODEの標準形:
dxdy+P(x)y=Q(x)
積分因子: μ(x)=e∫P(x)dx
導出過程:
両辺に μ(x) を掛けます:
μ(x)dxdy+μ(x)P(x)y=μ(x)Q(x)
左辺は積の微分規則により:
dxd[μ(x)y]=μ(x)Q(x)
積分すると:
μ(x)y=∫μ(x)Q(x)dx+C
y=μ(x)1[∫μ(x)Q(x)dx+C]
例題:RL回路
Ldtdi+Ri=E
標準形に変換:
dtdi+LRi=LE
積分因子: μ(t)=e(R/L)t
dtd[e(R/L)t⋅i]=LEe(R/L)t
積分:
e(R/L)t⋅i=REe(R/L)t+C
初期条件 i(0)=0 を適用:
i(t)=RE(1−e−(R/L)t)
時定数 τ=L/R で電流が定常状態 E/R に収束します。
形式: M(x,y)dx+N(x,y)dy=0
完全条件:
∂y∂M=∂x∂N
この条件を満たせば、F(x,y)=C となるポテンシャル関数 F が存在します。
解法:
- ∂x∂F=M から F を x について積分
- ∂y∂F=N の条件で積分定数を決定
- 一般解: F(x,y)=C
例題:
(2xy+y2)dx+(x2+2xy)dy=0
完全性の確認:
∂y∂M=2x+2y=∂x∂N
完全方程式なので:
F=∫Mdx=∫(2xy+y2)dx=x2y+xy2+g(y)
∂y∂F=x2+2xy+g′(y)=N=x2+2xy より g′(y)=0、g(y)=C
一般解: x2y+xy2=C
形式:
dxdy+P(x)y=Q(x)yn(n=0,1)
置換: v=y1−n とすると線形ODEに変換されます。
v′=(1−n)y−ny′ なので、元の方程式を yn で割ると:
y−ndxdy+P(x)y1−n=Q(x)
1−n1dxdv+P(x)v=Q(x)
dxdv+(1−n)P(x)v=(1−n)Q(x)
これは v に関する1階線形ODEで、積分因子法で解けます。
応用: ロジスティック成長モデル dtdP=rP(1−KP) は n=2 のベルヌーイ方程式です。
標準形:
ay′′+by′+cy=0
特性方程式の導出: y=erx を代入します。
ar2erx+brerx+cerx=0
ar2+br+c=0
判別式 Δ=b2−4ac の符号により3つの場合が生じます。
場合1:異なる2つの実根 (Δ>0)
r1=r2 のとき:
y=C1er1x+C2er2x
場合2:重実根 (Δ=0)
r1=r2=r=−b/(2a) のとき:
y=(C1+C2x)erx
C2xerx を追加する理由は、ロンスキー行列式が0にならないように独立な第2の解を構成する必要があるためです。
場合3:共役複素根 (Δ<0)
r=α±iβ (ただし α=−b/(2a)、β=4ac−b2/(2a)) のとき:
y=eαx(C1cosβx+C2sinβx)
オイラーの公式 eiβx=cosβx+isinβx を使って実数解に変換した形です。
回路方程式(電荷 q(t) 基準):
Ldt2d2q+Rdtdq+Cq=0
標準形に整理:
q′′+LRq′+LC1q=0
特性方程式:
r2+LRr+LC1=0
r=−2LR±(2LR)2−LC1
減衰係数 α=R/(2L)、共振周波数 ω0=1/LC と定義すると:
r=−α±α2−ω02
過減衰(Overdamped): α>ω0 (R>2L/C)
q(t)=C1er1t+C2er2t(r1,r2<0)
2つの指数項の和で、振動なく単調減少します。
臨界減衰(Critically Damped): α=ω0 (R=2L/C)
q(t)=(C1+C2t)e−αt
振動なく最も速く平衡状態に戻ります。制御システム設計で非常に重要です。
不足減衰(Underdamped): α<ω0 (R<2L/C)
減衰振動周波数 ωd=ω02−α2 と定義すると:
q(t)=e−αt(C1cosωdt+C2sinωdt)
振動しながら減衰します。通信回路、振動システムでよく見られます。
物理的意味のまとめ:
| 条件 | 名称 | 応答特性 |
|---|
| R>2L/C | 過減衰 | 振動なく遅く減衰 |
| R=2L/C | 臨界減衰 | 振動なく最速減衰 |
| R<2L/C | 不足減衰 | 振動しながら減衰 |
| R=0 | 無減衰 | 持続振動 |
形式:
ay′′+by′+cy=f(x)
完全解: y=yh+yp
- yh: 斉次方程式の一般解(余関数)
- yp: 特殊解
f(x) の形式に応じて yp の形式を推測します。
| f(x) の形式 | yp の推測形式 |
|---|
| keax | Aeax |
| kxn | Anxn+⋯+A1x+A0 |
| kcosωx または ksinωx | Acosωx+Bsinωx |
| keaxcosωx | eax(Acosωx+Bsinωx) |
注意: yp の形式が yh の項と重なる場合は x を掛けて修正します。
例題: y′′+4y=3cos2x
斉次解: yh=C1cos2x+C2sin2x
yp の推測形が yh と重なるため修正:
yp=x(Acos2x+Bsin2x)
代入後に計算すると: A=0、B=3/4
yp=43xsin2x
これは**共振(resonance)**現象で、振幅が時間に比例して増加します。
強制振動応答:
mx¨+cx˙+kx=F0cosωt
定常状態の特殊解:
xp(t)=(1−r2)2+(2ζr)2F0/kcos(ωt−ϕ)
ここで振動数比 r=ω/ωn、減衰比 ζ=c/(2mk)。
r=1(共振条件)で振幅が最大になります。
未定係数法を適用できない一般的な f(x) に使います。
yh=C1y1+C2y2 が与えられるとき:
yp=−y1∫Wy2fdx+y2∫Wy1fdx
ロンスキー行列式: W=y1y2′−y1′y2
この公式はすべての連続関数 f(x) に適用できます。
n 個の1階ODEからなる連立方程式:
dtdX=AX
ここで X=[x1,x2,…,xn]T、A は n×n 係数行列。
解の形式: X=veλt
代入すると: λv=Av
すなわち λ は A の固有値、v は対応する固有ベクトルです。
特性方程式: det(A−λI)=0
例題: 2つのタンクが接続されたシステム
dtd(x1x2)=(−211−2)(x1x2)
特性方程式: (λ+2)2−1=0
λ1=−1,λ2=−3
固有ベクトル: v1=[1,1]T、v2=[1,−1]T
一般解:
X=C1(11)e−t+C2(1−1)e−3t
2ループ回路(キルヒホッフの電圧則):
L1dtdi1+R1i1−Mdtdi2=E1(t)
L2dtdi2+R2i2−Mdtdi1=E2(t)
ここで M は相互インダクタンス。行列形式に整理して固有値法またはラプラス変換で解けます。
定義:
L{f(t)}=F(s)=∫0∞f(t)e−stdt
s=σ+jω は複素変数で、積分が収束するには Re(s)>σc を満たす必要があります。
なぜラプラス変換を使うのか?
- 微分演算が代数演算に変換されます
- 初期条件を自動的に処理します
- 複雑なODEを簡単な代数方程式として解けます
- 伝達関数(Transfer Function)概念の基盤です
| f(t) | F(s)=L{f(t)} |
|---|
| 1 (単位ステップ) | s1 |
| t | s21 |
| tn | sn+1n! |
| eat | s−a1 |
| sinωt | s2+ω2ω |
| cosωt | s2+ω2s |
| eatsinωt | (s−a)2+ω2ω |
| eatcosωt | (s−a)2+ω2s−a |
| δ(t) (インパルス) | 1 |
| u(t−a) (遅延ステップ) | se−as |
線形性:
L{af(t)+bg(t)}=aF(s)+bG(s)
時間移動(第1移動定理):
L{eatf(t)}=F(s−a)
周波数移動(第2移動定理):
L{f(t−a)u(t−a)}=e−asF(s)
微分変換(最も重要な性質):
L{f′(t)}=sF(s)−f(0)
L{f′′(t)}=s2F(s)−sf(0)−f′(0)
L{f(n)(t)}=snF(s)−sn−1f(0)−sn−2f′(0)−⋯−f(n−1)(0)
初期条件がs領域で自動的に含まれます。
積分変換:
L{∫0tf(τ)dτ}=sF(s)
畳み込み定理:
L{(f∗g)(t)}=F(s)G(s)
ここで (f∗g)(t)=∫0tf(τ)g(t−τ)dτ
最終値定理:
limt→∞f(t)=lims→0sF(s)
初期値定理:
limt→0+f(t)=lims→∞sF(s)
部分分数分解:
F(s)=P(s)/Q(s) で分母を因数分解し、変換対の和に分解します。
場合1:異なる実数極
F(s)=(s−p1)(s−p2)⋯(s−pn)N(s)=s−p1A1+s−p2A2+⋯
Ak=lims→pk(s−pk)F(s)
場合2:重複極 (s=p が m 重根)
F(s)=⋯+(s−p)mAm+(s−p)m−1Am−1+⋯+s−pA1
Ak=(m−k)!1[dsm−kdm−k(s−p)mF(s)]s=p
場合3:共役複素極
s2+2αs+(α2+β2)As+B⇒e−αt(C1cosβt+C2sinβt)
例題:RLC直列回路の過渡応答
Ldt2d2i+Rdtdi+Ci=E0δ(t)
初期条件: i(0)=0、i′(0)=0(キャパシタに電荷なし)
解法:
ラプラス変換を適用:
I(s)=s2+(R/L)s+1/(LC)E0/L
α=R/(2L)、ω0=1/LC、ωd=ω02−α2 (不足減衰の場合) と定義すると:
I(s)=(s+α)2+ωd2E0/L
逆ラプラス変換:
i(t)=LωdE0e−αtsinωdt
これがRLC回路のインパルス応答であり、グリーン関数でもあります。
import numpy as np
from scipy.integrate import solve_ivp
import matplotlib.pyplot as plt
def rlc_circuit(t, y, R, L, C, Vs):
q, dq_dt = y
d2q_dt2 = (Vs - R * dq_dt - q / C) / L
return [dq_dt, d2q_dt2]
R = 100
L = 0.1
C = 1e-6
Vs = 10.0
omega_0 = 1.0 / np.sqrt(L * C)
alpha = R / (2 * L)
zeta = alpha / omega_0
print(f"共振周波数: {omega_0/(2*np.pi):.1f} Hz")
print(f"減衰比 zeta: {zeta:.3f}")
if zeta > 1:
print("-> 過減衰")
elif zeta == 1:
print("-> 臨界減衰")
else:
print("-> 不足減衰")
y0 = [0.0, 0.0]
t_span = (0, 0.01)
t_eval = np.linspace(0, 0.01, 2000)
sol = solve_ivp(
rlc_circuit, t_span, y0,
t_eval=t_eval,
args=(R, L, C, Vs),
method='RK45',
rtol=1e-8,
atol=1e-10
)
v_C = sol.y[0] / C
i = sol.y[1]
fig, axes = plt.subplots(2, 1, figsize=(10, 8))
axes[0].plot(sol.t * 1e3, v_C, 'b-', linewidth=2, label='キャパシタ電圧')
axes[0].axhline(y=Vs, color='r', linestyle='--', label=f'定常状態 {Vs}V')
axes[0].set_xlabel('時間 (ms)')
axes[0].set_ylabel('電圧 (V)')
axes[0].set_title('RLC直列回路 - ステップ応答')
axes[0].legend()
axes[0].grid(True, alpha=0.3)
axes[1].plot(sol.t * 1e3, i * 1e3, 'g-', linewidth=2, label='電流')
axes[1].set_xlabel('時間 (ms)')
axes[1].set_ylabel('電流 (mA)')
axes[1].set_title('RLC回路電流')
axes[1].legend()
axes[1].grid(True, alpha=0.3)
plt.tight_layout()
plt.savefig('rlc_response.png', dpi=150)
plt.show()
import sympy as sp
t, s = sp.symbols('t s')
R_sym, L_sym, C_sym = sp.symbols('R L C', positive=True)
Vs_sym = sp.Symbol('Vs')
v = sp.Function('v')
tau = sp.Symbol('tau', positive=True)
ode = sp.Eq(v(t).diff(t), (Vs_sym - v(t)) / (R_sym * C_sym))
solution = sp.dsolve(ode, v(t), ics={v(0): 0})
print("RC回路の解:")
print(solution)
sp.pprint(solution)
f = sp.exp(-t) * sp.sin(2*t)
F = sp.laplace_transform(f, t, s, noconds=True)
print(f"\nL{{e^(-t) sin(2t)}} = {F}")
F_inv = sp.inverse_laplace_transform(
1 / (s**2 + 2*s + 5), s, t
)
print(f"L^(-1){{1/(s^2+2s+5)}} = {F_inv}")
import numpy as np
import matplotlib.pyplot as plt
def f(t, y):
return -y
def euler_method(f, t0, y0, h, n):
t = np.zeros(n+1)
y = np.zeros(n+1)
t[0], y[0] = t0, y0
for i in range(n):
y[i+1] = y[i] + h * f(t[i], y[i])
t[i+1] = t[i] + h
return t, y
def rk4_method(f, t0, y0, h, n):
t = np.zeros(n+1)
y = np.zeros(n+1)
t[0], y[0] = t0, y0
for i in range(n):
k1 = h * f(t[i], y[i])
k2 = h * f(t[i] + h/2, y[i] + k1/2)
k3 = h * f(t[i] + h/2, y[i] + k2/2)
k4 = h * f(t[i] + h, y[i] + k3)
y[i+1] = y[i] + (k1 + 2*k2 + 2*k3 + k4) / 6
t[i+1] = t[i] + h
return t, y
h = 0.5
n = 10
t0, y0 = 0.0, 1.0
t_euler, y_euler = euler_method(f, t0, y0, h, n)
t_rk4, y_rk4 = rk4_method(f, t0, y0, h, n)
t_exact = np.linspace(0, n*h, 200)
y_exact = np.exp(-t_exact)
plt.figure(figsize=(10, 5))
plt.plot(t_exact, y_exact, 'k-', linewidth=2, label='厳密解')
plt.plot(t_euler, y_euler, 'r--o', label=f'オイラー法 (h={h})')
plt.plot(t_rk4, y_rk4, 'b--s', label=f'RK4 (h={h})')
plt.xlabel('t')
plt.ylabel("y(t)")
plt.title("オイラー法 vs RK4比較: y' = -y")
plt.legend()
plt.grid(True, alpha=0.3)
plt.tight_layout()
plt.show()
print(f"t=5でのオイラー法誤差: {abs(y_euler[-1] - np.exp(-5)):.6f}")
print(f"t=5でのRK4誤差: {abs(y_rk4[-1] - np.exp(-5)):.6f}")
import sympy as sp
s, t = sp.symbols('s t', real=True)
a, omega = sp.symbols('a omega', positive=True)
functions = {
'1': sp.Integer(1),
't': t,
't^2': t**2,
't^n': t**3,
'e^(at)': sp.exp(a*t),
'sin(wt)': sp.sin(omega*t),
'cos(wt)': sp.cos(omega*t),
't*e^(at)': t * sp.exp(a*t),
'e^(at)*sin(wt)': sp.exp(a*t) * sp.sin(omega*t),
}
print("ラプラス変換表:")
print("-" * 50)
for name, func in functions.items():
F = sp.laplace_transform(func, t, s, noconds=True)
print(f"L{{{name}}} = {sp.simplify(F)}")
問題: R=50Ω、L=0.2H、C=100μF の直列RLC回路に t=0 で Vs=100V DC電源が接続される。初期条件は vC(0)=0、i(0)=0。
ラプラス変換で解く:
キルヒホッフの電圧則:
Ldtdi+Ri+C1∫idt=Vsu(t)
i=CdvC/dt で置換して電荷 q で整理:
Lq¨+Rq˙+Cq=Vs
ラプラス変換:
(Ls2+Rs+C1)Q(s)=sVs
Q(s)=s(s2+LRs+LC1)Vs/L
数値代入: α=R/(2L)=125s−1、ω0=1/LC≈223.6s−1
ω0>α なので不足減衰です。
ωd=ω02−α2≈185.0s−1
部分分数分解後、逆ラプラス変換:
vC(t)=Vs[1−e−αt(cosωdt+ωdαsinωdt)]
=100[1−e−125t(cos185t+0.676sin185t)]V
問題: m=1kg、k=100N/m、c=4N⋅s/m、F(t)=10cosωtN
固有角振動数: ωn=k/m=10rad/s
減衰比: ζ=c/(2mk)=0.2 (不足減衰)
定常状態応答の振幅:
X=(1−r2)2+(2ζr)2F0/k
r=ω/ωn=1(共振)のとき:
Xres=2ζF0/k=2×0.210/100=0.25m
これは共振なし時の静的たわみ F0/k=0.1m の2.5倍です。これが共振の危険性です。
この記事で扱った内容:
- 微分方程式の基礎: 分類、階数、線形性、解の種類
- 1階ODEの解法: 変数分離法、積分因子法、完全ODE、ベルヌーイ方程式
- 2階線形ODE: 特性方程式、3つの場合、RLC回路の完全解析
- 非斉次方程式: 未定係数法、パラメータ変換法、強制振動
- 連立ODE: 行列表現、固有値・固有ベクトルによる解法
- ラプラス変換: 定義、変換対、性質、逆変換、ODEの解法
- Python実装: scipy、sympyによる数値・記号解法
次回は**フーリエ級数・変換と偏微分方程式(PDE)**を扱います。信号処理と電磁気学の核心的な数学ツールです。
- Kreyszig, E. "Advanced Engineering Mathematics", 10th Edition, Wiley
- Boyce, W. & DiPrima, R. "Elementary Differential Equations", 11th Edition, Wiley
- Simmons, G. "Differential Equations with Applications and Historical Notes", 3rd Edition
- SciPy ODEソルバー公式ドキュメント
- SymPy ラプラス変換ドキュメント
Q1. 積分因子法はどのようなODEに使われ、dy/dx + P(x)y = Q(x) の積分因子は何ですか?
答え: 積分因子法は1階線形ODE dy/dx + P(x)y = Q(x) の標準形を解くために使います。積分因子は mu(x) = exp(P(x)のインテグラル) です。
解説: 両辺に mu(x) を掛けると左辺が mu(x)*y の導関数になり、直接積分できます。これはすべての1階線形ODEに適用できる系統的な手法です。
Q2. RLC直列回路の3つの減衰の場合とその条件は何ですか?
答え: 3つの場合は減衰係数 alpha = R/(2L) と共振周波数 omega_0 = 1/sqrt(LC) の大小関係で決まります:
- 過減衰: alpha が omega_0 より大きい (R が 2*sqrt(L/C) より大きい) — 振動なく緩やかに減衰
- 臨界減衰: alpha が omega_0 に等しい (R が 2*sqrt(L/C) に等しい) — 振動なく最速で減衰
- 不足減衰: alpha が omega_0 より小さい (R が 2*sqrt(L/C) より小さい) — 振動しながら減衰
解説: 特性方程式 r^2 + (R/L)r + 1/(LC) = 0 の根 r = -alpha ± sqrt(alpha^2 - omega_0^2) において、判別式の符号が根が実数か複素数かを決定します。
Q3. ラプラス変換の畳み込み定理とは何ですか?なぜ重要ですか?
答え: 畳み込み定理は、2つの関数の畳み込みのラプラス変換が、それぞれの関数のラプラス変換の積に等しいことを述べます: L{(f*g)(t)} = F(s)*G(s)
解説: この定理は、線形時不変システムの出力が入力信号とシステムのインパルス応答の畳み込みであることを証明する工学の基本定理です。s領域では単純な乗算になるため、システム解析が大幅に簡単になります。
Q4. 強制振動における共振とはどのような現象で、どんな条件で発生しますか?
答え: 共振は振動数比 r = omega/omega_n が1になったとき、すなわち駆動周波数がシステムの固有振動数と等しいときに発生します。共振条件では定常状態の振幅が X = (F_0/k) / (2*zeta) となり、静的たわみの何倍にもなります。
解説: 未定係数法で y'' + 4y = 3*cos(2x) を解くとき、加振周波数が固有振動数と一致するため特殊解に x の係数が現れます (永年項)。実際のシステムでは減衰により振幅は無限大にはなりませんが、共振点で最大値をとります。構造・機械工学では共振回避が重要な設計課題です。
Q5. 固有値・固有ベクトルを使った連立ODEの解法を説明してください。
答え: dX/dt = AX の形の連立ODEに対して X = vexp(lambdat) の形の解を仮定します。代入すると lambdav = Av となり、lambda は行列 A の固有値、v は固有ベクトルです。一般解はすべての固有値・固有ベクトル対の線形結合です: X = 合計(Ck * vk * exp(lambda_k * t))
解説: 固有値の実部が負であればその固有モードは減衰します。すべての固有値の実部が負なら系は安定です。固有ベクトルはシステムの各固有モードの方向を定義します。