-
Notifications
You must be signed in to change notification settings - Fork 6.3k
Expand file tree
/
Copy pathIO.java
More file actions
198 lines (184 loc) · 7.78 KB
/
IO.java
File metadata and controls
198 lines (184 loc) · 7.78 KB
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
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
/*
* Copyright (c) 2024, 2025, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation. Oracle designates this
* particular file as subject to the "Classpath" exception as provided
* by Oracle in the LICENSE file that accompanied this code.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.lang;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.IOError;
import java.io.IOException;
import java.nio.charset.Charset;
import java.nio.charset.StandardCharsets;
import jdk.internal.util.StaticProperty;
/**
* A collection of static methods that provide convenient access to {@link System#in}
* and {@link System#out} for line-oriented input and output.
* <p>
* The {@link #readln()} and {@link #readln(String)} methods decode bytes read from
* {@code System.in} into characters. The charset used for decoding is specified by the
* {@link System##stdin.encoding stdin.encoding} property. If this property is not present,
* or if the charset it names cannot be loaded, then UTF-8 is used instead. Decoding
* always replaces malformed and unmappable byte sequences with the charset's default
* replacement string.
* <p>
* Charset decoding is set up upon the first call to one of the {@code readln} methods.
* Decoding may buffer additional bytes beyond those that have been decoded to characters
* returned to the application. After the first call to one of the {@code readln} methods,
* any subsequent use of {@code System.in} results in unspecified behavior.
*
* @apiNote
* The expected use case is that certain applications will use only the {@code readln}
* methods to read from the standard input, and they will not mix these calls with
* other techniques for reading from {@code System.in}.
*
* @since 25
*/
public final class IO {
/*
* We are deliberately not including printf, at least not initially, for
* the following reasons. First, it introduces a rather cryptic and arcane
* formatting language that isn't really suited to beginners. Second, it
* is inherently localizable, which drags in a whole bunch of issues about
* what locale should be used for formatting, the possible inclusion of
* an overload with an explicit Locale parameter, and so forth. These issues
* are best avoided for the time being. Third, when string templates come
* along, they might offer a better alternative to printf-style formatting,
* so it's best not be saddled with this unnecessarily.
*/
/*
* Notes on flushing. We want flushing to occur after every call to println
* and print, so that the user can see output immediately. This could be
* important if the user calls print() to issue a prompt before calling
* readln() instead of the readln(prompt) overload. It's also important to
* flush after print() in case the user is relying on print() to emit output
* as sort of a progress indicator.
*
* We rely on System.out to have autoflush enabled, which flushes after every
* println() call, so we needn't flush again. We flush unconditionally after
* calls to print(). Since System.out is doing a lot of flushing anyway, there
* isn't much point trying to make this conditional, for example, only if
* stdout is connected to a terminal.
*/
private IO() {
throw new Error("no instances");
}
/**
* Writes a string representation of the specified object and then writes
* a line separator to the standard output.
*
* <p> The effect is as if {@link java.io.PrintStream#println(Object) println(obj)}
* had been called on {@code System.out}.
*
* @param obj the object to print, may be {@code null}
*/
public static void println(Object obj) {
System.out.println(obj);
}
/**
* Writes a line separator to the standard output.
*
* <p> The effect is as if {@link java.io.PrintStream#println() println()}
* had been called on {@code System.out}.
*/
public static void println() {
System.out.println();
}
/**
* Writes a string representation of the specified object to the
* standard output.
*
* <p> The effect is as if {@link java.io.PrintStream#print(Object) print(obj)}
* had been called on {@code System.out}.
*
* @param obj the object to print, may be {@code null}
*/
public static void print(Object obj) {
var out = System.out;
out.print(obj);
out.flush();
}
/**
* Reads a single line of text from the standard input.
* <p>
* One line is read from the decoded input as if by
* {@link java.io.BufferedReader#readLine() BufferedReader.readLine()}
* and then the result is returned.
* <p>
* If necessary, this method first sets up charset decoding, as described in
* above in the class specification.
*
* @return a string containing the line read from the standard input, not
* including any line separator characters. Returns {@code null} if an
* end of stream has been reached without having read any characters.
*
* @throws IOError if an I/O error occurs
*/
public static String readln() {
try {
return reader().readLine();
} catch (IOException ioe) {
throw new IOError(ioe);
}
}
/**
* Writes a prompt and then reads a line of input.
* <p>
* Writes a prompt as if by calling {@link #print print}, and then reads a single
* line of text as if by calling {@link #readln() readln}.
* <p>
* If necessary, this method first sets up charset decoding, as described in
* above in the class specification.
*
* @param prompt the prompt string, may be {@code null}
*
* @return a string containing the line read from the standard input, not
* including any line separator characters. Returns {@code null} if an
* end of stream has been reached without having read any characters.
*
* @throws IOError if an I/O error occurs
*/
public static String readln(String prompt) {
print(prompt);
return readln();
}
/**
* The BufferedReader used by readln(). Initialized under a class lock by
* the reader() method. All access should be through the reader() method.
*/
private static BufferedReader br;
/**
* On the first call, creates an InputStreamReader to decode characters from
* System.in, wraps it in a BufferedReader, and returns the BufferedReader.
* These objects are cached and returned by subsequent calls.
*
* @return the internal BufferedReader instance
*/
static synchronized BufferedReader reader() {
if (br == null) {
String enc = StaticProperty.stdinEncoding();
Charset cs = Charset.forName(enc, StandardCharsets.UTF_8);
br = new BufferedReader(new InputStreamReader(System.in, cs));
}
return br;
}
}