对象包括:
1、属性
2、方法
面向对象:
实质:就是把生活中要解决的问题都通过对象的方式进行存储。
对象和对象之间的互动是通过方法的调用完成的。如詹姆斯的投篮是通过詹姆斯调用投篮的方法。调用分为自身的调用,和调用他人的。
面向对象编程:就是数据结构都通过对象的结构进行存储
面向对象编程的思路:
1、识别对象
2、识别属性
3、识别行为(方法)
面向对象的基本原则:
1、对象内部的高内聚的
①:只负责一项特定的职能(如球星打球,歌手唱歌)
②:对象相关的内容都被封装到对象内部
2、对象外部都是低耦合的
①:外部对象可以看到对象的一些属性(并非全部)
②:外界对象可以看到对象的一些方法(并非全部)
注:主要跟权限设置有关。Public(全局)private(私有)protect(继承)
类:类是具有相似特征对象的集合,拥有相同的属性和方法。他是对象的描述,是该类对象的蓝图/原型。
类的对象成为类的一个实例。(如乔丹、詹姆斯、科比成为相应类的实例)
类的定义:
<?Php
Date_default_timezone_set(“PRC”);
Class NbaPlayer{
//实例化属性
Public $name=”Jordan”;
Public $height=”198cm”;
Public $weigth=”98kg”;
Public $team=”bull”;
Public $playerNumber=”23”;
//构造函数,在对象被实例化的时候自动调用
function __construct($name,$heigth,$weigt,4team,$playNumber){
Echo “In NbaPlayer constructor\n”;
$this->name=$name;//$this是php中的伪变量,表示对象自身,通过$this->的属性访问自身的属性和方法
$this->height=$height;
$this->weight=$weight;
$this->team=$team;
$this->payerNumber=$playerNumber;
}
//析构函数在程序结束时候会自动调用
//析构函数通常被用于清理程序使用的资源,如程序使用了打印机,那么析构函数可以释放打印机资源。
Function __destruct(){
Echo “Destroying “.$this->name.”\n”;
}
//实例化方法
Public function run(){
Echo “running\n”;
}
Public function jump(){
Echo “jumping\n”;
}
Public function dribble(){
Echo “dribbling\n”;
}
Public function shoot(){
Echo “shooting\n”;
}
Public function dunk(){
Echo “dunking\n”;
}
Public function pass(){
Echo “passing\n”;
}
}
//类到对象的实例化
$jordan=new NbaPlayer(“Jordan”,”198cm”,”98kg”,”bull”,”23”);//实例化对象
Echo $jordan->name.”\n”;//调用类的属性
$jordan->dribble();
$jordan->pass();
//实例化詹姆斯,每一次用new实例化对象的时候都会用类名后面的参数列表调用构造函数
$james=new NbaPlayer(“James”,”203cm”,”120kg”,”heat”,”23”);//实例化对象
Echo $james->name.”\n”;//调用类的属性
$james->dribble();
$james->pass();
$james1=$james;
$james2=&$james;
//通过把变量设置为null,可以触发析构函数的调用。
//当对象不再被使用时会自发触发析构函数
$james=””;//若$james=””则直接调用析构函数,若没有设置$james=””,则等到程序结束后才调用析构函数。
Echo “From now on James will not be used.”;
?>
对象引用赋值
$james2=&$jemas;和 $james1=$jemas;
区别:
1、对象的引用用于访问对象的属性和方法,$james、$james1和$james2都是对象的引用;
2、$james和$james1是两个对象的独立引用;
3、$james2是$james的影子,使用对象的同一个引用,对其中任何一个操作,两个都会受到影响;
继承(单继承原则):
他们拥有部分相同的属性和方法
继承的好处:
1、父类里面定义的类成员可以不用再子类中重复定义,节约时间和代价;
2、同一父类的子类拥有相同的父类定义类成员,因此外部代码调用他们的时候可以一视同仁;
3、子类可以修改和调整父类定义的类成员。
我们称为重写(overwrite)
一旦修改,就按修改后执行
Class Human(){
Public $name;
Public $height;
Public $weight;
Public function eat($food){
Echo $this->name.”’s eating”.$food.”\n”;
}
}
//php中可以用extends关键字来表示类的继承,后面跟父类的类名。
//php中extends后面只能跟一个类的类名,这就是php单继承原则
Class NbaPlayer extends Human{
Public $team=”bull”;
Public $playerNumber=”23”;
}
$jordan->eat(“Apple”);
面向对象:(访问控制)
面向对象的三种访问权限:
1、public公有的类成员,可以在任何地方呗访问。定义该成员的类(自身),其子类,或者其他类;
2、protected受保护的类成员,可以被其自身和其子类访问;
3、private私有类成员,只能被其自身访问。
Class Human(){
Public $name;
Public $height;
Public $weight;
Private $age;
Public function eat($food){
Echo $this->name.”’s eating”.$food.”\n”;
}
Public function getAge(){//是有属性只能类的内部获取
Echo $this->name.”’s age is”.$this->age.”\n”;
}
//省略其他方法。。。。。。。
}
//php中可以用extends关键字来表示类的继承,后面跟父类的类名。
//php中extends后面只能跟一个类的类名,这就是php单继承原则
Class NbaPlayer extends Human{
Public $team=”bull”;
Public $playerNumber=”23”;
}
$jordan->eat(“Apple”);
$jordan->getAge();
静态成员:
静态属性定义时在访问控制关键字后添加关键字static;public static $prisedent=”David stern”;
静态方法定义时在访问控制关键字后添加关键字static;public static function changePrisedent($newPre){....}
在类定义中使用静态成员的时候,用self或者static关键字后面跟着::操作符即可。Self::$prisedent=$newPre;(注意:在访问静态成员的时候,::后面需要加$)
在类定义外部访问静态属性。可以用类名加::操作符的方法来使用静态成员
使用parent::关键字来访问父类的静态成员,在类定义外部访问静态属性,则使用父类名::来访问静态成员。
1、静态属性用于保存类的公有数据;
2、静态方法里面只能访问静态属性,不能访问非静态属性;
3、静态成员不需要实例化对象就可以访问;
4、类的内部可以通过self或者static访问自身静态成员;
5、可以通过parent关键字访问父类的静态成员;
6、可以通过类的名称在类定义外部访问静态成员。
重写(overwrite):子类中定义相同父类中的方法称为重写。
Final关键字:(Final类不能有子类,Final方法不能被重写)
1、父类的方法不希望被子类修改,即可用final进行设置,子类将不能对其父类方法进行修改(final加在public之前)。
2、若某个类不想被其他类继承,则可以在该类前面添加final关键字即可限制其他类对其继承。(final关键字添加在class之前)
子类编写跟父类完全一致的方法名(参数可以不一致)可以完成对父类方法的重写(overwrite);
通过parent::可以访问父类中被子类重写的方法。
数据访问:
1、Parent关键字可以访问父类中被子类重写的方法;
2、Self关键字可以用于访问类自身的成员方法,也可以访问自身的静态成员和类常量;不能用于访问类自身的属性;使用常量的时候不需要在常量名称的前面添加$符号。
3、Static关键字用于访问自身定义的静态成员,访问静态属性时需要在其前面添加$;
接口:(重要)
定义:接口就是把不同的类的共同行为进行定义,然后在不同的类里面实现不同的功能。
1、Interface关键字用于定义接口,接口里面的方法不需要方法的实现;
2、Implements关键字用于变现类实现关键字;
3、实现了某个接口之后,必须提供接口定义的方法的具体实现;
4、不能实例化接口;
5、可以用instance关键字来判断某个对象是否实现了某个接口;
6、可以用extends让接口实现接口的集成,当类实现子接口时,父接口定义的方法也需要在这个类里面具体实现;
实现接口和继承类的区别:
1、实现接口和继承类很类似,但是接口不能直接创建自己的对象;
2、继承的父类必须有该方法的具体实现,子类可以重写父类的方法;
3、接口里面的方法是不需要具体实现的,只要定义方法的名称和参数就行,具体的实现必须在实现类中定义;
一句话:类的方法必须有实现,接口的方法必须为空。
多态:
相同的一行代码,对于传入的不同的接口的实现的对象的时候,表现是不同的,这就是多态。
如checkEat($obj);和checkEat($monkey);就是类的多态类型。
抽象类:(class前面使用abstract修饰)
1、使用extends实现抽象类的继承。
2、抽象类里面既可以包含已经实现的普通的方法,也可以包含有只定义没有具体实现的抽象方法;
3、在继承抽象类的时候,只需要实现抽象类没有具体实现的抽象方法,而不需要去实现抽象类中已经实现的普通方法。
魔术方法(只在PHP中使用):
1、__construct()、__destruct();
2、__tostring();//会把对象转化为string的时候自动调用
3、__invoke();//会在把对象当做一个方法的时候自动调用
4、__call();//当对象访问不存在的方法名称时,__call()会被自动调用
5、__callStatic();//当对象访问不存在的静态方法名称时,__callStatic()会被自动调用
这两个方法在PHP里面也被称为方法的重载(overloading)
①注意区分重写(overwrite)
②通过这两个方法,同一个方法的名称的调用可以对应不同方法的实现。
6、__get(),__set(),__isset(),__unset();
①在给不可访问属性赋值时,__set()会被自动调用
②读取不可访问属性时,__get()会被自动调用
③当对不可访问属性调用isset()或empty()时,__isset()会被自动调用
④当对不可访问属性调用unset()时,__unset()会被自动调用
注:所谓的不可访问属性,实际上就是在调用某个属性时发现这个属性没有被定义或者该定义为private而不具备访问权限,这时候不同的操作会触发不同的魔术方法。
这几个方法也被称为属性重载的魔术方法。
7、__clone();
$james2=clone $james;//复制一个$james,注意区别于引用。
注:$james2= &$james;和$james2= clone $james;的区别:
①$james2= &$james;只是引用$james,只是在栈中复制一个指针,将指针指向堆中存在的内存,当修改内存的内容时,所对应的两个变量中都会被修改;
②$james2= clone $james;不经在栈中复制一个指针,而且在堆中复制一份内存。当改变其中一个内存时,而另一个内存内容不会受到影响。
③这时可以使用比较运算符“==”和"===",来区分是引用还是clone。两个等号“==”是比较两个对象的内容,三个等号“===”不仅比较内容而且比较对象的引用地址。