printf() 和 scanf() 大家都会用,但格式符的门道远不止 %d 和 %f。占位符里夹的那些数字、点、负号,能精确控制对齐、宽度、精度。下面把它们一个个拆开看。
格式符是什么
格式符以 % 开头,告诉 printf()/scanf() 拿到的数据按什么类型解释、怎么排版。一套最小例子:
#include <stdio.h>
int main() {
int age = 25;
float salary = 45000.50;
char grade = 'A';
printf("Age: %d\n", age); // Age: 25
printf("Salary: %.2f\n", salary); // Salary: 45000.50
printf("Grade: %c\n", grade); // Grade: A
return 0;
}常用格式符逐个看
字符 %c
char c;
scanf("%c", &c); /* 读一个字符 */
printf("The entered character: %c", c);有符号整数 %d 和 %i
int x;
scanf("%d", &x);
printf("Printed using %%d: %d\n", x); /* %% 输出一个 % */
printf("Printed using %%i: %i", x); /* %d 和 %i 基本等价 */无符号整数 %u
给 %u 传负数,它会按二进制的补码解释,打出很大的正数:
unsigned int var;
scanf("%u", &var);
printf("Unsigned Integer: %u\n", var); // 3
printf("Printing -10 using %%u: %u\n", -10); // 4294967286浮点 %f、%e、%E
float a = 12.67;
printf("Using %%f: %f\n", a); // 12.670000
printf("Using %%e: %e\n", a); // 1.267000e+01(科学计数法)
printf("Using %%E: %E", a); // 1.267000E+01八进制 %o 与十六进制 %x / %X
int a = 67;
printf("%o\n", a); // 103
int b = 15454;
printf("%x\n", b); // 3c5e(小写)
printf("%X", b); // 3C5E(大写)字符串 %s
printf 里 %s 直接把字符串打完;scanf 里 %s 读到第一个空白就停,带空格的句子会被截断:
char str[50];
scanf("%s", str); /* 输入 "Hi Bob" 只拿到 "Hi" */
printf("Entered String: %s", str);想读整行带空格,用 fgets() 或者扫描集 %[ ]。
地址 %p
int a = 10;
printf("The Memory Address of a: %p", (void*)&a); // 0x7ffe6f71e60c长整型们
| 格式符 | 类型 |
|---|---|
%ld / %li | long |
%lf | double |
%Lf | long double |
%lu | unsigned long |
%lld / %lli | long long |
%llu | unsigned long long |
排版三件套:宽度、对齐、精度
在 % 和格式符之间可以插修饰:
- 数字 = 最小字段宽度,不够宽用空格补齐,超了不截断。
- - 号 = 左对齐(默认右对齐)。
- .数字 = 精度:整数指最少位数,字符串指最多字符数,浮点指小数位数。
一套对比最直观:
#include <stdio.h>
int main() {
char str[] = "online-compiler";
printf("%20s\n", str); /* 右对齐,宽 20 */
printf("%-20s\n", str); /* 左对齐,宽 20 */
printf("%20.5s\n", str); /* 宽 20,只取前 5 个字符,右对齐 */
printf("%-20.5s\n", str); /* 宽 20,只取前 5 个字符,左对齐 */
return 0;
}输出:
online-compiler
online-compiler
online
online浮点的精度最常见:%.2f 保留两位小数。
完整速查表
| 格式符 | 含义 |
|---|---|
%c | 字符 |
%d / %i | 有符号整数 |
%u | 无符号整数 |
%f | float |
%lf | double |
%Lf | long double |
%e / %E | 科学计数法浮点 |
%g / %G | 按当前精度选 %f 还是 %e |
%o | 八进制 |
%x / %X | 十六进制(小写/大写) |
%s | 字符串 |
%p | 指针地址 |
%ld | long |
%lld | long long |
%% | 输出一个百分号 % |
几个易错点
- 类型要配:%d 配 int、%f 配 float、%lf 配 double,配错是未定义行为。
- scanf 要取地址:
scanf("%d", &x),字符串除外(数组名本身就是地址)。 - 想打印 %:写
%%。 - scanf 的 %s 停空格:要读整行换 fgets()。
格式符是 C 语言里输出想好看、输入想稳的基本功,多写几遍就熟了。