Я искал в Интернете какое-то время для методов интеграции в физический движок, который я пытаюсь запрограммировать для развлечения (нужно любить некрасивость там: P). Я нашел метод Эйлера, RK4 и Verlet (а также исправленную по времени версию). Я также пытался придумать некоторые из моих собственных методов. Мне было интересно, знаете ли вы о других, которые вы нашли интуитивно понятными или полезными. Благодарю.Каковы некоторые хорошие алгоритмы для численного интегрирования для физического движка?
EDIT: Спасибо за вашу помощь. Что касается уточнения: возможно, я имею в виду цифровую интеграцию. Удивительно, но во всех моих исследованиях я не нашел столько, сколько технического ИМЯ за то, что я пытаюсь сделать! Возможно, описание моей конкретной проблемы сделает мой вопрос более ясным. Позволяет сказать, что я хочу имитировать шар, движущийся через круговое (или сферическое, когда я реализую 3d) гравитационное поле. Этот шар столкнется с векторами силы, которые могут быть использованы для вычисления соответствующего вектора ускорения для точки, в которой шар находится на этом конкретном тике. Из вашего класса физики вы знаете, что скорость = время ускорения *, но моя проблема заключается в том, что шар технически находится на этой точке только мгновенно, математически представленный в исчислении на dt. Очевидно, что я не могу использовать бесконечно малое число в C++, поэтому я должен аппроксимировать решение с помощью методов мгновенной интеграции (термин, который я слышал в некоторых чтениях, но я мог быть совершенно не прав) или то, что вы считаете численной интеграцией (вы, вероятно, так что я изменил название).
Вот моя (успешная) попытка реализации метода Эйлера численного интегрирования:
//For console output. Note: I know I could just put "using namespace std;" but I hate doing that.
#include <iostream>
using std::cout;
using std::system;
using std::endl;
//Program entry
int main (void)
{
//Variable decleration;
double time = 0;
double position = 0;
double velocity = 0;
double acceleration = 2;
double dt = 0.000001; //Here is the "instantanious" change in time I was talking about.
double count = 0; //I use count to make sure I am only displaying the data at whole numbers.
//Each irritation of this loop is one tick
while (true)
{
//This next bit is a simplified form of Euler's method. It is what I want to "upgrade"
velocity += acceleration * dt;
position += velocity * dt;
if (count == 1/dt) //"count == 1/dt" will only return true if time is a whole number.
{
//Simple output to console
cout << "Time: " << time << endl;
cout << "Position: " << position << endl;
cout << "------------------" << endl;
system ("pause");
count = 0; //To reset the counter.
}
//Update the counters "count" and "time"
count++;
time += dt;
}
return 1; //Program exit
}
Поскольку ускорение постоянно и эта разница на самом деле решаемая (почему я использую его, чтобы проверить, раствор position = time^2, это довольно точно, но если вы сделаете это немного сложнее, например, за счет ускорения с течением времени, алгоритм теряет точность очень быстро. Опять же, спасибо!
Что вы подразумеваете под «мгновенной интеграцией»? Вы имеете в виду «цифровую интеграцию»? –
Я думаю, автор означает «числовое интегрирование обыкновенных дифференциальных уравнений». Метод Рунге-Кутты довольно хорош. – lapk
@ Никол Болас Я сделал все возможное, чтобы разъяснить вам, ребята. – AnalyticalInsanity