有 Java 编程相关的问题?

你可以在下面搜索框中键入要查询的问题!

java内部类中的两个声明构造函数

我有一个公共类,里面有一个私人类:

public class A {

   private class B
   {
   }

   private final B b = new B();

   public static void main(String[] args) {
       Class<?> bClass = A.class.getDeclaredClasses()[0];
       Constructor<?>[] declaredConstructors = bClass.getDeclaredConstructors();
       System.out.println(declaredConstructors.length);  //result = 2
   }
}

问题是,类B中声明的构造函数等于2

尽管在其他情况下,B类施工人员的数量等于1:

public class A {

   private class B
   {
       public B()
       {
       }
   }

   private final B b = new B();

   public static void main(String[] args) {
       Class<?> bClass = A.class.getDeclaredClasses()[0];
       Constructor<?>[] declaredConstructors = bClass.getDeclaredConstructors();
       System.out.println(declaredConstructors.length);  //result = 1
   }
}

public class A {

   private class B
   {
   }

   public static void main(String[] args) {
       Class<?> bClass = A.class.getDeclaredClasses()[0];
       Constructor<?>[] declaredConstructors = bClass.getDeclaredConstructors();
       System.out.println(declaredConstructors.length);  //result = 1
   }
}

问题是为什么在第一种情况下有两个构造器? 谢谢


共 (1) 个答案

  1. # 1 楼答案

    正如chrylis刚刚提到的,你们在这里看到的是一个合成构造器

    基本上,无论何时从嵌套类访问嵌套类的私有属性,编译器都需要为此访问创建synthetic method

    在第一个示例中,默认构造函数是私有的,因此当您调用它时,会创建一个合成方法(因此存在“2”个构造函数)

    在第二个示例中,构造函数被声明为public,不存在这样的问题

    在第三个示例中,它是私有的,但从未访问过,因此无需创建合成方法

    如果您对更详细的内容感兴趣,请阅读Java语言规范(https://docs.oracle.com/javase/specs/jls/se7/html/jls-13.html)的第13.1.7章,其中会有进一步的解释

    另外,如果你对合成方法的含义感兴趣,这篇文章可能会让你感兴趣,讨论它们在安全性(和性能)方面的含义:What's the penalty for Synthetic methods?

    此外,如果你想更多地了解这个概念的内部运作,我可以推荐以下文章:https://www.javaworld.com/article/2073578/java-s-synthetic-methods.html(据我所知,它应该仍然是最新的)