變量是php中非常常用的一個(gè)東西,所有的操作都要經(jīng)過(guò)變量來(lái)傳遞,下面我來(lái)給各位同學(xué)介紹在php中變量的一些常用用法與關(guān)于php變量基礎(chǔ)知識(shí),
具體方法:
PHP變量用于存儲(chǔ)字符、數(shù)字、數(shù)組甚至對(duì)象內(nèi)容等,以便在我們需要的地方使用.定義一個(gè)變量的語(yǔ)法:
$變量名 = 值;
使用變量的例子:
實(shí)例代碼如下:
- $var_char = "你好!";
- echo $var_char;
- ?>
1 你好!
從這個(gè)例子可以看出,變量名以 $ 開(kāi)始,標(biāo)明這是一個(gè)變量.變量名以字母(a-z、A-Z)或者下劃線 _ 開(kāi)始,后面可以跟任意字母或數(shù)字以及下劃線,但不能是空格.如下這些變量名是有效的:
提示:關(guān)于變量命名,我們建議變量名以標(biāo)明其實(shí)際語(yǔ)意的組合為佳,如 $my_name 或 $myName 格式.
全局變量global
全局變量便是其中之一,當(dāng)然這個(gè)觀點(diǎn)頗具爭(zhēng)議,有許多人還是建議禁用全局變量,使用不當(dāng)對(duì)造成程序的可讀性很差!結(jié)構(gòu)混亂,調(diào)試更是一頭霧水,但是不可否認(rèn)他的便捷,這便是php為什么會(huì)用全局變量global原因吧!…
今天就遇到了php 全局變量不起作用的問(wèn)題.先上一段簡(jiǎn)單的代碼:
實(shí)例代碼如下:
- $a = 0 ;
- function Test()
- {
- $a =1;
- }
- Test();
- echo $a;
- ?>
上面的代碼中輸出是0,那是因?yàn)楹瘮?shù)體Test內(nèi)$a變量被缺省設(shè)置為局部變量,$a的作用域就是在Test內(nèi).修改代碼如下:
- ?
- $a = 0 ;
- function Test()
- {
- global $a;//申明函數(shù)體Test內(nèi)使用的$a變量為global全局變量
- $a =1;
- }
- Test();
- echo $a;
- ?>
申明函數(shù)體Test內(nèi)使用的$a變量為global全局變量后,使得$a的作用全局,所以輸出為1.上面的實(shí)例只是基本的global全局變量知識(shí),下面我們看看復(fù)雜點(diǎn)的:
實(shí)例代碼如下:
- //A.php 文件
- function Test_Global()
- {
- include 'B.php';
- Test();
- }
- $a = 0 ;
- Test_Global();
- echo $a;
- ?>
- //B.php 文件
- function Test()
- {
- global $a;//申明函數(shù)體Sum內(nèi)使用的$a變量為global全局變量
- $a =1;
- }
- ?>
為什么輸出的卻是0?!!
解釋:A.php文件的內(nèi)Test_Global是定義好的第三方函數(shù),該函數(shù)用include導(dǎo)入了B.php文件內(nèi)的$a的global全局變量,所以$a被限制在Test_Global局部函數(shù)范圍內(nèi),所以B.php文件內(nèi)的$a的作用范圍都在Test_Global內(nèi),而不是作用了整個(gè)A.php內(nèi)….
解決方案:
實(shí)例代碼如下:
- function Test_Global()
- {
- Test();
- }
- include 'B.php'; //將include 從局部Test_Global函數(shù)中移出
- $a = 0 ;
- Test_Global();
- echo $a;
- ?>
- //B.php 文件
- function Test()
- {
- global $a;
- $a =1;
- }
- ?>
2.優(yōu)秀的訪問(wèn)器
實(shí)例代碼如下:
- //A.php 文件
- include 'B.php';
- $a =0;
- Set_Global($a);
- echo $a;
- ?>
- //B.php 文件
- function Set_Global(&$var)
- {
- $var=1;
- }
- ?>
php變量 引用函數(shù) static變量
Text-Segment,這個(gè)段最大的特點(diǎn)就是只讀.一般存放可執(zhí)行代碼,也有可能常量也存放在這里,比如字符串常量 BSS-Segment,這里存放了那些沒(méi)有初始化的變量.某種意義來(lái)講,沒(méi)有初始化的變量都是垃圾,不可用 Data-Segment,這里存放了全局變量和靜態(tài)變量,直到腳本運(yùn)行結(jié)束,操作系統(tǒng)才會(huì)回收這里的內(nèi)存空間,變量亦會(huì)被銷(xiāo)毀.
Stack-Heap Segment 函數(shù)參數(shù)與本地變量(也稱(chēng)局部變量)存放在堆中(stack),還有返回值等等.用完了,操作系統(tǒng)就會(huì)回收這部分內(nèi)存空間.對(duì)于C程序員而言,可以自行從棧中(heap)申請(qǐng)內(nèi)存空間,用完了,也需要自己手動(dòng)釋放.
作為PHP程序言而言,我們關(guān)心的是全局變量、靜態(tài)變量、局部變量、函數(shù)參數(shù)以及函數(shù)返回值.局部變量和函數(shù)參數(shù)基本上一樣,在初始化的時(shí)候分配內(nèi)存空間,退出函數(shù)后操作系統(tǒng)會(huì)回收內(nèi)存空間。而全局變量與靜態(tài)變量要直php腳本運(yùn)行結(jié)束后,內(nèi)存空間才會(huì)被釋放.與全局變量不同的時(shí),所有靜態(tài)變量在程序執(zhí)行之前就初始化并且分配了內(nèi)存空間.
注:
1.函數(shù)外部聲明靜態(tài)變量意義不大,函數(shù)內(nèi)部聲明靜態(tài)變量受限于作用域,函數(shù)外部不能修改函數(shù)內(nèi)部靜態(tài)變量.
2.引用變量,也是變量,只不過(guò)它的值是變量的內(nèi)存地址.
php保留字global和static實(shí)例代碼如下:
- $i = $j = 8;
- function global_var() {
- global $j, $b;
- $c = $j = $b = $i = 4;
- }
- global_var();
- echo "i:$i, j:$j b:$b c:$c n"; //i:8, j:4 b:4 c:
- ?>
函數(shù)外和內(nèi)都有變量$i,但是他們二個(gè)是完全不同的變量.函數(shù)外的$i是全局變量,該內(nèi)存空間直到腳本運(yùn)行結(jié)束后才會(huì)被釋放.函數(shù)內(nèi)的$i是局部變量,程序流經(jīng)過(guò)函數(shù)的時(shí)候,初始化,退出函數(shù)的時(shí)候,內(nèi)存被系統(tǒng)回收,再次調(diào)用函數(shù),則再次分配內(nèi)存空間和回收內(nèi)存空間.二次分配的內(nèi)存空間有可能是同一內(nèi)存地址,也有可能不能同一內(nèi)存地址.
與$i不同的是$j,通過(guò)關(guān)鍵字global將局部變量”轉(zhuǎn)為”全局變量.當(dāng)調(diào)用函數(shù)global_var()的時(shí)候,并不會(huì)重新給$j分配內(nèi)存空間.同樣的,可以在函數(shù)外打印$b,卻不能打印$c是因?yàn)?b是全局變量,不會(huì)被銷(xiāo)毀.而$c則不能打印,$c已經(jīng)不存在了.在退出函數(shù)就給銷(xiāo)毀了.
實(shí)例代碼如下:
- $a = 2;
- static $b = 2;
- static $c = 3;
- function global_var() {
- static $i, $c;
- global $j, $a;
- $c = $a = $b = $i = $j = 4;
- }
- global_var();
- echo "a:$a b:$b c:$c i:$i j:$j"; //a:4 b:2 c:3 i: j:4
- ?>
首先,我們看函數(shù)外的$b和$c,即是全局變量又是static變量.這里static修飾沒(méi)有太大的意義,因?yàn)樗麄兌即娣旁跀?shù)據(jù)段(data-segment),直到腳本運(yùn)行完了之后才會(huì)被回收。然后,我們?cè)倏春瘮?shù)里面的$i和$c,函數(shù)調(diào)用后,$i和$c其實(shí)都沒(méi)有被回收,但是$i輸出是NULL和$c輸出是3,這是因?yàn)樗麄兊淖饔糜蚴呛瘮?shù)內(nèi)部,不是函數(shù)外部,也就是說(shuō)$i和$c在函數(shù)外是不可見(jiàn)的.函數(shù)內(nèi)static變量的意義就在于此:僅函數(shù)內(nèi)部可見(jiàn)且不會(huì)被銷(xiāo)毀。也就是說(shuō),保證函退出函數(shù),變量也不會(huì)被回收,但又不會(huì)被其它函數(shù)修改.(注:函數(shù)外和函數(shù)內(nèi)的$c是二個(gè)不同的變量)
實(shí)例代碼如下:
- function global_var() {
- static $i;
- ++$j;
- ++$i;
- echo "j:$j i:$i n";
- }
- global_var(); //j:1 i:1
- global_var(); //j:1 i:2
- global_var(); //j:1 i:3
- ?>
上例中,變量$j一直都是1,而$i每調(diào)用一次就累加1.這是因?yàn)?局部變量存放在堆段,每次退出函數(shù)時(shí)都會(huì)被回收.而$i存放在存放在數(shù)據(jù)段(data-segment),直到程序執(zhí)行完畢才會(huì)被回收.我們平常說(shuō)的static變量,如果沒(méi)有特別指明,都說(shuō)的是函數(shù)內(nèi)部的static變量.
引用函數(shù)與static變量
既然static變量要直到腳本執(zhí)行結(jié)束,才會(huì)被銷(xiāo)毀.那么,有沒(méi)有辦法訪問(wèn)該變量的值呢?我們來(lái)看看下面的示例:
實(shí)例代碼如下:
- get_local_static_var();
- $ptr = &get_local_static_var();
- get_local_static_var();
- ++$ptr;
- get_local_static_var();
- what_i($ptr);
- get_local_static_var(); //??
- what_p($ptr);
- get_local_static_var(); //??
- function &get_local_static_var() {
- static $i;
- ++$i;
- echo "i:$i n";
- return $i;
- }
- function what_i($ptr) {
- $i = &get_local_static_var();
- ++$i;
- ++$ptr;
- }
- function what_p(&$ptr) {
- $i = &get_local_static_var();
- ++$i;
- ++$ptr;
- }
- ?>
二個(gè)凝問(wèn)號(hào)處,分別輸出是8和12,這就說(shuō)明了只要變量沒(méi)有被銷(xiāo)毀,還是可以被訪問(wèn).我們可以通過(guò)引用函數(shù)將static變量的地址返回其它函數(shù),其它函數(shù)則可通過(guò)static變量的地址訪問(wèn)并且修改它的值.
drupal應(yīng)用賞析
drupal定義了一個(gè)drupal_static函數(shù),其它函數(shù)的static變量都存放在一個(gè)數(shù)組中,然后對(duì)drupal應(yīng)用到的所有static進(jìn)行統(tǒng)一管理,比如賦值,重置,刪除等.我覺(jué)得,這是一個(gè)好辦法.
實(shí)例代碼如下:
- function &drupal_static($name, $default_value = NULL, $reset = FALSE) {
- static $data = array(), $default = array();
- if (!isset($name)) {
- foreach ($default as $name => $value) {
- $data[$name] = $value;
- }
- return $data;
- }
- if ($reset) {
- if (array_key_exists($name, $default)) {
- $data[$name] = $default[$name];
- }
- else {
- return $data;
- }
- }
- elseif (!array_key_exists($name, $data)) {
- $default[$name] = $data[$name] = $default_value;
- }
- return $data[$name];
- }
- function ip_address() {
- $ip_address = &drupal_static(__FUNCTION__);
- if (!isset($ip_address)) {
- $ip_address = $_SERVER['REMOTE_ADDR'];
- if (variable_get('reverse_proxy', 0)) {
- if (array_key_exists('HTTP_X_FORWARDED_FOR', $_SERVER)) {
- $reverse_proxy_addresses = variable_get('reverse_proxy_addresses', array());
- if (!emptyempty($reverse_proxy_addresses) &&
- in_array($ip_address, $reverse_proxy_addresses, TRUE)
- ) {
- $ip_address_parts = explode(',', $_SERVER['HTTP_X_FORWARDED_FOR']);
- $ip_address = trim(array_pop($ip_address_parts));
- }
- }
- if (array_key_exists('HTTP_X_CLUSTER_CLIENT_IP', $_SERVER)) {
- $ip_address = $_SERVER['HTTP_X_CLUSTER_CLIENT_IP'];
- }
- }
- }
- return $ip_address;
- }
- ip_address();
- //在drupal中很多這樣的應(yīng)用方式,將其它函數(shù)的static變量都存放到一個(gè)地方,即drupal_static的data中,然后再統(tǒng)一管理,比如重置等等。
- ?>
|
新聞熱點(diǎn)
疑難解答