C语言 Sprintf 分段错误
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/7184227/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Sprintf Segmentation Fault
提问by syl
numCheck is number between 1-1000. This code gives me a segfault only when I collect the results of sprintf in charcheck. If I simply use sprintf without using the results, I don't get a seg fault. What's happening here?
numCheck 是 1-1000 之间的数字。仅当我在 charcheck 中收集 sprintf 的结果时,此代码才会给我一个段错误。如果我只是使用 sprintf 而不使用结果,我不会遇到段错误。这里发生了什么事?
char * numString;
int charcheck = sprintf(numString, "%d", numCheck);
采纳答案by Kerrek SB
You need to provide your own memory for sprintf. Also, don't use sprintf, but rather snprintf:
您需要为sprintf. 另外,不要使用sprintf, 而是snprintf:
char buf[1000] = {0};
snprintf(buf, 999, ....);
Alternatively you can allocate memory dynamically:
或者,您可以动态分配内存:
char * buf = new char[BUFSIZE];
snprintf(buf, BUFSIZE-1, ...);
/* ... */
delete[] buf;
回答by Seth Carnegie
The first argument to sprintfmust point to a valid buffer. You have a char*but it points to garbage.
的第一个参数sprintf必须指向一个有效的缓冲区。你有一个char*但它指向垃圾。
Change your code to:
将您的代码更改为:
char numString[80] = { };
int charcheck = sprintf(numString, "%d", numCheck);
So that numStringactually points to a valid buffer (of 80 characters in this example, all elements of which are initialised to 0).
所以这numString实际上指向一个有效的缓冲区(在本例中为 80 个字符,其中所有元素都初始化为 0)。
It would also be good to use snprintfso you can pass the size of your buffer to it, which will help prevent buffer overflows:
使用它也很好,snprintf因此您可以将缓冲区的大小传递给它,这将有助于防止缓冲区溢出:
const int bufsize = 80;
char numString[bufsize] = { };
int charcheck = snprintf(numString, bufsize - 1, "%d", numCheck);
Notice that you subtract one from the buffer size that you pass to snprintfbecause you don't want it to use the very last slot, which you want to make sure is NULLto denote the end of the string.
请注意,您从传递给的缓冲区大小中减去一个,snprintf因为您不希望它使用最后一个插槽,您希望确保它NULL表示字符串的结尾。
回答by sth
The pointer given as the first parameter to sprintfis expected to point to a memory location where sprintfshould write the formatted string.
作为第一个参数给出的指针应该sprintf指向sprintf应该写入格式化字符串的内存位置。
In this case you didn't initialize numStringto point to some memory you allocated for the formatted string. Since numStringisn't initialized it might point anywhere, and in your case trying to write the formatted output to that location results in a segmentation fault.
在这种情况下,您没有初始化numString指向您为格式化字符串分配的某些内存。由于numString未初始化,它可能指向任何地方,在您的情况下,尝试将格式化输出写入该位置会导致分段错误。
回答by Jeff
The most straightforward thing to do is to use an array as above, e.g.,
最直接的做法是使用上面的数组,例如,
char numString[80] = { };
suggested by Seth, Jesus and Kerrek.
由赛斯、耶稣和凯瑞克建议。
I think the last answer from sth is a good explanation: "the first parameter to sprintf is expected to point to a memory location where sprintf should write the formatted string." So apart from using an array of characters, which would force the allocation of memory for the string, you can also use this:
我认为 sth 的最后一个答案是一个很好的解释:“ sprintf 的第一个参数应该指向 sprintf 应该写入格式化字符串的内存位置。” 因此,除了使用字符数组(这会强制为字符串分配内存)之外,您还可以使用以下命令:
char *numstring = (char*) malloc(80);
This should let you explicitly free the allocated memory when it is no longer needed.
这应该让您在不再需要分配的内存时显式释放它。
回答by Jesus Ramos
You need to allocate space for the result such as
您需要为结果分配空间,例如
char numString[50];
int charcheck = sprintf(numString, "%d", numCheck);
In your case the interal workings of sprintf are trying to reference NULL which is the default value for a pointer in your case.
在您的情况下,sprintf 的内部工作正在尝试引用 NULL,这是您的情况下指针的默认值。

