Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/398.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/3/android/203.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_Multithreading_Sqlite_Handler - Fatal编程技术网

Java 未调用处理程序(如何在创建时等待资源初始化)

Java 未调用处理程序(如何在创建时等待资源初始化),java,android,multithreading,sqlite,handler,Java,Android,Multithreading,Sqlite,Handler,我正在努力在活动中初始化SQLite db。我想立即访问数据库,以填充listview。这个想法是让应用程序启动一个工作线程来打开数据库,然后等待线程完成,调用一个将dbExists设置为true的处理程序,然后退出while循环。在这段代码中,应用程序挂起,从未调用处理程序(我用日志消息检查): 然而,我发现如果我把dbExists=true在线程的run()方法中,整个设置工作正常 问题: 为什么我的处理程序没有被调用?我知道默认构造函数使用线程的默认循环器,因为它是主线程,主循环器已经在运

我正在努力在活动中初始化SQLite db。我想立即访问数据库,以填充listview。这个想法是让应用程序启动一个工作线程来打开数据库,然后等待线程完成,调用一个将dbExists设置为true的处理程序,然后退出while循环。在这段代码中,应用程序挂起,从未调用处理程序(我用日志消息检查):

然而,我发现如果我把
dbExists=true
在线程的
run()
方法中,整个设置工作正常

问题:

  • 为什么我的处理程序没有被调用?我知道默认构造函数使用线程的默认循环器,因为它是主线程,主
    循环器已经在运行,对吗?我在日志中没有收到任何异常或任何类型的警告消息
  • 这是否解决了不阻塞UI线程的问题
  • 如果我可以从另一个线程访问一个线程中的变量
    dbExists
    ,为什么还要麻烦使用这个处理程序呢

  • 当您使用SQLiteOpenHelper时,只要调用getWriteableDatabase或getReadableDatabase(如果数据库不存在),就会创建或升级该数据库-在这两种情况下,操作都是同步的,并且会返回有效的数据库。如果它已经存在,您显然也会得到一个有效的数据库。我不知道你为什么认为你必须等待。我这样做只是因为文档上说不要从UI线程调用这个方法。我一直忽略了这一点。我想这取决于创建/升级过程有多复杂。我使用AsyncTask进行初始创建,使用IntentService进行日常数据导入。另外,我对schama所做的唯一升级是使用新版本,并由AsyncTask处理。考虑一下,创建一个简单的布局,其中的TextView表示类似“处理数据…”,并使用ListView setEmptyView()方法。然后使用AsyncTask(带有不确定的ProgressDialog)调用getWritableDatabase,然后进行查询并设置ListView适配器。这基本上就是我所做的,但是对于一个非常简单的数据库,我在UI线程上运行它没有任何问题。
    public class MyActivity extends FragmentActivity {
    
    static boolean dbExists = false;
    static Handler dbHandler = new Handler() {
        public void handleMessage(Message m) {
            Log.d("handler", "this log message is never printed");
            dbExists = true;
        }
    };
    static SQLiteDatabase db;
    
    public void onCreate(Bundle sIS) {
        dbHelper = MySQLiteOpenHelper(this);
        Thread dbOpener = new Thread(new Runnable() {
            public void run() {
                db = dbHelper.getWritableDatabase();
                dbHandler.sendEmptyMessage(1);
            }
        });
        //my strategy to avoid NPE thrown when trying to use db before it exists
        while(!dbExists) {
            try {
                Thread.sleep(50);
            } catch (Exception e) {
                //do nothing
            }
        }
        //do something with the db
    }