Jacobian-based IK vs FABRIK: порівняння
Коли руці робота чи анімованому скелету потрібно дотягнутися до цілі, за цю роботу змагаються два принципово різні сімейства алгоритмів: методи на основі якобіана, вкорінені в точну кінематику швидкостей руки, і FABRIK (Forward And Backward Reaching Inverse Kinematics) — суто геометричний ітеративний розв'язувач. Жоден із них не є універсально «кращим» — вони по-різному компромісують між точністю, швидкістю та загальністю.
Задача зворотної кінематики
Пряма кінематика обчислює позу кінцевого ефектора за кутами суглобів — пряме множення ланцюга матриць. Зворотна кінематика (IK) ставить обернене питання: маючи бажану позицію (і часто орієнтацію) кінцевого ефектора, які кути суглобів її дають? Для послідовного ланцюга понад кілька суглобів ця система зазвичай нелінійна й або недовизначена, або перевизначена — точного розв'язку може не бути, розв'язків може бути нескінченно багато, або розв'язок важко знайти аналітично. І методи на основі якобіана, і FABRIK — це ітеративні чисельні розв'язувачі саме для такої ситуації.
IK на основі якобіана
Матриця якобіана J пов'язує малі зміни кутів суглобів Δθ зі зміною позиції/орієнтації кінцевого ефектора Δx у просторі задачі:
J — матриця (m × n): m = ступені свободи простору задачі (напр., 6), n = кількість суглобів
Кожен стовпець j матриці J — це миттєвий внесок швидкості суглоба j — для обертального суглоба стовпець j = z_j × (p_кінець − p_j), де z_j — вісь обертання суглоба, а p_j — його позиція. Щоб пересунути кінцевий ефектор до цілі, обертають цю залежність та ітерують:
Δθ = J⁺ · e // J⁺ = псевдообернена (або транспонована, див. нижче)
θ = θ + α · Δθ // α = малий крок
повторювати, доки |e| < допуск
Три поширені варіанти різняться тим, як перетворюють J на оновлення:
- Транспонування якобіана (JT): Δθ = Jᵀ · e — найдешевше обчислити (без обернення), але збігається повільно й потребує ретельного налаштування розміру кроку.
- Псевдообернена (JPI): Δθ = J⁺ · e, де J⁺ = Jᵀ(JJᵀ)⁻¹ — точний розв'язок методом найменших квадратів на кожному кроці, швидша збіжність, але нестабільна (величезні Δθ) поблизу сингулярностей.
- Damped Least Squares (DLS): Δθ = Jᵀ(JJᵀ + λ²I)⁻¹e — трохи жертвує точністю заради стійкості поблизу сингулярностей через коефіцієнт демпфування λ.
Сингулярності та damped least squares
Кінематична сингулярність виникає, коли рука повністю витягнута або дві осі суглобів вирівнюються, через що J втрачає ранг — деякі напрямки руху стають тимчасово недосяжними, хоч би як рухалися суглоби. Поблизу сингулярності проста псевдообернена ділить на майже нульове сингулярне значення й видає величезні, нестабільні команди швидкості суглобів. Damped least squares (DLS), також званий підходом Левенберга-Марквардта до IK, додає λ²I перед оберненням саме для того, щоб обмежити це:
λ ≈ 0 далеко від сингулярностей (поводиться як JPI); λ більше поблизу сингулярностей (жертвує швидкістю заради стійкості)
Саме тому виробничі розв'язувачі IK в робототехніці (плагін KDL у MoveIt, більшість ігрового IK) за замовчуванням використовують DLS, а не «сиру» псевдообернену.
FABRIK коротко
FABRIK (Forward And Backward Reaching Inverse Kinematics) повністю оминає якобіан і обернення матриць: він розглядає ланцюг як послідовність жорстких ланок і повторно «притягує» кожен суглоб на лінію до сусіда, чергуючи зворотний прохід (від кінцевого ефектора до кореня) та прямий прохід (від кореня назад до кінцевого ефектора), щоразу точно зберігаючи довжини ланок:
Прямий: скинути J_0 = якір, потім для i = 0..n−1: J_{i+1} = J_i + L_i · нормалізувати(J_{i+1} − J_i)
повторювати, доки |J_n − ціль| < допуск
Повний вивід та реалізацію дивіться у нашій окремій статті IK FABRIK з нуля.
Порівняння напряму
| Властивість | Якобіан (DLS) | FABRIK |
|---|---|---|
| Основна операція | Побудова матриці + обернення на кожному кроці | Нормалізація + масштабування вектора, без матриць |
| Вартість ітерації | O(n²)–O(n³) | O(n) |
| Типова кількість ітерацій до збіжності | 10–50 (подібно до градієнтного спуску) | 4–15 (дуже швидка геометрична збіжність) |
| Робота з цільовою орієнтацією | Так, природно (простір задачі включає обертання) | Не природно — потребує розширень |
| Розгалужені ланцюги | Так, зі складеним якобіаном | Так, задокументованими розширеннями |
| Поведінка при сингулярності | Потребує явного демпфування (DLS) | Немає сингулярностей — суто геометрично |
| Обмеження кутів суглобів | Природно додати як проєкцію в нуль-простір | Приблизно, через обмеження кута постфактум |
| Фізична правдоподібність | Враховує реальну динаміку швидкості суглобів | Лише геометрична — без поняття швидкості/моменту суглоба |
| Найкраще для | Реальних рук роботів, планування з урахуванням моменту, надлишкових рук | Анімації персонажів, ігор реального часу, щупалець/ніг павука |
JavaScript: розв'язувач transpose якобіана
Мінімальний 2D-розв'язувач transpose якобіана для плоскої руки з n ланками — зауважте, наскільки більше апарату лінійної алгебри тут потрібно порівняно з чистою векторною арифметикою FABRIK:
function jacobianTransposeStep(joints, angles, target, alpha = 0.01) {
const n = angles.length;
const end = forwardKinematics(joints, angles); // позиція кінцевого ефектора
const ex = target.x - end.x, ey = target.y - end.y;
const dTheta = new Array(n).fill(0);
let px = 0, py = 0, angleSum = 0;
const positions = [{x: 0, y: 0}];
// прямий прохід для отримання світової позиції кожного суглоба (потрібно для стовпців якобіана)
for (let i = 0; i < n; i++) {
angleSum += angles[i];
px += joints[i].length * Math.cos(angleSum);
py += joints[i].length * Math.sin(angleSum);
positions.push({x: px, y: py});
}
// стовпець якобіана i = z × (кінець − суглоб_i), у 2D зводиться до перпендикулярного вектора
for (let i = 0; i < n; i++) {
const rx = end.x - positions[i].x, ry = end.y - positions[i].y;
const jCol = { x: -ry, y: rx }; // перпендикуляр = 2D векторний добуток з віссю z
// Δθ_i = J_i^T · e (скалярний добуток цього стовпця з вектором похибки)
dTheta[i] = jCol.x * ex + jCol.y * ey;
}
return angles.map((a, i) => a + alpha * dTheta[i]);
}
alpha й зазвичай 20–40
ітерацій для плавної збіжності — порівняйте з типовими 4–15
ітераціями FABRIK взагалі без параметрів налаштування.
Що обрати
- Потрібно керувати орієнтацією кінцевого ефектора, а не лише позицією, або враховувати реальні обмеження моменту/ швидкості приводів? → На основі якобіана (DLS).
- Будуєте гру чи анімаційний риг реального часу (ноги павука, щупальця, персонаж, що тягнеться до дверної ручки), де швидкість і простота важливіші за фізичну реалістичність? → FABRIK.
- Працюєте з надлишковою рукою (7+ суглобів для 6-DOF задачі), де хочете використати нуль-простір для вторинних цілей (уникнення перешкод, тримання подалі від меж суглобів)? → На основі якобіана, оскільки проєкція в нуль-простір — природне розширення матричної формулювання.
- Обмежений бюджет CPU, багато ланцюгів на кадр (наприклад, сотня NPC)? → FABRIK, завдяки вартості O(n) на ітерацію та швидкій геометричній збіжності.
На практиці багато виробничих систем використовують обидва: FABRIK (або CCD) для швидкого приблизного досягання, уточненого кількома ітераціями Jacobian-DLS, коли потрібна точна орієнтація кінцевого ефектора.
🦾 Спробуйте зворотну кінематику
Порівняйте поведінку досягання FABRIK наживо, прямо в браузері.