我想获得表中的第一行和最后一行,我找到了两种方法:
$first = DB::table('shops')->first();
$last = DB::table('shops')->orderBy('id','DESC')->first();
和
$shops = DB::table('shops')->get();
$first2 = $shops[0];
$last2 = $shops[count($shops)-1];
我的问题是,使用相同的数据库哪种方式表现更快?或以任何方式记录查询时间?
DB可能很大,有1000行,10.000行等......
答案 0 :(得分:2)
大约8000行,结果如下:
第一种方式:
[2016-03-01 19:14:11] local.DEBUG: select * from `shops` limit 1; in 1.27 ms
[2016-03-01 19:14:11] local.DEBUG: select * from `shops` order by `id` desc limit 1; in 3.04 ms
第二种方式:
local.DEBUG: select * from `shops`; in 188.98 ms
你可以看到第二种方式比第一种方式慢得多。
因为在第二种方式中你必须从商店表中获取所有记录。这需要很多次。
对于更大的数据集,我认为第二种方法因请求超时而无效。
更新
只是为了另一个实验。
我尝试第三种方法在一个查询中解决您的问题,如下所示:
$shops = DB::table('shops')
->whereRaw('id = (SELECT MIN(id) from shops)')
->orWhereRaw('id = (Select MAX(id) from shops)')
->get();
我与第一种方式进行比较。这是结果:
# the 3rd way
[2016-03-01 19:51:56] local.DEBUG: select * from `shops` where id = (SELECT MIN(id) from shops) or id = (Select MAX(id) from shops); in 1.04 ms
# the 1st way
[2016-03-01 19:52:02] local.DEBUG: select * from `shops` limit 1; in 0.67 ms
[2016-03-01 19:52:02] local.DEBUG: select * from `shops` order by `id` desc limit 1; in 0.5 ms
使用子查询似乎查询时间更快。
答案 1 :(得分:1)
查询时间之间的差异实际上取决于您的计算机处理它们的速度,当然还有它正在处理的行数。
我现在可以告诉你,第一个解决方案只是在每个查询中抓取一个结果,因此会更快。您只使用两个查询获取两行。
第二个是将所有行加载到一个数组中,然后你抓住第一个和最后一行,有1000到10,000行,这可能需要相当长的时间。
您可以随时尝试手动运行查询,并查看加载所需的时间以获得实际差异。
您可以通过将toSql()
添加到eloquent查询的末尾来获取确切的SQL,就像这样。
答案 2 :(得分:1)
就像我评论的那样:第一个例子会更快。因为你只获得两条记录。最后一个示例将获取所有记录,在您的示例中可能是数千条记录。这是页面加载时间的巨大差异。
如果您想查看网页加载的时长,您可能需要查看barryvdh/laravel-debugbar。这将提供有关各种事物的重要信息,包括页面加载时间。