Simon Peyton-Jones wrote:
Folks
The concrete is setting fast, but Ross points out that the instance for Enum (Ratio a) is inconsistent with that for Enum Float and Enum Double. (It's strange that these non-integral types are in Enum, but we're stuck with that.)
All three use 'numericEnumFrom' etc for the enumFrom method, but Float and Double define succ and pred thus:
instance Enum Float where succ x = x+1 pred x = x-1
But Ratio does not... it uses the default method for succ/pred which gives
instance Integral a => Enum (Ratio a) where succ x = fromInt (1 + (toInt x))
Thus (succ (1.5 :: Float)) is 2.5 but (succ (3%2)) is 2%1
Furthermore, you'd expect that [x..y] would mean the same as [x,succ x .. y] and that is true for Float/Double but not for Ratio.
So I propose to modify the instance decl for Ratio by adding explicit defns for succ/pred just like those in Float/Double.
Any objections?
Simon
No objection, but here are additional related corrections to be made: (1) In section A (Standard Prelude), in the definition of `numericEnumFromThenTo`, change "n' > n" to "n' >= n", to agree with the last bullet in section 6.3.4. That is, the function definition should read: numericEnumFromThenTo n n' m = takeWhile p (numericEnumFromThen n n') where p | n' >= n = (<= m + (n'-n)/2) | otherwise = (>= m + (n'-n)/2) (2) In section 3.10, change "which Prelude type are in Enum" to "which Prelude types are in Enum". -- Dean