类中类外访问静态成员和普通成员 - PHP面向对象编程(OOP)

在php中的访问常量和静态量的方法总结

范围解析操作符 (::)

理解

类外使用

静态成员

  • $obj::$member1;//访问实例中的静态变量
  • ClassName::member3_visit2();//访问ClassName类中的静态方法

普通成员

  • echo $obj->member1;//访问实例中的变量
  • $obj->member2();//访问实例中的方法

常量

  • echo $obj::member1;//访问实例中的常量

类内使用

静态成员

  • self::$member2;//访问类中静态变量
  • ClassName::$member2;//访问类中静态变量(不建议使用)
  • self::member2;//访问类中静态方法

普通成员

  • echo $this->member2;//访问类中的变量
  • echo $this->member3();//方法中访问其他方法

常量

  • echo self::member2;//方法中访问常量

访问大纲

访问又分为静态成员的访问和普通成员访问

1:静态成员

  • 类内访问
self::$静态属性名 
self::$类常量名 

(其实类内页可以使用类外访问的类名的访问方式,不过考虑到了后期类名的更改,self就很方便的解决了这个问题)

  • 类外访问
类名::$静态属性名 
类名::$类常量名

2:普通成员

  • 类内访问
$this->属性名 
$this->方法名
  • 类外访问
$对象名->属性名 
$对象名->方法名 ($对象名 指的是实例化后的对象)

实战演示

一:静态成员属性的访问

1: 静态外部访问

<?php 
    class ClassName {
        //必须带“$”,否则是常量
        public static $member1 = '成员1';
    }
    $obj = new ClassName;
    //注意这里的“::”
    echo $obj::$member1;
?>

输出:

成员1

2:静态内部访问 (要知道,在类内部访问类成员必须定义一个方法来访问)

<?php 
    class ClassName {
        //必须带“$”,否则是常量
        public static $member2 = '成员2 <br />';
        
        public function member2() {
            echo self::$member2;
            //下面这条效果与上条相同,但不推荐使用(考虑继承中。类名会变的因素)
            echo ClassName::$member2;
        }
    }

    $obj = new ClassName;

    //类内访问类中静态成员
    $obj->member2();
?>

输出:

成员2
成员2
  • 1:类内访问类内成员首先要定义一个方法在方法内访问;
  • 2:最开始介绍到:类内其实可以使用类名的访问方式(echo ClassName::$member2;),考虑到项目后期可能会有类名更改问题,类内最好使用self来代替

(不过也正好证明了在类内访问其实就是使用类(名)进行指定类内的成员,讲这个是因为不同于普通成员中的类内访问方式--$this)

二:静态成员方法的访问

1:在类外访问类内静态方法

<?php 
    class ClassName {

        //静态方法
        public static function member3() {
            echo __METHOD__;//打印当前方法的方法名
        }

    }

    //类外访问类内静态方法
    ClassName::member3();
    
?>

输出:

ClassName::member3

在类外使用 类名::类中的方法名。 (__METHOD__指的是当前方法的方法名

2:在类内访问类内静态方法

<?php 
    class ClassName {

        //静态方法
        public static function member3() {
            echo __METHOD__.'<br />';//打印当前方法的方法名
        }

        //方法访问静态方法
        public function member3_visit1() {
            self::member3();
        }

        //静态方法访问静态方法
        public static function member3_visit2() {
            self::member3();
        }

    }

    $obj = new ClassName;

    $obj->member3_visit1();

    ClassName::member3_visit2();
    
?>

输出

ClassName::member3
ClassName::member3
  • 类内访问静态方法,同样需要在方法内访问,
  • 定义的方法可以使用普通方法进行访问,
  • 也可以定义一个同样是静态方法的方法来访问其他静态方法。。
  • (可能这句话有些绕,直接分析代码就行)

三:普通成员的属性访问

1:在类外访问

<?php 
    class ClassName {
        public  $member1 = '成员1 ';
    }

    $obj = new ClassName();

    //注意这里,不是“$member1”
    echo $obj->member1;
    
?>

输出:

成员1

这里有个重点,记得看后面

2:在类内访问

<?php 
    class ClassName {

        public  $member2 = '成员2 ';

        function member2() {
            echo $this->member2;
        }
    }

    $obj = new ClassName();

    $obj->member2();
    
?>

输出:

成员2

你可能已经发现了,为什么在最开始静态访问演示的时候,

        function member2() {
            echo $this->member2;
        }
$obj->member2();

上面变量名都有$符号,而这里却没有。
要知道这里面php里面有个可变属性和可变方法。下面来演示一下。

类中类外访问静态成员和普通成员 - PHP面向对象编程(OOP)

在外面如果不带$,就是代表着取obj这个对象中进行访问查找 为此名字的成员。

一旦加上$,因为在类外部,就会被当做变量来找,所以就会报错。当然可以这样写 ⬇

<?php 
    class ClassName {
        public  $member1 = '成员1 ';
        public  $member2 = '成员2 ';

        function member2() {
            echo $this->member2;
        }
    }

    $obj = new ClassName();

    $member1 = 'member1';

    echo $obj->$member1;

    $obj->member2();
    
?>

输出:

成员1 成员2

(其中一个值当作另一个的名)当obj进行指向访问的时候 $member就会被解析为 member

四:普通成员的方法访问

1:类外访问

<?php 
    class ClassName {
        
        public  $member2 = '成员2,<br /> ';

        function member2() {
            echo $this->member2;
        }

        public function member3() {
            echo __METHOD__;//打印当前方法的方法名
        }

    
    }

    $obj = new ClassName();

    $obj->member2();

    $obj->member3();

    
?>

输出

成员2,
ClassName::member3

2:类内访问

<?php 
    class ClassName {

        public function member3() {
            echo __METHOD__.'<br />';//打印当前方法的方法名
        }

        public function member4() {
            echo $this->member3();

            //与上面一行代码同样的意思
            $member3 = 'member3';
            echo $this->$member3();
        }

    }

    $obj = new ClassName();

    $member4 = 'member4';
    $obj->$member4();

    
?>

输出:

ClassName::member3
ClassName::member3

再次直接写了 可变的 形式,方法同样适用。

思考(这样的好处,以后比如前台页面的访问可以都给定 一个页面,页面中定义好类,类中定义好各个对象,通过页面点击传递要制定的对象名也就是方法名,然后使用可变的形式,来随时替换到变量,而调用只需要调用一次 $obj->变量名)

五:类常量的访问

首先:类常量就是const定义的常量。

要记住:类常量只能用const来定义

1:类外访问

<?php 
    class ClassName {
        const member1='类常量1<br />';
    }

    $obj = new ClassName;

    echo $obj::member1;

?>

输出:

类常量1

2:类内访问

<?php 
    class ClassName {

        const member2='类常量2<br />';

        public function visit() {
            echo self::member2;
        }
    }

    $obj = new ClassName;

    $obj->visit();

?>

输出

类常量2

跟静态方式其实一样,但唯一的差别就是最前面中的 注释,变量名在类内声明的时候没有 $

注意:(至于可变的形式,在常量中类内或者类外访问都不可以

<?php 
//以下代码采用可变方法访问常量,会报错
    class ClassName {

        const member1='类常量1<br />';
    }

    $obj = new ClassName;

    //可变方法
    $member1 = 'member1';
    echo $obj::$member1;

?>

不过在调用方法的时候可以使用可变的形式,毕竟跟常量也没太大关系。

类与对象的内存关系

我们上面都知道,静态访问和类常量都是使用 类名来访问,而其他都是通过实例化的对象来访问。

其实:

在类内部,是分空间的,静态成员一般保存在类空间里,而像其他的 普通属性都是保存在对象的空间里(这里的对象指的是实例化的对象)

而唯一特殊的就是 成员方法,它按我们的访问方式是通过 对象来访问的,但是它并不存储在对象的空间里,相反存储在了类的空间里

我们来使用前面的代码 证明一下:

<?php 
    class ClassName {
        public  $member1 = '成员1 ';
        public  $member2 = '成员2,<br /> ';
        function member2() {
            echo $this->member2;
        }


        //两个成员方法的访问
        public function member3() {
            echo __METHOD__.'<br />';//打印当前方法的方法名
        }


        public function member4() {
            $member3 = 'member3';
            echo $this->member3();
        }

    }

    $obj = new ClassName();

    $obj->member1 = '成员5';
    echo $obj->member1;

    $member1 = 'member1';
    echo $obj->$member1;
    $obj->member2();


    $obj->member3();


    $member4 = 'member4';
    $obj->$member4();


    $obj1 = new ClassName;
    echo $obj1->member1;
    
?>

输出

成员5成员5成员2,
ClassName::member3
ClassName::member3
成员1

可以看出 新声明的obj1 明显没有被前面的 obj 改变的成员5 而改变!

就算是这个特殊的成员方法虽然存在了类空间里,但是仍不会被改变。

这样的原因就是因为存储在了 实例化的对象的空间里,一个实例化中的改变不会影响其他实例化对象的改变

<?php 
    class ClassName {
        //两个静态属性
        public static  $member1 = '静态成员1 <br /> ';
        public static  $member2 = '静态成员2 <br /> ';

        //两个静态方法
        public static function member3() {
            echo __METHOD__.'<br />';//打印当前方法的方法名
        }

        public function member3_visit1() {
            self::member3();
        }

        public static function member3_visit2() {
            self::member3();
        }

        public function member2() {
            echo ClassName::$member2;
        }

    }

    $obj = new ClassName();

    //类外访问类中静态属性
    ClassName::$member1 = '11131313';
    echo ClassName::$member1;

    //类内访问类中静态属性
    $obj->member2();

    //类外访问类内静态方法
    ClassName::member3();

    $obj->member3_visit1();

    ClassName::member3_visit2();
    

    $obj1 = new ClassName;
    echo ClassName::$member1;

    
    
?>

而在类空间中除了不能改变的,常量外的静态成员,只要被改变,其他的实例化对象同样就会被调用。如上所显示。

参考文章

php

调用父类构造方法 - PHP面向对象编程(OOP)

2022-8-25 14:56:51

php

里氏替换原则 - PHP面向对象编程(OOP)

2022-8-26 17:03:09

⚠️
Npcink上的部份代码及教程来源于互联网,仅供网友学习交流,若您喜欢本文可附上原文链接随意转载。
无意侵害您的权益,请发送邮件至 1355471563#qq.com 或点击右侧 私信:Muze 反馈,我们将尽快处理。
0 条回复 A文章作者 M管理员
    暂无讨论,说说你的看法吧
个人中心
购物车
优惠劵
今日签到
有新私信 私信列表
搜索