【问题标题】:UITableView numberOfSectionsInTableView and numberOfRowsInSection called thrice on initial loadUITableView numberOfSectionsInTableView 和 numberOfRowsInSection 在初始加载时调用了三次
【发布时间】:2015-05-21 10:41:46
【问题描述】:

我正在制作一个没有任何数据源的REALLY BASIC UITableView 项目。我只是在第一个也是唯一一个单元格上显示“1”。

我在numberOfSectionsInTableViewnumberOfRowsInSection 中都是returning 1。我还在这两种方法上都做了一个NSLog,只是简单地说明了各自方法的名称。

在初始加载时,我得到了这个:

SomeShit[27511:936083] number of sections
SomeShit[27511:936083] number of rows in section
SomeShit[27511:936083] number of sections
SomeShit[27511:936083] number of rows in section
SomeShit[27511:936083] number of sections
SomeShit[27511:936083] number of rows in section

为什么这些方法调用三次?如果我错了,请纠正我,但这真的很奇怪。我认为他们应该只调用一次,因为两者的项目数都只有 1。

编辑:

我在viewDidLoad做什么,

self.tableView = [[UITableView alloc] initWithFrame:CGRectMake(0, 0, self.view.frame.size.width, self.view.frame.size.height) style:UITableViewStylePlain];
[self.view addSubview:self.tableView];

self.tableView.dataSource = self;
self.tableView.delegate = self;

[self.tableView registerClass:[UITableViewCell class] forCellReuseIdentifier:cellIdentifier];

【问题讨论】:

标签: ios uitableview ios8


【解决方案1】:

委托和数据源为表视图实现提供服务,方法可能被多次调用。您不必关心表格视图的实现细节,只需确保您的答案是一致的(即您可以在任何时间点正确回答,并且不调用reloadData,答案不会改变)。

【讨论】:

  • 好吧,我是在另一个我还没有提出的问题之后才提出这个问题的。它关于加载节标题并调整其大小。 Stuff 多次调用,我将其归结为只有一个 tableview 和 1 行。所以你确定它不会干扰将来使用这些方法发生的代码?
  • 这些方法通常很短,因此根据表格视图内部缓存结果的方式,它可能会多次询问您的数据源并委托这些问题。另一方面,不应过度调用cellForRowAtIndexPath,因为这是一种代价高昂的方法。
  • 是的,不,我不会再打电话给cellForRowAtIndexPath
【解决方案2】:

文档中没有任何地方说这些方法在重新加载数据周期中只调用一次。

您假设它们只需要调用一次,但正如您所展示的,这是一个错误的假设。

查看UITableViewUITableViewDataSource 的文档后,唯一的承诺就是这个。

-[UITableView numberOfSections]:

讨论

UITableView 从其数据源中获取该方法返回的值并缓存。

这意味着您无法知道对-[UITableView numberOfSections] 的调用将如何与对-[UITableViewDataSource numberOfSectionsInTableView:] 的调用对应。

更糟糕的是,调用这些方法的次数可以(并且已经)在不同的 iOS 版本之间发生变化。


简而言之,将这些方法设为idempotentperformant,忘记UITableView 的实现细节。

【讨论】:

  • “幂等”是一个我不知道的有趣术语,它更好地描述了我所说的“一致”。
【解决方案3】:

您可以尝试找出导致这些重新加载的原因。转到断点部分 (1),按下“加号”按钮 (2)。然后在“符号”字段中使用 -[UITableView reloadData] 添加符号断点。

然后运行您的应用程序并查看方法调用的堆栈跟踪。您将能够找出这种行为的原因。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2013-01-07
    • 1970-01-01
    • 2013-09-04
    • 1970-01-01
    • 1970-01-01
    • 2014-11-02
    • 2012-04-26
    相关资源
    最近更新 更多