如何在Symfony2中优化DQL查询?

Dav*_*eto 2 doctrine query-optimization symfony doctrine-orm

我有一个名为Abono的实体,它是Check,Efectivo,Debito等其他几个实体的父类.在我的应用程序中,我使用带有这样的DQL语句的存储库类查询Abono类实例的所有对象(代码是真实类型的简化版本):

$dql = "SELECT ab FROM FranquiciaBundle:Abono AS ab";
return $em->createQuery($dql)
          ->getResult();
Run Code Online (Sandbox Code Playgroud)

在我的模板中,我正在显示这样的结果(再次,简化代码):

{% for abono in abonos %}
    <tr>
        <td>{{ abono.id }}</td>
        <td>{{ abono.tipo }}</td>
    </tr>
{% endfor %}
Run Code Online (Sandbox Code Playgroud)

我有5000条记录对表和探查告诉我,该应用程序是打如我所料只是一次数据库的5000倍,而不是,所以我改变阙库使用位getArrayResult()代替getResult(),但问题是,这句话{{ abono.tipo }}是一个方法调用对象,而不是存储在数据库中的属性,因此它永远不会被水合到结果数组中.

所以我的问题是,如何让一个对象数组只攻击一次数据库?

UPDATE:getTipo()类Abono 的方法返回每个对象的Late Static Binding类名,它不是关联.

public function getTipo()
{
    $className = get_called_class();
    $pos = strrpos($className,'\\');
    return substr($className, $pos+1);
}
Run Code Online (Sandbox Code Playgroud)

Dav*_*eto 6

好的,我找到了问题的根源.

似乎在查询与关联相反的对象时,doctrine将始终获取这些实体以创建代理实例,即使控制器或模板中不需要这些实体也是如此.因此,配置文件栏向我展示的数据库的大量点击,实际上是在学习搜索我不想要的信息的方式.

解决方案是强制在存储库中使用部分加载,如下所示:

$dql = "SELECT ab FROM FranquiciaBundle:Abono AS ab";
return $em->createQuery($dql)
          ->setHint(Query::HINT_FORCE_PARTIAL_LOAD, true)
          ->getResult();
Run Code Online (Sandbox Code Playgroud)

更多信息可以在这里找到