The Java Tutorials have been written for JDK 8.Java教程是为JDK 8编写的。Examples and practices described in this page don't take advantage of improvements introduced in later releases and might use technology no longer available.本页中描述的示例和实践没有利用后续版本中引入的改进,并且可能使用不再可用的技术。See Java Language Changes for a summary of updated language features in Java SE 9 and subsequent releases.有关Java SE 9及其后续版本中更新的语言特性的摘要,请参阅Java语言更改。
See JDK Release Notes for information about new features, enhancements, and removed or deprecated options for all JDK releases.有关所有JDK版本的新功能、增强功能以及已删除或不推荐的选项的信息,请参阅JDK发行说明。
This page discusses the details of reading, writing, creating, and opening files. 本页讨论读取、写入、创建和打开文件的详细信息。There are a wide array of file I/O methods to choose from. 有许多文件I/O方法可供选择。To help make sense of the API, the following diagram arranges the file I/O methods by complexity.为了帮助理解API,下图按复杂性排列了文件I/O方法。
On the far left of the diagram are the utility methods 图的最左边是实用程序方法readAllBytes
, readAllLines
, and the write
methods, designed for simple, common cases. readAllBytes
、readAllLines
和write
方法,它们是为简单、常见的情况设计的。To the right of those are the methods used to iterate over a stream or lines of text, such as 在这些方法的右边是用于迭代一个或多个文本行的方法,例如newBufferedReader
, newBufferedWriter
, then newInputStream
and newOutputStream
. newBufferedWriter
、newBufferedWriter
、newInputStream
和newOutputStream
。These methods are interoperable with the 这些方法可以与java.io
package. java.io
包进行互操作。To the right of those are the methods for dealing with 右边是处理ByteChannels
, SeekableByteChannels
, and ByteBuffers
, such as the newByteChannel
method. ByteChannels
、SeekableByteChannels
和ByteBuffers
的方法,如newByteChannel
方法。Finally, on the far right are the methods that use 最后,最右边是使用FileChannel
for advanced applications needing file locking or memory-mapped I/O.FileChannel
的方法,用于需要文件锁定或内存映射I/O的高级应用程序。
This page has the following topics:此页面包含以下主题:
OpenOptions
ParameterOpenOptions
参数java.io
APIsjava.io
API互操作的方法ByteBuffers
ByteBuffers
的方法OpenOptions
ParameterOpenOptions
参数Several of the methods in this section take an optional 本节中的几个方法采用可选的OpenOptions
parameter. OpenOptions
参数。This parameter is optional and the API tells you what the default behavior is for the method when none is specified.此参数是可选的,API会告诉您在未指定任何参数时方法的默认行为。
The following 支持以下StandardOpenOptions
enums are supported:StandardOpenOptions
枚举:
WRITE
– APPEND
– WRITE
or CREATE
options.WRITE
或CREATE
选项一起使用。TRUNCATE_EXISTING
– WRITE
option.WRITE
选项一起使用。CREATE_NEW
– CREATE
– DELETE_ON_CLOSE
– SPARSE
– SYNC
– DSYNC
– If you have a small-ish file and you would like to read its entire contents in one pass, you can use the 如果您有一个小ish文件,并且希望一次性读取其全部内容,则可以使用readAllBytes(Path)
or readAllLines(Path, Charset)
method. readAllBytes(Path)
方法或readAllLines(Path, Charset)
方法。These methods take care of most of the work for you, such as opening and closing the stream, but are not intended for handling large files. 这些方法负责您的大部分工作,例如打开和关闭流,但不用于处理大型文件。The following code shows how to use the 以下代码显示了如何使用readAllBytes
method:readAllBytes
方法:
Path file = ...; byte[] fileArray; fileArray = Files.readAllBytes(file);
You can use one of the write methods to write bytes, or lines, to a file.可以使用其中一种写入方法将字节或行写入文件。
write(Path, byte[], OpenOption...)
write(Path, Iterable< extends CharSequence>, Charset, OpenOption...)
The following code snippet shows how to use a 下面的代码片段显示了如何使用write
method.write
方法。
Path file = ...; byte[] buf = ...; Files.write(file, buf);
The java.nio.file
package supports channel I/O, which moves data in buffers, bypassing some of the layers that can bottleneck stream I/O.java.nio.file
包支持通道I/O,它在缓冲区中移动数据,绕过一些可能导致流I/O瓶颈的层。
The newBufferedReader(Path, Charset)
method opens a file for reading, returning a BufferedReader
that can be used to read text from a file in an efficient manner.newBufferedReader(Path, Charset)
方法打开一个文件进行读取,返回一个BufferedReader
,可用于高效地从文件中读取文本。
The following code snippet shows how to use the 下面的代码片段显示了如何使用newBufferedReader
method to read from a file. newBufferedReader
方法读取文件。The file is encoded in "US-ASCII."该文件以“US-ASCII”编码。
Charset charset = Charset.forName("US-ASCII"); try (BufferedReader reader = Files.newBufferedReader(file, charset)) { String line = null; while ((line = reader.readLine()) != null) { System.out.println(line); } } catch (IOException x) { System.err.format("IOException: %s%n", x); }
You can use the 您可以使用newBufferedWriter(Path, Charset, OpenOption...)
method to write to a file using a BufferedWriter
.newBufferedWriter(Path, Charset, OpenOption...)
方法使用BufferedWriter
写入文件。
The following code snippet shows how to create a file encoded in "US-ASCII" using this method:以下代码段显示了如何使用此方法创建以“US-ASCII”编码的文件:
Charset charset = Charset.forName("US-ASCII"); String s = ...; try (BufferedWriter writer = Files.newBufferedWriter(file, charset)) { writer.write(s, 0, s.length()); } catch (IOException x) { System.err.format("IOException: %s%n", x); }
java.io
APIsjava.io
API互操作的方法To open a file for reading, you can use the 要打开文件进行读取,可以使用newInputStream(Path, OpenOption...)
method. newInputStream(Path, OpenOption...)
方法。This method returns an unbuffered input stream for reading bytes from the file.此方法返回一个无缓冲的输入流,用于从文件中读取字节。
Path file = ...; try (InputStream in = Files.newInputStream(file); BufferedReader reader = new BufferedReader(new InputStreamReader(in))) { String line = null; while ((line = reader.readLine()) != null) { System.out.println(line); } } catch (IOException x) { System.err.println(x); }
You can create a file, append to a file, or write to a file by using the 您可以使用newOutputStream(Path, OpenOption...)
method. newOutputStream(Path, OpenOption...)
方法创建文件、附加到文件或写入文件。This method opens or creates a file for writing bytes and returns an unbuffered output stream.此方法打开或创建用于写入字节的文件,并返回未缓冲的输出流。
The method takes an optional 该方法采用可选的OpenOption
parameter. OpenOption
参数。If no open options are specified, and the file does not exist, a new file is created. 如果未指定打开选项,且文件不存在,则会创建一个新文件。If the file exists, it is truncated. 如果文件存在,它将被截断。This option is equivalent to invoking the method with the 此选项相当于使用CREATE
and TRUNCATE_EXISTING
options.CREATE
和TRUNCATE_EXISTING
选项调用该方法。
The following example opens a log file. 下面的示例打开一个日志文件。If the file does not exist, it is created. If the file exists, it is opened for appending.如果文件不存在,则创建该文件。如果文件存在,则打开该文件进行附加。
import static java.nio.file.StandardOpenOption.*; import java.nio.file.*; import java.io.*; public class LogFileTest { public static void main(String[] args) { // Convert the string to a // byte array. String s = "Hello World! "; byte data[] = s.getBytes(); Path p = Paths.get("./logfile.txt"); try (OutputStream out = new BufferedOutputStream( Files.newOutputStream(p, CREATE, APPEND))) { out.write(data, 0, data.length); } catch (IOException x) { System.err.println(x); } } }
ByteBuffers
ByteBuffers
的方法While stream I/O reads a character at a time, channel I/O reads a buffer at a time. 当流I/O一次读取一个字符时,通道I/O一次读取一个缓冲区。The ByteChannel
interface provides basic read
and write
functionality. ByteChannel
接口提供基本的读写功能。A SeekableByteChannel
is a ByteChannel
that has the capability to maintain a position in the channel and to change that position. SeekableByteChannel
是一种ByteChannel
,能够在通道中保持位置并更改该位置。A SeekableByteChannel
also supports truncating the file associated with the channel and querying the file for its size.SeekableByteChannel
还支持截断与通道关联的文件并查询文件的大小。
The capability to move to different points in the file and then read from or write to that location makes random access of a file possible. 能够移动到文件中的不同点,然后从该位置读取或写入,从而可以对文件进行随机访问。See Random Access Files for more information.有关详细信息,请参阅随机访问文件。
There are two methods for reading and writing channel I/O.有两种读取和写入通道I/O的方法。
newByteChannel(Path, OpenOption...)
newByteChannel(Path, Set<? extends OpenOption>, FileAttribute<?>...)
newByteChannel
methods return an instance of a SeekableByteChannel
. newByteChannel
方法返回seekableytechannel
的实例。FileChannel
providing access to more advanced features such mapping a region of the file directly into memory for faster access, locking a region of the file so other processes cannot access it, or reading and writing bytes from an absolute position without affecting the channel's current position. FileChannel
,以提供对更高级功能的访问,例如将文件区域直接映射到内存中以实现更快的访问,锁定文件区域以使其他进程无法访问它,或者从绝对位置读取和写入字节,而不影响通道的当前位置。Both <两种newByteChannel
methods enable you to specify a list of OpenOption
options. newByteChannel
方法都允许您指定OpenOption
选项列表。/ins>The same open options used by the newOutputStream
methods are supported, in addition to one more option: READ
is required because the SeekableByteChannel
supports both reading and writing.newOutputStream
方法使用的相同打开选项也受支持,此外还有一个选项:READ
是必需的,因为SeekableByteChannel
同时支持读取和写入。
Specifying 指定READ
opens the channel for reading. READ
打开用于读取的通道。Specifying 指定WRITE
or APPEND
opens the channel for writing. WRITE
或APPEND
将打开写入通道。If none of these options are specified, then the channel is opened for reading.如果未指定这些选项,则打开通道进行读取。
The following code snippet reads a file and prints it to standard output:以下代码段读取文件并将其打印到标准输出:
public static void readFile(Path path) throws IOException { // Files.newByteChannel() defaults to StandardOpenOption.READ try (SeekableByteChannel sbc = Files.newByteChannel(path)) { final int BUFFER_CAPACITY = 10; ByteBuffer buf = ByteBuffer.allocate(BUFFER_CAPACITY); // Read the bytes with the proper encoding for this platform. If // you skip this step, you might see foreign or illegible // characters. String encoding = System.getProperty("file.encoding"); while (sbc.read(buf) > 0) { buf.flip(); System.out.print(Charset.forName(encoding).decode(buf)); buf.clear(); } } }
The following example, written for UNIX and other POSIX file systems, creates a log file with a specific set of file permissions. 下面的示例是为UNIX和其他POSIX文件系统编写的,它创建了一个具有特定文件权限集的日志文件。This code creates a log file or appends to the log file if it already exists. 此代码创建一个日志文件,如果日志文件已经存在,则将其附加到日志文件。The log file is created with read/write permissions for owner and read only permissions for group.日志文件是使用所有者的读/写权限和组的只读权限创建的。
import static java.nio.file.StandardOpenOption.*; import java.nio.*; import java.nio.channels.*; import java.nio.file.*; import java.nio.file.attribute.*; import java.io.*; import java.util.*; public class LogFilePermissionsTest { public static void main(String[] args) { // Create the set of options for appending to the file. Set<OpenOption> options = new HashSet<OpenOption>(); options.add(APPEND); options.add(CREATE); // Create the custom permissions attribute. Set<PosixFilePermission> perms = PosixFilePermissions.fromString("rw-r-----"); FileAttribute<Set<PosixFilePermission>> attr = PosixFilePermissions.asFileAttribute(perms); // Convert the string to a ByteBuffer. String s = "Hello World! "; byte data[] = s.getBytes(); ByteBuffer bb = ByteBuffer.wrap(data); Path file = Paths.get("./permissions.log"); try (SeekableByteChannel sbc = Files.newByteChannel(file, options, attr)) { sbc.write(bb); } catch (IOException x) { System.out.println("Exception thrown: " + x); } } }
You can create an empty file with an initial set of attributes by using the 可以使用createFile(Path, FileAttribute<?>)
method. createFile(Path, FileAttribute<?>)
方法创建具有初始属性集的空文件。For example, if, at the time of creation, you want a file to have a particular set of file permissions, use the 例如,如果在创建文件时希望文件具有特定的文件权限集,请使用createFile
method to do so. createFile
方法。If you do not specify any attributes, the file is created with default attributes. 如果未指定任何属性,则将使用默认属性创建文件。If the file already exists, 如果文件已经存在,createFile
throws an exception.createFile
将抛出异常。
In a single atomic operation, the 在单个原子操作中,createFile
method checks for the existence of the file and creates that file with the specified attributes, which makes the process more secure against malicious code.createFile
方法检查文件是否存在,并使用指定的属性创建该文件,从而使进程更安全地抵御恶意代码。
The following code snippet creates a file with default attributes:以下代码段使用默认属性创建文件:
Path file = ...; try { // Create the empty file with default permissions, etc. Files.createFile(file); } catch (FileAlreadyExistsException x) { System.err.format("file named %s" + " already exists%n", file); } catch (IOException x) { // Some other sort of failure, such as permissions. System.err.format("createFile error: %s%n", x); }
POSIX File Permissions has an example that uses POSIX文件权限有一个使用createFile(Path, FileAttribute<?>)
to create a file with pre-set permissions.createFile(Path, FileAttribute<?>)
创建具有预设权限的文件的示例。
You can also create a new file by using the 还可以使用newOutputStream
methods, as described in Creating and Writing a File using Stream I/O. newOutputStream
方法创建新文件,如使用流I/O创建和写入文件中所述。If you open a new output stream and close it immediately, an empty file is created.如果打开新的输出流并立即关闭,则会创建一个空文件。
You can create a temporary file using one of the following 可以使用以下createTempFile
methods:createTempFile
方法之一创建临时文件:
createTempFile(Path, String, String, FileAttribute<?>)
createTempFile(String, String, FileAttribute<?>)
The first method allows the code to specify a directory for the temporary file and the second method creates a new file in the default temporary-file directory. 第一种方法允许代码为临时文件指定目录,第二种方法在默认临时文件目录中创建新文件。Both methods allow you to specify a suffix for the filename and the first method allows you to also specify a prefix. 这两种方法都允许您为文件名指定后缀,第一种方法还允许您指定前缀。The following code snippet gives an example of the second method:以下代码段给出了第二种方法的示例:
try { Path tempFile = Files.createTempFile(null, ".myapp"); System.out.format("The temporary file" + " has been created: %s%n", tempFile) ; } catch (IOException x) { System.err.format("IOException: %s%n", x); }
The result of running this file would be something like the following:运行此文件的结果如下所示:
The temporary file has been created: /tmp/509668702974537184.myapp
The specific format of the temporary file name is platform specific.临时文件名的特定格式是特定于平台的。