Skip to content

判断语句(Conditional Statements)

判断语句让程序根据条件选择不同的执行路径,是实现"决策逻辑"的基础。C 语言提供 if-elseswitch-case 两种机制。


1. 为什么需要判断

没有判断,程序只能按固定顺序执行。判断赋予了程序"根据数据做不同事情"的能力:

用户登录?  ──是──→  显示主页
     │
     否
     │
     └──────→  显示登录界面

2. if 语句

2.1 基本形式

if (条件) {
    // 条件为真时执行
}
int temperature = 35;

if (temperature > 30) {
    printf("天气炎热,开启制冷\n");
}

2.2 if-else

if (temperature > 30) {
    printf("开启制冷\n");
} else {
    printf("制冷未开启\n");
}

2.3 if-else if-else 多分支

int score = 85;

if (score >= 90) {
    printf("等级:A\n");
} else if (score >= 80) {
    printf("等级:B\n");
} else if (score >= 70) {
    printf("等级:C\n");
} else if (score >= 60) {
    printf("等级:D\n");
} else {
    printf("等级:F\n");
}

2.4 条件表达式

在 C 语言中,条件的真假判定遵循简单规则:

条件值 判定
0 假(false)
非零(1-142 等) 真(true)
int flag = 1;
if (flag) {          // 等价于 if (flag != 0)
    printf("flag 为真\n");
}

int* ptr = NULL;
if (!ptr) {          // 等价于 if (ptr == NULL)
    printf("指针为空\n");
}

2.5 省略大括号的风险

// 危险写法——只有紧邻的一行属于 if
if (score > 60)
    printf("及格\n");
    printf("恭喜\n");   // 这行不论条件真假都会执行!

// 安全写法——始终使用大括号
if (score > 60) {
    printf("及格\n");
    printf("恭喜\n");
}

建议:即使只有一行语句,也保留大括号。这可以避免后续添加代码时无意中破坏逻辑。


3. switch-case 语句

当一个变量需要与多个离散值比较时,switch 比一连串 if-else if 更清晰。

3.1 基本形式

int day = 3;

switch (day) {
    case 1:
        printf("星期一\n");
        break;
    case 2:
        printf("星期二\n");
        break;
    case 3:
        printf("星期三\n");
        break;
    case 4:
        printf("星期四\n");
        break;
    case 5:
        printf("星期五\n");
        break;
    default:
        printf("周末\n");
        break;
}

3.2 break 的作用

break 跳出当前 switch 块。如果遗漏 break,程序会穿透(fall-through)到下一个 case 继续执行:

int n = 1;
switch (n) {
    case 1:
        printf("一\n");
        // 没有 break → 继续执行 case 2
    case 2:
        printf("二\n");
        break;
}
// 输出:
// 一
// 二

3.3 有意使用穿透

有时穿透是设计意图而非错误:

char grade = 'B';
switch (grade) {
    case 'A':
    case 'B':
    case 'C':
        printf("通过\n");   // A、B、C 共用同一处理
        break;
    case 'D':
    case 'F':
        printf("未通过\n");
        break;
}

多个 case 空标签叠放表示它们共享后续代码,这种写法比逐个 if 更简洁。

3.4 switch 的限制

限制 说明
表达式必须是整数类型 intcharenum 等;float/double 不可用
case 值必须是常量 不能是变量或表达式
不会自动跳出 必须写 break,否则会穿透

4. 嵌套判断

int year = 2024;

if (year % 4 == 0) {
    if (year % 100 == 0) {
        if (year % 400 == 0) {
            printf("%d 是闰年\n", year);
        } else {
            printf("%d 不是闰年\n", year);
        }
    } else {
        printf("%d 是闰年\n", year);
    }
} else {
    printf("%d 不是闰年\n", year);
}

嵌套层级超过 3 层时,可读性急剧下降。此时应拆分为独立函数或合并条件:

// 合并后的闰年判断(更清晰)
if ((year % 4 == 0 && year % 100 != 0) || (year % 400 == 0)) {
    printf("%d 是闰年\n", year);
} else {
    printf("%d 不是闰年\n", year);
}

5. if vs switch 选择指南

场景 推荐 原因
条件涉及范围(x > 10 if-else if switch 只支持等值比较
与多个离散常量比较 switch 结构更清晰,编译器可能优化为跳转表
条件涉及多个变量 if-else if switch 只能基于一个表达式
分支数 ≤ 3 if-else 简单场景不必引入 switch 的语法开销
浮点数比较 if-else if switch 不支持 float/double

6. 条件运算符的替代用法

对于简单的二选一赋值,条件运算符(?:)比 if-else 更紧凑:

// 用 if-else
int max;
if (a > b) {
    max = a;
} else {
    max = b;
}

// 用条件运算符(更简洁)
int max = (a > b) ? a : b;

但避免嵌套使用:

// 不推荐:嵌套条件运算符难读
int result = (a > b) ? ((a > c) ? a : c) : ((b > c) ? b : c);

// 推荐:拆分为 if-else if 或函数
int result;
if (a > b && a > c)      result = a;
else if (b > a && b > c) result = b;
else                     result = c;

7. 常见错误

错误 原因 正确写法
if (x = 5) 用了赋值 = 而非比较 == if (x == 5)
if (0 < x < 10) 数学写法在 C 中不合法,会先算 0 < x 得到 0 或 1,再与 10 比较 if (x > 0 && x < 10)
switch 遗漏 break 导致了非预期的穿透 每个 case 后确保有 break
case 后使用变量 case n: 中 n 必须是常量 改用 if-else if
多余的 ; if (x > 0); 后面的分号是一个空语句 删除多余分号

8. 总结

要点 说明
if-else 是通用判断 支持任意条件表达式,包括范围和逻辑组合
switch 适合等值多分支 表达式必须是整数类型,case 值必须是常量
不要忘记 break switch 中遗漏 break 会导致穿透
始终使用大括号 即使单行语句也保留,防止后续修改引入 bug
= 是赋值,== 是比较 编译器的警告可能救你一次
深度嵌套应重构 超过 3 层考虑提取函数或合并条件

作者: Qing | 修改日期: 2026-07-18