| 语句 | 作用范围 | 典型用途 | 注意事项 |
|---|---|---|---|
break | 最近的 switch、for、while、do-while | 提前退出循环、结束 case | 仅跳出一层,嵌套需标志变量或 goto |
continue | 最近的循环体 | 跳过本次迭代剩余代码,直接进入下一次判断 | for 会执行增量表达式,while/do-while 直接跳到条件判断 |
return | 当前函数 | 返回值、提前结束函数 | main 中 return 0 等价于 exit(0),但析构函数仍会执行 |
goto | 同一函数内标号 | 错误处理统一出口、跳出多层循环 | 慎用,破坏结构化,易造面条代码;Linux 内核风格允许 goto err 模式 |
switch (x) {
case 1: do_a(); break; // 有 break:执行完跳出 switch
case 2: do_b(); // 无 break:贯穿 执行 case 3
case 3: do_c(); break;
default: do_d();
}
break 可选。无 break 形成“贯穿”,利用该特性可合并多 case 逻辑(需注释 // fallthrough)。[[fallthrough]] 属性显式标注,消除编译器警告。while (outer_cond) {
for (int i = 0; i < n; ++i) {
if (cond) break; // 仅跳出 for
if (cond2) continue; // 仅跳过本次 for
}
// break 后继续执行此处
}
需跳出多层循环时,常用方案:
bool done = false;,内层 break 后外层检查再 break。return 直接退出。goto end_label;(仅此场景推荐)。void foo() {
for (int i = 0; ; ++i) {
if (i == 5) return; // 直接离开 foo,调用者继续
}
}
void bar() {
for (int i = 0; ; ++i) {
if (i == 5) break; // 仅跳出循环,继续执行 bar 后续代码
}
printf("after loop\n");
}
return:函数级跳转,销毁局部对象,执行析构/清理,返回调用点下一条指令。break:语句块级跳转,仅离开当前循环/switch,不影响函数栈帧。for (int i = 0; i < 10; ++i) {
if (i == 5) continue; // 执行 ++i,然后判断 i < 10
}
int i = 0;
while (i < 10) {
if (i == 5) continue; // 直接跳到 while 条件判断,i 不自增 → 死循环!
++i;
}
for 循环的增量表达式在 continue 后仍会执行,而 while/do-while 不会。这是新手极易踩坑的地方。
int init_system() {
Resource *r1 = acquire1();
if (!r1) goto err;
Resource *r2 = acquire2();
if (!r2) goto err_r1;
Resource *r3 = acquire3();
if (!r3) goto err_r2;
return 0;
err_r2: release2(r2);
err_r1: release1(r1);
err: return -1;
}
此模式在 Linux 内核、驱动开发中广泛使用,保证资源按逆序释放,代码线性、无嵌套地狱。仅限同一函数、向前跳转、标号语义清晰时使用。
break:跳出最近循环/switch。continue:跳过本次循环迭代,for 仍执行增量。return:退出当前函数,执行析构/清理。goto:函数内任意跳转,慎用,仅用于错误处理集中清理或跳出多层循环。switch 贯穿特性需显式注释或 [[fallthrough]]。熟练掌握四者的作用范围与细微差别,是编写正确、可维护 C/C++ 代码的基本功。