🙆‍♀️

【PHP】ざっくりオブジェクト指向 - staticと遅延静的束縛

2022/11/15に公開約2,400字

staticプロパティとstaticメソッド

前回までは、インスタンスを生成してプロパティとメソッドを使いました。インスタンスのプロパティとメソッドとは別に、クラスのプロパティとメソッドにアクセスすることもできます。これらをstaticプロパティ(静的プロパティ)とstaticメソッド(静的メソッド、クラスメソッド)とよびます。staticプロパティとstaticメソッドはクラスごとにあり、プロパティやメソッドのようにインスタンスごとにはありません。

例えば、生成したインスタンス数$numberをもちたい時にstaticプロパティを使います。生成したインスタンス数はクラスごとの値ですので、staticプロパティに値をセットするのがよいです。また、staticプロパティにアクセスするだけのメソッドgetNumber()は、インスタンスにある必要がないのでstaticメソッドを使うのがよいです。

Person3のクラス定義です。staticをつけるだけで、staticプロパティ$numberstaticメソッドgetNumber()を定義できます。

https://github.com/hyada/object-oriented-programming/blob/15f6b4e4a07b27a839ca65ff1bca6e209ccfc7cb/code/sample5-1.php

転送コール

子クラスから親クラスのメソッドをコールしたい時はparent::を使います。self::parent::を転送コールとよび、クラス定義でのみ使えます。parent::で親クラスのメソッドをコール後に処理を追加することで、子クラスのメソッドで処理を追加することができます。親クラスのメソッドを利用できることで、子クラスのメソッドでは変更分だけをコーディングだけですみます。

親クラスを転送コール
        parent::__construct($name, $age);

クラス内ではself::で自クラスのstaticプロパティとstaticメソッドにアクセスします。

staticプロパティにアクセス
        ++self::$number;

クラス外からはPerson3::getNumber()のように、クラス名を指定してstaticメソッドにアクセスします。

クラス外からstaticメソッドをコール
$person_number = Person3::getNumber();
実行結果
hiroyuki@blocs ~ % php sample5-1.php   
int(2)
hiroyuki@blocs ~ %

クラスから複数個のインスタンスが生成されるため、どのプロパティにアクセスするかを特定できないからです。

遅延静的束縛

PHPの中でも最強クラスの攻撃力がありそうな、遅延静的束縛でこの記事をしめたいと思います。転送コールparent:: self::で対応できないケースに、static::で転送コールする時に遅延静的束縛が発揮されます。

親クラスPersonでは親クラスのプロパティ$ageを、子クラスPerson2では子クラスのプロパティ$ageにアクセスする時に、転送コールstatic::を使います。転送コールself::$ageは常にPerson$ageにアクセスしますし、Personに親クラスがないため、転送コールparent::$ageは使えません。

https://github.com/hyada/object-oriented-programming/blob/046860b9101905ece398a66eca8bf72461e86cf7/code/sample7-1.php

実行結果
hiroyuki@blocs ~ % php sample7-1.php 
int(26)
int(28)
hiroyuki@blocs ~ %

staticは直近の非転送コールPerson:: Person2::を保存して、そのクラスに転送します。遅延静的束縛は英語で Late Static Bindings ですが、直近のクラス Latest class とstaticを結びつける Bindings ということなのでしょうか。この翻訳であってるんですかね?

Discussion

ログインするとコメントできます