同福

PHP的new self()和new static()的区别【20210610】

介绍

介绍

福哥在阅读一些“老外”写的PHP代码的时候发现了一些比较奇怪的语法,他们会使用self或static作为new关键字的对象名称,这个到底是什么意思啊??

self()

self字面意思是“自己”,那么是不是self()就是只代码所在的对象自己呢?

普通对象

代码

class TFUser{
    public function __construct(bool $fromCallByFunc=false){
        if($fromCallByFunc){
            echo "福哥创建了". get_class($this). "的实例<br />";
        }
    }

    public function call_by_self(){

        return new self(true);
    }
}

class myUser extends TFUser{

}

$myUser = new myUser();
$myUser->call_by_self();

效果

home/topic/2021/0610/14/14fa531ebbdb7acc79fac8553c6a4b8d.png

可以看到普通对象里面self指向的是方法所属对象本身,本例中就是TFUser这个对象。

继承对象

代码

class TFUser{
    public function __construct(bool $fromCallByFunc=false){
        if($fromCallByFunc){
            echo "福哥创建了". get_class($this). "的实例<br />";
        }
    }
}

class myUser extends TFUser{
    public function call_by_self(){

        return new self(true);
    }
}

$myUser = new myUser();
$myUser->call_by_self();

效果

home/topic/2021/0610/14/e54193d266625372100c334d55002834.png

可以看到继承对象里面self指向的也是方法所属对象本身,本例中就是myUser这个对象。

static()

static字面意思是“静态”,这个不太好理解,上代码测试一下。

普通对象

代码

class TFUser{
    public function __construct(bool $fromCallByFunc=false){
        if($fromCallByFunc){
            echo "福哥创建了". get_class($this). "的实例<br />";
        }
    }

    public function call_by_static(){

        return new static(true);
    }
}

$myUser = new TFUser();
$myUser->call_by_static();

效果

home/topic/2021/0610/14/14fa531ebbdb7acc79fac8553c6a4b8d.png

可以看到普通对象里面static指向的还是方法所属对象本身,本例中就是TFUser这个对象。

继承对象

代码

class TFUser{
    public function __construct(bool $fromCallByFunc=false){
        if($fromCallByFunc){
            echo "福哥创建了". get_class($this). "的实例<br />";
        }
    }
}

class myUser extends TFUser{
    public function call_by_static(){

        return new static(true);
    }
}

$myUser = new myUser();
$myUser->call_by_static();

效果

home/topic/2021/0610/14/e54193d266625372100c334d55002834.png

可以看到继承对象里面static指向的也还是方法所属对象本身,本例中就是myUser这个对象。

区别

可以发现self和static在普通对象和继承对象测试中的效果似乎都是一样的,那么他们之间有什么区别呢?

代码

class TFUser{
    public function __construct(bool $fromCallByFunc=false){
        if($fromCallByFunc){
            echo "福哥创建了". get_class($this). "的实例<br />";
        }
    }

    public function call_by_self(){

        return new self(true);
    }

    public function call_by_static(){

        return new static(true);
    }
}

class myUserA extends TFUser{

}

class myUserB extends TFUser{

}

$myUserA = new myUserA();
$myUserA->call_by_self();
$myUserA->call_by_static();

$myUserB = new myUserB();
$myUserB->call_by_self();
$myUserB->call_by_static();

效果

home/topic/2021/0610/14/a38376ffb4a78307584993fb846db776.png

这下看明白了吧?

self在任何时候都是指向方法所属的对象本身,无论这个方法是继承调用还是直接调用。

static则指向实例化的对象本身,无论这个对象是普通对象还是继承对象。

总结

看完了self和static的用法和区别之后,相信我们大家都会有一些想法了吧?

使用self可以创建对象自身的实例这个没什么可说的了,但是使用static居然可以创建继承“我”的对象的实例,这个太牛了有没有!!!