抽象クラス(やインターフェース)というものは、「ここにコンナものがある」というような抽象的な雛形を用意することである。抽象的であるがゆえ、実際のモノとして生成できず(インスタンス化不可)、「コンナもの」を詳しく継承先で記述してあげる必要がある。
■インターフェース
- サブクラスに実装を強制することができる
- 実装を強制させるメソッド以外は何も記述できない(抽象クラスとは異なる点)
- インスタンスを生成することはできない
- 複数のインターフェースを実装できる(抽象クラスとは異なる点)
<?php interface Dog { public function bark(); public function appeal($thing); } class Pochi implements Dog { public function bark(){ print('Bow!'); } public function appeal($thing){ print($thing); } } $pochi = new Pochi(); $pochi->bark();//Bow! $pochi->appeal('Give me feeds!!');//Give me feeds!! ?>
インターフェース間での継承
以下のようにインターフェースAnimalをインターフェースDogが継承することができる。その際、以下のようにキーワードextendsを用いる。
<?php interface Animal { public function appeal($thing); } interface Dog extends Animal { public function bark(); } class Pochi implements Dog { public function bark(){ print('Bow!'); } public function appeal($thing){ print($thing); } } $pochi = new Pochi(); $pochi->bark();//Bow! $pochi->appeal('Give me feeds!!'); ?>
複数のインターフェースの実装
以下のようにカンマで区切って複数のインターフェースを記述する。但し、メソッド名に重複があるとエラーになる。
<?php interface Human { public function walk(); } interface Dog { public function bark(); } class Pochi implements Human,Dog { public function bark(){ print('Bow!'); } public function walk(){ print('Walking!'); } } $pochi = new Pochi(); $pochi->bark();//Bow! $pochi->walk();//Walking! ?>
■抽象クラス
- サブクラスに実装を強制することができる
- 抽象メソッドを1つ以上持つクラスは、抽象クラスとしてabstractをつけて宣言しなくてはならない
- インスタンスを生成することはできない
- 仕様上、抽象メソッドにデフォルトの処理を記述することはできない
- 抽象クラス内の通常メソッドに、継承させるべく処理を記述することができる(インターフェースとは異なる点)
以下のように、キーワード「abstract」を用いて、抽象クラス、メソッドを記述できる。
<?php abstract class Dog { protected $name; abstract public function bark(); public function __construct($name){ $this->name = $name; } } class Pochi extends Dog { public function bark(){ print("My name is {$this->name}. Bow!"); } } $pochi = new Pochi('pochi'); $pochi->bark();//My name is pochi. Bow! ?>
但し、以下のように記述するとシンタックスエラーとなる。つまり、抽象プロパティというものは存在できない。
<?php abstract class Dog { abstract protected $name;//syntax error!! abstract public function bark(); public function __construct($name){ $this->name = $name; } } ?>
「抽象クラス」と「インターフェース」の同時利用
また、以下のように「抽象クラスの継承」と「インターフェースの実装」を、1つのクラスで同時に行うことができる。
<?php abstract class Animal { abstract public function walk(); } interface Dog { public function bark(); } class Pochi extends Animal implements Dog { public function bark(){ print('Bow!'); } public function walk(){ print('Walking!'); } } $pochi = new Pochi(); $pochi->bark();//Bow! $pochi->walk();//Walking! ?>
予備知識
PHPでは多重継承はサポートされていない。多重継承がサポートされている言語は、PythonやC++などだけである。