對象的“形”

要回答類與對象本質這個問題,我想可以先從“形”的角度來回答。本節以PHP爲例,來探討對象的“形”與“本”的問題。

類是我們對一組對象的描述

在PHP裏,每個類的定義都是以關鍵字clss開頭,後面跟着類名,緊接着一對花括號,裏面包含有類成員和方法的定義。如下面代碼所示:

class Person {
    public $name;
    public $gender;
    public function say()
    {
        echo $this->name,'is',$this->gender;
    }
}

在這裏,我們定義了一個Person類。代表了抽象出來的人這個概念,它含有姓名和性別這兩個屬性,還具有一個開口說話的方法,這個方法會告訴外界這個人的性別和姓名。我們接下來就可以產生這個類的實例:

$student = new Person();
$student->name = 'Tom';
$student->gender = 'male';
$student->say();

$teacher = new Person();
$teacher->name = 'Kate';
$teacher->gender = 'female';
$teacher->say();

這段代碼則實例化了Person類,產生了一個student對象和teacher對象的實例。實際上也就是從抽象到具體的過程。現實世界中,僅僅說“人”是沒有意義的,中國人把它叫“人”,美國人把它叫person或者human,如果高興,把它叫“God”或者“板凳”都無所謂。但是隻要你把“人”這個概念加上各種屬性和方法,比如說有兩條腿、直立行走、會說話,則無論是中國人,還是美國人,甚至是外星人都是能理解你所描述的事物。所以,一個類的涉及需要能充分展示其最重要的的屬性和方法,並且能與其他事物相區分。只有類本身有意義,從抽象到具體的實例化纔會有意義。

根據上面的實例代碼,可以有下面的一些理解:

  • 類定義了一系列的屬性和方法,並提供了實際的操作細節,這些方法可以用來對屬性進行加工。
  • 對象含有類屬性的具體值,這就是類的實例化。正是由於屬性的不同,才能區分不同的對象。在上面例子裏,由於student和teacher的性別和姓名不一樣,才得以區分開二人。
  • 類與對象的關係類似一種服務於被服務、加工與被加工的關係,具體而言,就如同原材料與流水線的關係。只需要在對象上調用類中所存在的方法,就可以對類的屬性進行加工,並且展示其功能。
類是屬性和方法的集合,那麼在PHP裏,對象是什麼呢?比較普遍的說法就是“對象由屬性和方法組成”。對象是由屬性組成,這很好理解,一個對象的屬性是它區別於另一個對象的關鍵所在。由於PHP的對象是用數組來模擬的,因此我們把對象轉換爲數組,就能看到這個對象所擁有的屬性了。

繼續使用上面代碼,可以打印student對象:

print_r((array)$student);
var_dump($student);
到這裏,可以很直觀地認識到,對象就是一堆數據。既然如此,可以把一個對象存儲起來,以便需要時用。這就是對象的序列化。

所謂序列化,就是把保存在內存中的各種對象狀態(屬性)保存起來,並且在需要時可以還原出來。下面的代碼實現了把內存中的對象當前狀態保存到一個文件中:

$str = serialize($student);
echo $str;
file_put_contents('store.txt',$str);

輸出序列化後的結果:

O:6:"Person":2:{s:4:"name";s:3:"Tom";s:6:"gender";s:4:"male";}

在需要時,反序列化取出這個對象:

$str = file_get_contents('store.txt');
$student = unserialize($str);
$student->say();


注意   在序列化和反序列化時都需要包含類的對象的定義,不然有可能出現在反序列化對象時,找不到該對象的類的定義,而返回不正確的結果。

可以看到,對象序列化後,存儲的只是對象的屬性。類是由屬性和方法組成的,而對象則是屬性的集合,由同一個類生成的不同對象,擁有各自不同的屬性,但共享了類的代碼空間中方法區域的代碼。

發佈了58 篇原創文章 · 獲贊 54 · 訪問量 14萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章