NSFetchRequest和predicateWithBlock [英] NSFetchRequest and predicateWithBlock

查看:327
本文介绍了NSFetchRequest和predicateWithBlock的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在玩一个使用Core Data和NSManagedObjects来填充UITableView的应用程序。在我的应用程序中只有一个类,名为 Event 。我在事件上创建了以下自定义实例方法:

I am playing with an app that uses Core Data and NSManagedObjects to populate a UITableView. There is only one class in my application, called Event. I have created the following custom instance method on Event:

- (BOOL)isExpired {
    return ([[self.endOn dateAtEndOfDay] timeIntervalSinceNow] < 0);
}

我想限制 UITableView 显示事件对象只有过期的事件 - 即 isExpired 返回 YES 。我试图这样做通过添加 NSPredicate NSFetchRequest

I would like to limit the UITableView that displays Event objects to only the Events that are expired - that is, where isExpired returns YES. I have tried to do this by adding an NSPredicate to the NSFetchRequest:

NSPredicate *predicate = [NSPredicate predicateWithBlock:^BOOL(id evaluatedObject, NSDictionary * bindings) {return([evaluatedObject isExpired]);}];
[fetchRequest setPredicate:predicate];

但我得到错误: ***由于未捕获异常终止应用程序'NSInvalidArgumentException',reason:'问题与subpredicate BLOCKPREDICATE(0x272ac)'
***
。这是否意味着您不能使用NSFetchRequest的块谓词?

but I get the error: *** Terminating app due to uncaught exception 'NSInvalidArgumentException', reason: 'Problem with subpredicate BLOCKPREDICATE(0x272ac)' ***. Does this mean that you can't use a block predicate with an NSFetchRequest? Or have I just constructed it improperly?

谢谢!

推荐答案

所以,似乎我们在对原始帖子的评论中建立,这可能是由于SQLite存储与块谓词不兼容,因为Core Data无法将这些转换为SQL在商店中运行(感谢,JoostK)

So, it appears that we've established in the comments to the original post that this is likely caused by SQLite stores being incompatible with block predicates, since Core Data cannot translate these to SQL to run them in the store (thanks, JoostK).

可能有几种方法来克服这个问题:

There might be a couple of ways to overcome this:


  • 实体的结束日期是常规属性,您可能可以将到期约束表示为谓词格式字符串,而不是块谓词,Core Data应该能够将其转换为SQL子句。

  • 如果上述情况可能,您可能会更喜欢使用获取请求模板以检索到期的项目。您需要传递一个替换变量,例如 $ NOW ,以访问当前日期。这有使谓词模板显示在模型编辑器中的优点。

  • 然而,两种方法都有重复现有功能的缺点(即您的 isExpired 方法)。因此,另一种方法是先获取所有有资格的实体,而不管它们的到期状态如何,然后对结果集合实体执行专用过滤步骤,以清除未过期的实体。因为到那时,他们已经从商店完全复活,你应该能够使用块谓词为此。

  • Provided that the end date of your entities is a regular attribute, you might be able to express the expiry constraint as a predicate format string instead of a block predicate, which Core Data should be able to translate into a SQL clause.
  • If the above is possible, you will probably prefer to use a fetch request template to retrieve the expired items. You would need to pass in a substitution variable like $NOW to give access to the current date, though. This has the advantage of making the predicate template show up in the model editor.
  • Both approaches, however, have the disadvantage of duplicating existing functionality (i.e., your isExpired method). So another way would be fetch all qualifiying entities regardless of their expiry state first, and then run a dedicated filtering step on the resulting set of entities to weed out the non-expired ones. Since by that point, they have been fully resurrected from the store, you should be able to use a block predicate for this.

这篇关于NSFetchRequest和predicateWithBlock的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆