0

嗨,我是一名安卓应用程序的初学者开发者。我为大学考试做这项工作。我阅读了更多文档,但在我的活动中显示进度对话框时遇到问题,而 asynktask 从服务器下载 Json 字符串,然后我必须将其放入列表视图中。在我的 UI 线程中,我调用了 Asynk 任务,但线程继续工作,我无法使用 httpGet 的结果(工作正常)。我使用 Log.i(...) 理解这一点 为什么 UI线程不会停止并参加结果?我做错了什么?请帮我。

package my.pack;


import java.util.concurrent.ExecutionException;

import android.app.Activity;
import android.app.ProgressDialog;
import android.os.AsyncTask;
import android.os.Bundle;
import android.util.Log;

public class TestDialogActivity extends Activity 
{


ProgressDialog dialog;
String url = "My URL";
String result= "init";

public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.main);

    DownloadJsonDataTask task = (DownloadJsonDataTask) new DownloadJsonDataTask(result).
            execute(url);   


    try {
        String ris = task.get();
    } catch (InterruptedException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    } catch (ExecutionException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }

    Log.i("GET",result);



}



public String requestInfoFromServer() {
    String request = null;
    HttpConnection http = HttpConnection.getInstance();
    http.setHttpClient(url);
    request = http.executeRequest();

    return request;
}   

private class DownloadJsonDataTask extends AsyncTask<String, Integer, String> 
{

    String Result;

    protected void onPreExecute()
    {
        dialog = new ProgressDialog(TestDialogActivity.this);
        dialog.setTitle("Download");
        dialog.setMessage("Please wait...");
        dialog.setIndeterminate(true);
        dialog.show();

    }

            public DownloadJsonDataTask(String response) {

                this.Result=response;
            }

    protected String doInBackground(String... urls) {
        String urldisplay = urls[0];

        Log.i("STRING URL:", urldisplay);

        String result = requestInfoFromServer();

        return Result; 

    }


    protected void onPostExecute(String result) {
        this.Result = result;
        dialog.dismiss();
    }
}

}
4

3 回答 3

1

除了萨米尔·曼格罗利亚。

task.get();是调用该方法的线程的阻塞调用。因此,在主 UI 线程上使用它会阻止它,这很糟糕,因为下载 smth 可能需要几秒钟。因此系统检测到 UI 线程被阻塞了这么长时间,并以 ANR(应用程序无响应)弹出窗口终止应用程序。将此移动结果处理修复到 AsyncTask 的 onPostExecute() (至少此时应启动结果处理,您可以在此处调用某些主机 Activity 的方法传递结果)。

于 2012-06-13T20:11:42.347 回答
0

啊,我在doInBackground(String... urls)函数中看到了问题,您现在已经声明了两个具有相似名称的不同字符串,因为变量名区分大小写,将一个字符串命名为 R 并且Result将另一个命名result为 R 和 r 被视为两个不同的字符是完全合法的,因此两者有唯一的名字。尽管这是有效的语法;这很容易出现逻辑错误。我相信这就是你遇到问题的地方。您没有在函数调用结束时为Resultto分配任何值,result这又是有效的语法,并且不像您声明时那样指向空变量Result它确实输入了一个空字符串的默认值。所以它会编译并且不会抛出空指针错误,因为变量不为空,即使其中没​​有字符串数据,指针仍然指向内存中的有效位置,所以就编译器而言,一切都是好,它不应该检查字符串的内容,只是传递它。同时result,您在通话结束之前将所有数据分配给的变量会加载您想要的所有数据。在调用结束之前被完全忽略,因为没有进一步的命令处理它。然后在调用结束时它被垃圾收集并且数据永远不会传递,因为它没有被告知只传递该变量Result

有道理?

于 2012-06-13T20:11:29.770 回答
0

在您的 doInBackground() 例程中,将下载的结果保存在成员变量 Result 中。然后,在 onPostExecute() 中,您将需要阅读 Result 并更新您的 UI。

例如:

private void updateUI(String jsondata)
{
    foo = do.something.to.derive.some.data.from.jsondata.

    TextView tv = findViewById(R.id.textview1);
    tv.setText (foo);
}

private class DownloadJsonDataTask extends AsyncTask<String, Integer, String> 
{

    String Result = null;
    ...
    protected String doInBackground(String... urls) 
    {
            Result = requestInfoFromServer();
    }


    protected void onPostExecute(String result) 
    {
         dialog.dismiss();
         updateUI(Result);
     }
  }
于 2012-06-13T20:25:11.040 回答