【问题标题】:Doctrine 2.2 + Zend Framework pagination speed optimizationDoctrine 2.2 + Zend Framework 分页速度优化
【发布时间】:2012-06-13 08:04:58
【问题描述】:

我在使用 HYDRATE_OBJECT 时遇到了 Doctrine 2 的性能问题。当我从HYDRATE_ARRAY 切换到HYDRATE_OBJECT 时,耗时将近10 倍!我使用doctrine 2 and zend paginator 作为参考:

$query = $em->createQuery($dql)
    ->setHydrationMode(\Doctrine\ORM\AbstractQuery::HYDRATE_ARRAY)
    ->setParameter('x', 1);

// Pagination
$paginator = new Doctrine\ORM\Tools\Pagination\Paginator($query, false);
$iterator = $paginator->getIterator();
die(); // 160 ms

$query = $em->createQuery($dql)
    ->setHydrationMode(\Doctrine\ORM\AbstractQuery::HYDRATE_OBJECT)
    ->setParameter('x', 1);

// Pagination
$paginator = new Doctrine\ORM\Tools\Pagination\Paginator($query, false);
$iterator = $paginator->getIterator();
die(); // 1.4s

我应该注意什么?如何减少处理时间并仍然使用HYDRATE_OBJECT?有没有更好的方法来完成分页?

*编辑:使用->setFirstResult($itemsPerPage * $page - $itemPerPage)->setMaxResults($itemsPerPage); 会显着减少加载时间,但使用$iterator 时:

$adapter =  new \Zend_Paginator_Adapter_Iterator($iterator);
$zend_paginator = new \Zend_Paginator($adapter);          
$zend_paginator->setItemCountPerPage($itemsPerPage)
    ->setCurrentPageNumber($page);

Zend 只知道$itemsPerPage, (count($iterator) == $itemsPerPage),因此分页链接总是只计算 1 页。如何使用 Zend_Paginator 完成正确的分页,并且只加载 $itemsPerPageentities?

【问题讨论】:

  • 你分析过你的代码吗?如果不知道您的模型中有什么样的业务逻辑,就很难回答这个问题。
  • 除了 ArrayCollection 的 ->add() 之外,实体中没有业务逻辑。 Rest 是普通的 setter 和 getter。
  • 使用 OneToMany 连接时 setMaxResults 不是问题吗?

标签: php performance doctrine-orm


【解决方案1】:

我现在通过为 Doctrine 分页创建 Zend 分页适配器包装器解决了这个问题;

<?php
class PaginatorAdapter extends Doctrine\ORM\Tools\Pagination\Paginator implements
        Zend_Paginator_Adapter_Interface
{
    public function getItems($offset, $itemCountPerPage)
    {
        $this->getQuery()->setFirstResult($offset)->setMaxResults($itemCountPerPage);
        return $this->getQuery()->getResult($this->getQuery()->getHydrationMode());
    }
}

【讨论】:

  • 执行速度非常慢,只加载 $itemsPerPageentities 进行分页
  • 不,我的意思是你的自定义实现 Zend_Paginator 比仅仅将 Doctrine 集合传递给 Zend_Paginate 更有效率
  • getIterator() 似乎填充了每个条目(例如 10000 行)。或者 setMaxResults 会使迭代器 count(),总是返回 maxresult 整数(不是整个集合)
  • @JonSkarpeteig:你如何使用它?您是否使用 getItems 而不是将适配器用作可迭代对象?这也适用于 OneToMayn Joins 吗?
  • 我在视图脚本中将它用作常规 Zend Paginator。有关更多信息,您可以查看:framework.zend.com/manual/en/zend.paginator.usage.html
猜你喜欢
  • 1970-01-01
  • 2014-01-17
  • 2012-04-03
  • 2012-02-22
  • 2011-12-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-06-27
相关资源
最近更新 更多