使用LINQ查找与条件匹配的元素的第一个索引

时间:2010-11-02 06:16:19

标签: c# linq

var item = list.Where(t => somecondition);

我希望能够找到返回的元素的索引,事实上,在我的情况下,我想要的只是一个索引,这样我就可以将.Skip()放到列表中了。 / p>

有没有办法在IEnumerable中执行此操作?我讨厌为此使用List<T>,但确实有FindIndex()方法

7 个答案:

答案 0 :(得分:42)

当然,这很简单:

var index = list.Select((value, index) => new { value, index = index + 1 })
                .Where(pair => SomeCondition(pair.value))
                .Select(pair => pair.index)
                .FirstOrDefault() - 1;

如果找到匹配的内容,则返回索引,否则返回-1。 +1和-1是为了获得没有匹配的情况的行为。如果你知道总会有匹配,那就更简单了:

var index = list.Select((value, index) => new { value, index })
                .Where(pair => SomeCondition(pair.value))
                .Select(pair => pair.index)
                .FirstOrDefault();

如果你很高兴从那时开始获得列表的其余部分,SkipWhile肯定是你的朋友,正如克里斯所提到的那样。如果想要列表的其余部分原始索引,那也很容易:

var query = list.Select((value, index) => new { value, index })
                .SkipWhile(pair => !SomeCondition(pair.value))

这将为您提供第一个匹配{ value, index }的值的SomeCondition对序列。

答案 1 :(得分:37)

如果您真的只需要第一个索引,那么请计算那些不匹配的索引:

var index = list.TakeWhile(t => !someCondition).Count()

答案 2 :(得分:26)

我需要更多上下文,但如果您只是获取索引以便拨打.Skip,我建议您查看.SkipWhile

如果您确实需要索引,我建议您编写自己的.IndexOf扩展方法。

答案 3 :(得分:17)

当然可以使用IEnumerable ......

 public static class EnumerableExtension
    {

        public static int FirstIndexMatch<TItem>(this IEnumerable<TItem> items, Func<TItem,bool> matchCondition)
        {
            var index = 0;
            foreach (var item in items)
            {
                if(matchCondition.Invoke(item))
                {
                    return index;
                }
                index++;
            }
            return -1;
        }
    }

答案 4 :(得分:8)

您可以首先使用索引投影列表项:

var item = list.Select((item, index) => new { Item = item, Index = index })
               .Where(pair => SomeCondition(pair.Item))
               .Select(result => result.Index);

答案 5 :(得分:0)

如果您知道自己有一个列表,而不是IEnumerbale或IQueryable之类的列表,那可能很好...

public static int IndexOf<T>(this IList<T> source, Func<T, bool> condition)
{
    for (int i = 0; i < source.Count; i++)
        if (condition(source[i]))
            return i;

    return -1;
}

答案 6 :(得分:0)

关于Jon Skeet的答案,可以在调用FirstOrDefault之前使用DefaultIfEmpty(),而无需在索引中进行加减。

   var index = list.Select((value, index) => new { value, index })
                .Where(pair => SomeCondition(pair.value))
                .Select(pair => pair.index).DefaultIfEmpty(-1)
                .FirstOrDefault();