java 示例初始化器与构造函数有何不同?

nkhmeac6  于 2023-04-28  发布在  Java
关注(0)|答案(7)|浏览(146)

换句话说,为什么需要示例初始化器?在编写示例初始化器时,与构造函数相比,你有什么区别或优势?

chhkpiq4

chhkpiq41#

这似乎很好地解释了这一点:
示例初始值设定项是示例变量初始值设定项的一个有用的替代方案,无论何时:

  • 初始值设定项代码必须捕获异常,或者
  • 执行无法用示例变量初始化器表示的花哨计算。* 当然,你可以总是在构造函数中编写这样的代码。*
    但是在一个有多个构造函数的类中,你必须在每个构造函数中重复代码。使用示例初始化器,您只需编写一次代码,无论使用什么构造函数创建对象,它都将被执行。示例初始化器在匿名内部类中也很有用,因为匿名内部类根本不能声明任何构造函数。

来自:JavaWorld Object initialization in Java

hm2xizp9

hm2xizp92#

在对象生命周期方面,没有区别。两者都是在构造时调用的,从逻辑上讲,初始化器块可以被认为是构造的一部分。
从语义上讲,初始化器是一个很好的工具,原因如下:
初始化器可以通过将初始化逻辑保持在被初始化的变量旁边来提高代码可读性:

public class Universe {
       public int theAnswer;
       {
         int SIX = 6;
         int NINE = 7;
         theAnswer = SIX * NINE;
       }

       // a bunch of other vars
   }

vs

public class Universe {
       public int theAnswer;

       // a bunch of other vars

       public Universe() {
         int SIX = 6;
         int NINE = 7;
         theAnswer = SIX * NINE;

         // other constructor logic
       }
   }

无论使用哪个构造函数,都会调用初始化器。
初始化器可以在匿名内部类中使用,而构造函数不能。

yks3o0rb

yks3o0rb3#

当你有很多构造函数,并且想为每个构造函数执行一些公共代码时,你可以使用示例初始化器。就像所有构造函数调用的那样。

dz6r00yl

dz6r00yl4#

一般来说,我会避免使用示例初始化器习惯用法--它相对于变量初始化器的唯一真实的优势是异常处理。
由于init方法(可从构造函数调用)也可以进行异常处理,也可以集中构造函数设置代码,但它的优点是可以对构造函数参数值进行操作,我认为示例初始化器是多余的,因此应该避免。

dgiusagp

dgiusagp5#

示例初始化器相对于构造函数的真实的优势体现在我们使用匿名内部类时。

匿名内部类不能有构造函数(因为它们是匿名的),****所以它们非常适合示例初始化器

nuypyhwy

nuypyhwy6#

在创建对象时,如果我们想执行示例变量的初始化,那么我们应该使用构造函数,而不是初始化活动,如果我们想在创建对象时执行任何活动,那么我们应该使用示例块。
我们不能用示例块替换构造函数,因为构造函数可以接受参数,但示例块不能接受参数。
我们不能用构造函数替换示例块,因为一个类可以包含多个构造函数。如果我们想用构造函数替换示例块,那么在每个构造函数中,我们都必须编写示例块代码,因为在运行时,我们无法预料哪个构造函数会被调用,这将不必要地增加重复代码。

示例:

class MyClass{

    static int object_count = 0;

    MyClass(){
        object_count++;
    }

    MyClass(int i){

        object_count++;
    }

    void getCount() {

        System.out.println(object_count);
    }

    public static void main(String... args) {
        MyClass one = new MyClass();
        MyClass two = new MyClass(2);
        two.getCount();
    }
}

输出:2

class MyClass{

    static int object_count = 0;

    {
        object_count++;
    }

    MyClass(){

    }

    MyClass(int i){     

    }

    void getCount() {

        System.out.println(object_count);
    }

    public static void main(String... args) {
        MyClass one = new MyClass();
        MyClass two = new MyClass(2);
        two.getCount();
    }
}

输出:2

66bbxpm5

66bbxpm57#

初始化器是在构造函数之间共享代码的一种方式,如果初始化器与变量声明一起使用,则会使代码更具可读性。
Java编译器将初始化器块复制到每个构造函数中。因此,这种方法可以用于在多个构造函数之间共享代码块。Oracle documentation

相关问题