2012-05-30 71 views
0

簡短版本:從活動和啓動服務訪問相同數據庫的最佳實踐方式是什麼?正確的方式從活動和已啓動的服務訪問數據庫?

長版本:我有一個情況,我從活動開始持久服務。當活動顯示在屏幕上時,服務正在用數據填充數據庫。它們都不是一直在運行 - 服務可以在沒有活動時運行,並且活動可以在尚未啓動服務時運行。但服務只能從活動中停止(它永遠不會停止)。

我正在使用SQLiteOpenHelper的子類訪問數據庫。我絆倒的問題顯然是closing DB in one SQLiteOpenHelper instance closes it in another too

我能想到的這些選項:

  1. 單例模式(單SQLiteDatabase例如在公共靜態無功 - 唯一的活動可以關閉它(因爲它知道,如果服務正在運行或不)) - 醜
  2. 如果
  3. 檢查服務/活動,在另一個關閉之前運行 - 醜陋
  4. 構建獲取/釋放到SQLiteOpenHelper的getReadableDatabase()/close()

我會和3.一起走,但這必須是一個非常常見的模式,所以我想知道是否已經有了這樣的內置機制 - 我不想重新發明輪子。

換句話說,什麼是正確的方法來做到這一點?

回答

1

Android上任何數據庫的通常範例是讓一個提供者打開數據庫並按照意圖處理請求。這具有序列化請求的優點。

從不同的代碼打開數據庫是完全不標準的。

如果您確實需要一個應用程序來注意每次添加內容時,來自提供者的廣播意圖可能就是答案。

+0

在這種情況下服務採集數據和活性顯示它(在圖)。請注意,當服務收集數據時,活動可能不運行 - 稍後,它必須顯示暫停時的數據歷史記錄。我可以解決這些限制,但在這種情況下,它會使應用程序變得更加複雜。 – johndodo

+0

經過進一步的思考,我開始喜歡你的想法...我已經用第三種方法解決了這個問題,但我會重構我的應用程序以使用廣播意圖(而不是重複讀取數據庫)。先生,謝謝你和+1。 ;) – johndodo

0

我已經解決了使用保留/釋放計數器的問題:

public class DBHandler extends SQLiteOpenHelper 
{ 
    private static int retainCount = 0; 

    @Override 
    public synchronized SQLiteDatabase getReadableDatabase() 
    { 
     DBHandler.retainCount++; 
     return super.getReadableDatabase(); 
    } 
    @Override 
    public synchronized SQLiteDatabase getWritableDatabase() 
    { 
     DBHandler.retainCount++; 
     return super.getWritableDatabase(); 
    } 
    @Override 
    public synchronized void close() 
    { 
     DBHandler.retainCount--; 
     if (DBHandler.retainCount == 0) 
      super.close(); 
     } 
    } 
}