Question

This is a really simple question. Lets denote the following:

>>> x = 1.2876

Now, round has this great optional second parameter that will round at that decimal place:

>>> round(x,3)
1.288

I was wondering if there is a simple way to round down the numbers. math.floor(x,3) returns an error rather than 1.287

Was it helpful?

Solution 2

This is just something that appeared in my mind. Why don't we convert it to string, and then floor it?

import math
def floor_float(x, index):
    sx = str(x)
    sx = sx[:index]+str(math.floor(float(sx[index]+"."+sx[index+1])))
    return float(sx)

A little advantage is that it's more representating-error-proof, it's more accurate in representating the numbers (since it's a string):

>>> floor_float(10.8976540981, 8)
10.897654

This maybe not the best pythonic solution though.. But it works quite well :)

Update

In Python 2.x, math.floor returns a float instead of integer. To make this work you'll to convert the result, to an integer:

    sx = sx[:index]+str(int(math.floor(float(sx[index]+"."+sx[index+1]))))

Update2

To be honest, the code above is basically nonsense, and too complicated ;)

Since it's flooring, you can just truncate the string, and float it back:

def floor_float(x, i):
    return float(str(x)[:i])

OTHER TIPS

This may be the easiest, if by "rounding down" you mean "toward minus infinity" (as floor() does):

>>> x = 1.2876
>>> x - x % .001
1.287
>>> x = -1.1111
>>> x - x % .001
-1.112

This is prone to lots of shallow surprises, though, due to that most decimal values cannot be exactly represented as binary floating-point values. If those bother you, do something similar with decimal.Decimal values instead.

There's always floor(x*10**3)*10**-3.

Another approach, building on the decimal module's more elaborate facilities. Like the builtin round(), this also supports negative "digits":

>>> round(1234.5, -1) # builtin behavior for negative `ndigits`
1230.0
>>> round(1234.5, -2)
1200.0
>>> round(1234.5, -3)
1000.0

and you can use any of the 8(!) rounding modes defined in decimal.

from decimal import ROUND_DOWN
def rfloat(x, ndigits=0, rounding=ROUND_DOWN):
    from decimal import Decimal as D
    proto = D("1e%d" % -ndigits)
    return float(D(str(x)).quantize(proto, rounding))

Example:

for i in range(-4, 6):
    print i, "->", rfloat(-55555.55555, i)

produces:

-4 -> -50000.0
-3 -> -55000.0
-2 -> -55500.0
-1 -> -55550.0
0 -> -55555.0
1 -> -55555.5
2 -> -55555.55
3 -> -55555.555
4 -> -55555.5555
5 -> -55555.55555

Try to parse strings instead at your own risk ;-)

def roundDown(num, places):
    return int(num*(10**places))/float(10**places)
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top