流程控制
关键词:选择判断、循环跳转、比较运算符、逻辑运算符、嵌套、条件表达式
一、引述
对于程序执行的流程顺序以及因应不同状况而选取不同的流程, 即为流程控制。流程控制可说是程序的灵魂, 它包含:条件判断、循环控制及条件跳跃三大类。
二、简述
选择语句要用到条件。条件就是布尔表达式,了解布尔类型、布尔值、布尔比较运算符、和布尔表达式。
(1)boolean类型的数据:用于声明boolean类型的数据变量;具有boolean值的变量称为boolean变量。
Java提供六种比较运算符也称关系运算符,用于比较两个值的大小。
运算符 | 名称 | 举例 | 结果 |
< | 小于 | radius<0 | false |
<= | 小于等于 | radius<=0 | false |
> | 大于 | radius>0 | true |
>= | 大于等于 | radius>=0 | true |
== | 等于 | radius==0 | false |
!= | 不等于 | radius!=0 | true |
注意:单个的(=)指赋值运算符;两个等号(==)才是传统意义上的相等,是比较运算符。
具有boolean型的变量只可能是以下这两个值中的一个:true和false。
true和false是直接量,不能作为标识符。
(2)逻辑运算符(也称 布尔运算符)是对布尔值进行的运算,它会创建新的布尔值。
Java提供六种逻辑运算符,用于操作布尔值。
运算符 | 名称 | 说明 | 举例 | 结果 | 口诀 |
& | AND(与) | 逻辑与 | false & true | false | 一假即假 |
| | OR(或) | 逻辑或 | false | true | true | 一真即真 |
! | NOT(非) | 逻辑非 | !true | false | 真假取反 |
^ | XOR(异或) | 逻辑异或 | true ^ false | true | 异真同假 |
&& | AND(短路与) | 条件与 | true &&false | false | 一假即假 |
|| | OR(短路或) | 条件或 | true ||false | true | 一真即真 |
说明:
&&(短路与)同&(逻辑与)的区别:
单个&参与运算时,左边无论真假,右边都参与运算。
两个&&参与运算时,如果左边为真,右边参与运算;如果左边为假,右边不参与运算。
||(短路或)同|(逻辑或)同理:单个|时,左右两边都参与运算。
两个||参与运算时,如果左边为真,右边不参与运算;如果左边为假,右边参与运算。
注意:布尔型值不能转换为其他类型的值,其他类型的值也不能转换成布尔型值。
表达式:1 <= dateOfMonth <=31 从数学的角度来看是正确的。但是,按照Java的语法来看是错误的。因为:首先按照运算顺序来看,同级比较运算符,自左向右计算1 <= dateOfMonth 得到一个布尔型的结果;一个布尔型的结果是不能同31一个整数型的数据相比较的。这两个操作数(一个布尔型和一个数值)是不兼容的。就如同你拿一个人的身高同另一个人的体重来做比较一样。
1 <= dateOfMonth <=31正确的Java表达式:
(1 <= dateOfMonth )&&(dateOfMonth <=31)
(3)目运算符(元运算符)
① 运算所需变量为一个的运算符叫单目运算符:逻辑非运算符!,按位取反运算符~,自增自减运算符++ --,负号运算符 -,类型转换运算符 (类型)。
② 运算所需变量为两个的运算符叫做双目运算符,例如+,-,*,/,%,<,>,>=,<=,==,!=,<<,>>,&,^,|,&&,||,=。
③ 运算所需变量为三个的运算符叫做三目运算符,只有条件表达式,语法如下:boolean-expresstion ? expresstion1 : expresstion2; (布尔表达式 ? 表达式1 : 表达式2)如果布尔表达式值为true,则条件表达式的结果为 表达式1;否则为表达式2;
例子:希望将num1和num2中较大的数赋值给max:
max = (num1 > num2) ? num1 : num2;
(4)选择语句:Java和所以高级程序设计语言一样提供选择语句,以便在两个或更多的流程中做出选择。其中选择语句需要条件判断,条件就是布尔表达式。
Java提供了五种类型的选择语句:
单向if语句、双向if语句、嵌套if语句、switch语句、条件表达式(三目运算式)。
① 单向if语句:单向if语句是指仅当条件为true时执行的动作。单向if语句的语法: if(布尔表达式){
执行代码语句(块)
}
注意:
如果布尔表达式的结果为true时,才执行代码块中的语句,否则,不会执行。
布尔表达式应用括号括住。
大括号(花括号)内只有一条语句,则可以省略大括号(花括号)。
② 双向if语句:如果你想指定条件为false时程序执行的动作,可以使用双向if语句。根据条件为true 或者 false,双向if语句可以指定不同的操作。
双向if语句的语法:
if(布尔表达式){
布尔表达式为真时执行的语句(块);
}
else{
布尔表达式为假时执行的语句(块);
}
提示:
当大括号(花括号)内只有一条语句,则可以省略大括号(花括号)。
③ 嵌套的if选择:如果程序需要实现多重选择时,可以使用嵌套。我们把外层的if语句里的内层if语句称为嵌套的。当然内层的if语句还可以包含其他if语句,事实上,对于嵌套的深度是没有限制的。
if嵌套的一种示例:
If(布尔表达式){
If(布尔表达式){
执行代码语句(块)
}
Else if(布尔表达式){
执行代码语句(块)
}
Else(布尔表达式){
执行代码语句(块)
}
}
Else{
执行代码语句(块)
}
注意:为了提供代码的可读性,避免深度缩减 和 深度嵌套。
if选择语句中常见的错误:
1.忘记大括号:当不添加大括号时,程序默认执行距if或者else最近的那一条语句。
2.在if行加上一个分号。例如:if( radius >= 0);——逻辑错误;
3.错误的布尔表达式:常常把赋值符(=)同相等比较符(==)混淆;例如:
if( flag = true) 这条语句没有语法错误,它给flag赋值true,这样flag恒等于true。
if(flag == true) 这条语句是判断flag的值是否为true。
4.else歧义:在同一个代码块中,else总是和距离它最近的if子句相匹配。
④ switch语句:当选择条件繁多时,为避免使用过多的嵌套if语句,Java提供switch
语句来处理多重条件的问题。switch语句的语法:
switch ( witch){
case 值1:语句(块);
break;
case 值2:语句(块);
break;
case 值3:语句(块);
break;
……
case 值N:语句(块);
break;
default :默认情况下执行的语句(块);
}
使用switch语句注意的细节:
1.switch表达式必须能计算出一个char、byte、short、或int型值,并总是用括号括住。
2.value1,……value N必须是与switch表达式的值具有相同的数据类型。其中value都是常量表达式,这里是不能包含变量的。
3.当switch表达式与case语句的值相匹配的时候,执行从该case开始的语句,知道遇到break语句或者到达该switch语句的末端(即向下贯通行为)。
4.关键字break是可选,break语句会立刻终止整个switch语句。
5.default语句是可选的,用来指定:当没有一个value值与switch表达式相匹配时的默认操作。
6.case语句是顺序检测判断执行的。
⑤ 条件表达式:有时给特定条件的变量赋值,一种很简捷的方法,语句中没有明确的if。
语法如下:boolean-expresstion ? expresstion1 : expresstion2;
(布尔表达式 ? 表达式1 : 表达式2)如果布尔表达式值为true,则条件表达式的结果为 表达式1;否则为表达式2;
例子:希望将num1和num2中较大的数赋值给max:
max = (num1 > num2) ? num1 : num2;
(5)循环语句:用来控制语句块重复执行的一种数据结构。循环语句的是程序设计的基础。Java提供四种类型的循环语句:while循环、do--while循环 和 for循环、for--each循环。
① while循环:
语法格式:
while(循环继续条件){
需要循环执行的语句;
}
标志值控制循环:即循环继续条件是一个标志值 如 :while(flag != 0){}
控制循环的常用技术是在读取和处理一个集合的值时指派一个特殊值。这个特殊的输入值称为标志值,用来表明循环的结束。如果一个循环通过标志值来控制它的执行,它就被称为标志值控制的循环。
while循环说明:
1.循环中包含的重复执行的语句部分被称为循环体。循环体每执行一次称为迭代一次。
2.每个循环都含有循环继续条件,循环条件是一个布尔表达式,控制循环体的执行。
3.在循环体执行前,总是先计算循环条件以决定是否继续执行它。循环条件为true则继续执行循环体;循环条件为false,则终止整个循环并执行while循环后的下一条语句。
while循环注意:
1.循环继续条件总是放在圆括号内,当循环体只包含一条语句,或不包含语句时,循环体的大括号(花括号)才可以被省略。
2.不要在循环继续条件后添加分号。
3.要保证循环继续条件最终会变成false,以便程序可以能够结束,否则会变成无限循环。
4.准确的循环条件,避免差一错误。(差一错误:因为不准确的循环条件,致使循环体多执行或者少执行一次)。
5.在循环控制中不要使用浮点数来比较值是否相等,因为浮点值都是某些值的近似值。使用它们可能会导致不准确的循环次数和不准确的结果。
② do--while循环
语法格式:
do{
循环体
}while(循环继续条件);
do--while循环说明:
1.do--while循环是while循环的变体;与while循环不同,它首先执行循环体,然后再计算循环继续条件判断循环是否继续。
2.do--while与while循环的区别:计算循环继续条件和执行循环语句的先后顺序不同。
do--while循环注意:
忘记分号:while(循环继续条件);
do--while适用情景提示:
当循环中的语句至少需要执行一次。
③for循环
语法格式:
for(初始操作;循环继续条件;每次迭代后的操作){
循环体
}
for循环说明:
1.for循环是从关键字for开始的,然后用双括号(圆括号和大括号)括住的循环结构体。
包括圆括号中的 控制结构体:初始动作,循环继续条件,和每次迭代后的动作。和大括号(花括号)中的循环结构体。
2.控制结构体中的 初始操作;循环继续条件;每次迭代后的操作,都要用分号分隔开。
3.一般情况下,for循环使用一个变量来控制循环体的执行次数,以及什么时候循环停止。这个变量称为控制变量。初始化动作是为了对控制变量进行初始化,每次迭代后操作都会对控制变量进行自增或自减操作。
4.for循环只执行一次初始动作,当循环条件继续为真的时候,重复执行循环体中的语句,然后完成迭代后的操作。
5.循环继续条件是一个布尔表达式,这个表达式在 控制变量初始化之后 和 迭代操作完成后 都会对控制变量进行一次判断,循环继续条件会检测控制变量是否达到终止值。如果为true则继续执行该循环体;如果结果为false则循环终止,程序转移执行到for循环后的下一条语句。
for循环提示:
控制变量必须在控制循环体内 或者 循环前说明。如果循环控制变量只在循环内使用而不在其他地方使用,那么在for循环的初始化动作中声明是一个很好的编程习惯。但是,在循环控制体内的变量不能循环外引用它。
for循环注意:
1.for循环的初始动作可以是0个或是多个以逗号隔开的变量声明语句或者赋值表达式。
2.for循环每次迭代后的操作也可以是0个或者多个以逗号隔开的语句。
3.不要在循环控制结构体后面添加分号。
4.如果省略for循环中的循环继续条件,则隐含的认为循环继续条件为true,即为无限循环。
④for--each循环:
语法格式:
for(数据类型 迭代变量名: 集合名){
循环体
}
for--each循环说明:
for--each循环也叫增强for循环(JDK.15开始支持),for--each循环的特点是没有角标指针,不能通过指针对元素进行操作。
for--each适用情景:遍历数组,而不对角标指针进行操作
for--each注意事项:
1.迭代变量必须在( )中定义
2.集合可以是数组;或者是实现了Interable接口的集合类
(6)while循环、do--while循环、for循环、for--each循环的适用情景:
循环继续条件在循环体之前判断的循环称为预测试循环。如:while循环和for循环。
循环继续条件在循环体之后判断的循环称为后测试循环。如:do--while循环。
其中,while循环总能转写成for循环;但是不是所有的for循环都可以转写成while循环。
for循环;
while循环;
do--while循环;
for--each循环;
(7)嵌套循环:嵌套循环是由一个外层循环和多个内层循环组成的,每当重复执行一次外层循环时再进入内层循环,然后重新开始。
(8)循环设计策略:
1.确定需要循环的语句。
2.根据执行特点,选择一个循环结构,将这些语句放入一个循环中。
3.编写循环继续条件,并为控制循环添加合适的语句。
(9)跳转语句:关键字break和continue可以在循环中使用,为循环提供额外的控制。
1.break关键词可以在选择语句中使用,也可在循环中使用。break可以立即终止该循环;如果break语句在内层循环,那么当执行到break关键字时流程会跳出包含break的内层循环。
2.循环中关键字continue的作用:当程序遇到continue关键字时,它会结束当前的迭代,程序控制会转向该循环体的末尾。
注意:
continue语句的跳转总是在一个循环内,在while和do--while循环中,continue语句之后会马上计算循环继续条件;而在for循环中,continue语句之后会立即先执行每次迭代后的动作,再计算循环条件。
区别:break是跳出了整个循环,但是continue只是跳出了一次迭代,并未跳出整个循环。