What is the return type of any operator ?
How to determine it?
Is it platform dependent ?
This question popped up while I was doing MISRA code compliance for as I was
required to typecast the parameters of the if keyword like this
if((bool_t)(cmd <= 1)){}
to appease lint of the 14.4 MISRA required guideline.
can you point me to some documentation regarding operator return type ?
If anyone can find out the documentation for the return types of the
operators please post it here as it will be of great help for people
referring hereafter.
Return types of operator == in C
... The result has type int
. ... C11dr Equality operators §6.5.9 3
What is the return type of any operator ?
Sometimes it depend on the operator and the operands
a*b --> result type could be `int`, `double`, etc.
Others, it is fixed.
a==b --> result type is `int`.
How to determine it?
By code analysis - you or a static analyzer looks at the code.
At run time, use _Generic()
The following handles many situations.
#define typenameX(X) _Generic((X), \
_Bool: "_Bool", \
signed char: "signed char", \
char: "char", \
unsigned char: "unsigned char", \
short: "short", \
unsigned short: "unsigned short", \
int: "int", \
unsigned: "unsigned", \
long: "long", \
unsigned long: "unsigned long", \
long long: "long long", \
unsigned long long: "unsigned long long", \
float: "float", \
double: "double", \
long double: "long double", \
_Complex float: "_Complex float", \
_Complex double: "_Complex double", \
_Complex long double: "_Complex long double", \
void *: "void *", \
char *: "char *", \
const char *: "const char *", \
default: "other" \
)
int main(void) {
double a = 2.0;
puts(typenameX(a));
puts(typenameX(a==4.0));
short b;
puts(typenameX(b));
puts(typenameX(b*1));
puts(typenameX(sizeof(b)));
double cmd;
puts(typenameX(cmd <= 1));
}
Output
double
int
short
int
unsigned long
int
Is it platform dependent ?
With cmd <= 1
, the return type in C is int
- "platform independent".
The result type of ((int)i) * 123456
is "platform dependent". It could be int
or long
for example.
can you point me to some documentation regarding operator return type ?
In the case of if((bool_t)(cmd <= 1)){}
, the result type of cmd <= 1
is int
. C11 §6.5.8 6. The bool_t
is not needed when compiling in C. Since the result type may differ in other languages (or with a non-compliant C compiler), code that needs to compile in more than one language may benefit by the cast.
The best document regarding operator return type is the (latest) C spec.
The concerns about "required to typecast the parameters of the if
keyword" comes into play in arcane situations. The result of a compare in C is not one of them.
C well defines the result of if(expression)
to be "if the expression compares unequal to 0.". C11dr §6.8.4.1 2
A non-compliant compiler may convert floating-point or a wide integer to an int
first and then test against zero. if((bool_t)x)
fixes that.
unsigned long long w = 0x800000000000u;
if (w) {
double x = 4294967296.0; // 0x1 0000 0000
if (x) {
double y = 0.123;
if (y) {
Handling of NaN is problematic. OTOH, C does not well define how NaN compares to 0. IEEE 758 does well define it and many C implementations follow that. I do not see casting to (bool_t)
helps in this case as it is equally lose concerning NaN.
double z = 0.0/0.0; // z is NaN;
if (z) {
if (!z) {
In early C++, there was no boolean either. A user defined object, (but not double
, float
, pointers), was converted to int
for the if()
. An arithmetic class (e.g. effecting a 256 integer) would have trouble should a non-zero value convert to int 0
. Using !!
solved that.
myint256 a = foo();
if (!!a) {
Note: If a compiler does not have a true boolean type, then (bool_t)
being maybe some integer type, will certainly foul code, much like above.