Found another cycles-eating monster today. We already assumed it was there after my last post about ISFALSE.
WHILE ISTRUE(GetMessage(tmsg, BYVAL %NULL, 0, 0))
'
'will be compiled to:
'
41119C 6A00 PUSH BYTE 00
41119E 6A00 PUSH BYTE 00
4111A0 6A00 PUSH BYTE 00
4111A2 8D9D28FEFFFF LEA EBX, DWORD PTR [EBP+FFFFFE28]
4111A8 53 PUSH EBX
4111A9 FF1508744100 CALL DWORD PTR [00417408]
4111AF E821290000 CALL L413AD5
4111B4 E823110000 CALL L4122DC
4111B9 D9E4 FTST
4111BB DFE0 FNSTSW AX
4111BD 9E SAHF
4111BE DDD8 FSTPST, ST(0)
4111C0 66B8FFFF MOV AX, WORD FFFF
4111C4 7502 JNZ SHORT L4111C8
4111C6 6640 INC AX
4111C8 E804110000 CALL L4122D1
4111CD D9E4 FTST
4111CF DFE0 FNSTSW AX
4111D1 9E SAHF
4111D2 DDD8 FSTPST, ST(0)
4111D4 0F849A000000 JZ L411274
' alternatively use:
WHILE (GetMessage(tmsg, BYVAL %NULL, 0, 0)<>0)
'
' and get this:
'
41119C 6A00 PUSH BYTE 00
41119E 6A00 PUSH BYTE 00
4111A0 6A00 PUSH BYTE 00
4111A2 6A00 PUSH BYTE 00
4111A4 8D9D28FEFFFF LEA EBX, DWORD PTR [EBP+FFFFFE28]
4111AA 53 PUSH EBX
4111AB FF1508744100 CALL DWORD PTR [00417408]
4111B1 E8FF280000 CALL L413AB5
4111B6 8F45D4 POP DWORD PTR [EBP-2C]
4111B9 3B45D4 CMP EAX, DWORD PTR [EBP-2C]
4111BC 0F849A000000 JZ L41125C
No floatingpoint-operations. Much shorter.
Note that saying something like:
IF aa <> 0 THEN
as a way of testing inequality is going to perform the same way as this:
IF aa THEN
because testing any value for a TRUE condition is effectively a test for an non-
zero state. This works for any integer or floating point value
Saying
IF aa = o THEN
is about as short as you can get, but some people like to say
IF aa = %FALSE THEN
with the same results.
You could also reverse logic by saying
IF NOT aa THEN
or
IF NOT aa = 0 THEN
or even
IF aa THEN
ELSE
....
END IF
The rules of logic as applied to computers is pretty straight forward, and can
include the use of parentheses (), AND, OR, XOR, and NOT (some languages
also support NOR and NAND, which are really abbreviations for NOT OR and
NOT AND).
Logic results are always evalutated as TRUE if the results are non-zero, and
FALSE if the results are exactly zero.
Parentheses () have a special purpose in PowerBasic when used in logical
expressions, as AND and OR are understood to mean each condition before
and after these terms is evaluated for a TRUE or FALSE result separately.
IF a AND b THEN
would mean that a must be TRUE and b must be TRUE before the expression
a AND b would be determined to be TRUE. The actual values of a and b are
inmaterial, except both would be non-zero.
However, if you wrote the expression as this:
IF (a AND b) THEN
then the compiler understands that you want it to relate the value in a directly
to the value in b on a bitwise basis, and if any bit is set in both a and b, then
the result will be considered TRUE, otherwise if all bits examined in a and b are
found to have either or both set to zero, then the outcome will be FALSE.
Bitwise operation in such cases may give unexpected results. Unless you know
what you are doing, and know what the results of bitwise operations will be,
you might be better off leaving out the parentheses or including explicit tests
for a and b like so:
IF a AND b THEN
or:
IF a THEN If b THEN
or:
IF a THEN
IF b THEN
END IF
END IF
or:
IF (a <> 0 AND b <> 0) THEN
You can even do this:
IF (a <> 0 AND b) THEN
because the a<>0 test will be performed first, a matter of operator precident,
and a TRUE state would be a -1 (not a positive 1, but negative 1). A negative
1 ANDed with any integer value is automatically going to find at least one pair
of bits both set if the second value is non-zero. But this would only work if b
is an Integer - it might well fail if b is a floating point type whose value is out
of the range of an integer (involving a decimal value or very large numeric
value with no bits set in the lower interger range).
Such tricks are not uncommon when looking at the code of someone well
versed in lower level features of the compiler, but some techniques can also result in code that can be hard to debug when you see it do something that was not expected. The best advice then is to replace implicit tests (such as the
last one involving b) with explicit tests (such as using b=0 or b<>0) so as to
close any loopholes based on a faulty understanding between what was expected and what actually occurred.