696

抽象クラスはコンストラクタを持つことができますか?

もしそうなら、それはどのように使用でき、どのような目的で使用できますか?

4

22 に答える 22

717

はい、抽象クラスはコンストラクタを持つことができます。このことを考慮:

abstract class Product { 
    int multiplyBy;
    public Product( int multiplyBy ) {
        this.multiplyBy = multiplyBy;
    }

    public int mutiply(int val) {
       return multiplyBy * val;
    }
}

class TimesTwo extends Product {
    public TimesTwo() {
        super(2);
    }
}

class TimesWhat extends Product {
    public TimesWhat(int what) {
        super(what);
    }
}

スーパークラスProductは抽象的で、コンストラクターがあります。具象クラスTimesTwoには、値 2 をハードコードするだけのコンストラクターがあります。具象クラスTimesWhatには、呼び出し元が値を指定できるようにするコンストラクターがあります。

抽象コンストラクターは、クラスの設定に必要な最小フィールドなど、クラスの制約または不変条件を強制するためによく使用されます。

注: 親抽象クラスにはデフォルト (または引数なし) のコンストラクターがないため、サブクラスで使用されるコンストラクターは親コンストラクターを明示的に呼び出す必要があります。

于 2008-11-04T03:19:37.777 に答える
173

次のいずれかの状況にある場合は、抽象クラスでコンストラクターを定義します。

  • サブクラスのインスタンス化が実際に行われる前に、(抽象クラ​​スのフィールドに対して)初期化を実行する必要があります
  • 抽象クラスでfinalフィールドを定義しましたが、宣言自体でそれらを初期化しませんでした。この場合、これらのフィールドを初期化するためのコンストラクターが必要です。

ご了承ください:

  • 複数のコンストラクターを定義できます(異なる引数を使用)
  • 保護されているすべてのコンストラクターを定義できます(すべきですか?)(とにかくそれらを公開することは無意味です)
  • サブクラスコンストラクターは、抽象クラスの1つのコンストラクターを呼び出すことができます。それ呼び出さなければならない場合もあります(抽象クラ​​スに引数なしのコンストラクターがない場合)

いずれにせよ、コンストラクターを定義しない場合、コンパイラーがコンストラクターを自動的に生成することを忘れないでください(これはパブリックであり、引数がなく、何もしません)。

于 2008-11-04T07:30:30.063 に答える
75

はい、コンストラクターを持つことができ、他のクラスのコンストラクターと同じように定義され、動作します。抽象クラスを直接インスタンス化することはできず、拡張するだけであるという点を除いて、したがって、使用は常にサブクラスのコンストラクターから行われます。

于 2008-11-04T02:59:52.247 に答える
6

もちろん、抽象クラスはコンストラクターを持つことができます。通常、クラスコンストラクターはフィールドの初期化に使用されます。したがって、抽象クラスコンストラクターは、抽象クラスのフィールドの初期化に使用されます。子クラスのインスタンス化が行われる前に、抽象クラスの特定のフィールドを初期化する場合は、抽象クラスのコンストラクターを提供します。抽象クラス コンストラクターを使用して、すべての子クラスに関連するコードを実行することもできます。これにより、コードの重複が防止されます。

抽象クラスのインスタンスを作成することはできませんが、抽象クラスから派生したクラスのインスタンスを作成することはできます。したがって、派生クラスのインスタンスが作成されると、親の抽象クラス コンストラクターが自動的に呼び出されます。

参考:この記事

于 2016-05-20T04:33:01.527 に答える
6

はい、できます。抽象クラスのコンストラクターは、通常、すべてのサブクラスに共通する初期化イベントのスーパー コールに使用されます。

于 2013-07-21T04:56:45.503 に答える
5

良い答えはたくさんありますが、私の2セントを差し上げたいと思います。

コンストラクターは OBJECT を構築しません。オブジェクトの初期化に使用されます。

はい、Abstract クラスには常にコンストラクターがあります。独自のコンストラクターを定義しない場合、コンパイラーはデフォルトのコンストラクターを Abstract クラスに提供します。上記は、ネストされた、抽象、匿名など、すべてのクラスに当てはまります。

抽象クラス (インターフェイスとは異なり) は、初期化が必要な非最終の非静的フィールドを持つことができます。これを行うには、抽象クラスに独自のコンストラクターを記述できます。ただし、その場合、デフォルトのコンストラクターはありません。

public abstract class Abs{
    int i;
    int j;
    public Abs(int i,int j){
        this.i = i;
        this.j = j;
        System.out.println(i+" "+j);
    }
}

抽象クラスの上に拡張するときは注意してください。各コンストラクターから明示的にスーパーを呼び出す必要があります。super() へのコンストラクター呼び出しの最初の行。super() を明示的に呼び出さない場合は、Java が自動的に呼び出します。以下のコードはコンパイルされません:

public class Imp extends Abs{

public Imp(int i, int j,int k, int l){
    System.out.println("2 arg");
}
}

以下の例のように使用する必要があります。

public class Imp extends Abs{

public Imp(int i, int j,int k, int l){
    super(i,j);
    System.out.println("2 arg");
}
}
于 2017-09-06T12:36:35.057 に答える
4

はい、抽象クラスはコンストラクタを持つことができます!

抽象クラスでコンストラクターを使用する例を次に示します。

abstract class Figure { 

    double dim1;        
    double dim2; 

    Figure(double a, double b) {         
        dim1 = a;         
        dim2 = b;         
    }

    // area is now an abstract method 

   abstract double area(); 

}


class Rectangle extends Figure { 
    Rectangle(double a, double b) { 
        super(a, b); 
    } 
    // override area for rectangle 
    double area() { 
        System.out.println("Inside Area for Rectangle."); 
        return dim1 * dim2; 
    } 
}

class Triangle extends Figure { 
    Triangle(double a, double b) { 
        super(a, b); 
    } 
    // override area for right triangle 
    double area() { 
        System.out.println("Inside Area for Triangle."); 
        return dim1 * dim2 / 2; 
    } 
}

class AbstractAreas { 
    public static void main(String args[]) { 
        // Figure f = new Figure(10, 10); // illegal now 
        Rectangle r = new Rectangle(9, 5); 
        Triangle t = new Triangle(10, 8); 
        Figure figref; // this is OK, no object is created 
        figref = r; 
        System.out.println("Area is " + figref.area()); 
        figref = t; 
        System.out.println("Area is " + figref.area()); 
    } 
}

それで、あなたは答えを得たと思います。

于 2015-04-21T19:26:54.027 に答える
2

このことを考慮:

abstract class Product { 
    int value;
    public Product( int val ) {
        value= val;
    }
    abstract public int multiply();
}

class TimesTwo extends Product {
    public int mutiply() {
       return value * 2;
    }
}

スーパークラスは抽象であり、コンストラクターがあります。

于 2008-11-04T02:52:55.663 に答える
1

はい、Abstract クラス変数の初期化について既に述べたように、追加できます。ただし、明示的に宣言しない場合でも、「コンストラクターチェーン」が機能するための暗黙のコンストラクターがあります。

于 2015-02-17T11:07:58.390 に答える
1

コンストラクターの連鎖を実現するために、抽象クラスにはコンストラクターがあります。コンパイラは、スーパークラス コンストラクターを呼び出すサブクラス コンストラクター内に Super() ステートメントを保持します。抽象クラスのコンストラクターがなかった場合、Java 規則に違反しているため、コンストラクター チェーンを実現できません。

于 2015-07-14T11:20:26.190 に答える
1

抽象クラスはインスタンス化できませんが、コンストラクターを持つことができます。ただし、抽象クラスで定義されたコンストラクターは、この抽象クラスの具象クラスのインスタンス化に使用できます。JLSを確認してください:

クラス インスタンス作成式を使用して抽象クラスのインスタンスを作成しようとすると、コンパイル エラーになります

それ自体が抽象ではない抽象クラスのサブクラスがインスタンス化される可能性があり、その結果、抽象クラスのコンストラクターが実行され、したがって、そのクラスのインスタンス変数のフィールド初期化子が実行されます。

于 2015-06-24T03:03:26.107 に答える
-5

はい..他のクラスと同じです。コンストラクターを持つことができ、基本クラスのオブジェクトを作成した後に呼び出されます。

于 2014-04-20T22:01:45.080 に答える