《Effective Java》笔记09:使用 try-with-resources 语句替代 try-finally 语句

Java 类库中包含许多必须通过调用 close 方法手动关闭的资源。 比如 InputStream,OutputStream 和 java.sql.Connection。 客户经常忽视关闭资源,其性能结果可想而知。 尽管这些资源中有很多使用 finalizer 机制作为安全网,但 finalizer 机制却不能很好地工作(详见第 8 条)。

从以往来看,try-finally 语句是保证资源正确关闭的最佳方式,即使是在程序抛出异常或返回的情况下:

static String firstLineOfFile(String path) throws IOException {
    BufferedReader br = new BufferedReader(new FileReader(path));
    try {
        return br.readLine();
    } finally {
        br.close();
    }
}

// 添加第二个资源时,情况会变得更糟
static void copy(String src, String dst) throws IOException {
    InputStream in = new FileInputStream(src);
    try {
        OutputStream out = new FileOutputStream(dst);
        try {
            byte[] buf = new byte[BUFFER_SIZE];
            int n;
            while ((n = in.read(buf)) >= 0)
                out.write(buf, 0, n);
        } finally {
            out.close();
        }
    } finally {
        in.close();
    }
}

Java 7 引入了 try-with-resources 语句时,所有这些问题一下子都得到了解决。要使用这个构造,资源必须实现 AutoCloseable 接口,该接口由一个返回为 void 的 close 组成。Java 类库和第三方类库中的许多类和接口现在都实现或继承了 AutoCloseable 接口。如果你编写的类表示必须关闭的资源,那么这个类也应该实现 AutoCloseable 接口。

  以下是我们的第一个使用 try-with-resources 的示例:

// 关闭资源的最佳方式
static String firstLineOfFile(String path) throws IOException {
    try (BufferedReader br = new BufferedReader(
           new FileReader(path))) {
       return br.readLine();
    }
}

static void copy(String src, String dst) throws IOException {
    try (InputStream   in = new FileInputStream(src);
         OutputStream out = new FileOutputStream(dst)) {
        byte[] buf = new byte[BUFFER_SIZE];
        int n;
        while ((n = in.read(buf)) >= 0)
            out.write(buf, 0, n);
    }
}

这里有一个版本的 firstLineOfFile 方法,它不会抛出异常,但是如果它不能打开或读取文件,则返回默认值:

static String firstLineOfFile(String path, String defaultVal) {
    try (BufferedReader br = new BufferedReader(new FileReader(path))) {
        return br.readLine();
    } catch (IOException e) {
        return defaultVal;
    }
}

结论很明确:在处理必须关闭的资源时,使用 try-with-resources 语句替代 try-finally 语句。生成的代码更简洁,更清晰,并且生成的异常更有用。


转载请注明来源,欢迎对文章中的引用来源进行考证,欢迎指出任何有错误或不够清晰的表达。可以在下面评论区评论,也可以邮件至 bin07280@qq.com

文章标题:《Effective Java》笔记09:使用 try-with-resources 语句替代 try-finally 语句

文章字数:519

本文作者:Bin

发布时间:2019-06-17, 14:39:14

最后更新:2019-08-06, 00:42:53

原始链接:http://coolview.github.io/2019/06/17/Effective-Java/%E3%80%8AEffective%20Java%E3%80%8B%E7%AC%94%E8%AE%B009%EF%BC%9A%E4%BD%BF%E7%94%A8%20try-with-resources%20%E8%AF%AD%E5%8F%A5%E6%9B%BF%E4%BB%A3%20try-finally%20%E8%AF%AD%E5%8F%A5/

版权声明: "署名-非商用-相同方式共享 4.0" 转载请保留原文链接及作者。

目录