web-dev-qa-db-ja.com

Javaユーティリティクラスとサービス

Javaはユーティリティクラス(静的メソッドを持つクラス)とServiceクラス( "サービス"を提供するパブリックメソッドを持つクラス)の違いは何ですか?)たとえば、暗号化オブジェクト(暗号化、復号化、ハッシュ、またはソルト値を取得するメソッドを提供)はサービスプロバイダーですが、多くの場合、CryptoUtil.encrypt(...)などの静的メソッドを使用して、この機能をユーティリティクラスにグループ化しています。どの方法がより良い「デザイン」に従うかを理解するために。

36
djunforgetable

異なるサービスオブジェクトを使用すると、異なる動作を取得できます。ユーティリティクラスの静的メソッドはスワップアウトできません。これは、テスト、実装の変更、その他の目的に非常に役立ちます。

たとえば、CryptoUtilencryptメソッドで言及したとします。さまざまな暗号化戦略、さまざまなメッセージ受信者などをサポートできるさまざまなオブジェクトがあると非常に便利です。

24
erickson

違いは、サービスクラスに状態がある可能性があることです。そして、状態とは、会話状態を意味します。概念的な注文システムを検討してください。

interface OrderSystem {
  void login(String username, String password);
  List<Item> search(String criteria);
  void order(Item item);
  void order(Item item, int quantity);
  void update(Item item, int quantity);
  void remove(Item item);
  void checkout();
  Map<Item, Integer> getCart();
  void logout();
}

このようなことは(一例として)ステートフルセッションBeanで実行できますが、その場合、認証はおそらくより伝統的なEJBメカニズムでカバーされます。

ここでのポイントは、1つの呼び出しの結果が後続の呼び出しに影響するという会話状態があることです。静的メソッドは、ローカルで実行される単純なステートレスサービスの束と見なすことができます。

サービスには、次のような幅広い意味があります。

  • ステートフル。
  • リモート;そして
  • 実装に依存します(つまり、インターフェースを介して)。

ベストプラクティスは、静的メソッドを便利なメソッドとして使用することです(特に、Javaには拡張メソッドがないため)。サービスはそれよりはるかに豊かです。

10
cletus

静的メソッドをオーバーライドすることはできません。これは、サービスを2つの異なる方法で実装し、それらを切り替える場合に大きな問題になる可能性があります。このため、静的ユーティリティクラスの使用を、「絶対に」(「never」の十分に長い値の場合))複数の方法で実行する必要がある単純なものに制限します。

6
quant_dev

厳格で迅速なルールはないと思います。

私は通常、いくつかのパラメーターを必要とする機能に静的メソッドを使用し、単一のメソッド呼び出しで実行できます。例:

  • 文字列のハッシュ値を計算する
  • 日付を標準表現に変換する

機能が多くのパラメーターを必要とし、関連する結果がいくつか作成される場合、実際のアクションを実行するいくつかのメソッドを使用して、コンストラクターで共有パラメーターを受け入れることができるクラスを用意するのがより現実的です。

典型的な例:最初に接続してからクエリを実行し、次に結果を取得するために使用するデータベース接続...

1
sleske

私は以前この質問にどこかで回答しましたが、サービスの動作を変更することは非常に簡単で、サービスを複数のサービスにリファクタリングすることができました。静的クラスを使用すると、かなりのリファクタリングが必要になります。

それが唯一の違いである場合(そして私はそうだと私は信じています)、静的クラスを使用しても意味がありません。

誰かが「これらのうちの2つ以上になることは決してない」と言うときはいつでも、それらのうちのn個をコード化します。

0
Bill K