22

我注意到类似问题的线程:Limit size of Queue<T> in .NET? 这正是我想要做的,但我使用的不是 .net,而是 GNU C++。我没有引用 GNU C++ 中的基类,因此 javasuper.***()或 .net 之类的base.***()将不起作用。我一直在尝试从队列类继承,但结果是徒劳的。

我想要做的:指定队列的大小,当队列满时自动出队。具体来说:如果我的队列的最大大小为 2,当我推送第 3 项时,会在推送新项目之前自动弹出第 1 项。

如何实现这样的队列?

谢谢。

4

4 回答 4

17

创建一个封装队列的新类并在新类中强制执行大小限制。

于 2009-08-13T16:18:06.663 回答
15

我知道您说“自动”,但是,为了简单起见:仅将Enqueue()ing 封装在本地函数中(不,不是干净的 OO,但它有效):

Queue<T> myQueue = new Queue<T>();

void addToMyQueue(T param)
{
   myQueue.Enqueue(param); //or push(param)
   if (myQueue.Count > LIMIT)
      myQueue.Dequeue(); //or pop()
}

void main()
{
   addToMyQueue(param);
}
于 2012-02-22T15:03:42.990 回答
9

听起来boost::circuclar_buffer 可以满足您的需求:

写入一个完整的缓冲区

如果数据源产生的数据多于固定大小的缓冲区可以容纳的数据,有几种方法可以处理这种情况:

  1. 通知数据源等到缓冲区中有空间(例如通过抛出溢出异常)。
  2. 如果最旧的数据是最重要的,则忽略源中的新数据,直到缓冲区中再次有空间。
  3. 如果最新的数据最重要,则覆盖最旧的数据。
  4. 让生产者负责在写入缓冲区之前检查缓冲区的大小。

很明显, circular_buffer实现了第三个选项。但它可能不太明显它没有实现任何其他选项 - 尤其是前两个。人们可能会觉得 circular_buffer应该实现前三个选项并提供一种在它们之间进行选择的机制。这种印象是错误的。被 circular_buffer设计和优化为循环(这意味着在满时覆盖最旧的数据)。如果启用了这样的控制机制,只会使事情复杂化,并且使用起来circular_buffer可能会不那么简单。

于 2009-08-13T17:05:30.390 回答
0

假设Queue<T>你的意思是std::queue<T>:队列只是一些在编译时传递的底层容器的适配器。您可以使用已经完成您想要的操作的容器。最合适的似乎是一个循环缓冲区,如果你能找到一个支持必要操作的缓冲区std::queue(我认为那是push_back()pop_front()size(),但我没有检查过)。

于 2009-08-13T16:29:32.303 回答