第三讲:分支和循环(上)

目录

1.if语句

1.1 if

1.2 else

1.3 分支中包含多条语句

1.4 嵌套if

1.5 悬空else问题

2.关系操作符

3.条件操作符

4.逻辑操作符:&&,||,!

4.1 逻辑取反运算符

4.2 与运算符

4.3 或运算符

4.4 练习:闰年的判断

4.5 短路

5.switch语句

5.1 if语句和switch语句的对比

5.2 switch语句中的break

5.3 switch语句中的default

5.4 switch语句中的case和default的顺序问题

6.whlie语句

6.1 if和while的对比

6.2 6.2while语句的执行流程

6.3 while循环的实践

6.4 练习

7.for循环

7.1 语法形式

7.2 for循环执行流程

7.3 for循环的实践

7.4 while循环和for循环的对比

7.5 练习

8.2 do while循环的执行流程

8.4 练习

9.break和continue

9.1 while循环中的break和continue

9.1.1 break举例

9.1.2 continue举例

9.2 for循环中的break和continue

9.2.1 break举例

9.2.2 continue举例

9.3 do while循环中的break和continue

10.循环的嵌套

10.1 练习

10.2 题目解析

10.3 参考代码

11.goto语句

12.本章节代码


C语⾔是结构化的程序设计语⾔,这⾥的结构指的是顺序结构、选择结构、循环结构,C语⾔是能够实 现这三种结构的,其实我们如果仔细分析,我们⽇常所⻅的事情都可以拆分为这三种结构或者这三种 结构的组合。

我们可以使用if、switch实现分支结构,使用for、while、do while实现循环结构。

1.if语句

1.1 if

if语句的语法形式如下:

if (表达式)

   语句

表达式成立(为真),则语句执行,表达式不成立(为假),则语句不执行。

在C语言中,0为假,非0表示真

例如:输入一个整数,判断是否为奇数

#include<stdio.h>
int main()
{
	int a = 0;
	scanf("%d", &a);
	if (a % 2 != 0)
		printf("是奇数\n");
	return 0;
}
1.2 else

如果一个数不是奇数,则是偶数,如果一个整数,要完整的判断是奇数还是偶数该怎么办呢?

if...else..语句可以很好的解决

if(表达式)

    语句1;

else

    语句2;

例如:输入一个整数,判断是否为奇数,如果是奇数打印奇数,不是奇数打印偶数。

#include<stdio.h>
int main()
{
	int a = 0;
	scanf("%d", &a);
	if (a % 2 == 0)
		printf("不是奇数\n");
	else
		printf("是偶数\n");//0是偶数
	return 0;
}

练习:输⼊⼀个年龄,>=18岁就输出:成年,否则就输出未成年

#include <stdio.h>
int main()
{
    int age = 0;
    if (age >= 18)
        printf("成年\n");
    else
        printf("未成年\n");
    return 0;
}

1.3 分支中包含多条语句

默认在if和else语句中都只控制一条语句,所以当想控制多条语句的时候,需要在对应的if或者else下面用{}将代码括起来

比如:

#include <stdio.h>
int main()
{
	int age = 0;
	scanf("%d", &age);
	if (age < 18)
	{
		printf("未成年\n");
		printf("很懵懂\n");
	}
	else
	{
		printf("成年\n");
		printf("长大了\n");
	}
		return 0;
}

(为了避免错误,建议在写像if这样的语句后面都带上{})

1.4 嵌套if

在if else语句中,else可以与另一个if语句连用,构成多重判断。

比如,要求输入一个整数,判断输入的整数是0,还是正数或负数。代码如下:

#include <stdio.h>
int main()
{
	int num;
	scanf("%d", &num);
	if (num == 0)
		printf("输入的数是0\n");
	else if (num > 0)
		printf("输入的数是正数\n");
	else if (num < 0)
		printf("输入的数是负数\n");
	return 0;
}

上面else后面又接了if就构成了嵌套if语句。

再⽐如: 输⼊⼀个整数,如果是正数,再判断是奇数还是偶数,并输出;如果不是正数则输出:负数。

#include <stdio.h>
int main()
{
	int num;
	scanf("%d",& num);
	if (num > 0)
	{
		if (num % 2 == 0)
			printf("这是一个正偶数\n");
		if (num % 2 != 0)
			printf("这是一个正奇数\n");
	}
	else
		printf("这是一个负数\n");
	return 0;
}

上面if里面又有if就是嵌套if

练习:

输⼊⼀个⼈的年龄

如果年龄18岁,打印"少年"

如果年龄在18岁⾄44岁打印"⻘年"

如果年龄在45岁⾄59岁打印"中⽼年"

如果年龄在60岁⾄89岁打印"⽼年"

如果90岁以上打印"耄耋"

#include <stdio.h>
int main()
{
	int age = 0;
	scanf("%d", &age);
	if (age < 18)
		printf("青年\n");
	else
	{
		if (age <= 44)
			printf("青年\n");
		else
		{
			if (age <= 59)
				printf("中老年\n");
			else
			{
				if (age <= 89)
					printf("老年\n");
				else 
				{
					if (age > 90)
						printf("耄耋\n");
				}
			}
		}
	}
	return 0;
}

当然,可以简化一些括号,看起来更简洁即:

#include <stdio.h>
int main()
{
	int age = 0;
	scanf("%d", &age);
	if (age < 18)
		printf("青年\n");
	else if (age <= 44)
		printf("青年\n");
	else if (age <= 59)
		printf("中老年\n");
	else if (age <= 89)
		printf("老年\n");
	else if (age > 90)
	    printf("耄耋\n");
	return 0;
}
1.5 悬空else问题

如果有多个if和else,可以记住这样一条规则,else总是跟着最近的if匹配

#include <stdio.h>
int main()
{
	int a = 0;
	int b = 0;
	if (a == 1)
		if (b == 2)
			printf("hehe\n");
	else
			printf("haha\n");
	return 0;
}

请问,上述代码运行的结构是什么?

其实,这里什么都不输出。原因是else只和最近的if匹配。只有当if(a==1)成立了,才可以执行下面的if...else..代码。其实上面的代码可以等同于

#include <stdio.h>
int main()
{
	int a = 0;
	int b = 0;
	if (a == 1)
	{
		if (b == 2)
			printf("hehe\n");
		else
			printf("haha\n");
	}
	return 0;
}

所以,为了避免这样的错误,可以习惯性的在if语句后面加{}

以后在写代码的时候也要注意代码的使用,让代码的可读性更高。

2.关系操作符

C语言用于比较的表达式,称为“关系表达式”,里面使用的运算符就称为“关系运算符”,主要有下面几个。

  • >  大于运算符
  • < 小于运算符
  • <= 小于等于运算符
  • >= 大于等于运算符
  • == 相等操作符
  • != 不相等运算符

关系表达式通常返回0或1,表示真假。

C语言中,0表示假,所有非0表示真。比如,8>1返回1,1>8返回0.关系表达式通常用于if或while结构。

if(x==2)

{...}

注意:相等运算符==与赋值运算符=是两个不一样的运算符,不要混淆。有时候,可能会不小心写成x=3,即:

if(x=3)

{...}

如果不小心写成x=3。表示对变量x赋值,它的返回值为3,所以if总是判断为真。

为了防止这种错误,有些程序员喜欢将变量写在等号右边。

if(3==a);

因为如果把==误写成=,编译器会报错。

x是不能赋值给3的(将值写在左边是一个好习惯,建议这么写)。

另外一个需要避免的错误是:多个关系运算符不宜连用。

i<j<k

上面式子中,连续使用两个小于运算符。编译器不会报错,但是很可能会出现想不到的结果。因为关系运算符是从左向右计算,所以实际是执行下面的表达式。

(i<j)<k

上面式子中i<j的结果返回0或1,所以最终是0或1与变量k进行比较。如果想要判断变量j的值是否在i和k之间,应该这样写:

i<j&&j<k

3.条件操作符

条件操作符也叫三目操作符,需要有三个操作数的,形式入下:

exp1?exp2:exp3

条件操作符的计算逻辑是:如果exp1为真,exp2计算,计算的结果是整个表达式的结果;如果exp1为假,exp3计算,计算的结果是整个表达式的结果。

比如:

#include <stdio.h>
int main()
{
	int a = 0;
	int b = 0;
	scanf("%d", &a);
	if (a > 5)
		b = 3;
	else
		b = -3;
	printf("%d", b);
	return 0;
}
//用三目操作符:
int main()
{
	int a = 0;
	int b = 0;
	scanf("%d", &a);
	b = a > 5 ? 3 : -3;
	printf("%d", b);
	return 0;
}

练习:使用条件表达式实现找两个数中的最大值。

#include<stdio.h>
int main()
{
	int a = 0;
	int b = 0;
	int c = 0;
	scanf("%d%d", &a, &b);
	c = a > b ? a : b;
	printf("%d", b);
	return 0;
}

4.逻辑操作符:&&,||,!

逻辑运算符提供逻辑判断功能,⽤于构建更复杂的表达式,主要有下⾯三个运算符。

  • !:逻辑取反运算符(改变单个表达式的真假)
  • &&:与运算符,就是并且的意思(两侧的表达式都为真,则为真,否则为假)。
  • ||:或运算符,就是或者的意思(两侧⾄少有⼀个表达式为真,则为真,否则为假)。
4.1 逻辑取反运算符

4.2 与运算符

4.3 或运算符

4.4 练习:闰年的判断

输⼊⼀个年份year,判断year是否是闰年

闰年判断的规则:

1.能被4整除并且不能被100整除是闰年

2.能被400整除是闰年

//法1
#include <stdio.h>
int main()
{
	int year = 0;
	scanf("%d", &year);
	if (year % 4 == 0 && year % 100 != 0)
		printf("%d年是闰年", year);
	else
	{
		if (year % 400 == 0)
			printf("%d年是闰年", year);

		else
			printf("%d年不是闰年", year);
	}
	return 0;
}
//法2
int main()
{
	int year = 0;
	scanf("%d", &year);
	if (year % 4 == 0 && year % 100 != 0||year%400==0)
		printf("%d年是闰年", year);
	else
		printf("%d年不是闰年", year);
	return 0;
}
4.5 短路

C语⾔逻辑运算符还有⼀个特点,它总是先对左侧的表达式求值,再对右边的表达式求值,这个顺序是保证的。

如果左边的表达式满⾜逻辑运算符的条件,就不再对右边的表达式求值。这种情况称为“短路”。如下面的代码:

if(month >= 3 && month 5)

表达式中&&的左操作数是month >= 3,右操作数是month ,当左操作数month >= 3的结果是0的时候,即使不判断month ,整个表达式的结果也是0。

所以,对于&&操作符来说,左边操作数的结果是0的时候,右边操作数就不再执⾏。

那||操作符又是怎么样的呢?

if(month == 12 || month==1 || month == 2)

如果month==12,则不⽤再判断month是否等于1或者2,整个表达式的结果也是1。所以,||操作符的左操作数的结果不为0时,就⽆需执⾏右操作数。

像这种仅仅根据左操作数的结果就能知道整个表达式的结果,不再对右操作数进⾏计算的运算称为短路求值

练习:阅读代码,计算代码输出的结果

#include <stdio.h>
int main()
{
	int i = 0, a = 0, b = 2, c = 3, d = 4;
	i = a++ && ++b && d++;
	printf("a=%d\nb=%d\nc=%d\nd=%d\n", a, b, c, d);
	return 0;
}

答案为:a=1 b=2 c=3 d=4

解析:先执行第一个表达式a++,根据公式可知a的值变为1,a++(先使用后加1)的表达式为0,所以整个表达式都为0,后面的表达式不再计算,即短路。于是后面的值(b、c、d)都不变(2、3、4)

5.switch语句

switch语句是⼀种特殊形式的if..else结构,⽤于判断条件有多个结果的情况。它把多重的else if改成更易⽤、可读性更好的形式。形式:

switch (expression)

{

case value1: statement

 case value2: statement

 default: statement

}

上⾯代码中,根据表达式expression不同的值,执⾏相应的case分⽀。如果找不到对应的值,就执⾏default分⽀。

注:

  • switch后的expression必须是整型表达式
  • case后的值,必须是整形常量表达式

这时候可能有人要说了switch后面的expression怎么必须是整型表达式呢,因为我们见过:

#include<stdio.h>
int main()
{
    char ch;
    scanf("%c", &ch);
    switch (ch)
    {
    case'b':
        printf("%c ", ch);
        break;
    case'a':
        printf("%c ", ch);
        break;
    }
    return 0;
}

switch里面有ch(字符)呢,其实这是因为,字符是以ASCII码的形式进行储存的,ASCII是整数,所以字符属于整形类。

另外,case后的值,必须是整形常量表达式。所以可以写为:

case1+2:

但是不能写成:

case1.0:

1.0就算小数了。

5.1 if语句和switch语句的对比

练习:case后的值,必须是整形常量表达式

使⽤if语句完成,如下:

#include <stdio.h>
int main()
{
	int num = 0;
	scanf("%d", &num);
	if (num % 3 == 0)
		printf("除3,余数为0\n");
	if(num%3==1)
		printf("除3,余数为1\n");
	if(num%3==2)
		printf("除3,余数为2\n");
	return 0;
}

使用switch完成,如下:

#include <stdio.h>
int main()
{
	int num = 0;
	scanf("%d", &num);
	switch (num % 3)
	{
	case 0:
		printf("除3,余数为0\n"); break;
	case 1:
		printf("除3,余数为1\n"); break;
	case 2:
		printf("除3,余数为2\n"); break;//记得写break
	}
	return 0;
}

注意:

  • case和后边的数字之间必须有空格
  • 每⼀个case语句中的代码执⾏完成后,需要加上break,才能跳出这个switch语句。
5.2 switch语句中的break

前⾯的代码中,如果我们去掉case语句中的break,会出现什么情况呢?

原因是switch语句也是分支效果的,只有在switch语句中使用break才能在跳出switch语句,如果某⼀个case语句的后边没有break语句,代码会继续往下执⾏,有可能执⾏其他case语句中的代码,直到遇到break语句或者switch语句结束。就⽐如上⾯的代码就执⾏了case 2中的语句。

所以switch语句中break语句是⾮常重要的,能实现真正的分⽀效果。当然,break也不是每个case语句都得有,这就得根据实际情况来看了。

练习:

1.输⼊1-5,输出的是“⼯作⽇”;

2.输⼊6-7,输出“休息⽇”

#include<stdio.h>
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;
	}
	return 0;
}
5.3 switch语句中的default

switch语句的时候,我们经常可能遇到⼀种情况,⽐如switch后的表达式中的值⽆法匹配代码中的case语句的时候,这时候要不就不做处理,要不就得在switch语句中加⼊default⼦句。

switch后边的expression的结果不是value1,也不是value2的时候,就会执⾏default⼦句。

就⽐如前⾯做的打印星期的练习,如果day的输⼊不是1~7的值,如果我们要提⽰:输⼊错误,则可以这样完成代码:

#include<stdio.h>
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");
		break;//最好也带上break
	}
	return 0;
}
5.4 switch语句中的case和default的顺序问题

在switch语句中case语句和default语句是没有顺序要求的,只要你顺序是满足实际要求就可以,只不过我们习惯把default放在最后。

6.whlie语句

C语⾔提供了3种循环语句,while就是其中⼀种,接下来就介绍⼀下while语句。

while语句的语法结构和if很相似。

6.1 if和while的对比

if(表达式)

    语句;

while(表达式)

    语句;

区别:

while(1)会循环打印hello world,而if(1)只打印一次。

6.2 6.2while语句的执行流程

⾸先上来就是执⾏判断表达式,表达式的值为0,循环直接结束;表达式的值不为0,则执⾏循环语句,语句执⾏完后再继续判断,是否进⾏下⼀次判断。

6.3 while循环的实践

练习:在屏幕上打印1~10的值

#include <stdio.h>
int main()
{
	int i = 1;//初始化部分
	while (i<=10)//判断部分
	{
		printf("%d ", i);
		i++;//调整部分
	}
	return 0;
}
6.4 练习

输⼊⼀个正的整数,逆序打印这个整数的每⼀位

例如:

输⼊:1234,输出:4 3 2 1

输⼊:521,输出:1 2 5

分析:

  1. 要想得到n的最低位,可以使⽤n%10的运算,得到的余数就是最低位,如:1234%10得到4
  2. 要想去掉n的最低位,找出倒数第二位,则使用n=n/10操作就可以去掉最低位的,如:n=1234/10得到123,123相较于1234就去掉了最低位,123%10就得到倒数第⼆位3。
  3. 循环1和2两个步骤,在n变成0之前,就能到所有的位。

参考代码:

#include <stdio.h>
int main()
{
	int num = 0;
	scanf("%d", &num);
	while (num)
	{
		int a = num % 10;
		printf("%d ", a);
		num = num / 10;
	}
	return 0;
}

7.for循环

7.1 语法形式

for循环是三种循环中使⽤最多的,for循环的语法形式如下:

for(表达式1;表达式2;表达式3)

     语句;

表达式1⽤于循环变量的初始化

表达式2⽤于循环结束条件的判断

表达式3⽤于循环变量的调整

补充:for循环的表达式不要乱省略,比如:

按道理来说,应该是25个hehe呢,即:

但是省略了表达式的for循环只有5个hehe是为什么?因为第一幅图中的j循环5次后j=5,然后执行i++,到了for(;j<5;j++)这里,j仍然是5,for(;j<5;j++)后面的语句是不会执行的。而在图二,每次都给j重新赋值为0。

所以,在还不熟练的时候最好不要随意省略表达式。

7.2 for循环执行流程

首先执行表达式1初始化,接下来执行表达式2的判断部分,表达式2的结果如果==0,则循环结束;表达式2的结果如果!=0则执⾏循环语句,循环语句执⾏完后,再去执⾏表达式3,调整循环变量,然后再去表达式2的地⽅执⾏判断,表达式2的结果是否为0,决定循环是否继续。

整个循环的过程中,表达式1初始化部分只被执⾏1次,剩下的就是表达式2、循环语句、表达式3再循环表达式2...

7.3 for循环的实践

练习:在屏幕上打印1~100的值

参考代码:

#include <stdio.h>
int main()
{
	for (int num = 1; num < 100; num++)
		printf("%d ", num);
	return 0;
}
7.4 while循环和for循环的对比

for和while在实现循环的过程中都有初始化、判断、调整这三个部分,但是for循环的三个部分⾮常集中,便于代码的维护,⽽如果代码较多的时候while循环的三个部分就⽐较分散,所以从形式上for循环要更优⼀些。

7.5 练习

计算1~100之间3的倍数的数字之和

#include <stdio.h>
int main()
{
	int num = 0;
	int sum = 0;
	for (num = 0; num < 100; num++)
	{
		if (num % 3 == 0)
		{
			sum = sum + num;
		}
	}
	printf("%d ",sum);
	return 0;
}

优化:

#include <stdio.h>
int main()
{
	int sum = 0;
	for (int num = 0; num < 100; num+=3)//num+=3表示num=num+3
			sum = sum + num;
	printf("%d ", sum);
	return 0;
}
8.2 do while循环的执行流程

在do while循环中先执⾏图上的“语句”,执⾏完语句,在去执⾏“判断表达式”,判断表达式的结果是!=0,则继续循环,执⾏循环语句;判断表达式的结果==0,则循环结束。

比如:用do while打印1-10

#include<stdio.h>
int main()
{
	int n = 1;
	do
	{
		printf("%d ", n);
		n++;
	} while (n <= 10);//注意,这里有分号
	return 0;
}

一般do while使用在循环体至少被执行一次的情况下

8.4 练习

输⼊⼀个正整数,计算这个整数是⼏位数?例如:

输⼊:1234 输出:4

输⼊:12 输出:2

#include<stdio.h>
int main()
{
	int c = 0;
	int num = 0;
	scanf("%d", &num);
	do
	{
	    num = num / 10;
		c++;
	} while (num);
	printf("%d", c);
	return 0;
}

用do while的好处是,即使输入0,输出结果也是1位数,0也可以被统计到结果。

9.break和continue

在循环执⾏的过程中,如果某些状况发⽣的时候,需要提前终⽌循环,这是⾮常常⻅的现象。C语⾔中提供了break和continue两个关键字,就是应该到循环中的。

  • break的作⽤是⽤于永久的终⽌循环,只要break被执⾏,直接就会跳出循环,继续往后执⾏。
  • continue的作⽤是跳过本次循环continue后边的代码,在for循环和while循环中有所差异的。
9.1 while循环中的break和continue
9.1.1 break举例

#include <stdio.h>
int main()
{
    int i = 1;
    while (i <= 10)
    {
        if (i == 5)
            break;
        printf("%d ", i);
        i++;
    }
    return 0;
}

请问,上述代码结果是什么?

结果是1 2 3 4.原因是打印了1,2,3,4后,当i等于5的时候,循环break的地⽅终⽌,不再打印,不再循环。所以break的作⽤就是永久的终⽌循环,只要break被执⾏,break就会跳出第一次循环。那以后我们在循环中,想在某种条件下终⽌循环,则可以使⽤break来完成我们想要的效果。

9.1.2 continue举例

上⾯的代码,如果把break换成continue会是什么结果呢?

#include <stdio.h>
int main()
{
    int i = 1;
    while (i <= 10)
    {
        if (i == 5)
            continue;
        printf("%d ", i);
        i++;
    }
    return 0;
}

答案是:先打印1 2 3 4然后陷入死循环。

解析:当i等于5后,就执⾏continue,直接跳过continue后面的代码,去循环判断的地⽅。因为这⾥跳过了i = i+1,所以i⼀直为5,程序陷⼊和死循环。

9.2 for循环中的break和continue
9.2.1 break举例

其实whilefor循环中的break也是⽤于终⽌循环的,不管循环还需要循环多少次,只要执⾏到了break,循环就彻底终⽌,我们上代码。

#include <stdio.h>
int main()
{
	int i = 0;
	for (i = 1; i <= 10; i++)
	{
		if (i == 5)
			break;
		printf("%d ", i);
	}
	return 0;
}

结果为1 2 3 4

break的作⽤是永久的终⽌循环,未来我们在某个条件发⽣的时候,不想再继续循环的时候,就可以使⽤break来完成。

9.2.2 continue举例

上⾯的代码,如果把break换成continue会是什么结果呢?

#include <stdio.h>
int main()
{
	int i = 0;
	for (i = 1; i <= 10; i++)
	{
		if (i == 5)
			continue;
		printf("%d ", i);
	}
	return 0;
}

结果是:1 2 3 4 6 7 8 9 10

因为continue的作⽤是跳过本次循环中continue后的代码,直接去到循环的调整部分。未来当某个条件发⽣的时候,本次循环⽆需再执⾏后续某些操作的时候,就可以使⽤continue来实现。

9.3 do while循环中的break和continue

do while语句中的break和continue的作用和while循环中几乎一样。

#include <stdio.h>
int main()
{
	int i = 1;
	do
	{
		if (i == 5)
			break;
		printf("%d ", i);
			i = i + 1;
	} while (i <= 10);
	return 0;
}

结果仍然为1 2 3 4

改为continue是什么样呢?

#include <stdio.h>
int main()
{
	int i = 1;
	do
	{
		if (i == 5)
			continue;
		printf("%d ", i);
			i = i + 1;
	} while (i <= 10);
	return 0;
}

答案是1 2 3 4然后一直死循环,原理和前面一样

10.循环的嵌套

前面学了while,do while,for,这三种循环往往会嵌套在⼀起才能更好的解决问题,就是我们所说的:循环嵌套,这⾥我们就看⼀个例⼦。

10.1 练习

找出100~200之间的素数,并打印在屏幕上。

注:素数⼜称质数,只能被1和本⾝整除的数字。

10.2 题目解析
  1. 要从100~200之间找出素数,⾸先得有100~200之间的数,这⾥可以使⽤循环解决。
  2. 假设要判断i是否为素数,需要拿2~i-1之间的数字去试除i,需要产⽣2~i-1之间的数字,也可以使⽤循环解决。
  3. 如果2~i-1之间有数字能整除i,则i不是素数,如果都不能整除,则i是素数。
10.3 参考代码
#include<stdio.h>
int main()
{
	int i = 0;
	for (i = 100; i <= 200; i++)
	{
		int flag = 1;
		int j = 0;
		for (j = 2; j < i; j++)
		{
			if (i % j == 0)
				flag = 0;
                break;
		}
		if (flag == 1)// ==不要误写成=!
			printf("%d ", i);
	}
	return 0;
}

初学的宝子可能不会想到设一个flag,可能会按照题目写成:

#include <stdio.h>
int main()
{
    int i = 0;
    for (i = 100; i <= 200; i++)
    {
        int j = 0;
        for (j = 2; j < i; j++)
        {
            if (i % j != 0)
                printf("%d ", i);
        }
    }
    return 0;
}

上面是错误代码,没有考虑到for循环的嵌套,在 for (j = 2; j < i; j++)这个for循环里面写printf("%d ", i);将会导致打印出很多个i。所以要设一个flag,为1表示是素数,为0表示不是素数。

这种写法大家可以总结一下,看看什么情况下要这样写,以后就熟能生巧啦

另外一个错误就是,可能会把flag放在for循环的外面,即

#include<stdio.h>
int main()
{
    int i = 0;

    int flag=1;
    for (i = 100; i <= 200; i++)
    {
        int j = 0;
        for (j = 2; j < i; j++)
        {
            if (i % j == 0)
                flag = 0;

                break;
        }
        if (flag == 1)// ==不要误写成=!
            printf("%d ", i);
    }
    return 0;
}

乍一看好像没有什么问题,但是运行结果却不是想要的。其实我们可以在脑海里运行一下。比如:最开始i=100,j=2,模为0,所以flag赋值为0;再i=101,101%j是不会等于0的,可是这时候的flag没有变,还是0。再往后想一下,我们可以知道flag其实永远都是0,if (flag == 1)这条语句根本不会被用到。所以我们必须把flag写在for循环的里面,让flag有变化。

11.goto语句

goto语句可以实现在同⼀个函数内跳转到设置好的标号处。

例如:

#include<stdio.h>
int main()
{
	int i = 0;
	scanf("%d", &i);
	if (i < 1)
		goto next;
		printf("haha\n");
	return 0;
next:
	printf("跳过了haha的打印");
}

goto语句如果使⽤的不当,就会导致在函数内部随意乱跳转,打乱程序的执⾏流程,所以我们的建议是能不⽤尽量不去使⽤;但是goto语句也不是⼀⽆是处,在多层循环的代码中,如果想快速跳出使⽤goto就⾮常的⽅便了。

比如:

for (...)
{
    for (...)
    {
        for (...)
        {
            if (disaster)
                goto error;
        }
    }
}

error:...

本来for循环想提前退出得使用break,⼀个break只能跳出⼀层for循环,如果3层循环嵌套就得使⽤3个break才能跳出循环,所以在这种情况下我们使⽤goto语句就会更加的快捷。

另外,goto语句不仅可以往后跳,也可以往回跳。写法一样,我们可以根据需要使用。

12.本章节代码

https://gitee.com/guo-yaxinkaixin/programming-code-c3


完 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值