Friction River Software

  • お問い合わせ

CakePHP5入門【CakePHP5基礎編②】オブジェクト指向

B美

今回は「オブジェクト指向」について説明していくよー

A子

いや、なんでよ

前回の続きなら、「CakePHP」の話じゃないの?

B美

その「CakePHP」自体が「オブジェクト指向」の考え方で作られてるからよ

まぁ、急がば回れってやつね

C菜

聞いたことあるです~

今のプログラムって、ほとんどが「オブジェクト指向」らしいですよ~

B美

そうなのよ

現在ほとんどのプログラム言語が「オブジェクト指向言語」になってるし、PHP言語も当然「オブジェクト指向言語」ってわけ

A子

それって、以前の文法編では出てこなかったよね?

B美

ええ、PHPって「非オブジェクト指向」的にも使えるし、「オブジェクト指向」的にも使えるのよ
以前の文法編では「非オブジェクト指向」的な説明しかしてこなかったからね

それじゃ、まずは「オブジェクト」とは何か?
はい、C菜!

C菜

英単語としての「Object」だったら「物体」とかそういう意味だったと思います~

未確認飛行物体(UFO)って、「Unidentified Flying Object」の略ですからね~

B美

正解!
「物」とか「物体」って意味ね

「オブジェクト指向」では、一個の独立した「モノ」と考えるわ
これすなわち、複数の変数や関数を組み合わせたものを一つの独立した「モノ」と考えて、生産性や再利用性を高めるための仕組みってわけ

プログラムの「部品化」と言っても良いかな

A子

「オブジェクト」という部品を用意しておけば、また別のプログラムで再利用しやすくなる…ってこと?

B美

正確に言えば、用意するのは「クラス」よ

「オブジェクト」という実体は、「クラス」という設計図から作られる

C菜

「クラス」が一つあれば、いくつでも「オブジェクト」を作ることができる…ってことですかぁ~?

B美

その通り!
まぁ、難しく考えずに「オブジェクト指向」とはそういうものだ…と思っておけば良いわ

んで、重要なキーワードが三つあります
それが

カプセル
継承けいしょう(インヘリタンス)
多態性たたいせい(ポリモーフィズム)

A子

うへぇー
なんだか難しそうな話になってきそう…

B美

最初に言っておくけど、Webフレームワークを利用するときって「カプセル化」さえ理解しておけば十分だからね

もちろん「継承」も使ってるんだけど、それはWebフレームワークのほうで使ってるだけで、我々が意識する必要は無いわ

C菜

それで~

カプセル化」って何ですか~?

A子

字面じづらだけ見ると「カプセルイヒ」に見えるわね

B美

「いひ」じゃねぇよ!

それはともかく…
「カプセル化」とは、変数(「フィールド」と呼びます)と関数(「メソッド」と呼びます)を一体化したものって意味ね

C菜

ん~
よく分からないです~

A子

以前の「関数」の授業のときに変数と関数を一緒に使ってたじゃん
あれとは違うの?

B美

そうねー
あのときのコードを「クラス」という集合の中にパッケージングしたようなイメージかな

まぁ、実際にやってみれば分かるから、サンプルコードを打ち込んで実行確認してみましょう
「html」ディレクトリの中にある「test9.php」は以下のようになってると思うんだけど…

<?php

$test_file = 'test1.php';
$result = myfile_read($test_file);
echo $result;

function myfile_read($filename) {
  if (file_exists($filename)) {
    $info_file = file_get_contents($filename, false);
    $result = htmlspecialchars($info_file, ENT_QUOTES);
    return nl2br($result);
  }
}

?>

これを次のように書き換えてから「test11.php」というファイル名で保存してね

<?php

class MyFileRead {
  private $test_file = '';

  function __construct($file) {
    $this->test_file = $file;
  }


  public function myfile_read() {
    if (file_exists($this->test_file)) {
      $info_file = file_get_contents($this->test_file, false);
      $result = htmlspecialchars($info_file, ENT_QUOTES);
      return nl2br($result);
    }
  }

}

$test = new MyFileRead('test1.php');
echo $test->myfile_read();

?>





B美

ソースコードの中の緑色で囲んでいるのが「クラス」よ
(クラス名は適当に「MyFileRead」としています)

そのクラスを「new」することで、「クラス」という設計図から「オブジェクト」という実体を生成して、それを$testという変数から参照しているの
(ちなみに、「オブジェクト」は「インスタンス」とも言います)

A子

だいだいの枠で囲んでいるのが「変数」で、functionで始まる青色赤色の部分が「関数」ってこと?

B美

そうよ
正確には「Fieldフィールド」と「Methodメソッド」だけどね

あ、メソッドの中で「__construct」だけはちょっと特殊なメソッド(「コンストラクタ」と呼びます)で、「new」する(「インスタンス化」と呼びます)際に必ず呼び出されるメソッドなの
(左端は半角の「アンダースコア」が二文字連続します)

C菜

「new」するときに渡した「test1.php」という文字列が「__construct」の「$file」に渡されて、それを「$this->test_file」に代入してますね~

というか、「$this->test_file」なんて無いですよ~?

B美

クラスの中で「フィールド」にアクセスしたいとき、フィールド名の「$」の次に「this->」を付けなきゃいけないって規則なの
(ちなみに、「->」は「アロー」と呼びます)

つまり、コンストラクタを呼び出した際に渡した文字列「test1.php」は、フィールド「$test_file」に格納されるってわけ

A子

あ、だから「myfile_read」メソッドの中でも「$this->test_file」って書き方になってるんだね

B美

その通り

理屈が分かればそんなに難しくは無いでしょ?

C菜

ん~
privateプライベート」とか「publicパブリック」って、何ですかぁ~?

B美

「private」が先頭に付いた「フィールド」や「メソッド」は、クラスの外から直接アクセスできない
(「クラス」内で使うことができるだけ…ってこと)

逆に「public」が付いたものは、クラス外からアクセス可能ってわけ…

基本的に「フィールド」は「private」に、「メソッド」は「public」にすることが多いわね
(これを「フィールド隠蔽いんぺい」と呼びます)

A子

「フィールド」を外から書き換えられちゃうと、しっちゃかめっちゃかになって、わけが分からなくなるから?

B美

まさにその通り!

私がこの処理を部品化するにあたって、「フィールド」については「インスタンス化」するときだけ設定できるようにしたってわけ
(クラス外から「フィールド」の読み書きをしたければ、別途publicな「メソッド」を追加するようにしてね)

なお、隠蔽いんぺいされている「フィールド」の値を読み出すメソッドのことを「Getterゲッター」、値を上書きするメソッドのことを「Setterセッター」と呼びます

C菜

この「オブジェクト」を参照している$testから「myfile_read」メソッドを呼び出す場合も「->アロー」が必要なんですよね~?

B美

そうよ
だからこそ、こういうこともできる

<?php

class MyFileRead {
  private $test_file = '';

  function __construct($file) {
    $this->test_file = $file;
  }

  public function myfile_read() {
    if (file_exists($this->test_file)) {
      $info_file = file_get_contents($this->test_file, false);
      $result = htmlspecialchars($info_file, ENT_QUOTES);
      return nl2br($result);
    }
  }
}

$test1 = new MyFileRead('test1.php');
$test2 = new MyFileRead('test2.php');
echo $test1->myfile_read()."<hr>".$test2->myfile_read();

?>

これを「test12.php」というファイル名で保存してね
赤字が追加した箇所)



C菜

二つのファイルの中身が連続して表示されました~

ん~、「設計図(クラス)が一つあれば、いくつでも実体(オブジェクト)を作れる」…って、こういうことなんですね~

A子

なるほどねぇ
これって、たしかにプログラムの「部品化」と言っても良い気がする

クラス内でどういう処理をしていようが関係ない、使い方さえ分かっていれば良い…ってことでしょ?

B美

そういうこと!
大規模なアプリケーションシステムを構築する際、複数のクラスを組み合わせていくことによって、格段に生産性が高まるって寸法よ

だからこそ、Webフレームワークでは必ず「オブジェクト指向」を使っているのよね

A子

そういえばさぁ

クラスの名前って「パスカルケース」にするって決まってるの?
(「○○ケース」という記法に関しては【コラム③】を参照のこと)

B美

別に規則ってわけじゃないわよ

でも、ほとんどのプログラマはそうしてるみたいだけどね
(CakePHPでもそうしています)

ま、とにかく、何となくでも「オブジェクト指向」という考え方が分かってもらえたかしら?

C菜

大丈夫です~

A子

まぁ、何となくは…(苦笑)