3

I am currently making an application in Swift 2 for OS X where I have a variable called x, of type double, that I do not know what it is. What I want to do with this variable x is to get the decimal value and store it as an int.

This is what I want to do:

var x:Double = some random value
var xdp:Int = decimal part of x

To make it easier to understand, say my variable x is 72.535, I would want variable xdp to be 535. So far I have been able to x%1 which gives me 0.535 using this example, I could then times that by 1000 which will give me 535 (which is what I want), however if that value was 0.53, I would end up getting 530 which is 10 times bugger then what I want.

How would I be able to get the decimal value using swift 2 for OS X?

Sorry if this is hard to understand, I wasn't sure how to say it. If this is hard to understand, please tell me and I will try my best to re-word it.

iProgram
  • 6,057
  • 9
  • 39
  • 80
  • why do you think that 530 is 10 times bigger? if 535 means 535 thousandths, than 530 means 530 thousandths, so it is correct, isn't it? – user3441734 Mar 22 '16 at 18:00

3 Answers3

2

I would try using a hack like this using String if it's acceptable in your context:

let x:Double = 72.535
var xdp:Int = 0

if let decimalString = String(x).componentsSeparatedByString(".").last, let decimal = Int(decimalString) {
    xdp = decimal   // 535
}

but it's just a trick, so don't forget to check for errors when you use the result.

Eric Aya
  • 69,473
  • 35
  • 181
  • 253
  • What I have done is change it into an extension. I return the decimal value if it is possible, otherwise I return -1, just because it is unlikely that I will get that value (or never). This way if the number is greater than or equal to 0, it is a very strong possibility that it has worked. Is that ok for error checking do you think? – iProgram Oct 28 '15 at 20:38
  • 1
    Making an extension is a good idea. As for the error handling, it depends on how the rest of your code is organized. If this system fits *you*, then it's ok. You could also make `xdp` an Optional. And a lot of other possibilities... – Eric Aya Oct 28 '15 at 20:42
0

The tricky thing here is that doubles can't exactly store most decimal numbers. The short decimals you see are the result of the string converter rounding the number for display. If you want to get the same results you will need some rounding in your code.

The code below is in C (I don't know swift but it should be fairly easy to translate it to most other languages. It should give the result you want in most sensible cases. It assumes int is 32-bit.

double d1 = frac(x);
double d2 = (d1 * 10000000000.0);
if (tempd > 2147483647.0) d2 = d1 * 1000000000.0;
int xdp = (int)round(tempd);
while ((xdp > 0) && ((xdp % 10) == 0)) xdp = xdp /10;
plugwash
  • 9,724
  • 2
  • 38
  • 51
0

your approach seems to be OK

import Darwin

let r0 = 0.750

let f4 = Int(round(r0 % 1 * 4))
print(r0, "is", f4, "quarters")
// 0.75 is 3 quarters

let f1000 = Int(round(r0 % 1 * 1000))
print(r0, "is", f1000, "thousendths")
// 0.75 is 750 thousendths
user3441734
  • 16,722
  • 2
  • 40
  • 59