Урок 86. AsyncTask. Знакомство, несложный пример
Урок 86. AsyncTask. Знакомство, несложный пример
В этом уроке:
- создаем несложный пример с AsyncTask
Click here to read this article!
- создаем несложный пример с AsyncTask
Click here to read this article!
Последний раз редактировалось damager82 20 май 2017, 20:09, всего редактировалось 4 раза.
Re: Урок 86. AsyncTask. Знакомство, несложный пример
Что то не было проблем никогда с тасками, а сейчас всплыла проблема такого характера: делаю в AsyncTask'e sleep но экран блокируется (точнее он просто чёрный).
sleep происходит в другом потоке, но почему тогда чёрный экран? почему тогда активити ждёт завершения AsyncTaska а потом уже вываливает экран.
Код: Выделить всё
public class Example extends Activity {
private AuthorizationTask task;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_example);
init();
}
private void init() {
Log.i("MyTag", "name thread: " + Thread.currentThread().getName());
boolean isAuthorization = false;
task = new AuthorizationTask();
task.execute(5);
try {
isAuthorization = task.get();
} catch (InterruptedException e) {
Log.i("MyTag", "InterruptedException in Example");
e.printStackTrace();
} catch (ExecutionException e) {
Log.i("MyTag", "ExecutionException in Example");
e.printStackTrace();
}
if(isAuthorization) {
Log.i("MyTag", "authorization is true");
Intent intent = new Intent(this, ExampleTwo.class);
startActivity(intent);
}
else {
Log.i("MyTag", "authorization is false");
Intent intentLogin = new Intent(this, LoginActivity.class);
startActivity(intentLogin);
}
}
public class AuthorizationTask extends AsyncTask<Integer, Void, Boolean> {
protected void onPreExecute() {
super.onPreExecute();
}
protected void onProgressUpdate(Void... value) {
super.onProgressUpdate(value);
}
@Override
protected Boolean doInBackground(Integer... params) {
Log.i("MyTag", "name thread: " + Thread.currentThread().getName());
for(int i = 0; i < params[0]; i++) {
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException e) {
Log.i("MyTag", "InterruptedException in doInBackground");
e.printStackTrace();
}
}
return new Boolean(false);
}
protected void onPostExecute(Boolean result) {
super.onPostExecute(result);
}
}
}
R.id.team
Политика на форуме запрещена
Политика на форуме запрещена
Re: Урок 86. AsyncTask. Знакомство, несложный пример
а если убрать isAuthorization = task.get(); то sleep'a вообще не происходит, то есть сразу грузится экран.
R.id.team
Политика на форуме запрещена
Политика на форуме запрещена
Re: Урок 86. AsyncTask. Знакомство, несложный пример
попробуй init () перенести в onStart() или в onResume().
У меня тоже бывало возникали глюки с onCreate()
У меня тоже бывало возникали глюки с onCreate()
Re: Урок 86. AsyncTask. Знакомство, несложный пример
не помогло.
R.id.team
Политика на форуме запрещена
Политика на форуме запрещена
Re: Урок 86. AsyncTask. Знакомство, несложный пример
Ну все правильно, task.get() останавливает UI поток и ждет выполнения задачи.
Эту задачу нужно подругому решать, я бы использовал onPreExecute и onPostExecute они выполняются в UI потоке
Эту задачу нужно подругому решать, я бы использовал onPreExecute и onPostExecute они выполняются в UI потоке
Re: Урок 86. AsyncTask. Знакомство, несложный пример
это понятно, но задержку нужно выполнить допустим на 5 секунд, и это нужно делать в другом потоке что бы не блакировать основной, к тому же в основном будет progressbar работать.
R.id.team
Политика на форуме запрещена
Политика на форуме запрещена
Re: Урок 86. AsyncTask. Знакомство, несложный пример
Тогда никаких тасков не нужно - вот например, у меня запускается из onCreate():
Код: Выделить всё
private void newGame() {
showDialog(PROGRESS_DIALOG, null);
Thread t = new Thread() {
@Override
public void run() {
model.newGame();
dismissDialog(PROGRESS_DIALOG);
}
};
t.start();
}
Re: Урок 86. AsyncTask. Знакомство, несложный пример
загружаю со страницы новости, далее все что загрузил вывожу на listview, нужно теперь реализовать диалог чтоб юзер знал что идет загрузка, но у меня что то не получается при созданий адаптера для listview выдает ошибку примерная структура моего кода, помогите плз.
Код: Выделить всё
private ArrayList<String> listTitle = new ArrayList<String>();
private ArrayList<String> listLink = new ArrayList<String>();
private String[] arrayTitle = new String[]{"..."};
private String[] arrayLink = new String[]{"..."};
public void onCreate...{
pd = ProgressDialog.show(this, "Working...", "request to server", true, false);
new ParseSite().execute("http://www...");
}
private class ParseSite extends AsyncTask<String, Void, String[]>{
@Override
protected String[] doInBackground(String... params) {
try {
String html = params[0];
Document doc = Jsoup.connect(html).get();
listTitle.clear();
listLink.clear();
for (Element link : doc.select("div")){
// Получаю массив из ссылок и содержимых href
}
arrayTitle = ConvertToStringArray(listTitle);
arrayLink = ConvertToStringArray(listLink);
}
catch (IOException e) {}
return null;
}
protected void onPostExecute(String[] arrayTitle) {
pd.dismiss();
lvNews = (ListView)findViewById(R.id.lvNews);
ArrayAdapter<String> adapter = new ArrayAdapter<String>(this,
R.layout.list_news, arrayTitle);
lvNews.setAdapter(adapter);
}
}
Re: Урок 86. AsyncTask. Знакомство, несложный пример
прогресс бар бесконечно крутиться (( убрал вот эти строчки
Код: Выделить всё
lvNews = (ListView)findViewById(R.id.lvNews);
ArrayAdapter<String> adapter = new ArrayAdapter<String>(this,
R.layout.list_news, arrayTitle);
lvNews.setAdapter(adapter);
Re: Урок 86. AsyncTask. Знакомство, несложный пример
3Gern, выбросьте массивы - они не нужны. Оставьте только списки. Адаптер принимает список в качестве аргумента.
В doInBackground() после нахождения ссылки вызывайте publishProgress();
В onProgressUpdate() обновляйте списки - и информруйте ListView что список изменился с помощью notifyDataSetChanged().
Пользователь сможет кликать на уже загруженные ссылки даже пока идёт загрузка.
Но прогрессбар крутится, означая что загрузка продолжается.
В onPostExecute() убираете прогрессбар.
В doInBackground() после нахождения ссылки вызывайте publishProgress();
В onProgressUpdate() обновляйте списки - и информруйте ListView что список изменился с помощью notifyDataSetChanged().
Пользователь сможет кликать на уже загруженные ссылки даже пока идёт загрузка.
Но прогрессбар крутится, означая что загрузка продолжается.
В onPostExecute() убираете прогрессбар.
Re: Урок 86. AsyncTask. Знакомство, несложный пример
Столкнулся со следующей ситуацией:
- при завершении задачи с использованием AsyncTask поток почему-то разрушается и создается новый при выполнении новой задачи;
- при работе с потоками "по-старинке" (пусть и сложновато, да еще и сохраняются корявости при повороте экрана) поток создается и разрушается как ему положено
об этих выводах ярко повествует мониторинг потоков
Вопрос таков, что выгоднее и правильнее???
- при завершении задачи с использованием AsyncTask поток почему-то разрушается и создается новый при выполнении новой задачи;
- при работе с потоками "по-старинке" (пусть и сложновато, да еще и сохраняются корявости при повороте экрана) поток создается и разрушается как ему положено
об этих выводах ярко повествует мониторинг потоков
Вопрос таков, что выгоднее и правильнее???
Re: Урок 86. AsyncTask. Знакомство, несложный пример
так что никто не сталкивался с такой ситуацией?
Re: Урок 86. AsyncTask. Знакомство, несложный пример
правильно поток и будет пересоздаваться так как при повороте экрана активити "пересеоздаётся"при работе с потоками "по-старинке" (пусть и сложновато, да еще и сохраняются корявости при повороте экрана) поток создается и разрушается как ему положено
а вот здесь не понятно что имеете в виду, скорее всего не правильно построили поток- при завершении задачи с использованием AsyncTask поток почему-то разрушается и создается новый при выполнении новой задачи;
R.id.team
Политика на форуме запрещена
Политика на форуме запрещена
Re: Урок 86. AsyncTask. Знакомство, несложный пример
А это уж как запрограммируете. Ни AsyncTask, ни Thread не уничтожаются при повороте экрана. Но если не принять сооветствующих мер - результат будет выводиться в старые View (которые как раз пересоздаются при повороте).
Как это делать, расказано в следующих уроках.
Как это делать, расказано в следующих уроках.
Re: Урок 86. AsyncTask. Знакомство, несложный пример
Да нет вопрос не про уничтожение потока при повороте экрана. Интересует то, что СПЕЦИАЛЬНО СДЕЛАННЫЙ ДЛЯ УДОБСТВО МЕХАНИЗМ AsyncTask оставляет исполняемый поток в памяти, после исполнения и закрытия такого, и при вызове снова действия, разделенного на потоки создает новый и т.д.
Thread - после разрушения пропадает.
Все ето можно наблюдать в Debug
Thread - после разрушения пропадает.
Все ето можно наблюдать в Debug
Re: Урок 86. AsyncTask. Знакомство, несложный пример
А почему он должен убиваться при повороте экрана? Он продолжает работать, работать и работать - пока Вы его сами не остановите - впрочем, так же как и Thread - ведь при этом его не обазательно останавливать, достаточно его перенастроить.
А если при повороте экрана Вы не разовравжись запускаете второй экземпляр AsyncTask - тоже Ваши проблемы. Вдруг и в самом деле нужен второй AsyncTask ?
А если при повороте экрана Вы не разовравжись запускаете второй экземпляр AsyncTask - тоже Ваши проблемы. Вдруг и в самом деле нужен второй AsyncTask ?
Re: Урок 86. AsyncTask. Знакомство, несложный пример
В Андроид вообще никакие объекты не уничтожаются немедленно после использования, за это отвечает сборщик мусора и мы не можем никак повлиять на его работу. Можно, конечно, вызвать System.gc() но даже в этом случае разработчики Андроид не гарантируют, что он будет немедленно вызван и почистит всю память от всех неиспользуемых объектов, этой командой мы лишь уведомляем систему, что наступил удобный момент для уборки мусора.Umix писал(а):Да нет вопрос не про уничтожение потока при повороте экрана. Интересует то, что СПЕЦИАЛЬНО СДЕЛАННЫЙ ДЛЯ УДОБСТВО МЕХАНИЗМ AsyncTask оставляет исполняемый поток в памяти, после исполнения и закрытия такого, и при вызове снова действия, разделенного на потоки создает новый и т.д.
Thread - после разрушения пропадает.
Все ето можно наблюдать в Debug
Вообще не вижу причин для беспокойства, ну и пусть они висят DDMS, мне так они не мешают.
Что касается AsyncTasks, то его изначально планировалось использовать для разовых, коротких задач:
AsyncTasks в идеале, должны быть использованы для коротких операций (несколько секунд, не больше.) Если вам нужно сохранять потоки в течение длительного периода времени, то настоятельно рекомендуется использовать различные API, предоставляемые пакетом java.util.concurrent , таких как Executor, ThreadPoolExecutor и FutureTask
Re: Урок 86. AsyncTask. Знакомство, несложный пример
У меня такая проблема: пытаюсь заранее создать содержимое activity с множеством View, чтобы при его вызове оно показывалось мгновенно(иначе примерно 2 секунды загружается). Как я понял, это должно получиться реализовать с помощью создания в AsyncTask, вызываемом в MainActivity, нового View, содержащего в себе все это множество вьюшек, и потом при вызове этого тяжёлого activity просто добавить в него уже созданный в предыдущем activity View.
Но столкнулся с такой проблемой, что в doInBackground не получается создать новый элемент View, так как непонятно что писать в параметры при его создании:
Методы getContext() и getBaseContext() не работают... Что делать в такой ситуации?
P.S.: Я недавно начал программировать под Андройд, и, возможно, это не самый лучший способ реализовать предварительное создание тяжёлого Acivity...
Но столкнулся с такой проблемой, что в doInBackground не получается создать новый элемент View, так как непонятно что писать в параметры при его создании:
Код: Выделить всё
LinearLayout linLayout = new LinearLayout(context);
P.S.: Я недавно начал программировать под Андройд, и, возможно, это не самый лучший способ реализовать предварительное создание тяжёлого Acivity...
Re: Урок 86. AsyncTask. Знакомство, несложный пример
Обычно, если в классе нужен контекст активити или приложения, то его туда передают в конструкторе и вызывают его методы через него:
public class MyAsyncTask extends AsyncTask {
private Context mContext;
public MyAsyncTask (Context context){
this.mContext=context;
}
...
И вызывают методы контекста или передают его где нужно в конструкторы View
LinearLayout linLayout = new LinearLayout(mContext);
А в Activity передают ссылку на свой контекст (т.е. на себя) при создании объекта
MyAsyncTask myTask = new MyAsyncTask(this);
public class MyAsyncTask extends AsyncTask {
private Context mContext;
public MyAsyncTask (Context context){
this.mContext=context;
}
...
И вызывают методы контекста или передают его где нужно в конструкторы View
LinearLayout linLayout = new LinearLayout(mContext);
А в Activity передают ссылку на свой контекст (т.е. на себя) при создании объекта
MyAsyncTask myTask = new MyAsyncTask(this);