Regelung mit anfangs starkem Überschwinger

Gast #36931
Lesenswert?
• ▲
▼
Hallo,
ich habe mir einen PI Regler für meine Durchflussregelung gebastelt,
der eigentlich auch schon ganz gut funktioniert.
Nur habe ich zu Beginn immer einen ziemlich riesigen Überschwinger. Ich
frage mich, ob es ein Hardwareproblem sein könnte (A/D Wandler oder
Gasflussensor), oder ob ich da noch etwas an der Regelung probieren
müßte. Mit unterschiedlichen k_p Werten habe ich schon gearbeitet (s.
excel file). Habt ihr noch eine Idee?

(ps: Durchflussregelung müßte eigentlich auch ohne D-Anteil möglich
sein, ich habe gehört, daß die D-Anteile immer relativ schwer
einzustellen sind.)

Gruß,
Stefan
Angehängte Dateien:
Gast #36932
Lesenswert?
• ▲
▼
Hi

evtl. hilft es die Regelabweichung die du errechnest auf einen gewissen
Maximalwert zu begrenzen. Dann dauert es zwar etwas länger bis der
Sollwert erreicht wird aber die Überschwinger sind lange nicht so
heftig.

Matthias
Gast #36933
Lesenswert?
• ▲
▼
Hi Stefan

1. Ich würde mit einem D-Anteil arbeiten!
2. In deinem Fall ist aber der I-Anteil viel zu groß! Setze ihn mal um
0,6 runter und lasse den P-Anteil mal wie er ist!

Liebe Grüße
Tassilo
Gast #36934
Lesenswert?
• ▲
▼
Hallo Tassilo,
danke für die Tipps. Einen D-Anteil habe ich bisher nicht eingebaut,
ich habe nur mal etwas am I-Anteil gedreht. Sieht aber nicht besonders
viel besser aus, einen Überschwinger bekomme ich immer, ist jedoch
immer nur genau ein AD Wert. Frage mich ob das vielleicht irgendwie mit
dem Messrauschen des Sensors zusammenhängen könnte. Nur je kleiner ich
den I-Anteil mache, desto größer wird die bleibende Regelabweichung
(irgendwie logisch). Ich habe das Bild nochmal mit angehängt.
Gruß,
Stefan
Angehängte Dateien:
Gast #36937
Lesenswert?
• ▲
▼
Hier ist der wesentliche Sourcecode: (D-Anteil habe ich noch nicht
eingebaut)

unsigned int v_ist;
int e_k;    // Regelabweichung
float k_i =0.05;
float k_p =0.002;    // 1.446 Verstärkungsfaktor
int u_i = 0;
int u_p = 0;
int u_g = 0;
volatile unsigned int v_soll;
char istwert[4];
char wert[4];


#define ADC_VREF_TYPE 0x00
// ADC interrupt service routine
interrupt [ADC_INT] void adc_isr(void)
{
unsigned int adc_data;  //in adc_data wird das Ergebnis gespeichert
// Read the AD conversion result
adc_data=ADCW;

  // aktuelle Spannung einlesen (Wert zwischen 0 und 1023):
  v_ist = adc_data;


  // Regelabweichung e_k berechnen:
   e_k = v_soll - v_ist;


   // Begrenzung der Regelabweichung:
   if (e_k > 600) u_p = 600;
       else if (e_k < -600) u_p = -600;


   // P-Anteil
   u_p = (int) (e_k * k_p);

   // I-Anteil
    u_i += (int) (e_k * k_i);

    // gesamte Stellgröße (Summe aus P und I)
    u_g = u_i + u_p;


      // Stellgrößenbegrenzung:
       //if (u_p > 600) u_p = 600;
       //else if (u_p < 400) u_p = 400;

       // Stellgröße in entsprechenden PWM Wert umrechnen und
       // Pulsbreite setzen:
       OCR1A = (int) u_g;

       itoa(v_ist,istwert);
         puts(istwert);
     }

Antwort schreiben

Eine eigene Frage? Dieser Thread ist über 23 Jahre alt. Stell sie in einem eigenen Thread – dort lesen mehr Leute mit, und sie wird öfter und schneller beantwortet.

Neuen Thread starten

Eine Lösung, Ergänzung oder Rückmeldung zu diesem Thread? Dann antworte hier.

Formatierung
  • [c]C-Code[/c]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] – Link zu einem Artikel
  • Verweis auf einen anderen Beitrag: Rechtsklick auf dessen Beitrags-ID (#8078628), „Adresse kopieren“, in den Text einfügen

Mehr zur Formatierung

Längeren Sourcecode als Anhang, nicht in den Text. JPG nur für Fotos und Scans; Zeichnungen und Screenshots als PNG oder GIF. Siehe Bildformate.

Schon registriert? Anmelden

Wird nicht angezeigt. Wir schicken dir einen Link; sobald du damit bestätigst, erscheint dein Beitrag.

Mit dem Abschicken legst du einen kostenlosen Account an und erkennst die Nutzungsbedingungen und die Datenschutzerklärung an.