游标、SQLite 和查询 [英] Cursors, SQLite, and queries

查看:48
本文介绍了游标、SQLite 和查询的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在我的应用程序中实现了一个 sqlite 数据库,并且在启动时不断收到 IllegalStateException.

I have a sqlitedatabase I'm implementing within my app and I keep receiving an IllegalStateException when launching.

09-21 22:48:26.749  15762-16277/nz.co.exium.panther E/AndroidRuntime﹕ FATAL EXCEPTION: SyncAdapterThread-2
java.lang.IllegalStateException: Couldn't read row 0, col 4 from CursorWindow.  Make sure the Cursor is initialized correctly before accessing data from it.
        at android.database.CursorWindow.nativeGetString(Native Method)
        at android.database.CursorWindow.getString(CursorWindow.java:438)
        at android.database.AbstractWindowedCursor.getString(AbstractWindowedCursor.java:51)
        at android.database.CursorWrapper.getString(CursorWrapper.java:114)
        at nz.co.exium.panther.sync.PantherSyncAdapter.getRegistrationId(PantherSyncAdapter.java:269)
        at nz.co.exium.panther.sync.PantherSyncAdapter.onPerformSync(PantherSyncAdapter.java:64)
        at android.content.AbstractThreadedSyncAdapter$SyncThread.run(AbstractThreadedSyncAdapter.java:254)

我相信这是由于查询返回一个相当空的表(自动递增的 _ID 除外),然后当我尝试从游标中获取字符串时引起的.

I believe this is caused by the query returning a fairly empty table (except for _ID that is autoincremented) and then when I attempt to get a String from the cursor.

String registrationID = "";
    Uri uri = CustomerEntry.CONTENT_URI;
    Cursor cursor = mContext.getContentResolver().query(uri, CUSTOMER_PROJECTION, null, null, null);
    if (cursor.moveToFirst())   {

        registrationID = cursor.getString(INDEX_CUST_REGID);
    }

SQL 创建表调用:

final String SQL_CREATE_CUSTOMER_TABLE = "CREATE TABLE " + CustomerEntry.TABLE_NAME + " (" +
            CustomerEntry._ID + " INTEGER PRIMARY KEY AUTOINCREMENT, " +
            CustomerEntry.COLUMN_CUST_NAME + " TEXT NOT NULL, " +
            CustomerEntry.COLUMN_CUST_EMAIL + " TEXT NOT NULL, " +
            CustomerEntry.COLUMN_CUST_QRHASH + " TEXT NOT NULL," +
            CustomerEntry.COLUMN_CUST_REGID + " TEXT NOT NULL)";

在这种情况下,INDEX_CUST_REGID 是与 String[] 投影中的位置相关的最终静态 int,在这种情况下是第三个位置.这会抛出是有道理的,但是是否有一种方法或方法可以查询 SyncAdapter 以获取特定列(如 CUST_REGID),或者在尝试使用 cursor.getString() 之前检查请求的列是否已返回的方法?

In this case, the INDEX_CUST_REGID is a final static int related to the position in the String[] projection, 3rd position in this case. It makes sense this would throw but is there a method or way to query the SyncAdapter for a specific column like the CUST_REGID or a method to check if the Column requested was returned before attempting a cursor.getString()?

这也可能解决我在知道 EMAIL、NAME、QRHASH 之前保存 Reg ID 的另一个问题.不能只插入一列而其余列也没有值(NOT NULL),即使它是毫无价值的数据并尽快被覆盖.

This also might solve another problem I have with saving the Reg ID before knowing the EMAIL, NAME, QRHASH. Can't insert just one column without the rest having a value as well (NOT NULL), even though it would be worthless data and overwritten asap.

尝试存储注册 ID 的方法.

Method attempting to store Reg ID.

private void storeRegistrationID(Context context, String regID) {
    //DB insert regid
    ContentValues cValues = new ContentValues();
    cValues.put(CustomerEntry.COLUMN_CUST_NAME, "");
    cValues.put(CustomerEntry.COLUMN_CUST_EMAIL, "");
    cValues.put(CustomerEntry.COLUMN_CUST_QRHASH, "");
    cValues.put(CustomerEntry.COLUMN_CUST_REGID, regID);
    mContext.getContentResolver().insert(CustomerEntry.CONTENT_URI, cValues);
}

按要求投影:

 String[] CUSTOMER_PROJECTION = new String[]{
        CustomerEntry._ID,
        CustomerEntry.COLUMN_CUST_NAME,
        CustomerEntry.COLUMN_CUST_EMAIL,
        CustomerEntry.COLUMN_CUST_QRHASH,
        CustomerEntry.COLUMN_CUST_REGID
};

推荐答案

您确定该表是实际创建的吗?SQL_CREATE_CUSTOMER_TABLE 文本字符串的末尾缺少一个分号 - 尽管我不确定是否必须运行 sql 来创建表.我建议在 Eclipse 模拟器上运行它,然后从 DDMS 的角度来看,在某个地方复制数据库,在那里你可以使用 Firefox 的 SQLite Manager 插件打开它 - 这将显示数据库表.

Are you certain the table was actually created? There's a semi-colon mising from the end of your SQL_CREATE_CUSTOMER_TABLE text string - although I'm not sure if it is mandatory to run the sql for creating the table. I would suggest running it on the Eclipse emulator, then from the DDMS perspective, take a copy of the database somewhere where you can open it with the SQLite Manager plugin for Firefox - this will show you the database tables.

这篇关于游标、SQLite 和查询的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆