From Friday, April 19th (11:00 PM CDT) through Saturday, April 20th (2:00 PM CDT), 2024, ni.com will undergo system upgrades that may result in temporary service interruption.

We appreciate your patience as we improve our online experience.

LabVIEW

cancel
Showing results for 
Search instead for 
Did you mean: 

Is there any good reason why the Absolute Value Function doesn't accept U32 values?

Hi X.,

 

using subtraction on U32 values gives you the "distance" between those U32 values.

When you convert the U32 result to an I32 value (with "To I32") you get the correct answer (-10 in your example)!

 

Applying simple math (add & sub) on unsigned integer values is a very basic operation in each microprocessor and well defined.

The only problem with LabVIEWs ADD and SUB function is: you don't get a Carry/Borrow flag as you would in a µP…

 

On your original question: What's the point of applying Abs() on unsigned values?

(But I have to agree with Christian as the current behaviour breaks LabVIEW code when you apply Abs() on clusters.)

Best regards,
GerdW


using LV2016/2019/2021 on Win10/11+cRIO, TestStand2016/2019
0 Kudos
Message 11 of 19
(2,388 Views)

I don't see the existing behaviour as a bug- I see it as the sane choice. You can always write your own 'absolute value' function that takes anything you like- unsigned integers, strings, refnums etc.

0 Kudos
Message 12 of 19
(2,367 Views)

@ToeCutter wrote:

You can always write your own 'absolute value' function that takes anything you like- unsigned integers, strings, refnums etc.


You cannot easily write such a function that works properly on mixed numeric clusters. remember that "abs" even works for complex and gives you the vector lenght.

 

Create me a polymorphic function that accepts the following clusters (and anything similar!) with no limit on the number, type and order of the cluster elements and will perform the abs function.

 

Cluster 1: [DBL : CDB : I32 : I32 : U8]

Cluster 2: [I16 : I16 : I32 : U64 : DBL : DBL : CDB]

etc....

 

Hint: You would need an infinite amount of very complicated polymorphic subVIs (e.g. containing an IPE(unbundle/bundle) absoluting all elements that are allowed and skiping the unsigned integers. 

 

A broken wire is simply not aceptable behavior. There is no doubt what the output should be for an unsigned input: return the input value unchanged (i.e. the same behavior it already does for 50% of all possible I32 values ;)).

 

There are plenty of other functions that don't do anything useful, but still don't break the VI (e.g. build array of height=1 set to concatenate, a compound node of height=1, etc.).

 

(The "negate function" also does not accept unsigned integers, but that makes quite a bit more sense. Even here it could accept the input and do an implicit conversion to DBL to avoid the broken wire, i.e. same as it currently does with 1/x, instead of breaking the entire VI. The coercion dot would be sufficient to alert the user that something is not quite right)

 

My opinion: Don't break the wire and thus the entire VI. In the worst case, create a warning.

 

0 Kudos
Message 13 of 19
(2,353 Views)

@X. wrote:

@aputman wrote:

Because the values are not evaluated until runtime.  The compiler doesn't know or care what values are in your constant, as long as the datatype is correct.


Right. So it is perfectly fine to obtain the value of 0 - X at runtime, where 0 and X are both U32:

 

0minusx.png

 

which gives, for instance:

 

Screen Shot 2016-01-07 at 15.21.25.png

 

 


This is a perfectly valid calculation in 2's complement arithmetic, implemented in most CPUs the same and standardized by IEEE. And LabVIEW tries to maintain compatibility with IEEE for floating points and integers in every possible way.

 

The absolute value of an unsigned integer is an entirely different case. By definition its a NOP. Yes NI could have decided to allow it and just do a "do nothing" function call there, but all those primitives do add some execution time and since the datatype is defined at compile time it was decided that that should rather cause a compilation error than add unneccessary execution time to the runtime code.

 

It's definitely not a bug! And for the scalar unsigned integer a convinience and the cluster containing unsigned integers an inconvinience. So +1 - 1 = neutral. I for myself have real problems to tackle instead of getting upset about such things Smiley Very Happy

Rolf Kalbermatter
My Blog
0 Kudos
Message 14 of 19
(2,326 Views)

@rolfk wrote:
 but all those primitives do add some execution time and since the datatype is defined at compile time it was decided that that should rather cause a compilation error than add unneccessary execution time to the runtime code.

No, the compiler would be good enough to do the proper transform and just replace it with a wire behind the scenes. There will be no execution overhead. No need to break the VI. 😉

 

 

0 Kudos
Message 15 of 19
(2,290 Views)

Tada!

 

absolutely.png

0 Kudos
Message 16 of 19
(2,149 Views)

Similarly:

 

absolutely2.png

 

QED: There is no good reason to prevent the abs Function to take a U32 and output the same U32...

 

And BTW, yes, this suggestion was a joke.

0 Kudos
Message 17 of 19
(2,133 Views)

Following up on this discussion now that LabVIEW 2017 is released and we have now the wonderful feature of Malleable VIs exposed to the user. It is even more inconvenient to break a VI if an unsigned integer is wired to the absolute value function. This is a real road block that now requires clumsy workarounds!

 

A universal algorithm that include an absolute value function should not be off-limits to unsigned integers, ever!

 

I'll try to write up an idea if it does not exist already! (... or maybe there is a CAR for this?)

 

 

 

 

0 Kudos
Message 18 of 19
(1,588 Views)

@X. wrote:

More of the same or similar arbitrariness and non-standard behavior:

 

Screen Shot 2016-01-07 at 14.44.52.png

 

Notice that it is perfectly fine to substract a U32 from another one and request a U32 result, but negating a U32 (which WILL return a I32 by construction of the function) is forbidden with the same justification as above.

Why can ask for the sign of U32 when this should be flagged as anathema by the NI guardians of positiveness?


It's not really as arbitrary as you think it to be.Subtraction of unsigned integers is fully defined with two complements overflow arithmetic. The result is still an unsigned value. The Negate would have to change the datatype to always be signed and that is something LabVIEW integer nodes usually try to avoid. LabVIEW does automatic promotion to double floating point when it makes sense but leaves integers usually alone. I think this could be probably relaxed nowadays for these things you mention but there was most likely a good reason to restrict it like that.

 

It'probably also a remainder of C influence. I just recently edited some C code for image filtering, which was using int everywhere to use uint32_t instead because the image can't really have negative dimensions and offsets and run into the problem that I got lots of compiler warnings that the unary negative operator could not be applied to unsigned integers and the result would be still unsigned (probably the two complements of the original value). Doing a 0 - i everywhere fixed that.

 

You could of course question the C standard, but there have been many very smart people debating about all these kind of things ad nauseam and there is always a reason for those decisions.

Rolf Kalbermatter
My Blog
0 Kudos
Message 19 of 19
(1,572 Views)