2015-06-10 57 views
0

我正在为汽车制造商,模型和引擎等从月体数据的相关集合中创建4或5个级别的这种树数据结构。它需要长达一分钟尽管如此。有没有更快的方法做到这一点?提高linq构建的树形数据结构的性能

var carData = (from manufacturer in manufacturerMonths.Select(m => m.Manufacturer).Distinct() 
        select new 
        { 
         ManufacturerData = (from manufacturerMonth in manufacturerMonths 
         .Where(t => t.Manufacturer == manufacturer) 
         select new 
         { 
          Date = manufacturerMonth.Date, 
          Volume = manufacturerMonth.Volume, 
          Models = new 
          { 
           ModelsData = (from model in modelMonths 
           .Where(m => m.Manufacturer == manufacturer) 
           .Select(m => m.Model).Distinct()                                        
            select new                                        
            { 
            ModelData = (from modelMonth in modelMonths 
            .Where(m => m.Model == model)                        
             select new 
             { 
              Date = modelMonth.Date, 
              Volume = modelMonth.Volume, 
              Engines = new  
              { 
               EnginesData = (from engine in engineMonths 
               .Where(e => e.Model == model) 
               .Select(e => e.Engine).Distinct() 
                select new 
                { 
                EngineData = .... 
                } 
              } 
             } 
            } 
          } 
         } 
        } 
       } 
+0

“manufacturerMonths”中有多少个对象?如果您尝试将所有这些东西写入单独的操作中,哪些操作花费最多时间?您还可以使用探查器来剖析代码以获取最耗时的代码 –

+0

'modelMonth'是什么类型? 'engineMonths'? 'manufacturerMonths'? –

回答

0

这么多LINQ的:o

恕我直言,尝试用类层次结构与 “具有” 继承。

LINQ是懒惰初始化的,并且会花费您的性能开销。 请参阅:Is a LINQ statement faster than a 'foreach' loop?

如果您可以编写自己的自定义代码以迭代List,在某些情况下可以分解循环(如果这对于您的设计来说确实可行)。这会有点痛苦,但是在更长的时间内它会给你带来好处。

此外,代码将更容易调试,如果LINQ使用“新”(匿名)对象进行深入处理,将会很慢并且很难检查是否有什么东西远离预期。

1

对每个外部语句项执行内部linq语句。这就像嵌套的foreach循环。所以请确保你不会一遍又一遍地处理相同的数据。当使用字典时,它可以提高性能:

例如, (只是为了显示我的意思,不要杀我,如果它是错的...)

而不是

          EnginesData = (from engine in engineMonths 
              .Where(e => e.Model == model) 
              .Select(e => e.Engine).Distinct() 
               select new 
               { 
               EngineData = .... 
               } 

创建字典开头:

Dictionary<Model, Engine[]> modelToEnginesDict = engineMonths 
    .GroupBy(e => e.Model) 
    .ToDictionary(
    x => x.Key, 
    x => x.Select(e => e.Engine).Distinct().ToArray()) 

,并用它在linq语句中:

EnginesData = (from engine in modelToEnginesDict[model] 
    select new 
    { 
    EngineData = .... 
    } 

与此同时,您将巨大的查询拆分成更小的块,它们执行一些预处理唱数据。

+0

如果你还活着,那么它一定是正确的:) –