如何将列表的子集添加到另一个列表中的对象的属性-最佳/最快的做法
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了如何将列表的子集添加到另一个列表中的对象的属性-最佳/最快的做法相关的知识,希望对你有一定的参考价值。
我试图找到一种基于键属性从列表中选择项的子集并将该子集(列表)分配给另一个列表中项的属性的最快,最高效的方法。性能方面很重要,因为这部分代码将在每个工作日被频繁调用。我用滴答声衡量了性能,以清楚地看到相对差异。
我有两个列表(设置示例);
List<CategorySetting> catList;
List<Customer> custList;
CategorySetting
实体具有称为SettingsId
的属性。 Customer
实体也具有SettingsId
属性,实际上这是从Customers
到CategorySetting
的外键。
我编写的第一段代码是最直接的;
// normal for each: 13275 ticks foreach (var catItem in catList) catItem.Customers = custList.Where(c => c.SettingsId == catItem.SettingsId).ToList();
这大约需要13275个刻度。
然后我想也许使用并行处理会更快一些?所以我写了这段代码;
// parallel for each: 82541 ticks Parallel.ForEach(catList, catItem => catItem.Customers = custList.Where(c => c.SettingsId == catItem.SettingsId).ToList(); );
这花了更长的时间; 82541滴答声。由于这种方法的并行性,这对我来说毫无意义。它应该使用多个线程来执行此操作,因此理论上应该更快。然后我开始怀疑,如果多个线程尝试同时访问客户列表,将会发生什么情况。这可能会导致锁和队列,从而由于开销而花费更多时间?与写入主列表相同。
我尝试了另一种方法。我为catList(主列表)设置了ConcurrentBag
。
ConcurrentBag<CategorySettings> csBag = new ConcurrentBag<CategorySettings>(catList);
我将清单列表插入已经由
ConcurrentDictionary
分组的SettingsId
。
var dict = custList.GroupBy(c => c.SettingsId).ToDictionary(x => x.Key, y => y.ToList()); ConcurrentDictionary<int?, List<Customer>> concDict = new ConcurrentDictionary<int?, List<Customer>>(dict);
最后的尝试是这样的:
// paralell, bag, concurrent dictionary: 40255 Parallel.ForEach(caBag, ca => concDict.TryGetValue(ca.SettingsId, out var selCust); ca.Customers = selCust; );
这将需要40255个滴答声。谁能解释为什么这仍然需要更长的时间?更重要的是,除了“只是” foreach循环外,没有别的方法了吗?感觉就像我在这里丢失了一些东西。
任何想法都将不胜感激!
我试图找到一种基于键属性从列表中选择项的子集并将该子集(列表)分配给另一个列表中项的属性的最快,最高效的方法。 ...
您可以尝试使用ToLookup
LINQ方法:
以上是关于如何将列表的子集添加到另一个列表中的对象的属性-最佳/最快的做法的主要内容,如果未能解决你的问题,请参考以下文章
更正SQL“JOIN”以从主列表创建子集 - 一个表中的id字段到另一个表中的id和标题#VB / C#