Round half up Error

I need to round to the nearest whole number so 2.5 should be 3 and 2.4 should be 2. I am trying to use round_half_up to get around the round half even issue. The error I get: conversion from Series to Decimal is not supported. I’m not sure how to make this round correctly.

from decimal import *

getcontext().prec = 1

for i in range(15, df.shape[1],2):  
    df.iloc[:,i+1] = decimal.Decimal(df.iloc[:,i+1])

Why are you using the Decimal module? It’s for fixed-point numbers and it doesn’t support what looks like numpy arrays or pandas dataframes.

Use numpy arrays have a .round method. Use that instead.

Incidentally, Python uses “banker’s rounding”, where you round to the nearest even number. That’s because a half is exactly between two numbers, so always rounding up would lead to a bias.

You say that you are trying to use round_half_up, but the code you show doesn’t use round_half_up anywhere.

By the way, for serious numeric work, you should not use ROUND_HALF_UP, you should use the default rounding mode ROUND_HALF_EVEN as that will reduce the overall rounding errors for most data.

The error is that you are trying to convert a “Series” object, whatever that is, into a Decimal. What’s df?

Can you show us what df.iloc[:,i+1] returns, and what you expect to convert it into?

The error is that you are trying to convert a “Series” object, whatever
that is, into a Decimal. What’s df?

That’ll be a pandas Series object and df is a conventional variable
name for a pandas DataFrame (array of Series instances).

A Series is an indexed array of values, and the numeric ones are
generally numpy arrays underneath.

Can you show us what df.iloc[:,i+1] returns, and what you expect to
convert it into?

See
https://pandas.pydata.org/pandas-docs/stable/reference/api/pandas.DataFrame.iloc.html

Pandas overloads indexing on its arrays to do a variety of funky things
useful in that space.

Cheers,
Cameron Simpson cs@cskk.id.au

If you do in fact need to use round half up for some reason, here’s a way to do it:

from decimal import Decimal, getcontext, ROUND_HALF_UP

getcontext().rounding = ROUND_HALF_UP

for i in range(15, df.shape[1],2): 
    df.iloc[:,i+1] = df.iloc[:,i+1].apply(Decimal).apply(round, ndigits=0)
1 Like

I tried your suggestion and I got this error: “unsupported operand type(s) for -: ‘float’ and ‘decimal.Decimal’”

Again, I am trying to make everything, odd and even numbers, round up if it is x.5 so 2.5 should be 3 and 3.5 should be 4.

I don’t think you got that from the code I posted, since I didn’t do any subtraction.

If you post the actual code that produced the error, we might be able to help.

You can’t mix floats and Decimals in the same operation. You either have to convert your floats to Decimals, or your Decimals to floats.

Using Decimals has the downside that your code will be slower and, perhaps, a tiny bit less accurate in some cases. Using floats has the downside that you can’t control the rounding mode.

Why? That introduces bias into the rounding and makes your final results less accurate.

You are making a massive MASSIVE assumption about the meaning of the numbers involved. Why do you always know better than everyone who posts here? Do you just enjoy telling people how wrong they are?