Хабр Курсы для всех
РЕКЛАМА
Практикум, Хекслет, SkyPro, авторские курсы — собрали всех и попросили скидки. Осталось выбрать!
class A {
function foo() {
if (!isset($this) || get_class($this) !== __CLASS__) {
$self = new A;
return $self->foo();
}
// do smth
}
}
A::foo();
<?php
class A {
function x() {
var_dump(get_class($this));
}
}
class B {
function __construct() {
A::x();
}
}
new B;
PHP Strict standards: Non-static method A::x() should not be called statically, assuming $this from incompatible context in test.php on line 9
string(1) "B"
isset($this) && $this instanceof get_called_class()
class A {
public function __construct() {
A::x();
}
function x() {
var_dump(get_class($this));
}
}
new A;
class A {
public function __construct() {
A::x();
}
function x() {
var_dump(get_class($this));
}
}
class B extends A {
function __construct() {
A::x();
}
}
new B;
The pseudo-variable $this is available when a method is called from within an object context. $this is a reference to the calling object (usually the object to which the method belongs, but possibly another object, if the method is called statically from the context of a secondary object).
<?php
class A
{
public function DynamicMethod()
{
var_dump(debug_backtrace());
return 'I am Dynamic';
}
}
echo A::DynamicMethod();
/*
Вывод:
array (size=1)
0 =>
array (size=6)
'file' => string 'C:\OpenServer\domains\test1.ru\index.php' (length=40)
'line' => int 11
'function' => string 'DynamicMethod' (length=13)
'class' => string 'A' (length=1)
'type' => string '::' (length=2)
'args' =>
array (size=0)
empty
I am Dynamic
*/
?>
parent::__construct();<?php
class A { function test() { echo $this->property . " A\n"; } }
class B extends A { function test() { echo $this->property . " B\n"; } }
class C extends B {
public $property;
function test() { echo $this->property . " C\n"; }
function run() { $this->property = "TEST"; A::test(); }
}
$obj = new C;
$obj->run();
мой пример хотя бы может иметь какую-то отдаленную практическую ценность
Чтобы окончательно запутать людей, которые будут поддерживать код после вас — да.
По факту — «вы не должны этого хотеть»
class A {
static $i;
public static function i(){
return self::$i? self::$i: self::$i = new static;
}
function say(){ echo get_class($this) . "\n"; }
}
class B extends A{}
class C extends A{}
B::i()->say();
C::i()->say();
B
B
class A {
public static function i(){
static $i;
return $i? $i: $i = new static;
}
function say(){ echo get_class($this) . "\n"; }
}
class B extends A{}
class C extends A{}
B::i()->say();
C::i()->say();
B
C
class A {
public static function i(){
$f = function($name){
static $i;
return $i? $i: $i = new $name;
};
return $f(get_called_class());
}
function say(){ echo get_class($this) . "\n"; }
}
class B extends A{}
class C extends A{}
B::i()->say();
C::i()->say();
B
C
function j($name){
static $i;
return $i? $i: $i = new $name;
}
class A {
public static function i(){
return j(get_called_class());
}
function say(){ echo get_class($this) . "\n"; }
}
class B extends A{}
class C extends A{}
B::i()->say();
C::i()->say();
B
B
B::i()C::i()class A {
public static function i(){
static $i;
var_dump($i);
return $i? $i: $i = new static;
}
function say(){ echo get_class($this) . "\n"; }
}
class B extends A{}
class C extends A{}
B::i()->say();
C::i()->say();
/*
Вывод:
null
B
null
C
*/
<?php
class A {
public static function Method($value)
{
static $v;
$v=$v ? : $value;
echo'Я метод класса '.get_called_class().' $v='.$v.'<br>'.PHP_EOL;
}
}
class B extends A{}
class C extends A{}
B::Method(5);
C::Method(8);
?>
Особенности при перехватах вызовов методов с помощью __call() и __callStatic() в PHP