package patricia-tree

  1. Overview
  2. Docs

Parameters

module Key : KEY

Signature

type key = Key.t

The type of keys.

type 'a t

A map from keys to values of type 'a.

module BaseMap : HETEROGENEOUS_MAP with type 'a t = 'a t and type _ key = key and type ('a, 'b) value = ('a, 'b) snd

Underlying basemap, for cross map/set operations

Basice functions

val empty : 'a t

The empty map.

val is_empty : 'a t -> bool

Test if a map is empty; O(1) complexity.

val min_binding : 'a t -> key * 'a

Returns the (key,value) where Key.to_int key is minimal (in unsigned representation of integers); O(log n) complexity.

val max_binding : 'a t -> key * 'a

Returns the (key,value) where Key.to_int key is maximal; O(log n) complexity.

val singleton : key -> 'a -> 'a t

singleton key value creates a map with a single binding, O(1) complexity.

val cardinal : 'a t -> int

The size of the map

val is_singleton : 'a t -> (key * 'a) option

is_singleton m is Some (k,v) iff m is singleton k v

val find : key -> 'a t -> 'a

Return an element in the map, or raise Not_found, O(log(n)) complexity.

val find_opt : key -> 'a t -> 'a option

Return an element in the map, or None, O(log(n)) complexity.

val mem : key -> 'a t -> bool

mem key map returns true iff key is bound in map, O(log(n)) complexity.

val remove : key -> 'a t -> 'a t

Returns a map with the element removed, O(log(n)) complexity. Returns a physically equal map if the element is absent.

val pop_minimum : 'a t -> (key * 'a * 'a t) option

pop_minimum m returns None if is_empty m, or Some(key,value,m') where (key,value) = min_binding m and m' = remove m key. O(log(n)) complexity.

val pop_maximum : 'a t -> (key * 'a * 'a t) option

pop_maximum m returns None if is_empty m, or Some(key,value,m') where (key,value) = max_binding m and m' = remove m key. O(log(n)) complexity.

val insert : key -> ('a option -> 'a) -> 'a t -> 'a t

insert key f map modifies or insert an element of the map; f takes None if the value was not previously bound, and Some old where old is the previously bound value otherwise. The function preserves physical equality when possible. O(log(n)) complexity. Preserves physical equality if the new value is physically equal to the old.

val update : key -> ('a option -> 'a option) -> 'a t -> 'a t

update key f map modifies, insert, or remove an element from the map; f takes None if the value was not previously bound, and Some old where old is the previously bound value otherwise. The function preserves physical equality when possible. It returns None if the element should be removed O(log(n)) complexity. Preserves physical equality if the new value is physically equal to the old.

val add : key -> 'a -> 'a t -> 'a t

Unconditionally adds a value in the map (independently from whether the old value existed). O(log(n)) complexity. Preserves physical equality if the new value is physically equal to the old.

Iterators

val split : key -> 'a t -> 'a t * 'a option * 'a t

split key map splits the map into:

  • submap of map whose keys are smaller than key
  • value associated to key (if present)
  • submap of map whose keys are bigger than key Where the order is given by Key.to_int.
val iter : (key -> 'a -> unit) -> 'a t -> unit

Iterate on each (key,value) pair of the map, in increasing order of keys.

val fold : (key -> 'a -> 'acc -> 'acc) -> 'a t -> 'acc -> 'acc

Fold on each (key,value) pair of the map, in increasing order of keys.

val filter : (key -> 'a -> bool) -> 'a t -> 'a t

Returns the submap containing only the key->value pairs satisfying the given predicate. f is called in increasing number of keys

val for_all : (key -> 'a -> bool) -> 'a t -> bool

Returns true if the predicate holds on all map bindings. Short-circuiting

In the following, the *no_share function allows taking arguments of different types (but cannot share subtrees of the map), while the default functions attempt to preserve and benefit from sharing the subtrees (using physical equality to detect sharing).

val map : ('a -> 'a) -> 'a t -> 'a t

map f m returns a map where the value bound to each key is replaced by f value. The subtrees for which the returned value is physically the same (i.e. f key value == value for all the keys in the subtree) are guaranteed to be physically equal to the original subtree. O(n) complexity. f is called in increasing order of keys.

val map_no_share : ('a -> 'b) -> 'a t -> 'b t

map_no_share f m returns a map where the value bound to each key is replaced by f value. O(n) complexity. f is called in increasing order of keys.

val mapi : (key -> 'a -> 'a) -> 'a t -> 'a t

mapi f m returns a map where the value bound to each key is replaced by f key value. The subtrees for which the returned value is physically the same (i.e. f key value == value for all the keys in the subtree) are guaranteed to be physically equal to the original subtree. O(n) complexity. f is called in increasing order of keys.

val mapi_no_share : (key -> 'a -> 'b) -> 'a t -> 'b t

mapi_no_share f m returns a map where the value bound to each key is replaced by f key value. O(n) complexity. f is called in increasing order of keys.

val filter_map : (key -> 'a -> 'a option) -> 'a t -> 'a t

filter_map m f returns a map where the value bound to each key is removed (if f key value returns None), or is replaced by v ((if f key value returns Some v). The subtrees for which the returned value is physically the same (i.e. f key value = Some v with value == v for all the keys in the subtree) are guaranteed to be physically equal to the original subtree. O(n) complexity. f is called in increasing order of keys.

val filter_map_no_share : (key -> 'a -> 'b option) -> 'a t -> 'b t

filter_map m f returns a map where the value bound to each key is removed (if f key value returns None), or is replaced by v ((if f key value returns Some v). O(n) complexity. f is called in increasing order of keys.

Operations on pairs of maps

The following functions combine two maps. It is key for the performance, when we have large maps who share common subtrees, not to visit the nodes in these subtrees. Hence, we have specialized versions of these functions that assume properties of the function parameter (reflexive relation, idempotent operation, etc.)

When we cannot enjoy these properties, our functions explicitly say so (with a nonreflexive or nonidempotent prefix). The names are a bit long, but having these names avoids using an ineffective code by default, by forcing to know and choose between the fast and slow version.

It is also important to not visit a subtree when there merging this subtree with Empty; hence we provide union and inter operations.

val reflexive_same_domain_for_all2 : (key -> 'a -> 'a -> bool) -> 'a t -> 'a t -> bool

reflexive_same_domain_for_all2 f map1 map2 returns true if map1 and map2 have the same keys, and f key value1 value2 returns true for each mapping pair of keys. We assume that f is reflexive (i.e. f key value value returns true) to avoid visiting physically equal subtrees of map1 and map2. The complexity is O(log(n)*Delta) where Delta is the number of different keys between map1 and map2.

val nonreflexive_same_domain_for_all2 : (key -> 'a -> 'b -> bool) -> 'a t -> 'b t -> bool

nonreflexive_same_domain_for_all2 f map1 map2 returns true if map1 and map2 have the same keys, and f key value1 value2 returns true for each mapping pair of keys. The complexity is O(min(|map1|,|map2|)).

val reflexive_subset_domain_for_all2 : (key -> 'a -> 'a -> bool) -> 'a t -> 'a t -> bool

reflexive_subset_domain_for_all2 f map1 map2 returns true if all the keys of map1 also are in map2, and f key (find map1 key) (find map2 key) returns true when both keys are present in the map. We assume that f is reflexive (i.e. f key value value returns true) to avoid visiting physically equal subtrees of map1 and map2. The complexity is O(log(n)*Delta) where Delta is the number of different keys between map1 and map2.

val idempotent_union : (key -> 'a -> 'a -> 'a) -> 'a t -> 'a t -> 'a t

idempotent_union f map1 map2 returns a map whose keys is the union of the keys of map1 and map2. f is used to combine the values a key is mapped in both maps. We assume that f is idempotent (i.e. f key value value == value) to avoid visiting physically equal subtrees of map1 and map2, and also to preserve physical equality of the subtreess in that case. The complexity is O(log(n)*Delta) where Delta is the number of different keys between map1 and map2. f is called in increasing order of keys. f is never called on physically equal values.

val idempotent_inter : (key -> 'a -> 'a -> 'a) -> 'a t -> 'a t -> 'a t

idempotent_inter f map1 map2 returns a map whose keys is the intersection of the keys of map1 and map2. f is used to combine the values a key is mapped in both maps. We assume that f is idempotent (i.e. f key value value == value) to avoid visiting physically equal subtrees of map1 and map2, and also to preserve physical equality of the subtrees in that case. The complexity is O(log(n)*Delta) where Delta is the number of different keys between map1 and map2. f is called in increasing order of keys. f is never called on physically equal values.

val nonidempotent_inter_no_share : (key -> 'a -> 'b -> 'c) -> 'a t -> 'b t -> 'c t

nonidempotent_inter_no_share f map1 map2 returns a map whose keys is the intersection of the keys of map1 and map2. f is used to combine the values a key is mapped in both maps. f does not need to be idempotent, which imply that we have to visit physically equal subtrees of map1 and map2. The complexity is O(log(n)*min(|map1|,|map2|)). f is called in increasing order of keys. f is called on every shared binding.

val idempotent_inter_filter : (key -> 'a -> 'a -> 'a option) -> 'a t -> 'a t -> 'a t

idempotent_inter_filter f m1 m2 is like idempotent_inter f m1 m2 (assuming idempotence, using and preserving physically equal subtrees), but it also removes the key->value bindings for which f returns None.

val slow_merge : (key -> 'a option -> 'b option -> 'c option) -> 'a t -> 'b t -> 'c t

slow_merge f m1 m2 returns a map whose keys are a subset of the keys of m1 and m2. The f function is used to combine keys, similarly to the Map.merge function. This funcion has to traverse all the bindings in m1 and m2; its complexity is O(|m1|+|m2|). Use one of faster functions above if you can.

val disjoint : 'a t -> 'a t -> bool
module WithForeign (Map2 : BASE_MAP with type _ key = key) : sig ... end

Combination with other kinds of maps.

val pretty : ?pp_sep:(Format.formatter -> unit -> unit) -> (Format.formatter -> key -> 'a -> unit) -> Format.formatter -> 'a t -> unit

Pretty prints all bindings of the map. pp_sep is called once between each binding pair and defaults to Format.pp_print_cut.

Conversion functions

val to_seq : 'a t -> (key * 'a) Seq.t

to_seq m iterates the whole map, in increasing order of Key.to_int

val to_rev_seq : 'a t -> (key * 'a) Seq.t

to_rev_seq m iterates the whole map, in decreasing order of Key.to_int

val add_seq : (key * 'a) Seq.t -> 'a t -> 'a t

add_seq s m adds all bindings of the sequence s to m in order.

val of_seq : (key * 'a) Seq.t -> 'a t

of_seq s creates a new map from the bindings of s. If a key is bound multiple times in s, the latest binding is kept

val of_list : (key * 'a) list -> 'a t

of_list l creates a new map from the bindings of l. If a key is bound multiple times in l, the latest binding is kept

val to_list : 'a t -> (key * 'a) list

to_list m returns the bindings of m as a list, in increasing order of Key.to_int

OCaml

Innovation. Community. Security.