마 젠토에서 컬렉션을 복제하는 방법?


12

이 컬렉션에 대해 두 가지 다른 작업을 수행하려는 방법에 하나의 컬렉션이 있습니다. 따라서 동일한 컬렉션의 두 복사본을 별도로 원한 다음 두 컬렉션 중 하나를 원래 컬렉션에 다시 할당하고 반환합니다.

이것을 간단하게하기 위해이라는 객체 컬렉션이 있다고 가정합니다 $collection.

이제 Magento 컬렉션 복제가 내장되어 있는지 여부를 알 수 없으므로 PHP 복제로 시도하고 있습니다.

$coll1 = clone $collection;
$coll2 = clone $collection;

이제 원본 컬렉션의 두 개의 개별 복제본에서 다른 작업을 수행하려고합니다.

$coll1->getSelect()->where('some where condition');
$coll2->getSelect()->where('some different where condition');
if($coll1->count() == 0) {
    $collection = $coll2;
} else {
    $collection = $coll1;
}

그러나 이상한 점은이 복제 된 컬렉션 모두에 지정된 위치 조건이 있다는 것입니다. $ coll1 조건은 $ coll2의 조건과 함께 $ coll2에 적용되며 그 반대도 마찬가지입니다.

누구든지 이것을 달성하는 방법을 알고 있습니까?

감사!

답변:


14

딥 클로닝이 필요한 PHP 클론 연산자를 사용하려면 속성에 객체를 저장하는 클래스가 객체를 복사하기 위해 __clone 메서드를 구현해야합니다. 이들이 정의하지 않으면 두 인스턴스의 속성이 동일한 객체를 참조합니다.

Magento는 컬렉션 초록에 __clone을 구현하지 않으므로 원하는대로 딥 클로닝을 지원하지 않습니다.

컬렉션을 복제하는 데 비용이 많이 들기 때문에 원하는 작업을 수행하는 다른 방법을 찾는 것이 좋습니다.

예를 들어 사용자가 제공 한 예제는 선택을 복제하고로드 할 레코드 수를 선택하도록 수정 한 다음 해당 결과에 따라 콜렉션을 수정하도록 변경 될 수 있습니다. 컬렉션을로드하지 않고 사용할 컬렉션을 결정하기 위해 계산하는 것이므로 성능도 향상됩니다.

편집 : 다음은 컬렉션을로드하거나 실제로 수정하지 않고 카운트를 얻는 방법을 보여줍니다.

$collection = Mage::getModel(...)->getCollection();

$count = $collection->getSelectCountSql();
$count->where('some where condition');
if ($count->query()->fetchColumn() == 0) {
    ...
} else {
    ...
}

작은 세부 사항 : $collection->getSelect()컬렉션 자체가 아닌 위치에 대한 정보가 저장 됩니다.
Fabian Blechschmidt

대답 해줘서 고마워요. 그러나 where condition 만 적용한 후에는 수집 횟수를 알고 싶습니다. 그 수에 따라 다른 where 조건을 사용할지 여부를 결정하고 싶습니다. 코드 스 니펫을 게시하여 방법을 더 잘 이해할 수 있습니까?
MagExt

코드 예제로 답변을 업데이트했습니다. @FabianBlechschmidt가 지적했듯이, where는 select에 있습니다. 여기서 컬렉션 개체가 복제 될 때 복제되지 않고 둘 다 동일한 선택 개체 인스턴스를 참조하기 때문에 특정 문제가 발생합니다.
davidalger

업데이트 해 주셔서 감사합니다. 나는 이미 그와 같은 해결책을 얻었으므로 이것을 시도하지 않았습니다.
MagExt

실제로 컬렉션을 복제하는 데 문제가 있으면 직렬화 및 직렬화 해제가 프로세스에서 도움이 될 수 있습니다. PHP에서 복제하는 다른 대안도 꽤 괜찮습니다. 그러나 모든 David는 정확합니다 ... 기본적으로 객체를 복제 할 때 연결된 객체에 대한 포인터를 복제하고 있지만 그의 대답은 근본적인 문제를 올바르게 나타내지 않았습니다.
mprototype

1

@ davidalger의 답변을 확장하려면 카운트와 다른 작업을 수행하려는 경우 선택을 재설정 할 수 있습니다 .

$select= $collection->getSelectCountSql()->reset();

$select
    ->from('newsletter_subscriber', array('some_column'))
    ->distinct();

컬렉션이 수정되므로 나중에 프로세스에 해로운 영향을 줄 수 있으므로주의하십시오.

더 나은 방법은 선택을 어떻게 든 복제하는 것이지만 객체에 복잡한 유형 (Varien_Db_Select 또는 Zend_Db_Select에 __clone메소드가 있음) 이 포함되어 있기 때문에 얕은 사본은 잘라 내지 않습니다 .

이 문제를 해결하는 한 가지 방법은 선택 데이터를 저장하고 수정하고 쿼리를 실행 한 다음 원래 선택 데이터를 다시 넣는 것입니다.

예를 보려면 여기를 참조하십시오 : https://ka.lpe.sh/2013/05/23/magento-clone-collection-how-to-clone-collection-in-magento/

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.