我在使用memcpy函数时遇到问题。我需要一个将数据存储到void指针的函数。这是一个简单的例子:
void saveData(void* data)
{
char inputData[] = "some data";
memcpy((char*)data, inputData, sizeof(inputData));
}
然而,当我这样做时,我会出现分段错误,即使它编译得很好。我的函数参数必须是一个void指针,因为我可能有不同的数据格式输入,我可能不知道数据的大小提前。有人能告诉我我做错了吗?
请,谢谢你。
** 更新: 谢谢大家的有益回应。正如大多数人所指出的,我没有初始化void 数据。修好了。 现在我的问题是:当我为void *数据(甚至char *数据)进行动态分配时,我给它一个大小,但是当我做memcpy时,它允许我写一个比我第一次分配空间更大的字符串。我也尝试过做char *数据,同样的事情发生了。这是我的示例代码:
char inputData[] = "123456789";
void* data1 = malloc(5*sizeof(char));
char* data2 = (char*)malloc(5*sizeof(char));
memcpy(data1,inputData,sizeof(inputData));
memcpy(data2,inputData,sizeof(inputData));
当我打印出结果时,即使我只为5个字符分配了足够的空间,整个inputData字符串也会被复制。这不应该给我一个错误吗?
答案 0 :(得分:4)
您的函数参数data
需要指向可用内存的地方。
你可以这样做:
int main()
{
char myString[256];
saveData((void*)myString);
}
如果您更喜欢使用malloc
和free
,那么您的代码将更像这样:
int main()
{
char* myString = (char*)malloc(256);
saveData((void*)myString);
free(myString);
}
..这两者的问题在于你不知道字符串需要多长时间。使用std :: string会更安全/更容易。
std::string myString; // an empty string
myString += "some data"; // append a string
答案 1 :(得分:2)
请注意,源代码的大小不是由sizeof
给出的,而是由strlen给出的。假设调用者不想分配内存,则需要malloc
存储并让void *存储一个句柄。鉴于save函数调用malloc,我会设置相应的释放函数。
bool saveData(void** retSave, const char* input)
{
bool success = false;
size_t storageSize = strlen(input) + 1;
void* store = malloc(storageSize);
if (store)
{
memcpy(store, input, storageSize);
success = true;
}
return success;
}
void releaseSavedData(void* savedData)
{
free(savedData);
}
int main()
{
void* saveHandle = 0;
bool ok = saveData(&saveHandle, "some data");
if (ok)
{
releaseSavedData(saveHandle);
}
return 0;
}
答案 2 :(得分:1)
data
需要指向您有权写入的地方。您无权访问的空指针区域(除非您正在运行DOS或其他东西)。
使用malloc
分配一块内存以从inputData
复制到。
答案 3 :(得分:1)
如果你不提前知道数据的大小,那么让它工作的唯一方法是malloc一些任意大的缓冲区,并确保你永远不要将那些字节数复制到void *中。不是最好的设计,但它会起作用。
另外,不要忘记在字符串末尾为NULL char分配一个额外的字节,并且不要忘记将null实际放在内存缓冲区的末尾。在上面的示例中,data
中的字符串末尾不会有NULL。