TimLinden
TimLinden

Reputation: 117

C++ making each decimal in a double into array elements?

(This is for an exercise) I'm trying to create a program that takes a double like 1.2041 and makes each decimal into an element in an array.

Through a loop I want the array to end up like this: ar[0] = 0.2; ar[1] = 0.00; ar[2] = 0.004; ar[3] = 0.0001;

After that I'm going to add the decimals together and end up with 0,2041 but I can't seem to find any way to reach out to each decimal alone.

I tried with multiplying and subtracting but I can't seem to get it to work.

Anyone know a simple way of making each decimal in a double into their own separate elements in an array?

Upvotes: 0

Views: 3123

Answers (2)

Dietmar Kühl
Dietmar Kühl

Reputation: 153840

Unless you are keen to implement Dragon4 (see "How to Print Floating-Point Numbers Accurately" by Guy L.Steele Jr. and Jon L.White) you'd be best off to format the double value into a string, e.g., using std::to_string(), and compute the respective digit value [approximations] from that.

When representing a decimal value with fractional digits in a double which is usually represented using a binary floating point representation the value generally get rounded. For example, it is impossible to exactly represent 0.1 using a double. Instead, the closest representable value will be stored. When using an appropriate algorithm to recover a decimal representation, e.g., Dragon4 or Grisu (where the latter is typically faster but sometimes falls back to Dragon4 as far as I understand it) the original rounding is taken into account. These algorithms are somewhat non-trivial. You can find the source of a variation of Dragon4 in dtoa.c by David Gay. You may want to have a look at more details in the article Here be dragons: advances in problems you didn’t even know you had.

When you use a naive approach trying to deduce each digit you'll get a value but at best you are getting the value actually represented by the double. For example, your value 1.2041 is represented as 1.204099999999999948130380289512686431407928466796875. The easiest way to see how a value is represented is to use the IEEE-754 Analysis: get two analyzers, enter the value into the first one, take the hexadecimal representation (in your case 3FF343FE5C91D14E), and dump it into the second one. It will show the exact decimal value used by the double.

Upvotes: 3

Desaroll
Desaroll

Reputation: 333

If you multiply by 10^n, and turn the result into an int, you'll get the whole number up to the wanted decimal. If you then get the remainder of that number divided with 10, you'll get only the number.

Then, you divide with 10^n and get the decimal:

(double)((int)(number/pow(10,n))%10)/pow(10,n)

That should do the trick.

NOTE: This code requires "math.h", number is the whole number, and n the decimal. n=1 is the first decimal.

Note 2: As Dietmar Kühl noted, this code has problems with the last decimal, as can be seen here: http://ideone.com/xOracn I'm looking for a workaround or a fix.

Upvotes: 1

Related Questions