/usr/share/doc/haskell98-report/html/haskell98-report-html/ratio.html is in haskell98-report 20080907-5.
This file is owned by root:root, with mode 0o644.
The actual contents of the file can be viewed below.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 | <title>The Haskell 98 Library Report: Rational Numbers</title>
<body bgcolor="#ffffff"> <i>The Haskell 98 Report</i><br> <a href="index.html">top</a> | <a href="pragmas.html">back</a> | <a href="complex.html">next</a> | <a href="index98.html">contents</a> | <a href="prelude-index.html">function index</a> <br><hr>
<a name="sect12"></a>
<h2>12<tt> </tt>Rational Numbers</h2><p>
<table border=2 cellpadding=3>
<tr><td>
<tt><br>
module Ratio (<br>
Ratio, Rational, (%), numerator, denominator, approxRational ) where<br>
<br>
infixl 7 %<br>
data (Integral a) => Ratio a = ...<br>
type Rational = Ratio Integer<br>
(%) :: (Integral a) => a -> a -> Ratio a<br>
numerator, denominator :: (Integral a) => Ratio a -> a<br>
approxRational :: (RealFrac a) => a -> a -> Rational<br>
instance (Integral a) => Eq (Ratio a) where ...<br>
instance (Integral a) => Ord (Ratio a) where ...<br>
instance (Integral a) => Num (Ratio a) where ...<br>
instance (Integral a) => Real (Ratio a) where ...<br>
instance (Integral a) => Fractional (Ratio a) where ...<br>
instance (Integral a) => RealFrac (Ratio a) where ...<br>
instance (Integral a) => Enum (Ratio a) where ...<br>
instance (Read a,Integral a) => Read (Ratio a) where ...<br>
instance (Integral a) => Show (Ratio a) where ...<br>
<br>
</tt></td></tr></table>
<p>
For each <tt>Integral</tt> type t, there is
a type <tt>Ratio</tt> t of rational pairs with components of
type t. The type name <tt>Rational</tt> is a synonym for
<tt>Ratio Integer</tt>. <p>
<tt>Ratio</tt> is an instance of classes <tt>Eq</tt>, <tt>Ord</tt>, <tt>Num</tt>, <tt>Real</tt>,
<tt>Fractional</tt>, <tt>RealFrac</tt>, <tt>Enum</tt>, <tt>Read</tt>, and <tt>Show</tt>. In each case,
the instance for <tt>Ratio</tt> t simply "lifts" the corresponding operations
over t. If t is a bounded type, the results may be unpredictable;
for example <tt>Ratio Int</tt> may give rise to integer overflow even for
rational numbers of small absolute size.<p>
The operator <tt>(%)</tt> forms the ratio of two
integral numbers, reducing the fraction to terms with no common factor
and such that the denominator is positive. The functions
<tt>numerator
</tt>and <tt>denominator</tt> extract the components of a
ratio; these are in reduced form with a positive denominator.
<tt>Ratio</tt> is an abstract type. For example, <tt>12 % 8</tt> is reduced to 3/2
and <tt>12 % (-8)</tt> is reduced to (-3)/2.<p>
The <tt>approxRational</tt> function, applied to two real fractional numbers
<tt>x</tt> and <tt>epsilon</tt>, returns the simplest rational number within the open
interval <I>(</I><tt>x</tt><I>-</I><tt>epsilon</tt><I>, </I><tt>x</tt><I>+</I><tt>epsilon</tt><I>)</I>.
A rational number <I>n/d</I> in reduced form is said to
be simpler than another <I>n'/d'</I> if <I>|n| <=|n'|</I> and <I>d <=d'</I>.
Note that it can be proved that any real interval contains a unique
simplest rational.<a name="Ratio"></a><p>
<a name="sect12.1"></a>
<h3>12.1<tt> </tt>Library <tt>Ratio</tt></h3>
<tt><br>
-- Standard functions on rational numbers<br>
<br>
module Ratio (<br>
Ratio, Rational, (%), numerator, denominator, approxRational ) where<br>
<br>
infixl 7 %<br>
<br>
ratPrec = 7 :: Int<br>
<br>
data (Integral a) => Ratio a = !a :% !a deriving (Eq)<br>
type Rational = Ratio Integer<br>
<br>
(%) :: (Integral a) => a -> a -> Ratio a<br>
numerator, denominator :: (Integral a) => Ratio a -> a<br>
approxRational :: (RealFrac a) => a -> a -> Rational<br>
<br>
<br>
-- "reduce" is a subsidiary function used only in this module.<br>
-- It normalises a ratio by dividing both numerator<br>
-- and denominator by their greatest common divisor.<br>
--<br>
-- E.g., 12 `reduce` 8 == 3 :% 2<br>
-- 12 `reduce` (-8) == 3 :% (-2)<br>
<br>
reduce _ 0 = error "Ratio.% : zero denominator"<br>
reduce x y = (x `quot` d) :% (y `quot` d)<br>
where d = gcd x y<br>
<br>
x % y = reduce (x * signum y) (abs y)<br>
<br>
numerator (x :% _) = x<br>
<br>
denominator (_ :% y) = y<br>
<br>
<br>
instance (Integral a) => Ord (Ratio a) where<br>
(x:%y) <= (x':%y') = x * y' <= x' * y<br>
(x:%y) < (x':%y') = x * y' < x' * y<br>
<br>
instance (Integral a) => Num (Ratio a) where<br>
(x:%y) + (x':%y') = reduce (x*y' + x'*y) (y*y')<br>
(x:%y) * (x':%y') = reduce (x * x') (y * y')<br>
negate (x:%y) = (-x) :% y<br>
abs (x:%y) = abs x :% y<br>
signum (x:%y) = signum x :% 1<br>
fromInteger x = fromInteger x :% 1<br>
<br>
instance (Integral a) => Real (Ratio a) where<br>
toRational (x:%y) = toInteger x :% toInteger y<br>
<br>
instance (Integral a) => Fractional (Ratio a) where<br>
(x:%y) / (x':%y') = (x*y') % (y*x')<br>
recip (x:%y) = y % x<br>
fromRational (x:%y) = fromInteger x :% fromInteger y<br>
<br>
instance (Integral a) => RealFrac (Ratio a) where<br>
properFraction (x:%y) = (fromIntegral q, r:%y)<br>
where (q,r) = quotRem x y<br>
<br>
instance (Integral a) => Enum (Ratio a) where<br>
succ x = x+1<br>
pred x = x-1<br>
toEnum = fromIntegral<br>
fromEnum = fromInteger . truncate -- May overflow<br>
enumFrom = numericEnumFrom -- These numericEnumXXX functions<br>
enumFromThen = numericEnumFromThen -- are as defined in Prelude.hs<br>
enumFromTo = numericEnumFromTo -- but not exported from it!<br>
enumFromThenTo = numericEnumFromThenTo<br>
<br>
instance (Read a, Integral a) => Read (Ratio a) where<br>
readsPrec p = readParen (p > ratPrec)<br>
(\r -> [(x%y,u) | (x,s) <- readsPrec (ratPrec+1) r,<br>
("%",t) <- lex s,<br>
(y,u) <- readsPrec (ratPrec+1) t ])<br>
<br>
instance (Integral a) => Show (Ratio a) where<br>
showsPrec p (x:%y) = showParen (p > ratPrec)<br>
(showsPrec (ratPrec+1) x . <br>
showString " % " . <br>
showsPrec (ratPrec+1) y)<br>
<br>
<br>
<br>
approxRational x eps = simplest (x-eps) (x+eps)<br>
where simplest x y | y < x = simplest y x<br>
| x == y = xr<br>
| x > 0 = simplest' n d n' d'<br>
| y < 0 = - simplest' (-n') d' (-n) d<br>
| otherwise = 0 :% 1<br>
where xr@(n:%d) = toRational x<br>
(n':%d') = toRational y<br>
<br>
simplest' n d n' d' -- assumes 0 < n%d < n'%d'<br>
| r == 0 = q :% 1<br>
| q /= q' = (q+1) :% 1<br>
| otherwise = (q*n''+d'') :% n''<br>
where (q,r) = quotRem n d<br>
(q',r') = quotRem n' d'<br>
(n'':%d'') = simplest' d' r' d r<br>
<p>
<hr><i>The Haskell 98 Report</i><br><a href="index.html">top</a> | <a href="pragmas.html">back</a> | <a href="complex.html">next</a> | <a href="index98.html">contents</a> | <a href="prelude-index.html">function index</a> <br><font size=2>December 2002</font>
</tt>
|