2

このパターンがいくつかの異なる場所で使用されているのを見てきましたが、それが何のためにあるのか、なぜそれが必要なのか正確にはわかりません。質の高いプロジェクトで見たことがあるので、役に立つと思いますが、盲目的にフォローするのではなく、理解したいと思います。このパターンは、サーブレットフィルターとStruts2インターセプター(概念的にはフィルターと非常によく似ています)で特に見られます。

Google Guice(サーブレット)3.0の例を次に示します。

Context previous = localContext.get();

try {
  localContext.set(new Context((HttpServletRequest) servletRequest,
      (HttpServletResponse) servletResponse));

  //dispatch across the servlet pipeline, ensuring web.xml's filterchain is honored
  filterPipeline.dispatch(servletRequest, servletResponse, filterChain);
} finally {
  localContext.set(previous);
}

finallyブロックの値を復元するための必要性または利点は何ですか?

4

3 に答える 3

5

tryこれは基本的に、ブロックに対してのみ変更をスコープする方法です。ブロックが正常に実行されたかどうかに関係なく、ブロックを終了すると、入力したときの値に復元されたことがわかります。

于 2011-01-19T21:49:11.597 に答える
4

This is a pattern that is very useful, and it effectively emulates non-lexical scoping in Java. Consider the local context being essentially a global variable, or, more commonly, a thread-local variable. You modify the global to a set value (because e.g. you don't want to pass to each and every method called the HTTP request and response), which can be retrieved later on, in methods deep in the call stack. If you want to nest these modifications, a single exception can throw you out of whack - hence this construct. No matter what happens (short of a VM crash or forced process termination by the OS), that finally block will be executed as the stack unwinds, and its job is to undo the modification to global variables, because the nesting of functionality is no longer needed.

See also Thread#setContextClassLoader().

于 2011-01-19T21:53:57.603 に答える
0

このパターンが役立つと思われる別の例を挙げてみましょう。本質的には、「(通常は)グローバルリソースを使用してtry / catchブロックが完了した後、それらを予測可能な状態に復元する」と言っています。

例:DB接続プールを使用しています=>新しい接続の作成にはコストがかかることを理解しており、限られた接続プールを再利用したいと考えています。したがって、一部のサーブレットクラスのtryブロックは、Connectionで始まり、そのステートメントとResultSetを作成し、結果をObjectOutputStreamに書き込みます。これらにより、SQLException(誰かがdbテーブルの不要な列を削除し、SQLが失敗する)やキャッチブロックでキャッチしたIOException(サーブレットがまだ書き込みを行っている間にクライアントhttp接続が切断されました)。ここで、例外がスローされるかどうかに関係なく、他のスレッドが使用できるようにdb接続を閉じます。このクロージングは​​finallyブロックで行われます。

お役に立てば幸いです-MS

于 2011-01-19T22:39:14.530 に答える