为了账号安全,请及时绑定邮箱和手机立即绑定

Linq:GroupBy,Sum和Count

Linq:GroupBy,Sum和Count

当年话下 2019-08-08 16:03:24
Linq:GroupBy,Sum和Count我有一系列产品public class Product {    public Product() { }    public string ProductCode {get; set;}    public decimal Price {get; set; }    public string Name {get; set;}}现在,我想根据产品代码对集合进行分组,并返回一个对象,其中包含每个代码的名称,数量或产品以及每个产品的总价格。public class ResultLine{    public ResultLine() { }    public string ProductName {get; set;}    public string Price {get; set; }    public string Quantity {get; set;}}所以我使用GroupBy按ProductCode进行分组,然后计算总和并计算每个产品代码的记录数。这是我到目前为止:List<Product> Lines = LoadProducts();    List<ResultLine> result = Lines                 .GroupBy(l => l.ProductCode)                 .SelectMany(cl => cl.Select(                     csLine => new ResultLine                     {                         ProductName =csLine.Name,                         Quantity = cl.Count().ToString(),                         Price = cl.Sum(c => c.Price).ToString(),                     })).ToList<ResultLine>();由于某种原因,总和正确完成但计数始终为1。Sampe数据:List<CartLine> Lines = new List<CartLine>();             Lines.Add(new CartLine() { ProductCode = "p1", Price = 6.5M, Name = "Product1" });             Lines.Add(new CartLine() { ProductCode = "p1", Price = 6.5M, Name = "Product1" });             Lines.Add(new CartLine() { ProductCode = "p2", Price = 12M, Name = "Product2" });样本数据的结果:Product1: count 1   - Price:13 (2x6.5)Product2: count 1   - Price:12 (1x12)产品1应该有count = 2!我尝试在一个简单的控制台应用程序中模拟这个,但我得到以下结果:Product1: count 2   - Price:13 (2x6.5)Product1: count 2   - Price:13 (2x6.5)Product2: count 1   - Price:12 (1x12)产品1:应该只列出一次...上面的代码可以在pastebin上找到:http://pastebin.com/cNHTBSie
查看完整描述

3 回答

?
青春有我

TA贡献1784条经验 获得超8个赞

我不明白第一个“带样本数据的结果”来自哪里,但控制台应用程序中的问题是您正在使用SelectMany查看每个组中的每个项目

我想你只想要:

List<ResultLine> result = Lines
    .GroupBy(l => l.ProductCode)
    .Select(cl => new ResultLine
            {
                ProductName = cl.First().Name,
                Quantity = cl.Count().ToString(),
                Price = cl.Sum(c => c.Price).ToString(),
            }).ToList();

使用First()此处获取产品名称假设具有相同产品代码的每个产品具有相同的产品名称。如评论中所述,您可以按产品名称和产品代码进行分组,如果任何给定代码的名称始终相同,则会产生相同的结果,但显然会在EF中生成更好的SQL。

我还建议你应该分别更改QuantityPrice属性intdecimal类型 - 为什么使用字符串属性显然不是文本的数据?


查看完整回答
反对 回复 2019-08-08
?
侃侃无极

TA贡献2051条经验 获得超10个赞

以下查询有效。它使用每个组来进行选择而不是SelectManySelectMany适用于每个集合中的每个元素。例如,在您的查询中,您有2个集合的结果。SelectMany获得所有结果,总共3个,而不是每个集合。以下代码适用于IGrouping选择部分中的每个代码,以使您的聚合操作正常工作。

var results = from line in Lines
              group line by line.ProductCode into g              select new ResultLine {
                ProductName = g.First().Name,
                Price = g.Sum(_ => _.Price).ToString(),
                Quantity = g.Count().ToString(),
              };


查看完整回答
反对 回复 2019-08-08
  • 3 回答
  • 0 关注
  • 1853 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信