1. 程式人生 > >Android關於attempt to re-open an already-closed object: SQLiteDatabase: /data/data/

Android關於attempt to re-open an already-closed object: SQLiteDatabase: /data/data/

產生原因:
在一個數據庫增刪改查方法中呼叫了另一個數據庫查詢方法,注意:每個執行緒只能使用一個SQLiteOpenHelper,也就使得每個執行緒也只有一個SQLiteDatabase物件(多執行緒操作資料庫會報錯),不要以為多幾個database物件就可以了.
下面是一個例子:

/**
     * 此方法在下面一個數據庫方法內部呼叫
     * 注意1 db不能close
     *    2 cursor必須close
     */
    private int quaryNoCloseDB(String imageName) {
        int noticeCount = -1
; SQLiteDatabase db = helper.getReadableDatabase(); db.beginTransaction(); Cursor cursor; try { cursor = db.query(TABLENAME, new String[]{Constants.NOTICECOUNT}, Constants.IMAFENAME + "=?", new String[]{imageName}, null, null, null); while (cursor.moveToNext()) {//遍歷得到的所有行
.... } db.setTransactionSuccessful();// 設定事務執行成功 } finally { db.endTransaction(); } if (noticeCount == -1) { Log.i(TAG, "quary failed"); } //db.close;//不能關閉 cursor.close();//必須關閉 return noticeCount; }
 /**
     *此updata方法呼叫上面的方法
     *
     */
    public long updata(String imageName) {
        SQLiteDatabase db = helper.getWritableDatabase();
        db.beginTransaction();
        long result = 0;
        try {
            int noticeCount = this.quaryNoCloseDB(imageName);//上述方法在這裡呼叫
            ContentValues value = new ContentValues();
            value.put(Constants.NOTICECOUNT, noticeCount + 1);
            result = db.update(TABLENAME, value, Constants.IMAFENAME + "=?", new String[]{imageName});
            db.setTransactionSuccessful();// 設定事務執行成功
        } finally {
            db.endTransaction();
        }
        db.close();
        if (result != 1) {
            Log.i(TAG, "updata failed");
        }
        return result;
    }