Como implemento meu próprio cenário avançado de produtor / consumidor?

NOTA:
fiz um retrabalho completo da minha pergunta. você pode ver a pergunta original através do histórico de alterações.

estou precisando de uma fila "poderosa", que ofereça as seguintes funcionalidades:

Eu tenho um certo escopo para um grupo de objetos. isso significa quegrupo A, Grupo B, ... terão sua própria filaestou preenchendo uma fila em um segmento com escopo de grupoTópico A (Produtor)estou lendo uma fila em um segmento com escopo de grupoLinha B (Consumidor)

então terei os seguintes cenários:

existe e não haverá itens na fila (como os trabalhos foram chamados com um "grupo de destino" vazio):Linha B deve escapar do loopatualmente não há nenhum item na fila, poisTópico A está trabalhando no item para enfileirar:Linha B deveria esperarexistem itens na fila:Linha B deve conseguir desenfileirar e processar o itemnão há nenhum item na fila, poisTópico A não tem mais itens para enfileirar:Linha B deve escapar do loop

agora eu vim com a seguinte implementação:

public class MightyQueue<T>
  where T : class
{
    private readonly Queue<T> _queue = new Queue<T>();

    private bool? _runable;
    private volatile bool _completed;

    public bool Runable
    {
        get
        {
            while (!this._runable.HasValue)
            {
                Thread.Sleep(100);
            }
            return this._runable ?? false;
        }
        set
        {
            this._runable = value;
        }
    }

    public void Enqueue(T item)
    {
        if (item == null)
        {
            throw new ArgumentNullException("item");
        }

        this._queue.Enqueue(item);
    }

    public void CompleteAdding()
    {
        this._completed = true;
    }

    public bool TryDequeue(out T item)
    {
        if (!this.Runable)
        {
            item = null;
            return false;
        }
        while (this._queue.Count == 0)
        {
            if (this._completed)
            {
                item = null;
                return false;
            }
            Thread.Sleep(100);
        }
        item = this._queue.Dequeue();
        return true;
    }
}

que então seria usado

Produtor

if (anythingToWorkOn)
{
    myFooMightyQueueInstance.Runable = false;
}
else
{
    myFooMightyQueueInstance.Runable = true;
    while (condition)
    {
        myFooMightyQueueInstance.Enqueue(item);
    }
    myFooMightyQueueInstance.CompleteAdding();
}

Consumidor

if (!myFooMightyQueueInstance.Runable)
{
    return;
}

T item;
while (myFooMightyQueueInstance.TryDequeue(out item))
{
    //work with item
}

mas acredito que essa abordagem está errada, pois estou usando algumasThread.Sleep()-está lá (não pode haver algum waitHandle ou algo mais?) ... eu também não sou sobre o algo ... alguém pode me ajudar?

questionAnswers(5)

yourAnswerToTheQuestion