简体   繁体   中英

Why does C assume integer type within a calculation for a double?

I was trying to plot a function in GNU plot, and my plot kept differing from the one in the paper. Upon reading that GNU interprets functions as C would, I tried coding the function in C. Same problem.

Eventually I figured out the problem could be exhibited with this tidbit:

#include <stdio.h>
#include <stdlib.h>

int main()
{
double p = 1.0;
double pMinusOneHalf1 = p - (1.0/2.0);
double pMinusOneHalf2 = p - (1/2);

printf("\nFirst = %lf \n Second = %lf\n\n", pMinusOneHalf1, pMinusOneHalf2);

return 0;
}

which gives output

First = 0.500000 
Second = 1.000000

Just wondering if anyone has an explanation as to why C would assume "1" and "2" as INTs inside of the expression for a DOUBLE.

Seems like a very easy thing for people to get caught on. gcc's -Wall option doesn't even comment on it.

/ doesn't particularly care that its result is being subtracted from a double .

All it knows is that it's given two integers, so it gives you back an integer.

Why don't they do it?

They assume that a user who programs an INT/INT will know what s/he is doing, and not second-guess her/him. What if you wanted an integer divide? Are you going to force the user to use additional notation? Seems easy enough to me to let expressions evaluate locally according to the defined behavior, rather than trying to guess what the user wants. Otherwise, gcc could just guess about where you meant to insert semicolons, and do that for you as well.

The brackets cause division of two integers before involving the double. Removing the brackets wouldn't work because the division has precedence over the subtraction.

You expression gets evaluated in the order you tell it to. In this case division has higher precedence than subtraction (parenthesis around the division or not). So the first part of the equation that gets evaluated is 1/2 . As you know 1/2 is 0 in integer arithmetic. Then the expression becomes (1.0-0) which converts the result to a double, but the result of 1.0-0 is 1.0 .

The integer constants 1 and 2 are of type int (as is any decimal integer constant whose value doesn't exceed INT_MAX).

In most cases, the type of a C expression is determined entirely by the expression itself, not by the context in which it appears. (1/2) is an expression of type int with the value 0; the fact that it's subtracted from an expression of type double doesn't change that.

C could have been defined differently, so that integer subexpressions inherit some kind of floating-point context from any expressions in which they appear. The existing rules, though they can lead to some seemingly counter-intuitive results, are actually simpler to understand. (They're also probably simpler to implement in a compiler, something that was quite important back in the 1970s when the first C compilers were being written.)

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM