【问题标题】:Can initializer block throw exception?初始化程序块可以抛出异常吗?
【发布时间】:2013-10-20 22:41:58
【问题描述】:

我在一个类中使用 BufferedReader 来读取文件。我正在尝试在初始化程序块中初始化它。

class ReadFromFile
{
    BufferedReader br;

    {
        br = new BufferedReader(new FileReader(new File("file.txt")));
    }
}

初始化块中的行抛出FileNotFoundException 异常。所以,编译器给出错误。我不想用 try-catch 块包围它。我通过使用构造函数而不是初始化块解决了这个问题:

class ReadFromFile
{
    BufferedReader br;

    public ReadFromFile() throws FileNotFoundException   
    {
        br = new BufferedReader(new FileReader(new File("file.txt")));
    }
}

但仍然想知道是否有任何方法可以从初始化程序块中抛出异常而不会出现编译错误。谢谢:)

【问题讨论】:

    标签: java


    【解决方案1】:

    初始化程序块只能抛出未经检查的异常,或声明为由所有构造函数抛出的检查异常。 (这包括声明的子类的异常。)

    在没有声明构造函数的类中,您不能从初始化程序中抛出已检查异常,因为您将有效地获得一个无参数构造函数,声明它会抛出任何东西。

    来自section 11.2.3 of the JLS

    如果命名类的实例变量初始化程序或实例初始化程序可以抛出已检查的异常类,除非该异常类或其超类之一在其类的每个构造函数的 throws 子句中显式声明,则这是编译时错误并且该类至少有一个显式声明的构造函数。

    【讨论】:

    • 我不明白您如何阅读问题、编写答案并从规范中找到重要的引述,并在发布问题的同一分钟内完成所有这些操作...+1跨度>
    • @noone Jon 的练习比大多数人都多,而且永远不会少...... ;)
    • @noone:original 的答案很快 - 但我后来扩展了它,前五分钟内的编辑没有显示...
    • @noone - 这被称为经验,它确实很重要。谢谢乔恩 :)
    【解决方案2】:

    但仍然想知道是否有任何方法可以将异常从初始化程序块中抛出而不会出现编译错误。

    是的,但这是一个非常糟糕的主意。你可以这样做

    class ReadFromFile {
        BufferedReader br;
    
        {
            try {
                br = new BufferedReader(new FileReader(new File("file.txt")));
            } catch(IOException ioe) {
                // there is a number of ways to blindly throw a checked exception.
                Thread.currentThread().stop(ioe); // don't try this at home.
            }
        }
    }
    

    这一切都可以编译和工作,但它是不必要的混乱。

    【讨论】:

    • 这真的是“不要在家里尝试这个”的东西。 +1 因为学到了新东西:)
    猜你喜欢
    • 1970-01-01
    • 2011-02-09
    • 1970-01-01
    • 1970-01-01
    • 2011-08-20
    • 1970-01-01
    • 1970-01-01
    • 2011-04-16
    相关资源
    最近更新 更多