如何检查Async Task是否已在运行

时间:2012-09-02 14:50:55

标签: android android-asynctask

我有一个应用程序需要在启动时执行密集的数据库操作。该应用程序在手机上保存联系人的本地副本,并在启动时与Android联系人数据库同步。

如果用户启动应用程序,则启动异步任务,在后台执行数据库同步。如果用户关闭应用程序,操作将继续运行,这很好。但是,如果用户再次打开应用程序,则会启动异步任务并生成错误。

有没有检查任务是否已经从应用程序的其他实例运行?

4 个答案:

答案 0 :(得分:91)

使用getStatus()获取AsyncTask的状态。如果状态为AsyncTask.Status.RUNNING,那么您的任务正在运行。

编辑:您应该重新考虑您的实施,并将AsyncTask放在ServiceIntentService,以便从网上获取您的数据。

答案 1 :(得分:33)

是的,伙计这些是一些例子。

LoadMusicInBackground lmib = new LoadMusicInBackground();

if(lmib.getStatus() == AsyncTask.Status.PENDING){
    // My AsyncTask has not started yet
}

if(lmib.getStatus() == AsyncTask.Status.RUNNING){
    // My AsyncTask is currently doing work in doInBackground()
}

if(lmib.getStatus() == AsyncTask.Status.FINISHED){
    // My AsyncTask is done and onPostExecute was called
}

答案 2 :(得分:6)

我设法用某种Singleton模式处理这个问题。 希望它有所帮助。

// fill the places database from a JSON object
public class myAsyncTask extends AsyncTask<Void,Integer,Integer> {

    Activity mContext = null;
    static AsyncTask<Void,Integer,Integer> myAsyncTaskInstance = null; 

    // Private Constructor: can't be called from outside this class
    private myAsyncTask(Activity iContext) {
        mContext = iContext; 
    }

    public static AsyncTask<Void, Integer, Integer> getInstance(Activity iContext) {
        // if the current async task is already running, return null: no new async task 
        // shall be created if an instance is already running
        if (myAsyncTaskInstance != null && myAsyncTaskInstance.getStatus() == Status.RUNNING) {
            // it can be running but cancelled, in that case, return a new instance
            if (myAsyncTaskInstance.isCancelled()) {
                myAsyncTaskInstance = new myAsyncTask(iContext);
            } else {
                // display a toast to say "try later"
                Toast.makeText(iContext, "A task is already running, try later", Toast.LENGTH_SHORT).show();    

                return null;
            }
        }

        //if the current async task is pending, it can be executed return this instance
        if (myAsyncTaskInstance != null && myAsyncTaskInstance.getStatus() == Status.PENDING) {
            return myAsyncTaskInstance;
        }

        //if the current async task is finished, it can't be executed another time, so return a new instance
        if (myAsyncTaskInstance != null && myAsyncTaskInstance.getStatus() == Status.FINISHED) {
            myAsyncTaskInstance = new myAsyncTask(iContext);
        }


        // if the current async task is null, create a new instance
        if (myAsyncTaskInstance == null) {
            myAsyncTaskInstance = new myAsyncTask(iContext);
        }
        // return the current instance
        return myAsyncTaskInstance;
    }

    @Override
    protected Integer doInBackground(Void... iUnUsed) {
        // ...
    }
}

答案 3 :(得分:3)

我认为您应该检查ApplicationAndroid的概念。 http://developer.android.com/reference/android/app/Application.html

实际上没有

这样的东西
  

应用的不同实例

。所有Application的{​​{1}}始终相同 这意味着您已离开Activities/Services.并再次打开它,有两种情况可能:

  1. 系统已杀死您的应用程序。在这种情况下,Activity已经死了,开始一个新的
  2. 是安全的
  3. AsyncTask仍然存在,因此Application可能仍在运行。
  4. 在第二种情况下,我建议使用一些静态变量,指向此AsyncTask或它的状态。如果您的应用程序在第二次打开时仍处于活动状态 - 所有静态引用仍然有效,因此您可以成功运行。

    PS:顺便说一句,在当前的方法中,请注意您的应用程序可以随时被系统终止。所以AsyncTask可以随时中断。它对你不好 - 请检查AsyncTask - 专为背景操作目的而设计的组件。 http://developer.android.com/reference/android/app/IntentService.html

    祝你好运!