Планирование загрузки с помощью алгоритма циклического перебора?

Мне нужно написать алгоритм циклического перебора, чтобы запланировать загрузку на n конечных точек?

Итак, если у меня есть серверы A, B и C

Я хотел убедиться, что они циклически перебираются для каждого запроса, который я получаю. Как это сделать на С#?


person Nevin Mathai    schedule 21.04.2010    source источник
comment
Будет ли это постоянная нагрузка или вы хотите равномерно распределять нагрузку?   -  person Avitus    schedule 21.04.2010
comment
Я думаю, что «циклический перебор» указывает на отсутствие попытки равномерно распределить нагрузку.   -  person Henk Holterman    schedule 21.04.2010


Ответы (3)


Для справки, определение циклического перебора:

http://en.wikipedia.org/wiki/Round-robin_scheduling

Просто используйте очередь. Снимите один с верхней части, используйте его и положите обратно. Это гарантирует, что последнее использованное всегда будет выбрано последним.

Queue<Server> q = new Queue<Server>();

//get the next one up
Server s = q.DeQueue();


//Use s;


//put s back for later use.
q.Enqueue(s);

Ссылка на класс очереди:

http://msdn.microsoft.com/en-us/library/7977ey2c.aspx

person kemiller2002    schedule 21.04.2010
comment
Я бы бросил вызов человеку, который сказал, что хочет внедрить циклический перебор, чтобы выяснить, действительно ли он имеет в виду циклический перебор. - person Tim; 21.04.2010
comment
Он постоянно используется для распределения нагрузки на сервер. - person kemiller2002; 21.04.2010
comment
При использовании этого шаблона может быть целесообразно немедленно поставить сервер в очередь перед его использованием (или поместить очередь в блок finally). Таким образом, любые исключения, возникающие при использовании сервера, не приведут к полному удалению сервера из ротации. - person bvoyelr; 16.09.2015
comment
это должно быть завернуто в класс - person JJS; 03.06.2016
comment
Разве связанный список не будет лучше, чем очередь? не нужно повторно ставить элементы в очередь, просто перезапустите из головы :) - person VisualBean; 25.09.2017

Та же идея, что и у ebpower, но основное внимание уделяется следующему элементу, а не индексу следующего элемента.

public class RoundRobinList<T>
{
    private readonly IList<T> _list;
    private readonly int _size;
    private int _position;

    public RoundRobinList(IList<T> list)
    {
        if (!list.Any())
            throw new NullReferenceException("list");

        _list = new List<T>(list);
        _size = _list.Count;            
    }

    public T Next()
    {
        if (_size == 1)
            return _list[0];

        Interlocked.Increment(ref _position);
        var mod = _position % _size;
        return _list[mod];
    }
}
person Joseph Simpson    schedule 03.06.2013
comment
передать IEnumerable‹T› в конструктор и записать мод до Incrementing _position, а это деньги. - person JJS; 03.06.2016
comment
Interlocked.Increment достигнет int.MaxValue в сценариях с очень высокой нагрузкой. В этом случае он обрабатывает состояние переполнения и возвращает int.MinValue в соответствии с documentation, и этот код выдаст System.ArgumentOutOfRangeException при доступе к массиву из-за отрицательного индекса. С этим справится простая проверка: `... Interlocked.Increment(ref _position); if(_position == Int32.MinValue) { Interlocked.Exchange(ref _position, 0); } ... ` - person SalvatoreGarrubba; 20.01.2020

Если доступ к вашим конечным точкам осуществляется через список или массив, вам нужно только увеличивать индекс циклическим образом:

public class RoundRobinIndex
{
    volatile int index = 0;
    int count;

    public int Next
    {
        get
        {
            if (index == count)
            {
                index = 0;
            } 
            return index++;
        }
    }

    public RoundRobinIndex(int countArg)
    {
        count = countArg;
    }
}
person Ed Power    schedule 21.04.2010
comment
Использование этого вызовет исключение IndexOutOfRangeException. - person IBootstrap; 21.08.2013
comment
@IBootstrap - не вызывает исключения IndexOutOfRangeException. Вы действительно проверяли это? - person Ed Power; 11.07.2014
comment
Следующее также может быть достигнуто с помощью: (index + 1) % count; - person Aerokneeus; 26.10.2015