【问题标题】:NSPredicate something equivalent of SQL's GROUP BYNSPredicate 相当于 SQL 的 GROUP BY
【发布时间】:2011-10-13 22:49:03
【问题描述】:

为了简化: 名为卡片的表中有 3 列。

id packTitle 术语

id 是一列 - 从 0.....100 开始的整数

packTitle - 描述包的字符串,假设有 3 种包 PACK1、PACK2、PACK3

term - 101 个项目的不同未排序名称。

通过 SQL 语句

select packTitle from cards group by packTitle;

我可以得到 3 个项目的列表。

您能否建议 NSPredicate 等效于 SQL 语句 GROUP BY。我需要获取一个数组来填充 UITableView。

【问题讨论】:

    标签: objective-c ios core-data nspredicate


    【解决方案1】:

    CoreData 是一个对象图管理框架,而不是 SQL 数据存储。因此,您应该尽快摆脱 SQL 思维模式。 NSPredicate 旨在作为对象图中限定对象的谓词(不足为奇)。因此,您可以获取与查询匹配的所有对象,但这与对这些结果进行分组不同。如果要进行聚合操作,请使用 Key-Value 编码的collection operators。在底层,Core Data可能将这些转换为合理的 SQL,但这只是一个实现细节。

    在这种情况下,您可以获得一组唯一的packTitle

    [myCards valueForKeyPath:@"@distinctUnionOfObjects.packTitle"];
    

    这将为您提供myCards 集合中不同的packTitle 值集。如果您想对 Core Data 存储中的所有卡片进行此操作,则必须对所有 cards 运行查询,然后应用此收集操作。

    另一种方法是创建一个PackInformation 实体,或者一些包含title 属性的实体。然后,您可以在数据存储中仅包含 3 个这些实体,并从相应的包实体中引用它们。获取所有三个(或任何最终数字)并获取它们的标题是微不足道的。

    正如其他人所说,如果您要从根本上报告关系数据集,则最好直接使用 SQLite。这完全取决于您从 Core Data 中获得了多少其他好处。

    【讨论】:

    • 非常感谢您提供这些详细信息,并特别感谢您关注我的问题。看来我需要学习键值编码才能理解您的答案。如何删除所有带有名为 PACK1 的 packTile 的卡片也很有趣。希望我能找到一个朝着这个方向发展的答案。
    • NSPredicate 本身与 Core Data 无关。它可能与数组和其他数据库(如 Realm)一起使用。这就是为什么这是一个有效的问题,并且可以与 SQL 进行比较
    【解决方案2】:

    假设您正在使用 CoreData... 根据Apple Documentation

    您不一定要将“任意”SQL 查询转换为 谓词或获取请求。例如,没有办法转换 一条 SQL 语句,例如

    SELECT t1.name, V1, V2
        FROM table1 t1 JOIN (SELECT t2.name AS V1, count(*) AS V2
            FROM table2 t2 GROUP BY t2.name as V) on t1.name = V.V1
    

    进入一个获取请求。您必须获取感兴趣的对象,然后 要么直接使用结果进行计算,要么使用 数组运算符。

    如果您需要执行这样的复杂查询,最好使用 SQLite。

    【讨论】:

    • 感谢您的回复。然后我必须处理结果。
    猜你喜欢
    • 1970-01-01
    • 2016-11-29
    • 2019-04-26
    • 1970-01-01
    • 2011-02-14
    • 2016-01-06
    • 2010-10-24
    • 1970-01-01
    • 2020-05-11
    相关资源
    最近更新 更多