Unterschied zwischen getSize () und count () zur Sammlung
-
16-10-2019 - |
Frage
Ich habe schon oft gehört, dass beide gleich sind. Aber ich stehe vor einem seltsamen Problem, in der Produktsammlung von Katalogestechern, Count () kehrt die korrekte Produktzahl zurück, während GetSize () Null zurückgibt.
Im Grunde genommen bekomme ich das:
$collection->count(); //correct count
$collection->getSize(); //0
Aber ich möchte, dass die GetSIZE () die richtige Zählung hat, da sie entscheidet, ob Pagination und Produkte auf der Suchseite angezeigt werden sollen oder nicht. Ich verwende innere Join, links Join und wo Zustand nur in der Sammlung genauer ist.
Irgendwelche Ideen, warum ich dieses seltsame Problem bekomme?
Vielen Dank
AKTUALISIEREN:
Meine vorherige Frage, Wie klonen Sie die Sammlung in Magento? Ich wollte zwei verschiedene Operationen auf einer Sammlung ausführen. Die erste Sammlung zeigt korrekt GetSIZE (), aber wenn das GetSize () Null ist, habe ich die Where -Klausel entfernt und neue Wo -Bedingung gegeben. Danach erhalte ich korrektes RAW SQL, was ich erwartet habe, und es gibt auch eine korrekte Datensätze, aber nur GetSize () in der Sammlung gibt keine Zählungen.
Im Grunde muss ich die Sammlung möglicherweise neu laden, wie GetSize () alte Zählung nimmt. Macht Sinn?
Lösung
Die meisten (wenn nicht alle) verlaufen die Sammlungen Varien_Data_Collection_Db
. Hier sind die 2 Methoden dieser Klasse
public function getSize()
{
if (is_null($this->_totalRecords)) {
$sql = $this->getSelectCountSql();
$this->_totalRecords = $this->getConnection()->fetchOne($sql, $this->_bindParams);
}
return intval($this->_totalRecords);
}
public function count() //inherited from Varien_Data_Collection
{
$this->load();
return count($this->_items);
}
Da ist ein Unterschied. Zum getSize()
Die Sammlung ist nicht geladen. Zum count()
es ist. Normalerweise verwenden Sammlungsmodelle dasselbe getSize()
Methode wie oben und nur überschreiben getSelectCountSql()
.
Im getSelectCountSql()
Das Limit wird zurückgesetzt, um die Gesamtzahl der für die festgelegten Filter verfügbaren Datensätze zu erhalten (where
Aussage). Sehen Sie, wie das getSelectCountSql()
Arbeiten
public function getSelectCountSql()
{
$this->_renderFilters();
$countSelect = clone $this->getSelect();
$countSelect->reset(Zend_Db_Select::ORDER);
$countSelect->reset(Zend_Db_Select::LIMIT_COUNT);
$countSelect->reset(Zend_Db_Select::LIMIT_OFFSET);
$countSelect->reset(Zend_Db_Select::COLUMNS);
$countSelect->columns('COUNT(*)');
return $countSelect;
}
Andere Tipps
Vorsichtig sein. Dies ist richtig, aber die Methoden werden in überschrieben Varien_Data_Collection_Db
Wie von Marius beschrieben
Schauen Sie sich nur an
// \Varien_Data_Collection::getSize
public function getSize()
{
$this->load();
if (is_null($this->_totalRecords)) {
$this->_totalRecords = count($this->getItems());
}
return intval($this->_totalRecords);
}
// \Varien_Data_Collection::count
public function count()
{
$this->load();
return count($this->_items);
}
So sollte es auf diesem niedrigen Niveau gleich sein. Beide Methoden laden die Sammlung und zählen die Elemente.
AKTUALISIEREN
Oh, ich sehe ein Problem: GetSize () zwischen den _totalrecords, das bedeutet, dass es nicht neu berechnet wird. Überprüfen Sie wo _totalRecords
ist eingestellt?
Diese Antwort wird in Google für "Magento GetSize falsch" und ähnliche Suchanfragen angezeigt, daher möchte ich ein mögliches Szenario hinzufügen, das für jemanden nützlich sein könnte
Wenn Sie eine Gruppenanweisung in Ihrer Anfrage haben und a machen
SELECT COUNT(DISTINCT e.entity_id) ... GROUP BY ( at_id_art.value )
MySQL gibt eine Anzahl für jede der Gruppen zurück, daher wird VIVIEN_DATA_Collection_db :: getSize () die falsche Antwort zurückgeben. Dies liegt daran, dass diese Funktion die erste Zeile abreißt:
public function getSize()
{
if (is_null($this->_totalRecords)) {
$sql = $this->getSelectCountSql();
$this->_totalRecords = $this->getConnection()->fetchOne($sql, $this->_bindParams);
}
return intval($this->_totalRecords);
}
Wenn es bevölkert
$this->_totalRecords = $this->getConnection()->fetchOne($sql, $this->_bindParams);
Es wählt die erste Zeile aus und gibt daher die Gesamtsumme der ersten Gruppe als Gesamtgröße zurück.
Am Ende habe ich diesen Code zum Zählen gemacht, basierend auf den eindeutigen Werten der Attribute in meiner Abfrage.
$select = clone $collection->getSelect();
$group = $select->getPart(Zend_Db_Select::GROUP);
$select->reset(Zend_Db_Select::GROUP)->reset(Zend_Db_Select::COLUMNS)->columns("COUNT(DISTINCT {$group[0]})");
$totalCount = $collection->getConnection()->fetchOne($select);
Nur für den Fall, dass Sie hier landen, gibt es eine weitere einfache Lösung zum Versuch:
System -> Index Management
und wählen Sie sie alle aus (auch wenn sie "grün, kein Redex benötigt" angeben, und zwingen Sie sie zur Reindex.
Dies löste meine leere getSize()
Das Problem, das wiederum die speziellen und neuen Datenbankanfragen erlaubte, die Produkte zu finden, die "if" -Bedingungen zu erfüllen und ordnungsgemäß zu rendern.
Wann count($collection)
war anders als $collection->getSize()
Ich musste reindex
Die Produkte, dann funktionierte alles gut.
Es gibt einen Hauptunterschied für GetSize () Die Produktsammlung ist nicht geladen. Für count () wird die gesamte Produktsammlung geladen. Für einen großen Katalog ist es also nicht ratsam, die Zählfunktion in einer Sammlung zu verwenden.