我們專(zhuān)注於高端品牌網(wǎng)站創(chuàng)意設(shè)計(jì)與開(kāi)發(fā)
深圳網(wǎng)站建設(shè)中,我們經(jīng)常會(huì)遇到網(wǎng)站程序各種語言的多態(tài),下面就介紹幾點(diǎn):
多態(tài)確切的含義是:同一類(lèi)的對(duì)象收到相同消息時(shí),會(huì)得到不同的結(jié)果。而這個(gè)消息是不可預測(cè)的。多態(tài),顧名思義,就是多種狀態(tài),也就是多種結(jié)果。
以Java為例,由於Java是強(qiáng)類(lèi)型語言,因此變量和函數(shù)返回值是有狀態(tài)的。比如,實(shí)現(xiàn)一個(gè)add函數(shù)的功能,其參數(shù)可能是兩(liǎng)個(gè)int型整數(shù),也可能是兩(liǎng)個(gè)float型浮點(diǎn)數(shù),而返回值可能是整型或者浮點(diǎn)型。在這種情況下,add函數(shù)是有狀態(tài)的,它有多種可能的運(yùn)行結(jié)果。在實(shí)際使用時(shí),編譯器會(huì)自動(dòng)匹配適合的那個(gè)函數(shù)。這屬於函數(shù)重載的概念。需要說(shuō)明的是,重載並不是面向對(duì)象裡的東西,和多態(tài)也不是一個(gè)概念,它屬於多態(tài)的一種表現(xiàn)形式。
多態(tài)性是一種通過(guò)多種狀態(tài)或階段描述相同對(duì)象的編程方式。它的真正意義在於:實(shí)際開(kāi)發(fā)中,只要關(guān)心一個(gè)接口或基類(lèi)的編程,而不必關(guān)心一個(gè)對(duì)象所屬於的具體類(lèi)。
很多地方會(huì)看到「PHP沒有多態(tài)」這種說(shuō)法。事實(shí)上,不是它沒有,而是它本來(lái)就是多態(tài)的。PHP作為一門(mén)腳本語言,自身就是多態(tài)的,所以在語言這個(gè)級(jí)別上,不談PHP的多態(tài)。在PHP官方手冊(cè)也找不到對(duì)多態(tài)的詳細(xì)描述。
既然說(shuō)PHP沒有多態(tài)這個(gè)概念(實(shí)際上是不需要多態(tài)這個(gè)概念),那為
什麼又要講多態(tài)呢?可以看下面的例子,如下所示:
<?php
class employee{
protected function working(){
echo'本方法需重載才能運(yùn)行';
}
}
class teacher extends employee{
public function working(){
echo'教書(shū)';
}
}
class coder extends employee{
public function working(){
echo'敲代碼';
}
}
function doprint($obj){
if(get_class($obj)=='employee'){
echo'Error';
}else{
$obj->working();
}
}
doprint(new teacher());
doprint(new coder());
doprint(new employee());
通過(guò)判斷傳入的對(duì)象所屬的類(lèi)不同來(lái)調(diào)用其同名方法,得出不同結(jié)果,這是多態(tài)嗎?如果站在C++角度,這不是多態(tài),這只是不同類(lèi)對(duì)象的不同表現(xiàn)而已。C++裡的多態(tài)指運(yùn)行時(shí)對(duì)象的具體化,指同一類(lèi)對(duì)象調(diào)用相同的方法而返回不同的結(jié)果。看個(gè)C++的例子,如下所示:
#include<cstdlib>
#include<iostream>
/**
C++中用虛函數(shù)實(shí)現(xiàn)多態(tài)
*/
using namespace std;
class father{
public:
father():age(30){cout<<"父類(lèi)構(gòu)造法,年齡"<<age<<"\n";}
~father(){cout<<"父類(lèi)析構(gòu)"<<"\n";}
void eat(){cout<<"父類(lèi)吃飯吃三斤"<<"\n";}
virtual void run(){cout<<"父類(lèi)跑10000米"<<"\n";}//虛函數(shù)
protected:
int age;
};
class son:public father{
public:
son(){cout<<"子類(lèi)構(gòu)造法"<<"\n";}
~son(){cout<<"子類(lèi)析構(gòu)"<<"\n";}
void eat(){cout<<"兒子吃飯吃一斤"<<"\n";}
void run(){cout<<"兒子跑100米"<<"\n";}
void cry(){cout<<"哭泣"<<"\n";}
};
int main(int argc,char*argv[])
{
father*pf=new son;
pf->eat();
pf->run();
delete pf;
system("PAUSE");
return EXIT_SUCCESS;
}
上面的代碼首先定義一個(gè)父類(lèi),然後定義一個(gè)子類(lèi),這個(gè)子類(lèi)繼承父類(lèi)的一些方法並且有自己的方法。通過(guò)father*pf=new son;語句創(chuàng)建一個(gè)派生類(lèi)(子類(lèi))對(duì)象,並且把該派生類(lèi)對(duì)象賦給基類(lèi)(父類(lèi))指針,然後用該指針訪(fǎng)問(wèn)父類(lèi)中的eat和run方法。下圖所示是運(yùn)行結(jié)果。
由於父類(lèi)中的run方法加了virtual關(guān)鍵字,表示該函數(shù)有多種形態(tài),可能被多個(gè)對(duì)象所擁有。也就是說(shuō),多個(gè)對(duì)象在調(diào)用同一名字的函數(shù)時(shí)會(huì)產(chǎn)生不同的效果。
這個(gè)例子和PHP的例子有什麼不同呢?C++的這個(gè)例子所創(chuàng)建的對(duì)象是一個(gè)指向父類(lèi)的子對(duì)象,還可以創(chuàng)建更多派生類(lèi)對(duì)象,然後上轉(zhuǎn)型為父類(lèi)對(duì)象。這些對(duì)象,都是同一類(lèi)對(duì)象,但是在運(yùn)行時(shí),卻都能調(diào)用到派生類(lèi)同名函數(shù)。而PHP中的例子則是不同類(lèi)的對(duì)象調(diào)用。
由於PHP是弱類(lèi)型的,並且也沒有對(duì)象轉(zhuǎn)型機(jī)制,所以不能像C++或者Java那樣實(shí)現(xiàn)father$pf=new son;把派生類(lèi)對(duì)象賦給基類(lèi)對(duì)象,然後在調(diào)用函數(shù)時(shí)動(dòng)態(tài)改變其指向。在PHP的例子中,對(duì)象都是確定的,是不同類(lèi)的對(duì)象。所以,從這個(gè)角度講,這還不是真正的多態(tài)。
通過(guò)判斷對(duì)象的類(lèi)屬性實(shí)現(xiàn)「多態(tài)」,此外,還可以通過(guò)接口實(shí)現(xiàn)多態(tài),如下所示:
<?php
interface employee{
public function working();
}
class teacher implements employee{
public function working(){
echo'教書(shū)';
}
}
class coder implements employee{
public function working(){
echo'敲代碼';
}
}
function doprint(employee$i){
$i$i->working();
}
$a=new teacher;
$b=new coder;
doprint($a);
doprint($b);
這是多態(tài)嗎?這段代碼和代碼清單1-8相比沒有多少區(qū)別,不過(guò)這段代碼中doprint函數(shù)的參數(shù)是一個(gè)接口類(lèi)型的變量,符合「同一類(lèi)型,不同結(jié)果」這一條件,具有多態(tài)性的一般特徵。因此,這是多態(tài)。
如果把代碼清單1-8中doprint函數(shù)的obj參數(shù)看做一種類(lèi)型(把所有弱類(lèi)型看做一種類(lèi)型),那就可以認(rèn)為代碼清單1-8中的代碼也是一種多態(tài)。
再次把三段代碼放在一起品味,可以看出:區(qū)別是否是多態(tài)的關(guān)鍵在於看對(duì)象是否屬於同一類(lèi)型。如果把它們看做同一種類(lèi)型,調(diào)用相同的函數(shù),返回了不同的結(jié)果,那麼它就是多態(tài);否則,不能稱(chēng)其為多態(tài)。由此可見(jiàn),弱類(lèi)型的PHP裡多態(tài)和傳統(tǒng)強(qiáng)類(lèi)型語言裡的多態(tài)在實(shí)現(xiàn)和概念上是有一些區(qū)別的,而且弱類(lèi)型語言實(shí)現(xiàn)起多態(tài)來(lái)會(huì)更簡(jiǎn)單,更靈活。
本節(jié)解決了什麼是多態(tài),什麼不是多態(tài)的問(wèn)題。至於多態(tài)是怎麼實(shí)現(xiàn)的,各種語言的策略是不一樣的。但是,最終的實(shí)現(xiàn)無(wú)非就是查表和判斷。總結(jié)如下:
多態(tài)指同一類(lèi)對(duì)象在運(yùn)行時(shí)的具體化。
PHP語言是弱類(lèi)型的,實(shí)現(xiàn)多態(tài)更簡(jiǎn)單、更靈活。
類(lèi)型轉(zhuǎn)換(huàn)不是多態(tài)。
PHP中父類(lèi)和子類(lèi)看做「繼父」和「繼子」關(guān)係,它們存在繼承關(guān)係,但不存在血緣關(guān)係。因此子類(lèi)無(wú)法向上轉(zhuǎn)型為父類(lèi),從而失去多態(tài)最典型的特徵。
多態(tài)的本質(zhì)就是if…else,只不過(guò)實(shí)現(xiàn)的層級(jí)不同。
文章引用:http://www.szymweb.com/new/141.html
本站文章為深圳網(wǎng)站建設(shè)·源美網(wǎng)絡(luò)原創(chuàng)策劃(huà),如有版權(quán)糾紛或者違規(guī)問(wèn)題,請聯(lián)繫我們刪除,謝謝!
上一篇: 對(duì)PHP接口的思考
下一篇: 魔術(shù)方法的應(yīng)用
售後保障
承諾任何問(wèn)題1小時(shí)內(nèi)解決數(shù)據(jù)備份
更安全、更高效、更穩(wěn)定價(jià)格公道精準(zhǔn)
項(xiàng)目經(jīng)理精準(zhǔn)報(bào)價(jià)不弄虛作假合作無(wú)風(fēng)險(xiǎn)
重合同講信譽(yù),無(wú)效全額退款