Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/go/7.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
&引用;构造函数调用必须是构造函数中的第一条语句;获取Java代码中的错误?_Java_Inheritance_Constructor - Fatal编程技术网

&引用;构造函数调用必须是构造函数中的第一条语句;获取Java代码中的错误?

&引用;构造函数调用必须是构造函数中的第一条语句;获取Java代码中的错误?,java,inheritance,constructor,Java,Inheritance,Constructor,这段代码中有两个错误 构造函数调用必须是构造函数中的第一条语句 public class Child extends Parent { Child(int x)// error 2 { super(0,0,0); } Child(int x, int y)// error 2 { super(x,y,0); } Child(int x, int y, int z) { super(x,y,z); System.out.println("Creating child");

这段代码中有两个错误

  • 构造函数调用必须是构造函数中的第一条语句

  • public class Child extends Parent
    {
    Child(int x)// error 2   
    {
       super(0,0,0);
    }
    Child(int x, int y)// error 2
    {
       super(x,y,0);
    }
    Child(int x, int y, int z)
    {
     super(x,y,z);
    
     System.out.println("Creating child");
    
    }
    
  • 隐式超级构造函数父级()未定义。必须显式调用另一个构造函数

  • public class Child extends Parent
    {
    Child(int x)// error 2   
    {
       super(0,0,0);
    }
    Child(int x, int y)// error 2
    {
       super(x,y,0);
    }
    Child(int x, int y, int z)
    {
     super(x,y,z);
    
     System.out.println("Creating child");
    
    }
    
    所以请帮我解决这些问题

    class Parent
    {
      public Parent(int x, int y,int z)
      {
        System.out.println("Created Parent");
      }
    }
    public class Child extends Parent
    {
      Child(int x)// error 2   
      {
    
      }
      Child(int x, int y)// error 2
      {
      }
      Child(int x, int y, int z)
      {
        this(x);
        super(x,y,z);// error 2
        System.out.println("Creating child");
        this(x,y);// error 1
      }
      public static void main(String [] args)
      {
        Child c=new Child(1,2,3);
      }
    }
    

    答案在问题中。您必须在子类构造函数中的任何其他语句之前调用父类构造函数

    public class Child extends Parent
    {
    Child(int x)// error 2   
    {
       super(0,0,0);
    }
    Child(int x, int y)// error 2
    {
       super(x,y,0);
    }
    Child(int x, int y, int z)
    {
     super(x,y,z);
    
     System.out.println("Creating child");
    
    }
    
    如果base有默认构造函数,则对base构造函数的调用不是强制性的,在代码中不是这样


    这背后的理论是,在任何继承层次结构中,当实例化任何派生对象时,首先将初始化最顶端的基,然后初始化下一个基,依此类推,直到实际的派生点。

    构造函数必须做的第一件事是调用父类构造函数

    public class Child extends Parent
    {
    Child(int x)// error 2   
    {
       super(0,0,0);
    }
    Child(int x, int y)// error 2
    {
       super(x,y,0);
    }
    Child(int x, int y, int z)
    {
     super(x,y,z);
    
     System.out.println("Creating child");
    
    }
    
    隐式默认值是
    super()
    (不带任何参数),但这在您的情况下不起作用,因为父类
    parent
    没有无参数构造函数,它只有一个带三个int参数的构造函数,所以您需要调用该构造函数

    您需要在构造函数的第一行中这样做

    public class Child extends Parent
    {
    Child(int x)// error 2   
    {
       super(0,0,0);
    }
    Child(int x, int y)// error 2
    {
       super(x,y,0);
    }
    Child(int x, int y, int z)
    {
     super(x,y,z);
    
     System.out.println("Creating child");
    
    }
    
    除了调用超级构造函数,还可以在同一个类上调用另一个构造函数(另一个
    this()
    )。假定超级构造函数由另一个构造函数调用(否则它将无法编译)

    但是您还必须在构造函数的第一行调用
    this()

    public class Child extends Parent
    {
    Child(int x)// error 2   
    {
       super(0,0,0);
    }
    Child(int x, int y)// error 2
    {
       super(x,y,0);
    }
    Child(int x, int y, int z)
    {
     super(x,y,z);
    
     System.out.println("Creating child");
    
    }
    
    在您调用了
    this()
    super()
    之后,就不能再调用它了


    不编译,因为没有与隐式调用匹配的
    super()

    Child(int x, int y)// error 2
    {
    }
    
    同样的问题

    Child(int x, int y, int z)
    {
      this(x);
      super(x,y,z);// error 2
      System.out.println("Creating child");
      this(x,y);// error 1
    }
    

    除非在第一行,否则不能调用
    super()
    this()

    有四件事你需要了解:

    • 如果未指定任何显式构造函数调用,编译器将为您插入对
      super()
      的调用

    • 任何构造函数必须只有一个构造函数调用-显式或隐式
      super()
      调用。(您的
      子(int,int,int)
      构造函数中有三个

    • public class Child extends Parent
      {
      Child(int x)// error 2   
      {
         super(0,0,0);
      }
      Child(int x, int y)// error 2
      {
         super(x,y,0);
      }
      Child(int x, int y, int z)
      {
       super(x,y,z);
      
       System.out.println("Creating child");
      
      }
      
    • 显式构造函数调用必须是构造函数体中的第一条语句

    • 您只能调用实际存在的构造函数-因此,从
      子级调用
      super()
      会在
      父级中查找不存在的无参数构造函数

    一种常见的模式是有一个“主”构造函数,同一类中的其他构造函数链接到该构造函数,然后该构造函数链接到超类。例如:

    Child(int x)
    {
        this(x, 0); // Chains to the Child(int, int) constructor, defaulting y to 0
    }
    
    Child(int x, int y)
    {
        // Chains to the Child(int, int, int) constructor, defaulting z to 0
        this(x, y, 0);
    }
    
    Child(int x, int y, int z)
    {
        super(x, y, z);
        System.out.println("Creating child");
    }
    

    当您创建子类的新实例时,首先要做的是调用super(x,y,z),否则它将无法工作。事实上,子类“是”父类,所以要有一个Child实例,您必须能够实例化超类。因此Child(intx){super(x,0,0);}是子类的一个可能构造函数,但Child(intx){}不是因为父类没有默认构造函数。请记住,当您向类显式添加构造函数时,默认构造函数不再可用。最后,您编写的构造函数是:Child(int x,int y,int z){this(x);super(x,y,z);this(x,y);}无法工作,因为在一个构造函数中调用了三个不同的构造函数,但希望有多少个实例?每个构造函数只能创建一个实例。

    实例化子对象时,调用构造函数的顺序是 父项-->后跟子项。 因此,构造函数中的第一行必须是对父构造函数的调用(如果您不提供自己的构造函数,编译器将为您插入一行)或对自己的重载构造函数的调用(如上所述,它将调用super)

    导致错误1的原因是您仅在执行某些可执行语句后才调用构造函数

    对于错误2。。。 您必须知道的第一件事是,如果您根本不提供任何类型的构造函数,编译器将为每个类提供默认的无参数构造函数

    但现在,你提供了一个构造函数,编译器不再给你一个默认的构造函数。你需要自己编写一个

    第二件事,默认情况下,如果子类中没有super(),编译器将在默认情况下对super()进行无参数调用

    这就是你的问题所在

    您为父类提供了一个参数化构造函数,因此编译器没有提供无参数默认构造函数。现在,当您在子类中没有放置自己的super(xy,z)调用时,它将放置一个默认的无参数super()调用。但是父类没有无参数构造函数……因此出现错误

    你可以做两件事来解决这个问题,或者写一个
    父(){}

    建造师

    或者直接调用super--> 超级(0,0,0)
    在每个子构造函数中,我认为第一个错误非常清楚。第二个错误非常清楚。