- Authors

- Name
- Youngju Kim
- @fjvbn20031
- はじめに — 「ロボットをやるには数学何からやればいいですか」
- 線形代数 — 6つの枝の中で唯一後回しにできないもの
- 三角法と回転表現 — 関数ひとつが半分です
- 微積分と多変数 — ヤコビアンは偏微分の表です
- 微分方程式と制御理論 — ゲインを手で触る前に
- 確率と推定 — センサーが嘘をつくとき
- 最適化 — 逆運動学も軌道計画も結局これです
- 順序に整理する — 何をいつ、何を後で
- 締めくくり — 同じ道具がずっと繰り返し出てきます
はじめに — 「ロボットをやるには数学何からやればいいですか」
この問いへのよくある答えは2つあります。ひとつは「線形代数と微積分です」という答えですが、広すぎてどこで止まればよいか分かりません。もうひとつは大学院のカリキュラムをそのまま移した目録ですが、それを全部終えてからロボットを始めた人はほとんどいません。
問題は目録ではなく順序と深さです。ロボットアームを作っていると数学が必要になる瞬間があり、その瞬間ごとに必要な深さがまったく違います。回転行列を掛けるのは学部1年の最初の1か月で十分ですが、特異点付近で関節速度がなぜ発散するのかを理解するには特異値分解まで行く必要があり、その間の差が数学期分です。ところがこの2つをひとつの目録として渡されると、最初の行で止まります。
だからこの記事は6つの枝を順序立てて整理しつつ、各枝ごとに3つを一緒に記します。
- ロボットアームのどの部分で正確に使われるか
- どの水準まで知れば十分か
- 何を後回しにしてよいか
3番目がもっとも重要です。ほとんどの人が止まる地点はまさに「これは学ばずに進んでもよいのか」で確信が持てなくなる瞬間だからです。後回しにしてよいものを明示しておくと前に進めます。
この記事はロボットアームの構造から順運動学と逆運動学を経て制御ループまで来たシリーズの最後の記事です。前の4本の記事で計算はすでに全部済ませたので、この記事はその計算の下に何が敷かれていたのかを振り返ります。
線形代数 — 6つの枝の中で唯一後回しにできないもの
ロボット工学において線形代数は道具ではなく言語です。他の5つの枝は必要になったときに学んでもよいですが、これは違います。回転行列を理解できなければ順運動学の最初の行すら読めません。
どこに使われるか。 回転行列、同次変換行列、ヤコビアン、慣性行列、これらは全部行列です。リンクごとに座標系を付けてその間を行き来することは全部基底変換です。特異点はヤコビアンのランクが落ちる現象で、操作性は特異値で定義され、冗長ロボットの零空間は文字どおり零空間です。
深さ別に分けるとこうです。
第一に、行列積とベクトル。 すぐに必要です。3×3と4×4の行列を手で掛けられて、掛け算の順序が変わると結果が変わることを体で知っていればよいです。T01 · T12とT12 · T01が違うという事実ひとつが、座標系の符号ミスの半分を防いでくれます。
第二に、基底変換。 これもすぐに必要です。この概念ひとつをしっかり押さえれば順運動学は事実上終わりです。
回転行列を「回す演算」とだけ見ると覚えることが増えていきます。代わりに列を読んでください。 回転行列の1列目は回転された座標系のx軸が元の座標系でどの方向を指すか、2列目はy軸、3列目はz軸です。
R = [ x̂' ŷ' ẑ' ] ← 新しい座標系の3つの軸を列として並べて書いたもの
したがって R · p_local は
「p_local の成分を新しい軸方向へ加重合計する」という意味になります。
こう見ると回転行列の性質が覚えるものではなく当然のことになります。列が互いに直交していて長さが1だというのは座標軸が直交していて単位長さだという意味で、だから逆行列が転置と同じになります。軸を表に書いたものなので、逆に読めば逆変換です。
第三に、ランクと零空間。 順運動学までは不要で、逆運動学に入ると必要になります。
ヤコビアンが6×6なのにランクが5に落ちると、手先が行ける方向が6次元から5次元に減ります。その失われたひとつの方向が特異点で行けない方向です。逆に関節が7個の腕ではヤコビアンが6×7で、零空間が1次元残ります。その零空間の中で関節を動かすと手先は止まったまま肘だけ動きます。冗長自由度はこういう構造です。
第四に、特異値分解。 逆運動学を数値的に解き始めると必要です。そしてこの道具がヤコビアン解析の主力です。
SVDは行列を3段階に分けます。
J = U · Σ · Vᵀ
V : 関節空間で「どの組み合わせで動くか」の主軸
Σ : その組み合わせが手先速度にどれだけ増幅されるか(特異値、対角)
U : 作業空間で「その結果がどの方向か」の主軸
なぜヤコビアンに特にSVDなのかは、特異値の意味を見れば明確になります。特異値ひとつひとつが方向別の速度伝達比です。大きい特異値に対応する方向は関節を少し回すだけで手先が大きく動き、小さい特異値の方向は関節をたくさん回さないと手先が少ししか動きません。
そうすると特異点が何なのかも自動的に出てきます。もっとも小さい特異値が0へ行く地点です。その方向へ手先を動かすには関節速度が無限大でなければなりません。最小特異値はだから「特異点までどれだけ残っているか」を測る自然な尺度で、最大と最小の比である条件数は腕の姿勢がどれだけバランスが取れているかをひとつの数字で教えてくれます。
直接確認するほうが説明を読むより速いです。上腕0.20メートル、前腕0.15メートルの2リンク平面腕のヤコビアンを、肘角度を変えながら分解してみます。
import numpy as np
L1, L2 = 0.20, 0.15
def jacobian(t1, t2):
"""2リンク平面腕の解析的ヤコビアンです。各列が関節ひとつの寄与です。"""
s1, c1 = np.sin(t1), np.cos(t1)
s12, c12 = np.sin(t1 + t2), np.cos(t1 + t2)
return np.array([
[-L1 * s1 - L2 * s12, -L2 * s12],
[ L1 * c1 + L2 * c12, L2 * c12],
])
def fk(t1, t2):
return np.array([L1 * np.cos(t1) + L2 * np.cos(t1 + t2),
L1 * np.sin(t1) + L2 * np.sin(t1 + t2)])
print(" 肘角度 σ_max σ_min 条件数")
for deg in [90, 45, 20, 10, 5, 1, 0.1]:
J = jacobian(np.radians(30), np.radians(deg))
sv = np.linalg.svd(J, compute_uv=False)
print(f" {deg:6.1f}度 {sv[0]:.6f} {sv[1]:.6f} {sv[0] / sv[1]:12.1f}")
実行結果です。
肘角度 σ_max σ_min 条件数
90.0度 0.269451 0.111337 2.4
45.0度 0.351840 0.060292 5.8
20.0度 0.375011 0.027361 13.7
10.0度 0.379341 0.013733 27.6
5.0度 0.380427 0.006873 55.4
1.0度 0.380774 0.001375 276.9
0.1度 0.380789 0.000138 2769.3
肘が伸びるほど最小特異値が0へ向かって下がり、条件数が爆発します。10度から1度、また0.1度へ減らすと条件数が27.6、276.9、2769.3とほぼぴったり10倍ずつ大きくなります。最小特異値が角度にほぼ比例して減っていくからです。腕を完全に伸ばした姿勢が特異点だという逆運動学の記事の記述が、この表の中に数字として入っています。
そして減衰最小二乗法がなぜ通じるのかもここで説明されます。擬似逆行列は特異値をそのまま反転して1/σを使うので、σが0に近いと発散します。減衰を入れるとσ / (σ² + λ²)の形になり、σが大きいときは1/σとほぼ同じで、σが0に近いときは滑らかに0へ下がります。特異点で無限大になる代わりに「その方向は諦める」になるのです。SVDなしでこれを説明しようとするとずっと難しくなります。
どの水準まで知れば十分か。 手で3×3行列の積と転置ができて、回転行列の列が軸だと知っていて、ランクと零空間の意味を言葉で説明できて、SVDの3つの断片がそれぞれ何か分かれば十分です。計算はnumpy.linalg.svdがやってくれます。特異値だけ必要ならcompute_uvを偽にするとUとVᵀを計算せず速くなります。上のコードでそう使った理由です。
何を後回しにしてよいか。 抽象ベクトル空間の公理、ジョルダン標準形、行列式の余因子展開、グラム・シュミット直交化の手計算、テンソル記法です。これらはロボットアームで使う機会が事実上ないか、必要になった時点でその場で学んでも遅くありません。
三角法と回転表現 — 関数ひとつが半分です
この枝は分量は少ないですが間違いは多く出ます。
どこに使われるか。 2リンクと3リンク腕の逆運動学の解析解が余弦定理で解かれます。回転表現は手先の姿勢を何として保存し、どう補間するかの問題です。
まず関数ひとつから押さえます。atan2です。
import numpy as np
# atan2(y, x) は符号をそれぞれ見るので象限を区別します。
print(np.degrees(np.arctan2( 1.0, 1.0))) # 45.0
print(np.degrees(np.arctan2( 1.0, -1.0))) # 135.0
print(np.degrees(np.arctan2(-1.0, -1.0))) # -135.0
# 一方、比ひとつだけを渡すと第1象限と第3象限が区別できません。
print(np.degrees(np.arctan(1.0 / 1.0))) # 45.0
print(np.degrees(np.arctan(-1.0 / -1.0))) # 45.0 ← 実際には-135度
ロボットアームのコードで肩角度が急に180度反転するバグはほとんどここから来ます。角度を求めるときは割った値ひとつを渡さず、yとxを別々に渡してください。この習慣ひとつが符号デバッグ時間のかなりの部分をなくしてくれます。
asinとacosにも同じ落とし穴があります。定義域が切られているので、丸め誤差で入力が1をほんの少し超えるとNaNが出ます。余弦定理で肘角度を求めるコードで、目標がちょうど腕の長さ分だけ離れているとき実際にこれが起きます。入力を切り取る一行が必要です。
cos_t2 = np.clip(cos_t2, -1.0, 1.0) # この一行がないと境界でNaN
回転表現は4種類あり、それぞれ違う場所で使います。
| 表現 | 数の個数 | 強み | 弱み | 主に使う場所 |
|---|---|---|---|---|
| 回転行列 | 9 | 座標変換にそのまま掛かる | 保存が大きく数値ドリフト | 計算内部 |
| オイラー角 | 3 | 人が読み書きできる | ジンバルロック、順序規約が十数種類 | ユーザー入力、ログ |
| 軸角 | 4 | 物理的な意味が直感的 | 合成が面倒 | 回転命令の表現 |
| クォータニオン | 4 | 特異点なし、補間が安価 | 人が読めない | 姿勢の保存と補間 |
実務でこの表が意味することは単純です。人が触れる境界ではオイラー角、内部計算では回転行列またはクォータニオン。 そしてその間の変換をひとつの場所にまとめておくと符号ミスが減ります。
オイラー角の順序規約は特に注意が必要な部分です。同じ3つの数字が規約によって違う回転を意味します。ライブラリを2つ混ぜて使って姿勢がおかしくなったら、まず規約を確認してください。
どの水準まで知れば十分か。 atan2を反射的に使えて、余弦定理で三角形を解けて、クォータニオンについては「掛けると回転の合成で、正規化を保つ必要があり、補間はslerpを使う」程度を知っていれば十分です。クォータニオン代数を導出する必要はありません。
何を後回しにしてよいか。 四元数の代数的構成、リー群とリー代数、指数写像と対数写像、スクリュー理論です。これらは後でとても役に立ち、特に最適化ベースの制御でコードをきれいにしてくれますが、最初の腕を動かすには必要ありません。シリアル腕をひとつ最後まで作ってから見るとずっとよく読めます。
微積分と多変数 — ヤコビアンは偏微分の表です
どこに使われるか。 ヤコビアンがすべてです。そしてヤコビアンはロボットアームで3回登場します。速度の関係で、力の関係で、そして拡張カルマンフィルタの線形化で登場します。
ヤコビアンという名前は威圧的ですが、実体は単純です。出力それぞれを入力それぞれで偏微分した値を格子状に集めたものです。
手先位置が (x, y) で関節が (θ1, θ2) なら
J = [ ∂x/∂θ1 ∂x/∂θ2 ]
[ ∂y/∂θ1 ∂y/∂θ2 ]
j 番目の列 = "θj だけを1 rad/s で回すとき手先が行く方向と大きさ"
列をこう読む習慣をつけるとヤコビアンが手に取るように分かります。腕をまっすぐ伸ばした姿勢で2つの列がほぼ同じ方向を指すようになり、だから2つの列で作れる方向の幅が狭くなり、それが前の節の最小特異値が0へ行く現象です。同じ事実を偏微分でもSVDでも見られます。
実務のコツがひとつあります。解析的ヤコビアンを導いたら必ず数値微分で検算してください。 符号ひとつ間違ったヤコビアンはIKを見当違いの方向へ収束させ、その症状は「収束が遅い」程度にしか見えないので原因を見つけにくいです。
def numeric_jacobian(f, q, eps=1e-6):
"""中心差分でヤコビアンを近似します。解析解の検算用です。"""
q = np.asarray(q, dtype=float)
base = f(*q)
J = np.zeros((len(base), len(q)))
for j in range(len(q)):
dq = np.zeros_like(q)
dq[j] = eps
J[:, j] = (f(*(q + dq)) - f(*(q - dq))) / (2 * eps)
return J
q = np.radians([30.0, 40.0])
Ja = jacobian(*q)
Jn = numeric_jacobian(fk, q)
print("解析的ヤコビアン:\n", np.round(Ja, 8))
print("数値ヤコビアン :\n", np.round(Jn, 8))
print("最大誤差 :", np.max(np.abs(Ja - Jn)))
実行結果です。
解析的ヤコビアン:
[[-0.24095389 -0.14095389]
[ 0.2245081 0.05130302]]
数値ヤコビアン :
[[-0.24095389 -0.14095389]
[ 0.2245081 0.05130302]]
最大誤差 : 2.6600312230673495e-11
誤差が1e-9水準なら導出が合っていて、1e-2水準ならどこか間違っています。中間の値が出たら大抵は符号ではなく単位(度とラジアン)を混ぜた場合です。
連鎖律もここで正体を現します。関節が6個の腕では手先位置が6つの角度の合成関数で、ヤコビアンを求めることはその合成を微分することです。フレームを掛け合わせていったのと同じ構造で微分が続きます。
どの水準まで知れば十分か。 偏微分を計算でき、連鎖律を使え、勾配がもっとも急な方向だと知っていて、数値微分で検算できれば十分です。解析的ヤコビアンを手で導くのは2リンクと3リンクまでやってみれば感覚がつかめます。6リンクはライブラリに任せてください。
何を後回しにしてよいか。 微分幾何学、多様体上の微積分、変分法、テンソル解析です。そして積分は意外とあまり使いません。ロボットアームで積分が出てくる場所はPIDのI項と軌道の累積量くらいで、どちらも離散和で実装するので解析的積分技法を使う機会はありません。
微分方程式と制御理論 — ゲインを手で触る前に
どこに使われるか。 腕がなぜ跳ねるのか、PIDの3つの項がなぜあの役割を果たすのか、制御周期がなぜ安定性を削るのか、これらすべてがこの枝です。
ロボットアームの運動方程式はこんな形です。
M(q)·q̈ + C(q, q̇)·q̇ + g(q) = τ
M(q) 慣性行列 — 姿勢によって変わります
C(q, q̇) コリオリ・遠心力 — 速度の2乗に比例します
g(q) 重力項 — 姿勢だけに依存します
τ 関節トルク — 私たちが作るもの
この式を解く必要はありません。ただし読めなければなりません。3つのことが見えます。第一に、慣性が定数ではなく姿勢の関数です。だから腕を折りたたんだときにうまく合わせたゲインが伸ばしたときには合いません。第二に、速度の2乗に比例する項があるので速く動くほど非線形性が大きくなります。第三に、重力項は速度と無関係に常にあります。だから重力補償をフィードフォワードであらかじめ引いておくと、フィードバックがすべき仕事が大きく減ります。
制御理論で実際に手に馴染ませるべきなのが2次系ひとつです。
標準形: ẍ + 2ζωn·ẋ + ωn²·x = ωn²·u
ωn 固有振動数 — どれだけ速いか
ζ 減衰比 — どうやって到着するか
ζ < 1 過小減衰、通り過ぎて戻ってきます(オーバーシュート)
ζ = 1 臨界減衰、通り過ぎずにもっとも速いです
ζ > 1 過減衰、ゆっくり染み込みます
PD制御器を付けた関節ひとつがまさにこの形になります。Pゲインがωn²に、Dゲインが2ζωnに対応します。そうするとゲイン調整の意味が変わります。数字2つを感覚でいじるのではなく、「どれだけ速く(ωn)どんな方式で(ζ)到着させるか」を決めてそれをゲインに換算する作業になります。
この対応を知っていればよくある症状がすぐに診断できます。オーバーシュートが大きければζが小さいのでDを上げます。遅いのにオーバーシュートもなければωnが小さいのでPとDを一緒に上げる必要があります。Pだけ上げると速くなる代わりにζが下がってオーバーシュートが生まれます。この関係が制御ループの記事でゲインをいじっていた作業の背景です。
遅延の問題もここから出てきます。制御周期が長いかセンサーフィルタが遅延を作ると、フィードバックが過去の誤差に反応することになり、それは位相が後ろへずれるという意味です。位相余裕が減るとゲインを少し上げただけで発振します。「サンプリングを2倍速くしたらゲインをもっと上げられるようになった」という経験がこの理論の直接の結果です。
どの水準まで知れば十分か。 2次系標準形を見てζとωnを読めて、それがPDゲインとどう対応するか知っていて、遅延が位相余裕を削るという事実を知っていれば十分です。ラプラス変換は「微分が掛け算になる」ということと極の位置が応答を決めるという概念程度でよいです。
何を後回しにしてよいか。 状態空間最適制御(LQR)、頑健制御、リアプノフ安定性証明、ナイキスト判別法の厳密な適用、適応制御です。これらはロボットアームを製品にするときに必要になりますが、腕を初めて動かす段階ではPDと重力補償で十分遠くまで行けます。
確率と推定 — センサーが嘘をつくとき
どこに使われるか。 エンコーダは量子化されていて、IMUはドリフトし、ビジョンは照明で揺れます。複数のセンサーの値が食い違うとき何を信じるか決めるのがこの枝です。
この枝は前の4つより遅く必要になります。 位置制御だけをする腕はエンコーダひとつだけを使い、その値をそのまま信じてもだいたいうまくいきます。確率が必要になる時点は大抵センサーが2つ以上になったときです。腕にカメラを付けるか、IMUを追加するか、力センサーを入れるときです。
核心となる概念は3つです。
第一に、不確実性を数字で書く方法。 測定値ひとつではなく「平均と分散」の対で扱います。多次元なら共分散行列になり、その行列は不確実性がどの方向にどれだけ広がっているかを表す楕円です。ここで線形代数が再び出てきます。共分散行列の固有ベクトルが楕円の軸で、固有値が軸の長さです。
第二に、不確実性の伝播。 不正確な関節角度から順運動学を計算すると手先位置も不正確になります。どれだけ不正確かはヤコビアンで計算します。
関節角度の共分散がΣqのとき、手先位置の共分散は
Σx ≈ J · Σq · Jᵀ
ヤコビアンがまた出てきました。この記事でヤコビアンに3回出会うと言った理由がこれです。そしてこの式は実務的に重要な事実を教えてくれます。特異点付近ではヤコビアンが特定方向に大きく増幅するので、同じエンコーダ誤差が手先ではずっと大きな誤差になります。特異点は速度だけの問題ではなく精度の問題でもあります。
第三に、カルマンフィルタ。 名前は怖いですが1次元では一行で説明できます。予測値と測定値がそれぞれ不確実性を持っているとき、両方を精度(分散の逆数)で加重平均することです。
予測: x̂ = 5.0, 分散 = 4.0 (精度 0.25)
測定: z = 6.0, 分散 = 1.0 (精度 1.00)
重み = 1.00 / (0.25 + 1.00) = 0.8 ← これがカルマンゲインです
更新値 = 5.0 + 0.8 × (6.0 - 5.0) = 5.8
更新分散 = 1 / (0.25 + 1.00) = 0.8 ← どちらよりも小さいです
測定のほうが正確なのでそちら寄りに動き、2つの情報を合わせたので不確実性が減りました。これで全部です。多次元カルマンフィルタはこの計算を行列に移したもので、拡張カルマンフィルタは非線形モデルを毎ステップヤコビアンで線形化してから同じ計算をするものです。
どの水準まで知れば十分か。 ガウス分布の平均と分散、共分散行列が楕円だという感覚、上の1次元カルマン更新を手で計算できる程度で十分です。実際の実装はライブラリを使いますが、チューニングパラメータであるプロセスノイズと測定ノイズが何を意味するかは知っておく必要があります。
何を後回しにしてよいか。 パーティクルフィルタ、ファクターグラフとグラフSLAM、ベイズ推論の理論的基礎、情報フィルタ、無香カルマンフィルタです。そしてロボットアームだけを扱うならSLAM全体を後回しにできます。SLAMは移動ロボットの問題で、固定されたベースを持つ腕には登場しません。
最適化 — 逆運動学も軌道計画も結局これです
どこに使われるか。 この枝の要点は、これまで別々に学んだものが同じ枠組みの中に入ってくるということです。
数値逆運動学は最小二乗問題です。目標位置と現在位置の差を最小にする関節角度を探します。減衰最小二乗法はそこに関節速度の大きさへの罰則を足したもの、つまり正則化された最小二乗法です。機械学習でリッジ回帰と呼ぶものと同じ構造です。
通常の最小二乗: minimize ‖J·Δq - Δx‖²
減衰最小二乗: minimize ‖J·Δq - Δx‖² + λ²·‖Δq‖²
└── この項が発散を防ぎます
軌道計画も最適化です。最小ジャーク軌道はジャークの2乗積分を最小化した結果で、時間最適軌道はトルクと速度限界の下で時間を最小化した結果です。制御ループの記事で5次多項式を導いたことも、境界条件6つを満たす関数の中からなめらかなものを選ぶという点で同じ種類の問題です。
最近の腕制御の標準形は速度レベルの逆運動学を2次計画法(QP)で解くことです。目的は手先を目標速度で動かすことで、制約として関節角度限界、関節速度限界、衝突回避を不等式で入れます。一度にひとつずつ処理していたものをひとつの問題にまとめる方式です。
ここで知っておくべき概念は3つです。
凸と非凸の違い。 凸問題は局所解がそのまま大域解なので、どこから出発しても同じ場所に到着します。最小二乗法とQPがここに属します。一方、位置レベルの逆運動学は非凸なので初期値によって違う解へ行きます。肘が上に曲がった解と下に曲がった解が両方とも正解である状況がそれです。非凸問題では初期値がアルゴリズムの一部です。 直前の姿勢を初期値として使う理由がここにあります。
正則化の意味。 罰則項の係数を上げると解が小さく安定的になりますが、目標追従は悪くなります。減衰最小二乗法の減衰係数を調整することが正確にこの綱引きで、特異点付近だけで減衰を大きくする技法は綱引きの位置を状況に応じて変える方法です。
制約がある問題とない問題。 関節限界を罰則として入れることと不等式制約として入れることは違います。罰則は限界を少し超える解を許し、制約は許しません。実際のハードウェアでは関節限界を超えると物理的にぶつかるので、制約のほうが正しいです。
どの水準まで知れば十分か。 最小二乗問題を正規方程式で書けて、正則化項が何をするか知っていて、凸性と初期値依存性の関係を知っていて、勾配降下法がどう回るか知っていれば十分です。QPソルバーはライブラリを使います。
何を後回しにしてよいか。 内点法の実装、双対性理論とKKT条件の導出、逐次二次計画法(SQP)の詳細、軌道最適化の直接法と間接法の比較です。これらは自前のソルバーを作るか論文を書くときに必要です。腕を動かすにはソルバーを呼び出せれば十分です。
順序に整理する — 何をいつ、何を後で
6つの枝をひとつの表に畳み込むとこうなります。左に行くほど先に必要で、右の列がこの記事でもっとも重要な部分です。
| 枝 | いつ必要になるか | ロボットアームのどこに | この程度で十分 | 後回しにしてよいもの |
|---|---|---|---|---|
| 行列積、基底変換 | 初日 | 回転行列、同次変換 | 3×3の手計算、列が軸だという理解 | 抽象ベクトル空間、ジョルダン標準形 |
三角法、atan2 | 最初の週 | 2リンクIK解析解 | 余弦定理、象限の区別 | リー群、指数写像、スクリュー理論 |
| 回転表現 | 3次元に入るとき | 姿勢の保存と補間 | 4つの表現の用途区別、slerp | 四元数代数の構成 |
| 偏微分、ヤコビアン | 速度を扱うとき | 速度・力の関係、数値IK | 偏微分と連鎖律、数値検算 | 微分幾何、変分法 |
| ランク、零空間、SVD | 特異点に出会うとき | 特異点、操作性、冗長自由度 | 特異値が方向別伝達比だという理解 | 数値SVDアルゴリズムの実装 |
| 2次系、減衰比 | ゲインを触るとき | PIDチューニング、遅延と安定性 | ζとωnがゲインに対応する関係 | LQR、頑健制御、リアプノフ証明 |
| 最小二乗、正則化 | 数値IKを使うとき | DLS、軌道最適化 | 正規方程式、罰則の役割 | 内点法、KKT導出、SQP |
| ガウス分布、共分散 | センサーが2つ以上のとき | 誤差伝播、フィルタリング | 1次元カルマン手計算 | パーティクルフィルタ、ファクターグラフ |
教科書をひとつだけ選ぶなら、ケビン・リンチとフランク・パークのModern Robotics: Mechanics, Planning, and Controlを勧めます。プレプリントPDFと講義動画、そしてPython・MATLAB・Mathematicaの実装がすべて公開されているので、上の表のどの行でつまずいても該当する章に入っていけます。ただしこの本はスクリュー理論を前面に押し出す構成なので、上の表の「後回しにしてよいもの」に先に出会うことになります。最初に読むときはその部分を飛ばして必要な章だけ選んでも構いません。
もっともよくある間違いはこの表を上から下まで全部終えてからロボットを始めようとすることです。逆にやるほうがずっと速いです。最初の2行だけ持って2リンク腕を動かしてみて、特異点で腕が暴れるのを自分の目で見てから5行目を読むと、その日のうちに理解できます。必要が生まれた後に学ぶことと必要を想像しながら学ぶことでは吸収率が違います。
そして後回しにしてよいもの列をもう一度見てください。あの右の列の項目は例外なく学部カリキュラムのかなりの部分を占めます。リー群、LQR、KKT条件、パーティクルフィルタ。これらが必要ないという意味ではなく、これらがなくても動く腕は作れるという意味です。そして動く腕を一度作ってみた人があの目録を読むと、各項目がどの問題を解くのか見えるのでずっと速く学べます。
締めくくり — 同じ道具がずっと繰り返し出てきます
この記事を書きながらもうひとつ確認したことがあります。6つの枝に分けましたが、実際にはいくつかの道具がずっと繰り返し出てくるという事実です。
ヤコビアンは速度の関係で最初に出て、力の関係で再び出て、誤差伝播でまた出て、拡張カルマンフィルタの線形化でまた出ます。SVDは特異点を説明し、操作性を定義し、減衰最小二乗法がなぜ通じるのかを説明し、共分散楕円の軸を教えてくれます。最小二乗法は逆運動学であり軌道計画でありフィルタリングです。
だから学習戦略も決まります。広く浅く見るより、頻繁に出てくる道具を深く掘るほうがよいです。 ヤコビアンひとつを4つの文脈で理解するほうが、その4か所を別々に学ぶより時間がかからず長く残ります。
そしてこの記事の目録でもっとも価値が大きい部分は前ではなく後ろ、後回しにしてよいものです。学ぶことを決めるより学ばないことを決めるほうが前に進みます。数学が足りなくてロボットを始められなかった人より、全部学んでから始めようとして始められなかった人のほうがずっと多いです。
一行に縮めるとこうなります。行列積とatan2だけ持って始めても腕は動きます。残りは腕がおかしな動きをしたときに学べばよいのです。