Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/android/228.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/cassandra/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 异步任务中的虚假事务错误_Java_Android_Sqlite_Android Asynctask - Fatal编程技术网

Java 异步任务中的虚假事务错误

Java 异步任务中的虚假事务错误,java,android,sqlite,android-asynctask,Java,Android,Sqlite,Android Asynctask,当用户单击btnSearch时,我在main activity中启动了一个AsyncTask的background时,我遇到了错误 这里是doInBackground的一部分,在这里我可能没有错误,可能在1个事务后出错,可能在23个事务后在记录23001处出错。在尝试insertWord之后,我得到了returnCode

当用户单击
btnSearch
时,我在
main activity
中启动了一个
AsyncTask
background
时,我遇到了错误

这里是
doInBackground
的一部分,在这里我可能没有错误,可能在1个事务后出错,可能在23个事务后在记录23001处出错。在尝试
insertWord
之后,我得到了
returnCode<0

private class LoadDatabase extends AsyncTask<Object, Integer, Void
{
  protected Void doInBackground(Object[] params)
  {
...
    my_openDb("DatabaseConnector.LoadDatabase.doInBackground");

    while(scDict.hasNext())
    {
        int kTransactions = 0;
        try
        {
            mDatabase.beginTransaction();

            while(kTransactions < MAX_TRANSACTIONS && scDict.hasNext())
            {
                s = scDict.next();
                count++;
                long returnCode = insertWord(s); // error here **********
                if(returnCode < 0)
                {
                    if(debug) Log.w("`````Abort--can't add <",s + "> at " + count + " with RC = " + returnCode + " and KT = " + kTransactions );
                    my_closeDb("DatabaseConnector.LoadDatabase.doInBackground DISASTER");//$$
                    System.exit(0);
                }
                ++ kTransactions;
            }
            mDatabase.setTransactionSuccessful();
        }
        catch(Exception e){ Log.w("`````", "Exception " + e.toString()); }
        finally
        {
            mDatabase.endTransaction();
            publishProgress((Integer) (int) s.charAt(0));
        }
    } 
my_closeDb("doInBackground outer while ended");
注释掉的行在过去一直有效,直到对代码进行大的修改以简化代码。(好主意。)(不是!)我是从
https://developer.android.com/reference/android/database/sqlite/SQLiteDatabase.html
他们说的
insertWithOnConflict
是将行插入数据库的
通用方法

当然,我从一本教科书中得到了
insert
。如前所述,这是一种将行插入数据库的方便方法。但它确实缺乏解决冲突的算法。不应该有任何冲突。当我在
insert
中遇到错误时,我更改为
insertWithOnConflict

这可能是我第一次警告说我的处境很艰难

我从
MainActivity
调用
DatabaseConnector
,它调用内部类:
DatabaseHelper
,调用
LoadDatabase
,然后调用
doInBackground

我不确定是否应该将
AsyncTask
直接连接到
MainActivity
,因为答案和注释表明并发问题可能是个问题

另一个建议是将
AsyncTask
放在
MainActivity
中。这意味着我必须将类
DatabaseConnector
及其内部类也移动到那里。如果这一切看起来过于复杂,我只是在教科书中引用了一个大例子。但是您必须将数据库连接到活动,并且您确实需要帮助,如果任务必须在后台运行,那么我理解它必须是
AsyncTask

main活动调用

dbc = new DatabaseConnector(MainActivity.this, getAssets(), databaseFileExists());
在DatabaseConnector中:

  public DatabaseConnector(Context _context, AssetManager _assets, boolean dbExists)
  {
    mContext = _context;
    mDbOpenHelper = new DbOpenHelper(_context, DATABASE_NAME, null, 1);
    SQLiteDatabase db = mDbOpenHelper.getWritableDatabase();
    if( ! dbExists)
        createAndOrFillDb(db);
  }
createandfilldb

    void createAndOrFillDb(SQLiteDatabase db)
    {
    ...
        db.execSQL("CREATE TABLE " + TABLE_NAME + "(" + WORD_COLUMN_NAME + " TEXT primary key );")
    //...
         cursor = db.query(TABLE_NAME, mColumns, null, null, null, null, WORD_COLUMN_NAME);
    //...
        LoadDatabase
            __loadDb;
            __loadDb = new LoadDatabase();
            __loadDb.execute((Object[]) null);
      }
所以我的问题是

(1) 您是否认为我在
doInBackground
中的事务中得到了虚假的结果,因为它位于与
MainActivity
不同的类中?如果是,我该怎么办

(2) 你认为我应该只在
MainActivity
中插入1200行代码,这样我就不必担心并发性了,从而产生2200行的怪物吗

(3) 可能从与UI分离的线程启动
doInBackground
?(不知道如何控制,但我愿意尝试。)


(4) 您还有什么建议吗?

没有人要吗?认真地太久了?不清楚的?我尽了最大的努力,自上而下,逻辑性地表达出来,你知道吗?没有接受者?认真地太久了?不清楚的?我尽了最大的努力,自上而下,逻辑性地表达出来,你知道吗?
    void createAndOrFillDb(SQLiteDatabase db)
    {
    ...
        db.execSQL("CREATE TABLE " + TABLE_NAME + "(" + WORD_COLUMN_NAME + " TEXT primary key );")
    //...
         cursor = db.query(TABLE_NAME, mColumns, null, null, null, null, WORD_COLUMN_NAME);
    //...
        LoadDatabase
            __loadDb;
            __loadDb = new LoadDatabase();
            __loadDb.execute((Object[]) null);
      }