double to int, a bit confused...

S

Simon

Hi all

I am writing a small app that uses real numbers all over the place for
calculations.

But when it comes to displaying values it is better to only display an it,
(especially when it comes to % values and so on).

so I first thought that the best way would be...
....

double x = 1.23456789012345;
int y = (int)x;

but that does not always work, in fact when the double has a lot of decimal
places I get a rather nasty looking number.
I am assuming that the casting could get it wrong if there are too many
decimal places.

so I thought I'd use the ceil(...); and floor(...); functions
....
y = (x>=0)?(int((floor(x))) : (int(ceil(x))));

the logic been that the decimal places are removed by both functions and the
casting then works just fine.

but that raises a few questions.

Why does the cast not work some times? is the floor/ceil method "guaranteed"
to work? What would be the preferred/best method?

Many thanks in advance.

Simon
 
V

Vladimir Ciobanu

Simon said:
Hi all

I am writing a small app that uses real numbers all over the place
for
calculations.

But when it comes to displaying values it is better to only display
an it,
(especially when it comes to % values and so on).

so I first thought that the best way would be...
...

double x = 1.23456789012345;
int y = (int)x;

but that does not always work, in fact when the double has a lot of
decimal
places I get a rather nasty looking number.
I am assuming that the casting could get it wrong if there are too
many
decimal places.

so I thought I'd use the ceil(...); and floor(...); functions
...
y = (x>=0)?(int((floor(x))) : (int(ceil(x))));

the logic been that the decimal places are removed by both functions
and the
casting then works just fine.

but that raises a few questions.

Why does the cast not work some times? is the floor/ceil method
"guaranteed"
to work? What would be the preferred/best method?

The C++ Standard, 4.9[1] says that a rvalue of a floating point type
can be converted
to a rvalue of an integral type by truncating (discarding the
fractional part). However,
as expected, if the truncated value cannot be represented in the
integral type, the
behavior is undefined.

Are you getting abnormal results when using very large double values ?
Also, why are you
using C-style casts ? It is preferred to use the C++ casts:

double x = 1.234;
int y = static_cast<int>(x);

Have you tested the code with other compilers ?

Vladimir Ciobanu
 
I

Ivan Vecerina

Simon said:
I am writing a small app that uses real numbers all over the place for
calculations.

But when it comes to displaying values it is better to only display an it,
(especially when it comes to % values and so on).

so I first thought that the best way would be...
...

double x = 1.23456789012345;
int y = (int)x;

but that does not always work, in fact when the double has a lot of
decimal
places I get a rather nasty looking number.

Could you provide actual examples of these "nasty looking" numbers ?
One thing that might be happening is that the number is too large
to be stored in an int...
I am assuming that the casting could get it wrong if there are too many
decimal places.

so I thought I'd use the ceil(...); and floor(...); functions
...
y = (x>=0)?(int((floor(x))) : (int(ceil(x))));

the logic been that the decimal places are removed by both functions and
the
casting then works just fine.

but that raises a few questions.

Why does the cast not work some times? is the floor/ceil method
"guaranteed"
to work? What would be the preferred/best method?
floor/ceil will work, but if the number is beyond the range of int,
the same problem will occur when the conversion is made.

This said, if you are only performing these conversions for
display purposes, it may be possible to specify the format for
the output of the double value instead of converting to an int.
Consider for example:

using namespace std; //after include <iostream> <iomanip> <cstdio>

double d = 12.3456;

cout << setprecision(0) << setiosflags(ios_base::fixed) << d << endl;


printf("%.0f\n",d); // if you still prefer c-style output


hth,
Ivan
 
G

Gary Labowitz

Simon said:
Hi all

I am writing a small app that uses real numbers all over the place for
calculations.

But when it comes to displaying values it is better to only display an it,
(especially when it comes to % values and so on).

so I first thought that the best way would be...
...

double x = 1.23456789012345;
int y = (int)x;

but that does not always work, in fact when the double has a lot of decimal
places I get a rather nasty looking number.

1. How do you know it isn't working?
2. It works fine with g++
3. Post a complete, small program that shows the symptom (example below) and
we'll look at it further.
#include <iostream>
int main( )
{
double x = 1.23456789012345;
int y = (int)x;
std::cout << x << ":" << y << std::endl;

return 0;
}
 
S

Simon

1. How do you know it isn't working?

I could see it. :).
2. It works fine with g++

I am using VC6++, on windows XP. (I know everybody has strong feeling about
MS products but that's not the point here I hope).
3. Post a complete, small program that shows the symptom (example below)
and we'll look at it further.

Well, it seems to work fine on my XP pro machine.
Before I have to totally bury my head in shame, I will try and look at more
windows machine. The problem was reported on a Win98SE machine.

I guess I'll also need to look if I am not trying to work with doubles that
are out of int range.

Regards

Simon
 
S

Simon

The C++ Standard, 4.9[1] says that a rvalue of a floating point type
can be converted
to a rvalue of an integral type by truncating (discarding the
fractional part). However,
as expected, if the truncated value cannot be represented in the
integral type, the
behavior is undefined.

Sorry, can I be rude and ask to see that section of the standard?

Simon
 
V

Vladimir Ciobanu

Simon said:
The C++ Standard, 4.9[1] says that a rvalue of a floating point
type
can be converted
to a rvalue of an integral type by truncating (discarding the
fractional part). However,
as expected, if the truncated value cannot be represented in the
integral type, the
behavior is undefined.

Sorry, can I be rude and ask to see that section of the standard?

Yes. Here it is:
4.9[1]: "An rvalue of a floating point type can be converted to an
rvalue of an integer type. The conversion truncates; that is, the
fractional part is discarded. The behavior is undefined if the
truncated value cannot be represented in the destination type."

Vladimir Ciobanu
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,768
Messages
2,569,574
Members
45,048
Latest member
verona

Latest Threads

Top