web-dev-qa-db-ja.com

SQLite接続オブジェクトがリークしました-Android

私は最初のAndroid=アプリを作成しています。最初にいくつかのsqliteチュートリアルを行い、SQLiteOpenHelperを拡張するdatabaseHelperを使用する方法を学びました。そのため、私のdatabaseHelperはSQLiteOpenHelperを拡張します。sqlite接続リーク警告が表示されますLogcatでは、それを修正するために何をすべきかについてアドバイスが必要です。

このエラーが発生します:

02-01 21:39:50.740: W/SQLiteConnectionPool(32061): A SQLiteConnection object for database '/data/data/com.btf271.fashionassistant/databases/clothingManager' was leaked!  Please fix your application to end transactions in progress properly and to close the database when it is no longer needed.

リークが発生した場所で呼び出される私のdatabaseHelper関数:

 public List<Sticker> getObjectsByGenderAndCategory(String gender, String category) {
        List<Sticker> objects = new ArrayList<Object>();
        String selectQuery = String.format(
                "SELECT * FROM %s WHERE %s = \"%s\" AND %s = \"%s\"",
                TABLE_OBJECT, KEY_GENDER, gender, KEY_CATEGORY, category);

        Log.e(LOG, selectQuery);

        SQLiteDatabase db = this.getReadableDatabase();
        Cursor c = db.rawQuery(selectQuery, null);
     try{
        // looping through all rows and adding to list
        if (c.moveToFirst()) {
            do {
                Object o = createClothingItemJavaObject(c);

                // adding to object list
                objects.add(o);
            } while (c.moveToNext());
        }
     }finally {
           c.close();
db.close();
     }
        return objects;
    }

見つけました これは明日試してみます。遅いです

ありがとう。

10
user3164083

私がしたのは 同様の質問に対するこの回答を実装する だけでしたが、SQL接続オブジェクトのリークエラーは表示されません。これはお勧めできません。実装して機能するのに数分しかかかりませんでした。

コードは次のとおりです。

public class DatabaseHelper extends SQLiteOpenHelper { 

  private static DatabaseHelper mInstance = null;

  private static final String DATABASE_NAME = "database_name";
  private static final String DATABASE_TABLE = "table_name";
  private static final int DATABASE_VERSION = 1;

  public static DatabaseHelper getInstance(Context ctx) {

    // Use the application context, which will ensure that you 
    // don't accidentally leak an Activity's context.
    // See this article for more information: http://bit.ly/6LRzfx
    if (mInstance == null) {
      mInstance = new DatabaseHelper(ctx.getApplicationContext());
    }
    return mInstance;
  }

  /**
   * Constructor should be private to prevent direct instantiation.
   * make call to static factory method "getInstance()" instead.
   */
  private DatabaseHelper(Context ctx) {
    super(ctx, DATABASE_NAME, null, DATABASE_VERSION);
  }
}
18
user3164083

追加してこれを修正しました

@Override
protected void finalize() throws Throwable {
    this.close();
    super.finalize();
}

私のSQLiteOpenHelper拡張クラスに

11
Javi Martínez

getReadableDatabase()およびgetWritableDatabase()への各呼び出しを、同じデータベースオブジェクト上の対応するclose()に一致させます。

たとえば、getAllClothingItemsByGenderAndCategory()getReadableDatabase()を呼び出しますが、close()は呼び出しません。 db.close()の後にc.close()を追加します。

closeDB()は、getReadableDatabase()でデータベースへの新しい参照を取得し、thatで閉じるため、意味がありません。既存のデータベース接続を閉じることはありません。

5
laalto