реклама на сайте
подробности

 
 
2 страниц V  < 1 2  
Reply to this topicStart new topic
> PID регулятор от Atmel, как-то не радует он меня. А должен.
demiurg_spb
сообщение May 24 2010, 12:08
Сообщение #16


неотягощённый злом
******

Группа: Свой
Сообщений: 2 746
Регистрация: 31-01-08
Из: Санкт-Петербург
Пользователь №: 34 643



Цитата(raf329 @ May 24 2010, 15:41) *
c ПИД регулятором работаю впервые, так когда необходимо вызывать данную ф-ию?
Почитайте пожалуйста теорию, хотя бы немного...


--------------------
“Будьте внимательны к своим мыслям - они начало поступков” (Лао-Цзы)
Go to the top of the page
 
+Quote Post
Tanya
сообщение May 24 2010, 12:33
Сообщение #17


Гуру
******

Группа: Модераторы
Сообщений: 8 752
Регистрация: 6-01-06
Пользователь №: 12 883



Цитата(demiurg_spb @ May 24 2010, 15:22) *
Может значить, а может и нет (я утрировал).

Предупреждать надо. Вы же не утром писали...

Цитата(raf329 @ May 24 2010, 14:32) *
вызывать pid_Reset_Integrator() при error == 0 или когда???

Можете вызывать джинна Обнулятора и в этот момент. Только один раз.
Или держать интегральный член нулевым до уменьшения скорости в ... X раз.
А еще лучше - плавно менять задатчик, не вызывая джинна.
Go to the top of the page
 
+Quote Post
demiurg_spb
сообщение May 24 2010, 13:11
Сообщение #18


неотягощённый злом
******

Группа: Свой
Сообщений: 2 746
Регистрация: 31-01-08
Из: Санкт-Петербург
Пользователь №: 34 643



Цитата(Tanya @ May 24 2010, 16:33) *
Предупреждать надо. Вы же не утром писали...
Когда встал - тогда и утро!
Тем не менее, бью челом! Простите холопа:-)


--------------------
“Будьте внимательны к своим мыслям - они начало поступков” (Лао-Цзы)
Go to the top of the page
 
+Quote Post
Jenyok2
сообщение Oct 9 2011, 16:40
Сообщение #19


Участник
*

Группа: Участник
Сообщений: 41
Регистрация: 25-02-09
Из: Russia, Moscow
Пользователь №: 45 341



Вот реализация ПИД алгоритма.
В процедуре DoChart 4-е цикла с разными реализациями ПИД алгоритма.
Язык программирования Delphi 7.0 .
Функция для регулироания fPID внутри процедуры DoChart.
Для тестирования и применения в ваших программах.
.
Код
  function TForm1.ChangeValPoint(s : String) : String;
    var
      i : Integer;
    begin
       Result:=s;
       i:=Length(s);
       while (i > 0) and (Result[i] <> '.') do Dec(i);
       if (i > 0) then Result[i]:=',';
    end;

  procedure TForm1.DoChart;
    var
      f    : array[1..4000] of Real;
      f1   : array[1..4000] of Real;
      f2   : array[1..4000] of Real;
      f3   : array[1..4000] of Real;

      A, B : Real;
      i    : Integer;
      n    : integer;

      min_integ_error,
      max_integ_error,
      integral : Real;
      diapazon : Real;

      T0   : Real; { Ïåðèîä êâàíòîâàíèÿ (äèñêðåòèçàöèè) }
      Ti   : Real; { Ïîñòîÿííàÿ èíòåãðèðîâàíèÿ }
      Td   : Real; { Ïîñòîÿííàÿ äèôåðåíöèðîâàíèÿ }

      q0   : Real;
      q1   : Real;
      q2   : Real;

      Uk   : Real; { Òåêóùåå çíà÷åíèå U(k) }
      Uk1  : Real; { Ïðåäûäóùåå çíà÷åíèå U(k-1) }
      ek   : Real; { Òåêóùåå çíà÷åíèå îøèáêè e(k) }
      ek1  : Real; { Ïðåäûäóùåå çíà÷åíèå îøèáêè e(k-1) }
      ek2  : Real; { Ïðåäûäóùåå çíà÷åíèå îøèáêè íà äâà øàãà íàçàä e(k-2) }

      Uust : Real; { Çíà÷åíèå óñòàâêè (âõîäíîé âåëå÷èíû) }

      Kp   : Real;
      Ki   : Real;
      Kd   : Real;
      Ku   : Real;

    function fPID(i : Integer; Uk : Real) : Real;
      begin
        B:=0.2;
        A:=i / 10.0;
//        Result:=Uk * ((1.0 / A) / (B + 1.0 / A));

//        t:=(i - 1) / 250000.0;
//        f[i]:=k * (1.0 - Exp(-1.0 * t / Tau));

//        Result:=10.0 * sin(((i - 1) - Uk) / 40.0);
        Result:=sin(((i - 1) - Uk) / 40.0);
      end;

    begin

      { Series1 - Ôóíêöèÿ äëÿ ðåãóëèðîâàíèÿ }
      { Series2 - PID }
      { Series3 - PID + Ôóíêöèÿ ðåãóëèðîâàíèÿ }
      { Series4 - Îøèáêà }

      Form1.LabeledEdit1.Text:=ChangeValPoint(Form1.LabeledEdit1.Text);
      Form1.LabeledEdit2.Text:=ChangeValPoint(Form1.LabeledEdit2.Text);
      Form1.LabeledEdit3.Text:=ChangeValPoint(Form1.LabeledEdit3.Text);
      Form1.LabeledEdit4.Text:=ChangeValPoint(Form1.LabeledEdit4.Text);
      Form1.LabeledEdit5.Text:=ChangeValPoint(Form1.LabeledEdit5.Text);
      Form1.LabeledEdit6.Text:=ChangeValPoint(Form1.LabeledEdit6.Text);
      Form1.LabeledEdit7.Text:=ChangeValPoint(Form1.LabeledEdit7.Text);
      Form1.LabeledEdit8.Text:=ChangeValPoint(Form1.LabeledEdit8.Text);
      Form1.LabeledEdit9.Text:=ChangeValPoint(Form1.LabeledEdit9.Text);

      Uust:=StrToFloat(Form1.LabeledEdit1.Text);
      Kp:=StrToFloat(Form1.LabeledEdit2.Text);
      Ki:=StrToFloat(Form1.LabeledEdit3.Text);
      Kd:=StrToFloat(Form1.LabeledEdit4.Text);
      T0:=StrToFloat(Form1.LabeledEdit5.Text);
      n:=StrToInt(Form1.LabeledEdit6.Text);
      Ku:=StrToFloat(Form1.LabeledEdit7.Text);
      min_integ_error:=StrToFloat(Form1.LabeledEdit8.Text);
      max_integ_error:=StrToFloat(Form1.LabeledEdit9.Text);

//      n:=200;


      for i:=1 to n do
        begin

          f[i]:=Ku * fPID(i, 0.0);
          Series1.AddXY(i, f[i]);

        end;


      diapazon:=Uust;

      Uk:=0.0;
      Uk1:=0.0;

      ek:=0.0;
      ek1:=0.0;
      ek2:=0.0;

      integral:=0.0;

      if (CheckBox1.State = cbChecked) then begin
      for i:=1 to n do
        begin

          ek:=Uust - Uk;

          f1[i]:=ek;
          Series4.AddXY(i, f1[i]);

//          integral:=integral + ek;

          if ((min_integ_error < ek) and (ek < max_integ_error))
            then integral:=integral + ek
            else integral:=0.0;

          Uk:=Kp * ek + Ki * integral * T0 + (Kd * (ek - 2.0 * ek1 + ek2)) / T0;
//          Uk:=Kp * ek + Ki * integral + (Kd * (ek - 2.0 * ek1 + ek2));

          if (-1.0 * diapazon > Uk) then Uk:=-1.0 * diapazon;
          if (Uk > diapazon) then Uk:=diapazon;

          f2[i]:=Uk;
          Series2.AddXY(i, f2[i]);

          f[i]:=Ku * fPID(i, Uk);
          Series3.AddXY(i, f[i]);

          ek2:=ek1;
          ek1:=ek;

          Uk:=f[i];


{ http://kazus.ru/forums/showthread.php?t=11558 }
{ http://kazus.ru/forums/showthread.php?t=11558&page=4 }

        end;
      end
      else begin
        Series2.Clear;
        Series3.Clear;
        Series4.Clear;
      end;


      Uk:=0.0;
      Uk1:=0.0;

      ek:=0.0;
      ek1:=0.0;
      ek2:=0.0;

      integral:=0.0;

      if (CheckBox2.State = cbChecked) then begin
      for i:=1 to n do
        begin

          ek:=Uust - Uk;

          f1[i]:=ek;
          Series7.AddXY(i, f1[i]);

          integral:=ek;

          if ((min_integ_error < integral) and (integral < max_integ_error))
            then integral:=integral
            else integral:=0.0;

          Uk:=Uk1 + Kp * (ek - ek1) + Kp * Ki * integral + Kp * Kd * (ek - 2.0 * ek1 + ek2);

          if ((-1.0 * diapazon) > Uk) then Uk:=-1.0 * diapazon;
          if (Uk > diapazon) then Uk:=diapazon;

          f2[i]:=Uk;
          Series5.AddXY(i, f2[i]);

          f[i]:=Ku * fPID(i, Uk);
          Series6.AddXY(i, f[i]);

          ek2:=ek1;
          ek1:=ek;

          Uk:=f[i];
          Uk1:=Uk;

{ http://ru.wikipedia.org/wiki/%D0%9F%D0%98%D0%94-%D1%80%D0%B5%D0%B3%D1%83%D0%BB%D1%8F%D1%82%D0%BE%D1%80 }

        end;
      end
      else begin
        Series5.Clear;
        Series6.Clear;
        Series7.Clear;
      end;


      { Ñêîðîñòíîé ìåòîä }
      q0:=Kp * (1.0 + Kd);
      q1:=Kp * (-1.0 - 2.0 * Kd + Ki);
      q2:=Kp * Kd;

      Uk:=0.0;
      Uk1:=0.0;

      ek:=0.0;
      ek1:=0.0;
      ek2:=0.0;

      if (CheckBox3.State = cbChecked) then begin
      for i:=1 to n do
        begin

          ek:=Uust - Uk;

          f1[i]:=ek;
          Series10.AddXY(i, f1[i]);

          Uk:=Uk1 + q0 * ek + q1 * ek1 + q2 * ek2;

          if (-1.0 * diapazon > Uk) then Uk:=-1.0 * diapazon;
          if (Uk > diapazon) then Uk:=diapazon;

          f2[i]:=Uk;
          Series8.AddXY(i, f2[i]);

          f[i]:=Ku * fPID(i, Uk);
          Series9.AddXY(i, f[i]);

          ek2:=ek1;
          ek1:=ek;

          Uk:=f[i];
          Uk1:=Uk;

{ http://www.rlda.ru/PID_Control_Tutor.htm }

        end;
      end
      else begin
        Series8.Clear;
        Series9.Clear;
        Series10.Clear;
      end;


      { Ìåòîä òðàïåöèè }
      q0:=Kp * (1.0 + 0.5 * Ki + Kd);
      q1:=Kp * (-1.0 - 2.0 * Kd + 0.5 * Ki);
      q2:=Kp * Kd;

      Uk:=0.0;
      Uk1:=0.0;

      ek:=0.0;
      ek1:=0.0;
      ek2:=0.0;

      if (CheckBox4.State = cbChecked) then begin
      for i:=1 to n do
        begin

          ek:=Uust - Uk;

          f1[i]:=ek;
          Series13.AddXY(i, f1[i]);

          Uk:=Uk1 + q0 * ek + q1 * ek1 + q2 * ek2;

          if (-1.0 * diapazon > Uk) then Uk:=-1.0 * diapazon;
          if (Uk > diapazon) then Uk:=diapazon;

          f2[i]:=Uk;
          Series11.AddXY(i, f2[i]);

          f[i]:=Ku * fPID(i, Uk);
          Series12.AddXY(i, f[i]);

          ek2:=ek1;
          ek1:=ek;

          Uk:=f[i];
          Uk1:=Uk;

{ http://www.rlda.ru/PID_Control_Tutor.htm }

        end;
      end
      else begin
        Series11.Clear;
        Series12.Clear;
        Series13.Clear;
      end;


    end;


Сообщение отредактировал Jenyok2 - Oct 9 2011, 16:43
Go to the top of the page
 
+Quote Post

2 страниц V  < 1 2
Reply to this topicStart new topic
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 


RSS Текстовая версия Сейчас: 19th July 2025 - 00:06
Рейтинг@Mail.ru


Страница сгенерированна за 0.01417 секунд с 7
ELECTRONIX ©2004-2016