私volatile
はJavaのキーワードについてかなり良い考えを持っていると思いますが、いくつかのコードをリファクタリングすることを考えていて、それを使うのは良い考えだと思いました.
基本的にDBキャッシュとして機能するクラスがあります。データベースから読み取った一連のオブジェクトを保持し、それらのオブジェクトの要求を処理し、(タイムアウトに基づいて) ときどきデータベースを更新します。骸骨はこちら
public class Cache
{
private HashMap mappings =....;
private long last_update_time;
private void loadMappingsFromDB()
{
//....
}
private void checkLoad()
{
if(System.currentTimeMillis() - last_update_time > TIMEOUT)
loadMappingsFromDB();
}
public Data get(ID id)
{
checkLoad();
//.. look it up
}
}
そのため、loadMappingsFromDB は待ち時間の長い操作になる可能性があり、それは受け入れられないという懸念があります。そのため、最初は、キャッシュの起動時にスレッドをスピンアップし、それをスリープさせて、バックグラウンドでキャッシュを更新できると考えていました。しかし、その後、クラス (またはマップ) を同期する必要があります。そして、すべてのキャッシュアクセスを遅くするために、時折大きな一時停止を行うだけです。
それから私はなぜ使わないのかと思いましたvolatile
マップ参照を揮発性として定義できます
private volatile HashMap mappings =....;
そして、get
(またはマッピング変数を使用する他の場所)で、参照のローカルコピーを作成します:
public Data get(ID id)
{
HashMap local = mappings;
//.. look it up using local
}
バックグラウンドスレッドは一時テーブルにロードされ、クラス内の参照を交換します
HashMap tmp;
//load tmp from DB
mappings = tmp;//swap variables forcing write barrier
このアプローチは理にかなっていますか?それは実際にスレッドセーフですか?