Java 为什么在实例化对象时,默认构造函数需要在具有参数化构造函数的POJO文件中声明?

Java 为什么在实例化对象时,默认构造函数需要在具有参数化构造函数的POJO文件中声明?,java,constructor,pojo,default-constructor,Java,Constructor,Pojo,Default Constructor,假设我有一个POJO类用户,其构造函数为公共用户(int-id,String-name){…}。 但是当我在没有参数的情况下实例化用户对象,如User u=new User(),Eclipse会给出错误,如构造函数User()未定义。但是,当我没有参数化构造函数时,它工作得很好。有人能解释一下为什么需要定义默认构造函数吗?只有在您没有提供其他构造函数的情况下才会提供默认(无参数)构造函数。如果为类定义了一个构造函数,则必须使用显式定义的(即,在代码中)构造函数之一来实例化对象。当然,您可以定义自

假设我有一个POJO类用户,其构造函数为
公共用户(int-id,String-name){…}
。 但是当我在没有参数的情况下实例化用户对象,如
User u=new User()
,Eclipse会给出错误,如构造函数User()未定义。但是,当我没有参数化构造函数时,它工作得很好。有人能解释一下为什么需要定义默认构造函数吗?

只有在您没有提供其他构造函数的情况下才会提供默认(无参数)构造函数。如果为类定义了一个构造函数,则必须使用显式定义的(即,在代码中)构造函数之一来实例化对象。当然,您可以定义自己的零参数、空构造函数,如果这对您要做的工作有效的话

编辑:
为什么?


编译器提供一个默认构造函数,以便在没有定义构造函数时可以实例化对象。但是,如果您定义了参数化构造函数,这意味着当您创建该类的新实例时,它的变量应该使用您传递的参数初始化(或执行类似操作)。如果没有这些初始化,对象可能不会以预期的方式运行。因此,编译器通过不定义默认构造函数(当您定义了一个构造函数时)来防止这种情况的发生。

Java编译器会自动为任何没有构造函数的类提供一个无参数的默认构造函数。如果类中没有定义构造函数,那么Java编译器将在生成的类文件中添加一个无参数构造函数。但如果类中有带参数的构造函数,则需要编写无参数构造函数,编译器不会添加它。

编译器会自动提供无参数,没有构造函数的任何类的默认构造函数,但如果您显式地为任何构造函数提供参数,则编译器将不会提供默认构造函数,主要是由于安全原因

所以你能做的就是

 public User(int id, String name){...}
 public User(){this(defualtID,defaultName)};

如果开发人员没有提供构造函数,编译器将自动添加no-arg构造函数。但是,一旦您放置了自己的自定义参数化构造函数,编译器就会停止为您添加默认构造函数

在这种情况下,如果仍要使用无参数构造函数,则必须自己显式提供它:

public User() {
}

public User(int id, String name) {
}
这背后的逻辑是:如果定义自己的参数化构造函数,则声明构造函数中列出的参数是构造类的对象所必需的。因此,您还隐式声明,如果库的用户不提供这两个参数,则对象应该无法构造。因此,编译器不会为您添加no-arg构造函数


如果您还想声明,如果参数化构造函数中没有提供任何指定参数,并且您(没有参数),那么您可以通过自己提供非参数构造函数来显式声明类仍然可以工作

我这么晚才给出答案,但让我们试着与您分享我所知道的:

  • 当您不提供构造函数时,编译器将提供构造函数。为什么?因为它确定您将只使用无参数构造函数初始化对象。所以编译器为你们做了这件事

  • 当您提供参数化构造函数时,编译器不知道将使用哪个构造函数初始化对象。所以编译器并没有为您提供一个无参数构造函数。所以你必须明确地写

    希望它能帮助你


  • 是的,我知道这个事实。但为什么呢?为什么JVM不每次都提供默认构造函数?对于“为什么”我没有一个好的答案。因为语言就是这样建立起来的。这可能是为了避免在调用没有明确定义的构造函数时出现混淆。Java为您提供默认构造函数完全是出于您自身的方便。@VimalBera:提供默认构造函数的不是JVM,而是Java编译器。不懂方法的孩子需要帮助。但是一个知道去哪里的人不需要它。若并没有定义构造函数,编译器会抓住你们。若你们有一个自定义构造函数,编译器会解释你们不需要一个默认的无参数构造函数。如果需要,可以显式定义它。@VimalBera,它是这样的:编译器提供一个默认构造函数,以便在没有定义构造函数的情况下实例化对象。但是,如果您定义了参数化构造函数,这意味着当您创建该类的新实例时,它的变量应该使用您传递的参数初始化(或执行类似操作)。如果没有这些初始化,对象可能不会以预期的方式运行。因此,编译器通过不定义默认构造函数(当您定义了一个构造函数时)来防止这种情况的发生。编译器是这样做的。(这是一个没有参数的构造函数,而不是参数-调用构造函数或方法时会提供参数。)@JonSkeet yep在您进行通信时我正在更正:-)谢谢!但不是争论部分?(老实说,我不确定这个答案是否真的比Kon的答案更重要。)@JonSkeet,而我同意参数传递和参数接收这两个术语的一般用法;使用术语“默认无参数构造函数”非常常见。@RaviThapliyal:common,但不正确。为什么要传播这种错误?术语的使用有很多不好的地方——我正在努力改进术语的使用,因为我认为它很重要。谢谢分享你的经验。:)