Я пытаюсь найти ошибку в нашем коде. Я отложил его до фрагмента ниже. В приведенном ниже примере у меня есть сетка ints (список строк), но я хочу найти индексы столбцов, у которых есть 1. Реализация этого заключается в создании перечислителя для каждой строки и переходе через каждый столбец в поверните, удерживая счетчики в шаге.
class Program
{
static void Main(string[] args)
{
var ints = new List<List<int>> {
new List<int> {0, 0, 1}, // This row has a 1 at index 2
new List<int> {0, 1, 0}, // This row has a 1 at index 1
new List<int> {0, 0, 1} // This row also has a 1 at index 2
};
var result = IndexesWhereThereIsOneInTheColumn(ints);
Console.WriteLine(string.Join(", ", result)); // Expected: "1, 2"
Console.ReadKey();
}
private static IEnumerable<int> IndexesWhereThereIsOneInTheColumn(
IEnumerable<List<int>> myIntsGrid)
{
var enumerators = myIntsGrid.Select(c => c.GetEnumerator()).ToList();
short i = 0;
while (enumerators.All(e => e.MoveNext())) {
if (enumerators.Any(e => e.Current == 1))
yield return i;
i++;
if (i > 1000)
throw new Exception("You have gone too far!!!");
}
}
}
Однако я заметил, что MoveNext()
не запоминается каждый раз вокруг цикла while
. MoveNext()
всегда возвращает true, а Current
- всегда 0. Является ли это целенаправленной особенностью Linq, чтобы сделать его более свободным от побочных эффектов?
Я заметил, что это работает:
private static IEnumerable<int> IndexesWhereThereIsOneInTheColumn(
IEnumerable<List<int>> myIntsGrid)
{
var enumerators = myIntsGrid.Select(c =>
c.ToArray().GetEnumerator()).ToList(); // added ToArray()
short i = 0;
while (enumerators.All(e => e.MoveNext())) {
if (enumerators.Any(e => (int)e.Current == 1)) // added cast to int
yield return i;
i++;
}
}
Так это просто проблема со списком?