2012-04-09 12 views
71

Così ho eseguire una query al DB e ho una gamma completa di oggetti:Rails filtrano array di oggetti dal valore di attributo

@attachments = Job.find(1).attachments 

Ora che ho un array di oggetti che non si desidera eseguire un'altra query db, ma vorrei per filtrare l'array in base alla Attachment oggetto del file_type modo che io possa avere un elenco di attachments dove il tipo di file è 'logo' e poi un altro elenco di attachments dove il tipo di file è 'image'

Qualcosa così:

@logos = @attachments.where("file_type = ?", 'logo') 
@images = @attachments.where("file_type = ?", 'image') 

Ma in memoria anziché una query DB.

Cheers

risposta

135

Prova:

Questo va bene:

@logos = @attachments.select { |attachment| attachment.file_type == 'logo' } 
@images = @attachments.select { |attachment| attachment.file_type == 'image' } 

ma per le prestazioni saggio non è necessario per scorrere @Attachments due volte:

@logos , @images = [], [] 
@attachments.each do |attachment| 
    @logos << attachment if attachment.file_type == 'logo' 
    @images << attachment if attachment.file_type == 'image' 
end 
+1

Come la soluzione di @ Vik è praticamente ideale, aggiungerò semplicemente che in casi binari, potresti usare una funzione 'partizione' per rendere le cose più dolci. http://ruby-doc.org/core-1.9.3/Enumerable.html#method-i-partition – Vlad

+0

Grazie a @Vlad, è bello, ma supporta solo se abbiamo bisogno di raccogliere solo due cose dall'oggetto. – Vik

+0

Sì, è per questo che ho detto "binario" :). Nella domanda, apparentemente c'era una scelta di logo o immagine, quindi ho aggiunto questo per completezza. – Vlad

2

hai provato a caricare carico?

@attachments = Job.includes(:attachments).find(1).attachments 
+0

Mi dispiace non sto essendo chiaro: come faccio a filtrare in base al valore di un attributo dell'oggetto senza eseguire il looping della matrice? – joepour

+0

Se ho capito bene, vuoi meno query in db, in particolare, una volta eseguita una query come '@attachments = Job.first.attachments', vuoi eseguire il ciclo' @ attachments' nel frattempo non vuoi più altre query db . è questo quello che vuoi fare? –

+0

Faccio una query db e ricevo una matrice di oggetti. Quindi voglio creare due liste separate da quella matrice filtrando gli oggetti in base al valore dei loro attributi (vedi post originale) - cheers – joepour

3

Se gli allegati sono

@attachments = Job.find(1).attachments 

Questa matrice sarà di attaccamento oggetti

Utilizzare il metodo di selezione per filtrare basato su file_type.

@logos = @attachments.select { |attachment| attachment.file_type == 'logo' } 
@images = @attachments.select { |attachment| attachment.file_type == 'image' } 

Ciò non attiverà alcuna query db.

Problemi correlati