onCreate有时在后台运行

时间:2014-01-14 16:02:32

标签: android android-activity

我不太确定如何调试我目前在Android应用程序中看到的现象。 我有一个Activity只是做一些网络的东西(需要在后台完成)。 此活动是使用Intent从PreferencesFragment启动的。 当用户选择首选项时,会触发Intent并启动Activity(然后它会执行网络操作并使用finish()退出。)

我创建了一个AsyncTask来在后台执行网络操作。 (我认为onCreate很可能会在UI线程中运行......) 但后来发生了异常: java.lang.RuntimeException:无法在未调用Looper.prepare()的线程内创建处理程序

onCreate()是否已在后台运行???

为了测试,我将网络功能直接移动到onCreate()。 这很好用...... ......至少几次。

突然间,抛出异常: java.lang.RuntimeException:无法启动活动ComponentInfo {...}:android.os.NetworkOnMainThreadException

将代码移回AsyncTask有一段时间了。

有谁知道为什么会出现这种现象? 是否有onCreate()在UI线程中运行的情况以及onCreate()在后台运行时的其他情况?

我的课很简单:

public class ReregisterInDb extends Activity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        new ReregisterAsyncTask().execute(""); // solution 1

            // solution 2
        //GCMFunctions gcmFunctions = new GCMFunctions(getApplicationContext());
        //gcmFunctions.registerInDb();

        super.onCreate(savedInstanceState);
        finish();
    }

    class ReregisterAsyncTask extends AsyncTask<String, Void, Void> {

        @Override
        protected Void doInBackground(String... params) {
            GCMFunctions gcmFunctions = new GCMFunctions(getApplicationContext());
            gcmFunctions.registerInDb();
            return null;
        }

    }

}

3 个答案:

答案 0 :(得分:0)

在调用super.onCreate(...)之前,您无法执行任何操作,如下所示。编辑:此外,您在AsyncTask中使用getApplicationContext可能会导致问题,尝试创建一个全局Context变量并在onCreate中初始化该变量并查看是否有效。

Context mContext;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    mContext = this;
    new ReregisterAsyncTask().execute(""); // solution 1

    finish();
}

class ReregisterAsyncTask extends AsyncTask<String, Void, Void> {

    @Override
    protected Void doInBackground(String... params) {
        GCMFunctions gcmFunctions = new GCMFunctions(mContext);
        gcmFunctions.registerInDb();
        return null;
    }

}

答案 1 :(得分:0)

尝试在异步任务的onPostExecute方法中移动活动方法finish()的调用

答案 2 :(得分:0)

我终于找到了这种奇怪行为的原因。 我没有发布registerInDb()方法的内容。 在那种方法中,有一个Toast:

Toast.makeText(context, 
  "Not currently registered with GCM. [...]", 
  Toast.LENGTH_LONG).show();

此消息导致例外...

解决方案是:

  • 在UI线程中调用该函数,以便Toast消息可以正常工作 在此处输入代码,使AsyncTask仅覆盖实际的网络代码。

很抱歉没有提供所有细节。我不认为Toast消息是根本原因。

我了解到你不能在AsyncTasks中拥有Toasts。总是必须在UI线程上运行。