Switch Case语句在C语言中如何高效使用?

99ANYc3cd6
预计阅读时长 19 分钟
位置: 首页 C语言 正文

switch 语句是一种多路分支控制结构,它允许一个变量根据其值来执行不同的代码块,可以把它看作是 if-else if-else 链的一种更清晰、更高效的替代方案,特别是在需要检查一个变量与多个常量值是否相等的情况下。

switch case语句 c语言
(图片来源网络,侵删)

基本语法

switch 语句的基本结构如下:

switch (expression) {
    case constant1:
        // 当 expression 的值等于 constant1 时,执行的代码
        break;
    case constant2:
        // 当 expression 的值等于 constant2 时,执行的代码
        break;
    case constant3:
        // 当 expression 的值等于 constant3 时,执行的代码
        break;
    default:
        // 当 expression 的值与所有 case 都不匹配时,执行的代码
        break;
}

语法详解

switch (expression)

  • expression 是一个整型表达式(在 C99 标准之前,只允许是 int 类型,C99 及以后可以是 intcharenum 或其他可以隐式转换为 int 的类型)。
  • 这个表达式的值会与每个 case 后面的常量进行比较。

case constant:

  • constant 必须是一个常量或常量表达式(不能是变量)。
  • 每个 case 的值必须是唯一的,不能重复。
  • switch 表达式的值与某个 case 的常量匹配时,程序就会从该 case 处开始执行代码。

break;

  • 这是 switch 语句中非常重要的部分!
  • break 语句的作用是立即跳出 switch 语句,防止程序继续执行下一个 case 的代码。
  • 如果没有 break,程序会继续执行下一个 case 的代码,这种现象称为“贯穿”(fall-through),这在某些情况下是有意为之的,但大多数情况下,忘记写 break 是一个常见的错误。

default:

  • default 是可选的,但强烈推荐使用。
  • switch 表达式的值与任何一个 case 都不匹配,程序就会执行 default 分支中的代码。
  • default 分支通常放在 switch 语句的最后,但它也可以放在任何位置。

工作流程

  1. 计算 switch(expression) 的值。
  2. 将计算得到的值与第一个 case 的常量进行比较。
  3. 如果匹配,则从该 case 处开始执行代码,直到遇到 breakswitch 语句的末尾。
  4. 如果不匹配,则跳到下一个 case 进行比较。
  5. 如果所有 case 都不匹配,并且存在 default 分支,则执行 default 分支的代码。
  6. 如果没有 default 分支且所有 case 都不匹配,则 switch 语句不执行任何操作。

示例代码

示例 1:基本用法(带 break

这是一个最典型的用法,根据输入的数字(1-7)输出对应的星期几。

#include <stdio.h>
int main() {
    int day = 3;
    char* dayName;
    switch (day) {
        case 1:
            dayName = "Monday";
            break;
        case 2:
            dayName = "Tuesday";
            break;
        case 3:
            dayName = "Wednesday";
            break;
        case 4:
            dayName = "Thursday";
            break;
        case 5:
            dayName = "Friday";
            break;
        case 6:
            dayName = "Saturday";
            break;
        case 7:
            dayName = "Sunday";
            break;
        default:
            dayName = "Invalid day";
            break;
    }
    printf("Day %d is %s\n", day, dayName); // 输出: Day 3 is Wednesday
    return 0;
}

示例 2:贯穿(Fall-through)特性

有时,我们需要多个 case 执行相同的代码块,这时就可以利用“贯穿”特性。

#include <stdio.h>
int main() {
    char grade = 'B';
    switch (grade) {
        case 'A':
            printf("Excellent!\n");
            break;
        case 'B':
        case 'C':
            printf("Good job!\n"); // 当 grade 是 'B' 或 'C' 时,都会执行这句
            break;
        case 'D':
            printf("You passed.\n");
            break;
        case 'F':
            printf("You failed.\n");
            break;
        default:
            printf("Invalid grade.\n");
            break;
    }
    return 0;
}
// 输出: Good job!

示例 3:忘记 break 的错误示例

这个例子展示了忘记 break 会发生什么。

switch case语句 c语言
(图片来源网络,侵删)
#include <stdio.h>
int main() {
    int number = 2;
    switch (number) {
        case 1:
            printf("This is case 1.\n");
            break; // number 是 1,到这里就停止了
        case 2:
            printf("This is case 2.\n");
            // 故意忘记 break
        case 3:
            printf("This is case 3.\n");
            break;
        default:
            printf("This is the default case.\n");
    }
    return 0;
}

输出结果:

This is case 2.
This is case 3.

原因分析:

  • number 的值是 2,与 case 2 匹配。
  • 程序开始执行 case 2 的代码,打印 "This is case 2."。
  • 由于没有 break,程序没有跳出 switch,而是继续向下执行 case 3 的代码,打印 "This is case 3."。
  • 遇到 case 3break 后,才最终跳出 switch 语句。

switch vs. if-else if-else

特性 switch 语句 if-else if-else 语句
判断条件 只能判断相等 () 可以判断任何关系 (>, <, , 等)
表达式类型 整型表达式 任何表达式(布尔、浮点等)
执行效率 通常更高,因为它通常实现为“跳转表”(jump table),查找速度快。 效率相对较低,因为可能需要逐个条件判断。
代码可读性 当需要检查一个变量与多个常量是否相等时,switch 结构更清晰。 当逻辑复杂或需要范围判断时,if-else 更灵活、更易读。

选择建议:

  • 如果你的逻辑是 "x 等于 1...,x 等于 2...,x 等于 3...",优先使用 switch
  • 如果你的逻辑是 "x 大于 10...,否则如果 x 小于 0...",或者需要组合条件,必须使用 if-else

C 语言中的新特性 (C++ 和 C99)

在 C 语言中,switch 语句的限制比 C++ 要严格一些。

switch case语句 c语言
(图片来源网络,侵删)

C99 的变化:

C99 标准允许 switch 语句的 expressioncase 标签使用 long 类型,以及更宽的整型。

C++ 的扩展:

C++ 对 switch 做了重要的扩展,使其更安全、更强大:

  1. 作用域:在 C++ 中,可以在 switch 语句内部定义变量,但必须放在 case 标签之前。
  2. 类型:C++ 的 switch 可以接受更多类型,包括 std::string(通过重载 operator==)和枚举。
  3. 贯穿提示:C17 标准引入了属性 [[fallthrough]],用于明确表示你希望代码“贯穿”,这是一种更安全、更清晰的写法,可以避免忘记 break 的警告。

C++ 示例 (作用域):

// C++ 代码
switch (day) {
    int x; // 在 C 中,这里会报错,在 C++ 中,只要在所有 case 之前定义即可。
    case 1:
        // ...
        break;
    case 2:
        // ...
        break;
}

C17 示例 (显式贯穿):

// C17 代码
switch (value) {
    case 1:
        printf("One\n");
        [[fallthrough]]; // 明确告诉编译器和阅读者:这里会贯穿
    case 2:
        printf("One or Two\n");
        break;
}
  • switch 是 C 语言中处理多路分支的有效工具,特别适合基于单个整型变量的值进行选择。
  • break 语句是 switch 的核心,用于防止代码“贯穿”,除非你确实需要这种行为。
  • default 分支是一个好习惯,用于处理所有未预料到的情况。
  • 根据逻辑的复杂性,在 switchif-else if-else 之间做出明智的选择。
-- 展开阅读全文 --
头像
织梦模板如何优化SEO技术博客?
« 上一篇 昨天
织梦dede模板为何不见?如何找回?
下一篇 » 昨天
取消
微信二维码
支付宝二维码

目录[+]