2

強制終了ダイアログから報告されたユーザーから、次のようなバグレポートが多数届いています。

java.lang.ExceptionInInitializerError
at com.MyRequest.execute(MyRequest.java:59)
at org.nsdev.MySyncAdapter.onPerformSync(MySyncAdapter.java:90)
at android.content.AbstractThreadedSyncAdapter$SyncThread.run(AbstractThreadedSyncAdapter.java:164)
  Caused by: java.lang.RuntimeException: 
  Can't create handler inside thread that has not called Looper.prepare()
at android.os.Handler.<init>(Handler.java:121)
at android.os.AsyncTask$InternalHandler.<init>(AsyncTask.java:421)
at android.os.AsyncTask$InternalHandler.<init>(AsyncTask.java:421)
at android.os.AsyncTask.<clinit>(AsyncTask.java:152)

今、私はこの問題をどのように解決するのが最善かを考えようとしています。onPerformSync実装内で、いくつかのAsyncTaskを作成して実行しています。私の問題は、onPerformSyncから戻る前にこれらのタスクが完了するのを待っていないことだと思います。私は次のことをしようとしました:

Looper.prepare();

// Execute async tasks

Looper.loop();

次に、カウンターを設定し、そのカウンターがゼロに減少したら、非同期タスクからのコールバック内でLooper.myLooper()。quit()を呼び出します。

しかし、これを行うと、次のランタイムエラーでアプリケーションがさらに激しくクラッシュします。

java.lang.RuntimeException: Main thread not allowed to quit
    at android.os.MessageQueue.enqueueMessage(MessageQueue.java:175)
    at android.os.Looper.quit(Looper.java:173)
    at org.nsdev.MySyncAdapter$1.requestFinished(MySyncAdapter.java:89)
    at com.MyAsyncTask.onPostExecute(MyAsyncTask.java:84)
    at android.os.AsyncTask.finish(AsyncTask.java:417)
    at android.os.AsyncTask.access$300(AsyncTask.java:127)
    at android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.java:429)
    at android.os.Handler.dispatchMessage(Handler.java:99)
    at android.os.Looper.loop(Looper.java:123)
    at android.app.ActivityThread.main(ActivityThread.java:4627)
    at java.lang.reflect.Method.invokeNative(Native Method)
    at java.lang.reflect.Method.invoke(Method.java:521)
    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:868)
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:626)
    at dalvik.system.NativeStart.main(Native Method)

同期を正しく実行する方法はありますか?

4

3 に答える 3

4

私はこの投稿が古いことを知っていますが、このスレッドに出くわした他の人にとっては、メインスレッドでlooper.quit()を呼び出さないのはどうですか?以下は、いくつかのAsyncTasksを生成するSyncAdpaterサービスから私のために機能しますが、パフォーマンスの観点からこれを行わない他の理由があるかもしれません...

Handler h = new Handler(Looper.getMainLooper());
            h.post(new Runnable() {
                public void run() {

                    // AsyncTask... execute();
                }
            });
于 2012-09-30T17:35:35.673 に答える
2

実際にはできません。AsyncTaskはメインUIスレッドを使用し、そこでは使用できないハンドラーとルーパーに依存します。純粋なスレッド実装を使用します。AsyncTaskはアクティビティでのみ使用する必要があります。

于 2012-05-23T17:53:41.580 に答える
0

ablocの応答で問題は解決しますが、この解決策の問題はUIがフリーズすることです。この問題は、Android2.2とAndroid2.3に存在します。私が見つけたトリックは、クラスでAsyncTaskのコンストラクターを呼び出して、次SyncAdapterを使用することでしたLooper.prepare()

/**
 * Constructor. Obtains handle to content resolver for later use.
 */
public SyncAdapter(Context context, boolean autoInitialize) {
    super(context, autoInitialize);
    mHandler = new Handler();
    //Crear un dummy AsyncTask
    new AsyncTask<Void, Void,String>() {
        @Override
        protected String doInBackground(Void... params) {
            return null;
        }
    }.execute(null,null);
}
于 2014-01-09T13:57:01.210 に答える