質問: new C(); $c->test(); //fails ?>``` ``` php //結果 success! success! success! Fatal error: Call to private method C::foo() from context 'A' in /tmp/test.php on line 9 ``` php.netの遅延静的束縛のページにあるコードなのですが、なぜこの結果なるのかわかりません。 > > より正確に言うと、遅延静的束縛は直近の "非転送コール" のクラス名を保存します。 静的メソッドの場合、これは明示的に指定されたクラス (通常は :: 演算子の左側に書かれたもの) となります。静的メソッド以外の場合は、**そのオブジェクトのクラス**となります。 > > > php.netの解説に上記のようにあるのですが、「そのオブジェクトのクラス」が何を指すのかわかりません。 上記の例でstaticはクラスAを指す、ということでしょうか? それと static::foo(); の部分は静的でないメソッドを静的に呼び出していると思うのですが、 http://php.net/manual/ja/language.oop5.static.php ↑の注意書きに > > 警告 > > PHP 7 では、static でないメソッドを静的にコールすることが非推奨になりました。 E_DEPRECATED レベルの警告が発生します。 将来的にはサポートされなくなる見込みです。 > > とあります。 > > > static::foo(); はこの警告に当てはまるコード、という理解で良いですよね?
回答: > > php.netの解説に上記のようにあるのですが、「そのオブジェクトのクラス」が何を指すのかわかりません。 > > 上記の例でstaticはクラスAを指す、ということでしょうか? > > > いえ、**継承された後のクラス**を指しています。だから、`C`のほうでは`private C::foo`を`A`から呼び出そうとして失敗しています。 > > static::foo(); > > の部分は静的でないメソッドを静的に呼び出していると思うのですが > > > いえ、`static::`や`parent::`による呼び出しは**インスタンスメソッド**を呼ぶこともできるもので、警告は無関係です。