分类: PHP
2013-03-06 10:37:17
首先要感谢“LAMP兄弟连” 的精彩视频,感谢 高洛峰 老师认真细心的讲解
魔术方法:
在类中写出了某个魔术方法, 这个方法对象的功能 就会添加上
方法名称都固定的(都是系统给我们提供好),没有自己定义的,
每一个魔术方法, 都是在不同时刻为了完成某一功能自动调用的方法
不同的魔术方法有不同调用 时机
都是以 __开头的方法
__construct();
__destruct();
__set();
__get();
__isset();
__unset();
__clone();
__call();
__sleep();
__weakup();
__toString()
...
__autoload();
构造函数:
定义方法:
php4中 和类名相同。
php5中 是用魔术方法 __construct()所有类中声明构造方法都使用这个名称,优点是在改变类名时,构造方法名称不变
两种方式可共同存在,php5优先。
作用:为成员属性初始化。
析构函数:
当对象被释放之前最后一个 “自动”调用的方法
作用:关闭一些资源,做一些清理工作
__destruct();
对象释放时由于栈的原因,后进先出,倒序
成员属性的设定:
只要一个变量,需要在多个方法使用,就将这个方法声明为成员属性,可以直接在这个对象中的所有方法中使用
成员属性,就相当于这个对象中的全局变量
成员属性都会在方法中使用, 成员属性值的变化其实就是在改变方法的执行行为, 也就是改变了对象的功能
成员属性的值如果不正常, 方法执行的功能也就不正常了
封装:
就是把对象的成员(属性,方法)结合成一个独立的相同单位,并尽可能隐藏对象的内部细节
public protected
private 私有的, 用这个关键字修饰的成员,只能在对象内部访问(只有用$this访问),不能在对象外部使用
和封装有关的魔术方法:
__set(); 直接设置私有成员属性值时,自动调用的方法
__get(); 直接获取私有成员属性值时,自动调用的方法
__isset(); 是isset直接查看对象中私有属性是否存在时,自动调用这个方法
__unset(); 是unset直接删除对象中私有属性时,调用的方法。
继承:
开放性、可扩充性
增加代码的重用性
提高了软件的可维护性
继承就是用子类去“扩展”父类
c++属于多继承,同一个类可以有多个父类
php和java属于单继承,同一个类只能有一个父类
不管是多继承还是单继承,都可以有多个子类
声明一个子类,使用extends关键字去继承(扩展)一个父类
子类可以从父类,继承所有的内容,包括成员属性、成员方法、构造函数...在子类中都可使用。
访问类型控制
虽然子类可以从父类中继承所有内容,但private的成员, 只能在本类中使用, 子类中也不能使用
封装时,即可以让自己类的内部可以访问,也让子类可以用,但类的外部不能使用, private --> protected
由于php为弱类型语言,创建函数时,参数类型和个数都没有限定,所以php没有函数的重载,可子类有重载父类的方法:
1.子类可以声明和父类相同的方法名,即子类覆盖了父类中同名的方法。
子类的方法对父类方法的扩展:
在子类中 调用 父类中 被覆盖的方法
父类名::方法名() or parent::方法名()
在子类中编写构造方法,如果父类中也有构造方法一定要去调用一次父类中被覆盖的那个构造方法。
注意:子类中重载的方法,不能低于父类中的访问权限(子类可以放大权限private-->protected-->public,但不能缩小权限)
php中常用的关键字
1.final
final不成修饰成员属性(类中常不是用这个关键字)final不能修饰成员属性(类中)
final只能修饰类和方法
作用:
使用final修饰的类 不 能被子类继承
使用final修饰的方法不能被子类去覆盖
用来限制类不被继承,方法不被覆盖就使用fianl
2.static
使用static可以修饰成员属性和成员方法,不能修饰类
用static修饰的成员属性,可以被同一个类的所有对象共享
静态的数据是存在 内存中的 数据段中(初使化静态段)
静态的数据是在类每一次加载时 分配到内存中的, 以后再用到类时就直接从数据段中获取
什么是类被加载? 只要在程序中使用到这个类(有这个类名出现)
注意:静态的成员都要使用类名去访问,不用创建对象,不用对象去访问。
类名::静态成员
如果在类中使用静态成员, 可以使用 self代表本类($this)
静态方法(static修饰的方法), 不能访问非静态的成员(在非静态的方法中,可以访问静态成员)
因为非静态的成员, 就必须用对象来访问,访问内部的成员使用的就是$this
静态方法 不用使用对象来调用, 也就没有对象, $this也就不能代表什么对象, 非静态的成员还必须使用对象
如果你确定一个方法不使用非静态的成员, 则可以将这个方法声明为 静态方法(不用创建对象,直接使用类名就可以访问)
静态成员: 类名::成员 , 在类内部访问其它成员 self::成员
3.const
只能修饰成员属性
define('HOST','');
final int A=1;
类中声明常量属性使用const
命名的方式和我们以前学习 define是一样的效果
常量一定要在声明时就给初值
PHP中常用的魔术方法
__call()
作用: 在调用对象中不存在的方法时就会出现系统报错,然后程序退出。
什么时候自动调用: 就会在调用一个对象中不存的的方法时自动调用
处理一些不存在方法的错误调用
这个方法需要两个参数,第一个是错误方法名,第二个是错误参数数组
__toString()
直接输出对象引用时自动调用, 用来快速获取对象的字符串表示的最便捷的方式
__clone()
与$p1=$p这类不同,这种等于将$p指向的地址赋给$p1,$p1和$p现在都指向相同的内存空间
克隆对象使用clone去处理
原本 (原来的对象)
复本 (复制出来的对象)
__clone()就是在克隆对象时自动调用的方法
只要一个对象一诞生,就要有初使化的动作, 和构造方法__construct作用相似
在__clone()方法中的 $this关键字,代表的是复本, $that代表原本对象
__autoload()
注意: 其它的魔术方法都是在类中添加起作用, 这是一个唯一一个不在类中添加的方法
只要在页面中使用到一个类,只要用到类名就会自动将类名传给这个参数
对象串行化(序列化): 将一个对象转为二进制串 (对象是存储在内存)
1. 将对象长时间存储在数据库或文件中时
2. 将对象在多个PHP文件中传输时
serialize() : 参数是一个对象, 返回来的就是串行化后的二进制串
unserialize() : 参数就是对象的二进制串, 返回来的就是新生成的对象
__sleep()
是在序列化时自动调用的方法
作用:就是可以将一个对象部分串行化
只要这个方法中返回一个数组,数组中有几个成员属性就序列化几个成员属性,如果不加这个方法,则所有成员都被序列化
__wakeup()
是在反序列化时自动调用的方法
也是对象重新诞生的一个过程(__construct(), __clone(),__wakeup())
抽象类
什么是抽象方法?
定义:如果一个类中的方法,没有方法体的方法就是抽象方法(就是一个方法没有使用{}而直接使用分号结束)
abstract function test(); //抽象方法
function test(){ } //有方法体,但方法体为空的
如果一个方法是抽象方法,就必须使用abstract修饰
什么是抽象类?
1. 如果一个类中,有一个方法是抽象的则这个类就是抽象类
2. 如果一个类是抽象类,则这个类必须要使用abstract修饰
3. 抽象类是一种特殊的类,就是因为一个类中有抽象方法,其他不变。也可以在抽象类中声明成员属性,常量,非抽象的方法。
4. 抽象类不能实例化对象(不能通过抽象类去创建一个抽象类的对象)
5. 就是在定义一些规范,让子类按这些规范去实现自己的功能
作用:
要想使用抽象类,就必须使用一个类去继承抽象类,而且要想使用这个子类,也就是让子类可以创建对象,子类就必须不能再是抽象类, 子类可以重写父类的方法(给抽象方法加上方法体)
抽象方法中的方法没有方法体, 子类必须实现这个方法 (父类中没写具体的实现, 但子类必须有这个方法名)
目的:
就是要将你自己写的程序模块 加入 到原来已经写好的程序中去 (别人写好的程序,不能等你开发完一个小模块,根据你的小模块继续向后开如)
接口技术
抽象类是一种特殊的类,接口是一种特殊的抽象类
接口和抽象类是一样的作用
因为在PHP是单继承的, 如果使用抽象类,子类实现完抽象类就不能再去继承其它的类了。如果即想实现一些规范, 又想继承一个其他类。就要使用接口。
声明方式:
interface 接口名{
const XXX=“xxx”;
function funX();
}
接口和抽象类的对比:
1. 作用相同,都不能创建对象, 都需要子类去实现
2. 接口的声明和抽象类不一样
3. 接口被实现的方式不一样
4. 接口中的所有方法必须是抽象方法,只能声明抽象方法(不用使用abstract修饰)
5. 接口中的成员属性,只能声明常量,不能声明变量
6. 接口中的成员访问权限 都必须是public, 抽象类中最低的权限protected
7. 使用一个类去实现接口, 不是使用extends关键字, 而是使用implements这个词
可以使用抽象类去实现接口中的部分方法.如果想让子类可以创建对象,则必须实现接口中的全部抽象方法.
如果子类是重写父接口中抽象方法,则使用implements, 类--接口, 抽象类---接口 implements 接口---接口 extends
可以使用抽象类去实现接口中的部分方法
一个类可以去实现多个接口(按多个规范去开发子类), 使用逗号分隔多个接口名称
class XXX implements Demo1,Demo2,Demo3{...}
一个类可以在继承一类的同时,去实现一个或多个接口(先继承,再实现)
class XXX extends OOO implements Demo1,Demo2,Demo3{...}
使用implements的两个目的:
1. 可以实现多个接口 ,而extends词只能继承一个父类
2. 没有使用extends词,可以去继承一个类, 所以两个可以同时使用
点击(此处)折叠或打开
点击(此处)折叠或打开
点击(此处)折叠或打开