go_away

Recent Posts

Pages: 1 ... 8 9 10
91
Software / Re: My first little PID: please comment
« Last post by obiwanjacobi on May 14, 2013, 12:38:18 PM »
I've never switched controller types in mid stream. It isn't uncommon to modify the gains as a function of operating conditions (referred to as gain scheduling) but switching between PI and PD or whatever would be unusual.

This gives me an idea. If you put a gain of zero in for a specific term you basically shut it of. I could optimize the code to keep performing the maintenance on the variables but not calculate anything when gain equals zero. That would simplify the public interface of this class considerably.


Code: [Select]
/*
BaseT is used as a base class and implements:
T getFeedback()
unsigned int getDeltaTime()
T getSmallestAcceptableError()

T is the data type that hold the values. Either float or double.

Algorithm:
Error = SetPoint - Feedback
P = Error * gainP
I = Sum(previous-I's) + ((Error * deltaTime) * gainI)
D = ((Error - previous-Error) / deltaTime) * gainD

PI = P + I
PD = P + D
PID = P + I + D
*/
template<class BaseT, typename T>
class PID : public BaseT
{
public:
// pass a gain of zero to bypass a specific term.
T Process(T setPoint, T gainP, T gainI, T gainD)
{
T input = BaseT::getFeedback();
T error = CalcError(setPoint, input);
unsigned int deltaTime = BaseT::getDeltaTime();

return CalcP(error, gainP) + CalcI(error, deltaTime, gainI) + CalcD(error, deltaTime, gainD);
}

private:
T _integralAcc;
T _lastError;

inline T CalcError(T setPoint, T input)
{
T error = setPoint - input;

if ((error < BaseT::getSmallestAcceptableError() && error > 0) ||
(error > -BaseT::getSmallestAcceptableError() && error < 0))
{
error = 0;
                        _integralAcc = 0; // Good idea??
}

return error;
}

inline T CalcP(T error, T gain)
{
if (gain == 0) return 0;

return error * gain;
}

inline T CalcI(T error, unsigned int deltaTime, T gain)
{
if (gain != 0)
{
_integralAcc += (error * deltaTime) * gain;
}

return _integralAcc;
}

inline T CalcD(T error, unsigned int deltaTime, T gain)
{
T value = 0;

if (gain != 0)
{
value = ((error - _lastError) / deltaTime) * gain;
}

_lastError = error;

return value;
}
};
92
Electronics / Re: Question as to where to start!
« Last post by Adeptbot on May 14, 2013, 12:24:42 PM »
Lots og great info! I am planning on buying the micro controller for this site. I would also like to know (there is no info on the tutorials) where is a good place to get battery operated cameras with a streaming capability? Also any place that sells wheel chair used parts?

Thanks,
93
Mechanics and Construction / Re: Motor torque selection
« Last post by mado on May 14, 2013, 12:18:09 PM »
if i used two motors of 2 oz of torque , will it be enough to move the load ?
i need to know how to get enough torque .
how to calculate the required torque?
94
Software / Re: My first little PID: please comment
« Last post by obiwanjacobi on May 14, 2013, 11:16:56 AM »
Another option to deal with constantly accumulating I error is to use a leaky integrator for the I term, just like you do for the D term. Except for the D term, it's a single-pole low-pass filter; for the I term it's a single-term high-pass filter.

I understand what low-pass and high-pass mean (from audio) but I have no idea how to build code for it...


Another thing I noticed is that I see people mix up the way the delta error is calculated. Some do
Code: [Select]
previousError - newErrorOthers do
Code: [Select]
newError - previousError
Is this something that you will trim/tune out of the controller (using gains) or is one correct and the other one not?
95
Software / Re: My first little PID: please comment
« Last post by jwatte on May 14, 2013, 10:45:26 AM »
Another option to deal with constantly accumulating I error is to use a leaky integrator for the I term, just like you do for the D term. Except for the D term, it's a single-pole low-pass filter; for the I term it's a single-term high-pass filter.

Also, yes, with an I term you will almost always get a little bit of overshoot. The point of the D term is to limit the slew rate of the response, so that the overshoot can be dampened. With a well tuned system, your I/D control terms will end up being "critically damped" which is a nice place to start from by way of trading responsiveness and damping.
96
Mechanics and Construction / Re: Motor torque selection
« Last post by jwatte on May 14, 2013, 10:41:04 AM »
65 kg is a lot of payload. Accelerating at 1.5 ft/s/s is a fair bit of thrust (evel though it's "only" 1/20th of a g, if I can do unit conversions in my head.) You will need strong motors to achieve that level of acceleration.
Also note that typical motors run in the thousands of rpm, and don't have a lot of torque, but use gear boxes to trade rpm for torque. Thus, a 12V motor with 1,000 kV constant and 2 ozin of torque would run at 12,000 rpm at 12 V; use a 500:1 gearbox and it gets to 24 rpm and has 1,000 ozin of torque! (That motor would be too small for your design case, but that's a pretty small RC car motor I described...)
97
Misc / Coursera.com Control of Mobile Robots
« Last post by obiwanjacobi on May 14, 2013, 08:54:22 AM »
Coursera.com has a free course called "Control of Mobile Robots".
https://www.coursera.org/course/conrob

The course itself is passed but if you enroll, you can still access the video lectures etc.

Hope it helps.
98
Software / Re: My first little PID: please comment
« Last post by jkerns on May 14, 2013, 08:41:56 AM »
 
Yes, I wondered about that (about I).

It keeps building up and up and you would have to undo all that. To my naive mind that would cause overshoot and oscillation.

So if the I-term reaches the max value it just stops accumulating? Or when the combined output (return value from my methods) reaches max value? I would need some value range management in my class anyway, especially when mulitple P/I/D Terms are added together...

Stop the integrator when the combined output reaches it's limit.


Quote
Thinking on the I-term some more, I would even say that if your error is 0 (or within the acceptable error-band) I would simply stop using the I-term altogether and perhaps reset it (to what value I don't know - some % of its current value?) for when it is used later on (when we travel outside the error band) it would otherwise make the system 'jerk'.

Leave it running. The point of using the I is pretty much to drive the error to zero.  Turning it off or resetting it will just introduce some error to the sytem.

Quote
PS: Had already found your YT channel and I have no trouble sleeping ;-)  Thanx.
;D
99
Software / Re: My first little PID: please comment
« Last post by obiwanjacobi on May 14, 2013, 08:21:21 AM »
Yes, I wondered about that (about I).

It keeps building up and up and you would have to undo all that. To my naive mind that would cause overshoot and oscillation.

So if the I-term reaches the max value it just stops accumulating? Or when the combined output (return value from my methods) reaches max value? I would need some value range management in my class anyway, especially when mulitple P/I/D Terms are added together...

Thinking on the I-term some more, I would even say that if your error is 0 (or within the acceptable error-band) I would simply stop using the I-term altogether and perhaps reset it (to what value I don't know - some % of its current value?) for when it is used later on (when we travel outside the error band) it would otherwise make the system 'jerk'.

Does that make sense?

PS: Had already found your YT channel and I have no trouble sleeping ;-)  Thanx.
100
Software / Re: My first little PID: please comment
« Last post by jkerns on May 14, 2013, 07:47:14 AM »
Thank you. It's all about (tweaking) constants, I see  :P

In
filtered_error = (1 - filter_constant)*filtered_error + filter_constant*error


Is the bold 'filtered_error' a previous filtered_error value or...?


Yes. Your software is running in a loop so the variable "filtered_error" has a value from last time and now you use the old value in the calculation and it ends up in the new value. Much like using ++i or similar in C.

Quote
Also: is it likely you would dynamically (at runtime) switch using P, I or D terms for a single controller process? I mean do I need to take into account that all methods update the delta-time, I-accumulator and last-error variables in order to allow mixed calling of the P, PI, PD and PID methods?


I've never switched controller types in mid stream. It isn't uncommon to modify the gains as a function of operating conditions (referred to as gain scheduling) but switching between PI and PD or whatever would be unusual.

OH! I forgot to look! Do you have anti-windup on the I term? You need that. Really.  If the output of your controller is at the limit of the physical variable that you are sending to the actuator (e.g. 100% duty cycle)
you need to freeze the integrator so it doesn't keep integrating to some unobtainable value that has to be un-integraged some time later on - that is very destabilizing.  Typically you would compare the output of the controller with the actual limits of whatever your physical output is and either not call the integrator sub-function or just substitute zero for the error in the input to the integrator. I guess you could consider that a dynamic switch but that is not a common terminology.

If you are having trouble sleeping, I drone on and on for about an hour on PID control here... http://www.youtube.com/playlist?list=PL3ea3YrO-K5gxpOrrgKytFBvIzBv_WsXs
Pages: 1 ... 8 9 10

Get Your Ad Here