Methoden und Algorithmen zur diskreten (Punkt-für-Punkt-)Integration
jives 08.03.2008 - 11:17 848 1
jives
And the science gets done
|
Eine Frage an die Mathe- und Informatikgurus hier im Forum Ich muss im Zuge eines größeren Projektes einen PID-Regler auf einem 8Bit-µC implementieren, und möchte dafür Funktionen zur Berechnung des Differentials und des Integrals schreiben. Offensichtlich handelt es sich hierbei um ein diskretes System (mit konstantem dt). Die Berechnung des Differentials lässt kaum Fragen offen: x'[n] = (x[n] - x[n-1]) / dt
Eine Variable die von einer auf die nächste Iteration gerettet werden muss ist - glaube ich - das Optimum, das man hier erreichen kann. Kleines Detail am Rande: Ich habe hier undokumentierte Implementierungen von solchen Funktionen (siehe auch weiter unten), bei der x'[n] = (x[n] - x[n-2]) / (2 * dt)
gerechnet wird. Was für einen Sinn hat das? Aus meiner Sicht hat das keine Vorteile, und man hängt mehr oder weniger mit der Berechnung unnötig einen Punkt hinten nach. Das Integral ist naturgemäß schwerer, und und ich bin nun auf der Suche nach einem möglichst schnellen und speichersparenden Algorithmus dafür. Die Implementierung (nicht in C) zu der ich Zugang habe, wählt dafür Simpson: y[n] = ((x[n] + 4 * x[n-1] + x[n-2]) / 6) * dt
bzw. für die Initialisierung y[n] = x[n] * 0.5 * dt
In C implementiert habe ich das Ganze jetzt vorerst so float function integral(float x, float dt, bool init)
{
static float y;
static float x1; // x[n-1]
static float x2; // x[n-2]
if (init)
{
y = x * 0.5 * dt;
x2 = 0;
x1 = x;
return y;
}
else
{
y += ((x + 4. * x1 + x2) / 6.) * dt;
x2 = x1;
x1 = x;
return y;
}
}
Ich brauche hier allerdings drei static-Variablen, noch dazu alle mit 32Bit, was auf meinem µC nicht ganz so optimal ist. Gibt es einen besseren Algorithmus bzw. eine bessere Methode diesen zu Implementieren? Würde mich über jeglichen Input sehr freuen - tia
Bearbeitet von jives am 08.03.2008, 11:25
|
v2.1
Bloody Newbie
|
Kann mich zwar dunkel an die Simpsons Rule erinnern (aus der Schulzeit), bin allerdings kein Mathematiker und frage mich warum du die da überhaupt brauchst? Frage jetzt nur mal interesse halber, warum würde denn folgende naive Methode nicht funktionieren: float function integral(float x, float dt, bool init)
{
static float y;
if (init)
{
y = x * dt;
}
else
{
y += x * dt;
}
return y;
}
Wenn Du dt=1 setzen kannst solltest Du überlegen ob es nicht mit Integern realisierbar wäre.
|