RSLogix5000. How to write Expression to find Greater Than other values

Stepping back, we could also consider what the meaning of the most-sampled wind direction over a minute of samples. What if, over the course of one minute, the wind blows for 29s out of the north at 10kt, and for 31s out of the south at 1kt. Wouldn't North be a better choice for that minute?

Because, as Alan Watts wrote (cf.
61KNAL-ZlWL._SL350_.jpg
), gusts tend to veer counter-clockwise in OP's half of the planet.

(Is that not a gorgeous boat on the cover of that book? That class was the first modern planing dinghy; my brother, my wife and I raced that class decades ago, and we just re-acquired a couple for retirement!)
 
It will look summat like this:
I think i can handle this code. I will give it a try but will likely not produce a result for another few days because i need to do my day job. Which does not involve any actual coding.

I do not really understand yet how this code will produce the outcome i am looking for. But i think i will better understand it once i put it together and run it a few times. It will be a good learning experience either way.

We have some rain days coming up (cannot work in the rain) so i think i will dedicate these days working on this problem.
 
Because, as Alan Watts wrote (cf.), gusts tend to veer counter-clockwise in OP's half of the planet.

(Is that not a gorgeous boat on the cover of that book? That class was the first modern planing dinghy; my brother, my wife and I raced that class decades ago, and we just re-acquired a couple for retirement!)
Alan Watts is the best.

https://www.youtube.com/watch?v=S6O34-Sk6to&ab_channel=T&H-Inspiration&Motivation

The video footage used here are obviously bias towards the USA, but if you ignore the video footage, the philosophy and the background music composition is inspirational.
 
I do not really understand yet how this code will produce the outcome i am looking for.
See the images below.

The first image counts how many time the wind comes from a given direction; I only used the cardinal compass points (North, East, South West), but of course it could be expanded to additional inter-cardinal points (NNE, NE, ...). The direction indices are 1, 2, 3, and 4 for directions North, East, South, and West, respectively.

The important thing to note is that the cts (Array DINT[1..4]) contains the counts for each direction (cts[1] has the North counts; cts[2], cts[3], and cts[4] for East, South, and West, respectively.
max_count_00.png

CCW was what I had to hand when I did this, I assume it is similar enough to RSLogix to be clear what I am doing. The [sample_trigger] is equivalent to the /DN bit of a one-repeating one-second RSLogix timer.

N.B. [Switch 1] is 1 when the wind is coming from North, [Switch 2] is 1 when the wind is coming from the East, etc.
The second image shows how to determine the direction (N/E/W/S), as a directional index (1/2/3/4), that has the greatest number of counts. I hope it is straightforward enough to understand. To answer the original question from Post #1, we don't need to compare the North count against all 16 counts from NNE, NE, ENE, E, ..., to determine if North is the wind direction with the most counts, then compare the NNE count against N, NE, ENE, ..., etc. It is enough to compare N counts against NNE counts, and save the wind direction of the greater of the two, then compare NE counts against that previous result and update the result, then ENE, etc. Since at any point in that process, the count of the intermediate result (wind direction) cannot be less than any of the previously-tested counts, if the next count tested is greater than the intermediate result, then that next count must be greatest.

That is called the invariant condition of the algorithm: the count of the intermediate direction result is not less than any of the previous directions tested. To initialize the algorithm, we assign 1 (North) as the intermediate result, which meets the invariant condition because no other direction has been tested. Then on each pass of the algorithm, we test a new index, and adjust the intermediate result as needed to maintain the invariant condition.
max_count_01.png
My point is that the code from my other example does exactly this, but in a loop, so there needs to be only one rung branch that does the compare and move sixteen times with a different value of the direction index TEST_INDEX each time (instead of 1, 2, 3, ..._, and the other branches increment the direction index to be tested and repeat (loop) until all direction indices have been tested:
Untitled.png
 
Last edited:
Stepping back, we could also consider what the meaning of the most-sampled wind direction over a minute of samples. What if, over the course of one minute, the wind blows for 29s out of the north at 10kt, and for 31s out of the south at 1kt. Wouldn't North be a better choice for that minute?


E.g. the directional wind barbs in the wind speed part of the plot at this link use a speed-weighted directional average for each plotted barb. It's not complex, and RSLogix 5000 does have cosine, sine, and arc tangent instructions.
I currently using a FIFO then average to display wind speed. I have future plans to expand this method of measurement also to show max and min wind speads over time. But this is for another time.

The reason why i am not using the wind speed as a 'weight' for determining wind direction is mainly due to gusts. Certain directions of wind gust quite strong, while other directions are more steady and some lighter.

This being the case, i believe a wind speed weighted measurement would scew the wind direction results.
 
See the images below.

The first image counts how many time the wind comes from a given direction; I only used the cardinal compass points (North, East, South West), but of course it could be expanded to additional inter-cardinal points (NNE, NE, ...). The direction indices are 1, 2, 3, and 4 for directions North, East, South, and West, respectively.

The important thing to note is that the cts (Array DINT[1..4]) contains the counts for each direction (cts[1] has the North counts; cts[2], cts[3], and cts[4] for East, South, and West, respectively.
View attachment 62545

CCW was what I had to hand when I did this, I assume it is similar enough to RSLogix to be clear what I am doing. The [sample_trigger] is equivalent to the /DN bit of a one-repeating one-second RSLogix timer.

N.B. [Switch 1] is 1 when the wind is coming from North, [Switch 2] is 1 when the wind is coming from the East, etc.
The second image shows how to determine the direction (N/E/W/S), as a directional index (1/2/3/4), that has the greatest number of counts. I hope it is straightforward enough to understand. To answer the original question from Post #1, we don't need to compare the North count against all 16 counts from NNE, NE, ENE, E, ..., to determine if North is the wind direction with the most counts, then compare the NNE count against N, NE, ENE, ..., etc. It is enough to compare N counts against NNE counts, and save the wind direction of the greater of the two, then compare NE counts against that previous result and update the result, then ENE, etc. Since at any point in that process, the count of the intermediate result (wind direction) cannot be less than any of the previously-tested counts, if the next count tested is greater than the intermediate result, then that next count must be greatest.

That is called the invariant condition of the algorithm: the count of the intermediate direction result is not less than any of the previous directions tested. To initialize the algorithm, we assign 1 (North) as the intermediate result, which meets the invariant condition because no other direction has been tested. Then on each pass of the algorithm, we test a new index, and adjust the intermediate result as needed to maintain the invariant condition.My point is that the code from my other example does exactly this, but in a loop, so there needs to be only one rung branch that does the compare and move sixteen times with a different value of the direction index TEST_INDEX each time (instead of 1, 2, 3, ..._, and the other branches increment the direction index to be tested and repeat (loop) until all direction indices have been tested:


Woke up uber early this morning and figured i should give this code a try.

I have attached two pictures.

The first picture shows some of my counters and how they are structured. They are only being tested at the moment, so the counts are really high. I only expect a count of 1 for the final product. So please ignore the count values.

The second image shows me trying to create an array using Counter.....ACC as array elements.

So baby steps. How do i create an array using Counter...ACC as array elements?

Wind Counters.png Wind Direction array.png
 
This being the case, i believe a wind speed weighted measurement would skew the wind direction results.


I can see that.

It depends what you want:

  • The most-likely direction a viewer would have seen if they glanced once and briefly at the sensor at some point during the minute of samples, or
  • The mean motion of a balloon (or other zero-mass volume) from the beginning of the minute to the end.
Neither is perfect; the implementation of the latter does not account for the balloon moving away from the sensor into a different flow field by assuming the flow field is uniform.
 
So baby steps. How do i create an array using Counter...ACC as array elements?

You can't.

You can (I think; consider item (iv) below ;)) create an array of COUNTER structures (cf. here), and each one has a .ACC element e.g. so counters[0].ACC, counters[1].ACC, ..., counters[15].ACC.

[+]-counters | COUNTER[16] | ...

 
Last edited:
P.S. so that CTU rung becomes

XIC Timer_Flashing_2b.DN ONS ons[5].28
BST XIC N CTU counters[0] 0 0
NXB XIC NNE CTU counters[1] 0 0
...
BND




If you also put the N, NNE, ..., booleans in an array, the whole megillah could also be coded in a loop, so you would not need to maintain (or edit or scroll through) sixteen branches. That said, for only 16 instances most people would keep the 16 branches and eschew the loop, as it is easier to understand and diagnose later, and any development savings are lost in the operational duration of the project.



Sidebar: unless Timer_Flashing_2b is on for several scans in a row, do you need the ONS?

P.P.S. why would the count stop at 1?
 
What i have gathered so far is that the key to creating an array of counters is i need to somehow use '[ ]' square brackets to make some king of magic happen.


You already have at least one array: the DINT[20] Wind_Average_Array FIFO for calculating wind speed.

And yes, things like arrays (and loops) definitely take the gun out of the holster, switch off the safety, and point it squarely at your foot.
 
You can't.

You can (I think; consider item (iv) below ;)) create an array of COUNTER structures (cf. here), and each one has a .ACC element e.g. so counters[0].ACC, counters[1].ACC, ..., counters[15].ACC.

[+]-counters | COUNTER[16] | ...

Currently reading up on how to do this.

From Thread: http://www.plctalk.net/qanda/showthread.php?t=112766

Quote:
__________________________________________________ ___________

You can do it on ladder as well.

Array[100]

Index

Array[index]

If index end up higher than your array size it will trip a recoverable fault.

__________________________________________________ _________

Also watched a youtube video on the subject.

What i have gathered so far is that the key to creating an array of counters is i need to somehow use '[ ]' square brackets to make some king of magic happen.

...

Will keep pushing through for a little longer then i will need to head out to work.
 
What i have gathered so far is that the key to creating an array of counters is i need to somehow use '[ ]' square brackets to make some king of magic happen.


You already have at least one array: the DINT[20] Wind_Average_Array FIFO for calculating wind speed.

And yes, things like arrays (and loops) definitely take the gun out of the holster, turn of the safety, and point it squarely at your foot.
 
P.S. so that CTU rung becomes

XIC Timer_Flashing_2b.DN ONS ons[5].28
BST XIC N CTU counters[0] 0 0
NXB XIC NNE CTU counters[1] 0 0
...
BND




If you also put the N, NNE, ..., booleans in an array, the whole megillah could also be coded in a loop, so you would not need to maintain (or edit or scroll through) sixteen branches. That said, for only 16 instances most people would keep the 16 branches and eschew the loop, as it is easier to understand and diagnose later, and any development savings are lost in the operational duration of the project.



Sidebar: unless Timer_Flashing_2b is on for several scans in a row, do you need the ONS?

P.P.S. why would the count stop at 1?
I need to get ready for work now, i will take a screen shot of your suggestion and try to process it in my mind during the day and see if i have a revolutionary flash of understanding. Ideally before lunch.

Quick answer to some of your questions:

Why a 2 second timer? This is the sampling time. Every 2 seconds, a "sample" of wind direction is recorded and counts up. If the direction is say: NNE, then NNE counts up 1.

Why do i only expect a count of 1. This is an error on my part. Please ignore. Redundant idea. My original idea was to measure which wind direction was dominant at any 2 second period, then reset all the counters. Which is why they would only count to 1.

But i have since developed the design to use a FIFO of counters, (not very well explained here as i need to rush off to work). If i am able to get the counter...ACC inside a FIFO, or something similar, then i can create a moving average of the wind direction. So instead of saying

"over the past 1 minute, wind direction was predominantly NNE" , RESET, then the "next minute the wind is predominatly NE".

A moving average will say

"in the last 60 seconds that just went by before this moment, the wind direction was:.... (eg. NNE)".

The end goal is to be able to see the average wind direction, using a moving average, over the last 10 min.
 

Similar Topics

I am replacing a PLC5 with a 1756-L73 and i am trying to reuse a 1771-DB Basic Module. I am leaving the PLC5 in the chassis setup as RIO adapter...
Replies
7
Views
5,128
Need good example/sample of aoi RSLogix5000 code to read&write through RS232 port on Need good example/sample of aoi RSLogix5000 code to...
Replies
0
Views
1,844
Hey All, As the title states, how do I write a MinorFault generated by an instruction, for example a negative .PRE value was entered for a timer...
Replies
12
Views
3,010
Is it possible to partially restrict the types of communications allowed through a ControlLogix communications module? Ideally I'd like something...
Replies
7
Views
3,333
Hello everyone, Wondering if anybody can help me with this: I have a CompactLogix processor running a little robot cell. Every 200 cycles...
Replies
8
Views
136
Back
Top Bottom