在 Rails 中 pluck 和 Collection 有什么区别?

这里有两个样本代码。

第一个是 collect:

User.first.gifts.collect(&:id)

第二个是 pluck:

User.first.gifts.pluck(:id)

他们在性能或其他方面有什么不同吗?

92892 次浏览

pluck在数据库级别。它将只查询特定的字段。

当你这样做:

 User.first.gifts.collect(&:id)

您已经加载了具有所有字段的对象,并且由于基于枚举的方法,您只需获得 id

所以:

  • 如果您需要 只有与 Rails 4的 id,请使用 ids: User.first.gifts.ids

  • 如果您需要使用 Rails 4的某些字段,请使用 pluck: User.first.gifts.pluck(:id, :name, ...)

  • 如果您需要使用 Rails 3的一个字段,请使用 pluck: User.first.gifts.pluck(:id)

  • 如果需要 所有字段,请使用 collect

  • 如果您需要使用 Rails 4的一些字段,仍然可以使用 pluck

  • 如果您需要使用 Rails 3的某些字段,请使用 selectcollect

是的。根据 Rails 指南pluck直接将数据库结果转换为 array,而不构造 ActiveRecord对象。这意味着对于大型查询或经常运行的查询具有更好的性能。

除了@apneadiving 的回答,pluck还可以使用单列和多列名称作为参数:

Client.pluck(:id, :name)
# SELECT clients.id, clients.name FROM clients
# => [[1, 'David'], [2, 'Jeremy'], [3, 'Jose']]

基本和主要的区别是 Pluck 应用于数据库级别,收集所有数据,然后将记录返回给您 当你需要所有的记录使用收集和当很少的领域然后使用拨号

如果您使用检索到的记录的少量属性。在这种情况下,您应该使用 pluck

User.collect(&:email)

在上面的例子中,如果你只需要电子邮件属性,那么你就是在浪费内存和时间。因为它将检索数据库中用户表中的所有列,所以为每个属性(包括永远不会使用的属性)分配内存

注意: pluck不返回用户的 ActiveRecord _ Relations

派对迟到了,但是如果你想要一个更深的 pluck,你可以使用 includes:

User.all.includes(:groups).pluck("users.id", "users.name", "groups.id", "groups.name")

这将导致更大的数组,如

[
[12, "Sam", 4, "FriendsRUs"],
...
]

collectpluck之间的主要区别在于,collect加载来自 DB 的所有属性,而 pluck只加载您提到的属性。 例如:

User.all.collect(&:id)

这将加载内存中 User 记录的所有属性并返回 id。 当你这么做的时候:

User.all.pluck(:id)

这样只加载内存中的 id,所以在只需要访问少量属性的情况下更有效。