okuzawatsの日記

Android / Kotlin / GitHub Actions Enthusiast 🤖

自己カプセル化

目次

自己カプセル化(Self-Encupsulation) は、クラスの持つフィールドに対してクラス内部からアクセスする場合もアクセサメソッドを経由して行うパターンです。

以下のコード(Javaっぽい疑似コードです)は、自己カプセル化のパターンを適用する前のコードです。コンストラクタおよび getUserName で、アクセサメソッドを経由せずに firstNamelastName にアクセスしています。

class UserName {
  private String firstName;
  private String lastName;

  public UserName(String firstName, String lastName) {
    this.firstName = firstName;
    this.lastName = lastName;
  }

  public String getUserName() {
    return firstName + " " + lastName;
  }
}

firstNamelastName に対するアクセサメソッドを追加して、 firstNamelastName へのアクセスをアクセサメソッド経由に変更します。

class UserName {
  private String firstName;
  private String lastName;

  public UserName(String firstName, String lastName) {
    setFirstName(firstName);
    setLastName(lastName);
  }

  public String getUserName() {
    return getFirstName() + " " + getLastName();
  }

  private void setFirstName(String firstName) {
    this.firstName = firstName;
  }

  private String getFirstName() {
    return firstName;
  }

  private void setLastName(String lastName) {
    this.lastName = lastName;
  }

  private String getLastName() {
    return lastName;
  }
}

これだけだとコード量が増えただけで旨味がないですが、例えばsetterにassertionを追加した場合はどうでしょうか。この場合、 firstName への代入を必ずsetter経由で行うのであれば、 firstNamenull を代入できないことが保証されます。

  private void setFirstName(String firstName) {
    assert firstName != null;
    this.firstName = firstName;
  }

また、例えば仮に「 firstName は10文字以上を設定しなければならない」という仕様が追加された場合であっても、容易にそれを保証することができます1

  private void setFirstName(String firstName) {
    assert firstName != null;
    assert firstName.length >= 10;
    this.firstName = firstName;
  }

クラスの内部からアクセサメソッド経由でフィールドにアクセスするメリットは他にもあって、例えば、クラスの継承を行う場合にサブクラスでのフックを提供できるということが挙げられます。

But there are common circumstances where self-encapsulation is worth the effort. If there is logic in the setter, then it’s wise to consider it for any internal updates too. Another circumstance is when the class is part of an inheritance structure, in which case the accessors provide valuable hook points for subclasses to override behavior. (Martin Fowler(2017))

Reference

  1. Martin Fowler、(2017)、SelfEncapsulation、Retrieved from https://martinfowler.com/bliki/SelfEncapsulation.html(最終アクセス日:2022/06/05)

  1. 「仮に」です。 ↩︎

#Design

書いている人 😎

profile

茨城県つくば市在住のモバイルアプリケーションアーキテクト(Androidが得意です)。モバイルアプリのアーキテクチャ、自動テスト、CI/CDに興味があります。いわゆる「レガシーコード」のリファクタリング・リアーキテクチャが好きです。

👉 もっと詳しく

著書 ✍

Android 依存性注入 ヒッチハイク・ガイド🧳

Androidアプリでの依存性注入(Dependency Injection)に入門するためのガイダンスです。依存性注入の概念やメリットを理解し、Dagger Hiltを用いてAndroidアプリに適用する方法を解説しています。

販売サイトへ🏃

ソフトウェアデザイン 2023年6月号📚

特集「クリーンアーキテクチャとは何か?」の第5章「モバイルアプリ開発における実践」を執筆しました。

販売サイトへ🏃

Android クリーンアーキテクチャ ヒッチハイク・ガイド🧳

Androidアプリでのクリーンアーキテクチャに入門するためのガイダンスです。クリーンアーキテクチャの概念を理解し、Androidアプリに適用する方法を解説しています。

販売サイトへ🏃

Android ユニットテスト ヒッチハイク・ガイド🧳

Androidアプリのユニットテストに入門するためのガイダンスです。初学者が混乱せずにAndroidアプリのユニットテストを書き始めることができる、ということを目的としています。

販売サイトへ🏃

Android MVVMアーキテクチャ入門🛠

Androidアプリ開発の初学者に向けた、MVVM(Model-View-ViewModel)アーキテクチャの入門書を書きました。初学者の方を確実にネクストレベルに引き上げる技術書です。NextPublishingより出版されています。

販売サイトへ🏃

関連記事 👀

お問い合わせ✉️

Androidアプリ開発、特にレガシープロジェクトに関するご相談はこちらまで📨

お名前

メールアドレス

お問い合わせ内容