LINQ indexВ отдельной записи

У меня есть веб-приложение MVC3 С#.Net. У меня есть следующий массив строк.

    public static string[] HeaderNamesWbs = new[]
                                       {
                                          WBS_NUMBER,
                                          BOE_TITLE,
                                          SOW_DESCRIPTION,
                                          HARRIS_WIN_THEME,
                                          COST_BOGEY
                                       };

Я хочу найти Индекс данной записи, когда в другом цикле. Я думал, что в списке будет IndexOf. Я не могу найти его. Любые идеи?

Ответ 1

Ну, вы можете использовать Array.IndexOf:

int index = Array.IndexOf(HeaderNamesWbs, someValue);

Или просто объявите HeaderNamesWbs вместо IList<string> - который все равно может быть массивом, если вы хотите:

public static IList<string> HeaderNamesWbs = new[] { ... };

Обратите внимание, что я не буду препятствовать экспорту массива как public static, даже public static readonly. Вы должны рассмотреть ReadOnlyCollection:

public static readonly ReadOnlyCollection<string> HeaderNamesWbs =
    new List<string> { ... }.AsReadOnly();

Если вы когда-нибудь захотите этого для IEnumerable<T>, вы можете использовать:

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

(+1 и -1 таковы, что он будет возвращать -1 для "отсутствует", а не 0.)

Ответ 2

Я опоздал на эту тему. Но я хотел поделиться своим решением. Джон потрясающе, но я предпочитаю простые лямбды для всего.

Вы можете расширить LINQ самостоятельно, чтобы получить то, что вы хотите. Это довольно просто сделать. Это позволит вам использовать синтаксис, например:

// Gets the index of the customer with the Id of 16.
var index = Customers.IndexOf(cust => cust.Id == 16);

Это, скорее всего, не является частью LINQ по умолчанию, поскольку оно требует перечисления. Это не просто еще один отложенный селектор/предикат.

Также обратите внимание, что это возвращает только первый индекс. Если вам нужны индексы (множественное число), вы должны вернуть IEnumerable<int> и yeild return index внутри метода. И, конечно же, не возвращаются -1. Это было бы полезно, если вы не фильтруете первичный ключ.

  public static int IndexOf<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate) {

     var index = 0;
     foreach (var item in source) {
        if (predicate.Invoke(item)) {
           return index;
        }
        index++;
     }

     return -1;
  }

Ответ 3

В правом List есть IndexOf(), просто объявите его как ILIst<string>, а не string[]

public static IList<string> HeaderNamesWbs = new List<string>
                                   {
                                      WBS_NUMBER,
                                      BOE_TITLE,
                                      SOW_DESCRIPTION,
                                      HARRIS_WIN_THEME,
                                      COST_BOGEY
                                   };

int index = HeaderNamesWbs.IndexOf(WBS_NUMBER);

MSDN: Список (из T). Метод IndexOf (T)