如何改进我的查询以防止“PHP 致命错误:允许的内存大小”(laravel 5.2 中的排序和分页)

Posted

技术标签:

【中文标题】如何改进我的查询以防止“PHP 致命错误:允许的内存大小”(laravel 5.2 中的排序和分页)【英文标题】:How can I improve my query for not to get "PHP Fatal error: Allowed memory size" (Ordering and paginating in laravel 5.2) 【发布时间】:2017-08-30 08:41:51 【问题描述】:

我有几件叫做海报的物品,上面有日志。我想在这些日志的创建日期之前订购这些海报。

我有一个名为 Poster 的模型,代码如下:

class Poster extends Model 

protected $table = 'posters';

public function pos_log_resumenEnviado()

    return $this->hasMany('App\models\PosterLog', 'pos_id')->where('log', 'Autores de poster enviado')->orWhere('log', 'Resumen de poster modificado')->latest();

然后在我的控制器中检索结果如下:

$posters = Poster::with('pos_log_resumenEnviado', 'user')->where('state', 'Resumen pendiente de aceptacion')->get();

$posters = $posters->sortBy(function($pos)

    if( sizeof($pos->pos_log_resumenEnviado) > 0)
        return $pos->pos_log_resumenEnviado[0]->created_at;
)->take(1200);

我得到所有海报,然后订购它们并获取前 1200 个结果。这一直工作正常(性能缓慢),但现在我得到了我在标题中所说的 php 错误。错误甚至在 sortBy 执行之前就出现了,只是 get()

如果我不必使用 sortBy 我可以使用 paginate() 方法,但我不知道是否有其他方式来订购。

【问题讨论】:

我好像在用 PHP 对结果进行排序,为什么不使用 mysql 呢? 因为我不知道怎么用MYSQL按这个字段排序。 我不使用 Laravel,但您应该阅读文档以使用 mysql 执行命令。这样会更快,避免php内存限制错误。 谢谢@Mcsky。我知道如何在 mysql 中使用 orderBy,但我不知道如何在这个特定字段中使用它,因为它来自模型关系。无论如何,我什至在 de ordering 开始执行之前就收到了错误。 最好使用 eloquent 而非 php 进行排序!会引发性能问题,请查看下面的答案 【参考方案1】:

这是您必须使用的正确查询 首先,使用 where first 排除不需要的条目,然后在 with 回调中,您可以使用 eloquent 过滤结果:

$posters = Poster::where('state', 'Resumen pendiente de aceptacion')->with(['pos_log_resumenEnviado' => function($q)
                return $q->orderBy('poster_logs.created_at','ASC');
            ])->with('user')->get();

【讨论】:

但是如何将日志创建日期放在 orderBy 中?这不是海报表的列。 当你在回调里面时,你可以直接访问pos_log_resumenEnviado,只需输入orderBy('created_at','ASC'); 非常感谢。现在我可以使用 paginate() 并避免 php 内存错误。不幸的是,现在项目的顺序不正确。 如果您检查每张海报的 pos_log_resumenEnviado,它们的顺序是否正确? 我意识到问题在于“$q->orderBy('created_at','ASC');”是按海报的 'created_at' 排序,而不是 log 的 created_at

以上是关于如何改进我的查询以防止“PHP 致命错误:允许的内存大小”(laravel 5.2 中的排序和分页)的主要内容,如果未能解决你的问题,请参考以下文章

如何改进此 LINQ 查询以查找用户将列表中的所有技能

如何在单个查询完成执行之前锁定事务以防止出现死锁错误

如何改进表数据库设计

如何锁定 Access 数据库以防止写入

如何在保持程序化行选择的同时防止用户点击行选择?

如何改进我的地理位置查询,以免占用 8 分钟的 CPU 时间