Std::cout not printing expected float? [duplicate] - c++

This question already has an answer here:
Integer division always zero [duplicate]
(1 answer)
Closed 6 years ago.
This is really basic question, I'm testing std::cout to print float's, the following works correctly:
std::cout<<10 / 3.2<<std::endl; //Output: 3.125
But when I try:
std::cout<< 500000 / 1000000<<std::endl; //Output: 0
Why is the output of my second example not 0.5? Is this automatically rounding down?
I'm compiling with g++ -std=c++14

In your second code example 500000 and 1000000 both have integer type, so, when you divide one to another, you have integer division (the result is rounded bottom), which is 0. To fix this, try multiplying them by 1.0 or casting to any floating-point type.

The compile time evaluable constant expression 500000 / 1000000 will be evaluated in integer arithmetic, which effectively means that any remainder is discarded. (Note that / has higher precedence than << so the division is evaluated first).
A clear rememdy is to promote one of the arguments to floating point (the other one is then promoted automatically by the compiler). I always pick the first one to signal to the reader of your code that you know what you're doing:
500000.0 / 1000000

Related

Why does hardcoded variable (2^62 + 1) subtracted by pow(2, 62) evaluate to 0 instead of 1? [duplicate]

While running the following lines of code:
int i,a;
for(i=0;i<=4;i++)
{
a=pow(10,i);
printf("%d\t",a);
}
I was surprised to see the output, it comes out to be 1 10 99 1000 9999 instead of 1 10 100 1000 10000.
What could be the possible reason?
Note
If you think it's a floating point inaccuracy that in the above for loop when i = 2, the values stored in variable a is 99.
But if you write instead
a=pow(10,2);
now the value of a comes out to be 100. How is that possible?
You have set a to be an int. pow() generates a floating point number, that in SOME cases may be just a hair less than 100 or 10000 (as we see here.)
Then you stuff that into the integer, which TRUNCATES to an integer. So you lose that fractional part. Oops. If you really needed an integer result, round may be a better way to do that operation.
Be careful even there, as for large enough powers, the error may actually be large enough to still cause a failure, giving you something you don't expect. Remember that floating point numbers only carry so much precision.
The function pow() returns a double. You're assigning it to variable a, of type int. Doing that doesn't "round off" the floating point value, it truncates it. So pow() is returning something like 99.99999... for 10^2, and then you're just throwing away the .9999... part. Better to say a = round(pow(10, i)).
This is to do with floating point inaccuracy. Although you are passing in ints they are being implicitly converted to a floating point type since the pow function is only defined for floating point parameters.
Mathematically, the integer power of an integer is an integer.
In a good quality pow() routine this specific calculation should NOT produce any round-off errors. I ran your code on Eclipse/Microsoft C and got the following output:
1 10 100 1000 10000
This test does NOT indicate if Microsoft is using floats and rounding or if they are detecting the type of your numbers and choosing the appropriate method.
So, I ran the following code:
#include <stdio.h>
#include <math.h>
main ()
{
double i,a;
for(i=0.0; i <= 4.0 ;i++)
{
a=pow(10,i);
printf("%lf\t",a);
}
}
And got the following output:
1.000000 10.000000 100.000000 1000.000000 10000.000000
No one spelt out how to actually do it correctly - instead of pow function, just have a variable that tracks the current power:
int i, a, power;
for (i = 0, a = 1; i <= 4; i++, a *= 10) {
printf("%d\t",a);
}
This continuing multiplication by ten is guaranteed to give you the correct answer, and quite OK (and much better than pow, even if it were giving the correct results) for tasks like converting decimal strings into integers.

pow work differently, explain in detail? [duplicate]

This question already has answers here:
Strange behaviour of the pow function
(5 answers)
Closed 5 years ago.
int a=pow(100,2);//line 1
int b=ceil(pow(100,2));//line 2
cout<<pow(100,2);//line 3
line 1 gives a=9999 on printing the value of a
line 2 gives b=10000 on printing value of b
line 3 prints 10000
I understood that pow give value 9999.9999 so ceil func. in line 2 gives it the upper value.
But why didn't cout print 9999.9999
Can anyone explain why pow behave like this return decimal value pow is just a power function why doesn't it simply give 100*100 as answer?
In the cout statement, pow(100, 2) is indeed a double-precision value and slightly below 10000 (by a well-known effect of the pow function), but the default accuracy setting of cout causes rounding and output as an integer.
The reason is due to pow taking two double values as arguments (and returning a double) and is typically implemented such that pow(x, y) is exp(y log x). This "goes off" for even seemingly trivial input values. See Is floating point math broken?
Note that std::pow has overloads for integral types which can be helpful when working in integer arithmetic.

C++ program is rounding by default [duplicate]

This question already has answers here:
Division not outputting correct answer c++
(2 answers)
Closed 7 years ago.
I'm currently working on a C++ program where I have a bankAccount class and I need to calculate interest. Problem is, my function is rounding off my numbers to the whole number, even though I'm using a float as my variable type. So if I had code like this:
float BankAccount::CalculateInterest(int Time)
{
float thing;
thing = (967 / 365);
return thing;
}
thing ends up equaling 2.00000000, when it should equal 2.649315068.
Any ideas? I had my interest equation in there before, and the result was always 1.00000000 no matter what, so I put this in as a test and I saw that it's rounding to the "floor".
Thanks for your help!
It's not rounding.
You are dividing two integers and the result will be an integer.
You can remedy this by simply adding ".0" to both numbers, or explicitly defining them as floats.
967 and 365 are integers, so integer division is used and the remainder discarded. Make one a floating point number and floating point division will be done: 967 / 365.0.
Alternatively:
float thing = 967; // integer converted to float during assignment
thing /= 365; // division of float and converted integer

Why is there no division by zero compile time warning or run time crash in this code? [duplicate]

This question already has answers here:
Divide by zero prevention
(3 answers)
divide by zero - c programming
(3 answers)
Closed 8 years ago.
class Divide
{
public:
float divident, divisor;
Divide():divident(10.0f),divisor(0.0f){}
};
int main()
{
Divide obj[100];
int quotient = obj[1].divident/obj[1].divisor;
return quotient;
}
Edit: Compiler Qt 5.3.1 , Windows 7-32 bit.
Why is there no division by zero warning at compile time or a run time crash happening?
It doesn't crash because you've got a floating-point division by zero, not an integer division by zero. Floating-point division by zero is a valid way to obtain infinity.
The conversion from float to int is undefined, since infinity is not in int's range, so crashing would be allowed there, but that is simply not what typical implementations make it do.
That's quite a code analysis you would be expecting on the part of the compiler in this particular case. I can't think of an existing compiler that would give you that level of analysis. I don't have much more of an answer than that.

C++ integer floor function

I want to implement greatest integer function. [The "greatest integer function" is a quite standard name for what is also known as the floor function.]
int x = 5/3;
My question is with greater numbers could there be a loss of precision as 5/3 would produce a double?
EDIT: Greatest integer function is integer less than or equal to X.
Example:
4.5 = 4
4 = 4
3.2 = 3
3 = 3
What I want to know is 5/3 going to produce a double? Because if so I will have loss of precision when converting to int.
Hope this makes sense.
You will lose the fractional portion of the quotient. So yes, with greater numbers you will have more relative precision, such as compared with 5000/3000.
However, 5 / 3 will return an integer, not a double. To force it to divide as double, typecast the dividend as static_cast<double>(5) / 3.
Integer division gives integer results, so 5 / 3 is 1 and 5 % 3 is 2 (the remainder operator). However, this doesn't necessarily hold with negative numbers. In the original C++ standard, -5 / 3 could be either -1 (rounding towards zero) or -2 (the floor), but -1 was recommended. In the latest C++0B draft (which is almost certainly very close to the final standard), it is -1, so finding the floor with negative numbers is more involved.
5/3 will always produce 1 (an integer), if you do 5.0/3 or 5/3.0 the result will be a double.
As far as I know, there is no predefined function for this purpose.
It might be necessary to use such a function, if for some reason floating-point calculations are out of question (e.g. int64_t has a higher precision than double can represent without error)
We could define this function as follows:
#include <cmath>
inline long
floordiv (long num, long den)
{
if (0 < (num^den))
return num/den;
else
{
ldiv_t res = ldiv(num,den);
return (res.rem)? res.quot-1
: res.quot;
}
}
The idea is to use the normal integer divison, but adjust for negative results to match the behaviour of the double floor(double) function. The point is to truncate always towards the next lower integer, irrespective of the position of the zero point. This can be very important if the intention is to create even sized intervals.
Timing measurements show that this function here only creates a small overhead compared with the built-in / operator, but of course the floating point based floor function is significantly faster....
Since in C and C++, as others have said, / is integer division, it will return an int. in particular, it will return the floor of the double answer... (C and C++ always truncate) So, basically 5/3 is exactly what you want.
It may get a little weird in negatives as -5/3 => -2 which may or may not be what you want...