18.PHP面向对象-高级实践

继承

运动员 所拥有的的属性和方法:
姓名 身高 体重 所在球队 球员号码 讲话 行走 扣篮 运球

演员 所拥有的的属性和方法:
姓名 身高 体重 艺名 所属公司 讲话 行走 唱歌 演戏

我们可以把公用的成员提取出来,他们拥有部分相同的属性和方法 因为他们都是人类。

继承的好处

  • 父类里面定义的成员可以不用再子类中重复定义,节约了变成的时间和代价

  • 同一父类的子类拥有相同的父类定义类的成员,因此外部调用他们的时候可以一视同仁

  • 子类可以修改和调整父类定义的类成员,我们称之为重写,一旦类修改了,就按照子类修改之后的功能执行

在php中可以用extends关键字来标示类的继承,后面跟父类的类名,extends后面只能跟一个类的类名,这就是php中的单继承原则

访问控制

关键字 特点
public 公有类成员 可以在任何地方被访问
protected 受保护的类成员,可以被其自身以及子类访问
private 私有的类成员,只能被自身访问

静态成员,static

好处

使类的静态成员特性就可以共用属性。

定义

静态属性定义时在访问控制关键字后面添加static关键字即可

调用

在类定义中使用静态成员的时候,用self或者static关键字紧跟着::操作符调用。

self与static的差异
其差异体现在继承时:slef永远绑定的是代码所在类;static调用时确定哪个类。常用static,更加符合常规逻辑。

定义外部访问静态属性,我们可以用类名加::操作符的方法来访问类的静态成员;使用parent关键字技能访问父类的静态成员。

静态方法里面只能访问静态属性

访问 ClassName::method() 或者 ClassName::$property

如何使用静态成员

例如:老师要统计学生的数量,问题是,如果所有的操作,严格按照面向对象的思想去做,意味着会出现无数个对象,其中很多,仅仅为了辅助完成个别功能,也要定义类,实例化对象, 万物万事都是对象,难道真的要定义万事万物?

此时,通过在某些类上增加静态成员的方式,完成某类特定的操作。

总结:当使用静态成员时,认为被所有的当前类对象所共享的数据和操作,应该声明成静态的。被对象所独有的数据和操作,应该声明成为非静态的。

语法细节

无论采用对象还是类,都可以调用静态、非静态方法。但是涉及到语法严谨规范化。

类常量

常量一旦定义,不能修改,选择用常量的原因:之一,语法层面保证,数据不会被修改;之二,将特定的数据语义化,得到计算快,同时表述有逻辑含义。

定义常量

如果需要类,拥有某个不需要变化的数据,则可以通过定义类常量完成。定义通过const关键字,执行名字和值,不需要访问修饰。

使用常量

通过::访问

设计相关

设计层面,当需要完成某种约束规范时,怎么去实现?

抽象 abstract

通过关键字abstract,限制类、方法。称之为抽象类、抽象方法

抽象类

限制之后,该类就不能用于实例化对象。

例如,在设计商品管理系统的时候,认为所有的商品(book,phone)应该都是某种类型的商品的实例,而不是goods对象,goods类仅仅是为了提供所有类型商品的公共属性和操作。如果满足设计需求,语法上可将goods定义为抽象,从而保证不会被实例化。

其作用是:语法层面的限制。

抽象方法

仅仅包含了方法的声明(方法名和形参列表),没有方法的实现(方法体),称之为抽象方法。

使用抽象方法的原因:需要限制子类,一定要存在,但是实现可以是不同的方法。例如任何类型的商品,都有获取商品名称的能力(方法),不同类型的商品获取的方式不一样。

终极 final

final可以用来修饰限制类、方法,也称之为终极类、终极方法。

final类

final修饰类导致类不能被继承使用。一个fianl类仅仅用来被实例化。

为什么要设计为final类呢?

设计层面,类达到某个级别的时候,就不能再继承拓展了。

final方法

final修饰方法导致方法不能被子类重写。

作用在于:为了保证所有的子类中实现完全一致的方法,才会将父类的方法声明为终极方法。

例如:价格是所有商品统一计算的,可以将价格获取定义在good类中,并声明终极方法,此时所有的子类使用的计算价格的方法都是统一的。

接口 interface

封装性:隐藏内部实现,仅仅开放外部接口,语法上,公共的方法就是外部接口。

接口实现技术:用来约束(限制)某个类(对象)应该具有满足公共方法(接口)列表的。

例如:作为一个usb设备厂商,设计程序。要求所有的设备都满足某个操作规范,该规范在面向对象设计时就可以设计成技术结构。

定义

关键字interface进行定义,接口结构中,仅仅存在公共的抽象方法。接口的目的是定义标准化操作规范,而不去实现,由采用该接口的实体实现。

实现

关键字implements进行实现接口。一个类可以实现多个接口,用,连接起来。

接口和抽象类的差异
接口:制作标准化,主要目的是标准化时用接口。
抽象类:在普通类的基础上,增加了抽象方法。为子类提供公共成员的同时,额外的限定子类的某些成员。

语法上:
接口中的抽象方法,仅仅能是公共的。
抽象类中的抽象方法,可以是保护的和公共的。

设计模式

想法先行,语法后行

单例|单例模式

单个实例,单个对象,语法上一个类可以实例化无数个对象。

  • 设计思想:如果一个类的一个对象就可以完成所有的功能
    例如:通常的项目中,只需要操作一个数据库服务器,完成所有的功能。因此仅仅需要一个数据库操作对象即可。

既然存在一个对象可以完成功能的对象,就需要在语法层面上,限制该类去得到多个对象,只能得到一个对象,目的为了节约对象成本,这种设计,就被成为单例设计。

设计思路

  1. 私有化构造方法
    限制在类外实例化对象,结果不能实例化对象,如何实例化对象?
    如果可以在类内调用该构造方法,就可以完成实例化工作了。

  2. 静态的公共方法
    在没有对象前,可以使用类调用静态方法的方式。

  3. 静态的私有方法
    完善公共静态方法的业务逻辑,保证即使多次调用也只能得到一个对象
    核心在于,第一次可以将对象存储起来,第二次调取对。

  4. 私有化克隆方法
    禁止被克隆。

class A{
    //三私一公
    private static $class;
    private function __construct(){
    }
    private function __clone(){
    }
    public static function newClass(){
        if(!isset(static::$class)){
            static::$class = new A();
        }
        return static::$class;
    }
}

单例的另一种体现形式

function getOne(){
    static $class = null;
    if(!isset($class)){
        $class = new A();
    }
    return $class;
}

劣势:并没有从根本上解决单例问题,仍然可以new出来。
优势:灵活,不需要去更改类本身的结构,可以做到同时适应多个类。

所以实际开发中:
如果要严格限制单例效果,使用三私一公单例模式,如果仅仅想实现单例效果,就使用类外的实现

如果想实现其他类的单例,可以传参数

function getOne($classname){
    static $classlist = array();
    if(!isset($classlist[$classname])){
        $classlist[$classname] = new $classname();
    }
    return $classlist[$classname];
}
工厂模式

从类的功能上讲,如果某个类的主要功能,用来生产其他类的对象,这样的类,称之为工厂类

工厂模式
class Factory{
    //生产线
    public static function getClass($class){
        static $classList = array();
        if(!isset($classList[$class])){
           $classList[$class] = new $class();
        }
        return $classList[$class];
    }
}

魔术方法

  • __tostring()
    echo $obj;//需要快速展示某个对象的摘要信息时会使用该方法。

  • __invoke($params)
    当对象被当成方法调用时,这个方法会被自动调用
    $obj();

  • __call($name,$params)
    当对象访问不存在的方法名称时,__call方法会被自动调用
    这个方法的参数第一个就是调用的方法名称,第二个参数是方法调用的参数组成的数组

  • __callStatic()
    当对象访问不存在的静态方法名称时,__callStatic方法会被自动调用
    这两个方法在php里面也被成为方法的重载

  • __get($name)
    读取不可访问属性的值时,会被调用

  • __set($name,$value)
    在给不可访问属性赋值时,会被调用

  • __isset($name)
    当对不可访问属性调用isset()或empty()时,__isset()会被调用

  • __unset($name)
    当对不可访问属性调用时,会被调用

  • __clone()
    $obj1 = $obj2 址传递 clone实现复制

相关函数

  • class_exists(类名)

  • method_exists(对象,方法名)

  • property_exists(对象,属性名)

  • interface_exists(接口名)

  • get_class(对象)

  • get_called_class()得到调用该方法的类

  • get_parent_class(类名)得到类的父类

  • is_object()判断是否是对象

  • is_a(对象,类名) instanceof判断是否是某个类的实例

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 213,014评论 6 492
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,796评论 3 386
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 158,484评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,830评论 1 285
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,946评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,114评论 1 292
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,182评论 3 412
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,927评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,369评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,678评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,832评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,533评论 4 335
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,166评论 3 317
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,885评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,128评论 1 267
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,659评论 2 362
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,738评论 2 351

推荐阅读更多精彩内容