Simple PID code
One method of handling the integration and bumpless transfer to automatic mode is an algorithm that calculates the change in output from one pass to the next using the derivative of the PID algorithm, or:
dOut/dt = gain x (dError/dt + ResetRate x Error + Derivative x d2Error/dt2)
derivative of output = gain x (derivative of error + reset rate x error + second derivative of error)
This program is run every second. If the control loop is in manual, the output is adjusted by the operator through the operator interface software. If the control loop is in Automatic, the output is computed by the PID algorithm.
Each pass the output is changed by adding the change in output to the previous pass output. That change is the sum of:
- the change in error (Err - ErrLast)
- the error multiplied by the reset rate, and
- the second derivative of the error (Err-2 * ErrLast + ErrLastLast) times the derivative.
This simple version of the PID controller work well in most cases, and can be tuned by the standard PID tuning methods (some of which are discussed later). It has Parallel rather than Series reset and derivative, and derivative is applied to the error rather than the input only.
Variables:
Input - Process input
InputLast - Process input from last pass, used in deriv. calc.
Err - Error, Difference between input and set point
ErrLast - Error from last pass
ErrLastLast - Error from next to last pass
OutP - Output of PID algorithm
Mode - value is ‘AUTO’ if loop is in automatic
Action - value is ‘DIRECT’ if loop is direct acting
Derivative - Derivative value in minutes
Reset - reset rate in repeats per minute
SetP - Set Point, set by operator
Mode - String, set to "AUTO" or "Manual" by operator
Action - String, set to "REVERSE" or "DIRECT" during configuration
The PID emulation code:
Code: Select all
IF Mode = ‘AUTO’ THEN
Err = SetP - Input /* Error based on reverse action */
IF Action = ‘DIRECT’ THEN
Err = 0 – Err /* Change sign of error for direct action */
ENDIF
/* Calculate the change in output using the derivative of the PID algorithm, then add to the previous output. */
OutP=OutP+Gain*(Err-ErrLast+Reset*Err+Deriv*(Err-ErrLast*2+ErrLastLast))
ErrLastLast = ErrLast
ErrLast = Err
ELSE
/* While loop in manual, stay ready for bumpless switch to Auto */
InputLast = Input
ErrLastLast = Err
ErrLast = Err
ENDIF
IF OutP > 100 THEN OutP = 100 /* Limit output to between */
IF OutP < 0 THEN OutP = 0 /* 0 and 100 percent */
The only serious problem with this form of the algorithm occurs when the output has reached an upper or lower limit. When it does, a change in the measurement can unexpectedly pull the output away from the limit.
Improved PID code
The method of implementing automatic reset described in using a positive feedback loop was first used with pneumatic analogue controllers. It can easily be implemented digitally.
There are several advantages of this algorithm implementation. Most important, it eliminates the problems that cause the output to pull away from a limit inappropriately. It also allows the use of external feedback when required.
Variables:
Input - Process input
InputD - Process input plus derivative
InputLast - Process input from last pass, used in deriv. calc.
Err - Error, Difference between input and set point
SetP - Set point
OutPutTemp - Temporary value of output
OutP - Output of PID algorithm
Feedback - Result of lag in positive feedback loop.
Mode - value is ‘AUTO’ if loop is in automatic
Action - value is ‘DIRECT’ if loop is direct acting
The PID emulation code:
Code: Select all
IF Mode = ‘AUTO’ THEN
InputD = Input + (Input - InputLast) * Derivative * 60 /* derivative */
InputLast = Input
Err = SetP - InputD /* Error based on reverse action */
IF Action = ‘DIRECT’ THEN Err = 0 – Err /* Change sign if direct */
/* Calculate the gain time the error and add the feedback */
OutPutTemp = Err * Gain + Feedback
/* Limit output to between */
IF OutPutTemp > 100 THEN OutPutTemp =100
/* 0 and 100 percent */
IF OutPutTemp < 0 THEN OutPutTemp = 0
/* The final output of the controller */
OutP = OutPutTemp
Feedback = Feedback + (OutP - Feedback) * ResetRate / 60
ELSE
InputLast=Input While loop in manual, stay ready for bumpless switch to Auto.
Feedback=OutP
ENDIF