If statement without equality, what does that mean? (c) - c

if(tree->left)
if(!(*tree))
Do they mean:
if(tree->left==0)
if((*tree)==1)
I did not find anything about this.

In C there are not booleans but only integers. The if statement just check for equality with 0, evaluating 0 as false and everything else as true, so your examples are equivalent to
if(tree->left != 0)
if((*tree)==0)

It means
if(tree->left != 0 )
if((*tree) == 0)

C and C++ will interpret 0 as false and anything else as true.
For example, doing
if (my_var & 0x0010) {
printf("Hello world");
}
will print the message if my_var has the bit set in the fifth position.

Related

In C, is '==' ever used in variable assignment?

Was working with some SASL code today and noticed the == in the below snippet. I'm no C expert but the only way I've ever used that operator was to test equality. Bug?
if ( !conn ) {
rc == LDAP_SUCCESS;
goto done;
}
That statement does nothing. It's a bug.
Now, you COULD assign (rc == LDAP_SUCCESS) to a variable, which would store the boolean result of that operation (1 if true, or 0 if false).

Difference between NOT false and true

I have this chunk of code:
if ( ( data.is_err != FALSE ) && ( available != FALSE ) )
{
Set_Dtc_TimerChange(DTC_VPOS, +dt_ms);
}
Why would you use not equal to false instead of just equal to true? Is there a difference at all?
This is a C question rather than an EE, but as C is very close to the hardware....
The old C definition of false is 0, with all other values being true, that is
if( 0 ){ ... }
will not execute the ... code, but for instance
if( 1 ){ ... }
if( -1 ){ ... }
if( 42 ){ ... }
all will. Hence you can test a truth value for being equal to FALSE (which is defined as 0), but when you want to compare it to true, which value would you use for true? Some say TRUE must be defined as (!FALSE), but that would yield -1, which is a value of true, but not the only one.
Hence programmers tended to avoid conparing to TRUE.
Modern C should have solved this by defining TRUE to be (I think) 1, but that stil has funny consequences, like
int probably( void ){ return 42; }
if( probably() ){ ... }
if( probably() == TRUE ){ ... }
Here the blame is on probbaly(), which returns an abiguous truth value.
Personally, I would have written
if ( data.is_err && available ) { ... }
which I think is much more readable and avoids the comparisons.
(BTW how can something be available when there is a data error?)
This code can be safely replaced by:
if ( data.is_err && available ) {
Set_Dtc_TimerChange(DTC_VPOS, +dt_ms);
}
unless the FALSE has some non-traditional definition somewhere in the program. A good compiler will produce equivalent code for either form, but the more readable one is preferred.
C does not have a Boolean type. Instead, it treats 0 as false and any other value as true. As a result, there is no value that you can test against to determine whether a value represents true. That's not important if you write idiomatic C code: if (x) ... will always do the right thing. Folks who are uncomfortable with this idiom like to test explicitly against some representation of false, but never explain why they limit that to one level. After all, x != FALSE is just a value, and by the same argument needs to be tested: if ((x != FALSE) != FALSE)....

C, debugger breakpoints on simple if else statement

I'm very new to coding, I'm editing a simple C function in CodeBlocks. I'm getting a red error dot next to "else", I could't spot any problem with my code, perhaps its something I have overlooked. Please help, thanks!
int isZero (float f)
{
unsigned int u = *(unsigned int*)&f;
if ((u== 0x0) || (u==0x80000000) );
return 1;
else
return 0;
return (EXIT_SUCCESS);
}
Watch out for all semicolons. There's one more than you want.
You've got an extra semicolon there.
Remove the one from the end of if ((u== 0x0) || (u==0x80000000) );
The compiler reads the ; as a single statement doing nothing; and considers that the contents of the if block. The next statement is return 1;, which will always execute. When the compiler sees the else, it can't find the if that goes with it because that if block got closed with the first semicolon.
The compiler parses this as
int isZero (float f)
{
unsigned int u = *(unsigned int*)&f;
if ((u== 0x0) || (u==0x80000000)
/* do nothing */;
return 1;
else /* what does this go with? */
return 0;
return (EXIT_SUCCESS);
}
When you put a ; after an if clause it means that the if is an empty block.Therefore whether the statement is true or false the statement next to if is always excecuted.So your code
if ((u== 0x0) || (u==0x80000000) );
return 1;
evaluates to
if ((u== 0x0) || (u==0x80000000) )
{ //empty block
}
return 1; //always excecuted
Therefore the else part is never excecuted and the compiler does not see a if statement to relate this else to so you get an error.

if ((float)(int_one && int_two) == (float)int_one && (float)int_two) always evaluates "false"

This is compiled with GCC in CC mode.
I'm looking at some basic interpreter code, and this code is run when parsing the "AND" operator. int_one and int_two are the integer values of the arguments to AND like this in basic:
int_one AND int_two
This portion of the interpreter has already determined that the arguments are integer types (instead of real types), so why do we care how they compare when cast as reals?
i'm not 100% sure what this check does, and furthermore, why it almost always evaluates to false! What is the significance of this check, and why on earth is it false?
Here is some tester code that illustrates some probably false assumptions about buffering the and results, which gives a different result:
#include <stdio.h>
#include <stdlib.h>
int one, two;
int main()
{
// Initialize
one = 3;
two = 3;
// do a test with buffering the and result
float int_and_cast_to_real = (float)(one && two);
float int_cast_to_real_and = (float)one && (float)two;
if (int_and_cast_to_real == int_cast_to_real_and) {
// This message gets fired, so the buffered results are true.
printf("oh they are equal buddy\n");
} else {
printf("you think they'd be equal, but they aint.\n");
}
// do it all at once
if((float)(one && two) == (float)one && (float)two) {
printf("int & real ands give equal result\n");
} else {
// This message gets fired, so the unbuffered results are false.
printf("int & real ands give inequal result\n");
}
return 0;
}
Yes. Because Boolean values are either 0 or 1. (one && two); will return Boolean 1 which after casting to float will give 1.000000 while (float)one will return 3.000000.
So, (float)(one && two) == (float)one && (float)two will be evaluated as ( (float)(one && two) == (float)one ) && (float)two (because of higher precedence of == than &&) which gives 0.000000 == 1.000000 which finally evaluated to false.
The (float)(one && two) == (float)one && (float)two conditions is evaluated as ((float)(one && two) == (float)one) && (float)two, but your intention seems to be (float)(one && two) == ((float)one && (float)two).

Trouble converting a nested if into if(condition1 || condition2)

I have the following code which functions correctly.
if((strcmppgm2ram((char*)name, (ROM char*)"products.htm") != 0))
{
if((strcmppgm2ram((char*)name, (ROM char*)"restock.htm") != 0))
{
return HTTP_IO_DONE;
}
}
I'd like to clean it up and put it in the form:
if((strcmppgm2ram((char*)name, (ROM char*)"products.htm") != 0) || (strcmppgm2ram((char*)name, (ROM char*)"restock.htm") !=0))
{
return HTTP_IO_DONE;
}
Unfortunately, the latter is not working correctly. What have I overlooked?? Thanks in advance!
P.S. strcmp == strcmppgm2ram for the sake of this question.
You are using || when you should be using &&.
The result should only be reached if BOTH conditions are true.
The reason it didn't work before is because even if one of the strings matched, the other one wouldn't, so regardless of input the statement would always result in returning HTTP_IO_DONE.
Notice that you only return HTTP_IO_DONE; if both conditions turned to be true, therefore you should use and (&&) and not or

Resources