例如,我需要获得审核计数,一种方法是这样做:
public function getActiveReviews()
{
return $this->getReviews()->filter(function(Review $review) {
return $review->isActive() && !$review->isDeleted();
})->count();
}
另一种方法是使用这样的查询生成器:
$qb = $this->createQueryBuilder('r')
->where('r.active = true')
->andWhere('r.deleted = false')
->select('count(r)')
哪种方式会给我更好的表现?为什么?
当然计数查询会更快,因为它会导致单个SQL查询返回单个值。
对实体的迭代将需要:
根据受影响的数据量的差异可能会非常大。
运行计数实体可能足够快的唯一情况是,您已经获取了所有实体并且只需要对它们进行计数。
它取决于Symphony count()实现,但你可能会。通常RDBMS在内部更快地计算其行,并且它需要更少的资源。
在第一种情况下,您请求整个行集,这可能是巨大的,然后您遍历它,您将过滤器函数应用于每一行,然后您只需查看过滤的行集大小并删除所有内容。 (但是,当然,这可能会以某种方式通过您的框架进行优化)。
在第二种情况下,您只需询问数据库它满足条件的行数。 DB返回一个数字,就是这样。
正如其他人所说,第一选择可能更快的唯一情况是当你已经缓存了行集(不需要连接到数据库) - 并且当你的数据库连接同时非常慢时。
我看到大型表上某些COUNT请求(Oracle)的数据库速度很慢,但它们仍然比同一行集上的PHP代码更快。 DB针对数据过滤和计数进行了优化。通常COUNT请求非常快。