1.インターフェースは「interface」キーワードを使って定義する。
2.インターフェースは実装を含むメソッドは定義できない。定数は定義できる。
3.インターフェースは多重実装が可能。
インターフェースとは
インターフェースは実装しなければいけないメソッドを定義するものです。
クラスはインターフェースをimplements演算子で「実装する」と指定することで、
そのインターフェースで定義づけられたメソッドを実装しなければならなくなります。
その点、抽象クラスと似ている部分もありますが、
抽象クラスには具象メソッドも定義することができましたが、
インターフェースはメソッドの実装は全く定義できません。
また、インターフェース内で定義される全てのメソッドはpublicである必要があります。
省略した場合は自動的にpublicになります。
インターフェース(と抽象クラス)が、コードの基本設計にあたり、
具象クラスが、コードの詳細設計にあたります。
ですので、最初からクラスを書くのでなく、
インターフェースを先に書くことで、
細かい実装に拘泥せず、必要なコードの大枠を定義できる利点があります。
インターフェースの定義構文
interface インターフェース名{
public function メソッド名();
}
インターフェースを実装するクラスの構文
class クラス名 implements インターフェース名{
}
インターフェースの継承
interface 子インターフェース名 extends 親インターフェース名{
}
インターフェースと定数
インターフェースでは定数を定義することができます。
しかし、その定数を、実装先のクラスでオーバーライドできません。
<?php
interface Constants{
const x = 100;
}
class Constants_ implements Constants{
const x = 1;
}
echo (new Constants_())->x;
?>
インターフェースのサンプル
interface If2_3_1{
const X = "xxx";
function if_x();
}
class Sample2_3_1 implements If2_3_1{
//const X = "xxx2";
function if_x(){
echo self::X;
}
}
$s = new Sample2_3_1;
$s->if_x();
インターフェースの多重実装
インターフェースは多重実装が可能です。
その場合、implementsに定義した全てのインターフェースで
宣言されているメソッドを実装する必要があります。
interface If2_3_2_1{
function a();
}
interface If2_3_2_2{
function b();
}
class Sample2_3_2 implements If2_3_2_1, If2_3_2_2{
function a(){
echo "a";
}
function b(){
echo "b";
}
}
補足
PHPでは多重継承(複数のクラスの継承)はできません。
その代替として、多重実装を使います。
たとえば、CSVにできるクラスと、JSONにできるクラスというクラス定義をして、
そのあとに、CSVにもJSONにもできるクラスを用意しようとしても、
できません。
代わりに、CSVにできるインターフェースと、JSONにできるインターフェースを用意し、
目的のクラスに、2つのインターフェースを多重実装させれば、同じ目的が達成できます。
<?php
interface CSVable
{
function toCSV();
}
interface JSONable
{
function toJSON();
}
class Product implements CSVable, JSONable
{
public function __construct(int $id, String $name)
{
$this->id = $id;
$this->name = $name;
}
public function toCSV()
{
$value = $this->id.",".$this->name;
return $value;
}
public function toJSON()
{
$candidate = json_encode($this);
if($candidate === false)
{
return "{}";
}
return $candidate;
}
}
$product = new Product(1, "PC");
echo "CSV : ".$product->toCSV()."</br>";
echo "JSON : ".$product->toJSON()."</br>";
?>
インターフェースと抽象クラスの併用
以下のように、抽象クラスを継承し、インターフェースを実装したクラスを定義することも可能です。
interface IF2_3_3{
function a();
function c();
}
abstract class Abs2_3_3{
abstract function a();
function b(){
echo "b";
}
}
class Sample2_3_3 extends Abs2_3_3 implements IF2_3_3{
function a(){
echo "a";
}
function c(){
echo "c";
}
}
$s = new Sample2_3_3();
$s->a();
$s->b();
$s->c();

