1月19日 C Primer Plus学习
7.7 多重选择:switch 和break
使用条件运算符和 if else 语句很容易编写二选一的程序。然而,有时程序需要在多个选项中进行选择。可以用if else if...else来完成。但是,大多数情况下使用switch语句更方便。
7.7.1 switch 语句
要对紧跟在关键字 switch 后圆括号中的表达式求值。然后程序扫描标签列表,直到发现一个匹配的值为止。然后程序跳转至那一行。如果没有匹配的标签怎么办?如果有default :标签行,就跳转至该行;否则,程序继续执行在switch后面的语句。 break语句在其中起什么作用?它让程序离开switch语句,跳至switch语句后面的下一条语句如果没有break语句,就会从匹配标签开始执行到switch末尾。

顺带一提,break语句可用于循环和switch语句中,但是continue只能用于循环中。尽管如此,如果switch语句在一个循环中,continue便可作为 switch语句的一部分。这种情况下,就像在其他循环中一样,continue让程序跳出循环的剩余部分,包括switch语句的其他部分。
C语言的case一般都指定一个值,不能使用一个范围。
switch在圆括号中的测试表达式的值应该是一个整数值(包括char类型)。case标签必须是整数类型(包括char类型)的常量或整型常量表达式(即,表达式中只包含整型常量)。不能用变量作为case标签。
7.7.2 只读每行的首字符
/* animals.c -- 使用switch语句 */
#include <stdio.h>
#include <ctype.h>
int main(void)
{
char ch;
printf("Give me a letter of the alphabet, and I will give ");
printf("an animal name\nbeginning with that letter.\n");
printf("Please type in a letter; type # to end my act.\n");
while ((ch = getchar()) != '#')
{
if ('\n' == ch)
continue;
if (islower(ch)) /* 只接受小写字母*/
switch (ch)
{
case 'a':
printf("argali, a wild sheep of Asia\n");
break;
case 'b':
printf("babirusa, a wild pig of Malay\n");
break;
case 'c':
printf("coati, racoonlike mammal\n");
break;
case 'd':
printf("desman, aquatic, molelike critter\n");
break;
case 'e':
printf("echidna, the spiny anteater\n");
break;
case 'f':
printf("fisher, brownish marten\n");
break;
default:
printf("That's a stumper!\n");
} /* switch结束 */
else printf("I recognize only lowercase letters.\n");
while (getchar() != '\n')
continue; /* 跳过输入行的剩余部分 */
printf("Please type another letter or a #.\n");
} /* while循环结束 */
printf("Bye!\n");
return 0;
}
一个独特之处是它读取输入的方式。运行程序时读者可能注意到了,当输入dab时,只处理了第1个字符。这种丢弃一行中其他字符的行为,经常出现在响应单字符的交互程序中。可以用下面的代码实现这样的行为:
while (getchar() != '\n')
continue; /* 跳过输入行的其余部分 */
循环从输入中读取字符,包括按下Enter键产生的换行符。注意,函数的返回值并没有赋给ch,以上代码所做的只是读取并丢弃字符。由于最后丢弃的字符是换行符,所以下一个被读取的字符是下一行的首字母。在外层的 while循环中,getchar()读取首字母并赋给ch。假设用户一开始就按下Enter键,那么程序读到的首个字符就是换行符。下面的代码处理这种情况:
if (ch == '\n') continue;
7.7.3 多重标签
没有关联break语句,所以程序流直接执行下一条语句。
7.7.4 switch 和if else
如果是根据浮点类型的变量或表达式来选择,就无法使用 switch。
如果根据变量在某范围内决定程序流的去向,使用 switch 就很麻烦,使用if 很方便。
如果使用switch,程序通常运行快一些,生成的代码少一些。
编程练习第11题
点击查看
#include<stdio.h>
void showMenu(void);
float addWeight(void);
int main(void)
{
float weightYJ,weightTC,weightHLB;
char selection;
do
{
showMenu();
scanf("%c",&selection);
switch (selection)
{
case 'a':
weightYJ += addWeight();
break;
case 'b':
weightTC += addWeight();
break;
case 'c':
weightHLB += addWeight();
case 'q':
break;
default:
printf("请按照要求输入\n");
}
}while(selection != 'q');
static float YJ = 2.05;
static float TC = 1.15;
static float HLB = 1.09;
printf("\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n");
printf("-------------------------------------------------\n");
printf("您订购了:\n");
printf("洋蓟(%.2f美元/磅) * %f磅 .......%f美元\n",YJ,weightYJ,weightYJ*YJ);
printf("甜菜(%.2f美元/磅) * %f磅 .......%f美元\n",TC,weightTC,weightTC*TC);
printf("胡萝卜(%.2f美元/磅) * %f磅 ......%f美元\n",HLB,weightHLB,weightHLB*HLB);
printf("订购的蔬菜费用:%f美元\n",weightYJ*YJ+weightTC*TC+weightHLB*HLB);
float discount;
if (weightYJ*YJ+weightTC*TC+weightHLB*HLB > 100)
{
discount = (weightYJ*YJ+weightTC*TC+weightHLB*HLB)*0.05;
}
else
{
discount = 0;
}
printf("订单的总费用:%f\n",weightYJ*YJ+weightTC*TC+weightHLB*HLB - discount);
printf("折扣:%f\n",(weightYJ*YJ+weightTC*TC+weightHLB*HLB)*0.05);
float freight;
if (weightYJ+weightTC+weightHLB <= 5)
{
freight = 6.5;
}
else if (weightYJ+weightTC+weightHLB > 5 && weightYJ+weightTC+weightHLB <= 20)
{
freight = 14;
}
else
{
freight = 14 + ((weightYJ+weightTC+weightHLB) - 20) * 0.5;
}
printf("运费和包装费:%f\n",freight);
printf("所有费用的总额:%f",weightYJ*YJ+weightTC*TC+weightHLB*HLB - discount + freight);
return 0;
}
void showMenu(void)
{
printf("-------------------------------------------------\n");
printf("选择你所要订购的内容:\n");
printf("a.洋蓟 b.甜菜 c.胡萝卜 q.退出订购\n");
printf("-------------------------------------------------\n");
}
float addWeight(void)
{
printf("请输入你要订购的具体重量(磅):\n");
float weight;
scanf("%f",&weight);
printf("\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n");
getchar();
return weight;
}
下列为运行结果:







浙公网安备 33010602011771号