2015-10-19 30 views
3

我在使用API​​,我無法控制哪個返回來自SQL Server的數據,因爲它是List<string>,每個字符串都有以逗號分隔的列分離。Linq - 如何通過'let'值進行分組,然後求和'let'值

這特定的數據集被返回作爲varchardatetime像這樣:

{ 
    "Prefix_IdentifierA,1/1/1900 12:30:00 AM,", 
    "Prefix_IdentifierA,1/1/1900 12:15:00 AM,", 
    "Prefix_IdentifierB,1/1/1900 01:00:00 AM,", 
    "Prefix_IdentifierB,1/1/1900 12:45:00 AM," 
} 

datetime僅表示一個時間,因此,所有日期的是相同的。

我需要將其轉換成對象的集合,每個標識符的總時長:

public class Log 
{ 
    public string Identifier { get; set; } 

    public int DurationInSeconds { get; set; } 
} 

所以結果集合應該是這樣的:

{ 
    Log { Identifier = "IdentifierA", DurationInSeconds = 45 }, 
    Log { Identifier = "IdentifierB", DurationInSeconds = 105 } 
} 

目前我在做這個在2個Linq查詢中:

1)從每行提取IdentifierDurationInSeconds

var logs1 = (from row in rows 
      select row.Split(',') 
      into columns 
      let identifier = columns[0].Replace("Prefix_", string.Empty) 
      let duration = DateTime.Parse(columns[1]) 
      let durationInSeconds = duration.Hour * 3600 + duration.Minute * 60 + duration.Second 
      select new { Identifier = identifier, DurationInSeconds = durationInSeconds }).ToList(); 

2)通過Identifier和總和DurationInSeconds分組:

var logs2 = (from log in logs1 
      group log by log.Identifier 
      into grouping 
      orderby grouping.Key 
      select new Log { Identifier = grouping.Key, DurationInSeconds = grouping.Sum(log => log.DurationInSeconds) }).ToList(); 

來自第一查詢匿名類型是一樣的Log對象,以便有任何方法對這些2次的查詢合併爲一個?

編輯:我迄今取得的進展

我已經identifier儘可能分組拿到,但不能工作如何再拿到durationInSeconds的總和:

var logs = (from row in rows 
      select row.Split(',') 
      into columns 
      let identifier = columns[0].Replace("Prefix_", string.Empty) 
      let duration = DateTime.Parse(columns[1]) 
      let durationInSeconds = duration.Hour * 3600 + duration.Minute * 60 + duration.Second 
      group rows by identifier 
      into grouping 
      select new { Identifier = grouping.Key, DurationInSeconds = grouping.Sum(?????) }).ToList(); 
+0

嘿,我未刪除我的帖子。我不確定它是否滿足您的問題(至少部分)。 – Kapol

+0

@Kapol - 謝謝,我已經編輯過,並會對你的回答發表評論 – Shevek

回答

4

您可以通過identifier組返回IGrouping<IEnumarable<T>>,這樣你就可以獲取從這個標識是什麼,但Key,接下來你可以再次投影IEnumarable介紹每個標識和解析duration變量存在本身。請注意,在分組數據之前不需要存儲它。

這個查詢應該正常工作對您: -

var logs = (from row in rows 
      select row.Split(',') into columns 
      let identifier = columns[0].Replace("Prefix_", string.Empty) 
      group columns by identifier into g 
      select new Log { 
        Identifier = g.Key, 
        DurationInSeconds = (from dur in g 
             let duration = DateTime.Parse(dur[1]) 
             select duration.Hour * 3600 + duration.Minute * 60 
               + duration.Second).Sum() 
          }).ToList(); 
+1

它確實,真棒! – Shevek

1

如何組合查詢語法與方法語法?

(...)select new { Identifier = identifier, DurationInSeconds = durationInSeconds }).GroupBy(l => l.Identifier)(...) 
+0

這個方法很有效,但是我很想知道是否只有linq答案。對於那些有興趣的,這裏是實際完整的Lambda工作:'.GroupBy(log => log.Identifier).Select(grouping => new Log {Identifier = grouping.Key,DurationInSeconds = grouping.Sum(log => log.DurationInSeconds)})。ToList();' – Shevek