2013-07-24 55 views
0

最後一天,我已經有了對象的列表這樣LINQ選擇當某些條件得到滿足

MyObject 
    .StartDate 
    .EndDate 
    .Number 

我需要知道什麼時候是最後一天數字的總和是超過一定的數量。 如果數字介於StartDate和EndDate之間,該數字將僅輸入當天的總和。

var list = List<MyObject>(); 

from list 
    where (list.Sum(x => x.Number) > 100) 
    select lastdate 

LINQ可以嗎?

+0

lastdate會是Max(EndDate/StartDate)不是嗎? –

+0

lastdate應該是數字總和高於100的最後一天。 但是,如果數字在StartDate和結束日期之間,該數字將只輸入當天的總和。 –

回答

4

假設該列表是爲了:

var list = List<MyObject>(); 

var lastDate = list.First(item => list.Where(l => l.EndDate <= item.EndDate) 
             .Sum(x => x.Number) > 100 
         ) 
        .EndDate 

如果不只是添加訂單:

var list = List<MyObject>(); 

var lastDate = list.OrderBy(item => item.EndDate) 
        .First(item => list.Where(l => l.EndDate <= item.EndDate) 
             .Sum(x => x.Number) > 100 
         ) 
        .EndDate 

但是你重新掃描每個項目的循環。使用簡單循環將會更高效:

DateTime endDate; 
int total; 
foreach(var item in list.OrderBy(item => item.EndDate)) 
{ 
    total += item.Number; 
    if(total > 100) 
    { 
     endDate = item.EndDate; 
     break; 
    } 
} 
+0

該列表未訂購。日期完全是隨機的。 我需要滿足條件的最後一天。 –

+0

@ user2496899然後,只需先訂購 - 查看更新後的答案 –

+0

我喜歡簡單的循環版本,它更清晰地表明您正在嘗試執行的操作,正如您所說的,它比嘗試實施單線解決方案更爲高效。人們經常會陷入這樣的概念:他們**有**使用某種技術,或者認爲一行解決方案更好,只是因爲閱讀的代碼較少。 – akousmata

1

您可能需要額外的屬性才能完成此操作。不知道如何做到這一點的一條線LINQ聲明:

public class MyObjectWithSum 
{ 
    public DateTime StartDate {get;set;} 
    public DateTime EndDate {get;set;} 
    public int Number {get;set;} 
    public int SumAsOfEndDate {get;set;} 
} 

var list = new List<MyObjectWithSum>(); 

foreach(var item in list) 
{ 
    item.SumAsOfEndDate = list.Sum(x => x.Number).Where(y => y.EndDate <= item.EndDate); 
} 

list.OrderBy(x => x.EndDate).First(x => x.SumAsOfEndDate > 100).EndDate; 
+0

對不起,我無法添加其他屬性。我正在從數據庫中的對象開始工作。 –

+0

@D斯坦利的解決方案應該可以工作,雖然我沒有測試過它,但是在orderby中添加他的解決方案非常簡單。 – akousmata

1
var result = items.Where(t => items.SkipWhile(tt => tt.EndDate != t.EndDate) 
    .Sum(tt => tt.Number) > 100).First().EndDate; 
0
 var lastdate = list.OrderByDescending(l => l.EndDate) 
     .First(l => 
      list.Where(s => s.StartDate <= l.EndDate && l.EndDate <= s.EndDate) 
      .Sum(s => s.Number) > 100).EndDate; 

我們並不需要檢查的任何日期,因爲總和的變化由改變ENDDATE決定。

所以:

  • 排序列表按降序結束日期順序,因爲我們只需要最後日期。
  • 搜索先打了哪些數字的總和是高於100:
    • 創建這之前已經開始和結束或結束日期後
    • 總和的所有數字
    • 的所有物品的清單

通過這種方式可以防止不必要的迭代,並且可能會在稍後檢查的日期之後啓動的項目被忽略。