表格结构如下所示(不列出所有关系):
products
id
launch_date
name
product_view_history
id
account_id
product_id
timestamps
我有查询,并且不定期地花费很长时间。通过我完成的所有分析,在SQL中花费的实际时间非常小(<50 ms
),但此代码执行的时间在900+ms
范围内:
$this->select('products.*', DB::raw('COUNT(product_view_history.id) as view_count'))
->leftJoin('product_view_history', 'product_view_history.product_id', '=', 'products.id', 'outer')
->groupBy('product_view_history.product_id')
->orderBy('view_count', 'DESC')
->orderBy('products.id', 'DESC')
->whereNotNull('products.launch_date')
->with(['owner.images', 'owner.star', 'owner.follows', 'owner.followers', 'company.products.alphas'])
->take(Config::get('xxxx.limits.small'))
->get();
但是,如果我注释掉<50ms
,则执行此代码所需的时间会减少适当的->orderBy('view_count', 'DESC')
。如果我将get()
换成toSql()
并手动运行这两个查询,我会发现时间相对相似且很小。要明确测量时间,不是SQL查询时间;我只是在几毫秒之前得到时间,并且在完成此操作后直接记录差异。
任何人都可以看到为什么->orderBy('view_count', 'DESC')
会在一整秒的时间内添加到代码执行的任何原因,即使SQL本身不是/最慢的?
答案 0 :(得分:1)
似乎执行查询原始,保湿和加载似乎加快了查询。这并没有回答为什么那个顺序会导致这样的问题,但它确实回答了如何解决手头的问题:
$products = self::hydrate(DB::select(
"select `products`.*, COUNT(product_view_history.id) as view_count
from `products` left join `product_view_history`
on `product_view_history`.`product_id` = `products`.`id`
where `products`.`launch_date` is not null
group by `product_view_history`.`product_id`
order by `view_count` desc, `products`.`id` desc limit {$limit}"))
->load(['owner.images', 'owner.star', 'owner.follows', 'owner.followers', 'company.products.alphas']);
答案 1 :(得分:0)
对我来说,这是由于在where查询中使用“错误”数据类型引起的。 例如,我被称为“用户名”的列过滤,该列是varchar,但插入了一个Int作为值进行过滤。 使用orderBy花费了很长时间,但是删除orderBy时又很快。 解决方案至少对我来说是将用户名转换为String,并且orderBy像以前一样流畅。我不知道真正的原因,但是在使用不匹配的数据类型时,也许雄辩地使用了口才或排序方式。