什麼是 Encapsulation (封裝)?

1
什麼是 Encapsulation (封裝)?:封裝(Encapsulation)是物件導向程式設計(OOP)的核心原則之一,將類別內部的資料(屬性)與操作方法綁定在一起,並透過存取控制隱藏實作細節,只暴露必要介面給外部使用。它就像膠囊藥丸,外層保護內部成分,防止外部直接干涉,同時確保資料安全與程式模組化,提高程式碼的可維護性與可靠性。

什麼是 Encapsulation (封裝)?

封裝(Encapsulation)是物件導向程式設計(OOP)的核心原則之一,將類別內部的資料(屬性)與操作方法綁定在一起,並透過存取控制隱藏實作細節,只暴露必要介面給外部使用。它就像膠囊藥丸,外層保護內部成分,防止外部直接干涉,同時確保資料安全與程式模組化,提高程式碼的可維護性與可靠性。

 

封裝的基本概念與目的

封裝透過「資料隱藏」實現,將類別內部狀態限制為私有,外部只能透過公開方法(如 Getter/Setter)存取。這避免無效輸入、意外修改,並將實作細節抽象化,讓使用者無需了解內部邏輯即可操作物件。主要目的包括保護資料完整性、促進鬆散耦合,以及簡化介面設計。

例如,銀行帳戶類別不允許直接修改餘額(防止負值),而須透過 deposit()withdraw() 方法驗證後操作。

 

存取修飾符與實現機制

封裝依賴語言提供的存取控制:

  • 公開(Public):外部可存取,如 public int balance;

  • 私有(Private):僅類別內部存取,如 private int _balance;

  • 受保護(Protected):子類別可存取,用於繼承。

  • 預設(Default/Package):同包內存取。

Getter/Setter 範例(Java):

public class BankAccount {
    private double balance;  // 私有屬性
    
    public double getBalance() {  // Getter
        return balance;
    }
    
    public void deposit(double amount) {  // Setter with validation
        if (amount > 0) balance += amount;
    }
}
 

外部呼叫:account.deposit(100);,無法直接 account.balance = -50;

 

封裝在不同語言的語法

語言 私有語法 Getter/Setter 範例
Java private getX() / setX()
Python _x 或 __x @property 裝飾器
C# private 自動屬性 {get; set;}
JS 慣例 _x #privateField (Private Fields)

Python 使用 @property 模擬:

class Circle:
    def __init__(self, radius):
        self._radius = radius  # 私有慣例
    
    @property
    def radius(self):
        return self._radius
    
    @radius.setter
    def radius(self, value):
        if value >= 0:
            self._radius = value
 

封裝與 OOP 其他特性的結合

  • 與繼承:子類可存取 protected 成員,但無法碰私有部分,維持父類穩定。

  • 與多型:公開介面一致,內部實作可變。

  • 抽象:進一步隱藏細節,僅定義合約。

實際應用如框架設計:使用者呼叫 user.save(),無需知曉是否存 SQL 或 NoSQL。

 

封裝的優點與實際範例

優點:

  • 資料保護:驗證輸入,防止無效狀態。

  • 易維護:內部變更不影響外部(如改用快取)。

  • 模組化:類別自給自足,降低耦合。

範例:購物車類別

class ShoppingCart:
    def __init__(self):
        self._items = {}  # 隱藏內部結構
    
    def add_item(self, name, price):
        self._items[name] = price  # 內部邏輯
    
    def total(self):
        return sum(self._items.values())
 

外部僅用 cart.add_item("蘋果", 50),不知內部用 dict 實作。

 

常見誤區與最佳實務

誤區:過度封裝(如全私有無介面)或無驗證 Setter。實務:

  • 只暴露必要方法。

  • 遵循最小驚喜原則(Least Surprise)。

  • 使用不變性(Immutable)物件如 String。

  • 避免大 Getter(洩漏內部狀態)。

封裝是 OOP 入門基石,讓程式如黑盒子般可靠。結合繼承與多型,形成強健架構,從簡單類別到企業系統皆適用。