我的产品有两个表,一个与主仓相关,另一个与小商店有关。两个表都保留了产品数量。
tblWareHouse
-----------------------------------
ProductID ProductSeries Amount
1 600 80
1 601 50
2 300 90
tblStore
-----------------------------------
ProductID ProductSeries Amount
1 700 20
1 601 40
2 400 10
每个产品都有唯一的ProductSeries编号。我需要加入并对这两个表进行分组,并按照ProductID为两个仓库和商店获得数量的产品总和,如下所示:
Output
------------------------------------------
ProductID StoreAmount WareHouseAmount
1 60 130
2 10 90
我的代码是这样的:
var q = from d in db.tblWareHouses
join s in db.tblStores on d.ProductID equals s.ProductID
group new { d, s } by d.ProductID into v
select new
{
ID = Convert.ToInt32(v.Key),
WareHouseAmount = v.Sum(x => x.d.Amount),
StoreAmount = v.Sum(x => x.s.Amount),
};
但是有一个问题,它会产生额外的输出行,同时总结它会给我更多的数量。例如,对于仓库中的ProductID 1,它将在连接中生成3行存储,而在求和时,它将对所有额外行进行求和。我需要删除重复的。希望我足够清楚。如何解决?
答案 0 :(得分:1)
由于每个表中的总和,我能够通过将总和分成单独的查询来实现:
var q1 = tblWareHouses.AsEnumerable()
.GroupBy(r => r.ProductID)
.Select(a => new
{
ProductID = a.Key,
Amount = a.Sum(r => r.Amount)
}).ToList();
var q2 = tblStores.AsEnumerable()
.GroupBy(r => r.ProductID)
.Select(a => new
{
ProductID = a.Key,
Amount = a.Sum(r => r.Amount)
}).ToList();
var q3 = (from d in q1
join s in q2 on d.ProductID equals s.ProductID
group new {d, s} by d.ProductID
into v
select new
{
ID = v.Key,
WareHouseAmount = v.Sum(x => x.d.Amount),
StoreAmount = v.Sum(x => x.s.Amount),
}).ToList();
<强>输出:强>
答案 1 :(得分:0)
加入很可能像具有相同ProductID的行之间的笛卡尔连接一样工作,因此会产生错误的结果。我会尝试放弃加入和分组,而是使用Zip()
。它从两个集合连接中获取相应的行,然后与新结果一起使用。它远非理想的解决方案,因为它很可能会评估计算机的内存。我认为你可以用sql避免这种情况,但是每个表都需要首先投射到包含行号的集合(即使用RANK
函数),然后连接需要在这个行号上。