在Java中,为什么在尝试显示FileNotFoundException时会出现NullPointerException?

在Java中,为什么在尝试显示FileNotFoundException时会出现NullPointerException?,java,nullpointerexception,try-catch,Java,Nullpointerexception,Try Catch,我认为只显示代码和我得到的输出比试图解释它更容易:) 这是我的主要方法: //prompt user for filename System.out.println("Please enter the text file name. (Example: file.txt):"); String filename = ""; //will be used to hold filename //loop until user enters valid file name

我认为只显示代码和我得到的输出比试图解释它更容易:)

这是我的主要方法:

//prompt user for filename
    System.out.println("Please enter the text file name. (Example: file.txt):");
    String filename = ""; //will be used to hold filename

   //loop until user enters valid file name
    valid = false;
    while(!valid)
    {
        filename = in.next();
        try
        {
            reader.checkIfValid(filename);
            valid = true; //file exists and contains text
        }
        catch (Exception e)
        {
            System.out.println(e + "\nPlease try again.");
        }
    }
这是reader.checkIfValid方法:

public void checkIfValid(String filename) throws InvalidFileException, FileNotFoundException
{
    try
    {
        in = new Scanner(new File(filename));

        if (!in.hasNextLine()) // can't read first line
            throw new InvalidFileException("File contains no readable text.");
    }
    finally
    {
        in.close();
    }
}
这是输入不存在的文件时得到的输出:

请输入文本文件名。(示例:file.txt):

doesNotExist.txt

java.lang.NullPointerException

请再试一次

为什么System.out.println(e)得到一个NullPointerException?当我输入一个空文件或一个包含文本的文件时,它工作正常。空文件打印InvalidFileException(自定义异常)消息

当我在“in=new Scanner(new File(filename));”周围放置一条try-catch语句,并让catch块显示异常时,我确实会打印出FileNotFoundException,然后是NullPointerException(我不完全确定,如果checkIfValid方法中已经捕获了异常,为什么会激活main方法中的catch块…)


我已经花了一段时间在这个问题上,我完全不知道到底是怎么回事。任何帮助都将不胜感激。谢谢!

编辑:我认为空指针来自对读者的调用,捕捉所有异常都是不好的做法,因为你不再知道它们来自何处

也许checkIfValid方法应该只检查文件名是否有效

public boolean checkIfValid(String filename) {
    try {
        File file = new File(filename);
        return file.exists();   
    } catch (FileNotFoundException) {
        System.out.println("Invalid filename ["+filename+"] "+e);
    }
}
然后调用它的代码可能看起来像

filename = in.next();
valid = reader.checkIfValid(filename);
if (valid)
    List<String> fileContents = readFromFile(filename);
filename=in.next();
valid=reader.checkIfValid(文件名);
如果(有效)
List fileContents=readFromFile(文件名);
然后在它自己的方法中包含所有文件读取逻辑,如下所示

public List<String> readFromFile(filename) {
    List<String> fileContents = new ArrayList<String>();
    try {
        in = new Scanner(new File(filename));
        while (in.hasNextLine()) {
            fileContents.add(in.nextLine);
        }
    } catch (IOException e){
        //do something with the exception
    } finally {
        in.close();
    }
    return fileContents;        
}
公共列表readFromFile(文件名){
List fileContents=new ArrayList();
试一试{
in=新扫描仪(新文件(文件名));
while(在.hasNextLine()中){
fileContents.add(在.nextLine中);
}
}捕获(IOE异常){
//做一些例外的事情
}最后{
in.close();
}
返回文件内容;
}

我的错误只有我能看到。我捕获了所有的异常,因此无法看到它来自何处。感谢您的帮助!

您能发布错误吗stacktrace@sheldonCooper,我没有看到stacktrace?我在哪里可以找到它?另外,我初始化了reader,它只在file不好。谢谢你的回答。为什么新文件调用会导致空指针异常?为什么当我用try-catch块包围new-file语句时,我得到了FileNotFoundException?这不表明新文件抛出了正确的异常吗?我对捕捉异常不熟悉,所以谢谢你的建议。我只是不喜欢e让代码充满try-catch的想法。这就是代码应该是什么样子的吗?想法是捕获最具体的异常,以便可以快速找到问题所在。在处理文件交互时,需要大量try/catch块来促进这一点。我见过的最优质的代码有许多catch块也支持这一点:)Aight,因此问题出在checkIfValid方法内部,在finally块中,in.close()导致了null。由于找不到文件,因此没有初始化“in”,in.close()方法无法执行此操作。我应该在构造函数中初始化它。