Override キーワードと New キーワードを使用する場合について (C# プログラミング ガイド)
更新 : 2007 年 11 月
C# では、新しいメソッドの取り扱い方を明確に規定している場合は、派生クラスのメソッドに基本クラスのメソッドと同じ名前を付けることができます。new と override の 2 つのキーワードの使用例を次に示します。
以下のコードでは、最初に Car という基本クラスと、そこから派生する ConvertibleCar クラスと Minivan クラスの、合わせて 3 つのクラスを宣言しています。基本クラスには、DescribeCar という 1 つのメソッドが含まれています。このメソッドは、自動車の説明をコンソールに送ります。また、派生クラスのメソッドにも DescribeCar というメソッドがあります。このメソッドは、それぞれに固有のプロパティを表示します。これらのメソッドも基本クラスの DescribeCar メソッドを呼び出し、Car クラスのプロパティをどのように継承しているかを示します。
この例では、違いを強調するために、ConvertibleCar クラスを new キーワードで定義し、Minivan クラスを override キーワードで定義しています。
// Define the base class
class Car
{
public virtual void DescribeCar()
{
System.Console.WriteLine("Four wheels and an engine.");
}
}
// Define the derived classes
class ConvertibleCar : Car
{
public new virtual void DescribeCar()
{
base.DescribeCar();
System.Console.WriteLine("A roof that opens up.");
}
}
class Minivan : Car
{
public override void DescribeCar()
{
base.DescribeCar();
System.Console.WriteLine("Carries seven people.");
}
}
ここで、次のようなコードを記述できます。このコードでは、これらのクラスのインスタンスを宣言し、それぞれのメソッドを呼び出して、オブジェクトがオブジェクト自体を説明できるようにします。
public static void TestCars1()
{
Car car1 = new Car();
car1.DescribeCar();
System.Console.WriteLine("----------");
ConvertibleCar car2 = new ConvertibleCar();
car2.DescribeCar();
System.Console.WriteLine("----------");
Minivan car3 = new Minivan();
car3.DescribeCar();
System.Console.WriteLine("----------");
}
このコードの出力は次のようになります。
Four wheels and an engine.
----------
Four wheels and an engine.
A roof that opens up.
----------
Four wheels and an engine.
Carries seven people.
----------
次のコード セクションでは、Car 基本クラスから派生したオブジェクトの配列を宣言します。この配列には、Car、ConvertibleCar、Minivan の 3 つのオブジェクトを格納できます。この配列は、次のように宣言します。
public static void TestCars2()
{
Car[] cars = new Car[3];
cars[0] = new Car();
cars[1] = new ConvertibleCar();
cars[2] = new Minivan();
}
これで、次のように foreach ループを使用して、配列内の各 Car オブジェクトにアクセスし、DescribeCar メソッドを呼び出すことができます。
foreach (Car vehicle in cars)
{
System.Console.WriteLine("Car object: " + vehicle.GetType());
vehicle.DescribeCar();
System.Console.WriteLine("----------");
}
このループの出力は次のようになります。
Car object: YourApplication.Car
Four wheels and an engine.
----------
Car object: YourApplication.ConvertibleCar
Four wheels and an engine.
----------
Car object: YourApplication.Minivan
Four wheels and an engine.
Carries seven people.
----------
ConvertibleCar の説明が、予想とは異なることに注意してください。このメソッドは、new キーワードで定義されているので、派生クラスのメソッドが呼び出されず、代わりに基本クラスのメソッドが呼び出されます。Minivan オブジェクトは、オーバーライドされたメソッドを正常に呼び出し、予想どおりの結果を生成します。
Car から派生したすべてクラスに DescribeCar メソッドを実装させる規則を適用する場合は、DescribeCar メソッドを abstract として定義する新しい基本クラスを作成する必要があります。抽象メソッドには、コードが含まれず、メソッド シグネチャだけが含まれます。この基本クラスから派生したクラスは、DescribeCar の実装を提供する必要があります。詳細については、「abstract (C# リファレンス)」を参照してください。