前言
C语言是一门结构型语言,那么在C语言中有哪些结构呢?其实包含顺序结构、循环结构、选择结构。其中if、swtich语句实现分支结构,while、for、do-while语句实现循环结构。今天我们就对分支和循环的知识进行讲解。
1.if语句
1.if
语法形式:(书写格式)
if(表达式)
语句
表达式作为一个判断标准(在C语言中,0为假,非0为真)
· 若表达式判断为真,则执行下面的语句,为假,则跳过不执行下面的语句
· 表达式计算结果为0,则为假,不执行语句,结果不为零,则执行下面语句
例子:输入一个整数,判断是否为奇数
#include <stdio.h>
int main()
{
int a = 0;
printf("请输入一个整数:");
scanf("%d", &a);
if (a % 2 == 1) // ==是判断==左右两边的值是否相等,相等为真,不相等为假; =是赋值运算符
printf("%d是奇数",a);
return 0;
}
2.else
从上面例子来说,一个整数判断之后不是奇数,那不就不就是偶数了,现在我们要对上述代码进一步优化,
这就要使用到if-else语句了,下面是书写格式:
if(表达式)
语句1
else
语句2
else的中文意思是否则,也就是说,在if-else语句中,要么是if语句执行,要么是else语句执行,两者必须有一方要执行
那我们将上面代码进行改造
#include <stdio.h>
int main()
{
int a = 0;
printf("请输入一个整数:");
scanf("%d", &a);
if (a % 2 == 1)
printf("%d是奇数", a);
else //若不是奇数,那就是偶数
printf("%d是偶数",a);
return 0;
}
练习:输入一个年龄,>=18就输出:成年,否则输出未成年
#include <stdio.h>
int main()
{
int age = 0;
printf("请输入一个年龄:");
scanf("%d", &age);
if (age>=18)
printf("成年");
else
printf("未成年");
return 0;
}
3.分支内包含多条语句
由上面年龄判断的代码引入,去掉未成年的判断,那如果我想在判断成年后面再加上一句输出:可以谈恋爱
代码改进如下:
#include <stdio.h>
int main()
{
int age = 0;
printf("请输入一个年龄:");
scanf("%d", &age);
if (age>=18)
printf("成年");
printf("可以谈恋爱");
return 0;
}
你想的改进方案是不是这种?来看代码运行的结果

结果是不是与我们想象的完全不一样,无论是不是>=18,结果都输出可以谈恋爱,这是为什么呢?
在C语言中,默认if后面只能跟1条语句,要是想控制多条语句,就得有{ }将多条语句都括起来,else类似
结合这个条件,if默认只能控制输出成年的这条语句,可以谈恋爱这条语句就作为独立语句,无论是否成年,该语句都会输出,
所以改进方案是将这2条语句用{ }括起来,就可以得到想要输出的结果啦!这里我就不做过多的演示了,根据提示完成改进代码。
4.嵌套if
在if-else语句中,else还可以和另一个if语句构成 多重判断
例子:输入一个整数,判断这个数是正数、负数还是0
#include <stdio.h>
int main()
{
int a = 0;
printf("请输入一个整数:");
scanf("%d", &a);
if (a > 0)
printf("%d是正数", a);
//在a>0判断后,还剩a<0和a=0,在else里继续进一步判断,所以说if-else语句里嵌套if
else if (a < 0)
printf("%d是负数", a);
else
printf("0");
return 0;
}
其实if语句不仅可以嵌套在else语句里,还可以嵌套在if语句里
#include <stdio.h>
int main()
{
int a = 0;
printf("请输入一个整数:");
scanf("%d", &a);
if (a >= 0)
{
if (a > 0)
printf("%d是正数", a);
else
printf("0");
}
else
printf("%d是负数",a);
return 0;
}
我个人更推荐 第一种 代码形式,更为简洁,若逻辑更清晰,使用{ }将每部分代码块括起来
5.悬空else问题
有了前面的知识的学习,我们下面来做一个练习
#include <stdio.h>
int main()
{
int a = 0;
int b = 2;
if (a == 1)
if (b == 2)
printf("hehe\\n");
else
printf("haha\\n");
return 0;
}
代码的运行结果是什么?
是不是就认为上来就判断a=0,0不等于1,执行else语句,输出:haha
但是运行代码后,发现啥也没有输出,你可能会说第1个if和后面的else都对齐了,为什么它们构成的if-else语句没有发挥作用?
一条重要规则 :else 总跟最接近的if进行匹配 (多条if和else的情况使用)
通过以上重要规则,你就明白了,其实else是与第2个if进行匹配的,不能局限于代码的格式,它可能会影响你的判断
所以,在第1个if判断为假时,不执行if里面的语句,同时没有与第1个语句匹配的else,即程序运行结束。
2.关系操作符
在C语言中,比较关系的表达式中用的运算符就叫“关系操作符”,用于判断大小关系,常用于if或while结构
主要有以下6个:
> 大于 、 < 小于
>= 大于等于、<=小于等于
== 相等、!= 不想等
通过关系表达式判断 0 为假,非0数为真(通常取1)
一些可能常犯的错误
1.==误写=,导致计算出的结果出错
if(x=3)
printf("yes");
第1个代码括号里是赋值运算,将3赋给x,导致得到的结果为3(非0数),结果永远为真,即yes无论在什么情况下,都会输出
if(x==3)
printf("yes");
第2个代码括号里是关系运算,判断x的值是否与3相等,若相等,返回1,输出yes;若不相等,返回0,不执行语句
关于这个错误,有一个建议,将变量写在表达式的右边,为什么呢?
// if(3=x)
// if(3==x)
对于关系运算不会有什么影响,万一少写了一个=,变成赋值表达式,程序会出现报错,变量x不能赋值给3,提醒你少了一个=
2.多个关系运算符不适合连用
举例:判断年龄在18~36岁,输出“青年”
#include <stdio.h>
int main
{
if(18<=age<=36)
printf("青年");
return 0;
}
你是不是想到写一个跟上面差不多的代码,但是你运行后你会发现,它只要输入大于18的任何数,都能输出青年,这是为什么呢?
一条运算规则: 关系运算符按照从左到右的顺序运算
括号里18<=age<=36,先输入一个大于18的数,先进行18<=age的判断,结果为真,返回1,1<=36,使得这个关系表达式在输入比18大的数时,永远为真,输出“青年”,这是跟你想要的结果完全不一样了。怎么改进呢?
改进之后的代码
#include <stdio.h>
int main
{
if(18<=age && age<=36) // &&表示和的意思,将两个关系判断分开,就可以得到想要的结果了,下面会将到逻辑运算符
printf("青年");
return 0;
}
3.条件操作符
条件操作符也叫“三目操作符”,是需要三个操作数参与运算
书写格式如下:
exp1?exp2:exp3
它的计算规则是先对表达式1进行计算,判断其真假,若为真,则执行表达式2,不执行表达式3,表达式2计算出的结果为整个表达式的结果;若为假,则执行表达式3,不执行表达式2,表达式3计算出的结果为整个表达式的结果。
为了帮助理解,将条件操作符所表达的意思转化为if的形式
if(exp1)
{exp2;}
else
{exp3;}
看完之后,条件操作符其实就是对if代码的一种简化写法
4.逻辑操作符:&&,||,!
&&、||都为双目操作符,!为单目操作符
&&:表示并且、和的意思。运算规则:当&&两侧的表达式都为真时,整个表达式才为真,否则为假
||:表示或者的意思。运算规则:当||两侧的表达式至少有一个是真时,整个表达式才为真,否则为假
!:表示取反的意思。运算规则:当表达式为真时,取反后结果为假;表达式为假时,取反后结果为真
1.逻辑取反运算符 !
根据上面对 **!**的描述,可以画出图的形式进一步理解

举一个代码例子,帮助理解
#include <stdio.h>
int main()
{
int flag = 0;
if (!flag)
printf("do something");
return 0;
}
上面代码 if括号里面的表达式要为真时,才会执行下面语句,!flag为真,那么flag就要为假,下面语句才会被执行
2.逻辑与运算符 &&
根据上面对 **&&**的描述,可以画出图的形式进一步理解

举一个代码例子,帮助理解
#include <stdio.h>
int main()
{
int month = 0;
scanf("%d", &month);
if (month >= 3 && month <= 5)
printf("春天");
return 0;
}
上面代码中,3~5月是春天,要满足输入的月份既要>=3,又要<=5,两个条件缺一不可,必须同时满足才能输出春天
3.逻辑或运算符 ||
根据上面对 **||**的描述,可以画出图的形式进一步理解

举一个代码例子,帮助理解
#include <stdio.h>
int main()
{
int month = 0;
scanf("%d", &month);
if (month == 12 || month == 1 || month == 2)
printf("冬天");
return 0;
}
上面代码,12月或1月或2月是冬天,输入的月份满足这3个其中1个,就可以输出冬天
4.练习:闰年的判断
输入一个年份year,判断year是否是闰年
闰年判断的规则:
1.能被4整除并且不能被100整除是闰年
2. 能被400整除是闰年
//能被4整除、不能被100整除是闰年是并列关系
// year % 4 == 0 && year % 100 != 0
//能被400整除是闰年
// year % 400 == 0
// 1和2两个判断条件只要满足任何一个,就可以判断是闰年,这里是用“或”的关系进行条件连接
#include <stdio.h>
int main()
{
int year = 0;
scanf("%d", &year);
if ((year % 4 == 0 && year % 100 != 0) || year % 400 == 0)
printf("闰年");
else
printf("平年");
return 0;
}
5.短路
仅仅根据左操作数的结果就能知道整个表达式的结果,不再对右操作数进⾏计算的运算称为短路求值。
&&短路
根据上面**&&的运算规则**:当&&两侧的表达式都为真时,整个表达式才为真,否则为假
当&&左侧的表达式结果为0,右侧表达式不执行(无论右侧的表达式是真是假),整个表达式的结果都为假,如下图所示

||短路
根据上面**||的运算规则**:当||两侧的表达式至少有一个是真时,整个表达式才为真,否则为假
当||左侧的表达式结果为1,右侧表达式不执行(无论右侧的表达式是真是假),整个表达式的结果都为真,如下图所示

5.switch语句
switch语句是一种特殊的if-else结构,用于判断多个结果的情况。
书写格式:
switch (expression) {
case value1: statement
case value2: statement
···
default: statement
}
//expression:表达式, value:值、结果 statement:语句
上述代码中,根据表达式的结果,寻找对应结果的case分支;若没有找到,则执行default下的语句
2个注意
· switch后的expression必须为整型表达式
· value必须为整型常量表达式(如整数、字符) 注:字符类型属于整型
1.if和switch语句对比
刚才说switch语句是一种特殊的if-else结构,用于判断多个结果的情况。
那么我们现在来用一个例子,去感受它们之间的相似点和不同点
例1:输入任意一个整数值,计算除3后的余数
使用if语句
int main()
{
// 存放整数
int a = 0;
// 提示
printf("请输入一个整数:");
// 输入
scanf("%d", &a);
//被3除后的余数有0,1,2
if (a % 3 == 0)
printf("余数是0");
else if (a % 3 == 1)
printf("余数是1");
else
printf("余数是2");
return 0;
}
使用switch语句
你可能是这样写的
#include <stdio.h>
int main()
{
int a = 0;
printf("请输入一个整数:");
scanf("%d", &a);
switch (a % 3)
{
case 0:
printf("余数是0\\n");
case 1:
printf("余数是1\\n");
case 2:
printf("余数是2\\n");
default:
printf("输入错误\\n");
}
return 0;
}
但是运行的结果是这样的:

为什么会输出2句话呢?
在switch语句中,当执行一个case分支时,若执行完没有让它结束的语句,则它会继续往下执行语句,直至执行到switch语句末尾。但是我们想要它执行完一个分支时,就结束在switch语句的运行,这时候就要用到break语句了
break语句 :只要执行break,就会跳出循环,继续往下执行(稍后在本文后面部分会进行更详细的讲解,这里先了解)
了解break的作用后,我们将代码进一步改进:
//在每一个case后都加上一个break语句,结束语句
#include <stdio.h>
int main()
{
int a = 0;
printf("请输入一个整数:");
scanf("%d", &a);
switch (a % 3)
{
case 0:
printf("余数是0\\n");
break;
case 1:
printf("余数是1\\n");
break;
case 2:
printf("余数是2\\n");
break;
default:
printf("输入错误\\n");
break;
}
return 0;
}
上述代码中的注意点
· case 和后边的数字之间必须有空格
· 每一个case 语句中的代码执行完成后,需要加上break ,才能跳出这个switch语句
2.switch语句的break
在switch语句中,break可以帮助实现分支效果,但不是在每一个分支都要使用到break,使用要结合实际情况。
如下面的一个例子:
1.输入1-7,数字分别对应了星期一到星期日
2.当输入1-5时,输出“工作日”; 6-7,则输出“休息日”
int main()
{
int day = 0;
scanf("%d", &day);
switch (day)
{
case 1:
case 2:
case 3:
case 4:
case 5:
printf("工作日\\n");
break;
case 6:
case 7:
printf("休息日\\n");
break;
default:
printf("输入错误\\n");
}
return 0;
}
因为星期一到五都属于工作日,在case5后去写输出工作日的语句,无论执行进入case1-5哪一个,程序都往下到case5语句处,在输出工作日和休息日2处末尾,加上break语句进行划分。为什么在default处不加上break语句呢?这是因为default语句在switch语句的结尾处,若执行它之后,也会自动跳出switch语句,往下继续执行。
根据实际需求,恰当去使用break语句才能发挥出最大的作用。
3.switch语句的default
在使用switch语句时,还会经常遇见一种情况,当switch表达式结果与case不能匹配上,需要去说明这种情况,就得使用到default语句了
在上面代码中,输入1-7,判断工作日和休息日,若输入不是1-7这几个数字,程序会匹配到default语句,并输出语句提醒你
4.switch语句的case和default的顺序问题
在switch语句中,case一定放在前面,default一定放在case的后面吗?
答:没有顺序要求,满足需求就可以。通常习惯把default放在case的后面而已,显得逻辑更清晰。
6.while循环
1.if和while对比
if(表达式)
语句
while(表达式)
语句 //多条语句同样是用{}括起来
例子:用if和while分别打印hehe

if满足条件,打印一次hehe

while满足条件,死循环打印无数个hehe
2.while的执行流程

执行while语句的流程:首先判断表达式的值的真假,若值不为0,执行括号内的语句,执行完后,再回到表达式判断,是否进行下一次循环,直到表达式为0,执行跳过语句,执行结束;若为0,结束循环。
3.while循环的实践
练习1:在屏幕上打印1~10的值
// 在屏幕上打印1~10的值
#include <stdio.h>
int main()
{
int n = 1;//初始化为1
while (n <= 10)//n<=10,n最大到10;大于10,表达式为0,循环结束
{
printf("%d ", n);
n++;//每次在n的基础上加1,去形成一个从1递增到10的变化
}
return 0;
}
练习2:输入一个正的整数,逆序打印这个整数的每一位
例如:
输入:1234,输出:4 3 2 1
输入:521,输出:1 2 5
代码示例:
#include <stdio.h>
int main()
{
int n = 0;
printf("请输入一个正整数:");
scanf("%d", &n);
while (n)
{
printf("%d ", n % 10);//n都对10取余,就可以得到个位上的数字
n = n / 10;
// 执行一次n/10可以去掉最低位上的数字,找倒数第二个数字(从右往左数第2位)
// 如:n = 1234 / 10得到123,123相较于1234就去掉了最低位,123 % 10就得到倒数第⼆位3。
// 在n变成0前,可以得到所有位
}
return 0;
}
7.for循环
1.for循环的语法形式
for(表达式1;表达式2;表达式3)
语句 //若有多条语句,用{}括起来
表达式1用于循环变量的初始化
表达式2用于循环结束条件判断
表达式3用于循环变量的调整
2.for循环的执行流程

进入for循环,第一步先执行表达式1,对循环变量做一个初始化,第二步执行表达式2,对循环变量的值进行判断,分2种情况:(1)表达式2判断为假或为0时,循环结束,往下执行
(2)表达式2判断为真或为非0数,执行循环内的语句,执行完后,再执行表达式3,对循环变量进行调整,调整后在进行表达式2的判断,重复操作,直到判断为假时,执行(1)操作。
· 注:表达式1在整个循环过程只执行1次
3.for循环的实践
学习完for循环的执行流程,我们来实践一下吧
练习:在屏幕上打印1~10的值
#include <stdio.h>
int main()
{
int n = 0;
for (n = 1; n <= 10; n++)
{
printf("%d ", n);
}
return 0;
}
4.while循环和for循环的对比


通过对比,我们可以发现,while循环的初始化、判断条件、调整比较分散,而for循环比较集中,便于代码的维护,
从形式上来说,for循环更优
5.练习
计算1~100之间3的倍数的数字之和
//思路1
#include <stdio.h>
int main()
{
int n = 0;
int sum = 0;
for (n = 3; n <= 100; n += 3)
{
sum += n;
}
printf("\\n%d", sum);
return 0;
}
//思路2
#include <stdio.h>
int main()
{
int i = 0;
int sum = 0;
for (i = 1; i <= 100; i++)
{
if (i % 3 == 0)
{
sum += i;
}
}
printf("%d\\n", sum);
return 0;
}
8.do-while循环
1.do-while循环的语法形式
do
{
语句;
}while(表达式);
2.do-while的执行流程

do-while循环的执行流程:第一步先执行括号内的语句,执行完后,第二步进行循环条件的判断,判断表达式是否为真或假,若表达式为假,循环结束,往下执行;若为真,则执行括号内的语句,重复操作,直到判断表达式为假时,循环结束。
· 注:do-while循环至少执行1次括号内的语句
3.do-while循环的实践
练习1:在屏幕上打印1~10的值
#include <stdio.h>
int main()
{
int n = 1; //初始化
do
{
printf("%d ", n);
n++;
} while (n <= 10);
return 0;
}
练习2:输入一个正整数,计算这个数是几位数?
例如:
输入:1234 输出:4
输入:123 输出:3
思路:
如123/10=12,去掉一位3,位数加1
12/10=2,去掉一位2,位数加1
2/10=0,去掉一位1,位数加1
0
从右往左数,每除10,位数加1,我们用do-while循环尝试写出代码
#include <stdio.h>
int main()
{
int n = 0; //n为循环变量
int i = 0; //i为记录位数
printf("请输入一个正整数:");
scanf("%d", &n);
do
{
n /= 10; //去掉一位
i++; //位数加1
} while (n); //当n=0时,位数已经全部计算完,同时n判断为假,循环结束
printf("该正整数为%d位数\\n", i);
return 0;
}
9.break和continue语句
在循环执行的过程中,如果某些状况发生的时候,需要提前终止循环,这是非常常见的现象。C语言提供了两个终止循环的关键字break和continue。
break语句:永久终止循环,执行break语句,结束循环,往下执行。若在多层循环中,break语句仅跳出当前的一次循环。
continue语句:跳过本次循环continue循环后面的代码。
例1.

i=1、2、3、4正常执行,当输出4后,i++,得到5时,判断5<=10,进行if判断,执行break语句,跳出while循环,程序运行结束。
例2.

i=1、2、3、4正常执行,当输出4后,i++,得到5时,判断5<=10,进行if判断,执行continue语句,跳过printf和i++的代码部分,i=5没有进行调整,继续判断5<=10,进行if判断,执行continue语句,跳过printf和i++的代码部分,陷入死循环。
例3.

先进行i++,i=2、3、4正常执行,当输出4后,i++,得到5时,判断5<=10,进行if判断,执行continue语句,跳过printf,进行i++,i=6、7、8、9、10正常执行,i=10输出后,判断10<=10,i++,判断if,再输出11,11<=10,循环结束。
例4.

i=1、2、3、4正常执行输出,当i=5时,执行break语句,跳出for循环
例5.

i=1、2、3、4正常执行输出,当i=5时,执行continue语句,跳过printf语句,i++,i变成6后,i=6、7、8、9、10正常执行输出,i=10输出后,i++,i=11,判断11<=10,循环结束。
例6.

i=1、2、3、4正常执行输出,当i=5时,执行break语句,跳出do-while循环,往下执行。
10.循环的嵌套
练习:
找出100~200之间的素数,并打印在屏幕上。
注:素数又称质数,只能被1和本身整除的数字
思路:
(1)先生成100~200之间的数–for循环
(2)假设要判断i是否为素数,需要拿2到i-1之间的数字去试除i,需要产生2到i-1之间的数字–for循环
(3)如果2~i-1之间有数字能整除i,则i不是素数,如果都不能整除,则i是素数–if判断
根据以上思路,写出代码
#include <stdio.h>
int main()
{
int i = 0; //存储100~200的数字的变量
for (i = 100; i <= 200; i++) //生成100~200的数字
{
int flag = 1; //先假设i是素数
int j = 0;//存储2~i-1的数字的变量
//生成2~i-1的数字
for (j = 2; j <= i – 1; j++)
{
//对素数进行判断
if (i % j == 0) //说明i不是素数
{
flag = 0; //i不是素数,改变flag的状态
break; //只要i被2~i-1中一个数整除了,就不用浪费时间往下判断了,跳出循环
}
}
if (flag == 1) //当flag状态没有被改变,循环结束是j>i-1时,说明if语句没被执行过,i是素数
{
printf("%d ", i);
}
}
return 0;
}
11.goto语句
在C语言中有一种特别的语法,是goto语句和跳转标号,goto语句可以实现在同一个函数内跳转到设置好的标号处
例1:
#include <stdio.h>
int main()
{
goto next;
printf("hehe\\n");
printf("haha\\n");
next :
printf("heihei\\n");
return 0;
}
//原本是要打印hehe和haha的,但是goto语句跳过这2句的输出,直接输出heihei
//goto语句使用尽量是goto在前,跳转标号在后,否则可能会造成死循环
一般不使用,适用于多层循环的代码中,想要快速跳出循环的情况
12. 总结
本文全面介绍了C语言中的分支和循环结构,这是构建程序逻辑控制的基础。主要内容总结如下:
一、分支结构
if语句:包括基本if、if-else、嵌套if和悬空else问题
- if语句根据条件表达式的结果(0为假,非0为真)决定是否执行相应语句
- 使用大括号{}控制多条语句的执行范围
- else总是与最近的if匹配,不受代码格式影响
关系操作符:>、<、>=、<=、==、!=
- 用于比较大小关系,返回0(假)或1(真)
- 注意避免将==误写为=,以及多个关系运算符不适合连用的问题
条件操作符(三目运算符):exp1 ? exp2 : exp3
- 根据exp1的真假选择执行exp2或exp3
- 是if-else语句的简化写法
逻辑操作符:&&(与)、||(或)、!(非)
- 用于组合多个条件判断
- 支持短路求值:&&左侧为假时右侧不执行,||左侧为真时右侧不执行
switch语句:用于多分支选择
- 表达式必须是整型,case值必须是整型常量
- 需要配合break语句实现分支效果
- default处理未匹配的情况,可放在任意位置
二、循环结构
while循环:先判断条件,再执行循环体
- 适合循环次数不确定的情况
- 注意避免死循环
for循环:for(初始化;条件判断;调整)
- 初始化、判断、调整三个部分集中在一起
- 适合循环次数确定的情况
- 代码结构清晰,便于维护
do-while循环:先执行循环体,再判断条件
- 至少执行一次循环体
- 适合需要先执行再判断的场景
三、循环控制语句
break语句:永久终止当前循环
- 在switch中用于跳出switch语句
- 在循环中用于提前结束循环
continue语句:跳过本次循环剩余代码
- 继续下一次循环的判断和执行
- 注意避免在while循环中造成死循环
四、高级应用
循环嵌套:循环内部包含另一个循环
- 常用于处理二维数据或多重条件判断
- 示例:寻找100-200之间的素数
goto语句:无条件跳转到指定标签
- 一般不推荐使用,可能破坏程序结构
- 适用于多层循环中快速跳出的特殊情况
五、编程建议
掌握这些分支和循环结构是学习C语言编程的基础,通过大量练习和实践,可以熟练运用这些结构解决实际问题。建议读者在学习过程中多动手编写代码,理解每个结构的执行流程和应用场景。
网硕互联帮助中心


![[完整代码分享]基于Python的雷达情报分析软件-网硕互联帮助中心](https://www.wsisp.com/helps/wp-content/uploads/2026/08/20260809110054-6a785de61dfac-220x150.png)


评论前必须登录!
注册