PHPでクラスを定義したときに、クラスの中のプロパティやメソッドを呼び出す方法に「::」がある。
使い方は「クラス名::$プロパティ名」や「クラス名::メソッド名()」。ただしこれ通りにしてもsyntax errorで呼び出せない時がある。
#エラーの例
PHP Fatal error: Uncaught Error: Access to undeclared static property Hello::$msg in /workspace/Main.php:11
この理由と対処法について。
「::」はクラスプロパティとクラスメソッドを呼び出す
そもそも「::」はインスタンス化せずともクラスの中のプロパティやメソッドが呼び出せる便利記号ではない。
これは、クラスメソッドとクラスプロパティという通常のメソッドやプロパティとは異なるクラス固有の変数や関数を呼び出すための記号。
結論から言うと、プロパティとメソッドの前に「static」の文字があるかないかで決まる。
staticの記載があるプロパティとメソッドは「::」で抜き出せる。
クラスメソッドとクラスプロパティとは何か?
クラスの中で定義するメソッドやプロパティは、通常、インスタンス毎に入る値や処理(渡す引数)が異なる。
しかし、クラスメソッドやクラスプロパティはインスタンス毎によらず、すべてのインスタンスで共有するデータ。
プロパティとクラスプロパティの違い実例
実際に見てみると早い。注目すべきはstaticの有無。
「::」を使ってプロパティを呼び出す場合
▼通常のプロパティ(staticなし)
class Hello {
public $msg = 'Hello World';
}
echo Hello::$msg;
実行すると、Helloというクラスの中に$msgというクラス固有のクラスプロパティがないのでエラーになる。
#実行結果
PHP Fatal error: Uncaught Error: Access to undeclared static property Hello::$msg in /workspace/Main.php:
▼クラスプロパティの場合(staticあり)
publicと$msgの間に「static」を追記。
class Hello {
public static $msg = 'Hello World';
}
echo Hello::$msg;
#実行結果
Hello World
エラーが出ずに実行結果が正しく表示された。これは、指定したクラスプロパティが存在するため。
インスタンスを使ってプロパティを呼び出す場合
先ほどと逆に、newでインスタンスを生成してプロパティを呼び出す場合は、staticありのプロパティは呼び出せない。
▼通常のプロパティ(staticなし)
class Hello {
public $msg = 'Hello World';
}
$obj = new Hello();
echo $obj->msg;
実行すると、Helloというクラスの中の$msgというプロパティの値を呼び出す。※インスタンスのプロパティを呼び出す場合$は不要。
#実行結果
Hello World
▼クラスプロパティの場合(staticあり)
publicと$msgの間に「static」を追記した場合。
class Hello {
public static $msg = 'Hello World';
}
$obj = new Hello();
echo $obj->msg;
#実行結果
PHP Notice: Accessing static property Hello::$msg as non static in /workspace/Main.php on line 10
PHP Warning: Undefined property: Hello::$msg in /workspace/Main.php on line 10
インスタンスからクラスプロパティ(static property)にアクセスしようとしているというエラーが表示される。
このようにインスタンスからは、クラスプロパティにアクセスできない。
メソッドの場合
メソッドの場合も同様に、staticがあれば「::」で呼び出せる。staticがなければ「::」では呼び出せない。
▼通常のメソッド(staticなし)
class Hello {
public function greeting(){
echo "Hello World";
}
}
Hello::greeting();
#出力結果
PHP Fatal error: Uncaught Error: Non-static method Hello::greeting() cannot be called statically in /workspace/Main.php:22
▼クラスメソッド(staticあり)
publicとfunctionの間に「static」を追記。
class Hello {
public function greeting(){
echo "Hello World";
}
}
Hello::greeting();
#出力結果
Hello World
まとめ
「::(ダブルコロン2つ)」はクラスからメソッドやプロパティを呼び出しているが、呼び出せるのはstaticがついているもののみ。
インスタンスからプロパティとメソッドを呼び出すのとは全く異なるので注意が必要。