2010-11-02 8 views

Respuesta

22

que iba a necesitar más de contexto, pero si usted acaba de entrar un índice para que pueda llamar .Skip, recomiendo echar un vistazo a .SkipWhile .

Si realmente necesita el índice, le sugiero que escriba su propio método de extensión .IndexOf.

+0

+1 por mencionar que probablemente quiera usar 'SkipWhile', porque encontrar el índice y luego llamar a 'Skip' enumera la consulta dos veces – Gabe

+0

Tan cerca ... ahora quiero usar SkipWhile junto con un contador, es decir, una lista. SkipWhile (myBusinessLogicCondition && list.Count - SkipIndex> someXnumber); – user494352

+0

user494352: Parece que quieres ver la 'lista.del.Presidente de Jon (Seleccionar) SkipWhile()' al final de su publicación. – Gabe

6

Puede proyectar los elementos de la lista con sus índices primera:

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

Claro, es bastante fácil:

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

Eso devolverá el índice si encuentra algo que coincida, o -1 en caso contrario. El +1 y -1 es para obtener el comportamiento para el caso donde no hay coincidencias. Si supieras que siempre habría un partido, sería más simple:

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

Si usted es feliz para obtener el resto de la lista a partir de ese punto en adelante, SkipWhile es sin duda su amigo, como se ha mencionado por Chris . Si desea que el resto de la lista y el índice original, que también es fácil:

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

qué le dará una secuencia de pares { value, index } del primer valor a juego SomeCondition.

+1

Es una pena que 'FirstOrDefault' no le permite especificar el valor por defecto, ¿eh? – Gabe

+0

@Gabe: Sí :(Es cierto que sería fácil escribir tu propia implementación ... –

+0

Gracias Jon, estoy tratando de incorporar SkipWhile con un índice, en lugar de contar para ver si me salté demasiado. – user494352

14

Por supuesto su posible uso de 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; 
     } 
    } 
+1

+1. Normalmente prefiero respuestas más parecidas a las de Jon, pero en este caso esta solución es mucho más fácil de ver y comprender. Y como método de extensión todavía se puede * usar * en una expresión linq. Ganar-ganar –

+0

No es necesario usar 'matchCondition.Invoke (item)'. Puedes hacer 'matchCondition (item)'. – ErikE

24

Si realmente sólo tiene el primer índice luego contar los que no coinciden:

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