2

目標:
Google App EngineサーバーとAndroidクライアントを使用して、AndroidクライアントのユーザーオーバーレイでGoogleマップを配置しようとしています。30秒ごとにサーバーをポーリングし、ユーザーを含むVectorを取得して、マップに追加しています。

現在のステータス:
私は1つの新しいスレッドですべてを使用しているので、アプリを実行した後、
奇妙な動作(遅延オーバーレイ、複数のオーバーレイ)が発生し、その後はでクラッシュしましConcurrentModificationExceptionた。
少し読んだ後、 AsyncTaskを使用する必要があることがわかりました。

間違っている場合は訂正してください。ただし、onCreateのアクティビティで行われるすべてがUIhreadで「実行中」であることを理解しているため、「ロジック」(すべてのネットワーク処理)をdoInBackgroundに配置し、すべてのUI処理を配置する必要があります。 onPostExecuteのマップ上のオーバーレイ。

私の質問は次のとおりです:
1)私がしている現在のステータスでは:

new Thread()
{
    @Override
    public void run() 
    {           
        super.run();
        while(true)
        {
            SystemClock.sleep(30000);   
            Vector responseFromServer = getUsersVectorFromServer();             
            putNewOnlineUserOnTheMap();
        }           
    }
}.start();

これをAsyncTaskに変換する正しい方法は何ですか?
doInBackgroundで新しいスレッドを使用してサーバーをポーリングしますか、それともこれを行う正しい方法がありますか?

2)onPostExecuteに配置するUIとしてカウントされるものの特定のリスト、または概念リストはありますか?
私の場合、putNewOnlineUserOnTheMap()をonPostExecuteに配置する必要があると思います。

ありがとう。

4

3 に答える 3

2

次のようなもの:

class UpdateTask extends AsyncTask<Void, Vector, Void>{

    @Override
    protected Void doInBackground(Void... params) {
        // this is running in a background thread.
        while (!isCancelled()) {
            SystemClock.sleep(30000);   
            Vector responseFromServer = getUsersVectorFromServer();
            // send the result back to the UI thread
            // onProgressUpdate will be called then
            publishProgress(responseFromServer);
        }
        return null;
    }

    @Override
    protected void onProgressUpdate(Vector... values) {
        // this is executed on the UI thread where we can safely touch UI stuff
        putNewOnlineUserOnTheMap(values[0]);
    }

}

タスクが終了したため、タスクの結果を使用することはできません。ただし、進行状況の公開メカニズムを使用して、定期的な結果を取得できます。そのように使用し、UIスレッドでConcurrentModificationException変更を行う場合、UIを安全に変更できる1つのスレッドで変更を行うため、取得するべきではありません。

ここで注意すべきことの1つは、バックグラウンドスレッドでの新しいインスタンスを作成Vectorし、それを使用してUIを更新することです。ただし、後でバックグラウンドスレッドで同じオブジェクトに触れないでください。そうすれば、バックグラウンドスレッドがそれを送信した後、それに触れるのはUIスレッドだけなので、同期は必要ありません。ArrayList(そして、の代わりに単純なものを使用することができますVector

于 2012-04-28T11:51:04.007 に答える
1

AsyncTaskはジェネリックスとvarargsを使用します。asyntaskに渡されるパラメーターはです。TypeOfVariableArgumentsParametersはdoInBackground()に渡され、ProgressParamは進行状況情報に使用され、ResultParamはdoInBackground()から返され、パラメーターとしてonPostExecute()に渡される必要があります。

例:-保護されたクラスParsingTaskはAsyncTaskを拡張します> {

     private ProgressDialog loadingDialog = new ProgressDialog(JsonParserActivity.this);



     protected void onPreExecute() {
         loadingDialog.setMessage("loading app store..");
         loadingDialog.show();
     }

    @Override
    protected ArrayList<Items> doInBackground( Context... params )  {

        // do ur process here.
        return result;
     }      

        if (!this.isCancelled()) {
        }

        return result;
    }

    @Override
    protected void onProgressUpdate(String... s)   {
        super.onProgressUpdate(s);
        Toast.makeText(getApplicationContext(), s[0], Toast.LENGTH_SHORT).show();
    }

    @Override
    protected void onPostExecute( ArrayList<Items> response )  {
    //if u r dealing with list view and adapters set the adapter here at the onPostExecute()
            loadingDialog.dismiss();

    }

    @Override
    protected void onCancelled() {
        super.onCancelled();

        Toast.makeText(getApplicationContext(), "The operation was cancelled", 1).show();
    }

}
于 2012-04-28T14:12:31.410 に答える
0

以下のようにAsyncTaskを使用できます。これがお役に立てば幸いです。

Class YourClass{
    void YourClass(){
       NetworkTask nT = new NetworkTasK();
       nT.execute();
    }
}
protected class NetworkTask extends AsyncTask<Void, String, Boolean>
{
    @Override
    protected Boolean doInBackground(Void... params) 
    {
        try 
        {
            String response;
            while(keepreceiving)
            {
                response = in.readLine();//Prog Counter stops here until getting i/p.

                if(response != null)
                    yourFunctionForResponse(response);
            }
        }

        catch (Exception ex) 
        {

        }
        return null;        
    }
     private void yourFunctionForResponse(String response){
     //things to do....
     }
}

これと一緒にrunOnUiThread(Runnable action)を試して、作業を実装することもできます。

于 2012-04-28T12:12:39.213 に答える