Kotlin中IntArray和StringArray的共同父类及FragmentAdapter适配问询
嘿,我来帮你拆解这两个问题~
首先明确:Kotlin中的IntArray是对应Java基本类型int[]的数组类,而你说的StringArray其实是Array<String>(对应Java的String[])。它们的共同父类是Any(Kotlin中所有类的根类),但更实用的是它们都实现了一些共同的接口:
Sized:只有一个size属性,用来获取数组长度Iterable<*>:支持遍历操作(IntArray实现的是Iterable<Int>,Array<String>实现的是Iterable<String>)
所以如果需要一个能同时接收这两种数组的类型,Sized或者Iterable<*>都是不错的选择,具体看你需要用到哪些操作。
先直接说:你现在的代码语法上就不可行,因为Array是泛型类,必须指定类型参数(比如Array<*>),而且即使改成Array<*>,也无法接收IntArray——因为IntArray和Array<T>是完全独立的类,IntArray并不是Array<Int>(后者对应Java的Integer[],是包装类型数组)。
那怎么实现一个能接收各类数组(包括基本类型数组和引用类型数组)的Adapter呢?给你几个解决方案:
方案1:使用Sized接口作为参数类型
既然你只需要用到size属性来返回页面数量,直接用Sized接口就足够了,它是Kotlin标准库中专门定义的、表示“有size属性”的接口,IntArray和Array<String>都实现了这个接口:
class MyPagerAdapter(val fragmentManager: FragmentManager, val collection: Sized) : FragmentStatePagerAdapter(fragmentManager) { override fun getCount(): Int { Log.i("viewpager", "count" + fragmentManager.fragments.size.toString()) return collection.size } }
这样调用的时候,不管是传入IntArray还是Array<String>都完全没问题:
// 传入IntArray val intArray = intArrayOf(1,2,3) val adapter1 = MyPagerAdapter(fragmentManager, intArray) // 传入Array<String> val stringArray = arrayOf("a","b","c") val adapter2 = MyPagerAdapter(fragmentManager, stringArray)
方案2:使用泛型+约束(如果需要更多操作)
如果你后续需要遍历数组元素来创建Fragment,那可以用泛型加上Iterable约束,这样既能获取size,又能遍历元素:
class MyPagerAdapter<T : Iterable<*>>(val fragmentManager: FragmentManager, val collection: T) : FragmentStatePagerAdapter(fragmentManager) { override fun getCount(): Int { Log.i("viewpager", "count" + fragmentManager.fragments.size.toString()) // 因为Iterable没有直接的size属性,所以可以转成List或者用count() return collection.count() } // 比如后续要实现getItem,可以遍历collection来创建Fragment override fun getItem(position: Int): Fragment { val item = collection.elementAt(position) // 根据item创建对应的Fragment,这里需要你自己实现逻辑 return MyFragment.newInstance(item.toString()) } }
方案3:统一转成List(最灵活)
如果不想纠结数组类型的差异,最简单的方式是把所有数组都转成List<*>,List是Kotlin集合框架的一部分,操作更统一:
class MyPagerAdapter(val fragmentManager: FragmentManager, val collection: List<*>) : FragmentStatePagerAdapter(fragmentManager) { override fun getCount(): Int { Log.i("viewpager", "count" + fragmentManager.fragments.size.toString()) return collection.size } }
调用的时候只需要把数组转成List:
val adapter1 = MyPagerAdapter(fragmentManager, intArray.toList()) val adapter2 = MyPagerAdapter(fragmentManager, stringArray.toList())
最后提个小建议:FragmentStatePagerAdapter在AndroidX中已经被标记为过时了,推荐使用ViewPager2配合FragmentStateAdapter,如果你是新项目的话,建议迁移到ViewPager2哦~
内容的提问来源于stack exchange,提问作者DJAMEL DAHMANE

