PHP反序列化

2022-09-10 03:33:10 字數 4076 閱讀 7340

類定義是以關鍵字class開頭,後跟類的名稱。類的主體是包含在一對花括號中,裡面有類的屬性與方法的定義。

類屬性存在於資料段,類方法存在於**段,對於乙個類來說,類的方法不占用類的空間,佔空間的只有類的屬性。

要建立乙個類的例項,必須使用new關鍵字。當建立新物件時該物件總是被賦值,除非該物件定義了建構函式並且在出錯時丟擲了乙個異常。類應在被例項化之前定義(某些情況下則必須這樣)。

如果在new之後跟著的是乙個包含有類名的字串,則該類的乙個例項被建立。如果該類屬於乙個名字空間,則必須使用其完整名稱。

//建立乙個例項

<?php

$instance = new ******class();

// 也可以這樣做:

$classname = 'kin';

$instance = new $classname(); // kin()

?>

如果乙個指令碼中想要呼叫之前乙個指令碼的變數,但是前乙個指令碼已經執行完畢,所有的變數和內容釋放掉了,我們要如何操作呢?

serialize和unserialize就是解決這一問題的存在,serialize可以將變數轉換為字串,並且在轉換中可以儲存當前變數的值;而unserialize則可以將serialize生成的字串變換回變數。

所有php裡面的值都可以使用函式serialize()來返回乙個包含位元組流的字串來表示。序列化乙個物件將會儲存物件的所有變數,但是不會儲存物件的方法,只會儲存類的名字。

可以這麼理解:

在程式執行結束時,記憶體資料便會立即銷毀,變數所儲存的資料便是記憶體資料,而檔案、資料庫是「持久資料」,因此php序列化就是將記憶體的變數資料「儲存」到檔案中的持久資料的過程。

舉個栗子:

<?php 

class user

}//建立乙個物件

$user = new user();

// 設定資料

$user->age = 17;

$user->name = 'kinyoobi';

//輸出資料

$user->printdata();

//輸出序列化之後的資料

echo serialize($user);

?>

結果:

o表示物件型別,4表示物件名長度為4,user為類名,

2表示有兩個引數;

{}裡面是引數的key和value:

s表示是string型別,3表示長度,age是key;

i表示是integer型別,17是value。

aarray

bboolean

ddouble

iinteger

ocommon object

rreference

sstring

ccustom object

oclass

nnull

rpointer reference

uunicode string

反序列化就是將序列化格式化儲存好的的字元還原成物件的過程。

注意:在解序列化乙個物件前,這個物件的類必須在解序列化之前定義。否則會報錯

舉個栗子:

<?php 

class user

}//重建物件

$user = unserialize('o:4:"user":2:');

$user->printdata();

?>

結果:

php 將所有以 __(兩個下劃線)開頭的類方法保留為魔術方法,在特定的情況下會被呼叫。

__construct 

建構函式

__destruct

物件被銷毀時觸發,析構函式

__tostring

把類當作字串使用時觸發

__wakeup()

unserialize前呼叫,用於預先準備物件資源

__sleep() 

serialize前呼叫

__call()

在物件上下文中呼叫不可訪問的方法時觸發

__callstatic() 

在靜態上下文中呼叫不可訪問的方法時觸發

__get() 

試圖讀取乙個並不存在的屬性的時候被呼叫

__set() 

用於將資料寫入不可訪問的屬性

__isset()

在不可訪問的屬性上呼叫isset()或empty()觸發

__unset() 

在不可訪問的屬性上使用unset()時觸發

__invoke()

指令碼嘗試將物件呼叫為函式時觸發

1)__sleep()

serialize()函式會檢查類中是否存在乙個魔術方法 __sleep()。如果存在__sleep(),該魔術方法會先被呼叫,然後才執行序列化操作。

此功能可以用於清理物件,並返回乙個包含物件中所有應被序列化的變數名稱的陣列。如果該方法未返回任何內容,則

null 被序列化,並產生乙個 e_notice 級別的錯誤。

2)__wakeup()

unserialize()函式會檢查是否存在乙個 __wakeup()方法。如果存在,則會先呼叫 __wakeup 方法,預先準備對

象需要的資源。

__wakeup() 經常用在反序列化操作中,例如重新建立資料庫連線,或執行其它初始化操作。

舉個栗子:

<?php 

class test

public function __construct()

public function __destruct()

public function __tostring()

public function __sleep()

public function __wakeup()

}$obj = new test(); //例項化物件,呼叫__construct()方法,輸出__construct

$obj->echop(); //呼叫echop()方法,輸出"abc"

echo $obj; //obj物件被當做字串輸出,呼叫__tostring()方法,輸出__tostring

$s =serialize($obj); //obj物件被序列化,呼叫__sleep()方法,輸出__sleep

var_dump($s);

echo "

";$u = unserialize($s); //$s首先會被反序列化,會呼叫__wake()方法

var_dump($u);

echo "

";// 指令碼結束又會呼叫__destruct()方法,輸出__destruct

?>

結果:

其中在序列化時,__sleep返回了varr1,達到了清理資料的目的;而在反序列化時,即類恢復成物件的時候,類本身的類屬性是不能被銷毀的,所以最後會列印出來varr1和varr2。

參考:

PHP反序列化

php反序列化漏洞 一 序列化定義 序列化 serialization 在電腦科學的資料處理中,是指將資料結構或物件狀態轉換成可取用格式 例如存成檔案,存於緩衝,或經由網路中傳送 以留待後續在相同或另一台計算機環境中,能恢復原先狀態的過程。概念很容易理解,其實就是將資料轉化成一種可逆的資料結構,自然...

php反序列化

php序列化 將物件或變數轉換成字串。php反序列化 是將字串轉換成原來的變數。serialize serialize 函式用於序列化物件或陣列,並返回乙個字串。serialize 函式序列化物件後,可以很方便的將它傳遞給其他需要它的地方,且其型別和結構不會改變。sites array google...

php序列化與反序列化

php的序列化 反序列化對與一些大檔案的壓縮操作,讀寫操作十分有用。乙個簡單的序列化案例 同時用到了序列化與反序列化函式,二者在被呼叫時會分別自己呼叫對應的函式,sleep 以及 wakeup.sleep和 wakeup練習題 故事 乙個果農生產了很多水果種類,於是需要把乙個買家指定的種類寄給他,生...