我的java程序中的资源泄漏

时间:2014-08-13 21:23:30

标签: java bufferedreader filereader resource-leak

我正在尝试在java中编写一个方法,我从文件中获取一些信息,看看文件是否包含用户查找的信息。但是,对于我提出的代码,eclipse标志着我有资源泄漏并且#34;返回true;"并且" br =新的BufferedReader(fr);"尽管我在程序结束时使用了close()方法,但它永远不会关闭。显然我错过了一些东西。有人能帮我弄清楚发生了什么吗?非常感谢提前!

import java.io.*;

class Help{
    String helpfile;

    Help(String fname){
        helpfile = fname;
    }

    boolean helpon(String what){
        FileReader fr;
        BufferedReader br;
        int ch;
        String topic, info;

        try{
            fr = new FileReader(helpfile);
            br = new BufferedReader(fr);
        }
        catch(FileNotFoundException e){
            System.out.println(e);
            return false;
        }

        try{
            do{
                ch = br.read();
                if(ch=='#'){
                    topic = br.readLine();
                    if(what.compareTo(topic) == 0){
                        do{
                            info = br.readLine();
                            if(info!=null)
                                System.out.println(info);
                        }while((info!= null) && (info.compareTo("")!= 0));
                        return true;
                    }
                }
            }while(ch!=-1);
        }
        catch(IOException e){
            System.out.println(e);
            return false;
        }

        try{
            br.close();
        }
        catch(IOException e){
            System.out.println(e);
        }
        return false;
    }
}

4 个答案:

答案 0 :(得分:3)

问题是您在程序有机会关闭资源之前返回。有两种方法可以解决此问题:

  1. 关闭资源后放置返回(通过将返回结果放在布尔值中)。
  2. 修改你的代码,将close放在finally块中,这样任何返回完成后仍会执行该代码。
  3. 2号通常是一种更为公认的做法,因为如果你将来添加更多东西,你仍然可以保证关闭资源(除非发生灾难性事件)。

    boolean helpon(String what){
        FileReader fr;
        BufferedReader br;
        int ch;
        String topic, info;
    
        try{
            fr = new FileReader(helpfile);
            br = new BufferedReader(fr);
            do{
                ch = br.read();
                if(ch=='#'){
                    topic = br.readLine();
                    if(what.compareTo(topic) == 0){
                        do{
                            info = br.readLine();
                            if(info!=null)
                                System.out.println(info);
                        }while((info!= null) && (info.compareTo("")!= 0));
                        return true;
                    }
                }
            }while(ch!=-1);
        } catch(IOException e){
            System.out.println(e);
            return false;
        } catch(FileNotFoundException e){
            System.out.println(e);
            return false;
        } finally {
            try {
                if (br != null) {
                    br.close();
                }
            } catch(IOException e){
                System.out.println(e);
                return false;
            }
        }
    }
    

答案 1 :(得分:2)

您在整个方法中都有返回语句,但最后只有br.close()。在代码流中,可以返回方法,使br仍然打开。

您可能有兴趣使用try with resources

try (
        FileReader fr = new FileReader(helpfile);
        BufferedReader br = new BufferedReader(fr)
    ) 
{
  //your code
}
catch (IOException e)
{
 //error
}

这样,将在资源上自动为您调用close方法。

答案 2 :(得分:1)

您应该将调用close()放在finally块中。在当前状态下,您的代码永远不会到达最终的try / catch,因为您返回true或false。

try {

    fr = new FileReader(helpfile);
    br = new BufferedReader(fr);

    do {
        ch = br.read();
        if(ch=='#'){
            topic = br.readLine();
            if(what.compareTo(topic) == 0){
                do{
                    info = br.readLine();
                    if(info!=null)
                        System.out.println(info);
                }while((info!= null) && (info.compareTo("")!= 0));
                return true;
            }
        }
    }while(ch!=-1);

} catch (IOException e) {
    System.out.println(e);
    return false;

} catch (FileNotFoundException e) {
    System.out.println(e);
    return false;

} finally  {

    try {

        if (br != null) {
            br.close();
        }

    } catch (IOException e) {
        System.out.println(e);
    }

}

答案 3 :(得分:0)

如果您使用的是Java 7,请使用try-with-resources功能:

http://docs.oracle.com/javase/tutorial/essential/exceptions/tryResourceClose.html