Какие физические методы моделирования наиболее подходят для действительно большого времени дельты (от часов до недель)?
Кроме того, не столкнусь ли я с какими-либо проблемами, связанными с различными методами для больших и малых значений дельты?
Какие физические методы моделирования наиболее подходят для действительно большого времени дельты (от часов до недель)?
Кроме того, не столкнусь ли я с какими-либо проблемами, связанными с различными методами для больших и малых значений дельты?
Ответы:
Вы, вероятно, будете использовать постоянное ускорение для этих больших промежутков времени (которое может быть нулевым ускорением). Производная постоянного ускорения по времени равна 0. Это означает, что она не изменяется по времени, поэтому не имеет значения, насколько велико ваше дельта-время.
Эта небольшая интеграция по времени дает уравнения, которые вам нужны.
a = a
v = at + v0
s = .5at^2 + v0*t + s0
Где: a = ускорение, v = скорость, v0 = начальная скорость, s = позиция, s0 = начальная позиция, t = время
Используя эту стратегию, вы можете использовать промежутки времени от миллисекунд до недель, если хотите. Комбинируя их будет заботиться о в v0и s0параметров уравнения.
Для обработки столкновений вам нужно будет реализовать стратегии, аналогичные тем, которые используются для высокоскоростных небольших объектов . Сначала вычисляется новая позиция, используя приведенное выше уравнение, а затем перемещается между старой и новой позицией для всех объектов. Поскольку любой из этих объектов мог пересекаться друг с другом (минуты или дни раньше), это может быть очень сложным. Скорее всего, поскольку у вас такое большое время дельты, надеюсь, у вас будет достаточно времени для обработки этих потенциальных коллизий.
Давайте возьмем пример с гравитацией.
В приведенной ниже функции предположим, что у нас есть переменные-члены класса для положения и скорости. Нам нужно обновлять их из-за силы тяжести каждые dt секунд.
void update( float dt )
{
acceleration = G * m / r^2;
velocity = velocity + acceleration * dt;
position = position + velocity * dt;
}
По мере того, как dtвсе меньше и меньше, наше моделирование становится все более и более точным (хотя, если dtстановится слишком маленьким, мы можем столкнуться с ошибками точности при добавлении крошечных чисел к большим числам).
По сути, вы должны решить, какой максимум dtможет выдержать ваша симуляция, чтобы получить достаточно хорошие результаты. А если dtвходящее слишком велико, просто разбейте симуляцию на более мелкие шаги, где каждый шаг - это максимум, dtкоторый вы допускаете.
void update( float dt )
{
acceleration = G * m / r^2;
velocity = velocity + acceleration * dt;
position = position + velocity * dt;
}
// this is the function we call. The above function is a helper to this function.
void updateLargeDt( float dt )
{
const float timeStep = 0.1;
while( dt > timeStep )
{
update( timeStep );
dt -= timeStep ;
}
update( dt ); // update with whatever dt is left over from above
}
Таким образом, с помощью этой стратегии вы можете просто приспособиться timeStep к любой точности воспроизведения (сделать ее секундой, минутой, часом или чем угодно, чтобы получить точное представление о физике).
В большинстве игр, как правило, используется простой метод прямого интегрирования Эйлера (то есть, интегрировать скорость в позицию во времени и интегрировать ускорение в скорость). К сожалению, метод Эйлера подходит только для очень маленьких временных масштабов и коротких периодов.
Существуют более сложные методы, которые более точны в течение очень длительного периода времени. Возможно, самым популярным и простым в реализации является Runge-Kutte-4 . RK4 определяет позицию в будущем, отбирая четыре позиции и скорости в прошлом и интерполируя. Он имеет тенденцию быть намного более точным, чем метод Эйлера, в более длительных временных масштабах, но является более дорогостоящим в вычислительном отношении.
Например, если вы хотите вычислить физику реальной орбитальной планеты, обновляемой каждые несколько дней в режиме реального времени, метод Эйлера заставит планету взлететь в космос после нескольких орбит из-за числовых ошибок. RK4, как правило, будет сохранять орбиту планеты примерно в одной и той же форме много тысяч раз, прежде чем накапливать слишком много ошибок.
Однако реализация коллизий в RK4 может быть очень сложной ...