Is it safe to compare boolean variable with 1 and 0 in C, C++? [duplicate]

守給你的承諾、 提交于 2021-02-20 19:13:19


Consider the code

bool f() { return 42; }

if (f() == 1)

Does C (C99+ with stdbool.h) and C++ standards guarantee that "hello" will printed? Does

bool a = x;

is always equivalent to

bool a = x ? 1 : 0;


In C++, bool is a built-in type. Conversions from any type to bool always yield false (0) or true (1).

Prior to the 1999 ISO C standard, C did not have a built-in Boolean type. It was (and still is) common for programmers to define their own Boolean types, for example:

typedef int BOOL;
#define FALSE 0
#define TRUE 1


typedef enum { false, true } bool;

Any such type is at least 1 byte in size, and can store values other than 0 or 1, so equality comparisons to 0 or 1 are potentially unsafe.

C99 added a built-in type _Bool, with conversion semantics similar to those for bool in C++; it can also be referred to as bool if you have #include <stdbool.h>.

In either C or C++, code whose behavior is undefined can potentially store a value other than 0 or 1 in a bool object. For example, this:

bool b;
*(char*)&b = 2;

will (probably) store the value 2 in b, but a C++ compiler may assume that its value is either 0 or 1; a comparison like b == 0 or b == true may either succeed or fail.

My advice:

  • Don't write code that stores strange values in bool objects.
  • Don't compare bool values for equality or inequality to 0, 1, false, or true.

In your example:

bool f() { return 42; }

Assuming this is either C++ or C with <stdbool.h>, this function will return true or, equivalently, 1, since the conversion of 42 to bool yields 1.

if (f() == 1)

Since you haven't constructed any strange bool values, this is well behaved and will print "hello".

But there's no point in making the comparison explicitly. f() is already of type bool, so it's already usable as a condition. You can (and probably should) just write:

if (f())

Writing f() == 1 is no more helpful than writing (f() == 1) == 1).

In a real program, presumably you'll have given your function a meaningful name that makes it clear that its value represents a condition:

if (greeting_required())


Yes. You are missing a step though. "0" is false and every other int is true, but f() always returns true ("1"). It doesn't return 42, the casting occurs in "return 42;".


In C macro bool (we are speaking about the macro defined in stdbool.h) expands to _Bool that has only two values 0 and 1.

In C++ the value of f() in expression f() == 1 is implicitly converted to int 1 according to the integral promotion.

So in my opinion this code

bool f() { return 42; }

if (f() == 1)

is safe.


The only real trick that I know of, that is useful with pre-C99 environments is the double negation

int a = 42;
if ( (!!a) != 0 ) printf("Hello\n");

this will print Hello because the result of the !! operation is a boolean that is true when the value is non-zero, false otherwise. But this is gonna cost you 2 negation to get the boolean that you want, in modern standards this is redundant because you will get the same result without the !! and it's a result granted by the language.