# Truth value

Discussion in 'C Programming' started by prasoonthegreat@gmail.com, May 13, 2009.

1. ### Guest

In the following C code snippet

int i=2,j=-1,k=-1,z;
x = ++i || ++j && ++k;

here the right side of || is not evaluated because ++i is a non zero
value( || is short circuit evaluating operator)...

But will the value of x be always 1????

________________________________________

, May 13, 2009

2. ### Guest

On May 13, 8:00 pm, Eric Sosman <> wrote:
> wrote:
> > In the following C code snippet

>
> > int i=2,j=-1,k=-1,z;
> > x = ++i || ++j && ++k;

>
> > here the right side of || is not evaluated because ++i is a non zero
> > value( || is short circuit evaluating operator)...

>
> > But will the value of x be always 1????

>
>      Yes, if `x' is a variable of a type that can hold the value `1'.
> If `x' is a `char*' or a `struct tm' or a `union foobar', or a
> `signed int : 1' bit-field, then No.
>
> --
>

My mistake 'z' was rather 'x'

int i=2,j=-1,k=-1,x;
x = ++i || ++j && ++k;

I mean to say... the value returned by the left sub-expression (++i ||
++j && ++k; ) is true in this case....

Does true always mean '1'????

, May 13, 2009

3. ### Keith ThompsonGuest

writes:
> On May 13, 8:00 pm, Eric Sosman <> wrote:
>> wrote:
>> > In the following C code snippet

>>
>> > int i=2,j=-1,k=-1,z;
>> > x = ++i || ++j && ++k;

>>
>> > here the right side of || is not evaluated because ++i is a non zero
>> > value( || is short circuit evaluating operator)...

>>
>> > But will the value of x be always 1????

>>
>>      Yes, if `x' is a variable of a type that can hold the value `1'.
>> If `x' is a `char*' or a `struct tm' or a `union foobar', or a
>> `signed int : 1' bit-field, then No.

>
> My mistake 'z' was rather 'x'
>
> int i=2,j=-1,k=-1,x;
> x = ++i || ++j && ++k;
>
> I mean to say... the value returned by the left sub-expression (++i ||
> ++j && ++k; ) is true in this case....
>
> Does true always mean '1'????

Yes and no.

In a conditional context (if, while, do-while, second clause of a for
loop, etc.), any expression that compares equal to 0 is treated as
false, and any expression that compares unequal to 0 (not just 1) is
treated as true. So this:

if (0) puts("0");
if (1) puts("1");
if (2) puts("2");

will print "1" and "2".

But a relational or equality operator (<, >, <=, >=, ==, !=), or a
logical operator (!, &&, ||) always yields either 0 or 1; they will
never yield any non-zero value other than 1.

But be careful about depending in this fact. Things other than
operators can yield boolean results, but those results aren't
necessarily normalized to 0 or 1. For example, the is*() functions
declared in <ctype.h> can return any non-zero value to indicate a true
condition.

You can define your own "false" and "true" symbols as 0 and 1,
respectively (or use the "bool" type in <stdbool.h> if your
implementation supports it), but you should be careful how you use
them. For example, this:

if (condition == true) ...

is dangerous, since condition could be true without being equal to 1.

if (condition) ...

--
Keith Thompson (The_Other_Keith) <http://www.ghoti.net/~kst>
Nokia
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"

Keith Thompson, May 13, 2009
4. ### Guest

On May 13, 8:44 pm, Eric Sosman <> wrote:
> wrote:
> > [...]
> > Does true always mean '1'????

>
>      C's comparison and logical operators always deliver `0'
> for "false" and `1' for "true."  So does the `!' operator.
>
>      C's testing constructs -- if(), while(), and so on --
> treat `0' as "false" and any non-zero value (including `1')
> as "true."  A null pointer compares equal to `0' and is
> therefore "false," while a non-null pointer compares unequal
> to `0' and is thus "true" even though it has no numeric value
> at all.  (My personal preference is to write `if (ptr != NULL)'
> rather than `if (ptr)', but not everyone shares my tastes.)

What is the basic significant difference between if(ptr!=NULL) and if
(ptr) (that means if ptr is true)????

>      Note that functions like isdigit() are not comparison
> or logical operators; they deliver `0' for "false" but may
> deliver something other than `1' for "true."

, May 13, 2009
5. ### jameskuyperGuest

wrote:
> On May 13, 8:00 pm, Eric Sosman <> wrote:
> > wrote:
> > > In the following C code snippet

> >
> > > int i=2,j=-1,k=-1,z;
> > > x = ++i || ++j && ++k;

> >
> > > here the right side of || is not evaluated because ++i is a non zero
> > > value( || is short circuit evaluating operator)...

> >
> > > But will the value of x be always 1????

> >
> > Yes, if `x' is a variable of a type that can hold the value `1'.
> > If `x' is a `char*' or a `struct tm' or a `union foobar', or a
> > `signed int : 1' bit-field, then No.
> >
> > --
> >

>
> My mistake 'z' was rather 'x'
>
> int i=2,j=-1,k=-1,x;
> x = ++i || ++j && ++k;
>
> I mean to say... the value returned by the left sub-expression (++i ||
> ++j && ++k; ) is true in this case....

For these particular values of i, j, and k, yes.

If you're asking if there are other values of i, j, and k which would
give z a value of 0, there are. If i==-1, and either j==-1 or k== -1,
then z will be 0.

> Does true always mean '1'????

No, in C true means !=0: that's how the if(), for() and while()
statements treat their conditions, and also how the conditional and
logical operators interpret their operands. Notice that, among other
things, this means that non-null pointers count as 'true'. However,
the comparison operators are defined as returning 1 when the
comparison is true, and the logical operators "!", "||" and "&&" are
defined as returning 1 when the corresponding truth table would have
"T".

jameskuyper, May 13, 2009
6. ### Giacomo Degli EspostiGuest

On 13 Mag, 17:56, wrote:
[...]
> What is the basic significant difference between if(ptr!=NULL) and if
> (ptr) (that means if ptr is true)????

There is no real difference: Any decent compiler would generate the
same
code for the two snippets.
It is a matter of style and readability of the source code.

ciao
Giacomo

Giacomo Degli Esposti, May 13, 2009
7. ### Spiros BousbourasGuest

On 13 May, 16:56, wrote:
> What is the basic significant difference between if(ptr!=NULL) and if
> (ptr) (that means if ptr is true)????

The basic difference is that in order to use (ptr!=NULL) you
need to include some header which defines NULL, for example
<stdio.h>. On the other hand you can always write if (ptr) or
if (ptr != 0) even if your code does not include any of the

--
If there really exist any apostate ex-Randroids, god damn I'd
love to meet them. Apparently, though, it's like a black hole,
i.e., once you go there, you don't come back - ever.

Spiros Bousbouras, May 13, 2009
8. ### Keith ThompsonGuest

Spiros Bousbouras <> writes:
> On 13 May, 16:56, wrote:
>> What is the basic significant difference between if(ptr!=NULL) and if
>> (ptr) (that means if ptr is true)????

>
> The basic difference is that in order to use (ptr!=NULL) you
> need to include some header which defines NULL, for example
> <stdio.h>. On the other hand you can always write if (ptr) or
> if (ptr != 0) even if your code does not include any of the

Well, that's *a* difference. In a program of any significant
complexity, you'll almost certainly already have a #include for one of
the several standard headers that define NULL. And even if you
didn't, IMHO adding a #include is a trivial price to pay for the added
clarity. (Yes, I find "if (ptr != NULL)" substantially clearer than
"if (ptr)".)

--
Keith Thompson (The_Other_Keith) <http://www.ghoti.net/~kst>
Nokia
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"

Keith Thompson, May 13, 2009
9. ### Spiros BousbourasGuest

On 13 May, 17:33, Keith Thompson <> wrote:
> Spiros Bousbouras <> writes:
> > On 13 May, 16:56, wrote:
> >> What is the basic significant difference between if(ptr!=NULL) and if
> >> (ptr) (that means if ptr is true)????

>
> > The basic difference is that in order to use (ptr!=NULL) you
> > need to include some header which defines NULL, for example
> > <stdio.h>. On the other hand you can always write if (ptr) or
> > if (ptr != 0) even if your code does not include any of the

>
> Well, that's *a* difference. In a program of any significant
> complexity, you'll almost certainly already have a #include for one of
> the several standard headers that define NULL.

I disagree. In a programme of sufficient complexity, you will have
some translation units #including some of the standard headers
but you may have others which do not.

> And even if you
> didn't, IMHO adding a #include is a trivial price to pay for the added
> clarity. (Yes, I find "if (ptr != NULL)" substantially clearer than
> "if (ptr)".)

If you ever need to examine the output of the preprocessor, including
redundant headers is not a trivial price to pay. Your compiler may do
other things too if you include headers which it wouldn't do if you
didn't.

--
preexisting condition and was not caused by what you suggest.
Erik Naggum

Spiros Bousbouras, May 13, 2009
10. ### Ali KaraaliGuest

On 13 Mayýs, 18:44, Eric Sosman <> wrote:
> wrote:
> > [...]
> > Does true always mean '1'????

>
>      C's comparison and logical operators always deliver `0'
> for "false" and `1' for "true."  So does the `!' operator.
>
>      C's testing constructs -- if(), while(), and so on --
> treat `0' as "false" and any non-zero value (including `1')
> as "true."  A null pointer compares equal to `0' and is
> therefore "false," while a non-null pointer compares unequal
> to `0' and is thus "true" even though it has no numeric value
> at all.  (My personal preference is to write `if (ptr != NULL)'
> rather than `if (ptr)', but not everyone shares my tastes.)
>
>      Note that functions like isdigit() are not comparison
> or logical operators; they deliver `0' for "false" but may
> deliver something other than `1' for "true."
>
> --
>

I want to ask a question. Why the standart is so inconsistent at this
point? Some functions yield 1 as true, some of them not. I've always
been curious about that. Thank you.

Ali Karaali, May 13, 2009
11. ### Keith ThompsonGuest

Spiros Bousbouras <> writes:
> On 13 May, 17:33, Keith Thompson <> wrote:
>> Spiros Bousbouras <> writes:
>> > On 13 May, 16:56, wrote:
>> >> What is the basic significant difference between if(ptr!=NULL) and if
>> >> (ptr) (that means if ptr is true)????

>>
>> > The basic difference is that in order to use (ptr!=NULL) you
>> > need to include some header which defines NULL, for example
>> > <stdio.h>. On the other hand you can always write if (ptr) or
>> > if (ptr != 0) even if your code does not include any of the

>>
>> Well, that's *a* difference. In a program of any significant
>> complexity, you'll almost certainly already have a #include for one of
>> the several standard headers that define NULL.

>
> I disagree. In a programme of sufficient complexity, you will have
> some translation units #including some of the standard headers
> but you may have others which do not.

Perhaps, but ...

>> And even if you
>> didn't, IMHO adding a #include is a trivial price to pay for the added
>> clarity. (Yes, I find "if (ptr != NULL)" substantially clearer than
>> "if (ptr)".)

>
> If you ever need to examine the output of the preprocessor, including
> redundant headers is not a trivial price to pay. Your compiler may do
> other things too if you include headers which it wouldn't do if you
> didn't.

I rarely need to examine the output of the preprocessor, but even if I
do it's easy enough to skip past the expanded #includes to see my own
preprocessed code.

What things (other than the obvious) would you expect a compiler to do
if I add "#include <stddef.h>" that it wouldn't do if I didn't?

If I need a null pointer constant, I'll use NULL, and if it's not
already visible I'll add "#include <stddef.h>" to the top of the file.
(I'd be happier if the equivalent of NULL were a keyword, but it
isn't, so there it is.)

That's not to say that I object to the "if (ptr)" style. I just
personally prefer "if (ptr != NULL)".

--
Keith Thompson (The_Other_Keith) <http://www.ghoti.net/~kst>
Nokia
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"

Keith Thompson, May 13, 2009
12. ### Keith ThompsonGuest

Ali Karaali <> writes:
> On 13 Mayýs, 18:44, Eric Sosman <> wrote:
>> wrote:
>> > [...]
>> > Does true always mean '1'????

>>
>>      C's comparison and logical operators always deliver `0'
>> for "false" and `1' for "true."  So does the `!' operator.
>>
>>      C's testing constructs -- if(), while(), and so on --
>> treat `0' as "false" and any non-zero value (including `1')
>> as "true."  A null pointer compares equal to `0' and is
>> therefore "false," while a non-null pointer compares unequal
>> to `0' and is thus "true" even though it has no numeric value
>> at all.  (My personal preference is to write `if (ptr != NULL)'
>> rather than `if (ptr)', but not everyone shares my tastes.)
>>
>>      Note that functions like isdigit() are not comparison
>> or logical operators; they deliver `0' for "false" but may
>> deliver something other than `1' for "true."

>
> I want to ask a question. Why the standart is so inconsistent at this
> point? Some functions yield 1 as true, some of them not. I've always
> been curious about that. Thank you.

I was about to say that the standard is consistent. Operators that
yield (logically) boolean results consistently yield 0 for false, 1
for true, while functions that yield boolean results yield 0 for
false, some unspecified non-zero value for true. See feof(),
ferror(), and the is*() functions in <ctype.h> and <wctype.h>.

Fortunately, I checked before posting. There are some comparison
macros in <math.h> (isgreater, isgreaterequal, et al) are defined to
yield 0 for false, 1 for true. I suppose that's because they're
closely analagous to the ">", ">=", et al operators.

But you're right, the standard isn't entirely consistent. It's
probably a matter of historical precedent. As Gordon Burditt pointed
out, the existing implementations of the is*() functions did yield
values other than 1 for true results, and the ANSI C committee's job
was (largely) to standardize existing practice. The comparison macros
in <math.h> are new in C99, and probably weren't bound by previous
implementations.

As a programmer, it's easy enough to deal with this. 99% of the time,
it shouldn't matter whether a true condition is represented as 1 or
137. You can safely assume that the built-in operators yield 0 or 1:

int count = 0;
count += x < y;
count += a < b;
if (count < 2) { ... }

but that's a fairly unusual usage. If you really need a 0 or 1 result
from, say, isupper(), you can write "isupper(c) ? 1 : 0", or
"!!isupper(c)".

--
Keith Thompson (The_Other_Keith) <http://www.ghoti.net/~kst>
Nokia
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"

Keith Thompson, May 13, 2009
13. ### jameskuyperGuest

Keith Thompson wrote:
> Ali Karaali <> writes:

....
> > I want to ask a question. Why the standart is so inconsistent at this
> > point? Some functions yield 1 as true, some of them not. I've always
> > been curious about that. Thank you.

....
> But you're right, the standard isn't entirely consistent. It's
> probably a matter of historical precedent. As Gordon Burditt pointed
> out, the existing implementations of the is*() functions did yield
> values other than 1 for true results, and the ANSI C committee's job
> was (largely) to standardize existing practice.

That just pushes the question back one level: why was existing
practice inconsistent?

> ... The comparison macros
> in <math.h> are new in C99, and probably weren't bound by previous
> implementations.

They were, on the other hand, implemented to meet IEC 60559
requirements, which may mandate the value returned (I don't have a
copy - I've lost track of my copy of the closely related IEEE 784
standard).

jameskuyper, May 13, 2009
14. ### Spiros BousbourasGuest

On 13 May, 19:27, Keith Thompson <> wrote:
> Spiros Bousbouras <> writes:
>
> > If you ever need to examine the output of the preprocessor, including
> > redundant headers is not a trivial price to pay. Your compiler may do
> > other things too if you include headers which it wouldn't do if you
> > didn't.

>
> I rarely need to examine the output of the preprocessor, but even if I
> do it's easy enough to skip past the expanded #includes to see my own
> preprocessed code.

It causes recent output to scroll away. I don't like that.

> What things (other than the obvious) would you expect a compiler to do
> if I add "#include <stddef.h>" that it wouldn't do if I didn't?

I wouldn't *expect* it to do anything beyond the obvious but I don't
think
there's any guarantee that it won't.

Spiros Bousbouras, May 13, 2009
15. ### Ben BacarisseGuest

Twirlip of the Mists <> writes:

> On Wed, 13 May 2009 11:44:45 -0700, Keith Thompson wrote:
>
>> If you really need a 0 or 1 result
>> from, say, isupper(), you can write "isupper(c) ? 1 : 0", or
>> "!!isupper(c)".

>
> FWIW, I would use "!!isupper(c)" as I consider "!!" idiomatic for
> "normalize a boolean value to 0 or 1".

If you are OK with C99, (bool)isupper(c) expressed the meaning more
clearly in my opinion.

--
Ben.

Ben Bacarisse, May 14, 2009
16. ### Keith ThompsonGuest

Ben Bacarisse <> writes:
> Twirlip of the Mists <> writes:
>> On Wed, 13 May 2009 11:44:45 -0700, Keith Thompson wrote:
>>> If you really need a 0 or 1 result
>>> from, say, isupper(), you can write "isupper(c) ? 1 : 0", or
>>> "!!isupper(c)".

>>
>> FWIW, I would use "!!isupper(c)" as I consider "!!" idiomatic for
>> "normalize a boolean value to 0 or 1".

>
> If you are OK with C99, (bool)isupper(c) expressed the meaning more
> clearly in my opinion.

Agreed. It doesn't *quite* mean the same thing. In particular, it
yields a result of type bool rather than int. But there are enough
implicit conversions that it's not likely to be a problem unless you
deliberately make it one.

--
Keith Thompson (The_Other_Keith) <http://www.ghoti.net/~kst>
Nokia
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"

Keith Thompson, May 14, 2009