java - 释放BufferedReader、InputStreamReader和InputStream获取的资源

标签 java android exception resources

我有以下代码:

public ArrayList<Crime> loadCrimes() throws IOException, JSONException {
    ArrayList<Crime> crimes = new ArrayList<Crime>();
    BufferedReader reader = null;
    try {
        // Open and read the file into a StringBuilder
        InputStream in = mContext.openFileInput(mFilename);
        //what if an exception gets thrown in the line below?
        reader = new BufferedReader(new InputStreamReader(in));
        StringBuilder jsonString = new StringBuilder();
        String line = null;
        while ((line = reader.readLine()) != null) {
            // Line breaks are omitted and irrelevant
            jsonString.append(line);
        }
        // Parse the JSON using JSONTokener
        JSONArray array = (JSONArray) new JSONTokener(jsonString.toString()).nextValue();
        // Build the array of crimes from JSONObjects
        for (int i = 0; i < array.length(); i++) {
            crimes.add(new Crime(array.getJSONObject(i)));
        }
    } catch (FileNotFoundException e) {
        // Ignore this one; it happens when starting fresh
    } finally {
        if (reader != null)
            reader.close();
        }
    return crimes;
}

首先,我想知道为什么我们只在 BufferedReader 对象上调用 .close(),而不是在 InputStreamInputStreamReader 上 对象。我检查了 Oracle 官方文档,并浏览了 stackoverflow 中的几个问题,根据我读到的内容,BufferedReader.close() 负责释放 InputStreamReader 获取的资源> 和 InputStream,因此我不必对它们调用 .close()

这是正确的吗?

其次,我想如果在创建 InputStream 对象之后和创建 BufferedReader 对象之前抛出异常会发生什么。也就是说,InputStreamReader(InputStream in) 构造函数或 BufferedReader(Reader in) 构造函数会引发异常。在这种情况下,我们已经通过 InputStream 获取了文件资源,但 BufferedReader 对象仍然是 null,因此在 finally 中> block 时,.close() 方法将不会被调用,并且 InputStream 也不会释放其已获取的资源。

然后我阅读了Oracle文档,根据它,这两个构造函数都没有抛出异常。所以这两行之间不可能发生异常,对吗?

我的最后一个问题是“这段代码是否确保它释放它获取的所有资源?”

最佳答案

First, I wondered why we call .close() just on the BufferedReader object and not on the InputStream and InputStreamReader objects. I checked the official Oracle documentation and skimmed through a couple of questions in stackoverflow and according to what I've read BufferedReader.close() takes care of releasing the resources acquired by InputStreamReader and InputStream, so I don't have to call .close() on them. Is this correct?

是的,确实如此。

My final question is "Does this piece of code make sure it releases all resources it acquires?"

很可能是的。即使在创建InputStreamReaderBufferedReader时出现一些奇怪的异常,在退出它们定义的 block 之后,在GC收集它们之前,它们也会自动关闭。当然,依靠 GC 来清理通常不是一个好主意,因此如果您想 100% 确定,您可能需要在 finally block 中自己进行清理。

另一种更简单的方法是使用 FileReader ,它仅使用两个对象即可简化代码:

BufferedReader reader = new BufferedReader(new FileReader(fileName));

(我假设您想从文件中读取)。

关于java - 释放BufferedReader、InputStreamReader和InputStream获取的资源,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21330303/

相关文章:

JavaFX。尝试在 Controller 内实例化阶段不会检索其中的值?是吗?

android - 如何使用 branch.io 显示排行榜(每周重置一次)

PHPUnit 和域异常测试

android - 如何将MySQL数据发送到fire-base数据库?

java - 在这种情况下我应该如何处理异常

java - 预期类型 : java. lang.Double 实际值 : java. lang.Hibernate 中的整数错误

java - 更新 pom xml 时 - PKIX 路径构建失败 : sun. security.provider.certpath.SunCertPathBuilderException

java - 如何访问从客户端传递的对象中的变量?

java - 不知道javac是否无法正常工作或我只是傻瓜

android - 如何在自定义 Android 键盘中应用字体