I have a dataframe where one of the columns deals with currency displayed in Euros. Due to the rounding issues I want to use the DECIMAL module to have precise arithmetic outcomes.
Python command: 0.1 + 0.2 == 0.3 is FALSE
Decimal module: Decimal(‘0.1’)+Decimal(‘0.2’) == Decimal(‘0.3’) is TRUE (This is the scenario I am looking for)
Steps to reproduce
Code snippet Streamlit:
d = {'name': ["A", "B", "C"], 'amount': [0.1, 0.2, 0.3]}
df = pd.DataFrame(data=d)
st.write(df)
for col in df:
if "amount" in col or "eur" in col:
df[col] = list(df[col])
df[col] = [Decimal(str(round(i,2))) for i in df[col]]
#Output dataframe
st.write(df)
#Testing Condition
st.write(df['amount'][0]+df['amount'][1]==df['amount'][2])
Expected behavior:
Actual behavior:
Amount column is incorrectly displayed at 1, 2 ,3 instead of 0.1, 0.2, 0.3.
Testing condition is correctly represented as true
Please upvote the issue on GitHub if you want our engineers to prioritize a fix.
The only workarounds until the bug is patched are to either:
Cast the column to numpy.float64 with pd.to_numeric ( A possible problem with to_numeric is that since a Decimal number has arbritary precision, it might not be representable by either integer or float types) or
Cast the column to str
Option 1:
d = {"name": ["A", "B", "C"], "amount": [0.1, 0.2, 0.3]}
df = pd.DataFrame(data=d)
st.write(df)
for col in df:
if "amount" in col or "eur" in col:
df[col] = list(df[col])
df[col] = [Decimal(str(round(i, 2))) for i in df[col]]
# Output dataframe
df.amount = df.amount.apply(pd.to_numeric)
st.write(df)
# Testing Condition
st.write(df["amount"][0] + df["amount"][1] == df["amount"][2]) # Evaluates to False
Option 2:
d = {"name": ["A", "B", "C"], "amount": [0.1, 0.2, 0.3]}
df = pd.DataFrame(data=d)
st.write(df)
for col in df:
if "amount" in col or "eur" in col:
df[col] = list(df[col])
df[col] = [Decimal(str(round(i, 2))) for i in df[col]]
# Output dataframe
df.amount = df.amount.apply(str)
st.write(df)
# Testing Condition
st.write(df["amount"][0] + df["amount"][1] == df["amount"][2])
Thanks a lot for the quick reply. I look at the two options that you posted. Unfortunately, the Testing condition would then be False once the value is changed back to numeric or string.
Sorry for the stupid question but I am still new to github. How can I upvote this issue please?
Additionally, you could also add a comment to the bottom of the issue, saying you’re running into the bug and a sentence about why a fix is important for your use case:
Could you use floats and implement your own rounding for the equality test? Since you are working with currencies the floating point error should always be many orders of magnitude smaller than the precision you need.
Thanks for stopping by! We use cookies to help us understand how you interact with our website.
By clicking “Accept all”, you consent to our use of cookies. For more information, please see our privacy policy.
Cookie settings
Strictly necessary cookies
These cookies are necessary for the website to function and cannot be switched off. They are usually only set in response to actions made by you which amount to a request for services, such as setting your privacy preferences, logging in or filling in forms.
Performance cookies
These cookies allow us to count visits and traffic sources so we can measure and improve the performance of our site. They help us understand how visitors move around the site and which pages are most frequently visited.
Functional cookies
These cookies are used to record your choices and settings, maintain your preferences over time and recognize you when you return to our website. These cookies help us to personalize our content for you and remember your preferences.
Targeting cookies
These cookies may be deployed to our site by our advertising partners to build a profile of your interest and provide you with content that is relevant to you, including showing you relevant ads on other websites.