ocaml-containers/src/core/CCFun.mli
2024-09-10 08:47:46 -04:00

126 lines
4.3 KiB
OCaml

(* This file is free software, part of containers. See file "license" for more details. *)
(** Basic operations on Functions *)
include module type of Fun
(** @inline *)
val and_pred : ('a -> bool) -> ('a -> bool) -> 'a -> bool
(** [and_p f g x] is [(f x) && (g x)].
Produces a predicate which is a conjunction of the two predicates.
@since 3.13.1
*)
val or_pred : ('a -> bool) -> ('a -> bool) -> 'a -> bool
(** [or_p f g x] is [(f x) || (g x)].
Produces a predicate which is a disjunction of the two predicates.
@since 3.13.1
*)
val compose : ('a -> 'b) -> ('b -> 'c) -> 'a -> 'c
(** [compose f g x] is [g (f x)]. Composition. *)
val compose_binop : ('a -> 'b) -> ('b -> 'b -> 'c) -> 'a -> 'a -> 'c
(** [compose_binop f g] is [fun x y -> g (f x) (f y)].
Example (partial order):
[List.sort (compose_binop fst CCInt.compare) [1, true; 2, false; 1, false]].
@since 0.6*)
val curry : ('a * 'b -> 'c) -> 'a -> 'b -> 'c
(** [curry f x y] is [f (x,y)].
Convert a function which accepts a pair of arguments into a function which accepts two arguments. *)
val uncurry : ('a -> 'b -> 'c) -> 'a * 'b -> 'c
(** [uncurry f (x,y)] is [f x y].
Convert a function which accepts a two arguments into a function which accepts a pair of arguments. *)
val tap : ('a -> _) -> 'a -> 'a
(** [tap f x] evaluates [f x], discards it, then returns [x]. Useful
in a pipeline, for instance:
{[CCArray.(1 -- 10)
|> tap CCArray.shuffle
|> tap @@ CCArray.sort Stdlib.compare
]}
*)
val lexicographic : ('a -> 'a -> int) -> ('a -> 'a -> int) -> 'a -> 'a -> int
(** Lexicographic combination of comparison functions. *)
val finally : h:(unit -> _) -> f:(unit -> 'a) -> 'a
(** [finally ~h f] calls [f ()] and returns its result. If it raises, the
same exception is raised; in {b any} case, [h ()] is called after
[f ()] terminates.
If [h ()] raises an exception, then this exception will be passed on and
any exception that may have been raised by [f ()] is lost. *)
val finally1 : h:(unit -> _) -> ('a -> 'b) -> 'a -> 'b
(** [finally1 ~h f x] is the same as [f x], but after the computation,
[h ()] is called whether [f x] rose an exception or not.
If [h ()] raises an exception, then this exception will be passed on and
any exception that may have been raised by [f ()] is lost.
@since 0.16 *)
val finally2 : h:(unit -> _) -> ('a -> 'b -> 'c) -> 'a -> 'b -> 'c
(** [finally2 ~h f x y] is the same as [f x y], but after the computation,
[h ()] is called whether [f x y] rose an exception or not.
If [h ()] raises an exception, then this exception will be passed on and
any exception that may have been raised by [f ()] is lost.
@since 0.16 *)
val opaque_identity : 'a -> 'a
(** [opaque_identity x] is like [x], but prevents Flambda from using [x]'s
definition for optimizing it. (flambda is an optimization/inlining pass
in OCaml >= 4.03).
@since 0.18 *)
val iterate : int -> ('a -> 'a) -> 'a -> 'a
(** [iterate n f] is [f] iterated [n] times. That is to say, [iterate 0 f x] is
[x], [iterate 1 f x] is [f x], [iterate 2 f x] is [f (f x)], etc.
@since 2.1 *)
(** {2 Infix}
Infix operators. *)
module Infix : sig
val ( %> ) : ('a -> 'b) -> ('b -> 'c) -> 'a -> 'c
(** [(f %> g) x] or [(%>) f g x] is [g (f x)]. Alias to [compose]. *)
val ( % ) : ('b -> 'c) -> ('a -> 'b) -> 'a -> 'c
(** [(f % g) x] or [(%) f g x] is [f (g x)]. Mathematical composition. *)
val ( let@ ) : ('a -> 'b) -> 'a -> 'b
(** [let@ x = foo in bar] is the equivalent of [foo @@ fun x -> bar].
It can be very useful for resource management, alongside with {!protect}.
@since 3.11 *)
val ( ||> ) : 'a * 'b -> ('a -> 'b -> 'c) -> 'c
(** [x ||> f] is [f (fst x) (snd x)]
@since 3.13.1 *)
val ( |||> ) : 'a * 'b * 'c -> ('a -> 'b -> 'c -> 'd) -> 'd
(** like [||>] but for tuples of size 3
@since 3.13.1 *)
end
include module type of Infix
(** {2 Monad}
Functions with a fixed domain are monads in their codomain. *)
module Monad (X : sig
type t
end) : sig
type 'a t = X.t -> 'a
(** Definition of a monad in continuation-passing style. *)
val return : 'a -> 'a t
(** Monadic [return]. *)
val ( >|= ) : 'a t -> ('a -> 'b) -> 'b t
(** Monadic [map]. *)
val ( >>= ) : 'a t -> ('a -> 'b t) -> 'b t
(** Monadic [bind]. *)
end