package zlist

  1. Overview
  2. Docs
Legend:
Page
Library
Module
Module type
Parameter
Class
Class type
Source

Source file zlist.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
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
(* Copyright 2016 Jesse Haber-Kucharsky *)
(* SPDX-License-Identifier: Apache-2.0 *)

let ( !! ) = Lazy.force

type 'a t = 'a node Lazy.t

and 'a node = Nil | Cons of 'a * 'a t

let rec iter f = function
  | (lazy Nil) -> ()
  | (lazy (Cons (x, t))) -> f x ; iter f t

let pp ~sep pp_item ppf t =
  let is_first = ref true in
  let print ppf v =
    if !is_first then is_first := false else sep ppf () ;
    pp_item ppf v in
  iter (print ppf) t

let rec fold_right f t z =
  match t with
  | (lazy Nil) -> !!z
  | (lazy (Cons (x, t))) -> f x (lazy (fold_right f t z))

let strict t = fold_right (fun x t -> x :: !!t) t (lazy [])
let unit x = lazy (Cons (x, lazy Nil))
let head = function (lazy Nil) -> None | (lazy (Cons (x, _))) -> Some x
let tail = function (lazy Nil) -> lazy Nil | (lazy (Cons (_, t))) -> t
let items xs = List.fold_right (fun x t -> lazy (Cons (x, t))) xs (lazy Nil)

let rec concat t1 t2 =
  match t1 with
  | (lazy Nil) -> t2
  | (lazy (Cons (x, t))) -> lazy (Cons (x, concat t t2))

let rec continually x = lazy (Cons (x, continually x))

let fold_left f z t =
  let rec loop acc = function
    | (lazy Nil) -> acc
    | (lazy (Cons (x, t))) -> loop (f acc x) t in
  loop z t

let rec take n t =
  if n <= 0 then lazy Nil
  else
    match t with
    | (lazy Nil) -> lazy Nil
    | (lazy (Cons (x, t))) -> lazy (Cons (x, take (n - 1) t))

let rec take_while p = function
  | (lazy Nil) -> lazy Nil
  | (lazy (Cons (x, t))) ->
      if p x then lazy (Cons (x, take_while p t)) else lazy Nil

let rec iterate z f = lazy (Cons (z, iterate (f z) f))
let exists f t = fold_right (fun a lb -> f a || !!lb) t (lazy false)

let rec for_all f = function
  | (lazy Nil) -> true
  | (lazy (Cons (x, t))) -> f x && for_all f t

let rec drop n t =
  if n <= 0 then t
  else
    match t with
    | (lazy Nil) -> lazy Nil
    | (lazy (Cons (_, t))) -> drop (n - 1) t

let rec drop_while p = function
  | (lazy Nil) -> lazy Nil
  | (lazy (Cons (x, t))) as tt -> if p x then drop_while p t else tt

let fill n x = continually x |> take n

let rec map f = function
  | (lazy Nil) -> lazy Nil
  | (lazy (Cons (x, t))) -> lazy (Cons (f x, map f t))

let rec zip_with f t1 t2 =
  match (t1, t2) with
  | (lazy Nil), _ | _, (lazy Nil) -> lazy Nil
  | (lazy (Cons (x, t1))), (lazy (Cons (y, t2))) ->
      lazy (Cons (f x y, zip_with f t1 t2))

let zip t1 t2 = zip_with (fun x y -> (x, y)) t1 t2

let flatten t =
  let lazy_concat t lt = fold_right (fun x lt -> lazy (Cons (x, !!lt))) t lt in
  fold_right lazy_concat t (lazy (lazy Nil))

let cycle t = continually t |> flatten

let filter p t =
  fold_right
    (fun x lt -> if p x then lazy (Cons (x, !!lt)) else !!lt)
    t
    (lazy (lazy Nil))

let of_array = function
  | [||] -> lazy Nil
  | arr ->
      let length = Array.length arr in
      let rec loop i =
        if i = length then lazy Nil else lazy (Cons (arr.(i), loop (i + 1)))
      in
      loop 0

let enum_from z = iterate z (fun x -> x + 1)
let enum_from_to low high = enum_from low |> take_while (fun x -> x <= high)

let unfold s f =
  let rec loop s =
    match f s with Some (s, x) -> lazy (Cons (x, loop s)) | None -> lazy Nil
  in
  loop s

let zip_all_with f t1 t2 =
  unfold (t1, t2) (function
    | (lazy Nil), (lazy Nil) -> None
    | (lazy (Cons (x, t1))), (lazy Nil) -> Some ((t1, lazy Nil), f (Some x) None)
    | (lazy Nil), (lazy (Cons (y, t2))) -> Some ((lazy Nil, t2), f None (Some y))
    | (lazy (Cons (x, t1))), (lazy (Cons (y, t2))) ->
        Some ((t1, t2), f (Some x) (Some y)))

let zip_all t1 t2 = zip_all_with (fun x y -> (x, y)) t1 t2

let equal f t1 t2 =
  zip_all_with
    (fun xo yo ->
      match (xo, yo) with
      | Some _, None | None, Some _ -> false
      | Some x, Some y -> f x y
      | None, None -> assert false)
    t1 t2
  |> for_all (fun x -> x)

let rec find p = function
  | (lazy Nil) -> None
  | (lazy (Cons (x, t))) -> if p x then Some x else find p t

let flat_map f t = map f t |> flatten

let map_filter f t =
  fold_right
    (fun x lt ->
      match f x with Some y -> lazy (Cons (y, !!lt)) | None -> !!lt)
    t
    (lazy (lazy Nil))

let length t = fold_left (fun n _ -> n + 1) 0 t
OCaml

Innovation. Community. Security.