#android #kotlin #arraylist #android-viewpager2
#Android #котлин #список объектов #android-страница просмотра 2
Вопрос:
Я создал переменную private var deals=ArrayListlt;Dealsgt;()
в a fragment
и установил прослушиватель щелчков onCerateView()
, как показано ниже.
binding.tvAllDeals.setOnClickListener { viewAllDeals() }
Так что это вызовет следующий метод
private fun viewAllDeals(){ val intent = Intent(context,ViewAllDealsActivity::class.java) intent.putExtra("details",deals) Log.d("Tag2", "Size is ${deals.size}") startActivity(intent) }
У меня есть следующая функция для получения данных из firestore
, а затем я сохраняю результат в переменной «сделки». Однако всякий раз, когда я нажимаю «tvAllDeals», он показывает много изображений, когда я проверяю размер «сделок» с помощью Log.d
«Tag1», всегда отображается правильный размер, равный 3, тогда как «Tag2» показывает некоторые случайные числа, такие как 6, 9, 24. Я пытаюсь выяснить, почему это происходит, но у меня не было ни малейшего представления. Переменная «deals» не используется нигде, кроме объявления и инициализации, для присвоения значения и передачи его в » viewAllDeals ()».
private fun getDeals() { FirestoreClass().getDeals( onSuccess = { list -gt; Result.success(list) successDeals(list) ///// THIS FUNCTION WILL SHOW THE IMAGES IN A VIEWPAGER deals.clear() deals=list Log.d("Tag1", "Size is ${deals.size}") }, onFailure = { } ) }
Редактировать:
ПРИМЕЧАНИЕ: «Tag3» также показывает правильный размер массива, как «Tag1». Однако,
private fun successDeals(list: ArrayListlt;Dealsgt;) { Log.d("Tag3", "Size is ${deals.size}") if (list.size gt; 0) { binding.vpDeals.visibility = View.VISIBLE val adapter = DealsAdapter(binding.vpDeals,requireContext(), list) binding.vpDeals.adapter = adapter binding.vpDeals.orientation = ViewPager2.ORIENTATION_HORIZONTAL sliderHandle= Handler() sliderRun= Runnable { binding.vpDeals.currentItem=binding.vpDeals.currentItem 1 } binding.vpDeals.registerOnPageChangeCallback( object :ViewPager2.OnPageChangeCallback(){ override fun onPageSelected(position: Int) { super.onPageSelected(position) sliderHandle.removeCallbacks(sliderRun) sliderHandle.postDelayed(sliderRun,4000) } } ) } else { binding.vpDeals.visibility = View.GONE } }
Комментарии:
1.Моя рекомендация-никогда не объединяться
var
с ArrayList или MutableList. Изменение его двумя различными способами усложняет работу с ним и затрудняет предотвращение ошибок. И если вы можете выбирать между аvar
List
и аval
MutableList
, тоvar
List
это менее подвержено ошибкам. Это делает невозможным случайное изменение экземпляра списка, от которого зависит какой-либо другой класс, например ваш видоискатель, или забывание очистить список перед добавлением элементов и т. Д. (Возможно, причиной вашей проблемы может быть то, что вы где-то забыли очистить список.)2. Можете ли вы показать
successDeals
функцию?3. Я не вижу конкретно, что вызывает вашу проблему, но я вижу множество запахов кода. 1)
Result.success(list)
создает объект результата и ничего с ним не делает, поэтому эту строку следует удалить. 2)deals
является одновременно avar
и anArrayList
, поэтому он может изменяться двумя различными способами. 3) Вы очищаете список, на который ссылается,deals
перед его переназначением. Поскольку вы передаете изменяемые списки, это может иметь неожиданные побочные эффекты, потому что кто знает, какие другие классы полагаются на этот список. Какой смысл его очищать? 4)successDeals
требует конкретно списка типов ArrayList…4. …без всякой причины, потому что он не мутирует и не делает ничего, требующего определенного поведения списка под капотом. 5) Создание обработчика внутри
successDeals
, поэтому каждый раз, когда он вызывается, старый обработчик теряется. Это очень подвержено ошибкам. Вы можете подумать, что ваш прослушиватель щелчков останавливает старую выполняемую программу, когда это не так, потому что он смотрит на другой обработчик, чем тот, который использовался ранее.5. 6) Создание адаптера inisde
successDeals
. Адаптеры следует создавать и назначать только один раз (обычно вActivity.onCreate
илиFragment.onViewCreated
), но это приведет к повторному созданию адаптера при каждомsuccessDeals
вызове, что приведет к потере всех ранее созданных представлений и исполняемых файлов.