Асинхронная задача в обработчике? Выполнение нескольких асинхронных задач в строке

у меня следующая проблема в андроиде:

Мне нужно обработать несколько асинхронных задач в строке (e.g. Async-Task 1 -> Async-Task 2 -> Asyc-Task 3). Все асинхронные задачи отвечают обработчиком (sendMessage(xy)).

Итак, мои обработчики должны запустить следующую асинхронную задачу. Это лучшая практика? Должен ли я предпочесть другой путь?

Резюме: я ищу способ последовательной обработки многих асинхронных задач...

Я не могу использовать функцию get() для asyncThread, потому что они возвращают свои ответы только в обработчиках.

Извините за мой плохой английский..


person Frame91    schedule 25.03.2013    source источник


Ответы (4)


Забавно, как оба других ответа пропустили тот факт, что вы хотите сделать это последовательно... :)

Лично я ненавижу AsyncTask, я бы предпочел реализовать это в своем собственном потоке, но это я.

Вы хотите, чтобы действие A (и после завершения) вызывало действие B (и так далее)... что означает, что вам действительно нужен один поток для выполнения последовательности действий BL.

Это может быть легко достигнуто с помощью объекта с двумя обработчиками, одним из которых является Handler вашего нового ThreadHandler для BL, а другим, вероятно, является обработчик потока пользовательского интерфейса для обновлений пользовательского интерфейса, как только задача завершается, он отправляет сообщение обработчику BL для запуска следующей задачи.

Это инкапсулирует процесс в целом, и ошибки можно будет легко отслеживать. Я сделал это моделирование дважды для потоков входа в систему с несколькими серверами и кодами проверки SMS и некоторыми другими вещами.

Он также будет охватывать сценарий, в котором результат успешного или неудачного выполнения задачи потребует вызова разных задач.

person TacB0sS    schedule 25.03.2013
comment
не могли бы вы опубликовать код для этой реализации, о которой вы говорите? и +1 за то, что действительно заметил, что парень спрашивает даже в своем заголовке. - person Emil Adz; 26.03.2013
comment
как насчет robospice?. использование asynctask по-прежнему рекомендуется для загрузки элементов списка в фоновом режиме"> stackoverflow.com/questions/15463146/ - person Raghunandan; 26.03.2013
comment
Я не знаком с robospice, никогда не нуждался ни в чем для управления асинхронными задачами, так как я очень быстро понял, что они содержат утечки памяти, если их не обрабатывать должным образом, и в большинстве случаев люди этого не делают, поэтому у меня всегда было чистое решение Java для всех этого. - person TacB0sS; 26.03.2013
comment
Что касается примера, это потребует существенной реализации, чтобы он действительно работал, я бы не хотел публиковать код песадо, который не работает должным образом, мы говорим о многопоточности. и, к сожалению, я очень занят... :( - person TacB0sS; 26.03.2013
comment
Спасибо за ответ! Можете ли вы объяснить в нескольких предложениях, что вы имеете в виду под собственным обработчиком потоков (что означает BL?)? Это было бы прекрасно! - person Frame91; 26.03.2013
comment
создайте новый Thread Handler() и вызовите его метод getHandler() (чтобы получить экземпляр обработчика нового потока, чтобы вы могли работать с ним). BL означает BusinessLogic, все, что вы хотите выполнять в фоновом режиме и незаметно, например. получить что-то с сервера, вычислить что-то огромное, дождаться прихода смс. - person TacB0sS; 26.03.2013
comment
Из того, что я искал в сети, robopsice избегает утечек памяти. может обрабатывать несколько запросов. уведомляет в потоке пользовательского интерфейса. Стоит взглянуть на это. - person Raghunandan; 26.03.2013

При первом появлении AsyncTasks выполнялись последовательно в одном фоновом потоке. Начиная с DONUT, это было изменено на пул потоков, позволяющий нескольким задачам работать параллельно. Начиная с HONEYCOMB, задачи выполняются в одном потоке, чтобы избежать распространенных ошибок приложений, вызванных параллельным выполнением.

Если вам действительно нужно параллельное выполнение, вы можете вызвать executeOnExecutor(java.util.concurrent.Executor, Object[]) с помощью THREAD_POOL_EXECUTOR. (Прямо из документа)

AsyncTask управляет пулом потоков, созданным с помощью ThreadPoolExecutor. Он будет иметь от 5 до 128 потоков. Если имеется более 5 потоков, эти дополнительные потоки останутся не более чем на 10 секунд, прежде чем будут удалены. (примечание: эти цифры относятся к видимому в настоящее время открытому исходному коду и зависят от версии Android). (ответ Commonware на аналогичный вопрос)

http://developer.android.com/reference/android/os/AsyncTask.html .

http://developer.android.com/reference/java/util/concurrent/Executor.html. Рассмотрите возможность использования executor.

Вы также можете рассмотреть возможность использования RoboSpice. https://github.com/octo-online/robospice Вы также можете сделать несколько spicerequest.

person Raghunandan    schedule 25.03.2013

Я рекомендую использовать комбинацию Otto & Tape (от Square).

Вы можете посмотреть пример, который загружает изображения на сервер с помощью очереди.

https://github.com/square/tape/tree/master/tape-sample/src/main/java/com/squareup/tape/sample

person dannyroa    schedule 25.03.2013

Если вам нужно, чтобы все эти задачи выполнялись одновременно, у вас действительно нет другого выбора, кроме запуска нескольких асинхронных задач. Однако, если вам просто нужно, чтобы все эти задачи выполнялись в фоновом режиме, вы, вероятно, можете просто запустить одну асинхронную задачу и задать ей параметры для выполнения других задач.

Я бы рекомендовал использовать Loaders вместо AsyncTasks. Loaders запускаются асинхронно и, на мой взгляд, ими проще управлять в коде. С загрузчиками, когда загрузчик завершает выполнение, вызывается метод onLoaderFinished, ваш Activity может реализовать обратные вызовы загрузчика, а onCreateLoader может обрабатывать несколько загрузчиков, поэтому все это намного проще, чем использование AsyncTask. Вот руководство по загрузчикам.

person Ali    schedule 25.03.2013