講義ch05 創新數位教材 銀髮族e化健康管理概論

Page 1

銀髮族E化健康管理概論-CH5程式語法

 PHP語法架構  PHP 檔案引入路徑問題


銀髮族 E 化健康管理系統(3/3)-程式語法

A. PHP 語法架構 3.1 index.php 基本架構 利用一個自定的動作變數(如$op),搭配 switch 來控制整個流程,然後把 所有的功能都做成函數或者物件以方便呼叫使用。 index.php: 1. 2.

<?php //引入檔案區(看需要引入甚麼檔,都在此先引入)

3. 4. 5.

include "setup.php"; include "function.php"; session_start();

6.

//流程控制區(判斷使用者要做的動作,去呼叫相關的函數或物件方法)

7. 8.

switch ($_REQUEST['op']) { case "register_form": //註冊

9. 10. 11. 12. 13. 14. 15.

$main_content = register_form(); break; case "register": // register($_POST['reg']); header("location: {$_SERVER['PHP_SELF']}"); break; case "login": //登入

16. 17. 18. 19.

check_user($_POST["id"],$_POST["passwd"],true); header("location: {$_SERVER['PHP_SELF']}"); break; case "logout": //登出

20. 21. 22. 23.

logout(); header("location: {$_SERVER['PHP_SELF']}"); break; case "profile": //帳號設定

24. $main_content = register_change($_SESSION["id"]); 25. break; 26. case "modify_profile": //修改帳號


27. 28. 29. 30. 31. 32. 33. 34. 35. 36. 37. 38. 39. 40. 41. 42.

modify_profile($_POST['reg']); header("location: {$_SERVER['PHP_SELF']}"); break; case "add": add($_POST['data']); header("location: {$_SERVER['PHP_SELF']}"); break; case "modify": modify($_POST['sn']); header("location: {$_SERVER['PHP_SELF']}?op=view&p={$_POST['p']}"); break; case "diagnosis": $main_content = diagnosis(); break; default: $main_content = (check_user($_SESSION["id"],$_SESSION["passwd"]))?add_form($_GET['sn'] ):login_form(); 43. break; 44. } 45. //呈現畫面區(若此動作是需要呈現在畫面上的,那麼統一在此輸出) 46. ?> 47. 48. 49. 50. 51.

<html> <head> <meta http-equiv="content-type" content="text/html; charset=Big5"> <link rel="stylesheet" type="text/css" media="screen" href="style.css"> <title>醫療資訊建置管理系統</title>

52. </head> 53. <body background="images/bg.gif"> 54. 55. 56. 57.

<div class="center_block"> <img src="images/title.png" class="logo"> <?php

echo toolbar(); 58. echo $main_content; 59. ?>


60. </div> 61. <div class="copyright">九十五學年度 南開技術學院 醫技中心 產學合作研 究案 62. </p>醫療資訊管理系統 63. </p>執行單位:南開科技大學 電子系 64. </p> 65. </p>課程計畫主持人:江昭龍 66. 67. 68. 69.

</p> </div> </body> </html>

第 2 ~ 4 行就是所謂的引入區,也就是 index.php 用得到的檔案,統一在這裡 引入。 第 6 ~ 44 行是流程控制區,也就是利用 switch( )來判斷 index.php 所接收到 的動作變數$op 的值,由於$op 可能是利用 post 或 get 的方式傳遞過來的,為了 方便起見,我們寫成$_REQUEST[‘ op‘],這樣不管$op 用什麼方式傳遞過來,都 一律可以接收。 至於呈現畫面區就是第 45 ~ 69 行,基本上就是呈現網頁的部份,搭配 CSS(style.css),就可以呈現出我們的程式主要畫面的外觀。

3.2 function.php 在 index.php 中,有著不同的動作變數$op 值,而$op 值經過 switch( )判斷, 會去呼叫相關的 function 來執行功能,而這些 function 就一律寫在 function.php 中。

3.2.1 註冊表單 //註冊表單 function register_form($the_id=""){ if(!empty($the_id)){ $op="modify_profile"; $readonly="readonly"; $mem=get_mem_data($the_id); foreach($mem as $col=>$val){ $val=stripslashes($val);


$mem[$col]=$val; } }else{ $op="register"; $readonly=""; } $main=<<<FORM <form action="{$_SERVER['PHP_SELF']}" method="post"> <table class="input_table"> <tr> <td class="col_title">設定帳號:</td> <td class="col"><input type="text" name="reg[id]" value="{$mem['id']}" class="txt" $readonly></td> </tr> <tr> <td class="col_title">設定密碼:</td> <td class="col"><input type="password" name="reg[passwd]" class="txt"></td> </tr> <tr> <td class="col_title">確認密碼:</td> <td class="col"><input type="password" name="reg[passwd2]" class="txt"></td> </tr> <tr> <td class="col_title">電子郵件:</td> <td class="col"><input type="text" name="reg[email]" value="{$mem['email']}" class="txt"></td> </tr> <td colspan="2" align="center"> <input type="hidden" name="op" value="{$op}"> <input type="submit" value="註冊" class="input_btn"> </td> </tr> </table> </form> FORM; return $main; }


程式碼中,要注意的是所有的欄位名稱我們都是寫成 reg[xxx]的形式,這表 示到時候所有使用者所填入的值是以「一個陣列」傳出去,這樣的好處是到時候 負責接收的函數不需要接收一堆參數。 而這個表單中,也利用了隱藏欄位 op 值 register,用意就是要告知下一個程 式要執行的動作就是「註冊」 。所以當使用者按下註冊時,程式就會將資料寫入。

3.2.2 註冊動作 使用者將註冊表單送出後,程式本身接收下來並接資料儲存到 data/id_passwd.csv 以便日後認證使用,而這個函式就是 register( )。 //註冊 function register($user=array()){ if(empty($user['id']))die("請填好欄位嘛!"); if(!eregi("[_.0-9a-z-]+@([0-9a-z-]+.)+[a-z]{2,3}$",$user['email']))die("Email 格式 不正確喔!"); if(eregi("[^a-zA-Z0-9]",$user['id']))die("帳號只能用英文數字喔!");

//利用輸入的帳號去取得資料 $mem=get_mem_data($user['id']); if(!empty($mem['id']))die("此帳號已有人使用囉!"); $fp = fopen (_MEM_FILE, "a+") or die("無法開啟 "._MEM_FILE." 檔案"); //取得目前最大的編號 while ((list($sn,$email,$id,$passwd) = fgetcsv($fp, 1000))) { if(!empty($sn))$i=$sn; } $new_sn=$i+1; if(!get_magic_quotes_gpc()){ foreach($user as $col=>$val){ $val=addslashes($val); $user[$col]=$val; } }


$passwd=md5($user['passwd']); $content="{$new_sn},\"{$user['email']}\",\"{$user['id']}\",\"{$passwd}\"\n"; fwrite ($fp, $content,strlen($content)); fclose($fp); } 此函數我們設了一個$user 參數,此參數就是使用者在註冊表單中所填的所 有值,是一個陣列的型態。一執行此函數就先判斷一下一些重要的資料是否存在 或者是否正確,例如帳密沒填或兩次密碼輸入不一樣的情形,或不符我們所要 的,如 Email 的格式是否正確?帳號是否是英文數字組成的,若有不符的情況, 可以讓程式秀出警告訊息。

3.2.3 登入表單 所謂的認證就是指若使用者在程式系統中已經有帳號密碼之後,當使用者要 登入網站時,就可以輸入帳號密碼來登入,系統也必須檢查帳號密碼是否正確, 而且不是只有在登入時才需要檢查,是執行任何一個功能都要做認證的動作,所 以要讓程式可以自動執行認證。 //登入表單 function login_form(){ $main=<<<FORM <form action="{$_SERVER['PHP_SELF']}" method="post"> <table class="input_table"> <tr> <td class="col_title">帳號:</td> <td class="col"><input type="text" name="id" class="txt"></td> </tr> <tr> <td class="col_title">密碼:</td> <td class="col"><input type="password" name="passwd" class="txt"></td> </tr> <td colspan="2" align="center"> <input type="hidden" name="op" value="login"> <input type="submit" value="登入" class="input_btn"> </td> </tr>


</table> </form> FORM; return $main; } 在這個函式中,我們利用隱藏表單元件將 op 值設為 login,也就是說當使用 者按下「登入」之後,就會執行 login,也就是要進行認證,而 index.php 就會去 執行 check_user( )的動作。

3.2.4 認證方式 而 check_user( )這個函數,主要的作用就是檢查是否有傳進來帳號密碼,還 有這個帳號密碼是否存在在會員檔案中,與會員檔案是否一致,若是就傳回 true,若否就傳回 false。 //身份確認 function check_user($id="",$passwd="",$md5=false){ if(empty($id) or empty($passwd))return false ; if($md5)$passwd=md5($passwd); $user=get_mem_data($id); if($user['id']==$id and $user['passwd']==$passwd){ if(empty($_SESSION["id"])){ $_SESSION["id"]=$id; $_SESSION["passwd"]=$passwd; $_SESSION["email"]=$user['email']; } return true; } return false; } 經過 check_user( )通過認證後,會將帳號密碼等相關資料存入 session 中, session 是存在主機中的一個小檔案,可以暫存帳號密碼,以方便讓 check_user( ) 隨時檢查密碼,這樣使用者就不需要每做一個動作就要再輸入帳號密碼一次,直 到使用者登出為止。


3.2.5 新增健康檢查資料 這個部份就是此網頁的主體部分,使用者可將健康檢查的相關資料在這個表 單中輸入,包括酸鹼度 PH、蛋白質 Pro、蛋白質 Pro…等十八項健康檢查輸入, 以便等下的儲存及判斷。 //秀出輸入頁面 function add_form($sn=""){ $flag=0; $fp = fopen (_DATA_FILE, "r"); //取得目前最大的編號 while ((list($sn,$d1,$r1,$d2,$r2,$d3,$r3,$d4,$r4,$d5,$r5,$d6,$r6,$d7,$r7,$d8,$r8,$d9,$r9,$ d10,$r10,$d11,$r11,$d12,$r12,$d13,$r13,$d14,$r14,$d15,$r15,$d16,$r16,$d17,$r17,$ d18,$r18,$d19,$id,$d20,$d21,$d22,$d23,$d24) = fgetcsv($fp, 1000))) { if(!empty($sn)){ if($_SESSION["id"]==$id){ $flag=1; $val_array=get_data($sn); if(!get_magic_quotes_gpc()){ foreach($val_array as $k=>$v){ $val[$k]=stripslashes($v); } }else{ $val=$val_array; } $op="modify"; $hidden_col=" <input type='hidden' name='sn' value='{$sn}'> <input type='hidden' name='p' value='{$_GET['p']}'>"; } } } if ($flag==0) { $op="add"; }


fclose($fp); $main=<<<FORM <form action="{$_SERVER['PHP_SELF']}" method="post" enctype="multipart/form-data"> <table class="input_table"> <tr> <td colspan="4" class="col_head_title">醫療檢驗項目(括號內為正常值)</td> </tr> <tr> <td class="col_title">(1)酸鹼度 PH(5.0- 5.5):</td><td class="col"><input type="text" name="data[d1]" value="{$val['d1']}" class="txt"></td> <td class="col_title">(2)蛋白質 Pro(0.0- 1.0):</td><td class="col"><input type="text" name="data[d2]" value="{$val['d2']}" class="txt"></td> </tr> <tr> <td class="col_title">(3)紅血球 RBC(390- 451):</td><td class="col"><input type="text" name="data[d3]" value="{$val['d3']}" class="txt"></td> <td class="col_title">(4)血色素 HGB(9.3- 13.2):</td><td class="col"><input type="text" name="data[d4]" value="{$val['d4']}" class="txt"></td> </tr> <tr> <td class="col_title">(5)血球容積 HCT(33.7- 41.0):</td><td class="col"><input type="text" name="data[d5]" value="{$val['d5']}" class="txt"></td> <td class="col_title">(6)白血球 WCB(4100- 5500):</td><td class="col"><input type="text" name="data[d6]" value="{$val['d6']}" class="txt"></td> </tr> <tr> <td class="col_title">(7)血細胞比容 MCV(85- 100):</td><td class="col"><input type="text" name="data[d7]" value="{$val['d7']}" class="txt"></td> <td class="col_title">(8)血紅蛋白量 MCH(26.0- 32.7):</td><td class="col"><input type="text" name="data[d8]" value="{$val['d8']}" class="txt"></td> </tr> <tr> <td class="col_title">(9)平均紅血球血紅素濃度 MCHC(30.7- 34.5):</td><td class="col"><input type="text" name="data[d9]" value="{$val['d9']}" class="txt"></td> <td class="col_title">(10)血小板 Plat(14.4- 38.0):</td><td class="col"><input


type="text" name="data[d10]" value="{$val['d10']}" class="txt"></td> </tr> <tr> <td class="col_title">(11)SGOT(12- 23):</td><td class="col"><input type="text" name="data[d11]" value="{$val['d11']}" class="txt"></td> <td class="col_title">(12)SGPT(9.0- 30.0):</td><td class="col"><input type="text" name="data[d12]" value="{$val['d12']}" class="txt"></td> </tr> <tr> <td class="col_title">(13)血清肌胺酸酐 CRE(0.8- 1.5):</td><td class="col"><input type="text" name="data[d13]" value="{$val['d13']}" class="txt"></td> <td class="col_title">(14)尿酸 UA(3.3- 7.5):</td><td class="col"><input type="text" name="data[d14]" value="{$val['d14']}" class="txt"></td> </tr> <tr> <td class="col_title">(15)總膽固醇 Chol(129- 200):</td><td class="col"><input type="text" name="data[d15]" value="{$val['d15']}" class="txt"></td> <td class="col_title">(16)三酸甘油酯 TG(34- 139):</td><td class="col"><input type="text" name="data[d16]" value="{$val['d16']}" class="txt"></td> </tr> <tr> <td class="col_title">(17)高密度脂蛋白 HDL-C(40- 94):</td><td class="col"><input type="text" name="data[d17]" value="{$val['d17']}" class="txt"></td> <td class="col_title">(18)低密度脂蛋白 LDL-C(41- 130):</td><td class="col"><input type="text" name="data[d18]" value="{$val['d18']}" class="txt"></td> </tr> <tr> <td colspan="4" align="center"> <input type="hidden" name="op" value="{$op}"> $hidden_col <input type="submit" value="儲存" class="input_btn"> </td> </tr> </table> <td colspan="4" div class='articletext'>


<a href='{$_SERVER['PHP_SELF']}?op=diagnosis'></td>診斷結果<td class="col"></a> </div> </form> FORM; return $main; } 將健康檢查的資料輸入之後,使用者必須先將資料儲存,而資料會存在 data/data.csv 之中,接這在按下「診斷結果」,此時將 op 值設為 diagnosis,並執 行診斷的動作。

3.2.6 健康檢查資料診斷 資料建立之後,以陣列的方式儲存進資料庫中,本網頁會先把健康檢查的資 料依各自的數據算出比值,再利用資料庫中的資料做比對的動作,尋找出最符合 使用者的健康檢查診斷。 //新增一筆資料 function add($data_array=array()){ $fp = fopen (_DATA_FILE, "a+"); //取得目前最大的編號 while ((list($sn,$d1,$r1,$d2,$r2,$d3,$r3,$d4,$r4,$d5,$r5,$d6,$r6,$d7,$r7,$d8,$r8,$d9,$r9,$ d10,$r10,$d11,$r11,$d12,$r12,$d13,$r13,$d14,$r14,$d15,$r15,$d16,$r16,$d17,$r17,$ d18,$r18,$d19,$id,$d20,$d21,$d22,$d23,$d24) = fgetcsv($fp, 1000))) { if(!empty($sn))$i=$sn; } $new_sn=$i+1; $id=$_SESSION['id']; foreach($data_array as $col=>$val){ if(!get_magic_quotes_gpc()){ $val=addslashes($val); } ${$col}=$val;


} $r1=$c1=number_format($d1/8, 2); $r2=$c2=number_format($d2/1, 2); $r3=$c3=number_format($d3/664, 2); $r4=$c4=number_format($d4/46, 2); $r5=$c5=number_format($d5/53.5, 2); $r6=$c6=number_format($d6/11300, 2); $r7=$c7=number_format($d7/100, 2); $r8=$c8=number_format($d8/33.8, 2); $r9=$c9=number_format($d9/35.1, 2); $r10=$c10=number_format($d10/41.1, 2); $r11=$c11=number_format($d11/84, 2); $r12=$c12=number_format($d12/140, 2); $r13=$c13=number_format($d13/12, 2); $r14=$c14=number_format($d14/12, 2); $r15=$c15=number_format($d15/289, 2); $r16=$c16=number_format($d16/594, 2); $r17=$c17=number_format($d17/94, 2); $r18=$c18=number_format($d18/197, 2); if(5.0<=$d1 && $d1<=5.5 && 0.0<=$d2 && $d2<=1.0) $d20="尿液檢查----------正常"; else $d20="尿液檢查----------不正常"; if(390<=$d3 && $d3<=451 && 9.3<=$d4 && $d4<=13.2 && 33.7<=$d5 && $d5<=41.0 && 4100<=$d6 && $d6<=5500 && 85<=$d7 && $d7<=100 && 26.0<=$d8 && $d8<=32.7 && 30.7<=$d9 && $d9<=34.5 && 14.4<=$d10 && $d10<=38.0) $d21="血液檢查----------正常"; else $d21="血液檢查----------不正常"; if(0.8<=$d13 && $d13<=1.5 && 3.3<=$d14 && $d14<=7.5) $d22="腎功能檢查-------正常"; else $d22="腎功能檢查-------不正常";


if(129<=$d15 && $d15<=200 && 40<=$d17 && $d17<=94 && 41<=$d18 && $d18<=130 && 34<=$d16 && $d16<=139) $d23="血脂肪檢查-------正常"; else $d23="血脂肪檢查-------不正常"; if(12<=$d11 && $d11<=23 && 9.0<=$d12 && $d12<=30.0) $d24="肝膽功能檢查----正常"; else $d24="肝膽功能檢查----不正常";

$content.="{$new_sn},\"{$d1}\",\"{$r1}\",\"{$d2}\",\"{$r2}\",\"{$d3}\",\"{$r3}\",\"{ $d4}\",\"{$r4}\",\"{$d5}\",\"{$r5}\",\"{$d6}\",\"{$r6}\",\"{$d7}\",\"{$r7}\",\"{$d8}\ ",\"{$r8}\",\"{$d9}\",\"{$r9}\",\"{$d10}\",\"{$r10}\",\"{$d11}\",\"{$r11}\",\"{$d12}\ ",\"{$r12}\",\"{$d13}\",\"{$r13}\",\"{$d14}\",\"{$r14}\",\"{$d15}\",\"{$r15}\",\"{$d 16}\",\"{$r16}\",\"{$d17}\",\"{$r17}\",\"{$d18}\",\"{$r18}\",\"{$d19}\",\"{$id}\",\"{ $d20}\",\"{$d21}\",\"{$d22}\",\"{$d23}\",\"{$d24}\"\n"; fwrite ($fp, $content,strlen($content)); fclose($fp);

$fp = fopen (_DATA_FILE, "r"); $content=""; $c19="無法辨識(資料輸入不完全或本資料庫無您的資料)"; while ((list($sn,$d1,$r1,$d2,$r2,$d3,$r3,$d4,$r4,$d5,$r5,$d6,$r6,$d7,$r7,$d8,$r8,$d9,$r9,$ d10,$r10,$d11,$r11,$d12,$r12,$d13,$r13,$d14,$r14,$d15,$r15,$d16,$r16,$d17,$r17,$ d18,$r18,$d19,$id,$d20,$d21,$d22,$d23,$d24) = fgetcsv($fp, 1000))) { if($sn<290){ if($r1==$c1 && $r2==$c2 && $r3==$c3 && $r4==$c4 && $r5==$c5 && $r6==$c6 && $r7==$c7 && $r8==$c8 && $r9==$c9 && $r10==$c10 && $r11==$c11 && $r12==$c12 && $r13==$c13 && $r14==$c14 && $r15==$c15 && $r16==$c16 && $r17==$c17 && $r18==$c18){ $c19=$d19; }


} if($_SESSION["id"]==$id){ if($d20=="尿液檢查----------正常" && $d21=="血液檢查----------正常" && $d22=="腎功能檢查-------正常" && $d23=="血脂肪檢查-------正常" && $d24==" 肝膽功能檢查----正常") $c19="正常"; if(!empty($sn)) $d19=$c19; } $content.="{$sn},\"{$d1}\",\"{$r1}\",\"{$d2}\",\"{$r2}\",\"{$d3}\",\"{$r3}\",\"{$d4} \",\"{$r4}\",\"{$d5}\",\"{$r5}\",\"{$d6}\",\"{$r6}\",\"{$d7}\",\"{$r7}\",\"{$d8}\",\"{$ r8}\",\"{$d9}\",\"{$r9}\",\"{$d10}\",\"{$r10}\",\"{$d11}\",\"{$r11}\",\"{$d12}\",\"{$ r12}\",\"{$d13}\",\"{$r13}\",\"{$d14}\",\"{$r14}\",\"{$d15}\",\"{$r15}\",\"{$d16}\",\ "{$r16}\",\"{$d17}\",\"{$r17}\",\"{$d18}\",\"{$r18}\",\"{$d19}\",\"{$id}\",\"{$d20}\ ",\"{$d21}\",\"{$d22}\",\"{$d23}\",\"{$d24}\"\n"; } fclose($fp); $fp = fopen (_DATA_FILE, "w"); fwrite ($fp, $content,strlen($content)); fclose($fp); } 當使用者輸入的資料經過比對之後,若有符合的,便將其結果輸出為使用者 的健康檢查資料,若使用者輸入不完整、不正確或是資料庫中無使用者的資料, 便輸出為「無法辨識(資料輸入不完全或本資料庫無您的資料)」,此時將網頁轉 入診斷結果的頁面。

3.2.7 診斷結果 這個頁面為最終頁面,使用者的診斷結果將會輸出在這個頁面,並且提供將 症狀列印的功能。 function diagnosis(){ $fp = fopen (_DATA_FILE, "a+");


//取得目前最大的編號 while ((list($sn,$d1,$r1,$d2,$r2,$d3,$r3,$d4,$r4,$d5,$r5,$d6,$r6,$d7,$r7,$d8,$r8,$d9,$r9,$ d10,$r10,$d11,$r11,$d12,$r12,$d13,$r13,$d14,$r14,$d15,$r15,$d16,$r16,$d17,$r17,$ d18,$r18,$d19,$id,$d20,$d21,$d22,$d23,$d24) = fgetcsv($fp, 1000))) { if($_SESSION["id"]==$id){ if(!empty($sn)){ $val_array=get_data($sn); if(!get_magic_quotes_gpc()){ foreach($val_array as $k=>$v){ $val[$k]=stripslashes($v); } }else{ $val=$val_array; } $hidden_col=" <input type='hidden' name='sn' value='{$sn}'> <input type='hidden' name='p' value='{$_GET['p']}'>"; } } } $main=<<<FORM <form action="{$_SERVER['PHP_SELF']}" method="post" enctype="multipart/form-data"> <table class="input_table"> <tr> <td colspan="4" class="col_head_title">醫療診斷結果</td> </tr> <tr> <td class="col_title"> $val[d20]</p> $val[d21]</p> $val[d22]</p> $val[d23]</p> $val[d24]</p> 您的症狀:$val[d19] </tr> </table>


<td colspan="4" div class='toolbar'> <input type=button value=列印醫療診斷結果 onclick="JavaScript:window.print()"> </div> </form> FORM; return $main; }


B. PHP 檔案引入路徑問題 [五分鐘教室] PHP 檔案引入路徑問題 - 網站製作學習誌 絕對路徑 絕對路徑就是指檔案在作業系統中所存放的路徑,例如: 1 2 /var/lib/php/ … 網站製作學習誌 Blog Archives 《PHP Smarty 樣版引擎》 勘誤表 Menu Blog Archives 《PHP Smarty 樣版引擎》勘誤表 RSS [五分鐘 教室] PHP 檔案引入路徑 ... ---------------------------------------------------------------------------------------------------相信大家都知道, PHP 提供了幾個敘述句來協助我們引入外部檔案: 

include

include_once require require_once

 

那麼它們是怎麼決定引入檔案的路徑呢?

絕對路徑 絕對路徑就是指檔案在作業系統中所存放的路徑,例如: 1 /var/lib/php/library/Zend/Loader.php (在 Unix like 環境) 2 D:\php\library\PEAR.php (在 Windows 環境) 所以我們可以在 include 及 require 裡直接引入這樣的檔案: 1 require_once '/var/lib/php/library/Zend/Loader.php'; 2 include 'D:\php\library\PEAR.php';

相對路徑 相對路徑看起來比較麻煩一點,這裡也常常是 PHP 開發者一開始容易搞混的地 方。


不過只要掌握住幾個重點,那麼引入相對路徑的檔案其實也沒有想像中那麼困 難。

相對於目前檔案所在路徑 在 PHP 預設的環境設定下,我們可以引用相對於目前這支程式的其他檔案,例 如我們有一支程式 "D:\WEB\wwwroot\index.php" ,其內容如下: 1 require 'library/Zend/Loader.php'; 那麼 require 實際引入的檔案就會是 "D:\WEB\wwwroot\library\Zend\Loader.php" 。 不過為了確保程式不會因為環境的改變而無法正確引入檔案 (稍後會提到怎麼 改變) ,我們還可以用以下方式來確保引入的檔案確實是 "D:\WEB\wwwroot\library\Zend\Loader.php" 這支程式: 1 require dirname(__FILE__) . '/library/Zend/Loader.php'; 從上面的例子可以看出,我們利用 dirname(__FILE__) 來取得目前檔案的實際所 在資料夾的完整路徑 (也就是 "D:\WEB\wwwroot" ) ,然後再引入相對於這個檔 案的 "/library/Zend/Loader.php" 。

相對於 include_path 所設定的路徑 前面我們提到 include 和 require 預設可以引入相對於目前檔案路徑的程式,其 實這是定義在 php.ini 裡的 include_path 這個設定值: 1 ; UNIX: "/path1:/path2" 2 ;include_path = ".:/php/includes" 3; 4 ; Windows: "\path1;\path2" 5 include_path = ".;c:\php\includes" 可以發現 php.ini 會把「 . 」 (也就是當前目錄) 做為預設的引入路徑。而在「 . 」 這個路徑後面,我們也可以加入自訂的引入位置,像是 "c:\php\include" 等等。 註:目錄前的分隔符號,在 Unix 和 Windows 是不同的 (分別是「 : (冒號) 」 及「; (分號) 」) 。在 PHP 程式裡,我們可以用 PATH_SEPARATOR 這個預定 義常數來表示。


因此如果在程式裡不指定前面的路徑位置時, PHP 程式就會依照 include_path 所設定的路徑一一去尋找符合的檔案 (有找到就不會再往下找了) 。 例如我們的 include_path 內容為: 1 include_path = ".;c:\php5\PEAR;c:\php5\library" 那麼如果我們在 "D:\WEB\wwwroot\index.php" 引入: 1 require 'Zend/Loader.php'; 那麼 PHP 就會依照以下順序尋找 "Zend/Loader.php" : 1. "D:\WEB\wwwroot\Zend\Loader.php" 2. "c:\php5\PEAR\Zend\Loader.php" 3. "c:\php5\library\Zend\Loader.php"

include_path 的順序很重要 從上面的例子可以看到 PHP 會針對 include_path 所設定的順序去尋找檔案,所 以 include_path 設定的路徑會決定 PHP 找到要載入檔案的機會。 不過這樣一來也會浮現一個問題:如果要載入的檔案路徑一直都是在 include_path 的最後一項時,那麼會因為尋找時間過久,導致程式效率變差。 這種狀況通常發生在要載入很多類別檔案的時候,尤其是目前時下流行的 MVC 框架。 所以很多框架都會在程式一開始執行時,去調整 include_path 的引入路徑,把框 架常用的類別庫路徑放在 include_path 的第一個;而為了不影響其他程式的執 行,最後還是會把當前目錄 (也就是「 . 」) 放在 include_path 的最後一項。

結論 include 及 require 引入路徑一直都是開發 PHP 時很重要的觀念,不過只要掌握 上述的重點後,其實它們也不是這麼難以瞭解。總之,兩個重點:要不就是用絕 對路徑 (善用 dirname ) ,要不就是確定 include_path 所設定的路徑。你就一定 能找到你要引入的檔案! 就是這麼簡單!


Turn static files into dynamic content formats.

Create a flipbook
Issuu converts static files into: digital portfolios, online yearbooks, online catalogs, digital photo albums and more. Sign up and create your flipbook.