【PHP・初心者向け】Classを使った書き方
Web開発の現場では、オブジェクト指向を使ったコーディングが当たり前のように行われています。
オブジェクト指向といえば、難しいイメージを持たれている方も多いと思いますが、基本的にはClassを使ってプログラミングを設計・実装することと考えてもらって大丈夫です。
しかし、プログラミングの学習をはじめて間もない方にとって、Classの考え方は少しわかりにくいかもしれません。ですが、Classを使うことに慣れると、とても柔軟なプログラムを書くことができますし、プログラムの設計力も上がります。
この記事では、PHPを使ったオブジェクト指向のプログラミングと、Classの基本的な考え方と使い方をお伝えします。
オブジェクト指向とは
オブジェクト指向とは、部品単位の固まりでプログラムを組み立てることです。と言っても、よくわからないかもしれません。オブジェクト指向の説明は前提知識を求めるものですし、ベテランによっても意見が分かれる厄介なものです。
仮にオブジェクト指向の話を詳しくするのであれば、話が壮大すぎて、この記事にはとても書ききれないボリュームになります。そこで、ここでは簡単にオブジェクト指向を使うメリットだけ説明します。
オブジェクト指向でプログラムを書く理由は、変更が発生したときに柔軟に対応ができるからです。要は、柔軟な設計を行うためにオブジェクト指向が役立つのです。
とはいえ、上の説明だけでは雲をつかむような話になってしまうので、今回はシンプルな例をイメージにし、それに付随したサンプルコードを提示して説明します。
今回のサンプルのイメージ
サンプルイメージはシンプルです。下のイメージを見て下さい。
Dog Class
変数1:$name (名前)
関数1:getName (名前を取得する関数)
Dachshund Class (Dog Classを継承するClass)
変数1:$sound (名前)
関数1:barking (名前を取得する関数)
イメージには2つのClass、DogとDachshund(ダックスフント)が存在していますが、今はDogの方だけに注目して頂ければ大丈夫です。
Dogは名前である変数$nameと関数getNameを持っています。
Dachshund(ダックスフント)は、Dogから派生したオブジェクトです。こちらは、鳴き声の変数$soundと変数barkingを持っています。
このイメージに沿って、PHPのサンプルコードを順番に説明していきます。
Classとは
Classを簡単に説明するなら、プロパティ(変数)とメソッド(関数)を持ったプログラムの固まりです。
オブジェクト指向とは、このClassという部品を複数作り、連携させることで、大きなプログラムを組み上げていくイメージです。
また、Classには別のClassと連携できる機能があります。これを「継承」と呼びます。継承に関しては、後ほど詳しく説明します。
プロパティ
プロパティとは、Class内で使われる変数のことを意味します。プロパティの元々の意味ですが、「物体の特性や属性」を指しています。つまり、Classというオブジェクトに所属している変数だから、プロパティと呼ばれているのです。
メソッド
メソッドとは、Class内で使われる関数のことです。こちらも、プロパティと同じように、Classに所属している関数となります。所属しているとは、どういう意味か気になっている方もいると思います。所属しているという意味は、後述するインスタンスのほうで説明します。
Classの実装例
Classのサンプルは以下の通りです。
// ①DogのClassを定義
class Dog {
// ②プロパティを定義。今回は名前なので、$nameとしている
private $name;
// ③インスタンス化するときに引数を受け取れるようにしている
public function __construct($name) {
$this->name = $name;
}
// ④名前を取得するメソッドを追加
public function getName() {
return $this->name;
}
}
まず、先ほどイメージにて説明したDogというClassを①で定義しています。
②では、プロパティを定義しています。今回は名前なので、変数名は$nameとしています。
③のpublic function __constructというのは、Classをインスタンス化したときに値を受け取るメソッドです。これは、インスタンスのところで詳しく説明します。
④では、名前を取得するメソッドgetNameを追加しています。後でこのメソッドを使って、Dogの名前を取得します。
インスタンスとは
インスタンスとは、プログラム内でClassを扱えるようにすることです。
Class自体は、プログラミングしただけでは使えません。インスタンス化して、はじめてClassの処理を実行することができます。
インスタンスの実装例
// ⑤Dog Classをインスタンス化している
$dog = new Dog("John");
// ⑥インスタンス化したメソッドを使って名前を取得し、$dog_nameに代入
$dog_name = $dog->getName();
// ⑦$dog_nameを表示
echo "名前: " . $dog_name . "\n";
⑤にて、Classをインスタンス化しています。
new ~
とありますが、これはインスタンス化するときのおまじないとして考えてください。
先ほどのサンプルコードにあった、__constructがここで生きてきます。
コードの中で、 new Dog(“John”)
という個所がありますが、Classの中で__constructメソッドを定義していると、()の中に引数を取れるようになります。今回の引数は”John”ですね。
さらに⑥では、インスタンス化したメソッドを使って名前を取得し、$dog_name
に代入しています。
通常、privateプロパティである$nameには直接アクセスできません。ですので、このようにメソッドを使ってClass内にあるプロパティ値を取得します。
プロパティ$name前に記述している"private"ですが、これをアクセス修飾子と呼びます。アクセス修飾子により、プロパティへのアクセス権限を指定しています。
アクセス修飾子には、public, protected, privateの3つの種類が存在します。
それぞれの特徴は以下の通りです。
- pubic:クラス内、クラスの外、どちらからでもアクセスできる
- private:privateが宣言されているクラス内からだけ、アクセスできる
- protected:protectedが宣言されているクラス内、もしくは継承しているクラス(サブクラス)からはアクセスできる
⑦では、単純にgetNameメソッドから取得したDogの名前をechoで表示しています。
Classの継承
Classの継承は新しいClass(Dachshund)に、すでに存在するClass(Dog)と同じ機能をそのまま引き継がせたい場合に使用します。
継承を受けたClassは、継承する元のClassの機能をそのまま使えるようになります。
Class継承の実装例
// ⑧Dachshund ClassはDog Classを継承
class Dachshund extends Dog {
// ⑨新たなプロパティ$soundを定義
private $sound = "Bow!!";
// ⑩新たなメソッドbarkingを定義
public function barking() {
return $this->sound;
}
}
// ⑪Dachshundを名前”Doh”でインスタンス化
$dachshund = new Dachshund("Doh");
// ⑫インスタンス化した後、Dogから継承したgetNameメソッドで名前を取得
$dachshund_name = $dachshund->getName();
// ⑬Dachshundで定義したbarkingメソッドで鳴き声を取得
$dachshund_sound = $dachshund->barking();
// ⑭名前と鳴き声を表示
echo "名前: " . $dachshund_name . "\n 鳴き声: " . $dachshund_sound;
今回は、Dogを継承したDachshund Classを例として挙げます。
Classを継承する方法ですが、⑧のようにextendを使って継承元のClassを指定するだけです。継承した後は、通常のClassと同じようにプロパティおよびメソッドを作成できます。
⑨では新たなプロパティ$soundを「鳴き声」として、⑩では新たなメソッドbarkingを「鳴き声を取得する関数」として定義しています。
さらに、⑪ではDachshundをインスタンス化しています。このとき、名前を変数としてインスタンス化していますが、これはDog Classに存在する__constructメソッドが呼び出されるからです。
継承元Classにあるメソッドは継承先のClassでも使えるので、このような現象が起きます。
⑫ではDog ClassのgetNameメソッドを利用して名前を取得しています。これも⑪と同じ理由です。
⑬においては、Dachshund Classのbarkingメソッドを実行しています。これはDachfund Class独自のメソッドで、Dog側では使えません。
最後に⑭で、Dachshundの名前と鳴き声を表示しています。
サンプルコード全体
最後にサンプルコード全体を実行してみましょう。
以下のサンプルコードをコピペすれば、実行できるはずです。推奨環境はPHP7.2です。
<html>
<title>Class サンプル</title>
<h1>Class サンプル</h1>
<?php
// ①DogのClassを定義
class Dog {
// ②プロパティを定義。今回は名前なので、$nameとしている
private $name;
// ③インスタンス化するときに引数を受け取れるようにしている
public function __construct($name) {
$this->name = $name;
}
// ④名前を取得するメソッドを追加
public function getName() {
return $this->name;
}
}
// ⑧Dachshund ClassはDog Classを継承
class Dachshund extends Dog {
// ⑨新たなプロパティ$soundを定義
private $sound = "Bow!!";
// ⑩新たなメソッドbarkingを定義
public function barking() {
return $this->sound;
}
}
?>
<h2>Dogの名前をインスタンスとメソッドを使って取得</h2>
<?php
// ⑤Dog Classをインスタンス化している
$dog = new Dog("John");
// ⑥インスタンス化したメソッドを使って名前を取得し、$dog_nameに代入
$dog_name = $dog->getName();
// ⑦$dog_nameを表示
echo "名前: " . $dog_name . "\n";
?>
<h2>Dachshund(ダックスフント)の名前と鳴き声インスタンスとメソッドを使って取得</h2>
<?php
// ⑪Dachshundを名前”Doh”でインスタンス化
$dachshund = new Dachshund("Doh");
// ⑫インスタンス化した後、Dogから継承したgetNameメソッドで名前を取得
$dachshund_name = $dachshund->getName();
// ⑬Dachshundで定義したbarkingメソッドで鳴き声を取得
$dachshund_sound = $dachshund->barking();
// ⑭名前と鳴き声を表示
echo "名前: " . $dachshund_name . "\n 鳴き声: " . $dachshund_sound;
?>
</html>
また、サンプルコードの実行結果は以下のようになります。
Class サンプル
Dogの名前をインスタンスとメソッドを使って取得
名前: John
Dachshund(ダックスフント)の名前と鳴き声インスタンスとメソッドを使って取得
名前: Doh
鳴き声: Bow!!
まとめ
今回はPHPのClassをサンプルコードを交えながら、入門者向けに説明しました。
Classを使いこなせるようになれば、PHPエンジニアとして大きく成長できるので、しっかりものにしていきましょう。