Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Easiest way to truncate float to 2 decimal places?

In Swift, is there a way to truncate a float to 2 decimals, such that you can perform further calculations with it? All of the threads I've seen deal with casting to a string, which I can't figure out how to then use mathematically.

I tried using an extension (found on this forum), figuring I could cast back to float after the truncation, but I end up where I started, with another, non-truncated float. I need my return value to be in quarter steps (i.e. 6.50, 6.75, 5.25, etc), and what I'm ending up with, are results like 6.990022....

There has to be a simple way to do this, but I'm hitting a wall. Thanks in advance...

Here's the issue:

func roundToNearestQuarter(#power : Float) -> String {

     var errorToLowerQuarterRaw : Float = power % 0.25  // 0.210000038146973

     var errorToLowerQuarterString = errorToLowerQuarterStepRaw.string(2)  // "0.21"

     var errorToLowerQuarter = NSString(string: errorToLowerQuaterStepString).floatValue  // 0.209999993443489

// more code

}

roundToNearestQuater(6.71)
like image 785
NoClue Avatar asked Jan 07 '15 20:01

NoClue


People also ask

How do I truncate a float to two decimals?

This is a two step process: Multiply the number by 100 and round the result down to the nearest integer. Divide the result by 100 to round down the float to 2 decimal places.

How do you truncate a number to two decimal places?

To truncate a number to 2 decimal places, miss off all the digits after the second decimal place. To truncate a number to 3 significant figures, miss off all the digits after the first 3 significant figures (the first non-zero digit and the next two digits).

How do I truncate to two decimal places in Excel?

Select the cells that you want to format. On the Home tab, click Increase Decimal or Decrease Decimal to show more or fewer digits after the decimal point.

How do you truncate a floating-point number?

Use the int Function to Truncate a Float in Python The built-in int() function takes a float and converts it to an integer, thereby truncating a float value by removing its decimal places. What is this? The int() function works differently than the round() and floor() function (which you can learn more about here).


2 Answers

You cannot round a Float or Double to 2 decimal digits exactly. The reason is that these data types use a binary floating point representation, and cannot represent numbers like 0.1 or 0.01 exactly. See for example

  • Why Are Floating Point Numbers Inaccurate?
  • What Every Computer Scientist Should Know About Floating-Point Arithmetic

But you said:

I need my return value to be in quarter steps (i.e. 6.50, 6.75, 5.25, etc),

and that is exactly possible because 0.25 = 2-2 can be represented exactly as a floating point number.

The round() function rounds a floating point number to the nearest integral value. To round to the nearest quarter, you just have to "scale" the calculation with the factor 4:

func roundToNearestQuarter(num : Float) -> Float {
    return round(num * 4.0)/4.0
}

roundToNearestQuarter(6.71) // 6.75
roundToNearestQuarter(6.6)  // 6.5
like image 106
Martin R Avatar answered Sep 30 '22 18:09

Martin R


If you need to work with true precision (for currency-related applications, for example), you will probably want to use NSDecimalNumber instead of floating point.

The above approach can be applied to NSDecimalNumbers as shown below. In this example, the "step" that you are rounding to can be anything you choose, just set "increment" accordingly.

let number: NSDecimalNumber = 100.52
let increment: NSDecimalNumber = 0.25

let handler = NSDecimalNumberHandler(roundingMode: NSRoundingMode.RoundBankers, scale: 0, raiseOnExactness: false, raiseOnOverflow: false, raiseOnUnderflow: false, raiseOnDivideByZero: false)     // Rounds to the nearest whole number
let result = number.decimalNumberByDividingBy(increment).decimalNumberByRoundingAccordingToBehavior(handler).decimalNumberByMultiplyingBy(increment)

For more on rounding with NSDecimalNumber see here: How to round an NSDecimalNumber in swift?

And yes, working with NSDecimalNumber is a terribly verbose way to do math, but it's not complicated. If you find yourself doing a project involving them frequently, I recommend you consider setting up Swift operator extensions so you can manipulate them in a more elegant way. Check out here for a nice example: https://gist.github.com/mattt/1ed12090d7c89f36fd28

like image 45
RGood Avatar answered Sep 30 '22 18:09

RGood