進度條

【PHP】23. 全域變數與系統函數

【PHP】23. 全域變數與系統函數

作者: 進度條編輯群 更新日期:

此文章也有影片介紹,可以搭配影片一起學習!

01. 全域變數與系統函數 (所屬課程)

02. 全域變數與系統函數 (所屬課程)


以下正式開始文章


關於全域變數

之前的課程就有提到一些全域變數,那我們現在來複習一下之前所學的內容,先建立一個函數並帶入參數,
 

<?php

  function printNumber($number){
    echo "{$number}<br/>";
  }

 printNumber(10);
?>    


輸出結果:

10    

 


如果想要參數乘以2,我們試著這樣寫:

 

<?php
  function printNumber($number){
    echo "{$number}<br/>";
    echo "{ $number*2 }<br/>";
  }

printNumber(10);
?>    

 


輸出結果:

 

 

 

你會發現失敗了,為什麼呢?因為大括號{}裡不能做運算,因此我們可以改成這樣子,

 

<?php
  function printNumber($number){
    echo "{$number}<br/>";
    $newNumber= $number * 2;
    echo "{$newNumber }<br/>";

  }

  printNumber(10);
?>    

 


輸出結果:

 

10
20    

 


這樣就能正常執行了,那如果<br/>也照著把它拿出來

 

<?php
  function printNumber($number){
    $br ="<br/>";
    echo "{$number}{$br}";
    $newNumber= $number * 2;
    echo "{$newNumber }{$br}";
  }

  printNumber(10);
?>    

 


輸出結果:

 

10
20    

 

 

結果是一樣的。

 

 

那麼我們再增加一個函數printEnd(),

 

<?php

  function printNumber($number){
    $br ="<br/>";
    echo "{$number}{$br}";
    $newNumber= $number * 2;
    echo "{$newNumber }{$br}";
  }

  function printEnd(){
     $br="<br/>";
     echo "------End------{$br}";

  }

  printNumber(10);
  printEnd();
?>    

 


輸出結果:

 

10
20
------End------    

 

 


既然兩個函數裡都有$br,那我們就試著把它拿到函數外共用
 

<?php

  $br = "<br/>";
  function printNumber($number){
    echo "{$number}{$br}";
    $newNumber= $number * 2;
    echo "{$newNumber }{$br}";
  }

  function printEnd(){
   echo "-------End-------{$br}";
  }

  printNumber(10);
  printEnd();
?>   

 


輸出結果:

 

1020 -------End------- 


結果並沒有成功,為什麼呢?

 

 

因為在PHP裡,函數內如果要調用全域變數的話,需要在函數裡的變數加上 global 這個關鍵字(JavaScript可以在函數裡直接調用全域變數,不須額外宣告),因此我們要這樣寫

 

<?php

  $br="<br/>";

  function printNumber($number){
    global $br;
    echo "{$number}{$br}";
    $newNumber= $number * 2;
    echo "{$newNumber }{$br}";
  }

  function printEnd(){
    global $br;
    echo "-------End-------{$br}";
  }

  printNumber(10);
  printEnd();
?>    

 


輸出結果:

 

10
20
------End------    


以上是讀取全域變數的方式。

 

 

 

關於系統函數

在第12堂「取得HTML傳遞參數」中有學到GET與POST的用法,我們可以用GET方法取得一些值,輸入 $_GET["value"]
 

 

<?php

  $br="<br/>";
  echo $_GET["value"];
  function printNumber($number){
    global $br;
    echo"{$number}{$br}";
    $newNumber= $number * 2;
    echo"{$newNumber }{$br}";
  }

 function printEnd(){
   global $br;
   echo "-------End-------{$br}";
 }


  printNumber(10);
  printEnd();
?>    

 

 


在瀏覽器輸入URL後方數入 ?value=hi 後,按下「Enter」

 

 

 

 

輸出結果:

 

 

 

 

已經抓到 $_GET["value"] 這個系統函數了,那它是否也可以直接放到函數裡呢?
 

 

<?php

  $br="<br/>";
  echo $_GET["value"];
  function printNumber($number){
    global $br;
    echo"{$number}{$br}";
    $newNumber= $number * 2;
    echo "{$newNumber }{$br}";
  }

 function printEnd(){
   global $br;
   echo "-------End-------{$br}";
 }

 printNumber(10);
 printEnd();
?>    

 

 

 

輸出結果:

 

 

答案是可以的。這時你會發現在PHP如果是自建變數的時候,如果函數調用全域變數需要在變數前面加上global,這樣似乎很麻煩,等於要打更多的程式碼,不過這個方式對於記憶體來說,這個變數只會佔到一個記憶體空間。

 

那有沒有其他方式,可以在函數外面和裡面都同時拿到值呢? 答案是當然可以的,有幾種方法:

 

第一個方法是使用系統global array

 $GLOBALS["br"] = "<br/>"

 

<?php
  $GLOBALS["br"] = "<br/>";

  function printNumber($number){
    global $br;
    echo "{$number}{$GLOBALS["br"] }";
    $newNumber= $number * 2;
    echo "{$newNumber }{$GLOBALS["br"] }";
  }

 function printEnd(){
   global $br;
   echo "-------End-------{$br}";
 }
 
 printNumber(10);
 printEnd();

?>    

 


輸出結果:

   

10
20
------End------    


但是這個方法有點不太好,因為global是整個PHP裡面都可以拿到的函數。

 

 

 

第二個方法是const(常數)

如果變數不會變的話,可以使用這個方式,利用 const BR = "<br/>"

<?php
  const BR = "<br/>";

  function printNumber($number){
    global $br;
    echo "{$number}". BR;
    $newNumber= $number * 2;
    echo "{$newNumber }".BR;
  }

 function printEnd(){
   global $br;
   echo "-------End-------{$br}";
 }

 printNumber(10);
 printEnd();
?>    

 


輸出結果:

 

10
20
------End------    

 

 

※ { $number }中的大括弧內只能放變數,因此echo "{$number}{BR}" 要改成  echo "{$number}". BR,否則{BR}會被視為字串。

 

在很多程式語言裡面都有const,它是constant 的縮寫,也就是「常數」的意思。當我們宣告const以後,就不能被再改成其他的值了。例如我試圖再把const的BR改成其他值

 

 

<?php

  const BR = "<br/>";
  BR="<hr/>";
  function printNumber($number){
    global $br;
    echo "{$number}". BR;
    $newNumber= $number * 2;
    echo "{$newNumber }".BR;
  }

 function printEnd(){
   global $br;
   echo "-------End-------{$br}";
 }

 printNumber(10);
 printEnd();

?>    

 


輸出結果:

 

 

 

結果是失敗的。

 

 

第三個方法是define

這是比較傳統的方式,不過在WordPress裡面常常看到:
 

 

<?php
  define(BR, "<br/>");
  function printNumber($number){
    global $br;
    echo "{$number}" . BR ;
    $newNumber = $number * 2;
    echo "{$newNumber}". BR;
  }

  function printEnd(){
    global $br;
    echo "-------End--------{$br}";
  }

  printNumber(10);
  printEnd();
?>    

 


輸出結果:

10
20
------End------    

 


結果是一樣的。

不過define跟const還是有一些差異,譬如我們試著覆寫它,將<br/>改成<hr/>

 

 

<?php
  define(BR, "<br/>");
  define(BR, "<hr/>");


  function printNumber($number){
    global $br;
    echo "{$number}" . BR ;
    $newNumber = $number * 2;
    echo "{$newNumber}". BR;
  }

  function printEnd(){
    global $br;
    echo "-------End--------{$br}";
  }

  printNumber(10);
  printEnd();
?>    

 


輸出結果:
 

10
20
------End------    

 

 


結果是沒有變化的。但是它不會死掉(無法執行)。然後在下面放const BR = "<hr/>"

 

 

<?php
  define(BR, "<br/>");
  const(BR, "<hr/>");


  function printNumber($number){
    global $br;
    echo "{$number}" . BR ;
    $newNumber = $number * 2;
    echo "{$newNumber}". BR;
  }

  function printEnd(){
    global $br;
    echo "-------End--------{$br}";
  }

  printNumber(10);
  printEnd();
?>    

 


輸出結果:

 

10
20
------End------    

 


也還是沒事。因此簡單來說,如果define過一次的變數,之後的改變就對它沒有任何影響。如果將剛剛的const BR = "<hr/>" 移到最前面

 

<?php
  const BR = "<hr/>";
  define (BR, "<br/>");
  define (BR, "<hr/>");


  function printNumber($number){
    global $br;
    echo "{$number}" . BR ;
    $newNumber = $number * 2;
    echo "{$newNumber}". BR;
  }

  function printEnd(){
    global $br;
    echo "-------End--------{$br}";
  }

  printNumber(10);
  printEnd();

?>    

 


輸出結果:

 

 

分隔線就正常出現了,但是後面的define就沒有作用。

 

剛才在宣告const BR = "<br/>"後再宣告BR="<hr/>"的時候,系統會死掉。

不過如果我重複宣告兩個const BR = "<hr/>"的時候呢?

 

<?php
  const BR = "<hr/>";
  const BR = "<hr/>";


  function printNumber($number){
    global $br;
    echo "{$number}" . BR ;
    $newNumber = $number * 2;
    echo "{$newNumber}". BR;
  }

  function printEnd(){
    global $br;
    echo "-------End--------{$br}";
  }

  printNumber(10);
  printEnd();
?>    


輸出結果:

 

 

 

沒有任何變動,並不會因為重複宣告而死掉。

那如果宣告const BR = "<hr/>",再宣告const BR = "<br/>"的時候呢?


 

<?php

  const BR = "<hr/>";
  const BR = "<br/>";


  function printNumber($number){
    global $br;
    echo "{$number}" . BR ;
    $newNumber = $number * 2;
    echo "{$newNumber}". BR;
  }

  function printEnd(){
    global $br;
    echo "-------End--------{$br}";
  }

  printNumber(10);
  printEnd();

?>    

 


輸出結果:

 

 

 

儘管不會成功改變成<br/>,但也不會死掉。

 

 

來個結論:

如果我們如果要使用常數的話,有const和define兩種方式可以使用。那以目前的PHP版本(7以上)來說,const和define大致上是一樣的意思。只是在比較舊版PHP的話,const只能使用在class(類別)裡面,目前還沒有教。

 

而在wordpress裡面因為看到大量的define而不是const,如果語法上許可的話,用define會比較安全,如果需要比較明確的指示,就用const。實際上在很多的程式語言define跟const還是很模糊,那以老師個人的習慣,如果是class或function裡面會使用const,如果是設定檔會用define。

 

因此在WordPress裡面看到define,基本上都是設定檔的位置。例如我們在WordPress第一個改的設定檔就是wp-config,而這個wp-config裡會看到大量的define而不是const,因為它是設定檔。

 

 


最後,如果你喜歡我們的文章,別忘了到我們的FB粉絲團按讚喔!!

Small logo

進度條編輯群

進度條編輯團隊