构造函数可以在Java中引发exception吗?

允许构造函数抛出exception吗?

是的,构造函数可以抛出exception。 通常这意味着新对象立即有资格进行垃圾回收(尽pipe当然可能不会收集一段时间)。 如果在构造函数中(例如,通过分配一个静态字段或将其自身添加到一个集合中)使它自己可见,则“半结构化”对象可能仍然存在。

有一件事要小心在构造函数中抛出exception:因为调用者(通常)将无法使用新的对象,构造函数应该小心避免获得非托pipe资源(文件句柄等),然后抛出一个exception而不会释放它们。 例如,如果构造函数试图打开一个FileInputStream和一个FileOutputStream ,并且第一个成功但第二个失败,则应该尝试closures第一个stream。 如果这是一个抛出exception的子类构造函数,这变得更难了,当然…这一切都变得有点棘手。 这经常不是问题,但值得考虑。

是的,他们可以抛出exception。 如果是这样,他们只会被部分初始化,如果是非最终的,则会受到攻击。

以下是安全编码指南2.0 。

可以通过终结器攻击来访问部分初始化的非最终类的实例。 攻击者重写子类中受保护的finalize方法,并尝试创build该子类的新实例。 此尝试失败(在上例中,ClassLoader的构造函数中的SecurityManager检查会引发安全exception),但攻击者只是忽略任何exception并等待虚拟机对部分初始化的对象执行完成。 当发生这种情况时,会调用恶意的finalize方法实现,攻击者可以访问这个方法,对正在定义的对象进行引用。 虽然对象只是部分初始化,攻击者仍然可以调用它的方法(从而绕过SecurityManager检查)。

绝对。

如果构造函数没有收到有效的input,或者无法以有效的方式构造对象,则除了抛出exception并提醒其调用者外,别无select。

是的,构造函数被允许抛出exception。

然而,select他们应该是什么样的exception非常明智 – 检查exception或不检查。 未经检查的exception基本上是RuntimeException的子类。

在几乎所有情况下(我不能拿出这个例子的例外),你需要抛出一个检查exception。 原因是未经检查的exception(如NullPointerException)通常是由于编程错误(如不能充分validationinput)所致。

被检查的exception提供的优点是程序员被迫在他的实例化代码中捕获exception,从而认识到可能无法创build对象实例。 当然,只有代码审查才能抓住吞噬exception的糟糕编程习惯。

是的,它可以抛出一个exception,你也可以在构造函数的签名中声明这个exception,如下例所示:

 public class ConstructorTest { public ConstructorTest() throws InterruptedException { System.out.println("Preparing object...."); Thread.sleep(1000); System.out.println("Object ready"); } public static void main(String ... args) { try { ConstructorTest test = new ConstructorTest(); } catch (InterruptedException e) { System.out.println("Got interrupted..."); } } } 

是。

构造函数只不过是特殊的方法,可以像其他方法一样抛出exception。

一个构造函数CAN会抛出任何exception。 但是,如果任何子类构造函数调用引发exception的超类构造函数,那么子类构造函数必须捕获exception或抛出exception。

 public class Stack { class SizeOutOfBounds extends Exception{ private static final long serialVersionUID = 1L; public SizeOutOfBounds(String value){ super(value); } } private static final int DEFAULT_SIZE = 10; int[] stack; //another example where constructor can throw exception.. public Stack(int size) throws SizeOutOfBounds{ if(size <= 0){ throw new SizeOutOfBounds(String.valueOf(size)); } stack = new int[size]; } public Stack() throws SizeOutOfBounds{ this(DEFAULT_SIZE); } /** * */ 

}