Java | 基礎文法:定数クラス(軽く)

Java Java
スポンサーリンク

定数クラスの全体像

定数クラスは「アプリ全体で共有する変わらない値」を一か所にまとめて、意味のある名前で再利用するための入れ物です。マジックナンバーや散らばった文字列を排除し、変更箇所を一か所に集約できます。基本は「public static final」で公開し、クラスはインスタンス化不可(private コンストラクタ)にして名前空間として使います。関連が強いものは列挙型(enum)を優先し、単なる値の束は定数クラスへ——これが実用的な使い分けです。


基本形と安全な作り方

最小の定数クラス(インスタンス化不可)

public final class AppConst {
    private AppConst() {} // インスタンス化禁止

    public static final int MAX_RETRY = 3;
    public static final String DEFAULT_USER = "guest";
    public static final double TAX_RATE = 0.10;
}
Java
  • インスタンス化を防ぐための private コンストラクタは「定数クラスの型」です。
  • フィールドは public static final(不変)。複合オブジェクトは不変な型(List.of、Map.of など)で持つと安全です。

不変コレクションを持つ

import java.util.List;
import java.util.Map;

public final class Roles {
    private Roles() {}
    public static final List<String> DEFAULT_ROLES = List.of("USER");
    public static final Map<String, Integer> PERMISSIONS = Map.of("READ", 1, "WRITE", 2);
}
Java
  • 不変ならスレッドセーフで、思わぬ変更が起きません。

名前空間の切り方(関連ごとに分ける)

分類してスッキリ保つ

public final class PathsConst {
    private PathsConst() {}
    public static final String TMP_DIR = "/tmp/app";
    public static final String DATA_DIR = "/var/app/data";
}

public final class MsgConst {
    private MsgConst() {}
    public static final String ERR_NOT_FOUND = "not_found";
    public static final String ERR_UNAUTHORIZED = "unauthorized";
}

public final class NumbersConst {
    private NumbersConst() {}
    public static final int PAGE_SIZE_DEFAULT = 50;
    public static final int PAGE_SIZE_MAX = 200;
}
Java
  • 1クラスに詰め込みすぎず、目的別に分けると見通しが良くなります。
  • 変更時も「どこを見るか」が明確です。

重要ポイントの深掘り:enum との使い分け

値に意味と集合があるなら enum

public enum UserRole {
    ADMIN, EDITOR, VIEWER
}
Java
  • 取りうる値の集合が固定なら enum が最適です。型安全で、switch・比較が明瞭になります。

生の値だけなら定数クラス

  • 単なる閾値、文言キー、パス、正規表現などは定数クラスが軽量で扱いやすいです。

付加情報を持つ enum

public enum Currency {
    JPY("¥"), USD("$"), EUR("€");
    public final String symbol;
    Currency(String symbol) { this.symbol = symbol; }
}
Java
  • enum はフィールドやメソッドも持てるため、「定数+意味」のまとまりを型で表現できます。

アンチパターンと注意点

Constant Interface は避ける

// 悪例:インターフェース継承で定数をばら撒く
public interface BadConst {
    int MAX = 5;
}
public class UseIt implements BadConst { /* どこでも見えてしまう */ }
Java
  • 継承は「振る舞いの契約」のための仕組み。定数のために使うと依存が広がり、意図しない露出になります。定数クラスで参照する形が安全です。

可変オブジェクトを公開しない

// 悪例:mutable を公開
public static final java.util.List<String> ITEMS = new java.util.ArrayList<>();
// → どこからでも変更できて壊れる
Java
  • 不変で公開(List.of / Collections.unmodifiableList)にするか、防御的コピーを返します。

static import の使い方

import static com.example.AppConst.MAX_RETRY;

if (retries > MAX_RETRY) { /* ... */ }
Java
  • 使い過ぎると「どこから来た値か」が不明瞭になります。よく知られた少数だけに限定すると読みやすさを保てます。

実用例で身につける

例 1: エラーコードとメッセージキー

public final class ErrorCodes {
    private ErrorCodes() {}
    public static final String NOT_FOUND = "ERR_NOT_FOUND";
    public static final String UNAUTHORIZED = "ERR_UNAUTHORIZED";
}
Java

使い方:

log.error("code={} path={}", ErrorCodes.NOT_FOUND, path);
Java

例 2: 正規表現・タイムアウト・閾値

public final class NetConst {
    private NetConst() {}
    public static final int CONNECT_TIMEOUT_MS = 3_000;
    public static final int READ_TIMEOUT_MS = 5_000;
    public static final String IPV4_REGEX =
        "^((25[0-5]|2[0-4]\\d|[01]?\\d\\d?)\\.){3}(25[0-5]|2[0-4]\\d|[01]?\\d\\d?)$";
}
Java

例 3: ロケールやフォーマット

import java.util.Locale;
import java.time.format.DateTimeFormatter;

public final class FormatConst {
    private FormatConst() {}
    public static final Locale DEFAULT_LOCALE = Locale.JAPAN;
    public static final DateTimeFormatter ISO_DATE = DateTimeFormatter.ISO_LOCAL_DATE;
}
Java

テストと変更に強い定数の書き方

意味のある名前で「用途」を伝える

public static final int PAGE_SIZE_DEFAULT = 50;   // 何のサイズか、何の用途かを名前で表す
Java
  • 「値そのもの」ではなく「役割」を名前に込めると、コメントがなくても理解できます。

変更頻度に応じて分離

  • よく変わるビジネス値(税率・閾値)と、ほぼ不変のシステム値(フォーマット・ディレクトリ)を分けると、改修時の影響範囲が読みやすくなります。

取りうる値が増え始めたら enum へ昇格

  • 文字列定数が増え続ける場合は、型安全性を高めるため enum の導入を検討します。

仕上げのアドバイス(重要部分のまとめ)

定数は「一か所に集約」「不変」「意味のある名前」が基本です。定数クラスは final+private コンストラクタで名前空間化し、public static final で公開。可変オブジェクトは不変で持ち、用途別にファイルを分ける。取りうる値の集合には enum を使い、Constant Interface は避ける。必要なら最小限の static import——この型が身につけば、マジックナンバーや散乱文字列から解放され、変更に強いコードになります。

タイトルとURLをコピーしました