使用whereIn方法返回相同数组值但不同索引的多个结果

时间:2016-04-10 04:57:44

标签: laravel eloquent laravel-query-builder

$ pidArray包含产品ID,其中一些产品ID可以相同。 I.E:34 34 56 77 99 34.按原样,看起来whereIn方法不返回它已经在$ pidArray中找到的productId的结果,即使它有不同的索引。

 $productDataForOrder = Product::whereIn('id', $pidArray)->get(['id','price']);


 $totalAmount = $productDataForOrder->sum('price');

$ productDataForOrder现在包含产品数据,但仅适用于$ pidarray中的唯一ProductID。因此,当运行sum函数时,总和是错误的,因为它没有考虑同一productID的多个实例的价格。

以下代码也不会为数组中的每个产品ID返回相同的对象。因此,如果$ pidArray包含三个相同的产品ID,则查询将只返回一个包含一个对象的集合,而不是三个。

   $query = Product::select();
        foreach ($pidArray as $id)
        {
            $query->orWhere('id', '=', $id);
        }

        $productDataForOrder = $query->get(['id','price']);

        $totalAmount = $productDataForOrder->sum('price');

3 个答案:

答案 0 :(得分:2)

您无法以您尝试的方式获取重复数据。 SQL返回与where子句匹配的行。它不会因为你的where子句有重复的id而返回重复的行。

以这种方式思考可能会有所帮助:

select * from products where id in (1, 1)

相同
select * from products where (id = 1) or (id = 1)

表中只有一条记录符合条件,所以这就是你要得到的所有记录。

您将不得不在PHP中进行一些额外的处理以获得价格。你可以这样做:

// First, get the prices. Then, loop over the ids and total up the
// prices for each id.

// lists returns a Collection of key => value pairs.
// First parameter (price) is the value.
// Second parameter (id) is the key.
$prices = Product::whereIn('id', $pidArray)->lists('price', 'id');

// I used array_walk, but you could use a plain foreach instead.
// Or, if $pidArray is actually a Collection, you could use
// $pidArray->each(function ...)
$total = 0;
array_walk($pidArray, function($value) use (&$total, $prices) {
    $total += $prices->get($value, 0);
});

echo $total;

答案 1 :(得分:0)

whereIn方法仅将结果限制为给定数组中的值。来自文档:

  

whereIn方法验证给定列的值是否包含在给定数组

Id创建一个查询变量并遍历数组,在每次传递中添加查询变量。像这样:

$query = Product::select();

foreach ($pidArray as $id)
{
    $query->where('id', '=', $id);
}

$query->get(['id','price']);

答案 2 :(得分:0)

这是一个适用于扩展@patricus的用例的代码 您首先从product表

中获取一个key数组作为id和value作为price
$prices = Product::whereIn('id', $pidArray)->lists('price', 'id');

$totalPrice = collect([$pidArray])->reduce(function($result, $id) use ($prices) {

      return $result += $prices[$id];

}, 0);