Skip to content

Commit

Permalink
refactor: Use Stdlib.String(Labels) implementations if available (o…
Browse files Browse the repository at this point in the history
…caml#10825)

This uses a trick to define the fallback functions and overwrite them if they're
available in the included module, otherwise they will be used. Needs to
silence warning 32 but that's a small price to pay to avoid conditional
compilation.

Signed-off-by: Marek Kubica <marek@tarides.com>
  • Loading branch information
Leonidas-from-XIV authored and anmonteiro committed Nov 17, 2024
1 parent 9799585 commit 20f6b48
Show file tree
Hide file tree
Showing 2 changed files with 24 additions and 20 deletions.
40 changes: 22 additions & 18 deletions otherlibs/stdune/src/string.ml
Original file line number Diff line number Diff line change
@@ -1,5 +1,27 @@
(* Because other the syntax s.[x] causes trouble *)
module String = Stdlib.String

module StringLabels = struct
(* functions potentially in the stdlib, depending on OCaml version *)

let[@warning "-32"] exists =
let rec loop s i len f =
if i = len then false else f (String.unsafe_get s i) || loop s (i + 1) len f
in
fun ~f s -> loop s 0 (String.length s) f
;;

let[@warning "-32"] for_all =
let rec loop s i len f =
i = len || (f (String.unsafe_get s i) && loop s (i + 1) len f)
in
fun ~f s -> loop s 0 (String.length s) f
;;

(* overwrite them with stdlib versions if available *)
include Stdlib.StringLabels
end

include StringLabels

let compare a b = Ordering.of_int (String.compare a b)
Expand Down Expand Up @@ -180,18 +202,6 @@ let longest_prefix = function
sub ~pos:0 x ~len:(loop len 0)
;;

let exists =
let rec loop s i len f =
if i = len then false else f (unsafe_get s i) || loop s (i + 1) len f
in
fun s ~f -> loop s 0 (length s) f
;;

let for_all =
let rec loop s i len f = i = len || (f (unsafe_get s i) && loop s (i + 1) len f) in
fun s ~f -> loop s 0 (length s) f
;;

let quoted = Printf.sprintf "%S"

let maybe_quoted s =
Expand Down Expand Up @@ -221,12 +231,6 @@ let enumerate_one_of = function
| s -> "One of " ^ enumerate_or s
;;

let concat ~sep = function
| [] -> ""
| [ x ] -> x
| xs -> concat ~sep xs
;;

let take s len = sub s ~pos:0 ~len:(min (length s) len)

let drop s n =
Expand Down
4 changes: 2 additions & 2 deletions otherlibs/stdune/src/string.mli
Original file line number Diff line number Diff line change
Expand Up @@ -78,8 +78,8 @@ val longest : string list -> int

val longest_map : 'a list -> f:('a -> string) -> int
val longest_prefix : t list -> t
val exists : t -> f:(char -> bool) -> bool
val for_all : t -> f:(char -> bool) -> bool
val exists : f:(char -> bool) -> t -> bool
val for_all : f:(char -> bool) -> t -> bool

(** [maybe_quoted s] is [s] if [s] doesn't need escaping according to OCaml
lexing conventions and [sprintf "%S" s] otherwise.
Expand Down

0 comments on commit 20f6b48

Please sign in to comment.