Issue 7046: decimal.py: use DivisionImpossible and DivisionUndefined (original) (raw)

Created on 2009-10-03 13:30 by skrah, last changed 2022-04-11 14:56 by admin. This issue is now closed.

Files
File name Uploaded Description Edit
div-deccheck2.py skrah,2009-10-03 13:30 div-deccheck2.py
Messages (6)
msg93490 - (view) Author: Stefan Krah (skrah) * (Python committer) Date: 2009-10-03 13:30
In many cases, decimal.py sets InvalidOperation instead of DivisionImpossible or DivisionUndefined. Mark, could I persuade you to isolate these cases by running a modified deccheck2.py from mpdecimal (See attachment), which does not suppress differences in the division functions?
msg93496 - (view) Author: Mark Dickinson (mark.dickinson) * (Python committer) Date: 2009-10-03 15:26
Just to be clear, the decimal context doesn't (and shouldn't) know about DivisionImpossible: there's no DivisionImpossible signal or trap described in the specification, but just a DivisionImpossible heading in the 'exceptional conditions' section of the spec. And that DivisionImpossible condition signals InvalidOperation (according to the spec). (And similarly for DivisionUndefined.) So I don't think decimal.py is in violation of the specification here. But decimal.py could be changed so that a call to _raise_error(context, DivisionImpossible, ...) results in the DivisionImpossible exception being raised instead of the InvalidOperation exception. This shouldn't break anything, since DivisionImpossible is a subclass of InvalidOperation. Note that the appropriate sections of decimal.py do already raise the right conditions (unless some have been missed): e.g., in Decimal._divide, we have the lines: # Here the quotient is too large to be representable ans = context._raise_error(DivisionImpossible, 'quotient too large in //, % or divmod') But the Context._raise_error method currently translates all the exceptional conditions to their corresponding signals, hence raises InvalidOperation in this case.
msg93498 - (view) Author: Mark Dickinson (mark.dickinson) * (Python committer) Date: 2009-10-03 15:33
Closed issue 7047 as a duplicate of this one: _raise_error(ConversionSyntax) also raises (if trapped) the InvalidOperation exception, when it could reasonably raise ConversionSyntax instead. It's the same cause as above: _raise_error translates each exceptional condition to the corresponding signal.
msg93509 - (view) Author: Stefan Krah (skrah) * (Python committer) Date: 2009-10-03 22:06
Thanks for the explanation, and I agree that decimal.py is perfectly correct. I based the report on the fact that decNumber updates the context status with e.g. Division_impossible. But Division_impossible is one of the flags that form IEEE_754_Invalid_operation, so presumably the intention is to signal IEEE_754_Invalid_operation by means of flagging Division_impossible. On a side note, I find the distinction between signals and exceptional conditions (mandated by the spec, as you pointed out) needlessly complicated and I'm happy to see that note 5 under "Abstract representation of context" says this might change in the future. I'm all for raising DivisionImpossible, if it is not too much trouble.
msg95789 - (view) Author: Mark Dickinson (mark.dickinson) * (Python committer) Date: 2009-11-28 15:36
I think it's actually easier for the user if we keep the exception type as it is, so that it's clear which flag it corresponds to. This didn't occur to me until I looked at the section of the doctests (around line 100 in decimal.py) that looks like: >>> print c.divide(Decimal(0), Decimal(0)) Traceback (most recent call last): ... ... ... InvalidOperation: 0 / 0 >>> print c.flags[InvalidOperation] 1 If the traceback specified 'DivisionUndefined' instead then the user has to figure out that the corresponding flag/trap is InvalidOperation. Of course this could be worked around by giving a more detailed error message, e.g. DivisionUndefined: (InvalidOperation) 0/0, but this doesn't seem worth changing to me.
msg95835 - (view) Author: Stefan Krah (skrah) * (Python committer) Date: 2009-11-30 12:50
I agree that it might add confusion. In the C-module,I currently do this: >>> Decimal(0) / 0 Traceback (most recent call last): File "", line 1, in cdecimal.InvalidOperation: [<class 'cdecimal.DivisionUndefined'>] But since you already have a detailed error message, this doesn't seem necessary for decimal.py. Close this one?
History
Date User Action Args
2022-04-11 14:56:53 admin set github: 51295
2009-11-30 19:31:24 rhettinger set status: open -> closedresolution: rejected
2009-11-30 12:50:21 skrah set messages: +
2009-11-28 15:36:19 mark.dickinson set messages: +
2009-10-03 22:06:47 skrah set messages: +
2009-10-03 15:33:57 mark.dickinson set priority: normalassignee: mark.dickinsonstage: needs patchtype: behaviorversions: + Python 2.6, Python 3.1, Python 2.7, Python 3.2
2009-10-03 15:33:03 mark.dickinson set messages: +
2009-10-03 15:30:52 mark.dickinson link issue7047 superseder
2009-10-03 15:26:17 mark.dickinson set messages: +
2009-10-03 13:30:55 skrah create