C++ 中的通用循环缓冲区实现

Generic circular buffer implementation in C++

我开始编写循环缓冲区库,只是为了好玩。我遇到了一个特殊问题:

template < class T >
T CircularBuffer<T>::pop()

它 returns 类型 T,但是当 CB 为空并且用户尝试使用 pop() 时会怎样?返回 nullptr 没有意义,因为 nullptr 不能转换为 double。显然,可以抛出异常,但有没有更语义友好的方式来抛出异常呢?

编辑:"semantically friendly" 我的意思是:

推入完整的CB时,抛出异常是很自然的。异常应该防止程序崩溃,因为没有足够的内存用于新元素。在弹出一个空的 CB 时抛出异常对我来说似乎是语义上的,因为程序不会崩溃。但如果这是唯一可用的选项,请告诉我。

这是 std::optional or boost::optional 的完美用例 - 它们 类 存储值 空状态。

您可以将签名更改为:

template < class T >
std::optional<T> CircularBuffer<T>::pop()

你的合同将是这样的:

  • 如果缓冲区为空,则返回std::nullopt

  • 否则返回一个非空std::optional<T>包含head元素


或者,考虑采用一个 "continuation" 函数,该函数仅在 pop 成功时才会被调用。示例:

template < class F >
decltype(auto) CircularBuffer<T>::pop(F&& continuation);

用法:

some_circular_buffer.pop([](auto popped_item)
{
    // I will only be called if the pop was successful.
});

您可以通过对 "pop failure" 案例进行额外的延续来扩展这个概念。