forked from tensorflow/swift
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathPrinter.swift
116 lines (100 loc) · 3.1 KB
/
Printer.swift
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
// Copyright 2019 The TensorFlow Authors. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
class Printer: CustomStringConvertible {
var description: String = ""
private var indentation: String = ""
private var indented: Bool = false
func indent() {
let count = indentation.count + 2
indentation = String(repeating: " ", count: count)
}
func unindent() {
let count = max(indentation.count - 2, 0)
indentation = String(repeating: " ", count: count)
}
func print<T: CustomStringConvertible>(when: Bool = true, _ i: T) {
print(when: when, i.description)
}
func print(when: Bool = true, _ s: String) {
guard when else { return }
let lines = s.split(omittingEmptySubsequences: false) { $0.isNewline }
for (i, line) in lines.enumerated() {
if !indented && !line.isEmpty {
description += indentation
indented = true
}
description += line
if i < lines.count - 1 {
description += "\n"
indented = false
}
}
}
func print<T>(_ x: T?, _ fn: (T) -> Void) {
guard let x = x else { return }
fn(x)
}
func print<T>(_ pre: String, _ x: T?, _ fn: (T) -> Void) {
guard let x = x else { return }
print(pre)
fn(x)
}
func print<T>(_ x: T?, _ suf: String, _ fn: (T) -> Void) {
guard let x = x else { return }
fn(x)
print(suf)
}
func print<S: Collection>(_ xs: S, _ fn: (S.Element) -> Void) {
for x in xs {
fn(x)
}
}
func print<S: Collection>(_ xs: S, _ sep: String, _ fn: (S.Element) -> Void) {
var needSep = false
for x in xs {
if needSep {
print(sep)
}
needSep = true
fn(x)
}
}
func print<S: Collection>(
whenEmpty: Bool = true, _ pre: String, _ xs: S, _ sep: String, _ suf: String,
_ fn: (S.Element) -> Void
) {
guard !xs.isEmpty || whenEmpty else { return }
print(pre)
print(xs, sep, fn)
print(suf)
}
func literal(_ b: Bool) {
print(String(b))
}
func literal(_ f: Float) {
print(String(f))
}
func literal(_ n: Int) {
print(String(n))
}
func hex(_ n: Int) {
print("0x" + String(format: "%X", n))
}
func literal(_ s: String) {
// TODO(#24): Print string literals with control characters in a useful way.
print("\"")
print(s)
print("\"")
}
}