2012-08-27 9 views
10

私は、prepareStatementキャッシングのためにいくつかの定義済みの "maxStatements"を使ってc3p0を使用しています。 このキャッシングは実際に何をしていますか?どのような種類のデータをキャッシュするか。どのレベル(db、アプリケーション、..)ですか? 例から理解するといいですね。たとえば、私はクエリを持っていますPreparedStatementキャッシング - それはどういう意味ですか(どのように動作するのですか)

select * from sometable where somecolumn =?

私はキャッシュされていない準備文で送信します。 そして、私はそれを送信し、それはキャッシュされます。 違いは?最初のケースと2番目のケースで何が起こったのですか?最初のケースと2番目のケースでDBサーバーに送信されるものは何ですか?

ありがとうございました。

答えて

9

キャッシュせずに、Connectionからリクエストするたびに新しいPreparedStatementが取得されます。キャッシュを使用すると、同じSQL文字列を指定すると、PreparedStatement型の完全に同じJavaオブジェクトを頻繁に取得します。異なるパラメータでも同じPreparedStatementに同じSQLを提供すると、多くの場合、データベースは実行計画のような情報を再利用できますが、同じPreparedStatementを引き続き使用する場合に限ります。キャッシングは、あなたのアプリがそのPreparedStatement参照自体を保持することを要求しないことで、それをより簡単にします。

8

John Wattsの回答はとても良いです。

文キャッシュは透過的であるため、提供できるサンプルコードはないことに注意してください。文を使用するコードはそうでないコードとまったく同じように見えます。 maxStatementsおよびmaxStatementsPerConnectionを正の値に設定することで、c3p0でStatementキャッシングをオンにするだけです。

ステートメントキャッシュのパフォーマンス上の利点は、データベース/ JDBCドライバーに依存します。ステートメントキャッシュが役立つかどうかを確認するには、ステートメントキャッシングをオフにしてアプリケーションをプロファイリングしてから、アプリケーションが繰り返し使用するプリペアドステートメントクエリの数にmaxStatementsPerConnectionを設定してみてください。一部のアプリケーション/データベース/ドライバでは、大きなメリットがあります。他の人にとっては、大きなメリットはありません。

+0

経験則はありますか?私のアプリは順番に約100の異なるsqlsを実行するので、PreparedStatementプールでは50のヒット率が0(LRU?)になると思います。 – j23

+1

最も簡単なことは、 'maxStatementsPerConnection'を使用して、アプリケーションによって頻繁に使用されるPreparedStatementの数に設定することです。 (つまり、アプリケーションの初期化時に使用されるステートメントを無視するか、または管理目的にはそれほど頻繁に使用されないステートメントなど)、アプリケーションが常に100個の別個のPreparedStatementを実行する場合は、必ず 'maxStatementsPerConnection'を100に設定してみてくださいそのメモリとリソースのフットプリントがどんな利点よりも重要であり、あなたがなくてはるかに良いことになるでしょう。あなたは見なければならないでしょう。 –