ryangriggs
Lifetime Supporting Member
PLC: 1769-L35E
Firmware: 16.24
RSLogix 5000 Full Edition V16.06.00 (CPR 9)
I'm trying to fix someone else's FBD program that calculates motor runtimes. The program currently stops counting at 4096.0015 hours and won't go any higher. I can manually edit the value to 4097, which then counts up a couple clicks to 4097.0015 and stops again.
I'm sure it's a floating point accuracy limitation, which makes additional 1-second additions result in the same value after dividing by 3600.0. I'm not sure the best way around it while keeping the existing code. Maybe it would be best to rewrite it completely.
The simplest way I can think of would be a simple adder, storing the runtime as "Seconds", then calculating another tag for runtime hours, instead of trying to convert hours to seconds then back to hours each loop.
Here's the FBD, which is called from a scheduled task which copies the motor runtime into 'value', the running status bit into 'running' and the runtime reset bit into 'reset' once per second.
As I understand it, the steps are as follows, repeated every second:
1. Multiply the current runtime hrs by 3600.0 to convert horus to seconds.
2. If the motor is running, add 1 to the value. If not running, add 0.0 to the value.
3. Divide the result by 3600.0 to convert back to hours
4. If Reset is enabled, copy 0.0 to the source tag. If Reset is not enabled, copy the resulting hours value to the source tag.
5. Reset 'reset' tag to 0.
(Frankly, I'm not sure why they chose this convoluted way to do such a simple task, but whatever...)
Thanks for any input. Suggestions and recommendations welcome.
Firmware: 16.24
RSLogix 5000 Full Edition V16.06.00 (CPR 9)
I'm trying to fix someone else's FBD program that calculates motor runtimes. The program currently stops counting at 4096.0015 hours and won't go any higher. I can manually edit the value to 4097, which then counts up a couple clicks to 4097.0015 and stops again.
I'm sure it's a floating point accuracy limitation, which makes additional 1-second additions result in the same value after dividing by 3600.0. I'm not sure the best way around it while keeping the existing code. Maybe it would be best to rewrite it completely.
The simplest way I can think of would be a simple adder, storing the runtime as "Seconds", then calculating another tag for runtime hours, instead of trying to convert hours to seconds then back to hours each loop.
Here's the FBD, which is called from a scheduled task which copies the motor runtime into 'value', the running status bit into 'running' and the runtime reset bit into 'reset' once per second.
As I understand it, the steps are as follows, repeated every second:
1. Multiply the current runtime hrs by 3600.0 to convert horus to seconds.
2. If the motor is running, add 1 to the value. If not running, add 0.0 to the value.
3. Divide the result by 3600.0 to convert back to hours
4. If Reset is enabled, copy 0.0 to the source tag. If Reset is not enabled, copy the resulting hours value to the source tag.
5. Reset 'reset' tag to 0.
(Frankly, I'm not sure why they chose this convoluted way to do such a simple task, but whatever...)
Thanks for any input. Suggestions and recommendations welcome.