You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Fragment中从ViewModel获取数据数组并绑定RecyclerView

解决Fragment关联ViewModel并通过API数据更新RecyclerView的方案

1. 确保ViewModel正确持有LiveData

ViewModel里要把API请求结果用MutableLiveData存储,让Fragment能观察数据变化:

class YourViewModel : ViewModel() {
    // 定义私有MutableLiveData存储数据,对外暴露不可变的LiveData
    private val _dataList = MutableLiveData<List<YourDataModel>>()
    val dataList: LiveData<List<YourDataModel>> get() = _dataList

    fun fetchDataFromApi() {
        // 以Retrofit调用API为例
        ApiService.instance.getData().enqueue(object : Callback<List<YourDataModel>> {
            override fun onResponse(call: Call<List<YourDataModel>>, response: Response<List<YourDataModel>>) {
                response.body()?.let {
                    // 子线程更新LiveData用postValue
                    _dataList.postValue(it)
                }
            }

            override fun onFailure(call: Call<List<YourDataModel>>, t: Throwable) {
                // 请求失败时设置空列表或错误状态
                _dataList.postValue(emptyList())
            }
        })
    }
}

2. 在Fragment中关联ViewModel并设置观察者

通过ViewModelProvider绑定ViewModel生命周期,观察LiveData更新RecyclerView:

class YourFragment : Fragment() {
    private lateinit var viewModel: YourViewModel
    private lateinit var recyclerView: RecyclerView
    private lateinit var adapter: YourAdapter

    override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
        val view = inflater.inflate(R.layout.your_fragment_layout, container, false)
        recyclerView = view.findViewById(R.id.recyclerView)
        // 初始化Adapter,先传入空列表
        adapter = YourAdapter(emptyList())
        recyclerView.adapter = adapter
        recyclerView.layoutManager = LinearLayoutManager(context)
        return view
    }

    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)
        // 获取与Fragment生命周期绑定的ViewModel实例
        viewModel = ViewModelProvider(this)[YourViewModel::class.java]
        
        // 触发API请求
        viewModel.fetchDataFromApi()
        
        // 观察LiveData变化,用viewLifecycleOwner避免内存泄漏
        viewModel.dataList.observe(viewLifecycleOwner) { newData ->
            // 通知Adapter更新数据
            adapter.updateData(newData)
        }
    }
}

3. 给Adapter添加数据更新方法

让Adapter支持动态更新,无需重新创建实例:

class YourAdapter(private var dataList: List<YourDataModel>) : RecyclerView.Adapter<YourAdapter.ViewHolder>() {

    // 新增数据更新方法
    fun updateData(newData: List<YourDataModel>) {
        dataList = newData
        // 简单刷新可用notifyDataSetChanged,追求性能可替换为DiffUtil
        notifyDataSetChanged()
    }

    // ViewHolder及其他核心方法保持原有逻辑
    inner class ViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
        fun bind(data: YourDataModel) {
            // 绑定数据到UI组件
        }
    }

    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
        val view = LayoutInflater.from(parent.context).inflate(R.layout.item_layout, parent, false)
        return ViewHolder(view)
    }

    override fun onBindViewHolder(holder: ViewHolder, position: Int) {
        holder.bind(dataList[position])
    }

    override fun getItemCount() = dataList.size
}

关键注意事项

  • 必须使用viewLifecycleOwner作为LiveData的观察者,确保Fragment销毁时自动移除监听,防止内存泄漏。
  • ViewModel中更新LiveData时,子线程用postValue(),主线程用setValue(),不能直接给_dataList赋值。
  • API请求逻辑完全放在ViewModel中,Fragment只负责UI渲染和事件触发,遵循MVVM职责分离原则。

内容的提问来源于stack exchange,提问作者Zares

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.06 08:08:26