27

こんにちは、私はJavaを初めて使用します。本番ワーカーのクラスで、このエラーが発生します。私のProductionworkerコンストラクターは、別のコンストラクターを明示的に呼び出すと言っています。どうしたらいいのかわからない?

import java.util.Date;

public class Employee
{
      private String name, number;
      private Date date;

      public Employee(String name, String number, Date date)
      {
            setName(name);
            setNumber(number);
            setDate(date);
      }

      public void setName(String n)
      {
            name = n;
      }
      public void setNumber(String n)
      {
            number = n;
            // you can check the format here for correctness
      }
      public void setDate(Date d)
      {
            date = d;
      }

      public String getName()
      {
            return name;
      }
      public String getNumber()
      {
            return number;
      }
      public Date getDate()
      {
            return date;
      }
}



public class ProductionWorker extends Employee
{
      private int shift;
      private double hourlyrate;
       // error is here (Implicit super constructor Employee() is undefined. Must explicitly invoke another constructor).
      public ProductionWorker(int shift, double hourlyrate)
      {
            setShift(shift);
            setHourlyPayRate(hourlyrate);
      }

      public void setShift(int s)
      {
            shift = s;
      }
      public void setHourlyPayRate(double rate)
      {
            hourlyrate = rate;
      }

      public int getShift()
      {
            return shift;
      }
      public double getHourlyPayRate()
      {
            return hourlyrate;
      }
}
4

6 に答える 6

31

ご存知のように、任意のクラスのコンストラクターはオブジェクトを作成します。したがって、コンストラクターには、そのクラスの適切な初期化コードが含まれている必要があります。ただし、別のクラスを拡張するクラスがある場合(「親」と呼びます)、クラスのコンストラクターに、定義による初期化に必要なすべてのコードを含めることはできません(たとえば、親のプライベートフィールドを定義することはできません)。そのため、クラスのコンストラクターはその親のコンストラクターを呼び出す必要があります。明示的に呼び出さない場合は、デフォルトの親コンストラクターが呼び出されます(パラメーターはありません)。

したがって、あなたの場合、親にデフォルトのコンストラクターを実装するか、クラス内の任意のコンストラクターを直接呼び出すことができます。

于 2011-03-30T15:13:39.790 に答える
9

public Employee(){}他の人がすでに述べたように、クラスにデフォルトのコンストラクターを提供する必要がありますEmployee

何が起こるかというと、コンパイラーは、コンストラクターのないクラスに対して、引数のないデフォルトのコンストラクターを自動的に提供します。クラスに明示的なスーパークラスがない場合、そのクラスには暗黙のスーパークラスがありObject引数なしのコンストラクターがあります。この場合、クラスでコンストラクターを宣言しているEmployeeため、引数なしのコンストラクターも指定する必要があります。

そのEmployeeクラスは次のようになります。

あなたのクラスの従業員

import java.util.Date;

public class Employee
{
      private String name, number;
      private Date date;

      public Employee(){} // No-argument Constructor

      public Employee(String name, String number, Date date)
      {
            setName(name);
            setNumber(number);
            setDate(date);
      }

      public void setName(String n)
      {
            name = n;
      }
      public void setNumber(String n)
      {
            number = n;
            // you can check the format here for correctness
      }
      public void setDate(Date d)
      {
            date = d;
      }

      public String getName()
      {
            return name;
      }
      public String getNumber()
      {
            return number;
      }
      public Date getDate()
      {
            return date;
      }
}

これがJavaOracleチュートリアル-クラスのコンストラクターの提供の章です。それを通過すると、何が起こっているのかをより明確に理解できます。

于 2011-03-30T15:38:34.133 に答える
3

ProductionWorker拡張Employee、したがって、それは従業員のすべての機能を備えていると言われています。これを実現するために、Javaは各コンストラクターの最初の行に自動的にsuper();呼び出しを行います。手動で呼び出すこともできますが、通常は必要ありません。あなたの場合、 Employeeのコンストラクターにパラメーターがあるため、への呼び出しを自動的に行うことができないため、これが必要です。super();

Employeeクラスでデフォルトのコンストラクターを定義するかsuper('Erkan', 21, new Date());、ProductionWorkerでコンストラクターの最初の行を呼び出す必要があります。

于 2011-03-30T15:12:40.120 に答える
2

親クラスに引数のないコンストラクターがない場合は常に、親クラスコンストラクターを明示的に呼び出す必要があります。引数なしのコンストラクターを親クラスに追加するか、子クラスの親クラスコンストラクターを明示的に呼び出すことができます。

于 2011-03-30T15:17:58.963 に答える
1

この問題は、コンストラクターがすぐにsuperを呼び出さない場合にも発生する可能性があります。

したがって、これは機能します:

  public Employee(String name, String number, Date date)
  {
    super(....)
  }

しかし、これはしません:

  public Employee(String name, String number, Date date)
  {
    // an example of *any* code running before you call super.
    if (number < 5)
    {
       number++;
    }

    super(....)
  }

2番目の例が失敗する理由は、Javaが暗黙的に呼び出しようとしているためです。

super(name,number,date)

コンストラクターの最初の行として....したがって、Javaは、コンストラクターの後半でsuperの呼び出しが行われていることを認識しません。それは本質的にこれを行おうとします:

  public Employee(String name, String number, Date date)
  {
    super(name, number, date);

    if (number < 5)
    {
       number++;
    }

    super(....)
  }

したがって、解決策は非常に簡単です...スーパー呼び出しの前にコードを配置しないでください;-)スーパーを呼び出す前に何かを初期化する必要がある場合は、別のコンストラクターでそれを実行してから、古いコンストラクターを呼び出します...この例では、このStackOverflowの投稿から取得しています:

public class Foo
{
    private int x;

    public Foo()
    {
        this(1);
    }

    public Foo(int x)
    {
        this.x = x;
    }
}
于 2013-05-24T14:10:20.623 に答える
0

最近、私のコンプラボでこの問題が発生しました。それは簡単で、Erkanは正しく答えました。コンストラクターの最初の行として、super("the name of your subclass")問題に関連してSoを配置します。super("ProductionWorker);subclass'

于 2013-02-23T01:15:20.433 に答える