C#中如何用LINQ GroupBy对产品数组统计次数并取Top3?
用C# LINQ处理JSON数组分组统计的实现方案
嘿,这个需求其实挺典型的,咱们一步步来搞定它。首先得明确核心问题:因为product是数组/列表(引用类型),直接用它做分组键会因为引用不同导致内容相同的数组被分到不同组,所以得先把数组转换成内容可比较的类型,再进行分组统计。
步骤1:定义实体类映射JSON结构
首先我们需要一个类来对应JSON里的每个对象,方便反序列化:
public class ProductEntry { public List<string> Product { get; set; } }
步骤2:反序列化JSON数据
这里我用.NET自带的System.Text.Json来反序列化(你也可以用Newtonsoft.Json,逻辑类似):
using System.Text.Json; // 你的原始JSON数据 string jsonData = @"[ { ""product"": [ ""a"", ""b"", ""c"" ] }, { ""product"": [ ""a"",""b"" ] }, { ""product"": [ ""b"",""c"" ] }, { ""product"": [ ""b"", ""c"" ] }, { ""product"": [ ""a"",""b"" ] }, { ""product"": [ ""b"", ""c"" ] }, { ""product"": [ ""a"" ] } ]"; // 反序列化为List<ProductEntry> var productEntries = JsonSerializer.Deserialize<List<ProductEntry>>(jsonData);
步骤3:LINQ分组、统计、排序、取前3
这是核心部分,重点是把Product列表转换成唯一标识内容的字符串(用逗号拼接)作为分组键,这样内容相同的数组会被分到同一组:
using System.Linq; var result = productEntries // 分组:用拼接后的字符串作为键,确保内容相同的数组被归为一组 .GroupBy(entry => string.Join(",", entry.Product)) // 统计每组的次数,同时保留原数组内容 .Select(group => new { ProductItems = group.First().Product, // 取组内第一个的Product数组(内容都一样) Count = group.Count() }) // 按次数降序排序,次数相同的话可以按数组内容升序排(可选) .OrderByDescending(item => item.Count) .ThenBy(item => string.Join(",", item.Product)) // 取前3组 .Take(3);
步骤4:输出结果
遍历结果展示你要的格式:
foreach (var item in result) { // 把数组转成带引号的字符串格式,比如"b","c" string productStr = string.Join("\",\"", item.ProductItems); Console.WriteLine($"\"{productStr}\" {item.Count}"); }
运行结果
针对你提供的JSON数据,输出会是:
"b","c" 3
"a","b" 2
"a","b","c" 1
(如果要把"a"排在第三,调整ThenBy为ThenByDescending即可,或者根据你的需求自定义排序逻辑)
补充说明
如果你不想用字符串拼接做分组键,也可以自定义一个IEqualityComparer<List<string>>来实现列表内容的比较,不过对于这个场景来说,字符串拼接已经足够简单高效了。
内容的提问来源于stack exchange,提问作者aliceangel
相关产品推荐
相关产品推荐

