Получить элемент в List<T> из индекса, но зациклиться на списке

Если бы у меня был список

List<string> fruits = new List<string>(){"apple", "pear", "banana"}

как я мог изменить

int i = 0;
while(true)
{
    Console.WriteLine(fruits[i]);
    i++;
}

выводить

apple
pear
banana
apple
pear
banana
...

вместо того, чтобы делать исключение индекса вне диапазона, когда мы достигаем конца списка?

В моем реальном коде у меня сотни списков разного размера. У меня есть таймер, который вызывает метод через равные промежутки времени, и метод должен возвращать одно значение из каждого списка, гарантируя, что в конечном итоге все элементы в каждом списке будут возвращаться одинаково часто.

Поскольку i со временем станет очень большим, приведенное ниже решение не является оптимальным.

int i = 0;
while(true)
{
    int a = i;
    while(a > fruits.Count)
    {
        a -= fruits.Count;
    }
    Console.WriteLine(fruits[a]);
}

Вот мой фактический код, который нужно исправить:

private static int _purgeNumber;
private static async Task<List<AutopurgeRow>> GetRowsToPurgeAsync()
{
    List<AutopurgeRow> rows = await Database.Data.Autopurge.GetRowsAsync(enabledOnly: true);

    List<AutopurgeRow> rowsToPurge = new List<AutopurgeRow>();
        foreach (SocketGuild guild in _client.Guilds)
        {
            if (rowsToPurge.Count(x => x.GuildId == guild.Id) == 0)
            {
                List<AutopurgeRow> guildRows = rows.Where(x => x.GuildId == guild.Id).OrderBy(x => x.ChannelId).ToList();
                AutopurgeRow row = guildRows[_purgeNumber % guildRows.Count];
                rowsToPurge.Add(row);
            }
        _purgeNumber++;
        if (_purgeNumber == int.MaxValue) _purgeNumber = 0;
    }

    return rowsToPurge;
}

@CamiloTerevinto Как указано в моем вопросе, он должен работать с несколькими списками с одним значением i.

230Daniel 23.12.2020 10:38
i = (i + 1) % fruits.Count
canton7 23.12.2020 10:38

«Решение должно работать с несколькими списками разного размера» — не совсем понятно, что вы имеете в виду. Можете ли вы отредактировать свой вопрос, включив в него пример кода, демонстрирующий вашу реальную проблему, а не использовать более простой пример кода и расплывчатое утверждение о том, насколько ваша реальная проблема сложнее?

canton7 23.12.2020 10:39

почему вы не используете цикл for?

Cagri D. Kaynar 23.12.2020 10:39

@canton7 Приношу свои извинения, я отредактировал, чтобы было понятнее.

230Daniel 23.12.2020 10:41

Все еще недостаточно ясно, предоставьте пример кода вашего случая

MichaelMao 23.12.2020 10:42

@ 230Daniel Итак, если у вас есть несколько списков, не заставляйте все примеры использовать один список, потому что все, что мы можем предположить, это то, что у вас есть разные списки, которые передаются одному методу.

Camilo Terevinto 23.12.2020 10:43

Хорошо, в вашем реальном коде вы уже используете % вместо цикла while. Есть ли еще конкретный баг? (Возможно, вам следует перейти к описанию общей проблемы и спрашивать о наилучшем способе ее решения в любом случае.)

Ry- 23.12.2020 10:51

@Ry- Да. Мне удалось убедить себя, что метод % почему-то не работает. Код, с которым у меня возникли проблемы, является более сложной версией приведенного выше, но он должен работать очень похожим образом. Я только что протестировал базовый код выше, и он работал отлично, я полагаю, что у меня должна быть какая-то другая странная ошибка, которую я могу найти. Спасибо за ответ, это будет полезно для других, столкнувшихся с этим.

230Daniel 23.12.2020 10:53
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
3
9
53
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий
int a = i;
while (a > fruits.Count)
{
    a -= fruits.Count;
}

Более эффективный способ сделать это (и более правильный, поскольку > должен быть >=) — взять остаток от деления i на fruits.Count с помощью оператора %:

int a = i % fruits.Count;

Другие вопросы по теме