Opened 6 years ago

Closed 6 years ago

#12157 closed Bugs (fixed)

Dividing zero by zero produces one in boost::multiprecision::cpp_dec_float

Reported by: vfaion@… Owned by: John Maddock
Milestone: Boost 1.62.0 Component: multiprecision
Version: Boost 1.60.0 Severity: Problem
Keywords: divide Cc:

Description

When using Boost multiprecision, dividing 0/0 produces 1. I would expected the result to be inf. When dividing other numbers by zero it does produce inf.

#include<iostream>
#include<boost/multiprecision/cpp_dec_float.hpp>

typedef boost::multiprecision::number<boost::multiprecision::cpp_dec_float<0>> BigFloat;

int main() {
   BigFloat zero(0);
   BigFloat one(1);
   std::cout << zero / zero << std::endl;
   std::cout << one / zero << std::endl;
}

I looked at operator/ from here: http://www.boost.org/doc/libs/1_60_0/boost/multiprecision/cpp_dec_float.hpp I think adding the case "if(iszero() && v.iszero())" as below could solve this issue.

template <unsigned Digits10, class ExponentType, class Allocator>
cpp_dec_float<Digits10, ExponentType, Allocator>& cpp_dec_float<Digits10, ExponentType, Allocator>::operator/=(const cpp_dec_float<Digits10, ExponentType, Allocator>& v)
{
   if(iszero() && v.iszero())
   {
      *this = inf();
      return *this;
   }

   const bool u_and_v_are_finite_and_identical = ( (isfinite)()
      && (fpclass == v.fpclass)
      && (exp == v.exp)
      && (cmp_data(v.data) == static_cast<boost::int32_t>(0)));

   if(u_and_v_are_finite_and_identical)
   {
      if(neg != v.neg)
      {
         *this = one();
         negate();
      }
      else
         *this = one();
      return *this;
   }
   else
   {
      if(iszero())
      {
         if((v.isnan)() || v.iszero())
         {
            return *this = v;
         }
         return *this;
      }
      cpp_dec_float t(v);
      t.calculate_inv();
      return operator*=(t);
   }
}

Change History (3)

comment:1 by anonymous, 6 years ago

It should be a NaN: 0/0 is undefined.

I'll look into it.

comment:2 by vfaion@…, 6 years ago

Oh I see, well in the case above, maybe just *this = nan() then.

comment:3 by John Maddock, 6 years ago

Milestone: To Be DeterminedBoost 1.62.0
Resolution: fixed
Status: newclosed
Note: See TracTickets for help on using tickets.