int sprintf(char* str, const char* format, ...);
str\0),錯誤返回負值
char buf[64];
sprintf(buf, "Int: %d, Hex: 0x%X, Float: %.2f, Str: %s", 42, 255, 3.14159, "hello");
// buf = "Int: 42, Hex: 0xFF, Float: 3.14, Str: hello"
%[flags][width][.precision][length]specifier
| 元素 | 說明 | 範例 |
|---|---|---|
| flags | - (左對齊) + (正負號) 空格 (正數前空格) # (替代形式) 0 (前導零) | %-10d, %+d, %#x |
| width | 最小欄寬,不足填充 | %5d → " 42" |
| .precision | 小數位數/最大字串長/最小數字位數 | %.2f, %.5s |
| length | hh/h/l/ll/j/z/t/L | %hhd, %lld, %Lf |
| specifier | d/i/u/o/x/X/f/F/e/E/g/G/a/A/c/s/p/n | %d, %s, %p |
sprintf 不檢查目標緩衝區大小,輸出超過 str 容量會導致緩衝區溢位,嚴重安全漏洞。
// 危險:buf 只有 8 字節,輸出遠超長度
char buf[8];
sprintf(buf, "This is too long"); // 緩衝區溢位!
snprintf (C99 標準)
int snprintf(char* str, size_t size, const char* format, ...);
size:目標緩衝區總大小(含結束符空間)str 以 \0 結尾(除非 size==0)
// 安全寫法
char buf[8];
snprintf(buf, sizeof(buf), "Length: %d", 12345);
// buf = "Length: " (截斷),但保證以 \0 結尾,無溢位
// 先用 snprintf 計算所需長度
int len = snprintf(NULL, 0, "User: %s, ID: %d", name, id);
char* buf = malloc(len + 1);
snprintf(buf, len + 1, "User: %s, ID: %d", name, id);
char buf[256];
int offset = 0;
offset += snprintf(buf + offset, sizeof(buf) - offset, "Part1: %d", a);
offset += snprintf(buf + offset, sizeof(buf) - offset, " Part2: %s", str);
void* ptr = &var;
char buf[32];
snprintf(buf, sizeof(buf), "Addr: %p", ptr); // 標準輸出指標格式
%n 獲取已寫入字元數
int n;
sprintf(buf, "Prefix%nSuffix", &n); // n = 6 ("Prefix" 長度)
sprintf_s
int sprintf_s(char* str, size_t size, const char* format, ...); // MSVC 專用
size 參數snprintfsnprintf,拒絕 sprintf。sizeof(buf)(陣列)或變數(動態分配)。>= size 表示發生截斷,需處理。掌握 snprintf 安全用法,是 C/C++ 開發者資安素養的基本體現。