HiveBrain v1.2.0
Get Started
← Back to all entries
patterncMajor

In C, why limit || and && to evaluate to booleans?

Submitted by: @import:stackexchange-cs··
0
Viewed 0 times
whylimitevaluateandbooleans

Problem

In some languages, e.g. Ruby, an expression like:

val = call_fn() || DEFAULT_VAL;


will set val to the results of call_fn() if it is truthy (non-zero, non-NULL, etc), or to DEFAULT_VAL otherwise. This can be really useful.

In C, the result of the || operator is always a boolean value (1 or 0).

Is there a strong argument for C limiting the result to a boolean value (other than tradition)?
Addendum

Using some gnu extensions, a macro that approximates the behavior I'm looking for could be written as:

#define OP_OR(a, b)                                 \
    ({                                              \
        __typeof__(a) _a = (a);                     \
        _a ? _a : b                                 \
    })


This evaluates to a iff it is truthy (i.e. non-0 for numeric values, non-NULL for pointers, not '\0' for chars), otherwise it evaluates to b. The __typeof__ line guarantees that a is evaluated exactly once.

Solution

Boolean types and Boolean expressions are the crux of the logical formalism and the latter is ubiquitous in programming. C was lacking them in the beginning, yet another design flaw of this language (took like twenty years to be fixed!).

Tinkering a boolean type with integers is not just a conceptual mistake, it is a source of problems, such as comparisons not behaving as expected.

I don't know about the semantics of && in Ruby, but presumably it has to make an asymmetric choice between the two values in case of two non-zeroes.

This said, the ternary ? operator allows you constructs like

val= call_fn();
val= val != 0 ? val : DEFAULT_VAL;


Independently of this answer, I don't see the trick

val = call_fn() || DEFAULT_VAL;


with a good eye, as it forces you to reserve the value 0 to somehow indicate "do not use this returned value" and cannot work with functions that can legitimately return 0. I'd prefer a function that returns DEFAULT_VAL directly.

Code Snippets

val= call_fn();
val= val != 0 ? val : DEFAULT_VAL;
val = call_fn() || DEFAULT_VAL;

Context

StackExchange Computer Science Q#155125, answer score: 21

Revisions (0)

No revisions yet.