【PHP】抽象メソッド(abstract) - オーバーライドを前提としたメソッド

【PHP】抽象メソッド(abstract) - オーバーライドを前提としたメソッド

PHPには抽象メソッドと呼ぶ、オーバーライドすることを前提としたメソッドがあります。

ここでは、抽象メソッドについて解説します。

検証環境

抽象メソッド

抽象メソッドは“オーバーライド(されること)を前提としたメソッド”です。

抽象クラスにのみ定義でき、メソッド名と引数のみ記述します。

また、抽象メソッドを持つ抽象クラスを継承した具象クラスは必ず抽象メソッドをオーバーライドして実装する必要があります。

基本構文

abstract class クラス名 {    
    abstract アクセス修飾子 function メソッド名( 仮引数1, 仮引数2 ... );
}

基本的に構文は通常のメソッドに同じですが、先頭にabstractを付け、ブロック({})は記述しません。

サンプル

<?php

// 人間クラス
abstract class Person {
    
    // 名前
    public $name;
    
    // コンストラクタ
    public function __construct( $name ) {
        $this->name = $name;
    }
    
    // あいさつ
    ___ih_hl_start
    abstract public function greeting();
    ___ih_hl_end
    
}

// 教師クラス
class Teacher extends Person {
    
    // 担当科目
    public $subject;
    
    // コンストラクタ
    public function __construct( $name, $subject ) {
        parent::__construct($name);
        $this->subject = $subject;
    }
    
    // あいさつ
    public function greeting() {
        echo "Hello.\n";
        echo "I'm a " . $this->name . ", a " . $this->subject . " instructor.\n";
    }
    
}

$teacher = new Teacher('TANAKA', 'Programming');
$teacher->greeting();

?>
$ php sample.php
Hello.
I'm a TANAKA, a Programming instructor.

15行目で抽象メソッドであるgreetingメソッドを定義しています。

このようにすることでPersonクラスを継承するTeacherクラスは必ずgreetingメソッドをオーバーライドして実装する必要があります。

なお、抽象クラスを継承した抽象クラスでは、抽象メソッドをオーバーライドする必要はありません。

継承したクラスが具象クラスの場合のみ、抽象メソッドのオーバーライドと実装が必須となります。

アクセス修飾子の制限

抽象メソッドはオーバーライドされることを前提としているため、アクセス修飾子にprivateを使うことができません。

publicまたはprotectedのみ使用可能となります。

演習問題

問題1

次の実行結果になるプログラムを作成してください。
なお、下記条件を満たすものとします。

  • 下記表の3つのクラスを作成する
  • 実行結果になるように各クラスのインスタンスを使う
クラス 英記 継承元 フィールド メソッド
チケットクラス
(抽象クラス)
Ticket なし $price(料金) info()
→ 抽象メソッド
ライブチケット LiveTicket Ticket $place(場所) info()
→ 場所と料金を出力
ライブ配信チケット LiveStreamingTicket Ticket $url(URL) info()
→ URLと料金を出力
===== ライブチケット =====
料金 : 8000円
場所 : ライブハウス
===== ライブ配信   =====
料金 : 3000円
URL : https://it-hack.net/live-streaming

問題2

次の実行結果になるプログラムを作成してください。
なお、下記条件を満たすものとします。

  • 下記表の3つのクラスを作成する
  • 実行結果になるように各クラスのインスタンスを使う
クラス 英記 継承元 フィールド メソッド
車クラス
(抽象クラス)
Car なし $distance(移動距離)
※ 初期値は0
$acceleration(加速度)
※ 初期値は60
display_distance()
→ $distanceの値を出力
run_distance()
→ 抽象メソッド
run()
→ run_distance()で前進距離を取得し出力する。また、$distanceに前進距離を加算
スポーツカークラス SportCar Car なし run_distance()
→ 前進距離を計算
→ 計算式は$acceleration * 1.2
ファミリーカークラス FamilyCar Car なし run_distance()
→ 前進距離を計算
→ 計算式は$acceleration * 0.8
===== スポーツカー  =====
72km進みます。
72km進みます。
移動距離 : 144km
===== ファミリーカー =====
48km進みます。
48km進みます。
移動距離 : 96km