目录
C语言的结构
C语言是一种“结构化”的语言,“结构化”主要体现在三个方面
一、顺序结构
二、选择结构
三、循环结构
什么是语句
程序所执行的就是语句。
C语言的语句可以分为以下五类
1、表达式语句 。
2、函数调用语句。
3、控制语句。
4、复合语句。
5、空语句。
选择与循环属于控制语句。
控制语句用于控制程序的执行流程,以实现程序的各种结构方式,它们由特定的语句定义符组成,C语言的控制语句有九种
1、条件判断(分支语句):if语句,switch语句。
2、循环执行语句:while,for,do while。
3、转向语句:break,goto,continue,return。
分支语句(选择结构)
if语句
if语句语法结构
if(表达式)
语句;
if语句分类
单分支语句
if(表达式)
语句1;
else
语句2;
多分支语句
if(表达式)
语句1;
else if
语句2;
else if
语句3;
else
语句4;
C语言中的真假
if(表达式)
语句1;
else
语句2;
上述语句中,如果表达式的结果为真,执行语句1,反之执行语句2.
那么什么为真,什么为假?
在C语言中,0为假,非0为真(这里值得注意,负数也是为真,不要想当然)
悬空else
#include<stdio.h>
int main()
{
int a=0;
int b=1;
if(a==0)
if(b==2)
printf("hehe\n");
else
printf("haha\n");
return 0;
}
上述的语句执行结果是haha,因为else匹配最近的if同时b!=2,所以执行结果是haha。
else是和离他最近的if匹配的。
switch语句
switch语句常常用于多分支的情况
switch语句语法结构
switch(表达式)
{
case 常量表达式1:语句1;
case 常量表达式2:语句2;
default:语句3;
}
比如确定今天是星期几。
int main()
{
int day;
scanf("%d", &day);
switch (day)
{
case 1:printf("星期一\n");
case 2:printf("星期二\n");
case 3:printf("星期三\n");
case 4:printf("星期四\n");
case 5:printf("星期五\n");
case 6:printf("星期六\n");
case 7:printf("星期七\n");
default:printf("别乱打\n");
}
system("pause");
return 0;
}
上面的代码中输入1~7会先输出对应的结果,但是输出完了以后程序会继续向下执行,直到输出别乱打为止,这是因为switch语句执行是按照顺序结构全部执行完,所以必须给switch语句设置跳出语句。
switch语句中的break(跳出语句)
下面在每条case后的语句之后加上break语句,程序就能正常输出。
break在switch语句中的作用是跳出当前的选项,实际效果就是把语句划分为不同的分支部分。
int main()
{
int day;
scanf("%d", &day);
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;
case 6:printf("星期六\n"); break;
case 7:printf("星期七\n"); break;
default:printf("别乱打\n"); break;
}
system("pause");
return 0;
}
break的巧妙用法
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");
}
system("pause");
return 0;
}
上面这段代码,利用了switch语句自动执行的特点和break语句跳出的特点,达到了准确输出工作日与休息日的结果。
break只跳出自己所在的语句。
default子句
default子句是switch语句中特有的,作用是当表达式的值与case标签的值都不匹配时,输出该标签后的结果。
default子句与case语句的顺序问题
switch语句是按照顺序自上而下执行的,在没有跳出语句时,选项在前的先执行,选项在后的后执行,所以如果编写需要顺序的代码时,一定要编好语句的顺序。
int main()
{
int day;
scanf("%d", &day);
switch (day)
{
default:printf("别乱打\n");
case 4:printf("星期四\n");
case 1:printf("星期一\n");
case 2:printf("星期二\n");
case 3:printf("星期三\n");
case 5:printf("星期五\n");
case 6:printf("星期六\n");
case 7:printf("星期七\n");
}
system("pause");
return 0;
}
上面这段代码day为4时,结果是从4开始向下输出,输入8时,结果时从default开始向下输出。
但是default子句放在switch语句内任何地方都可以,只要结果不是case标签的值,都能准确的匹配到。
循环语句(循环结构)
while语句
while语句的语法结构
while(表达式)
循环语句;
while语句中只要表达式不为假,则语句一直循环。
while语句中的break
break在while语句中是永久终止循环,当然break必须是同一while语句下。
int main()
{
int i = 0;
while (i < 10)
{
i++;
if (5 == i)
{
break;
}
printf("%d", i);
}
system("pause");
return 0;
}
上面这段代码,输出1,2,3,4的结果,表达式5==i的结果为真时,break起作用,while循环中断。
while语句中的continue
continue语句是用来终止当前循环,然后直接跳到判断部分,进行下一次的循环入口的判断。
int main()
{
int i = 0;
while (i < 10)
{
i++;
if (5 == i)
{
continue;
}
printf("%d", i);
}
system("pause");
return 0;
}
上面这段代码的结果是输出1,2,3,4,6,7,8,9,10。表达式5==i的结果为真时,continue起作用,跳过后面的代码,直接跳到了判断部分,因为i等于5且小于10,所以继续进入循环并且自增。
for语句
for语句语法
for(表达式1;表达式2;表达式3)
语句体;
表达式1:赋值部分
表达式2:判断部分
表达式3:调整部分
任何循环语句中,都具备赋值,判断,调整三个部分,它们共同决定了循环的次数
以打印1-10数字的循环为例
//while循环语句
int main()
{
int i = 1;//初始化部分
while (i <= 10)//判断部分
{
printf("%d ", i);
i++;//调整部分
}
system("pause");
return 0;
}
//for循环语句
int main()
{
int i = 0;
for (i = 1; i <= 10; i++)//(i=1初始化部分,i<=10判断部分,i++调整部分)
{
printf("%d ", i);
}
system("pause");
return 0;
}
上面代码的比较,for循环的赋值,判断,调整部分更为集中,所以后期维护起来更加方面,while循环的则比较分散,所以维护起来并不方便。
注意:任何循环语句中控制循环的变量,都只能用作控制循环不能用作其他用途,否则会对循环造成破坏。
int main()
{
int i = 0;
for (i = 1; i <= 10; i++)//(i=1初始化部分,i<=10判断部分,i++调整部分)
{
printf("%d ", i);
i = 12;
}
system("pause");
return 0;
}
上面代码中,因为调整部分的变量i在语句中被赋值为12,所以整个循环语句只执行了1次,输出的结果为1。
for语句中的break
for语句中的break与while语句中的break的作用相同,跳出当前的循环。
int main()
{
int i = 0;
for (i = 1; i <= 10; i++)//(i=1初始化部分,i<=10判断部分,i++调整部分)
{
if (5 == i)
{
break;
}
printf("%d ", i);
}
system("pause");
return 0;
}
for语句中的continue
for语句中的continue也与while语句中的作用相同,跳过当前循环直接开始下一循环,但是与while语句在细节部分还是有很大的差异。
//for语句部分
int main()
{
int i = 0;
for (i = 1; i <= 10; i++)//(i=1初始化部分,i<=10判断部分,i++调整部分)
{
if (5 == i)
{
continue;
}
printf("%d ", i);
}
system("pause");
return 0;
}
int main()
{
int i = 1;
while (i <= 10)
{
if (5 == i)
{
continue;
}
printf("%d ", i);
i++;
}
system("pause");
return 0;
}
上面的for语句执行的结果是,1、2、3、4、6、7、8、9、10,while语句执行的结果是1、2、3、4死循环,造成不同结果的原因是,for语句中continue跳过后面的语句部分后,程序会走到调整部分i++处,并执行一次i++,所以i会自增为6,然后再次经过判断进入循环,但是while语句中调整部分属于语句部分,continue跳过了调整部分,直接来到判断部分,没有调整i就永远等于5,所以造成死循环。
for语句中的循环控制变量
1、不可在循环体内修改循环控制变量,防止循环失去控制。
2、尽量采用前闭后开的写法
for(i=0;i<10;i++)//前闭后开写法
{}
for(i=0;i<=9;i++)//前闭后闭写法
{}
上面的两个语句都能够实现10次循环,但是前闭后开的写法更直观
当然具体的写法也是因程序而异,比如要进行10到20的循环,前闭后闭的写法就更直观
for(i=10;i<=20;i++)
一些for循环的变种
for语句的赋值,判断和调整部分都是可以省略的,所以形成许多for语句的变种,在编写for语句时要注意
for语句写死循环(无判断部分)
int main()
{
int i = 0;
for (;;)
{
printf("%d ", i);
}
system("pause");
return 0;
}
int main()
{
int i = 0;
for (i=0;;i++)
{
printf("%d ", i);
}
system("pause");
return 0;
}
上面两端代码,都是打印i的值,因为没有判断部分,所以程序陷入死循环,for语句没有判断部分时,判断的结果恒成立。
for语句省略赋值部分
未省略赋值部分
int main()
{
int i = 0, j = 0, count = 0;
for (i = 0; i<10; i++)
{
for (j = 0; j < 10; j++)
{
printf("%d ", count++);
}
}
system("pause");
return 0;
}
省略赋值部分
int main()
{
int i = 0, j = 0, count = 0;
for (; i<10; i++)
{
for (; j < 10; j++)
{
printf("%d ", count++);
}
}
system("pause");
return 0;
}
上面两端代码,未省略赋值部分的结果是输出了0-99,而省略了赋值部分的结果是0-9,这是因为内循环变量j=0这个赋值,有重新赋值的作用,当省略后j的值自增到10时,就无法再进入循环。
for语句的多个变量控制循环
int main()
{
int x, y;
for (x = 0, y = 0; x < 2 && y < 5; x++, y++)
{
printf("hehe\n");
}
system("pause");
return 0;
}
上面这段代码输出两个hehe,在判断部分中,当x为2时,x<2表达式不成立后面的y<5不再计算,整个表达式的结果为假。
一道笔试题目
int main()
{
int i,j,k;
for(i=0,j=0,k=0;k=0;i++,j++,k++)
{
printf("hehe");
}
return 0;
}
上述的代码,不输出任何结果,因为判断部分k被赋值为0,所以第一次判断时结果为假,没有进入循环。
do{}while
do while语法结构
do
{
循环语句;
}while(表达式);
do while语句特点
do while语句至少执行一次,所以使用的场景很有限。
do while中的break与continue
do while中的break与continue语句与while中的break与continue语句作用相同。
goto语句
C语言提供了可以随意滥用的goto语句和标记跳转的符号。
理论和实际上goto语句是没有必要的,但是某些场合下goto语句还是用的上的。
goto语句的语法结构
error:
goto error;
goto语句的例子
int main()
{
int a, b, c;
for (a = 0; a < 10; a++)
{
for (b = 0; b < 10; b++)
{
for (c = 0; c < 10; c++)
{
goto error;
}
}
}
error:
if (a < 2)
printf("成功跳出\n");
SYS;
R0;
}
上面代码,使用break时必须使用3次,才能跳出,因为每个break只能跳出一个循环,但goto语句能够一次跳出多个循环。
goto语句实现循环
int main()
{
char password[30];
printf("电脑一分钟后关机,输入\"我是猪\"取消关机\n");
system("shutdown -s -t 60");
again:
scanf("%s", password);
if (strcmp(password, "我是猪") == 0)
{
system("shutdown -a");
}
else
{
goto again;
}
SYS;
R0;
}