web-dev-qa-db-ja.com

Android SQLiteデータベースにテーブルが存在するかどうかを確認するにはどうすればよいですか?

データベースにレコードがあるかどうかを確認する必要があるAndroidアプリがあります。そうでない場合は、何かを処理して最終的に挿入し、データが存在する場合はデータベースからデータを読み取ります。 SQLiteOpenHelperのサブクラスを使用して、SQLiteDatabaseの書き換え可能なインスタンスを作成および取得します。テーブルが存在しない場合は、自動的にテーブルの作成を処理します(それを行うコードはonCreate(... ) 方法)。

ただし、テーブルがまだ存在せず、SQLiteDatabaseオブジェクトで最初に実行したメソッドがquery(...)の呼び出しである場合、logcatに「I/Database(26434):sqliteが返されました:error code = 1、msg = no such table:appdata "、そして確かに、appdataテーブルは作成されていません。

理由についてのアイデアはありますか?

テーブルが存在するかどうかをテストする方法を探しています(存在しない場合、データは確かに含まれていないため、書き込むまでテーブルを作成する必要はありません)適切に)、またはクエリの最初の呼び出しに間に合うように作成され、空になっていることを確認する方法(...)

編集
これは、以下の2つの回答の後に投稿されました。
問題が見つかった可能性があります。何らかの理由で、両方が同じデータベースファイルにアクセスしている場合でも、各テーブルに異なるSQLiteOpenHelperを作成することにしました。そのコードをリファクタリングして、1つのOpenHelperのみを使用し、onCreate内に両方のテーブルを作成すると、うまく機能すると思います...

82
camperdave

はい、私の編集の理論は正しかったことがわかりました:onCreateメソッドが実行されない原因は、SQLiteOpenHelperオブジェクトがデータベースを参照し、各テーブルに個別のオブジェクトを持たないという事実でした。両方のテーブルを1つのSQLiteOpenHelperにパックすると、問題が解決しました。

8
camperdave

これを試してください:

public boolean isTableExists(String tableName, boolean openDb) {
    if(openDb) {
        if(mDatabase == null || !mDatabase.isOpen()) {
            mDatabase = getReadableDatabase();
        }

        if(!mDatabase.isReadOnly()) {
            mDatabase.close();
            mDatabase = getReadableDatabase();
        }
    }

    Cursor cursor = mDatabase.rawQuery("select DISTINCT tbl_name from sqlite_master where tbl_name = '"+tableName+"'", null);
    if(cursor!=null) {
        if(cursor.getCount()>0) {
                            cursor.close();
            return true;
        }
                    cursor.close();
    }
    return false;
}
118
Nikolay DS

Android SQLite APIについては何も知りませんが、SQLで直接話すことができる場合、これを行うことができます。

create table if not exists mytable (col1 type, col2 type);

これにより、テーブルが常に作成され、既に存在する場合はエラーがスローされなくなります。

49
chrisbtoo

これは私がやったことです:

/* open database, if doesn't exist, create it */
SQLiteDatabase mDatabase = openOrCreateDatabase("exampleDb.db", SQLiteDatabase.CREATE_IF_NECESSARY,null);

Cursor c = null;
boolean tableExists = false;
/* get cursor on it */
try
{
    c = mDatabase.query("tbl_example", null,
        null, null, null, null, null);
        tableExists = true;
}
catch (Exception e) {
    /* fail */
    Log.d(TAG, tblNameIn+" doesn't exist :(((");
}

return tableExists;
11
AndroidDebaser

この質問にはすでに多くの良い答えがありますが、もっと簡単だと思う別の解決策を思いつきました。 tryブロックと次のcatchでクエリを囲みます。

catch (SQLiteException e){
    if (e.getMessage().contains("no such table")){
            Log.e(TAG, "Creating table " + TABLE_NAME + "because it doesn't exist!" );
            // create table
            // re-run query, etc.
    }
}

それは私のために働いた!

10
robguinness
 // @param db, readable database from SQLiteOpenHelper

 public boolean doesTableExist(SQLiteDatabase db, String tableName) {
        Cursor cursor = db.rawQuery("select DISTINCT tbl_name from sqlite_master where tbl_name = '" + tableName + "'", null);

    if (cursor != null) {
        if (cursor.getCount() > 0) {
            cursor.close();
            return true;
        }
        cursor.close();
    }
    return false;
}
  • sqliteは、データベース内のすべてのテーブルとインデックスの情報を含むsqlite_masterテーブルを維持します。
  • そのため、ここでは単純にSELECTコマンドを実行しています。テーブルが存在する場合、カウント1のカーソルを取得します。
2
Akshansh singh

SQLiteOpenHelperを拡張するクラスを作成し、onCreateメソッドを実装したことを述べました。そのクラスですべてのデータベース取得呼び出しを実行していることを確認していますか? SQLiteOpenHelper#getWritableDatabaseおよびSQLiteDatabaseを介してのみgetReadableDatabaseオブジェクトを取得する必要があります。そうしないと、必要なときにonCreateメソッドが呼び出されません。もしそれをしているなら、代わりにSQLiteOpenHelper#onUpgradeメソッドが呼び出されているかどうかを確認してください。その場合、データベースのバージョン番号はある時点で変更されましたが、それが発生したときにテーブルが適切に作成されませんでした。

余談ですが、データベースへのすべての接続を閉じてContext#deleteDatabaseを呼び出し、SQLiteOpenHelperを使用して新しいdbオブジェクトを取得することにより、データベースの再作成を強制できます。

2
Rich Schuler

no such table exists: errorが来るのは、同じデータベースにテーブルを作成するたびに1つのテーブルでデータベースを作成すると、このエラーが発生するためです。

このエラーを解決するには、新しいデータベースを作成する必要があり、onCreate()メソッド内で同じデータベースに複数のテーブルを作成できます。

0
Megha

Important条件はIF NOT EXISTSテーブルがすでに存在するかデータベースにないかをチェックする

好む...

String query = "CREATE TABLE IF NOT EXISTS " + TABLE_PLAYER_PHOTO + "("
            + KEY_PLAYER_ID + " TEXT,"
            + KEY_PLAYER_IMAGE + " TEXT)";
db.execSQL(query);
0
Pankaj Talaviya
 public boolean isTableExists(String tableName) {
    boolean isExist = false;
    Cursor cursor = db.rawQuery("select DISTINCT tbl_name from sqlite_master where tbl_name = '" + tableName + "'", null);
    if (cursor != null) {
        if (cursor.getCount() > 0) {
            isExist = true;
        }
        cursor.close();
    }
    return isExist;
}
0
Yogesh Rathi