亚洲激情专区-91九色丨porny丨老师-久久久久久久女国产乱让韩-国产精品午夜小视频观看

溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

PHP變量和數據類型

發布時間:2020-06-18 19:32:07 來源:網絡 閱讀:306 作者:張濤澤 欄目:web開發

編程語言可以分為三大類

1. 靜態類型語言,比如:C/Java等,在靜態語言類型中,類型的檢查是在編譯期(compile-time)確定的。

2. 動態語言類型,比如:PHP,python等各種腳本語言,這類語言中的類型是在運行時確定的。

3. 無類型語言,比如:匯編語言,匯編語言操作的是底層存儲,他們對類型毫無感知。

 

一、變量的結構和類型

1)變量的存儲結構

在官方的PHP實現內部,所有變量使用同一種數據結構(zval)來保存。 它不僅僅包含變量的值,也包含變量的類型。

在PHP中,存在8種變量類型,可以分為三類:

a. 標量類型: boolean、integer、float(double)、string

b. 復合類型: array、object

c. 特殊類型: resource、NULL

變量存儲結構如下:

struct _zval_struct {
    zvalue_value value;     /* 存儲變量的值 是個聯合體*/
    zend_uint refcount__gc;    /*表示引用計數 默認1*/
    zend_uchar type;    /* 變量具體的類型 */
    zend_uchar is_ref__gc;    /*表示是否為引用 默認0*/};

type的值可以為: IS_NULL、IS_BOOL、IS_LONG、IS_DOUBLE、IS_STRING、IS_ARRAY、IS_OBJECT和IS_RESOURCE之一。

 

2)變量的值存儲

上面的value是個聯合體,正因為是這樣,才能做到弱類型,聯合體如下:

PHP變量和數據類型

typedef union _zvalue_value {    long lval;    /*boolean integer*/
    double dval;    /*float*/
    struct {        char *val;        int len;
    } str;    /*String*/
    HashTable *ht;    /* Array */
    zend_object_value obj; /*Object*/} zvalue_value;

PHP變量和數據類型

 

3)哈希表(HashTable)

a. 鍵(key):用于操作數據的標示,例如PHP數組中的索引,或者字符串鍵等等。

b. 槽(slot/bucket):哈希表中用于保存數據的一個單元,也就是數據真正存放的容器。

c. 哈希函數(hash function):將key映射(map)到數據應該存放的slot所在位置的函數。

d. 哈希沖突(hash collision):哈希函數將兩個不同的key映射到同一個索引的情況。

 

4)PHP的哈希實現

PHP的大部分的語言特性都是基于哈希表實現的, 例如:變量的作用域、函數表、類的屬性、方法等,Zend引擎內部的很多數據都是保存在哈希表中的。

PHP中的哈希表是使用拉鏈法來解決沖突的,Zend為了保存數據之間的關系使用了雙向鏈表來鏈接元素。

拉鏈法如下圖所示:


圖中,”John Smith”和”Sandra Dee” 通過哈希函數都指向了152 這個索引,該索引又指向了一個鏈表, 在鏈表中依次存儲了這兩個字符串。

Zend引擎哈希表結構和關系如下:


a. Bucket結構體維護了兩個雙向鏈表,pNext和pLast指針分別指向本槽位所在的鏈表的關系。

b. 而pListNext和pListLast指針指向的則是整個哈希表所有的數據之間的鏈接關系。

c. HashTable結構體中的pListHead和pListTail則維護整個哈希表的頭元素指針和最后一個元素的指針。

 

二、常量

PHP內核會在詞法解析時將這些常量的內容賦值進行替換,而不是在運行時進行分析。

1)常量的存儲結構

常量是在變量的zval結構的基礎上添加了一額外的元素。

PHP變量和數據類型

typedef struct _zend_constant {
    zval value; /* zval結構,PHP內部變量的存儲結構,在第一小節有說明 */
    int flags;  /* 常量的標記如 CONST_PERSISTENT | CONST_CS | CONST_CT_SUBST*/
    char *name; /* 常量名稱 */
    uint name_len;  
    int module_number;  /* 模塊號 */} zend_constant;

PHP變量和數據類型

1. CONST_CS:常量大小寫敏感

2. CONST_PERSISTENT:常量需要持久化;如果是非持久常量,會在RSHUTDOWN階段就將該常量釋放,否則只會在MSHUTDOWN階段將內存釋放。用戶定義的常量都是非持久化的,通常擴展和內核定義的常量會設置為持久化。

3. CONST_CT_SUBST:Allow compile-time substitution(在編譯時可被替換)。在PHP內核中這些常量包括:TRUE、FALSE、NULL、ZEND_THREAD_SAFE和ZEND_DEBUG_BUILD五個。

PHP常量的定義過程如下:

define('KFJ', 'Hello World');

 

2)標準常量

PHP內置定義的常量,他們屬于標準常量。如錯誤報告級別E_ALL, E_WARNING等。

這些常量都是持久化常量。

 

3)魔術常量

PHP中有七個魔術常量,他們的值其實是變化的,它們的值隨著它們在代碼中的位置改變而改變。 所以稱他們為魔術常量。


 

三、預定義變量

  對于全部腳本而言,PHP 提供了大量的預定義變量。這些變量將所有的外部變量表示成內建環境變量,并且將錯誤信息表示成返回頭。

  $_GET,$_POST,$_SERVER,$_FILES等變量,會在PHP腳本運行之前就將它們加入到HashTable數據類型的符號表中。

  由于都存儲在一個地方,所以在某個局部函數中使用類似于$GLOBALS變量這樣的預定義變量, 如果在此函數中有改變的它們的值的話,這些變量在其它局部函數調用時會發現也會同步變化。

 

四、靜態變量

  通常意義上靜態變量是靜態分配的,他們的生命周期和程序的生命周期一樣, 只有在程序退出時(RSHUTDOWN)才結束期生命周期,這和局部變量相反,局部變量只有在函數執行時才會存在。 通常,當一個函數執行完畢,它的局部變量的值就已經不存在,而且變量所占據的內存也被釋放。

靜態變量可以分為3中:

1)靜態全局變量:PHP中的全局變量(預定義變量等)也可以理解為靜態全局變量,因為除非明確unset釋放,在程序運行過程中始終存在。

2)靜態局部變量:也就是在函數內定義的靜態變量,Zend為每個函數分配了一個私有的符號表(EG(active_op_array)->static_variables)來保存該函數的靜態變量。

3)靜態成員變量:這是在類中定義的靜態變量,和實例變量相對應,靜態成員變量屬于類,不屬于某個實例,新航道托福所以可以在所有實例中共享。

查看在線代碼

PHP變量和數據類型

//靜態局部變量function static_function() {    static $i=0;    $i++;    print_r($i);
}
static_function();//1static_function();//2static_function();//3

PHP變量和數據類型

PHP變量和數據類型

//靜態成員變量
//Zend為每個函數分配了一個私有的符號表來保存該函數的靜態變量。class static_class {    public static $i=0;    public function get_static() {        return ++self::$i;
    }
}$class1 = new static_class();$class2 = new static_class();print_r($class1->get_static());//1print_r($class2->get_static());//2

PHP變量和數據類型

 

五、類型提示的實現

PHP5中引入了類型提示這個概念。在定義方法參數時,同時定義參數的對象類型。

下面的示例代碼就是類型提示,但是在引用的時候傳入1,就會報錯。

function prompt(Array $arr) {    print_r($arr);
}
prompt(1);


類型提示的實現有2種:

1)參數聲明時的類型提示,例如“$arr=[1,2];”

2)函數或方法調用時的類型提示(上面的示例代碼)


 

六、變量的生命周期

在ZE進行詞法和語法的分析之后,生成具體的opcode,這些opcode最終被execute函數解釋執行。

1)變量的聲明和賦值

在使用一個變量時,我們不需要聲明,也不需要初始化,直接對其賦值就可以使用。

$a = 10;

當賦值的時候,zval結構中的refcount_gc默認為1,當引用這個值的時候,會加1。

$a = 10;$b = &$a;//$a和$b引用了同一個zval結構,refcount_gc變為2,is_ref_gc為1$c = $a;//$c新建了一個zvak結構,refcount_gc變為2為1

 

2)變量的作用域

變量按作用域類型分為:全局變量和局部變量。

與JavaScript不同,得益于閉包的特性,JavaScript可以在函數中調用函數外的變量,而PHP不行。下面的代碼是錯誤的:

$bar = 'outter';function _global() {    print_r($bar);//這里會報錯}
_global();print_r($bar);//輸出為outter

a. 全局變量會保存在symbol_table中, 也就是頂層作用域中的變量。

b. 函數或者對象的方法在被調用時會創建active_symbol_table來保存局部變量。

c. 函數中的靜態變量存放在私有的符號表(EG(active_op_array)->static_variables)中。所以不會在函數結束的時候銷毀。

 

3)global

global語句的作用是定義全局變量,也就是將變量放到symbol_table中。

將上面的代碼修改一下,增加一個global聲明:

PHP變量和數據類型

$bar = 'outter';function _global() {    global $bar ;//添加global聲明
    $bar = 'inner';    print_r($bar);
}
_global();print_r($bar);//輸出inner

PHP變量和數據類型

 

七、數據類型轉換

1)隱式類型轉換

a. 直接的變量賦值操作

b. 運算式結果對變量的賦值操作

PHP變量和數據類型

$str = 33;    //integer 另外的float(double)類似var_dump('prase'.$str);$str = null;    //nullvar_dump('prase'.$str);$str = true;    //booleanvar_dump('prase'.$str);$str = array(1,2);    //arrayvar_dump('prase'.$str);$str = new static_class();    //object 調用靜態變量中的類var_dump('prase'.$str);

PHP變量和數據類型


a. 隱式轉換null的時候,最后輸出的是空

b. boolean轉換成了0或1

c. 雖然array最后輸出了,但最后還是報錯。

d. 而類是直接報錯,沒有輸出。

 

2)顯示類型轉換

PHP中允許的強制類型有:

a. (int), (integer) 轉換為整型

b. (bool), (boolean) 轉換為布爾類型

c. (float), (double) 轉換為浮點類型

d. (string) 轉換為字符串

e. (array) 轉換為數組

f. (object) 轉換為對象

g. (unset) 轉換為NULL,這個還是第一次見到


向AI問一下細節

免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。

AI

黔江区| 崇文区| 蓬莱市| 苍梧县| 花垣县| 石棉县| 南通市| 塘沽区| 维西| 隆安县| 定西市| 永新县| 景宁| 三门县| 昌都县| 桦川县| 当阳市| 红河县| 德令哈市| 调兵山市| 天长市| 云霄县| 宁化县| 章丘市| 方城县| 黄浦区| 全椒县| 中超| 青海省| 蒙山县| 杭锦旗| 平顺县| 页游| 城口县| 体育| 胶州市| 客服| 农安县| 漳州市| 洪雅县| 正蓝旗|