Returning int instead of bool can actually make things _less_ efficient

Stewart Gordon smjg_1998 at yahoo.com
Thu Dec 7 09:38:44 PST 2006


There's been quite some debate over the fact that some functions in 
Phobos, including Object.opEquals, have return types of int, even though 
their returns are semantically boolean.

In some instances, it can help, if the efficiency lies in the ability to 
return a value other than 0 or 1 and avoid the overhead of converting 
the value to a boolean.

But in some cases, no efficiency can be gained by this.  Indeed, 
opEquals appears to be a prime example of this.  While a "not equals" 
function can gain efficiency by subtracting one value from the other and 
just returning the result, an "equals" function cannot.

If a function declared with a bool return type tries to return numbers 
other than 0 or 1, then the function must internally convert the value 
to a boolean.  However, if the compiler, while compiling a function 
declared to return bool, discovers that it never tries to return 
anything that isn't 0 or 1 - then there's no point generating the 
conversion code.

Moreover, if the compiler knows that a given variable or subexpression 
is boolean, then I can see a potential for the compiler to use this 
knowledge to optimise certain expressions/code forms.  For example, of 
these, which is more efficient?

b ? 43 : 42   or   42 + b
b ? 64 : 0    or   b << 6
b ? 32 : 16   or   16 << b
!b            or   1 - b
b & c         or   b * c
b & !c        or   b > c
!b | c        or   b <= c

If the compiler knows that b and c are boolean, it could optimise one 
form to the other, whichever is quicker on the processor for which the 
code is being compiled.  The last three could also work with && and ||, 
if the right operand is just a variable or something that can be reduced 
to one at compile-time.

Consider also the bit-twiddling operations common in programs that 
interface certain OS APIs.  Could these be more efficient with the 
optimisation of operations on booleans?  (OK, so _extracting_ a bit is 
an operation that could benefit from the added efficiency of returning 
an int or whatever, but that's aside.)

In both library and application code, there will be some divide between 
programmers who:
(a) have every function with a semantically boolean return value 
returning bool
(b) just use int to pass booleans around, having not got into using bool 
since migrating from C
(c) will consider each function and ask themselves which return type 
will work best from an efficiency POV

Programmers of kind (a), and to some extent (c), will sometimes want to 
make a function X return bool, but find themselves calling a third-party 
function Y that returns an int, albeit with boolean semantics.  If the 
implementation of Y never tries to return anything but 0 or 1, and the 
compiler can readily determine this fact, then nothing has been gained 
by returning an int.  The creator of X will have to either change the 
return type to int, still losing the optimisation potential of booleans 
further up the call stack, or put up with the extra instructions there 
and then to convert the int to a bool.

In conclusion....

If performance is a concern, and a given function could save a few 
instructions by returning a general integer rather than always returning 
0 or 1, then it's quite sensible to return an int.  (For libraries/APIs 
that are likely to have more than one implementation, the question is 
whether an implementation of the given function could feasibly be made 
more efficient in this way - and then if it can, it should.)  If OTOH, 
any feasible implementation would be just as efficient if it returned 
only 0 or 1, then it makes most sense to give it a return type of bool.

Stewart.



More information about the Digitalmars-d mailing list