Exemple de routine de calcul CPID
La méthode PID correspond à un PID classique, avec filtre éventuel sur le terme dérivé, antiwindup et bande morte. Il est programmé de la manière suivante :
SUBROUTINE CPID(Reg) USE SIRENE_parametres, ONLY : LONG USE TEMPS , ONLY : T USE D_REGULATION, ONLY : Regulateur_t IMPLICIT NONE TYPE(Regulateur_t), INTENT(INOUT) :: Reg REAL(KIND=LONG), POINTER :: KP,N,TI,TD,AWU,EOLD,SE,DE REAL(KIND=LONG) :: E,STI,A1,A2,U2 LOGICAL SATURE !< Détection de l'anti wind-up INTEGER :: iU !< Compteur pour les commandes U ! Pointeurs pour faciliter la lecture du code KP=>Reg%tPara(1) TI=>Reg%tPara(2) TD=>Reg%tPara(3) N=>Reg%tPara(4) AWU=>Reg%tPara(5) EOLD=>Reg%tPara(6) SE=>Reg%tPara(7) DE=>Reg%tPara(8) ! Calcul pour cette methode ! Nouvel ecart (e = y* - y) E=Reg%tY(1)%YTVal-Reg%tY(1)%VarY%V ! On gère une bande morte (POM 21/07/04) IF(ABS(E).LT.Reg%tY(IY)%DYMax) THEN E=0. ENDIF ! Terme integral (approximation de Tustin) IF(TI.NE.0.) THEN STI=KP*Reg%tU(1)%VarU%DT/TI*(EOLD+E)/2 ELSE STI=0. ENDIF ! On gère l'antiwindup en utilisant le code de blocage du filtre de la commande : !> 0 = Fonctionnement libre normal !> 1 = Caractéristique volontairement bloquée (Valeur calée par Umin>=Umax à la lecture du XML) !> 2 = Caractéristique bloquée par problème de régulation (Umin, Umax, surverse, hors-loi vanne mixte) !> 3 = FiltreU => Umin atteint !> 4 = FiltreU => Umax atteint !> 5 = FiltreU => DUmin atteint !> 6 = FiltreU => DUmav atteint SATURE=Reg%tU(1)%FiltreU%iFlagBloc>=3 .AND. Reg%tU(1)%FiltreU%iFlagBloc/=5 IF(AWU == 0. .OR. .NOT.SATURE) THEN SE=SE+STI ENDIF ! Terme derive IF(TD.NE.0.) THEN IF(N.EQ.0.) THEN ! Terme derive sans filtre (backward difference) ! Avec une consigne y* constante DE=KP/Reg%tU(1)%VarU%DT*TD*(E-EOLD) ELSE ! Terme derive avec filtre (backward difference) ! Avec une consigne y* constante A1=1/(1+N*Reg%tU(1)%VarU%DT/TD) A2=KP*N*A1 DE=A1*DE+A2*(E-EOLD) ENDIF ENDIF ! Calcul de la commande Reg%tU(1)%VarU%V=KP*E+SE+DE ! Ancien ecart EOLD=E ! Si plusieurs U (SIMO) on duplique la meme ouverture ! (interessant dans le cas de plusieurs vannes identiques en parallele, en mode V par exemple) DO iU=1, Reg%nbrU Reg%tU(iU)%VarU%V = Reg%tU(1)%VarU%V ENDDO END SUBROUTINE CPID
Si vous voulez un PID différent vous pouvez toujours copier cette routine dans un module USER et la modifier comme bon vous semble (dans ce cas faire aussi cela pour la routine LPID -> LUSER pour la lecture des paramètres)