Переменная возвращает ноль вне асинктической задачи Android
У меня есть asynctask, которая получает свои данные через php. Asynctask работает отлично, он передает значения глобальному arraylist. Однако, когда я пытаюсь вызвать переменную onCreate после.execute(), он возвращает нулевой размер / значение (я). Я хотел бы знать, почему эта глобальная переменная возвращает ноль, если предполагается, что она имеет значение. Заранее спасибо!
это код для asyntask:
private class get_pendingreq extends AsyncTask<String, Integer, String>
{
@Override
protected String doInBackground(String... arg0)
{
InputStream is = null;
String result = "";
try
{
HttpClient httpclient = new DefaultHttpClient();
HttpPost httppost = new HttpPost(url+"pending_requests.php");
List<NameValuePair> parameter = new ArrayList<NameValuePair>();
parameter.add(new BasicNameValuePair("email", globalVariables.accountemail));
httppost.setEntity(new UrlEncodedFormEntity(parameter));
HttpResponse response = httpclient.execute(httppost);
HttpEntity entity = response.getEntity();
is = entity.getContent();
} catch (Exception e)
{
Log.e("log_tag", "Error in http connection " + e.toString());
}
try
{
BufferedReader reader = new BufferedReader(
new InputStreamReader(is, "iso-8859-1"), 8);
StringBuilder sb = new StringBuilder();
String line = null;
while ((line = reader.readLine()) != null)
{
sb.append(line + "\n");
}
is.close();
result = sb.toString();
} catch (Exception e)
{
Log.e("log_tag", "Error converting result " + e.toString());
}
return result;
}
@Override
protected void onPostExecute(String result)
{
super.onPostExecute(result);
try
{
/* JSON parsing starts here */
JSONObject jArray = new JSONObject(result);
/*globalVariables.pendingdate = new ArrayList<String>();*/
JSONArray request = jArray.getJSONArray("request");
for (int i = 0; i < request.length(); i++)
{
JSONObject e = request.getJSONObject(i);
/* puts values to arraylist<String> */
globalVariables.pendingdate.add(e.getString("date"));
}
Log.d("striiing", globalVariables.pendingdate.toString());
} catch (JSONException e)
{
e.printStackTrace();
}
}
}
Основная деятельность:
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.calendar);
new get_pendingreq().execute();
System.out.print("alalala" + globalVariables.pendingdate.size());
}//this returns null
Глобальная переменная:
public static ArrayList<String> pendingdate = new ArrayList<String>;
4 ответа
Так как AsyncTask
не закончен. Положил System.out.print("finish");
в onPostExcute()
и посмотреть, кто печатается первым.
Идея, стоящая за AsyncTask
является то, что он работает асинхронно из основного потока, таким образом, в фоновом потоке. Таким образом, он не блокирует выполнение какого-либо кода в основном потоке.
Зная это, следующие строки будут выполняться сразу после друг друга:
new get_pendingreq().execute();
System.out.print("alalala" + globalVariables.pendingdate.size());
Ваш get_pendingreq
Класс не будет выполнять какую-либо реальную работу, пока не произойдет небольшая задержка, означающая, что после вызова первых строк в приведенном выше фрагменте ничего на самом деле не произошло. Вы только дали указание платформе запустить асинхронную задачу где-то в ближайшем будущем.
Теперь globalVariables.pendingdate
поле, к которому вы обращаетесь во второй строке, не будет иметь никаких значений, пока асинхронная задача не завершит свою работу. Это не происходит до onPostExecute()
выполнен. Другими словами: вы пытаетесь напечатать значения в неправильный момент времени.
Просто переместите эту печать в конец асинхронной задачи onPostExectute()
метод (но, очевидно, до return
- почему это вообще там?).
Я настоятельно рекомендую вам прочитать AsyncTask
документация по классам и статья о процессах и потоках.
Ясно, что имя действительно AsyncTask работает асинхронно... Позвольте мне объяснить, принимая во внимание ваш код:
new get_pendingreq().execute();
Эта строка создаст новый поток для выполнения, и он будет работать асинхронно, и поэтому следующая строка (ieSystem.out.print("alalala" + globalVariables.pendingdate.size());) будет выполнена сразу после этой строки, не ожидая асинхронности задача выполнить полностью.также поместите эту строку system.print в метод post execute...
Ты уверен, что globalVariables.pendingdate.add(e.getString("date"));
реально есть поле "данные"?