我已经用 C++20 编写了一个无锁的线程安全环形队列,到目前为止它可以正常工作。 唯一不完美的是它必须有两个
enque()
方法,一个接受对左值的 const 引用作为参数,另一个接受对右值的引用,以便将右值移入队列而不是再次构建。
之前版本的代码如下,只是一个骨架,要简化:
template <typename T>
class RingQue_t {
public:
explicit RingQue_t( size_t capacity );
~RingQue_t();
bool deque( T& dest_ ) { return true; };
// If we offer a const ref, the compiler will select this one
bool enque( const T& src_ ) {
// a lot of same codes goes here for a same logic...
new( _buff + _tail ) T( src_ );
};
// If we offer a rvalue ref, the compiler will select this one
bool enque( T& src_ ) {
// a lot of same codes goes here for a same logic...
new( _buff + _tail ) T( std::move( src_ ) );
};
protected:
T* _buff = nullptr;
};
我正在尝试将这两种方法合并为一个,并且已经阅读了一些关于
std::forward
的文档和示例,但我仍然可以NOT正确使用它。
这是我的期待:
template <typename T>
class RingQue_t {
public:
template<typename U>
bool enque( U&& src_ ) {
// new( _buff + _tail ) T( src_ );
// new( _buff + _tail ) T( std::move( src_ ) );
// new( _buff + _tail ) T( std::forward<T>( src_ ) );
std::allocator<T> allc;
allc.construct( _buff + _tail, std::forward<T>( src_ ) );
return true;
};
};
// testing
const std::string s0 { "s0" };
RingQue_t<std::string> str_que( 16 );
str_que.enque( std::string { "s1" } ); // works
str_que.enque( s0 ); // can not pass the compiling.
评论中的所有解决方案都已尝试,没有一个有效。 我总是收到一条错误消息:
类型‘std::remove_referencestd::__cxx11::basic_string
::type&’{又名‘std::__cxx11::basic_string&’}到‘const std::__cxx11::basic_string’的绑定引用丢弃限定符
请告诉我 std::forward 的正确使用方法,非常感谢!!!