2017-10-11 160 views
3

我有一個IEnumerable的值,我需要在開始時跳過某些元素,爲此我使用SkipWhile。但是,我絕對需要至少一個元素(因爲該序列甚至包含至少一個元素開頭)。如果所有元素都傳遞謂詞(即所有元素都被跳過),我只想得到最後一個元素。這在某種程度上可能無需昂貴的技巧,比如LINQ SkipWhile - 至少有一個

items.SkipWhile(/* my condition */).FallbackIfEmpty(items.Last()) 

(昂貴的:它需要兩次迭代的順序,我想阻止)

+0

是什麼'items'?它是一個'List ',[.Last()已經在O(1)時間運行](https://stackoverflow.com/questions/1377864/what-is-the-performance-of-the-last-extension -method-for-listt),並且你只遍歷你的列表一次 –

+0

如果你想讓它和任何謂詞一起工作,你不能繞過你的列表迭代至少一次。 –

+0

我不確定它是否更便宜,但是您可以使用IEnumerable .Reverse(),然後正常瀏覽它,返回第一個匹配項。 –

回答

5

LINQ不提供內置方法這,但你可以寫你自己的擴展。

此實現提升,在大多數情況下,從微軟的reference code

public static IEnumerable<TSource> SkipWhileOrLast<TSource>(
    this IEnumerable<TSource> source, 
    Func<TSource, bool> predicate 
) { 
    bool yielding = false; 
    TSource last = default(TSource); 
    bool lastIsAssigned = false; 
    foreach (TSource element in source) { 
     if (!yielding && !predicate(element)) { 
      yielding = true; 
     } 
     if (yielding) { 
      yield return element; 
     } 
     lastIsAssigned = true; 
     last = element; 
    } 
    if (!yielding && lastIsAssigned) { 
     yield return last; 
    } 
} 
相關問題