PID-Regelkreise mit großen und unvorhersehbaren Anomalien


10

Kurze Frage
Gibt es eine übliche Methode, um mit sehr großen Anomalien (Größenordnung) in einem ansonsten einheitlichen Kontrollbereich umzugehen?

Hintergrund
Ich arbeite an einem Steueralgorithmus, der einen Motor über einen allgemein einheitlichen Steuerbereich antreibt. Ohne / mit minimaler Belastung funktioniert die PID-Regelung hervorragend (schnelle Reaktion, wenig bis kein Überschwingen). Das Problem, auf das ich stoße, ist, dass es normalerweise mindestens einen Ort mit hoher Last gibt. Die Position wird vom Benutzer während der Installation festgelegt, daher gibt es für mich keine vernünftige Möglichkeit zu wissen, wann / wo sie zu erwarten ist.

Wenn ich die PID so einstelle, dass sie den Ort mit hoher Last bewältigt, führt dies zu großen Überschüssen auf den nicht belasteten Bereichen (was ich voll und ganz erwartet habe). Während es in Ordnung ist , während des Federwegs zu überschießen, gibt es keine mechanischen harten Anschläge am Gehäuse. Das Fehlen von Hardstops bedeutet, dass ein signifikantes Überschwingen dazu führen kann / muss, dass der Querlenker vom Motor getrennt wird (was zu einer toten Einheit führt).

Dinge, die ich prototypisiere

  • Verschachtelte PIDs (sehr aggressiv, wenn sie weit vom Ziel entfernt sind, konservativ, wenn sie in der Nähe sind)
  • Feste Verstärkung in der Ferne, PID in der Nähe
  • Konservative PID (arbeitet ohne Last) + eine externe Steuerung, die darauf achtet, dass die PID blockiert und zusätzliche Energie anlegt, bis entweder: das Ziel erreicht ist oder eine schnelle Änderungsrate erkannt wird (dh der Bereich mit hoher Last verlassen wird)

Einschränkungen

  • Volle Reise definiert
  • Hardstops können nicht hinzugefügt werden (zu diesem Zeitpunkt)
  • Der Fehler wird wahrscheinlich niemals auf Null gesetzt
  • Die hohe Last könnte von einer Fahrt von weniger als 10% erhalten worden sein (was bedeutet, dass kein "Laufstart" vorliegt).

Antworten:


2

Ihre Fehlerberechnung scheint beim Arbeiten mit dem abgeleiteten Term keinen Fehler zu akkumulieren, und Sie können dies ändern, da nur der abgeleitete Term auf schnelle Änderungen im Prozess reagieren kann.

Wenn ich es richtig verstanden habe, dein Code

// Determine the error delta
dE = abs(last_error - new_error);
last_error = new_error;

berechnet den Steuerterm immer basierend auf dem aktuellen Fehler. Dies ist die traditionelle Art und Weise, wie die PID implementiert wurde. Es ist in Ordnung, da der I-Begriff sowieso für akkumulierte Fehler sorgen soll.

Ich hatte jedoch einen Kunden, der auf die folgende Idee kam, die Sie vielleicht ausprobieren möchten. Da Sie einen Teil der Prozesskurve haben, in dem aggressivere Änderungen erforderlich sind, können Sie sogar den Fehler des D-Teils akkumulieren lassen:

if(TD)                                                 // Calculate D term
{  
   Last_C += (Error - Last_C) / TD;                    // D term simulates
   Dterm = (Error - Last_C) * KD;                      // capacitor discharging
}
else    
   Dterm = 0;                                          // D term is OFF (TD is 0)

Hier sind zwei interessante Dinge zu beachten:

  • Der TD-Wert ist nicht die Ableitungsverstärkung (die KD ist), sondern die Ableitungszeit, eine Benutzerkonstante, die die Zeit für die Akkumulation von Fehlern steuert. Wenn es auf Null gesetzt wurde, wird der D-Teil der PID unabhängig vom eingestellten KD-Verstärkungswert deaktiviert.

  • Beachten Sie, wie der aktuelle Fehler verwendet wurde, um den Last_C-Wert zu "berechnen", bevor er in die D-Teil-Berechnung übernommen wurde. Die Last_C-Variable verhält sich wie ein Kondensator. Sie würde sich aufbauen, während der Fehler groß war, so dass Ihr abgeleiteter Teil auch auf der Grundlage einer aktuellen "Historie" des Fehlers und danach (wenn der Fehler kleiner war) dieser "Historie" agieren würde 'entlädt sich wie ein Kondensator.

Natürlich sollten Sie die Gesamtleistung so begrenzen, wie Sie es wahrscheinlich bereits getan haben (Anti-Windup-Reset, stoßfreie automatische Übertragung auf manuelle Übertragung und andere übliche Dinge).

Ich kann weitere Details zu anderen Begriffen meines PID-Algorithmus veröffentlichen, wenn Sie dies nützlich finden, aber Sie möchten dies möglicherweise versuchen und sehen, was passiert. Es hat meinem Kunden jahrelang gute Dienste geleistet.


Danke für die Eingabe. Ich muss es versuchen. Auf den ersten Blick scheint es sinnvoll zu sein.
Adam Lewis

Ich verstehe, Sie haben also einen D-Term-Beitrag innerhalb Ihrer 'Haupt'-PID sowie die Blockierungserkennung, die zur Berechnung beiträgt.
Drazen Cika

1
Das ist richtig. Der Dterm des PID wird während des Tunings verwendet, obwohl er nicht sehr aggressiv ist. Was dieses Problem noch schwieriger macht, ist, dass sich die Last in sehr kurzer Zeit lösen kann . IE eine Verknüpfung wird gelöst. Diese abrupte Kraftentfernung verursacht große Überschwinger, wenn eine Glättungsfunktion (Summation) auf die Strömungsabrisskräfte ausgeübt wird.
Adam Lewis

Böses Problem, es wäre interessant zu wissen, wie gut ein Fuzzy-Logik-Algorithmus damit umgehen würde. Zumindest könnten Sie mehr von Ihrer problembezogenen Erfahrung in den Algorithmus einbauen, anstatt sich auf die Standardlösungen zu beschränken. Wie auch immer, viel Glück damit :-)
Drazen Cika

1

Erste Lösung

Stalled_pwm_output = PWM / | ΔE |

PWM = Max. PWM-Wert
ΔE = letzter Fehler - neuer Fehler

Die anfängliche Beziehung erhöht erfolgreich die PWM-Ausgabe basierend auf der fehlenden Änderung im Motor. In der folgenden Grafik finden Sie die Beispielausgabe.

Dieser Ansatz gilt seitdem für die Situation, in der die nicht aggressive PID ins Stocken geriet. Es hat jedoch das unglückliche (und offensichtliche) Problem, dass, wenn die nicht aggressive PID den Sollwert erreichen kann und versucht zu verlangsamen, der blockierte_pwm_Ausgang ansteigt. Dieser Anstieg verursacht ein großes Überschwingen, wenn Sie in eine unbelastete Position fahren.

1 / ΔE gegen ΔE

Aktuelle Lösung

Theorie

Stalled_pwm_output = (kE * PID_PWM) / | ΔE |

kE = Skalierungskonstante
PID_PWM = Aktuelle PWM-Anforderung von der nicht aggressiven PID
ΔE = letzter Fehler - neuer Fehler

Meine aktuelle Beziehung verwendet immer noch das 1 / ΔE-Konzept, verwendet jedoch den nicht aggressiven PID-PWM-Ausgang, um den Stall_pwm_output zu bestimmen. Dies ermöglicht es der PID, den Stall_pwm_output zu drosseln, wenn sie sich dem Zielsollwert nähert, und ermöglicht im Stillstand eine 100% ige PWM-Ausgabe. Die Skalierungskonstante kE wird benötigt, um sicherzustellen, dass die PWM in den Sättigungspunkt gelangt (über 10.000 in den nachstehenden Diagrammen).

Pseudocode

Beachten Sie, dass das Ergebnis von cal_stall_pwm zum PID-PWM-Ausgang in meiner aktuellen Steuerlogik hinzugefügt wird .

int calc_stall_pwm(int pid_pwm, int new_error)
{
    int ret = 0;
    int dE = 0;
    static int last_error = 0;
    const int kE = 1;

    // Allow the stall_control until the setpoint is achived
    if( FALSE == motor_has_reached_target())
    {
        // Determine the error delta
        dE = abs(last_error - new_error);
        last_error = new_error;

        // Protect from divide by zeros
        dE = (dE == 0) ? 1 : dE;

        // Determine the stall_pwm_output
        ret = (kE * pid_pwm) / dE;
    }

    return ret;
}

Ausgabedaten

Blockierter PWM-Ausgang Blockierter PWM-Ausgang

Beachten Sie, dass im Diagramm für blockierte PWM-Ausgänge der plötzliche PWM-Abfall bei ~ 3400 eine integrierte Sicherheitsfunktion ist, die aktiviert wurde, weil der Motor innerhalb einer bestimmten Zeit die Position nicht erreichen konnte.

Nicht geladener PWM-Ausgang PWM-Ausgang ohne Last


1

Sie sagen nicht, was Sie steuern ... Motordrehzahl? Position? Was auch immer es ist, der erste Schritt wäre zu definieren, was ein akzeptabler Fehler wäre. Wenn die Steuerung beispielsweise auf Geschwindigkeit ausgelegt ist, kann ein maximaler Fehler innerhalb von 1% des Ziels eingestellt werden. Ohne den akzeptablen Fehler zu definieren, können Sie nicht bestimmen, wie viel Auflösung Sie für die ADCs oder die PWM-Anzahl benötigen. Ohne dies könnte die PID-Kompensation perfekt sein, hätte aber immer noch Grenzzyklusschwingungen.

Dann müssen Sie die Dynamik des Open-Loop-Systems kennen. Ohne das können Sie nicht wissen, welche Verstärkungen für die proportionalen (P), integralen (I) und abgeleiteten (D) Teile der Schleife benötigt werden. Sie können die Dynamik mit dem Eingabeschritt (schrittweise Änderung des Antriebspegels oder der PWM) oder der schrittweisen Änderung der Last messen (dies scheint für Sie relevant zu sein).

Durch die Verwendung der Änderung des Zyklus-zu-Zyklus-Fehlers im Nenner Ihres Steueralgos zum Ändern des PWM-Werts wird sichergestellt, dass sich die Schleife niemals einstellt. Dies stellt eine Grenzzyklusschwingung in der Steuerung sicher. Die meisten Kunden würden sich das nicht gefallen lassen.

Der P-Teil der Schleife kümmert sich um den sofortigen Fehler (reagiert sofort auf einen Fehler). Aber es wird einen endlichen Gewinn haben, so dass ein Fehler übrig bleibt. Der I-Teil der Schleife reagiert langsam mit der Zeit, um eine unendliche Verstärkung (unendliche Zeit für eine unendliche Verstärkung) anzuwenden, um den Fehler zu korrigieren, der vom P-Teil übrig geblieben ist.

Da der I-Teil langsam ist, kann er mit der zur Fehlerminimierung erforderlichen Korrektur außer Phase geraten, selbst wenn Sie die richtige Verstärkung dafür eingestellt haben. Es wird also abgewickelt, und es dauert lange, bis es sich erholt hat. Oder es bleibt im Gegensatz zum P-Teil.

Der beste Weg, um das Aufwickeln zu handhaben, besteht darin, den maximal im Integrator gespeicherten Wert auf etwas mehr zu begrenzen, als zur Korrektur des proportionalen Fehlers im schlimmsten Fall erforderlich ist. Wenn der Integrator außer Phase gerät und im Gegensatz zum P auseinander steht, setzen Sie den Integratorwert am besten auf Null. Der Algo kann so ausgelegt werden, dass er dies erkennt und den Integrator bei Bedarf zurücksetzt.

Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.