2015-09-04 10 views
8

Voglio unire più raccolte in una sola. Io ho una soluzione, che è la seguente:Come unire correttamente più raccolte in Laravel

$allItems = $collection1->merge($collection2) 
         ->merge($collection3) 
         ->merge($collection4) 
         ->merge($collection5); 

Questo in realtà funziona, ma ho incontrato problemi nei casi in cui alcune o tutte le collezioni non contengono oggetti. Ottengo un errore sulla falsariga di call to merge() on non object.

In realtà ho provato a creare un array di tutte le raccolte, quindi a scorrere su di esse, controllandone la validità, ma non ha funzionato e ritengo che non fosse molto elegante.

Come posso ripetere in modo elegante questo processo di unione di più raccolte, tenendo conto del fatto che alcune o tutte le raccolte potrebbero essere vuote o non valide? Apprezzato!

risposta

11

Quello che ho finito è stato separando ogni passaggio. Era la catena di fusione che lo stava uccidendo, perché alcune o tutte le raccolte potevano essere state invalide.

$allItems = new \Illuminate\Database\Eloquent\Collection; //Create empty collection which we know has the merge() method 
$allItems = $allItems->merge($collection1); 
$allItems = $allItems->merge($collection2); 
$allItems = $allItems->merge($collection3); 
$allItems = $allItems->merge($collection4); 
+1

È strano che non sia possibile incatenarli, ma posso confermare che è corretto. – mopo922

+2

Solo un aggiornamento per le persone che vedono questo puoi fare '$ allItems = collect();' per creare una nuova collezione. –

0

dipendono i dati, se la raccolta è in realtà nulla o PHP sostegno che si può fare:

$allItems = $collection1->merge($collection2 ?: collect()) 
        ->merge($collection3 ?: collect()) 
        ->merge($collection4 ?: collect()) 
        ->merge($collection5 ?: collect()); 

o si vuole fare un ridurre:

$allItems = collect([$collection2, $collection3, $collection4])->reduce(function($arr, $item) { 
     if (empty($item) || $item->isEmpty()) 
      return $arr; 
     return $arr->merge($item); 
    }, $collection1); 

o semplice php ridurre senza overhead

$allItems = array_reduce([ 
     $collection2, 
     $collection3, 
     $collection4 
    ], function($arr, $item) { 
     if (empty($item) || $item->isEmpty()) 
      return $arr; 
     return $arr->merge($item); 
    }, $collection1); 
+0

Purtroppo questi non tengono conto del fatto che alcune o tutte le collezioni potrebbe essere valida, incluing $ collection1 – Marcel

1

ho avuto la stessa domanda, così ho risolto nel seguente modo:

$clients = ClientAccount::query()->get(); 
$admins = AdminAccount::query()->get(); 

$users = collect($clients)->merge($admins)->merge($anotherCollection)->merge(...);