[Haskell-beginners] Ratio data constructor

Bob Ippolito bob at redivi.com
Tue Jul 20 21:36:41 UTC 2021


Yes, the (%) function is a smart constructor for Data.Ratio because the
(:%) constructor is not exported. Other examples of this smart constructor
technique would be modules like Data.Set or Data.Map.

A smart constructor means that the module that defines the type does not
export its data constructor(s), making the implementation details
opaque, generally because the author wanted to be able to make assumptions
about the implementation that are not enforced by the type system. In this
case, they wanted all Ratio to be in reduced form. This makes many
operations faster or trivial, e.g. implementing Eq only requires comparing
the numerators and denominators. More information about the technique is
here: https://wiki.haskell.org/Smart_constructors



On Tue, Jul 20, 2021 at 2:17 PM Galaxy Being <borgauf at gmail.com> wrote:

> ... does the last question have to do with a "smart constructor" by
> chance? If so, how?
>
> On Tue, Jul 20, 2021 at 3:42 PM Galaxy Being <borgauf at gmail.com> wrote:
>
>> I'm investigating rational numbers with Haskell. This is the source I've
>> found
>>
>> data Ratio a = !a :% !a deriving (Eq)
>>
>> reduce ::  (Integral a) => a -> a -> Ratio a
>> {-# SPECIALISE reduce :: Integer -> Integer -> Rational #-}
>> reduce _ 0              =  ratioZeroDenominatorError
>> reduce x y              =  (x `quot` d) :% (y `quot` d)
>>                            where d = gcd x y
>> (%) :: (Integral a) => a -> a -> Ratio a
>> x % y =  reduce (x * signum y) (abs y)
>>
>> The Ratio data type would seem to be a parameterized type with two
>> parameters of the same type that must be "settled" in that they're not to
>> be lazily dealt with. Then the :% is the data constructor, the : meaning
>> it's a data constructor and not just an operation function. So this could
>> have been
>>
>> data Ratio a = :% !a !a deriving (Eq)
>>
>> correct? But then what confuses me is in reduce, why
>>
>> reduce x y  =  (x `quot` d) :% (y `quot` d)
>>
>> and not just %? We have :% defined in the data type and then (%) defined
>> as a function. What is going on here?
>>
>> --
>>>> Lawrence Bottorff
>> Grand Marais, MN, USA
>> borgauf at gmail.com
>>
>
>
> --
>> Lawrence Bottorff
> Grand Marais, MN, USA
> borgauf at gmail.com
> _______________________________________________
> Beginners mailing list
> Beginners at haskell.org
> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.haskell.org/pipermail/beginners/attachments/20210720/c2338c14/attachment.html>


More information about the Beginners mailing list