Penalty-Based Multibody Animation(1)

本文探讨了物理动画中如何通过穿透处理简化刚体间的碰撞计算,介绍了Lagrangian和Hamiltonian方法,并详细解释了如何利用弹簧-阻尼系统求取碰撞力,包括碰撞检测、穿透力计算和ODE求解的过程。讨论了常见问题及其解决方案,如接触法向量、穿透深度和连续性处理。

        在现实世界中,刚体与刚体由于接触力的作用是不可能发生穿透的,但是在物理动画世界,由于我们无法直接得到刚体与刚体的接触力,并且数据模型也很难具备现实世界的刚体属性。所以我们允许模型与模型之间发生穿透,这样我们就可以计算物体与物体之间的接触力,以此来进一步算出物体下一步的运动状态。

        基于穿透的物理模拟实际上是一个利用弹簧-阻尼系统来求取碰撞力的方法。

刚体运动基础

        在计算机物理模拟中,对于刚体运动通常使用常微分方程来进行描述,也就是常说的ODE。经常使用的ODE有两种,一种叫做Largrangian formulation,另一种是Hamiltonian formulation。

Largrangian formulation

        Largrangian formulation是对刚体的位置(r),刚体的姿态四元数(q),刚体的速度(v)与刚体的角速度(ω)进行求导,来构造ODE

 Hamiltonian formulation

        Hamiltonian formulation,大体上与Largrangian formulation一致,只不过用动量(P)与角动量(L)来代替速度与角速度,这样做的原因是由于动量守恒,所以可以写出更简单的方程

     在解决了OED方程的形式之后,我们需要考虑,如何构造出任意时刻刚体的OED方程。在每一帧的计算中,刚体的位置与刚体的姿态,对于我们来说都是已知的,那么重点就是求刚体的合外力与合外力矩。

        一个刚体所受的和外力应该是外力与它与其它刚体碰撞产生的碰撞力的和,同理合外力矩也应该是这样。

         在Penalty-Based中我们将碰撞里以穿透产生的弹簧力来表示

         在一个仿真循环中,通常可以分为三步

        1.运行碰撞检测,求出刚体与刚体与刚体之间的接触点

        2.计算穿透力

        3.求解ODE,来计算下一步的刚体运动状态。

        对于物体 j 来说,他受到的接触力是由于与它发生碰撞的物体 i 产生的。那么我们假设两物体间第K个接触点Pk,该点的法向量是Nk,由 i 指向 j 。这时我们考虑物体 j 所受的力,首先有穿透产生的弹簧力,还应该有弹簧回复产生的阻尼力,那么,我们就可以得到 j 所受到的穿透力。

 其中

 表示相对速度。

        又由于力的作用是相互的,那么

         同样的道理我们可以求出穿透产生的力矩

 rkj表示的是在 j 的质心坐标系中Pk的位置。 

        这样我们就可以计算出物体与物体接触所产生的力。然而事情没有那么简单。大部分情况下,我们很难得到令我们满意的接触法向量与穿透深度。比如

         

        又或者一个平面上的正方体盒子

         再或者,当某些时候接触法线变化会出现不连续的情况,就比如第一个问题图片那样。

        第一个问题出现的原因是因为在计算的时候只考虑局部,当我们从全局出发就不需要考虑这个问题。

        第二个问题,可以通过多个点采样来避免。

        第三个问题,有另外特定的方法去解决。

基于惩罚的双层梯度下降方法(Penalty-based bilevel gradient descent method)是一种用于解决双层优化问题的技术。双层优化问题通常包含一个上层问题和一个下层问题,下层问题的解会影响上层问题的目标函数。 ### 方法介绍 在双层优化问题中,上层问题通常是一个决策问题,而下层问题则是一个在给定上层决策下的优化问题。基于惩罚的双层梯度下降方法通过引入惩罚项来处理双层结构。其核心思想是将下层问题的约束条件以惩罚项的形式添加到上层问题的目标函数中,从而将双层优化问题转化为一个单层优化问题。 具体来说,假设上层问题的目标函数为 $F(x,y)$,其中 $x$ 是上层决策变量,$y$ 是下层问题的最优解,下层问题的目标函数为 $f(x,y)$ ,约束条件为 $g(x,y) \leq 0$。基于惩罚的双层梯度下降方法会构造一个新的目标函数: $F_{penalty}(x,y) = F(x,y) + \mu P(g(x,y))$ 其中 $\mu$ 是惩罚系数,$P(g(x,y))$ 是惩罚函数,通常是一个非负函数,当约束条件满足时 $P(g(x,y)) = 0$,否则 $P(g(x,y)) > 0$。 在每一次迭代中,算法会根据梯度信息更新上层决策变量 $x$ 和下层变量 $y$。对于 $x$ 的更新,使用 $F_{penalty}(x,y)$ 关于 $x$ 的梯度;对于 $y$ 的更新,使用下层问题的目标函数 $f(x,y)$ 关于 $y$ 的梯度。 ### 应用场景 - **机器学习中的超参数优化**:在机器学习中,模型的超参数选择是一个重要的问题。可以将超参数看作上层决策变量,模型参数看作下层变量。上层问题是最小化模型在验证集上的损失,下层问题是在给定超参数下最小化模型在训练集上的损失。基于惩罚的双层梯度下降方法可以用于自动选择最优的超参数 [^1]。 - **资源分配问题**:在资源分配问题中,上层问题可以是决定资源的分配策略,下层问题可以是在给定资源分配下各个子系统的优化问题。例如,在电力系统中,上层问题可以是决定发电计划,下层问题可以是在给定发电计划下各个电厂的经济调度问题。 - **多智能体系统中的协作优化**:在多智能体系统中,每个智能体可以看作一个下层优化问题,而整个系统的目标可以看作上层问题。基于惩罚的双层梯度下降方法可以用于协调各个智能体的行为,以实现整个系统的最优性能。 ### 代码示例 以下是一个简单的基于惩罚的双层梯度下降方法的 Python 代码示例: ```python import numpy as np # 上层目标函数 def F(x, y): return (x - 1)**2 + (y - 2)**2 # 下层目标函数 def f(x, y): return (y - x)**2 # 下层约束条件 def g(x, y): return y - 1 # 惩罚函数 def P(g_val): return max(0, g_val)**2 # 惩罚系数 mu = 1.0 # 学习率 lr_x = 0.1 lr_y = 0.1 # 初始化变量 x = 0.0 y = 0.0 # 迭代次数 num_iterations = 100 for i in range(num_iterations): # 计算下层问题的梯度 grad_y = 2 * (y - x) # 更新下层变量 y = y - lr_y * grad_y # 计算惩罚项的梯度 grad_g = 2 * max(0, g(x, y)) * (1 if g(x, y) > 0 else 0) grad_penalty_x = mu * grad_g * g(x, y) # 计算上层目标函数关于 x 的梯度 grad_F_x = 2 * (x - 1) + grad_penalty_x # 更新上层变量 x = x - lr_x * grad_F_x print("最优上层变量 x:", x) print("最优下层变量 y:", y) ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值