diff options
Diffstat (limited to 'libraries/base/Data/Function.hs')
-rw-r--r-- | libraries/base/Data/Function.hs | 37 |
1 files changed, 30 insertions, 7 deletions
diff --git a/libraries/base/Data/Function.hs b/libraries/base/Data/Function.hs index c5ded4cda5..7a77160a60 100644 --- a/libraries/base/Data/Function.hs +++ b/libraries/base/Data/Function.hs @@ -32,21 +32,41 @@ infixl 1 & -- | @'fix' f@ is the least fixed point of the function @f@, -- i.e. the least defined @x@ such that @f x = x@. +-- +-- For example, we can write the factorial function using direct recursion as +-- +-- >>> let fac n = if n <= 1 then 1 else n * fac (n-1) in fac 5 +-- 120 +-- +-- This uses the fact that Haskell’s @let@ introduces recursive bindings. We can +-- rewrite this definition using 'fix', +-- +-- >>> fix (\rec n -> if n <= 1 then 1 else n * rec (n-1)) 5 +-- 120 +-- +-- Instead of making a recursive call, we introduce a dummy parameter @rec@; +-- when used within 'fix', this parameter then refers to 'fix' argument, hence +-- the recursion is reintroduced. fix :: (a -> a) -> a fix f = let x = f x in x --- | @(*) \`on\` f = \\x y -> f x * f y@. +-- | @'on' b u x y@ runs the binary function @b@ /on/ the results of applying +-- unary function @u@ to two arguments @x@ and @y@. From the opposite +-- perspective, it transforms two inputs and combines the outputs. +-- +-- @((+) \``on`\` f) x y = f x + f y@ -- --- Typical usage: @'Data.List.sortBy' ('compare' \`on\` 'fst')@. +-- Typical usage: @'Data.List.sortBy' ('Prelude.compare' \`on\` 'Prelude.fst')@. -- -- Algebraic properties: -- --- * @(*) \`on\` 'id' = (*)@ (if @(*) ∉ {⊥, 'const' ⊥}@) +-- * @(*) \`on\` 'id' = (*) -- (if (*) ∉ {⊥, 'const' ⊥})@ -- -- * @((*) \`on\` f) \`on\` g = (*) \`on\` (f . g)@ -- -- * @'flip' on f . 'flip' on g = 'flip' on (g . f)@ - +on :: (b -> b -> c) -> (a -> b) -> a -> a -> c +(.*.) `on` f = \x y -> f x .*. f y -- Proofs (so that I don't have to edit the test-suite): -- (*) `on` id @@ -87,14 +107,17 @@ fix f = let x = f x in x -- = -- flip on (g . f) -on :: (b -> b -> c) -> (a -> b) -> a -> a -> c -(.*.) `on` f = \x y -> f x .*. f y - -- | '&' is a reverse application operator. This provides notational -- convenience. Its precedence is one higher than that of the forward -- application operator '$', which allows '&' to be nested in '$'. -- +-- >>> 5 & (+1) & show +-- "6" +-- -- @since 4.8.0.0 (&) :: a -> (a -> b) -> b x & f = f x + +-- $setup +-- >>> import Prelude |