Thanks for the missing warning
-
Hi, five minutes ago I was debugging a game I'm making and while tracing on this fragment of code:
#define XBALLOON_TYPE_1 0x01 #define XBALLOON_TYPE_2 0x02 #define XBALLOON_TYPE_3 0x04 k = 0; if (nPosX < 332) k |= XBALLOON_TYPE_1; if (nPosY < cBalloon.GetHeight()) { nPosY += y2; k |= XBALLOON_TYPE_2; } if (bBalloonIsThinking != FALSE) XBALLOON_TYPE_3; ...
I noticed that never could step in "if (bBalloonIsThinking != FALSE)
". The error is that the code should be:if (bBalloonIsThinking != FALSE) **k |=** XBALLOON_TYPE_3;
But with the missing "k |=
", the compiler (VS2005, in their default warning settings) says 0 errors, 0 warnings. Assume you are the compiler and found this:if (bBalloonIsThinking != FALSE) 0x04;
At least, I suppose you will insult me. Best regards, Mauro.It's a perfectly valid expression-statement according to the C++ standard. Any expression can be used as a statement. This just happens not to do anything. The compiler is therefore not allowed to issue a diagnostic. The UNUSED_ALWAYS macro in (I think) ATL, used to indicate that a parameter is unused (which would cause a warning) simply evaluates to the contents of its parameter. That is, the definition is
#define UNUSED_ALWAYS(x) (x)
which therefore generates an expression-statement.
DoEvents
: Generating unexpected recursion since 1991 -
It's a perfectly valid expression-statement according to the C++ standard. Any expression can be used as a statement. This just happens not to do anything. The compiler is therefore not allowed to issue a diagnostic. The UNUSED_ALWAYS macro in (I think) ATL, used to indicate that a parameter is unused (which would cause a warning) simply evaluates to the contents of its parameter. That is, the definition is
#define UNUSED_ALWAYS(x) (x)
which therefore generates an expression-statement.
DoEvents
: Generating unexpected recursion since 1991Mike Dimmick wrote:
It's a perfectly valid expression-statement according to the C++ standard. Any expression can be used as a statement. This just happens not to do anything. The compiler is therefore not allowed to issue a diagnostic.
I have to disagree with this logic. It's not an error, but compiler warnings are all about letting you know about things that are legal but likely to be an error like:
if (boolVal = false)
Perfectly legal C, but 99% of the time what was intended wasif (boolVal == false)
-- Help Stamp Out and Abolish Redundancy The preceding is courtesy of the Department of Unnecessarily Redundant Repetition Department.
-
Mike Dimmick wrote:
It's a perfectly valid expression-statement according to the C++ standard. Any expression can be used as a statement. This just happens not to do anything. The compiler is therefore not allowed to issue a diagnostic.
I have to disagree with this logic. It's not an error, but compiler warnings are all about letting you know about things that are legal but likely to be an error like:
if (boolVal = false)
Perfectly legal C, but 99% of the time what was intended wasif (boolVal == false)
-- Help Stamp Out and Abolish Redundancy The preceding is courtesy of the Department of Unnecessarily Redundant Repetition Department.
Ugh, the amount of times i've done that :sigh: If it where not for the compiler warning me, who knows how much time i could have wasted trying to figure out why stuff isn't working. Anyway, a 5 for an excellent point.
My current favourite word is: PIE! I have changed my name to my regular internet alias. But don't let the 'Genius' part fool you, you don't know what 'SK' stands for. -
The Undefeated
-
It's a perfectly valid expression-statement according to the C++ standard. Any expression can be used as a statement. This just happens not to do anything. The compiler is therefore not allowed to issue a diagnostic. The UNUSED_ALWAYS macro in (I think) ATL, used to indicate that a parameter is unused (which would cause a warning) simply evaluates to the contents of its parameter. That is, the definition is
#define UNUSED_ALWAYS(x) (x)
which therefore generates an expression-statement.
DoEvents
: Generating unexpected recursion since 1991Yes, but it is a value :) Best regards, Mauro.
-
Hi, five minutes ago I was debugging a game I'm making and while tracing on this fragment of code:
#define XBALLOON_TYPE_1 0x01 #define XBALLOON_TYPE_2 0x02 #define XBALLOON_TYPE_3 0x04 k = 0; if (nPosX < 332) k |= XBALLOON_TYPE_1; if (nPosY < cBalloon.GetHeight()) { nPosY += y2; k |= XBALLOON_TYPE_2; } if (bBalloonIsThinking != FALSE) XBALLOON_TYPE_3; ...
I noticed that never could step in "if (bBalloonIsThinking != FALSE)
". The error is that the code should be:if (bBalloonIsThinking != FALSE) **k |=** XBALLOON_TYPE_3;
But with the missing "k |=
", the compiler (VS2005, in their default warning settings) says 0 errors, 0 warnings. Assume you are the compiler and found this:if (bBalloonIsThinking != FALSE) 0x04;
At least, I suppose you will insult me. Best regards, Mauro.An expression statement isn't as rare as you might think. If you write
k++;
, that is an expression statement - it evaluatesk++
(which happens to have a side-effect) and discards the result.--Mike-- Visual C++ MVP :cool: LINKS~! PimpFish | CP SearchBar v3.0 | C++ Forum FAQ "That's what's great about doing user interface work. No matter what you do, people will say that what you did was idiotic." -- Raymond Chen
-
An expression statement isn't as rare as you might think. If you write
k++;
, that is an expression statement - it evaluatesk++
(which happens to have a side-effect) and discards the result.--Mike-- Visual C++ MVP :cool: LINKS~! PimpFish | CP SearchBar v3.0 | C++ Forum FAQ "That's what's great about doing user interface work. No matter what you do, people will say that what you did was idiotic." -- Raymond Chen
Yes, but like I said before, the preprocesor replaces the macro with a value. If it were a variable the discussion would be different... but it is a simple number. C/C++ parser: If token = number and it is alone... just ignore it. Regards, Mauro.
-
Yes, but like I said before, the preprocesor replaces the macro with a value. If it were a variable the discussion would be different... but it is a simple number. C/C++ parser: If token = number and it is alone... just ignore it. Regards, Mauro.
unless the number is 42 which is known to have numerous side effects
-
Mike Dimmick wrote:
It's a perfectly valid expression-statement according to the C++ standard. Any expression can be used as a statement. This just happens not to do anything. The compiler is therefore not allowed to issue a diagnostic.
I have to disagree with this logic. It's not an error, but compiler warnings are all about letting you know about things that are legal but likely to be an error like:
if (boolVal = false)
Perfectly legal C, but 99% of the time what was intended wasif (boolVal == false)
-- Help Stamp Out and Abolish Redundancy The preceding is courtesy of the Department of Unnecessarily Redundant Repetition Department.
-
That's why it's better to put constant first in your tests:
if (false = boolVal)
instead of:if (boolVal = false)
:)Excellent point. I've been doing that for years. Before I learned C, I was working in Pascal. In that language
=
is comparison and:=
is assignment. I got bit a few times. BDF -
Excellent point. I've been doing that for years. Before I learned C, I was working in Pascal. In that language
=
is comparison and:=
is assignment. I got bit a few times. BDFBig Daddy Farang wrote:
Before I learned C, I was working in Pascal. In that language = is comparison and := is assignment.
Yep. 'Equal to' and 'becomes equal to'. Perfectly logical. Why '=' and '==' were used in c syntax is one of the things that irritates me most about the language(s).
-
Big Daddy Farang wrote:
Before I learned C, I was working in Pascal. In that language = is comparison and := is assignment.
Yep. 'Equal to' and 'becomes equal to'. Perfectly logical. Why '=' and '==' were used in c syntax is one of the things that irritates me most about the language(s).
-
If I recall the justification from K&R, it was because assignment (=) was used far more often than equality (==), therefore assignment should be smaller. Remember, it *was* 1970.
Hopelessly pedantic since 1963.
This makes sense, of course, but I have always thought that it would be really cool to have a "smart" = operator that, depending on context, is either comparison or assignment; a dedicated := assignment operator for when you're returning the result of an assignment; and a dedicated == operator for when you really want to compare. That way, you won't get bit, but you can have C's power if you need it. I'm not sure why no languages I've seen have this.