Qual è la differenza tra pluck e collect in Rails?


123

Ecco due codici di esempio.

Il primo con collect:

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

Secondo con pluck:

User.first.gifts.pluck(:id)

C'è qualche differenza tra loro in termini di prestazioni o qualcos'altro?

Risposte:


230

pluckè a livello db. Interrogerà solo il campo specifico. Vedi questo .

Quando lo fai:

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

Hai oggetti con tutti i campi caricati e ottieni semplicemente i idringraziamenti per il metodo basato su Enumerable.

Così:

  • se ti serve soloid con Rails 4, usa ids:User.first.gifts.ids

  • se hai bisogno solo di alcuni campi con Rails 4, usa pluck:User.first.gifts.pluck(:id, :name, ...)

  • se hai bisogno di un solo campo con Rails 3, usa pluck:User.first.gifts.pluck(:id)

  • se hai bisogno di tutti i campi, usacollect

  • se hai bisogno di alcuni campi con Rails 4, usa ancora pluck

  • se hai bisogno di alcuni campi con Rails 3, usa selectecollect


"se hai bisogno di alcuni campi, usa selectand collect" - non puoi semplicemente usare pluckcon più attributi, come pluck(:id, :name)?
Alexander

@AlexPopov - Rails 4+ supporta pluckpiù campi, Rails 3 no, a meno che non si utilizzi la soluzione alternativa di Ryan Lefevre
marksiemers

3
In Rails 4, se hai solo bisogno di id, usa .idsRef doc: api.rubyonrails.org/classes/ActiveRecord/…
Ivan Chau

30

Sì. Secondo le guide Rails , pluckconverte direttamente un risultato di database in un array, senza costruire ActiveRecordoggetti. Ciò significa prestazioni migliori per una query di grandi dimensioni o spesso eseguita.

Oltre alla risposta di @ apneadiving, pluckpuò prendere come argomento sia nomi di colonne singole che multiple:

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

3

La differenza fondamentale e principale è che Pluck si applica a livello db e collect ottiene tutti i dati e quindi restituisce il record quando è necessario che tutti i record utilizzano collect e quando pochi campi utilizzano pluck


2

Se c'è un caso in cui stai usando pochi attributi del record recuperato. In questi casi dovresti usare pluck.

User.collect(&:email)

Nell'esempio sopra, se hai solo bisogno dell'attributo email, stai sprecando memoria e tempo. Poiché recupererà tutte le colonne dalla tabella utente nel database, alloca la memoria per ogni attributo (inclusi gli attributi che non userete mai)

NOTA: plucknon restituisce ActiveRecord_Relation dell'utente

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.