在以前的文章裡面,為了方面直接取用函式,所以我全都用public,現在要來整理一下所謂的存取修飾符,每一個的使用方式差在哪
修飾符 | 使用位置 | 類別內可存取 | 子類別可存取 | 類別外可存取 | 說明 |
---|---|---|---|---|---|
public |
屬性 / 方法 | ✓ | ✓ | ✓ | 最開放,任何地方都能存取,常用於對外介面(API、controller 方法等)。 |
protected |
屬性 / 方法 | ✓ | ✓ | ✗ | 受保護,只有類別本身與子類別能存取,用於允許子類擴充但不暴露給外部。 |
private |
屬性 / 方法 | ✓ | ✗ | ✗ | 最嚴格,僅限類別本身使用,用於封裝內部實作細節。 |
看一下程式碼的部分
<?php
// 父類別
class phone {
public $model;
public $price;
public function __construct($model, $price) {
$this->model = $model;
$this->price = $price;
}
private function call($number) { //定義私人函式
echo $this->model . " 撥號給 " . $number;
}
}
// 子類別
class SmartPhone extends phone {
}
$smartPhone = new SmartPhone("iPhone 15", 30000);
$smartPhone->call("0912345678"); // 繼承的功能
/*Fatal error: Uncaught Error: Call to private method phone::call() from context*/
?>
可以看到這邊我用子類別的物件去呼叫父類別的私人函式 會跑error
舉個例: private 就像是秘密,除了自己本身其他誰也不知道也不能用,如果我在爸爸那邊定義了一個 private ,那除了爸爸的類別裡面 誰想呼叫使用都不行。
舉個錯誤例子
<?php
// 父類別
class phone {
public $model;
public $price;
public function __construct($model, $price) {
$this->model = $model;
$this->price = $price;
}
// 私有函式
private function secretFunction() {
echo "這是爸爸的秘密功能";
}
// 公有函式
public function call($number) {
echo $this->model . " 撥號給 " . $number;
}
public function useSecret() {
$this->secretFunction(); // 爸爸內部可以使用私有函式
}
}
// 在外面定義爸爸的物件
$basicPhone = new phone("Nokia 3310", 2000);
$basicPhone->secretFunction();
/*Fatal error: Uncaught Error: Call to private method phone::secretFunction() from context 'index.php'*/
?>
這邊可以看到我在外面直接呼叫爸爸的秘密,這是不被允許的所以error,有個方法可以讓外面呼叫到這個秘密,就是使用橋梁
/*
$basicPhone->secretFunction(); 替換 $basicPhone->useSecret(); // 輸出:這是爸爸的秘密功能
*/
useSecret(爸爸裡面的函式)是可以使用private的所以先指向他,最後在外面透過這個公有函式呼叫
最後看 protected
<?php
class phone {
protected function protectedFunction() {
echo "受保護功能<br>";
}
public function useProtected() {
$this->protectedFunction(); // 爸爸內部可以使用
}
}
class SmartPhone extends phone {
public function useProtected() {
$this->protectedFunction(); // 子類別可以使用
}
}
// 測試
$smartPhone = new SmartPhone();
$smartPhone->useProtected();
$smartPhone->protectedFunction(); // 錯誤!外部不能使用
/*
受保護功能
Fatal error: Uncaught Error: Call to protected method phone::protectedFunction() from context 'index.php'
*/
?>
能夠看到想要在非類別裡面使用protected一樣要使用橋梁,他跟private的差別就式,protected可以給兒子使用private不行。
整理:
protected 函式 = 只有定義它的類別和它的子類別可以使用
爸爸不能使用兒子的 protected 函式
兒子可以使用爸爸的 protected 函式