C# 检查队列<;T>;连续不断地

C# 检查队列<;T>;连续不断地,c#,.net,multithreading,thread-safety,C#,.net,Multithreading,Thread Safety,我想要一个函数来检查一个线程上的新添加的队列 显然,有一个连续循环睡眠的选项,但我想要一些不那么浪费的东西 我考虑了某种类型的等待句柄,然后让队列发出信号,但我不能安全地覆盖排队,因为它不是虚拟的 现在,我正在考虑封装一个队列,作为我的最佳选择,但我想问各位好朋友,是否有更好的队列 其想法是:我希望多个线程访问套接字连接,同时保证它们只读取消息的响应,因此我将使用一个线程分派和读取响应,然后使用响应数据(纯文本)执行回调。尝试阻塞队列: 基本思想是,当您调用TryDequeue时,它将阻塞,直到

我想要一个函数来检查一个线程上的新添加的队列

显然,有一个连续循环睡眠的选项,但我想要一些不那么浪费的东西

我考虑了某种类型的等待句柄,然后让队列发出信号,但我不能安全地覆盖排队,因为它不是虚拟的

现在,我正在考虑封装一个
队列
,作为我的最佳选择,但我想问各位好朋友,是否有更好的队列

其想法是:我希望多个线程访问套接字连接,同时保证它们只读取消息的响应,因此我将使用一个线程分派和读取响应,然后使用响应数据(纯文本)执行回调。

尝试阻塞队列:

基本思想是,当您调用
TryDequeue
时,它将阻塞,直到队列中有东西为止。正如您所看到的,阻塞队列的“美妙之处”在于您不必轮询/睡眠或做任何类似疯狂的事情。。。它是生产者/消费者模式的基本支柱

我的阻塞队列版本是:

public class BlockingQueue<T> where T : class
{
    private bool closing;
    private readonly Queue<T> queue = new Queue<T>();

    public int Count
    {
        get
        {
            lock (queue)
            {
                return queue.Count;
            }
        }
    }

    public BlockingQueue()
    {
        lock (queue)
        {
            closing = false;
            Monitor.PulseAll(queue);
        }
    }

    public bool Enqueue(T item)
    {
        lock (queue)
        {
            if (closing || null == item)
            {
                return false;
            }

            queue.Enqueue(item);

            if (queue.Count == 1)
            {
                // wake up any blocked dequeue
                Monitor.PulseAll(queue);
            }

            return true;
        }
    }


    public void Close()
    {
        lock (queue)
        {
            if (!closing)
            {
                closing = true;
                queue.Clear();
                Monitor.PulseAll(queue);
            }
        }
    }


    public bool TryDequeue(out T value, int timeout = Timeout.Infinite)
    {
        lock (queue)
        {
            while (queue.Count == 0)
            {
                if (closing || (timeout < Timeout.Infinite) || !Monitor.Wait(queue, timeout))
                {
                    value = default(T);
                    return false;
                }
            }

            value = queue.Dequeue();
            return true;
        }
    }

    public void Clear()
    {
        lock (queue)
        {
            queue.Clear();
            Monitor.Pulse(queue);
        }
    }
}
公共类阻止队列,其中T:class
{
私自关门;
私有只读队列队列=新队列();
公共整数计数
{
得到
{
锁(队列)
{
返回队列。计数;
}
}
}
公共阻止队列()
{
锁(队列)
{
关闭=假;
Monitor.pulsell(队列);
}
}
公共布尔排队(T项)
{
锁(队列)
{
如果(结束| | null==项目)
{
返回false;
}
排队。排队(项目);
如果(queue.Count==1)
{
//唤醒任何阻塞的队列
Monitor.pulsell(队列);
}
返回true;
}
}
公众假期结束()
{
锁(队列)
{
如果(!关闭)
{
关闭=真;
queue.Clear();
Monitor.pulsell(队列);
}
}
}
public bool TryDequeue(out T值,int timeout=timeout.Infinite)
{
锁(队列)
{
while(queue.Count==0)
{
if(关闭| |(超时<超时.无限)| |!监视器.等待(队列,超时))
{
值=默认值(T);
返回false;
}
}
value=queue.Dequeue();
返回true;
}
}
公共空间清除()
{
锁(队列)
{
queue.Clear();
监测脉冲(队列);
}
}
}

非常感谢你为这一个

在我看来,这种实现似乎是错误的。如果我在有有限超时的空队列上调用
TryDequeue
,它将直接返回
default(t)
,否?在放弃之前,它应该至少等待
t
。在TryDequeue中(out t value,int timeout):timeout是一个int,它符合Monitor.wait()的预期,但是如果将负数指定为timeout,Monitor.wait()将抛出System.ArgumentOutOfRangeException。if的第二部分检查负超时,只是确保返回默认值,而不是引发异常。