author | wenzelm |
Fri, 23 May 2008 21:18:47 +0200 | |
changeset 26977 | e736139b553d |
parent 26545 | 6e1aef001b3b |
child 28027 | 051d5ccbafc5 |
permissions | -rw-r--r-- |
6316 | 1 |
(* Title: Pure/General/buffer.ML |
2 |
ID: $Id$ |
|
3 |
Author: Markus Wenzel, TU Muenchen |
|
4 |
||
26502 | 5 |
Efficient text buffers. |
6316 | 6 |
*) |
7 |
||
8 |
signature BUFFER = |
|
9 |
sig |
|
10 |
type T |
|
11 |
val empty: T |
|
12 |
val add: string -> T -> T |
|
26502 | 13 |
val add_substring: substring -> T -> T |
23785 | 14 |
val markup: Markup.T -> (T -> T) -> T -> T |
6316 | 15 |
val content: T -> string |
26545
6e1aef001b3b
output: canonical argument order (as opposed to write);
wenzelm
parents:
26502
diff
changeset
|
16 |
val output: T -> TextIO.outstream -> unit |
6316 | 17 |
val write: Path.T -> T -> unit |
18 |
end; |
|
19 |
||
20 |
structure Buffer: BUFFER = |
|
21 |
struct |
|
22 |
||
26502 | 23 |
(* datatype *) |
24 |
||
25 |
datatype T = |
|
26 |
EmptyBuffer |
|
27 |
| String of string * T |
|
28 |
| Substring of substring * T; |
|
6316 | 29 |
|
26502 | 30 |
val empty = EmptyBuffer; |
31 |
||
17062 | 32 |
|
26502 | 33 |
(* add content *) |
34 |
||
35 |
fun add s buf = if s = "" then buf else String (s, buf); |
|
36 |
fun add_substring s buf = if Substring.isEmpty s then buf else Substring (s, buf); |
|
17062 | 37 |
|
23785 | 38 |
fun markup m body = |
39 |
let val (bg, en) = Markup.output m |
|
40 |
in add bg #> body #> add en end; |
|
41 |
||
26502 | 42 |
|
43 |
(* cumulative content *) |
|
44 |
||
45 |
fun rev_content EmptyBuffer acc = acc |
|
46 |
| rev_content (String (s, buf)) acc = rev_content buf (s :: acc) |
|
47 |
| rev_content (Substring (s, buf)) acc = rev_content buf (Substring.string s :: acc); |
|
48 |
||
49 |
fun content buf = implode (rev_content buf []); |
|
50 |
||
51 |
||
52 |
(* file output *) |
|
17062 | 53 |
|
26502 | 54 |
fun rev_buffer EmptyBuffer acc = acc |
55 |
| rev_buffer (String (s, buf)) acc = rev_buffer buf (String (s, acc)) |
|
56 |
| rev_buffer (Substring (s, buf)) acc = rev_buffer buf (Substring (s, acc)); |
|
6316 | 57 |
|
26545
6e1aef001b3b
output: canonical argument order (as opposed to write);
wenzelm
parents:
26502
diff
changeset
|
58 |
fun output buffer stream = |
26502 | 59 |
let |
60 |
fun rev_output EmptyBuffer = () |
|
61 |
| rev_output (String (s, buf)) = (TextIO.output (stream, s); rev_output buf) |
|
62 |
| rev_output (Substring (s, buf)) = (TextIO.outputSubstr (stream, s); rev_output buf); |
|
63 |
in rev_output (rev_buffer buffer empty) end; |
|
64 |
||
26545
6e1aef001b3b
output: canonical argument order (as opposed to write);
wenzelm
parents:
26502
diff
changeset
|
65 |
fun write path buf = File.open_output (output buf) path; |
21630 | 66 |
|
6316 | 67 |
end; |