Jump to content

Question regarding operator precedence


Recommended Posts

Maybe I have a plank in front of my head right now, but why does (11 - 2^4) return 27 as a result ? (^ has a higher operator precedence than - ).

If you put 2^4 in parentheses, then of course it works (with + it works even without). With * and / the operator precedence also works without parentheses.

MsgBox(0, "Test : Operator Precedence", _
          "AutoIt Version : " & @AutoItVersion & @CRLF & @CRLF & _
          "(11 - 2^4)    = " & (11 - 2^4) & @CRLF & _
          "(11 - (2^4))  = " & (11 - (2^4)) & @CRLF & _
          @CRLF & _
          "(11 + 2^4)    = " & (11 + 2^4) & @CRLF & _
          "(11 + (2^4))  = " & (11 + (2^4)) & @CRLF & _
          @CRLF & _
          "(11 - 2*8)   = " & (11 - 2*8) & @CRLF & _
          "(11 - (2*8)) = " & (11 - (2*8)) & @CRLF & _
          @CRLF & _
          "(11 - 32/2)   = " & (11 - 32/2) & @CRLF & _
          "(11 - (32/2)) = " & (11 - (32/2)) & @CRLF)

(original question from the DE-Forum / tested with 3.3.15.6)

 

Musashi-C64.png

"In the beginning the Universe was created. This has made a lot of people very angry and been widely regarded as a bad move."

Link to comment
Share on other sites

  • Moderators

Musashi,

It looks as if AutoIt is treating the expected - operator as a unary minus. This recent thread went into the matter in some detail - and my advice remains the same: never rely on operator precedence and always uses parentheses.

M23

Public_Domain.png.2d871819fcb9957cf44f4514551a2935.png Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind

Open spoiler to see my UDFs:

Spoiler

ArrayMultiColSort ---- Sort arrays on multiple columns
ChooseFileFolder ---- Single and multiple selections from specified path treeview listing
Date_Time_Convert -- Easily convert date/time formats, including the language used
ExtMsgBox --------- A highly customisable replacement for MsgBox
GUIExtender -------- Extend and retract multiple sections within a GUI
GUIFrame ---------- Subdivide GUIs into many adjustable frames
GUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView items
GUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeView
Marquee ----------- Scrolling tickertape GUIs
NoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxes
Notify ------------- Small notifications on the edge of the display
Scrollbars ----------Automatically sized scrollbars with a single command
StringSize ---------- Automatically size controls to fit text
Toast -------------- Small GUIs which pop out of the notification area

 

Link to comment
Share on other sites

10 minutes ago, Melba23 said:

my advice remains the same: never rely on operator precedence and always uses parentheses.

That's what I've always done, I'd rather set (alleged) superfluous parentheses than too few :).

18 minutes ago, Melba23 said:

It looks as if AutoIt is treating the expected - operator as a unary minus.

The discussion in the German forum has come to the same conclusion.

Musashi-C64.png

"In the beginning the Universe was created. This has made a lot of people very angry and been widely regarded as a bad move."

Link to comment
Share on other sites

It's not only a question of precedence.
In this case the problem is, that the "-"-Operator seem to be executed twice - once as a unary operator (sign) and once as a binary operator (the minus operation).
This leads to the implicit calculation 11 - (-(2^4))
Therefore, it seems to be more of a bug in the parser.

Link to comment
Share on other sites

  • Moderators

AspirinJunkie,

I disagree with that analysis. (-2) ^ 4 = +16 - or at least it did when I was at school - so it looks as if AutoIt is actually assuming a + operator to get 27. I agree this could well be a parser problem - but I reiterate my advice to use parentheses to make all operator order explicit and so avoid any confusion.

M23

Public_Domain.png.2d871819fcb9957cf44f4514551a2935.png Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind

Open spoiler to see my UDFs:

Spoiler

ArrayMultiColSort ---- Sort arrays on multiple columns
ChooseFileFolder ---- Single and multiple selections from specified path treeview listing
Date_Time_Convert -- Easily convert date/time formats, including the language used
ExtMsgBox --------- A highly customisable replacement for MsgBox
GUIExtender -------- Extend and retract multiple sections within a GUI
GUIFrame ---------- Subdivide GUIs into many adjustable frames
GUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView items
GUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeView
Marquee ----------- Scrolling tickertape GUIs
NoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxes
Notify ------------- Small notifications on the edge of the display
Scrollbars ----------Automatically sized scrollbars with a single command
StringSize ---------- Automatically size controls to fit text
Toast -------------- Small GUIs which pop out of the notification area

 

Link to comment
Share on other sites

I know unary minus can be misinterpreted. In this case, I use an extra + like this:

11 - +2^4

The issue doesn't happen with variables:

Local $n = 2
ConsoleWrite((11 - $n^4) & @LF)

I believe I did open a ticket for that. Just checked and ... NO I didn't; I only contributed to threads about this issue.

Edited by jchd

This wonderful site allows debugging and testing regular expressions (many flavors available). An absolute must have in your bookmarks.
Another excellent RegExp tutorial. Don't forget downloading your copy of up-to-date pcretest.exe and pcregrep.exe here
RegExp tutorial: enough to get started
PCRE v8.33 regexp documentation latest available release and currently implemented in AutoIt beta.

SQLitespeed is another feature-rich premier SQLite manager (includes import/export). Well worth a try.
SQLite Expert (freeware Personal Edition or payware Pro version) is a very useful SQLite database manager.
An excellent eBook covering almost every aspect of SQLite3: a must-read for anyone doing serious work.
SQL tutorial (covers "generic" SQL, but most of it applies to SQLite as well)
A work-in-progress SQLite3 tutorial. Don't miss other LxyzTHW pages!
SQLite official website with full documentation (may be newer than the SQLite library that comes standard with AutoIt)

Link to comment
Share on other sites

We have all seen user requests in the past where operators (often concatenations of AND , OR, NOT etc.) did not lead to the result the user had expected. I agree with @Melba23  that the safest solution is to use parentheses (even if they may seem unnecessary in some cases). Parentheses are for free, so no need to use them sparingly :lol: .

 

Musashi-C64.png

"In the beginning the Universe was created. This has made a lot of people very angry and been widely regarded as a bad move."

Link to comment
Share on other sites

3 minutes ago, Melba23 said:

(-2) ^ 4 = +16 - or at least it did when I was at school

Good hint: I would sum up in my own words:

  • The minus has two functions - once as a binary minus operator and once as a unary sign operator.
  • The tricky thing about this is that the binary operator has a lower priority than the power operator.
    The sign operator, on the other hand, has a higher priority (as in mathematics) than the power operator.
  • This leads to the implicit execution (-2)^4
  • The basic problem here, however, is that even if the minus here is only interpreted as a sign operator, we still lack a binary operator that links the right side with the 11.
  • The parser simply assumes a plus operator for this.

This would explain the behaviour - but not whether it is a bug or not.
Basically, I still think it is a bug, because the form of the equation specifies the minus as a binary operator (especially from a mathematical view).
Furthermore, there is no indication in the AutoIt documentation that the sign operator has an operator priority that differs from the binary variant - so it is a behaviour that differs from the language definition. 

Link to comment
Share on other sites

  • Moderators

Hi,

i will add something to the Help file to highlight the possibility of binary minus/unary negation confusion.

M23

Edit:

Although the operator precedence should suffice in most cases, is recommended to use brackets to force the order of evaluation if the result is critical or if the expression is complex.

e.g. (2 + 4) * 10 equals 60.

This is particularly true for the - operator which can be used for both binary subtraction (subtraction of 2 numbers)and unary negation (setting the negative of a value). The use of brackets is highly recommended in this case to prevent confusion.

How about that?

Edit 2:

Done - will appear in 3.3.16.1.

Edited by Melba23

Public_Domain.png.2d871819fcb9957cf44f4514551a2935.png Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind

Open spoiler to see my UDFs:

Spoiler

ArrayMultiColSort ---- Sort arrays on multiple columns
ChooseFileFolder ---- Single and multiple selections from specified path treeview listing
Date_Time_Convert -- Easily convert date/time formats, including the language used
ExtMsgBox --------- A highly customisable replacement for MsgBox
GUIExtender -------- Extend and retract multiple sections within a GUI
GUIFrame ---------- Subdivide GUIs into many adjustable frames
GUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView items
GUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeView
Marquee ----------- Scrolling tickertape GUIs
NoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxes
Notify ------------- Small notifications on the edge of the display
Scrollbars ----------Automatically sized scrollbars with a single command
StringSize ---------- Automatically size controls to fit text
Toast -------------- Small GUIs which pop out of the notification area

 

Link to comment
Share on other sites

This would help to train users to use more brackets and thus avoid the problem in the first place.

However, it remains merely a workaround.
I still consider the case a bug and not just a confusion in the precedence evaluation of operators.

Because: 
1. the minus is wrongly interpreted as a unary operator although there is an independent expression to the left as well as to the right of the operator.
2. the expression as a unary minus is followed by a implicit plus-operator to join the result with the 11 on the left side without any expected logic underlying it.
3. this behaviour (as jchd showed) only occurs with Int constants (behaviour differs between AutoIt 3.3.14.5 and 3.3.16.0):

$x = 2

ConsoleWrite(11 - 2 ^ 4 & @CRLF)
ConsoleWrite(11 - 2.0 ^ 4 & @CRLF)
ConsoleWrite(11 - 2e0 ^ 4 & @CRLF)
ConsoleWrite(11 - $x ^ 4 & @CRLF)

So yes - I like the hint in the help very much and it will also serve a good purpose. 👍
However, we should classify the behaviour itself as a bug and suggest fixing it accordingly.

Edited by AspirinJunkie
Link to comment
Share on other sites

I agree, and for a pretty strong reason: if 11 - 2 ^ 4 is parsed as 11 (-2) ^ 4, then the expression becomes 11 ((-2) ^ 4) or 11 16 which is obviously invalid because there is no operator between 11 and the rest.

Also while 11 - 2 ^ 4 wrongly yields 27, 11 - 2 ^ 3 correctly evaluates to 3, go figure! Seems the behavior is correct for odd exponents.

This wonderful site allows debugging and testing regular expressions (many flavors available). An absolute must have in your bookmarks.
Another excellent RegExp tutorial. Don't forget downloading your copy of up-to-date pcretest.exe and pcregrep.exe here
RegExp tutorial: enough to get started
PCRE v8.33 regexp documentation latest available release and currently implemented in AutoIt beta.

SQLitespeed is another feature-rich premier SQLite manager (includes import/export). Well worth a try.
SQLite Expert (freeware Personal Edition or payware Pro version) is a very useful SQLite database manager.
An excellent eBook covering almost every aspect of SQLite3: a must-read for anyone doing serious work.
SQL tutorial (covers "generic" SQL, but most of it applies to SQLite as well)
A work-in-progress SQLite3 tutorial. Don't miss other LxyzTHW pages!
SQLite official website with full documentation (may be newer than the SQLite library that comes standard with AutoIt)

Link to comment
Share on other sites

To further isolate the cause, I ran the following test script with both version 3.3.16.0 and 3.3.14.5:

Global $sString = ""

$x = 2
$y = 4

$sString = StringFormat("% 15s = %d\n", "11 - 2 ^ 4", 11 - 2 ^ 4) & _
    StringFormat("% 15s = %d\n", "11 - 2.0 ^ 4", 11 - 2.0 ^ 4) & _
    StringFormat("% 15s = %d\n", "11 - 2e0 ^ 4", 11 - 2e0 ^ 4) & _
    StringFormat("% 15s = %d\n", "11 - $x ^ 4", 11 - $x ^ 4) & _
    StringFormat("% 15s = %d\n\n", "11 - 2 ^ $y", 11 - 2 ^ $y) & _
    StringFormat("% 15s = %d\n", "11 - 2 ^ 3", 11 - 2 ^ 3) & _
    StringFormat("% 15s = %d\n", "11 - 2.0 ^ 3", 11 - 2.0 ^ 3) & _
    StringFormat("% 15s = %d\n", "11 - 2e0 ^ 3", 11 - 2e0 ^ 3) & _
    StringFormat("% 15s = %d\n", "11 - $x ^ 3", 11 - $x ^ 3)


ConsoleWrite($sString)

The results between the AutoIt versions differ here.

v. 3.3.14.5:

11 - 2 ^ 4 = 27
   11 - 2.0 ^ 4 = -5
   11 - 2e0 ^ 4 = -5
    11 - $x ^ 4 = -5
    11 - 2 ^ $y = 27

     11 - 2 ^ 3 = 3
   11 - 2.0 ^ 3 = 3
   11 - 2e0 ^ 3 = 3
    11 - $x ^ 3 = 3

v. 3.3.16.0:

11 - 2 ^ 4 = 27
   11 - 2.0 ^ 4 = 27
   11 - 2e0 ^ 4 = 27
    11 - $x ^ 4 = -5
    11 - 2 ^ $y = 27

     11 - 2 ^ 3 = 3
   11 - 2.0 ^ 3 = 3
   11 - 2e0 ^ 3 = 3
    11 - $x ^ 3 = 3

 

Link to comment
Share on other sites

Maybe related to the fix for trac #3232.

This wonderful site allows debugging and testing regular expressions (many flavors available). An absolute must have in your bookmarks.
Another excellent RegExp tutorial. Don't forget downloading your copy of up-to-date pcretest.exe and pcregrep.exe here
RegExp tutorial: enough to get started
PCRE v8.33 regexp documentation latest available release and currently implemented in AutoIt beta.

SQLitespeed is another feature-rich premier SQLite manager (includes import/export). Well worth a try.
SQLite Expert (freeware Personal Edition or payware Pro version) is a very useful SQLite database manager.
An excellent eBook covering almost every aspect of SQLite3: a must-read for anyone doing serious work.
SQL tutorial (covers "generic" SQL, but most of it applies to SQLite as well)
A work-in-progress SQLite3 tutorial. Don't miss other LxyzTHW pages!
SQLite official website with full documentation (may be newer than the SQLite library that comes standard with AutoIt)

Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...