Android 扩展AsyncTask时如何以及在何处调用我的Task

Android 扩展AsyncTask时如何以及在何处调用我的Task,android,android-asynctask,Android,Android Asynctask,我很难理解AsyncTask,即使在读了Developer.Android上关于它的所有内容。我正在寻找一些关于我应该如何进行的见解。情况就是这样: 我有一个活动,它在onClick事件上调用底层LoginController类的LoginCheck()方法。LoginController类然后继续从UserInfo类或活动(用户和密码)获取任何nescesarry信息,并创建RestClient实例,然后调用web服务并尝试登录。RestClient有一个扩展AsyncTask的私有类Call

我很难理解AsyncTask,即使在读了Developer.Android上关于它的所有内容。我正在寻找一些关于我应该如何进行的见解。情况就是这样:

我有一个活动,它在onClick事件上调用底层LoginController类的LoginCheck()方法。LoginController类然后继续从UserInfo类或活动(用户和密码)获取任何nescesarry信息,并创建RestClient实例,然后调用web服务并尝试登录。RestClient有一个扩展AsyncTask的私有类CallServiceTask

我这里有一些设计上的问题,希望你能提供帮助

  • 我做得对吗?这是确保对web服务的任何调用都是异步完成的正确方法吗
  • 如何使用onProgressUpdate或其他方法通知用户应用程序正在登录
  • 如何获取保存在DoinBackground()中的数据
在下面,您可以找到有问题的项目片段:

RestClient

呼叫服务任务

私有类CallServiceTask扩展了AsyncTask
{
受保护对象[]doInBackground(对象…参数)
{
HttpUriRequest req=(HttpUriRequest)参数[0];
字符串url=(字符串)参数[1];
返回executeRequest(请求,url);
}
@凌驾
受保护的void onPostExecute(对象[]结果)
{
rtnda=结果;
}
}

任何可能长时间运行的操作都应该在单独的线程中执行,这是绝对正确的。而
AsyncTask
是解决这类问题的好方法,因为它还为您提供了一种将任务与UI线程同步的简单方法。这是你第一个问题的答案

现在,关于UI线程更新,以向用户显示应用程序没有被卡住。由于
AsyncTask
onPreExecute()
onPostExecute()
方法在UI线程内运行,因此您可以在那里轻松创建、运行和停止
ProgressDialog
ProgressBar
s。如果要显示任务的当前进度,应在
doInBackground()
中调用
publishProgress(int)
方法,然后在
AsyncTask
onProgressUpdate()方法中使用它。例如,您可以在那里更新
ProgressDialog

要从AsyncTask中获得结果,您可以调用其
get()
方法(这是一个同步调用),或者实现某种回调接口,告诉活动任务已经完成

我希望答案足够清楚,如果没有-请随意问更多的问题。希望这有帮助

编辑


使用一个方法创建一个名为
onFetchFinishedListener
的接口-
void onFetchFinished(String)
。启动
异步任务的活动必须实现此接口。现在,在
AsyncTask
中创建一个构造函数,将
OnFetchFinishedListener
对象作为参数,并在活动中实例化
AsyncTask
时,将对
活动的引用作为参数发送(因为它实现了
OnFetchFinishedListener
)。然后,当您的任务在活动的
doInBackground()
内完成时,调用
onFetchFinished()
。现在,在
活动的
onFetchFinished(String)
方法中,您可以使用回调带来的
字符串(或另一个对象)。同样,希望我说得够清楚。

你的回答很有帮助,但仍有几个问题留在我的脑海中。我一直在读“在UI线程上运行”和“在UI线程内运行”之类的东西。这是否意味着我可以在CallServiceTask类的OnPreExecute中简单地调用ProgressDialog之类的东西,UI元素将自动出现在屏幕上?现在,关于回调接口,我觉得这一切听起来都很希腊文。我还需要进一步了解:)@litemode,1)是的,你可以在onPreExecute()和onPostExecute()方法中创建对话框,2)我将尝试编辑我的答案来解释一些回调接口。
// From the constructor...
rtnData = new Object[]{ new JSONObject() , Boolean.TRUE  };

   public void ExecuteCall(RequestMethod method) throws Exception
{
    Object[] parameters = new Object[]{ new HttpGet() , new String("") };
    switch(method) {
        case GET:
        {
            //add parameters
            String combinedParams = "";
            if(!params.isEmpty()){
                combinedParams += "?";
                for(NameValuePair p : params)
                {
                    String paramString = p.getName() + "=" + URLEncoder.encode(p.getValue());
                    if(combinedParams.length() > 1)
                    {
                        combinedParams  +=  "&" + paramString;
                    }
                    else
                    {
                        combinedParams += paramString;
                    }
                }
            }

            HttpGet request = new HttpGet(url + combinedParams);

            //add headers
            for(NameValuePair h : headers)
            {
                request.addHeader(h.getName(), h.getValue());
            }
            parameters[0] = request;
            parameters[1] = url;

            new CallServiceTask().execute(request, url);


            jsonData = ((JSONObject) rtnData[0]).optJSONObject("data");
            connError = (Boolean) rtnData[1];
            break;

        }
        case POST: ....

    }
}

private Object[] executeRequest(HttpUriRequest request, String url)
{
    HttpClient client = new DefaultHttpClient();
    client = getNewHttpClient();

    HttpResponse httpResponse;

    try {
        httpResponse = client.execute(request);
        HttpEntity entity = httpResponse.getEntity();

        if (entity != null) {

            InputStream instream = entity.getContent();
            String response = convertStreamToString(instream);
            try {
                rtnData[0] = new JSONObject(response);
                rtnData[1] = false;

            } catch (JSONException e1) {
                rtnData[1] = true;
                e1.printStackTrace();
            }

            // Closing the input stream will trigger connection release
            instream.close();
        }

    } catch (ClientProtocolException e)  {
        client.getConnectionManager().shutdown();
        e.printStackTrace();
    } catch (IOException e) {
        client.getConnectionManager().shutdown();
        e.printStackTrace();
    }
    return rtnData;
}
    private class CallServiceTask extends AsyncTask<Object, Void, Object[]>
{

    protected Object[] doInBackground(Object... params) 
    {
        HttpUriRequest req = (HttpUriRequest) params[0];
        String url = (String) params[1];

        return executeRequest(req, url);
    }

    @Override
    protected void onPostExecute(Object[] result) 
    {
             rtnData = result;
    }
}