RxSwift Observeable 不会在数据更改时更新 tableview

Posted

技术标签:

【中文标题】RxSwift Observeable 不会在数据更改时更新 tableview【英文标题】:RxSwift Observeable doesn't update tableview on data change 【发布时间】:2017-05-11 12:05:17 【问题描述】:

我设置了 tableview 并希望在数据更改后立即更新 UI。我使用调度程序模拟数据更改。但问题是,该表不会更新。有人能解释一下如何使用 RxSwift 设置一个 tableview 来更新它的数据变化的单元格吗?

  @IBOutlet private var tableView: UITableView!
  let europeanChocolates: Variable<[Chocolate]> = Variable([])
  let disposeBag = DisposeBag()

  //MARK: View Lifecycle

  override func viewDidLoad() 
    super.viewDidLoad()
    title = "Chocolate!!!"
    setupCellConfiguration()
    europeanChocolates.value = Chocolate.ofEurope
    DispatchQueue.main.asyncAfter(deadline: .now() + 3) 
      var choclate = self.europeanChocolates.value[0]
      choclate.countryName = "Denmark"
    

  

  //MARK: Rx Setup

  private func setupCellConfiguration() 
    europeanChocolates.asObservable().bindTo(tableView.rx.items(cellIdentifier: ChocolateCell.Identifier, cellType: ChocolateCell.self)) 
      row, chocolate, cell in
      cell.configureWithChocolate(chocolate: chocolate)
    
    .addDisposableTo(disposeBag)
  

【问题讨论】:

【参考方案1】:

您没有提供 Chocolate 的实现,但我认为它是结构,在这种情况下您不会更改任何内容,因为在

    DispatchQueue.main.asyncAfter(deadline: .now() + 3) 
  var choclate = self.europeanChocolates.value[0]
  choclate.countryName = "Denmark"

您的来自 EuropeanChocolates 的巧克力被复制到新的 var choclate,但您从未保存它。你可以很容易地检查它,如果你试试这个

  override func viewDidLoad() 
    super.viewDidLoad()
    title = "Chocolate!!!"
    setupCellConfiguration()
    europeanChocolates.value = Chocolate.ofEurope
    europeanChocolates.asObservable().subscribe(onNext:  choco in
        print("choco changed \(choco)")
    )
    DispatchQueue.main.asyncAfter(deadline: .now() + 3) 
      var choclate = self.europeanChocolates.value[0]
      choclate.countryName = "Denmark"
    

  

我认为它不会打印“choco changed”。如果我是对的,这应该可以帮助你:

  override func viewDidLoad() 
    super.viewDidLoad()
    title = "Chocolate!!!"
    setupCellConfiguration()
    europeanChocolates.value = Chocolate.ofEurope
    DispatchQueue.main.asyncAfter(deadline: .now() + 3) 
      var choclate = self.europeanChocolates.value[0]
      choclate.countryName = "Denmark"
      self.europeanChocolates.value[0] = choclate
    

  

如果没有帮助,请提供 Chocolate 和 ChocolateCell 的实现

【讨论】:

【参考方案2】:

在 swift5 中,该变量已被弃用。所以最好你应该使用行为主题。要在其中传递值,请使用 OnNext 函数。如果它与表格视图绑定,那么它将自动刷新新数据。

【讨论】:

【参考方案3】:

您必须在数据更改后重新加载 tableView。要重新加载 tableView,请调用:

this.tableView.reloadData()

【讨论】:

这有点跑题了,因为问题是关于 RxCocoa 和 observables,而不是如何重新加载数据。

以上是关于RxSwift Observeable 不会在数据更改时更新 tableview的主要内容,如果未能解决你的问题,请参考以下文章

RxSwift:如何使用 shareReplay 懒惰地获取订阅

函数响应式编程和 RxSwift+MVVM

带有 UiTextField 的 RxSwift

RxSwift 分页

RxSwift: 链 Completable 到 Observable

RXSwift 简单的异步示例?