2012-02-06 11 views
1

フロントコントローラーとして機能するJavaサーブレットを作成しています。機能を実行するために、私はドメインコマンドパターンを使用しています。現在、私はすべてのコマンドを初期化して、コマンドの名前(文字列)をキーとして、オブジェクトを値としてマップに格納しています。サーブレットが要求を受信するたびに、私は、指定したURLからコマンドクエリを渡すことにより、マップからコマンドを取得する:コンパイルと実行時のサーブレットとコマンドパターン?

// at init 
Hashmap<String, DomainCommand> commands = new Hashmap<String, DomainCommand>(); 
commands.put("someCommand", new SomeCommand()); 

// at request 
String command = request.getParameter("command"); 
DomainCommand c = commands.get(command); 
c.execute(); 

これがうまく機能し、私のDomainCommandsは何のクラスはスレッド間で共有される属性がなかったので、私が何をしたいん。これに代わる方法は、反射を使用してオブジェクトを作成することです。

これらの両方が機能します。パフォーマンス/メモリ節約の観点からどれが良いでしょうか?

答えて

3

パフォーマンス

だけコストがHashMap(無視できる)にアクセスしているMapを使用。一方で、Reflectionは時間がかかり、安全性が低くなる可能性があります。ユーザーが偽のコードcommandを渡していないことを確認して、任意のコードを実行できるようにする必要があります。

メモリ

起動時にを作成するとき、彼らはこのように時間の大半をガベージコレクションの対象にされていない、いくつかの時間後に古い世代になってしまいます。リクエストごとに作成される場合は、すぐにガベージコレクションが行われます。したがって、全体的には、メモリフットプリントは同等ですが、2番目のアプローチではmor GCを実行する必要があります。

すべてのコマンドのマップははるかに良いアプローチです。あなたがSpringやGuiceのようなDIフレームワーク(これはあなたにとって過度のものでない限り)やStruts/Spring MVCのようなWebフレームワークなら、彼らはまったく同じ仕事をします。

+0

これは学校プロジェクトなので、ほとんどの機能を自分で実装する必要がありますが、これは私の質問にお答えします。 –

1

HashMapにコマンドを格納する最初の方法が優れています。 2番目の方法の問題は、そのコマンドを実行するたびにコマンドクラスをロードする必要があることです。

事実、個々のアクションクラスをコマンドとして持つフロントコントローラとしてのコントローラサーブレットのコマンドパターンに正確に基づいたStrutsのようなフレームワーク。

1

パフォーマンスの観点から言えば、第1のアプローチは間違いなく速いです。

次のオプションはどうですか?

  1. があなたのコマンドBeanを格納しJNDIに(リクエストから)、その名前によって、コマンドBeanの検索を行うコマンドの Visitorパターンを使用して使用して
  2. (JNDIからコマンドを取得するサービスを持っています)すべてのコマンドBeanがコンテナのスタートアップから初期化され、コマンドのルックアップがアプリケーションコンテキスト上で実行されるIoCフレームワーク(Spring)

パフォーマンス面では3番目のオプションが好きです。

0

2つのオプションを一緒にマージするのはどうですか?

Strutsはまったく同じことを行います。Servletによって要求されたすべてのコマンドをキャッシュするMapが含まれています。コマンドが存在しない場合は、コマンドのnewInstance()を作成します(作成したオプション2と同様)。

この利点は、プロセスの実行が速いことです。キャッシュからコマンドを取得します。新しいコマンドを&に作成し、キャッシュに保存します。オプション2よりもはるかに高速です。

1

パフォーマンス/メモリ節約の観点から答えを求めましたが、それ以外の答えが答えました。私は、この点でMapアプローチがおそらく良いと同意します。

ただし、この点を心配する前にこれが心配であることを確認する必要があります。私はあなたのサーブレットへの1回の呼び出しに対するネットワークオーバーヘッドが短い文字列の単一のHashMap参照をはるかに上回っていると仮定しています。

より大きな懸念事項は、明快さと保守性であるべきです。この点でも、私は地図のアプローチはそれとして、非常に優れていることを言うだろう:

  • は、実装に(クラスの名前を)API(コマンドパラメータの正当な値)を結ぶません
  • コマンドとして使用するクラスと使用しないクラスを明確にします(後で変更を加えたい場合は非常に重要です)
  • APIの柔軟性を可能にします(たとえば、大文字小文字を区別しないか、複数のコマンドを同じクラスにマップすることができます)

Zen of Pythonを引用するには:「明示的は暗黙的に優れています」。

関連する問題