#java #android #android_asynctask
Всё что внизу описано, это то как я использовал интерфейс для получения результата из AsynckTack в главный поток, используя CallBack. Почему мне сказали, что плохо , что я передал ссылку на активити в AsyncTask? И как лучше надо было это исполнить? Вот в классе MainActivity вызываю такой метод и как видите передаю ссылку на активити в AsyncTack private void UploadData() { String url = "https://qwerty.ru" ; AsyncUploadingData asyncUploadingData = new AsyncUploadingData(this); asyncUploadingData.execute(url); } } В AsyncTack вложен интерфейс interface AsyncResult { void getResult(String answer); } Объявлен private AsyncResult mCallback; И в конструкторе принимаю ссылку на активити. И неявно привожу к интерфейсу(правильно так выразиться?) AsyncUploadingData(AsyncResult mCallback) { this.mCallback = mCallback; } И в опеределенный момент вызываю метод интерфейса, а интерфейс подключен в MainActivity mCallback.getResult(answer);
Ответы
Ответ 1
Почему мне сказали, что плохо , что я передал ссылку на активити в AsyncTask? Хранение ссылки на активити в AsyncTask чревато тем, что в случае уничтожения переданной активити в момент работы асинстаска: а) Произойдет утечка памяти, так как GC не сможет убрать из памяти активити, так как на нее будет хранится ссылка (в случае с strong reference); б) Вызов методов активити, в лучшем случае, ни к чему не приведет, а в худшем – будут возникать ошибки. Первая проблема решается хранением активити в виде weak reference, однако вторая проблема остается. И как лучше надо было это исполнить? Существует большое количество способов решения данной проблемы. Например, можно воспользоваться лоадерами или retain-фрагментами (лоадеры сохраняют состояние как раз с помощью retain-фрагментов). Можно использовать различные библиотеки, например Chronos. Если используете MVP, то можно воспользоваться библиотекой Moxy, которая, в частности, решает возникшую у Вас проблему.Ответ 2
Да особой разницы в целом нет, будь то интерфейс или прямая ссылка на Activity. Не советовали туда передавать Activity так как нарушает инкапсуляцию. Так-то, конечно же, можно передавать Activity, но хотя бы заворачивать её тогда уж в WeakReference. WeakReferencemWeakActivity; public AsyncUploadingData(Activity activity) { mWeakActivity = new WeakReference (activity); } Но, независимо от подхода, при вызове из onPostExecute нужно проверять ссылку на null, так как к моменту завершения AsyncTack Activity уже могла быть пересоздана.
Комментариев нет:
Отправить комментарий