我正在使用我的前任使用过的C代码库:
#ifdef _MSC_VER
#if _MSC_VER<1900
#define snprintf sprintf_s
#endif
#endif
代码库需要在Linux(gcc / clang),OSX(gcc / clang)和Windows(VS)上编译。我第一次尝试在Visual Studio 2015中编译代码。以前使用过Visual Studio 2010。我遇到了here描述的错误,并且能够使用接受的答案中的线索进行编译:
snprintf
该项目现在使用Visual Studio 2015进行编译并在OSX上进行编辑。但是,我关注sprintf_s文档中的声明:
与snprintf不同,sprintf_s保证缓冲区将以空值终止(除非缓冲区大小为零)。
如果Visual Studio包含符合C99的#include <stdio.h>
#include <string.h>
int main(int argc, char** argv) {
char buf[5];
snprintf(buf, sizeof(buf), "abcdef");
printf("buffer: %s\n", buf);
printf("size of buffer: %lu\n", strlen(buf));
printf("last character a null terminator?: %s\n",
(strcmp(&buf[4], "\0") == 0) ? "yes" : "no");
return 0;
}
版本,那么该缓冲区是否应该保证以空值终止?
我写了一个小程序来评估行为。
~$c99 main.c
~$./a.out
buffer: abcd
size of buffer: 4
last character a null terminator?: yes
我使用Visual Studio 2015在OSX和Windows上构建并运行程序。
在OSX上,输出为:
> printf_evaluation.exe
buffer: abcd
size of buffer: 4
last character a null terminator?: yes
在使用Visual Studio 2015的Windows 7上,输出为
snprintf
不能证明输出实际上是以空值终止的,并且表明MSDN文档不正确吗?我的例子太琐碎了吗?是否存在使用Visual Studio 2015终止elem.style.opacity = +!parseInt(elem.style.opacity);
的输出为空的情况?
答案 0 :(得分:1)
snprintf()
总是会终止缓冲区。是的,MSDN文档是错误的。
From C11 standard, snprintf():
snprintf函数等效于fprintf,输出除外 写入数组(由参数s指定)而不是a 流。 如果n为零,则不写任何内容,s可能为null 指针。否则,超出n-1的输出字符是 丢弃而不是写入数组,为空字符 写在实际写入的字符末尾 数组。如果在重叠的对象之间进行复制,则 行为未定义。
(强调我的)。