如何使用sql查询优化代码
$collection->filter(function ($item) use ($i) {
return $item->created_at->month == $i->month;
})->count();
我希望在集合中代替过滤器函数在sql中进行过滤,这样可以更快
这是函数:
$data = [];
switch ($range) {
//monthly
case self::$timeRanges[0]:
for ($i = Carbon::now()->copy()->subYear()->endOfMonth(); $i <= Carbon::now()->subMonth()->endOfMonth(); $i->addMonths(1)) {
$data[$i->month] = $collection->filter(function ($item) use ($i) {
return $item->created_at->month == $i->month;
})->count();
}
break;
//weekly
case self::$timeRanges[1]:
$collection = $collection->where('created_at', '>=', Carbon::now()->subWeek()->endOfWeek()->subWeeks(5))->where('created_at', '<=', Carbon::now()->subWeek()->endOfWeek());
for ($i = Carbon::now()->copy()->subWeek()->endOfWeek()->subWeeks(5); $i <= Carbon::now()->copy()->subWeek()->endOfWeek(); $i->addWeeks(1)) {
$data[$i->weekOfMonth] = $collection->filter(function ($item) use ($i) {
return $item->created_at->weekOfYear == $i->weekOfYear;
})->count();
}
break;
}
return ($data);
感谢您的帮助,祝您有美好的一天!
答案 0 :(得分:1)
只需扩展@Elie的答案,您甚至无需使用原始查询。 Laravel很好地满足了日期条件,并且在Queries页上有很好的记录。
$desiredMonth = 12;
Model::whereMonth('created_at', $desiredMonth)->get();
但是,这并不能完全解决当前的问题。我们需要做的是检索所有相关结果,然后按月对检索到的结果进行过滤。我相信通过从SQL检索所有结果,然后按原样对它们进行过滤,但使用较少的迭代代码,这样做会更加高效,更快。
$collection = Model::whereYear(2018)->get();
$months = $collection->groupBy(function ($item, $key) {
return $item->created_at->month;
});
$months->toArray();
[
'1' => [[...],[...],[...]],
'2' => [[...],[...],[...]],
'3' => [[...],[...],[...]],
'4' => [[...],[...],[...]],
'5' => [[...],[...],[...]],
'6' => [[...],[...],[...]],
'7' => [[...],[...],[...]],
'8' => [[...],[...],[...]],
'9' => [[...],[...],[...]],
'10' => [[...],[...],[...]],
'11' => [[...],[...],[...]],
'12' => [[...],[...],[...]],
]
另外,如果您坚持使用SQL进行过滤,则可以执行groupBy
:
Model::groupBy(\DB::raw('MONTH(created_at) as month'))->get();
您需要针对哪种速度更快或至少效率最高进行自己的测试。另外,有些数据库不允许在不修改配置的情况下进行多个分组(我们在这里没有,但是您可能想要添加),因此除非您使用大量的数据集,否则我个人的头奖将是原始方法。 / p>
答案 1 :(得分:0)
尝试一下:
Model::where(\DB::raw('MONTH(created_at)') , $month )->get();