2009-07-13 2 views
21

上のSQLiteのカーソルない私はこれを感じているだけ...クエリとAndroid

だ場合、私はお尻でアンドロイド完全な痛みとかなりの魂破壊でのsqlite APIを扱う見つけることを確認して作業。誰かが私の人生を楽にするためのヒント/ヘルパーを持っていますか?

ここに私が話している事例があります。

//create code 

db.execSQL("CREATE TABLE " + CUSTOMER_TABLE_NAME + " (" 
         + GENERIC_ID_KEY+ " INTEGER PRIMARY KEY NOT NULL, " 
         + PHONE_KEY + " INTEGER NOT NULL, " 
         + CUSTOMER_NAME_KEY+ " TEXT NOT NULL, " 
         + EMAIL_KEY + " TEXT NOT NULL, " 
         + ADDRESS_KEY +" TEXT);"); 


//get code 
    Cursor mCursor = mDb.query(true, CUSTOMER_TABLE_NAME, new String[] {GENERIC_ID_KEY, 
         ADDRESS_KEY, PHONE_KEY, EMAIL_KEY,CUSTOMER_NAME_KEY}, GENERIC_ID_KEY + "=" + customerDbId, null, 
           null, null, null, null); 

     Customer customer = new Customer (customerDbId, (CharSequence)mCursor.getString(mCursor.getColumnIndexOrThrow(CUSTOMER_NAME_KEY)), 
          (CharSequence)mCursor.getString(mCursor.getColumnIndexOrThrow(PHONE_KEY)), 
          (CharSequence)mCursor.getString(mCursor.getColumnIndexOrThrow(EMAIL_KEY)), 
          (CharSequence)mCursor.getString(mCursor.getColumnIndexOrThrow(ADDRESS_KEY))); 

これは、dbクエリから単純な顧客オブジェクトを作成する簡単な例です。私のコードのいくつかはこれよりも厄介です。この方法で手作業でクエリを作成すると、実行時まで見つけることのできないすべてのエラーが発生します。

どのようなヒントも大いに喜ばれます!私は今、この持っている以下のヒントの後に[OK]を

:お客様で

db.execSQL("CREATE TABLE customer (_id INTEGER PRIMARY KEY NOT NULL, " 
         + "phone_number INTEGER NOT NULL, " 
         + "name TEXT NOT NULL, " 
         + "email TEXT NOT NULL, " 
         + "address TEXT);"); 


    //get code 
String q = "SELECT * FROM customer WHERE _id = " + customerDbId +";" 
     Cursor mCursor = mDb.rawQuery(q, null); 

     Customer customer = new Customer (mCursor); 

を、私は

:)はるかに良い感じ、この

mName = cursor.getString(2) 

ああのようなフィールドにアクセス歓声 si

+1

モバイルプラットフォームは、デスクトップオペレーティングシステムと同じ抽象化を提供しません。 –

+7

ああ、 'getColumnIndexOrThrow'は私を殺しています...列名を直接取る' getString'オーバーロードを作成できませんでしたか? –

答えて

39
  1. モデルオブジェクトを使用する必要がない場合は使用しないでください。私は、モデルオブジェクトを介してしか表現できない重要なビジネスロジックがない限り、モバイルプラットフォームでは価値があるよりも問題があると結論づけました。
  2. モデルオブジェクトがついていると仮定すると、パラメータを渡すのではなく、Cursorから自分自身をロードするようにします。
  3. query()は、SQLを知っていれば、限られた付加価値のためにははるかに冗長であるrawQuery()です。
  4. CREATE TABLE句を連結して組み立てることは、SQLiteやAndroidでは必須ではない自己苦痛です。
  5. カスタムコードからgetColumnIndexOrThrow()を使用しないでください。あなたはクエリーを書いているので、列が戻ってくる順序を知ることができます。与えられたCursorの詳細を知らない抽象ライブラリを作成する場合は、getColumnIndexOrThrow()のようなものだけを使用してください。
  6. StringCharSequenceから継承されているため、これらのキャストはすべて削除できます。
+0

ありがとう、rawQuery()!私はそれを見逃して、非常に便利に見える。私はモデルのオブジェクトを私がそれらにこだわっていないので、再考するつもりです。 – longhairedsi

+2

数週間前に私は自分のためにすべてを考え出したのですか?私がすでに疑っていたことを確認するのはうれしいですが、すべてのGoogleドキュメントがこの非常に複雑なルートに従っているように見えるのは残念です。 –

+0

こんにちはCommonsWare、あなたの答えの私の理解を確認できますか? Cursorはデータオブジェクトなので、カーソルを使用するときはモデル化されたオブジェクトは必要ないと言っていますか?データを操作する必要がない場合は、単にCursor? SQLiteのテーブルを "オブジェクト"にモデル化したように、私はSQLiteバックアップされたアプリケーションでモデル化されたオブジェクトをほとんど使用していません。カーソルを返すと、それはすべて必要なことです。あなたは同意しますか?詳細については、私の質問です:http://stackoverflow.com/questions/9791349/oop-modelled-objects-in-a-database-driven-app – AutoM8R

3

SQLiteでたくさんのSQLをテストしてから、文字列としてAndroidにコピーしました。コマンドラインと直接対話することができたら、デバッグするのが簡単です。

私が使用するもう1つの手法は、できるだけ多くのクエリを文字列定数または文字列リソースとして保存することです。

SQLiteはダックタイピング/マニフェストタイピングを使用するため、INTEGER NOT NULLなどのSQLも必要ありません。しかし、タイプアフィニティの助けとなります。