C: 循环结构

循环就像跑操场——只要没到终点就继续跑,条件满足就停。掌握循环,程序才不会只做一次就结束。

1. while 循环

while 是最基础的循环:先判断条件,为真则执行循环体,然后再判断,如此反复,直到条件为假。

C
#include <stdio.h>

int main(void) {
    int count = 1;
    while (count <= 5) {
        printf("第 %d 圈\n", count);
        count++;
    }
    printf("跑完了!\n");
    return 0;
}
TEXT 📖 仅展示
第 1 圈
第 2 圈
第 3 圈
第 4 圈
第 5 圈
跑完了!
⚠️ 循环体内一定要有让条件最终为假的操作(如 count++),否则会变成死循环,程序永远不会停止。

(1) while 的适用场景

当循环次数不确定,取决于运行时条件时,用 while 最自然。例如读取输入直到特定值:

C
#include <stdio.h>

int main(void) {
    int sum = 0;
    int num = 0;
    printf("输入正整数求和,输入0结束: ");
    scanf("%d", &num);
    while (num != 0) {
        sum += num;
        scanf("%d", &num);
    }
    printf("总和: %d\n", sum);
    return 0;
}
TEXT 📖 仅展示
输入正整数求和,输入0结束: 10 20 30 0
总和: 60

2. do-while 循环

do-while 先执行循环体,再判断条件。保证循环体至少执行一次,这是它和 while 的关键区别。

C
#include <stdio.h>

int main(void) {
    int num;
    do {
        printf("输入1-10的数字: ");
        scanf("%d", &num);
    } while (num < 1 || num > 10);
    printf("你输入了: %d\n", num);
    return 0;
}
TEXT 📖 仅展示
输入1-10的数字: 15
输入1-10的数字: 0
输入1-10的数字: 7
你输入了: 7
⚠️ do-while 末尾的分号不能省:} while (条件); 忘了分号会编译报错。

(1) while 与 do-while 的选择


3. for 循环

for 把初始化、条件判断、更新三部分集中在头部,是最常用的循环形式。

C
for (初始化; 条件; 更新) {
    循环体;
}
C
#include <stdio.h>

int main(void) {
    for (int i = 1; i <= 5; i++) {
        printf("%d ", i);
    }
    printf("\n");
    return 0;
}
TEXT 📖 仅展示
1 2 3 4 5

(1) for 的执行流程

  1. 执行初始化(仅一次)
  2. 判断条件——为假则退出循环
  3. 执行循环体
  4. 执行更新
  5. 回到第2步

(2) for 的灵活性

for 的三个部分都可以省略,但分号不能省:

C
#include <stdio.h>

int main(void) {
    int i = 1;
    for (; i <= 5; ) {
        printf("%d ", i);
        i++;
    }
    printf("\n");
    return 0;
}

省略条件就变成死循环:for (;;) {} 等同于 while (1) {}

💡 优先使用 for 循环——循环变量、边界条件、更新方式一目了然,不容易写出死循环。

(3) 作用域注意

C99 允许在 for 的初始化部分声明变量,该变量的作用域仅限于 for 循环内部:

C
#include <stdio.h>

int main(void) {
    for (int i = 0; i < 3; i++) {
        printf("i = %d\n", i);
    }
    return 0;
}

循环结束后 i 不再可用。如果需要在循环外使用 i,就要在 for 之前声明。


4. 嵌套循环

循环内部再放一个循环,就是嵌套循环。外层每执行一次,内层完整执行一轮。

(1) 打印矩形星号

C
#include <stdio.h>

int main(void) {
    int rows = 3;
    int cols = 5;
    for (int i = 0; i < rows; i++) {
        for (int j = 0; j < cols; j++) {
            printf("* ");
        }
        printf("\n");
    }
    return 0;
}
TEXT 📖 仅展示
* * * * *
* * * *
* * * * *

(2) 九九乘法表

C
#include <stdio.h>

int main(void) {
    for (int i = 1; i <= 9; i++) {
        for (int j = 1; j <= i; j++) {
            printf("%d*%d=%-4d", j, i, i * j);
        }
        printf("\n");
    }
    return 0;
}
TEXT 📖 仅展示
1*1=1
1*2=2   2*2=4
1*3=3   2*3=6   3*3=9
1*4=4   2*4=8   3*4=12  4*4=16
1*5=5   2*5=10  3*5=15  4*5=20  5*5=25
1*6=6   2*6=12  3*6=18  4*6=24  5*6=30  6*6=36
1*7=7   2*7=14  3*7=21  4*7=28  5*7=35  6*7=42  7*7=49
1*8=8   2*8=16  3*8=24  4*8=32  5*8=40  6*8=48  7*8=56  8*8=64
1*9=9   2*9=18  3*9=27  4*9=36  5*9=45  6*9=54  7*9=63  8*9=72  9*9=81
⚠️ 嵌套循环的总执行次数是外层次数×内层次数,3层嵌套就会急剧增长,注意性能。


5. break 语句

break 立即跳出当前循环(只跳一层),不再执行剩余循环。

C
#include <stdio.h>

int main(void) {
    for (int i = 1; i <= 10; i++) {
        if (i == 5) {
            break;
        }
        printf("%d ", i);
    }
    printf("\n遇到5就跳出\n");
    return 0;
}
TEXT 📖 仅展示
1 2 3 4
遇到5就跳出

(1) 查找第一个满足条件的元素

C
#include <stdio.h>

int main(void) {
    int nums[] = {3, 7, 2, 9, 5, 1};
    int target = 9;
    int found = 0;
    for (int i = 0; i < 6; i++) {
        if (nums[i] == target) {
            printf("找到 %d,下标 %d\n", target, i);
            found = 1;
            break;
        }
    }
    if (!found) {
        printf("未找到 %d\n", target);
    }
    return 0;
}
TEXT 📖 仅展示
找到 9,下标 3

6. continue 语句

continue 跳过当前这一轮循环的剩余语句,直接进入下一轮(回到条件判断或更新步骤)。

C
#include <stdio.h>

int main(void) {
    for (int i = 1; i <= 10; i++) {
        if (i % 3 == 0) {
            continue;
        }
        printf("%d ", i);
    }
    printf("\n3的倍数被跳过了\n");
    return 0;
}
TEXT 📖 仅展示
1 2 4 5 7 8 10
3的倍数被跳过了
⚠️ 在 whiledo-while 中使用 continue 要确保更新语句在 continue 之前,否则可能死循环。


7. 常见循环模式

(1) 计数模式

统计满足条件的元素个数:

C
#include <stdio.h>

int main(void) {
    int nums[] = {12, 45, 3, 67, 89, 23, 56};
    int count = 0;
    for (int i = 0; i < 7; i++) {
        if (nums[i] > 50) {
            count++;
        }
    }
    printf("大于50的有 %d 个\n", count);
    return 0;
}
TEXT 📖 仅展示
大于50的有 3 个

(2) 累加模式

把一系列值加在一起:

C
#include <stdio.h>

int main(void) {
    int sum = 0;
    for (int i = 1; i <= 100; i++) {
        sum += i;
    }
    printf("1到100的和: %d\n", sum);
    return 0;
}
TEXT 📖 仅展示
1到100的和: 5050

(3) 搜索模式

查找第一个满足条件的元素,找到后用 break 退出:

参见前面 break 示例。

(4) 遍历模式

依次处理数组中的每个元素:

C
#include <stdio.h>

int main(void) {
    int scores[] = {85, 92, 78, 96, 61};
    int len = 5;
    for (int i = 0; i < len; i++) {
        printf("学生%d: %d分 %s\n", i + 1, scores[i], scores[i] >= 60 ? "及格" : "不及格");
    }
    return 0;
}
TEXT 📖 仅展示
学生1: 85分 及格
学生2: 92分 及格
学生3: 78分 及格
学生4: 96分 及格
学生5: 61分 及格

8. 死循环与避免

死循环是条件永远为真的循环。有意为之的死循环用 for(;;)while(1),内部用 break 退出:

C
#include <stdio.h>

int main(void) {
    int num;
    while (1) {
        printf("输入数字(0退出): ");
        scanf("%d", &num);
        if (num == 0) {
            break;
        }
        printf("你输入了: %d\n", num);
    }
    printf("再见!\n");
    return 0;
}

无意产生的死循环通常是因为忘记更新循环变量或更新方向错误:

C
int i = 0;
while (i < 10) {
    printf("%d", i);
}
⚠️ 如果程序好像"卡住了"不动,第一个怀疑就是死循环。按 Ctrl+C 可以强制终止。

▶ 示例

用嵌套循环打印直角三角形:

C
#include <stdio.h>

int main(void) {
    int n = 5;
    for (int i = 1; i <= n; i++) {
        for (int j = 1; j <= i; j++) {
            printf("* ");
        }
        printf("\n");
    }
    return 0;
}
▶ 试一试
TEXT 📖 仅展示
*
* *
* * *
* * * *
* * * * *

▶ 示例

求两个正整数的最大公约数(辗转相除法),演示不确定次数的 while 循环:

C
#include <stdio.h>

int main(void) {
    int a = 48, b = 18;
    int orig_a = a, orig_b = b;
    while (b != 0) {
        int temp = a % b;
        a = b;
        b = temp;
    }
    printf("%d 和 %d 的最大公约数是 %d\n", orig_a, orig_b, a);
    return 0;
}
▶ 试一试
TEXT 📖 仅展示
48 和 18 的最大公约数是 6

9. 三种循环的选择

情况 推荐
循环次数确定 for
至少执行一次 do-while
循环次数不确定 while
交互式菜单 do-while + switch
💡 三种循环在逻辑上可以互相转换,选择最贴合业务场景的写法即可。

❓ 常见问题

Q forwhile 到底用哪个?
A 循环次数确定时用 for,循环次数不确定时用 while。这是最通用的选择标准。
Q break 能跳出多层循环吗?
A 不能。break 只跳出最内层循环。要跳出多层,可以用标志变量配合外层判断,或者用 goto(不推荐但有时实用)。
Q for(;;)while(1) 哪个好?
A 功能完全等价。while(1) 可读性更好,for(;;) 是传统C风格。选哪个看团队规范。
Q 循环变量用 ijk 可以吗?
A 简单循环中这是广泛接受的惯例。但如果变量有业务含义(如 rowcolstudent_index),用有意义的名字更好。

📖 小节

📝 作业

  1. 编写程序,用 for 循环计算 1! + 2! + 3! + ... + 10! 的值(阶乘之和)。
  2. 编写程序,用嵌套循环打印倒直角三角形(5行,第1行5颗星,第5行1颗星)。
  3. 编写程序,输入一个正整数,逆序输出它的每一位数字(如输入1234输出4 3 2 1)。
Web-Tutorial.com

Web-Tutorial 技术团队

由多位开发者共同维护的编程教程平台。每篇教程由对应领域的开发者编写和审核,确保内容准确可靠。如发现任何问题,欢迎向我们反馈。

100%

🙏 帮我们做得更好

我们是刚上线的编程教程站,几个人的小团队,精力有限。页面虽经检查,难免还有疏漏——链接失效、排版错乱、内容有误、语言生硬……

如果您发现了,麻烦告诉我们,我们会在收到反馈后第一时间进行修复,再次感谢您的光临 🙏