Hi Schrompf,
ganz so einfach ist es meine ich leider nicht, dass die semi-impliziten Integratoren stabil sind. Es hängt ganz stark von der Frequenz in den Signalen und der Abtastrate (also dem dt ab).
Ich bin kein Mathematiker (mögen mir diese verzeien, falls nicht alle Termini und Zusammenhänge richtig passen), aber versuche das noch einmal nach meinem Verständnis zusammenzufassen. Alles bespielhaft in einfacher Ausprägung:
Expliziter Integrator
- Aktuelle Werte werden aus vergangenen berechnet. Im Beispiel:
- Bringt tendenziell Energie ins System.
- Beispiel Auswirkung bei zu großem dt: Aus einer Kreisbahn wird numerisch integriert eine größer werdende Spirale, ein Feder-Masse-System schwingt auf
Impliziter Integrator
- Aktuelle Werte werden aus aktuellen (und evtl. vergangenen) berechnet. Im Beispiel:
- Entnimmt tendenziell Energie aus dem System.
- Beispiel Auswirkung bei zu großem dt: Aus einer Kreisbahn wird numerisch integriert eine kleiner werdende Spirale, ein Feder-Masse-System wird gedämpft
Implizit ist einem meist lieber, generell ist das oben genannte Verhalten zwar in beiden Fällen ungenau, allerdings geht zweiteres gegen Null, ersteres gegen Unendlich.
Genauigkeit / Stabilität:
- Hängt wie oben erwähnt sehr stark vom Signal und dem dt ab
- Hängt stark vom Integrator ab, implizit/explizit, Ordnung, Verfahren etc.
Semi-Implizit
Der Euler ist erster Ordnung und daher auch nicht sonderlich gut im Sinne von genau/stabil. Bei deinem Beispiel (mit kleiner Ergänzung)
Code: Alles auswählen
a = collectAllForces();
v(n+1) = v(n) + a(n)*dt;
p(n+1) = p(n) + v(n+1)*dt;
ist der erste Teil explizit, der zweite implizit und die oben genannten Eigenschaften heben sich einigermaßen auf. Drehst du deine beiden Zeilen um, entsteht
Code: Alles auswählen
a = collectAllForces();
p(n+1) = p(n) + v(n)*dt;
v(n+1) = v(n) + a(n)*dt;
Hier sind beide explizit wie in meinem 4-Komponentenvektor-Beispiel oben im Post, das ist somit ungenauer/instabiler.
Ordnung etc.
Wie erwähnt ist der Euler aber in der Form nur erster Ordnung und somit eher für Probleme geringer Genauigkeit geeignet.
Dein zweites Beispiel kann ich in dem Zusammenhang schwer vergleichen. Es ist ja (wieder etwas angepasst)
Code: Alles auswählen
a = collectAllForces();
v(n+1) = v(n) + a(n)*dt;
p(n+1) = p(n) + v(n+1)*dt + 0.5f*a(n)*dt*dt;
Das ist irgendwie auch etwas semi-implizit (wenn Du die Zeilen tauscht, wieder nicht), aber der zweite Teil geht ja eher in Richtung Verlet-Integration, also zweiter Ordnung. Dort könntest Du theoretisch auch in der ersten Zeile diesen Term der zweiten Ordnung einbringen, das wäre physikalisch der
Jerk, die zeitliche Änderung der Beschleunignung.
Wie gesagt, fällt mir schwer zu vergleichen.
Das ist aber nur eine grobes Verständnis meinerseits, man kann damit ja ganze Dissertationen füllen und hier fehlen ja noch viele weitere auch einfache Aspekte wie Mehrschritt-Verfahren (Adams-Bashforth, Adams-Moulton -- die beiden in Kombination lassen sich wieder semi-implizit einsetzen, wenn ich das recht in Erinnerung habe), Prädiktor-Korrektor-Verfahren, höhere Ordnungen (Runge-Kutta ist sehr beliebt, benannt mit der Ordnung, RK1 müsste Euler sein, RK2 Leapfrog oder Ähnliches, viel benutzt in Physiksimulationen mit viel Dynamik RK4, usw.). Und beliebige Kombinationen aus allem sowie Fehlerordnungen (an der Stelle wird man meine ich auch aussagekräftiger über die Stabilität, habe ich mich aber nie mit beschäftigt.).