【发布时间】:2011-06-12 16:39:42
【问题描述】:
在 C 中,我使用 strcpy 来制作字符串的深拷贝,但在 C++ 中使用 strcpy 还是 'fine' 还是存在我应该使用更好的替代品吗?
【问题讨论】:
-
您的字符串是否终止? stackoverflow.com/q/4691608/176769
在 C 中,我使用 strcpy 来制作字符串的深拷贝,但在 C++ 中使用 strcpy 还是 'fine' 还是存在我应该使用更好的替代品吗?
【问题讨论】:
我把它放在上面的评论中,只是为了让代码可读:
std::string a = "Hello.";
std::string b;
b = a.c_str(); // makes an actual copy of the string
b = a; // makes a copy of the pointer and increments the reference count
所以如果你真的想模仿strcpy的行为,你需要使用c_str()复制它;
更新
需要注意的是,C++11 标准明确禁止了以前在std::string 的许多实现中使用的常见写时复制模式。因此,不再允许引用计数字符串,以下将创建一个副本:
std::string a = "Hello.";
std::string b;
b = a; // C++11 forces this to be a copy as well
【讨论】:
c_str() 复制”:它只返回原始的char* 数据。然后将此数据传递给执行实际复制的 std::string 构造函数。如果它没有被复制,那么一旦 a 超出范围或被销毁, b 就会失效。
c_str() 复制。我说b = a.c_str() 复制了字符串。 c_str()不是操作的重点;复制赋值运算符是。
在 C++ 中,最简单的方法通常是使用 std::string 类而不是 char*。
#include <string>
...
std::string a = "Hello.";
std::string b;
b = a;
“b = a;”行执行与 strcpy 相同的操作。
【讨论】:
std::string 的operator= 实际上并没有做深拷贝。它执行引用计数的副本(因此,不完全像strcpy 所做的那样)。如果要对 std::string 进行深层复制,则需要这样调用它:std::string a = "Hello."; std::string b; b = a.c_str(); 以强制它实际进行复制,而不是仅仅复制指针并增加引用计数。
如果您使用的是 c++ 字符串,只需使用复制构造函数:
std::string string_copy(original_string);
赋值运算符
string_copy = original_string
如果您必须使用 c 风格的字符串(即以 null 结尾的字符数组),那么是的,只需使用 strcpy,或者作为更安全的替代方案,strncpy。
【讨论】:
建议您使用 strcpy_s,因为除了目标和源参数之外,它还有一个额外的目标缓冲区大小参数以避免溢出。但是,如果您使用 char 数组/指针,这仍然可能是复制字符串的最快方法。
例子:
char *srcString = "abcd";
char destString[256];
strcpy_s(destString, 256, srcString);
【讨论】: