onPostExecute() 无法重新运行从活动调用的 asyncTask

Posted

技术标签:

【中文标题】onPostExecute() 无法重新运行从活动调用的 asyncTask【英文标题】:onPostExecute() not working on re-run of asyncTask called from an activity 【发布时间】:2013-09-25 14:05:28 【问题描述】:

如果我第一次运行我的应用程序,那么在 doinBackground() 完成后,控件会转到 onPostExecute()。但如果我在设备上重新运行应用程序而不卸载,则永远不会执行 onPostExecute()。强>

我有一个 活动,我正在调用我的 asynTask。

代码:

public class AddThing extends Activity 

        @Override
        public void onCreate(Bundle savedInstanceState) 
            super.onCreate(savedInstanceState);
            requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS); 
try 
            Class.forName("android.os.AsyncTask");
         catch (ClassNotFoundException e) 
            e.printStackTrace();
        
private View.OnClickListener onSave = new View.OnClickListener() 
startAddThingType2Task();


private class ThingCallback implements ActionCallback 

        Context cntxt;

        public ThingCallback(Context context) 
            // TODO Auto-generated constructor stub
           this.cntxt = context;    
        

        public void onSuccess(ArrayList<?> objects) 

            setProgressBarIndeterminate(false);
            Intent intent = new Intent(getApplicationContext(),DocketDetail.class);

            startActivityForResult(intent, 1);
        

        public void onFailure(Exception exception)             
            Toast.makeText(cntxt, "Unable to add docket. Error is: "+ exception.getMessage(), Toast.LENGTH_LONG).show();
               
    
private void startAddThingType2Task() 


            final AddThingType2 task = new AddThingType2(AddThing.this,new ThingCallback(this));

            runOnUiThread(new Runnable() 

                public void run() 
                    // TODO Auto-generated method stub
                    task.execute();

                
            );

我的 asyncTask 类是:

public class AddThingType2Task2 extends AsyncTask<Void, Void, Boolean> 

    public ActionCallback callback = null;
    private Context context;
    private Exception ePriv = null;
    private Activity activity;

    public AddThingType2(Activity activity,ActionCallback callback, ) 
        this.callback = callback;
        this.context = context;
        this.activity = activity;

    

    @Override
    protected void onPostExecute(Boolean result) 
        // TODO Auto-generated method stub
        super.onPostExecute(result);
        if (result == true) 
            callback.onSuccess(null);
         else 
            callback.onFailure(ePriv);
                       
    

    @Override
    protected Boolean doInBackground(Void... params) 
        // TODO Auto-generated method stub


        Boolean retval = false;



        try 

            retval = true;
            

         catch (Exception e) 
            Log.e("AddThingType2Task", e.getMessage());
            ePriv = e;
        

        return retval;
    


ActionCallback接口有两个方法——onSuccess()OnFailure()

编辑 我也在我的应用程序中使用 commonsware 唤醒意图服务

第一次它像魅力一样工作,但重新运行 onpostExecute() 不起作用......

请帮忙!!

问候

重新运行后,我在 logcat 中得到了这个:

09-20 17:37:28.515: W/MessageQueue(9311): Handler4060df08 sending message to a Handler on a dead thread
09-20 17:37:28.515: W/MessageQueue(9311): java.lang.RuntimeException: Handler4060df08 sending message to a Handler on a dead thread
09-20 17:37:28.515: W/MessageQueue(9311):   at android.os.MessageQueue.enqueueMessage(MessageQueue.java:196)
09-20 17:37:28.515: W/MessageQueue(9311):   at android.os.Handler.sendMessageAtTime(Handler.java:457)
09-20 17:37:28.515: W/MessageQueue(9311):   at android.os.Handler.sendMessageDelayed(Handler.java:430)
09-20 17:37:28.515: W/MessageQueue(9311):   at android.os.Handler.sendMessage(Handler.java:367)
09-20 17:37:28.515: W/MessageQueue(9311):   at android.location.LocationManager$ListenerTransport.onStatusChanged(LocationManager.java:206)
09-20 17:37:28.515: W/MessageQueue(9311):   at android.location.ILocationListener$Stub.onTransact(ILocationListener.java:75)
09-20 17:37:28.515: W/MessageQueue(9311):   at android.os.Binder.execTransact(Binder.java:320)
09-20 17:37:28.515: W/MessageQueue(9311):   at dalvik.system.NativeStart.run(Native Method)

【问题讨论】:

如果您使用的是WakefulIntentService,则不需要AsyncTaskIntentService 已经为您提供了一个后台线程,WakefulIntentService 继承了该线程。您的 onHandleIntent() (IntentService) 或 doWakefulWork() (WakefulIntentService) 在后台线程上。事实上,fork 另一个后台线程可能会给你带来问题。 先生,实际上我通过AsyncTask 与我的server 在需要时进行通信并且独立于WakefulIntentService onPostExecute() 中没有 WakefulIntentService,因此永远不会运行。 onPostExecute() 来自AsyncTask。如果您没有使用WakefulIntentService 中的AsyncTask,那么WakefulIntentService 与您的问题无关。如果您正在使用来自WakefulIntentServiceAsyncTask,请不要这样做。 好的先生,但请第一次查看我的问题onpostExecuteAsyncTask 正在工作,但在不卸载应用程序的情况下重新运行它没有执行......我已经发布logcat 值请检查! 【参考方案1】:
public class AddThing extends Activity 
   private ThingCallback callback;
        @Override
        public void onCreate(Bundle savedInstanceState) 
            super.onCreate(savedInstanceState);
            ThingCallback = new ThingCallback(this);
            requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS); 
try 
            Class.forName("android.os.AsyncTask");
         catch (ClassNotFoundException e) 
            e.printStackTrace();
        
private View.OnClickListener onSave = new View.OnClickListener() 
startAddThingType2Task();


private class ThingCallback implements ActionCallback 
        Context cntxt;

        public ThingCallback(Context context) 
           this.cntxt = context;    
        

        public void onSuccess(ArrayList<?> objects) 
            setProgressBarIndeterminate(false);
            Intent intent = new Intent(getApplicationContext(),DocketDetail.class);
            startActivityForResult(intent, 1);
        

        public void onFailure(Exception exception)             
            Toast.makeText(cntxt, "Unable to add docket. Error is: "+ exception.getMessage(), Toast.LENGTH_LONG).show();
               
    

private void startAddThingType2Task() 
   final AddThingType2 task = new AddThingType2(AddThing.this, callback);
   task.execute();

【讨论】:

【参考方案2】:

除了 AsyncTask 之外,您还使用任何其他线程吗?如果没有,则无需使用 runOnUiThread。删除它并且不要使 AsyncTask 引用最终。 AsyncTask 永远不能执行两次,这就是为什么每次再次使用它时都必须实例化它的原因。 final 关键字将阻止新的实例化并使引用不可变。

private void startAddThingType2Task() 
   AddThingType2 task = new AddThingType2(AddThing.this,new ThingCallback(this));
   task.execute();

如果您需要 runOnUiThread,请考虑将 AsyncTask 实例声明为字段。这样你就不必在 runOnUiThread 中使用它。

编辑:

你会有这样的东西:

public class AddThing extends Activity 
        // Your field
        AddThingType2 task;

        @Override
        public void onCreate(Bundle savedInstanceState) 
            super.onCreate(savedInstanceState);
            requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS); 
            try 
                Class.forName("android.os.AsyncTask");
             catch (ClassNotFoundException e) 
                e.printStackTrace();
            

        private View.OnClickListener onSave = new View.OnClickListener() 
            startAddThingType2Task();
        

        private void startAddThingType2Task() 
            // no final needed and you can instantiate it multiple times
            task = new AddThingType2(AddThing.this, callback);
            task.execute();
        

【讨论】:

如何将AsyncTask实例声明为字段?? 好的,我看不出你到底在做什么,因为你发布的代码似乎还不完整。 我的代码太长...检查我编辑中的 logcat 值...我没有使用任何handler【参考方案3】:

把这个类加载到应用的onCreate中

public class MyApplication extends android.app.Application

   public void onCreate()
     try 
       Class.forName("android.os.AsyncTask");
      catch (ClassNotFoundException e) 
       e.printStackTrace();
     

   

【讨论】:

以上是关于onPostExecute() 无法重新运行从活动调用的 asyncTask的主要内容,如果未能解决你的问题,请参考以下文章

由于 AsyncTask 是一个单独的类,如何将 OnPostExecute() 的结果获取到主要活动?

在 AsyncTask 的 onPostExecute 之后,无法按意图更新 RecyclerView

将字符串值分配给来自AsyncTask的onPostExecute方法的活动字符串变量不起作用

返回时如何在活动上运行函数?

如何在异步任务中调用意图?或者如何在 onPostExecute 中开始新的活动?

无法覆盖 AsyncTask 类中的 onPostExecute() 方法或使其触发