You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Laravel 8中从HasMany关联仅取子模型数据及求和方法

Laravel关联查询优化:大表下获取最新价格总和的问题与解决

表关联与基础查询实现

我有两个MySQL表,通过HasMany/belongsTo关联,关联代码如下:

public function Products()
{
    return $this->hasMany(Prices::class, 'product_id');
}

public function Prices()
{
    return $this->belongsTo(Products::class);
}

通过以下关联方法可获取每个产品的最新价格:

public function LatestPrices()
{
    return $this->hasOne(Prices::class, 'product_id')->orderBy('date','desc');
}

在控制器中可通过foreach循环访问数据:

$values = Products::with('LatestPrices')->get();
foreach ($values as $value) {
  // 业务逻辑
  echo $value->LatestPrices->price;
}

问题

  1. 能否仅获取价格数据,得到仅包含价格的数组?
  2. 能否不通过foreach循环,直接计算所有产品最新价格的总和?

解决方案(针对200万+行的大表场景)

我是Laravel新手,习惯用原生PHP+MySQL,原本想把原生内连接查询转成Eloquent实现,但在200万+行的数据表中,Eloquent查询速度很慢。

原生SQL查询(性能基准)

原生查询语句如下:

SELECT SUM(a.sells_value) AS value FROM prices a 
INNER JOIN products b ON a.product_id = b.id 
INNER JOIN ( SELECT product_id, MAX(prices.date) as Max_date FROM prices GROUP BY product_id ) c 
ON a.product_id = c.product_id AND a.date = c.Max_date 
AND ((b.merchand = 1 and b.product_tag = "Something") or (b.merchand = 1 and b.product_tag = "Something"));

他人提供的Eloquent方案(性能不佳)

有人提供了Eloquent实现方案,虽然能得到正确结果,但耗时是foreach循环的4倍:

Products::where([['merchand','=',1],['product_tag','=', 'Something']])
        ->orWhere([['merchand','=',1],['product_tag','=', 'Something']])
        ->with('LatestPrices')
        ->get()
        ->pluck('LatestPrices.prices')
        ->sum();

最终最优方案:使用DB::select执行原生SQL

最终测试发现,用DB::select执行原生SQL的速度远快于foreach循环和普通Eloquent方案:

DB::select('SELECT SUM(a.sells_value) AS value FROM prices a 
INNER JOIN products b ON a.product_id = b.id 
INNER JOIN ( SELECT product_id, MAX(prices.date) as Max_date FROM prices GROUP BY product_id ) c 
ON a.product_id = c.product_id AND a.date = c.Max_date 
AND ((b.merchand = 1 and b.product_tag = "Something") or (b.merchand = 1 and b.product_tag = "Something"))');

内容的提问来源于stack exchange,提问作者Mohammed

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.27 18:13:25