package ocamlformat-lib
OCaml Code Formatter
Install
Dune Dependency
Authors
Maintainers
Sources
ocamlformat-0.26.1.tbz
sha256=da006e427f15b9ec612fb808d446599bd9b7c3ee25abeb3d555747a70d74c6d7
sha512=b7413f8dc47ba3a2372e89d59cae54f9a602ab81e31cd14ed986a831111080b79a5a3cc45dac04d8ffae5054c35bf29fe9559f145c76c87a30e191ed5400942a
doc/src/ocamlformat-lib/Non_overlapping_interval_tree.ml.html
Source file Non_overlapping_interval_tree.ml
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
(**************************************************************************) (* *) (* OCamlFormat *) (* *) (* Copyright (c) Facebook, Inc. and its affiliates. *) (* *) (* This source code is licensed under the MIT license found in *) (* the LICENSE file in the root directory of this source tree. *) (* *) (**************************************************************************) module type IN = sig include Comparator.S val contains : t -> t -> bool val compare_width_decreasing : t -> t -> int end module type S = sig type itv type t val of_list : itv list -> t (** If there are duplicates in the input list, earlier elements will be ancestors of later elements. *) val roots : t -> itv list val children : t -> itv -> itv list val dump : t -> Fmt.t (** Debug: dump debug representation of tree. *) end module Make (Itv : IN) = struct (* simple but (asymptotically) suboptimal implementation *) type itv = Itv.t type t = {roots: Itv.t list; map: Itv.t list Map.M(Itv).t} let empty = {roots= []; map= Map.empty (module Itv)} let roots t = t.roots let map_add_multi map ~key ~data = Map.update map key ~f:(function None -> [data] | Some l -> data :: l) (** Descend tree from roots, find deepest node that contains elt. *) let rec parents map roots ~ancestors elt = Option.value ~default:ancestors (List.find_map roots ~f:(fun root -> if Itv.contains root elt then let ancestors = root :: ancestors in ( match Map.find map root with | Some children -> parents map children ~ancestors elt | None -> ancestors ) |> Option.some else None ) ) let add_root t root = {t with roots= root :: t.roots} let add_child t ~parent ~child = {t with map= map_add_multi t.map ~key:parent ~data:child} let map_lists ~f {roots; map} = {roots= f roots; map= Map.map map ~f} let rec find_in_previous t elt = function | [] -> parents t.map t.roots elt ~ancestors:[] | p :: ancestors when Itv.contains p elt -> parents t.map [p] elt ~ancestors | _ :: px -> find_in_previous t elt px (** Add elements in decreasing width order to construct tree from roots to leaves. That is, when adding an interval to a partially constructed tree, it will already contain all wider intervals, so the new interval's parent will already be in the tree. *) let of_list elts = let add (prev_ancestor, t) elt = let ancestors = find_in_previous t elt prev_ancestor in let t = match ancestors with | parent :: _ -> add_child t ~parent ~child:elt | [] -> add_root t elt in (ancestors, t) in elts |> List.dedup_and_sort ~compare:Itv.compare_width_decreasing |> List.fold ~init:([], empty) ~f:add |> snd |> map_lists ~f:(List.sort ~compare:Itv.compare_width_decreasing) let children {map; _} elt = Option.value ~default:[] (Map.find map elt) let dump tree = let open Fmt in let rec dump_ tree roots = vbox 0 (list roots "@," (fun root -> let children = children tree root in vbox 1 ( str (Sexp.to_string_hum (Itv.comparator.sexp_of_t root)) $ wrap_if (not (List.is_empty children)) "@,{" " }" (dump_ tree children) ) ) ) in set_margin 100000000 $ dump_ tree tree.roots end
sectionYPositions = computeSectionYPositions($el), 10)"
x-init="setTimeout(() => sectionYPositions = computeSectionYPositions($el), 10)"
>