By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
445,820 Members | 1,142 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 445,820 IT Pros & Developers. It's quick & easy.

rounded to the nth decimal

P: n/a

Hi
how can I return
0.0002 from 0.00015
and
0.0002 from 0.00014

Example:
double myRound(double myNum, int precision);
myRound(0.00015, 4); //should return 0.0002
myRound(0.00014, 4); //should return 0.0001
myRound(0.00015, 3); //should return 0
myRound(0.00015, 5); //should return 0.00015
thanks
Mar 17 '07 #1
Share this Question
Share on Google+
4 Replies


P: n/a
"Gary Wessle" <ph****@yahoo.comwrote in message
news:m3************@localhost.localdomain...
>
Hi
how can I return
0.0002 from 0.00015
and
0.0002 from 0.00014

Example:
double myRound(double myNum, int precision);
myRound(0.00015, 4); //should return 0.0002
myRound(0.00014, 4); //should return 0.0001
myRound(0.00015, 3); //should return 0
myRound(0.00015, 5); //should return 0.00015
thanks
Okay, what you are trying to do is round to the nearerst. One problem you
may run into is that doubles are not exactly precise. That is, 0.00015 may
not be exactly stored as that number. It may be 0.000149999 or something.

Anyway, the way I would do it multiply by 10 for each decimal position, add
..5, take the int, divide by down by 10 for each. Understand? Let me show
you...

Value 0.00015. Mulitply by 10 for each position. Becomes 1.5. Add .5.
Becomes 2.0. Take int. 2. Divide back down Becomes 0.0002.
Value 0.00014. Multiply by 10 for each position. Becomes 1.4 Add .5.
Becomes 1.9. Take int. 1. Divide back down. Becomes 0.0001.

Mulitply b 10 for each postion can be done with the pow fucntion (power).
pow( 10, digits ); It's fairly straight forward but may not always give you
exactly what you want. In which case you may want to add .51 or something
to fudge it.

If you need code to do it let me know, but you should have enough to go on.
There may be an easier way, but this is how I would do it.
Mar 17 '07 #2

P: n/a
On Mar 17, 9:31 am, Gary Wessle <phd...@yahoo.comwrote:
Hi
how can I return
0.0002 from 0.00015
and
0.0002 from 0.00014

Example:
double myRound(double myNum, int precision);
myRound(0.00015, 4); //should return 0.0002
myRound(0.00014, 4); //should return 0.0001
myRound(0.00015, 3); //should return 0
myRound(0.00015, 5); //should return 0.00015
Try:

#include <cmath>

using std::pow;

inline
double myRound( double x, int prec)
{
return x * pow(10, prec) * 1.0/pow(10, prec);
}

The idea here is to use exponential expression to compensate for the
imprecise representation of decimal value. Ideally the difference
between the represented value and the true value should "ping-pong"
around 0 - and not steadily move away from 0 in a constant direction.

Greg

Mar 18 '07 #3

P: n/a
Greg Herlihy wrote:
On Mar 17, 9:31 am, Gary Wessle <phd...@yahoo.comwrote:
>Hi
how can I return
0.0002 from 0.00015
and
0.0002 from 0.00014

Example:
double myRound(double myNum, int precision);
myRound(0.00015, 4); //should return 0.0002
myRound(0.00014, 4); //should return 0.0001
myRound(0.00015, 3); //should return 0
myRound(0.00015, 5); //should return 0.00015

Try:

#include <cmath>

using std::pow;

inline
double myRound( double x, int prec)
{
return x * pow(10, prec) * 1.0/pow(10, prec);
}

The idea here is to use exponential expression to compensate for the
imprecise representation of decimal value. Ideally the difference
between the represented value and the true value should "ping-pong"
around 0 - and not steadily move away from 0 in a constant direction.
Did you try?

#include <cmath>

double myRound( double x, int prec ) {
return x * pow(10, prec) * 1.0/pow(10, prec);
}
#include <iostream>
#include <ostream>
#include <iomanip>

int main ( void ) {
double const high = 0.00015;
double const low = 0.00014;

for ( unsigned prec = 1; prec < 10; ++prec ) {
std::cout << prec << " digits. --";
std::cout << std::setprecision(20)
<< myRound( high, prec )
<< ' ';
std::cout << std::setprecision(20)
<< myRound( low, prec )
<< '\n';
}

}
Output on my machine:

1 digits. --0.00014999999999999998686 0.00013999999999999998774
2 digits. --0.00014999999999999998686 0.00013999999999999998774
3 digits. --0.00014999999999999998686 0.00013999999999999998774
4 digits. --0.00014999999999999998686 0.00013999999999999998774
5 digits. --0.00014999999999999998686 0.00013999999999999998774
6 digits. --0.00014999999999999998686 0.00013999999999999998774
7 digits. --0.00014999999999999998686 0.00013999999999999998774
8 digits. --0.00014999999999999998686 0.00013999999999999998774
9 digits. --0.00014999999999999998686 0.00013999999999999998774

To the OP:

Consider rounding at the time of writing the number to some stream.
std::setprecision is your friend.

What is the reason that you want to round intermediate results?
Best

Kai-Uwe Bux
Mar 18 '07 #4

P: n/a
Jim Langston wrote:
"Gary Wessle" <ph****@yahoo.comwrote in message
news:m3************@localhost.localdomain...
>Hi
how can I return
0.0002 from 0.00015
and
0.0002 from 0.00014

Example:
double myRound(double myNum, int precision);
myRound(0.00015, 4); //should return 0.0002
myRound(0.00014, 4); //should return 0.0001
myRound(0.00015, 3); //should return 0
myRound(0.00015, 5); //should return 0.00015
thanks

Okay, what you are trying to do is round to the nearerst. One problem you
may run into is that doubles are not exactly precise. That is, 0.00015 may
not be exactly stored as that number. It may be 0.000149999 or something.

Anyway, the way I would do it multiply by 10 for each decimal position, add
.5, take the int, divide by down by 10 for each. Understand? Let me show
you...
This won't work for negative values since floats are truncated when
converted to integers. E.g., -0.7 should round to -1 but will, by your
approach, round to 0. For negative values you can either subtract 0.5
instead of adding it, or flip the sign before and after the rounding
operation.
Mar 20 '07 #5

This discussion thread is closed

Replies have been disabled for this discussion.