std::array<char, size>是否以空字符结尾?用其初始化std::string是否安全?
结论
这段代码存在严重的安全问题,属于C++标准定义的未定义行为,绝对不可以在生产环境使用。
问题原因
- 你提到的
std::string接受const char*入参的构造函数,确实要求输入指针必须指向以\0(空字符)结尾的C风格字符串,构造函数内部会从指针指向的地址开始逐字节读取,直到遇到\0才会停止拷贝。 - 你定义的
std::array<char, 4> word{'a', 'b', 'c', 'd'}总长度只有4字节,所有空间都被a/b/c/d四个字符占满,既没有预留存储\0的空间,std::array本身也不会自动在末尾追加空终止符。 word.data()返回的是数组首元素的指针,d之后的内存内容完全不可控:构造std::string时会一直往后读内存,要么读到随机的垃圾字符拼接进字符串,要么读到非法内存地址直接触发程序崩溃。
修复方案
你可以根据需求选择下面任意一种安全写法:
- 方案1:给数组预留空终止符的存储空间
// 数组长度设为5,最后一位显式存\0 std::array<char, 5> word{'a', 'b', 'c', 'd', '\0'}; // 也可以直接用字面值初始化,自动补空终止符 std::array<char, 5> word = "abcd";
- 方案2:构造
std::string时显式指定长度,不依赖空终止符
std::array<char, 4> word{'a', 'b', 'c', 'd'}; // 第二个参数指定要拷贝的字符数,不会越界读内存 std::string p(word.data(), word.size());
- 方案3:直接使用本身自带空终止的字符串字面值初始化
const char* word = "abcd"; std::string p = word; // 完全安全
内容的提问来源于stack exchange,提问作者user11910061
相关产品推荐
相关产品推荐

