如何编写可同时接收Activity和Fragment作为参数的函数?
问题原因解析
- 第一个类型不兼容报错:Fragment 与 Activity 没有继承关系,无法将 Fragment 实例传入 Activity 类型的入参
- 替换为 Context 后
is CargoFragment报错:Fragment 本身不继承 Context,Context 类型的变量永远不可能是 Fragment 实例,该判断逻辑本身无效,编译器直接拦截错误
解决方案
方案1(推荐):定义统一回调接口解耦
该方案避免硬编码类型判断,后续新增调用场景无需修改工具函数逻辑,耦合度最低。
- 首先定义通用回调接口
interface ProductListCallback { // 产品列表请求成功回调 fun success(productList: List<Product>) // 请求失败隐藏加载框回调 fun hideProgressDialog() }
- 让所有需要调用该函数的页面实现该接口:
让CargoActivity、CheckoutActivity、CargoFragment均实现ProductListCallback接口,原有success、hideProgressDialog方法的逻辑无需修改,仅需要加上接口实现声明即可。 - 修改工具函数入参为接口类型
fun getProductList(callback: ProductListCallback) { mFireStore.collection("abc") .get() .addOnSuccessListener { // 原有解析生成 productList 的逻辑保持不变 productList.add(product) // 直接调用回调即可,无需再判断类型 callback.success(productList) } .addOnFailureListener { e -> // 避免空指针,不要直接用 !! 取 message Log.d("CheckTag", e.message ?: "产品列表请求失败") callback.hideProgressDialog() } }
- 调用方式:Activity 和 Fragment 中均直接传入
this即可。
方案2(快速适配):修改入参为 Any 类型
如果不想调整现有结构,可以直接把入参改为 Any 兼容 Activity、Fragment 两种类型,原有逻辑改动最小:
fun getProductList(target: Any) { mFireStore.collection("abc") .get() .addOnSuccessListener { // 原有解析生成 productList 的逻辑保持不变 productList.add(product) when (target) { is CargoActivity -> target.success(productList) is CheckoutActivity -> target.success(productList) is CargoFragment -> target.success(productList) } } .addOnFailureListener { e -> Log.d("CheckTag", e.message ?: "产品列表请求失败") when (target) { is CargoActivity -> target.hideProgressDialog() is CheckoutActivity -> target.hideProgressDialog() // 若 CargoFragment 需要处理失败逻辑,可在此补充对应分支 } } }
注意事项
- 异步请求过程中如果对应 Activity/Fragment 已销毁,持有实例引用会造成内存泄漏,建议结合 Lifecycle 绑定请求生命周期,页面销毁时自动取消请求
- 不要直接用
!!强制取可空变量的值,避免空指针崩溃
内容的提问来源于stack exchange,提问作者Codist
相关产品推荐
相关产品推荐

