src/Pure/General/buffer.ML
author wenzelm
Sun, 20 May 2018 15:05:45 +0200
changeset 68228 326f4bcc5abc
parent 60982 67e389f67073
child 70600 6e97e31933a6
permissions -rw-r--r--
more scalable;
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
6316
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
     1
(*  Title:      Pure/General/buffer.ML
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
     2
    Author:     Markus Wenzel, TU Muenchen
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
     3
26502
7f64d8cf6707 added add_substring;
wenzelm
parents: 23785
diff changeset
     4
Efficient text buffers.
6316
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
     5
*)
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
     6
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
     7
signature BUFFER =
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
     8
sig
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
     9
  type T
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
    10
  val empty: T
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
    11
  val add: string -> T -> T
23785
ea7c2ee8a47a added markup operation;
wenzelm
parents: 23226
diff changeset
    12
  val markup: Markup.T -> (T -> T) -> T -> T
6316
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
    13
  val content: T -> string
68228
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    14
  val chunks: T -> string list
60982
67e389f67073 precise BinIO, without newline conversion on Windows;
wenzelm
parents: 29323
diff changeset
    15
  val output: T -> BinIO.outstream -> unit
6316
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
    16
end;
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
    17
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
    18
structure Buffer: BUFFER =
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
    19
struct
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
    20
29323
868634981a32 removed unused add_substring;
wenzelm
parents: 28027
diff changeset
    21
datatype T = Buffer of string list;
6316
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
    22
29323
868634981a32 removed unused add_substring;
wenzelm
parents: 28027
diff changeset
    23
val empty = Buffer [];
17062
7272b45099c7 tuned Buffer.add;
wenzelm
parents: 16712
diff changeset
    24
29323
868634981a32 removed unused add_substring;
wenzelm
parents: 28027
diff changeset
    25
fun add "" buf = buf
868634981a32 removed unused add_substring;
wenzelm
parents: 28027
diff changeset
    26
  | add x (Buffer xs) = Buffer (x :: xs);
17062
7272b45099c7 tuned Buffer.add;
wenzelm
parents: 16712
diff changeset
    27
23785
ea7c2ee8a47a added markup operation;
wenzelm
parents: 23226
diff changeset
    28
fun markup m body =
ea7c2ee8a47a added markup operation;
wenzelm
parents: 23226
diff changeset
    29
  let val (bg, en) = Markup.output m
ea7c2ee8a47a added markup operation;
wenzelm
parents: 23226
diff changeset
    30
  in add bg #> body #> add en end;
ea7c2ee8a47a added markup operation;
wenzelm
parents: 23226
diff changeset
    31
29323
868634981a32 removed unused add_substring;
wenzelm
parents: 28027
diff changeset
    32
fun content (Buffer xs) = implode (rev xs);
60982
67e389f67073 precise BinIO, without newline conversion on Windows;
wenzelm
parents: 29323
diff changeset
    33
68228
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    34
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    35
(* chunks *)
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    36
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    37
local
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    38
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    39
val max_chunk = 4096;
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    40
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    41
fun add_chunk [] res = res
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    42
  | add_chunk chunk res = implode chunk :: res;
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    43
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    44
fun rev_chunks [] _ chunk res = add_chunk chunk res
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    45
  | rev_chunks (x :: xs) len chunk res =
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    46
      let
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    47
        val n = size x;
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    48
        val len' = len + n;
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    49
      in
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    50
        if len' < max_chunk then rev_chunks xs len' (x :: chunk) res
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    51
        else rev_chunks xs n [x] (add_chunk chunk res)
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    52
      end;
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    53
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    54
in
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    55
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    56
fun chunks (Buffer xs) = rev_chunks xs 0 [] [];
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    57
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    58
fun output buf stream =
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    59
  List.app (fn s => BinIO.output (stream, Byte.stringToBytes s)) (chunks buf);
26502
7f64d8cf6707 added add_substring;
wenzelm
parents: 23785
diff changeset
    60
6316
4a786a8a1a97 simple string buffers;
wenzelm
parents:
diff changeset
    61
end;
68228
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    62
326f4bcc5abc more scalable;
wenzelm
parents: 60982
diff changeset
    63
end;