RAII 字符缓冲区

RAII char buffer

我想包装几个 C 函数以安全地使用 C++。有一个 C 函数将原始指针指向数组及其大小,如 -

void function(char* bufferToFill, size_t bufsize)

现在,我无法找到可以公开要传递给此类函数的原始指针的 C++ 对象。我想避免使用 new[] 并记住在每次抛出异常时删除它。

std::string 显然不能暴露它的 char*,std::vector 类似,我唯一想到的是 std::unique_ptr 但感觉有点奇怪(因为它通常用于拥有一个对象,不是数组?)

解决此类问题的正确 C++ 方法是什么? 提前致谢

std::string obviously cant expose its char*, std::vector similar

当然可以; C++11 保证 std::string1std::vector 的存储是连续的,所以你可以做 &str[0] 来获得指向基础数据(edit:实际上 std::vector &str[0] 如果 str.size()==0 是不行的,但是 data() 方法保证始终有效).

指针的有效性受制于通常的引用失效规则(即只要您不执行任何潜在的重新分配操作,它就是有效的)。

极端情况:空容器

虽然在这种情况下空容器不是问题(为什么有人会传递一个零长度缓冲区来填充?)了解以下内容仍然很有用:

  • 对于std::string,要求&str[0]总是安全的,即使字符串为空;事实上,该标准明确表示(在 [string.access]):

    Returns: *(begin() + pos) if pos < size(), otherwise a reference to an object of type T with value charT(); the referenced value shall not be modified.

  • 对于std::vector,可能vector为空的话调用&str[0]是不行的; operator[]在序列容器的一般要求中指定,具有操作语义*a.begin(),如果size()为0,则为未定义行为;但是,C++11 确实提供了 data() 方法,它总是 returns 某种有效指针(尽管在空向量的情况下指向空的有效范围)

不幸的是,您不能只记住 data() 对两个容器都是正确的,至于 std::string 它 returns 一个 const 指针与 c_str() 完全一样.


  1. 在所有答案中,我所说的 std::string 实际上指的是 std::basic_string 的任何专业化。

the only thing that comes to my mind is std::unique_ptr but it feels kinda odd (because its usually used to own an object, not array?)

这里又是一个误解。

数组是对象,the language specifically allows for std::unique_ptr of arrays:

std::unique_ptr<int[]> p(new int[10]);