我可以在这里使用reinterpret_cast吗?

Can I use a reinterpret_cast here?

本文关键字:cast reinterpret 在这里 我可以      更新时间:2023-10-16

简化后,我有如下的类模板:

template<class T> class Buffer{
  char * ptr;
  T * getPtr(){return (T*)ptr;} // (1) Which cast to use ?
}

当我还不知道它们的类型T时,从文件生成许多这样的Buffer并存储到数组中。

Buffer<char> buffers[10];
do_something_to_load_buffers_from_file();

最后,当我知道它们的类型时,我想通过函数按值返回它们:

template<class T> Buffer<T> getBuffer(int i){
  return (Buffer<T>)buffers[i]; // (2) Which cast to use ?
}
...
Buffer<int> ibuf = getBuffer<int>(5);

现在的问题是:在标记的行上使用哪些强制类型转换?(我故意在给定的示例中使用c风格的强制转换作为占位符。)

标记(1):重新诠释演员阵容应该能起到正确的作用,是这样吗?

标记(2):

  • 重新解释演员阵容也可以在这里完成工作,但这是好的做法吗?
  • 对于我的一般理解:这一行将首先调用转换构造函数Buffer(Buffer&B),并在返回后调用move构造函数。对吧?

您可以使用以下命令:

template<class T> class Buffer{
  char * ptr;
  T * getPtr(){return reinterpret_cast<T*>(ptr);}
  template<typename U>
  Buffer(const Buffer<U>& rhs) : ptr(rhs.ptr) {}
};

之后:

template<class T> Buffer<T> getBuffer(int i){
  return buffers[i];
}
  1. reinterpret_cast是这里明显的选择,因为这就是我们正在做的:重新解释存储在char*中的位模式,就好像它是T*一样。
  2. 这里没有内置cast是一个好主意。Buffer<char>Buffer<T>不相关。它们的布局兼容性没有任何保证(或者至少您需要非常仔细地定义它们以确保布局兼容性)。在char*比其他指针长的平台上,这可能会严重破坏。

一种可能的处理方法是:

class Buffer{
  char * ptr;
  template <typename T>
  T * getPtr() {return reinterpret_cast<T*>(ptr);}
};

另一种方法是交叉复制Buffer<T>,正如另一个答案所建议的那样。