第3章 运算符与流程控制
本章要点
掌握Java运算符的使用方法
掌握if语句使用方法
掌握swith语句使用方法
理解if语句和switch语句的区别
掌握while、do...while和for语句的使用方法,理解三种语句的区别
理解跳转语句的使用
程序运行时通常是按由上至下的顺次执行的,但有时程序会根据不同的情况,选择不同的语句区块来运行,或是必须重复运行某一语句区块,或是跳转到某一语句区块继续运行。这些根据不同条件运行不同语句区块的方式被称为“程序流程控制”。Java语言中的流程控制语句有分支语句、循环语句和跳转语句3种。
3.1 运算符
在Java语言中,与类无关的运算符主要有赋值运算符、算术运算符、关系运算符、逻辑运算符和位运算符,下面将一一介绍各个运算符的使用方法。
3.1.1 赋值运算符
赋值运算符的符号为“=”,它的作用是将数据、变量或对象赋值给相应类型的变量或对象,例如下面的代码:
赋值运算符
int i = 75; // 将数据赋值给变量
long l = i; // 将变量赋值给变量
Object object = new Object(); // 创建对象
赋值运算符的结合性为从右到左。例如,在下面的代码中,首先是计算表达式“9412 + 75”,然后将计算结果赋值给变量result:
int result = 9412 + 75;
如果两个变量的值相同,也可以采用下面的方式完成赋值操作,具体代码如下:
int x, y; // 声明两个int型变量
x = y = 0; // 为两个变量同时赋值
3.1.2 算术运算符
算术运算符支持整数型数据和浮点数型数据的运算,当整数型数据与浮点数型数据之间进行算术运算时,Java会自动完成数据类型的转换,并且计算结果为浮点数型。Java语言中算术运算符的功能及使用方法如表3-1所示。
算术运算符
表3-1 算术运算符
运 算 符 |
功 能 |
举 例 |
运 算 结 果 |
结 果 类 型 |
---|---|---|---|---|
+ |
加法运算 |
10 + 7.5 |
17.5 |
double |
- |
减法运算 |
10 - 7.5F |
2.5F |
float |
* |
乘法运算 |
3 * 7 |
21 |
int |
/ |
除法运算 |
21 / 3L |
7L |
long |
% |
求余运算 |
10 % 3 |
1 |
int |
在进行算术运算时,有两种情况需要考虑,一种情况是没有小数参与运算,另一种情况则是有小数参与运算。
1.没有小数参与运算
在对整数型数据或变量进行加法(+)、减法(-)和乘法(*)运算时,与数学中的运算方式完全相同,这里就不再介绍了。下面介绍在整数之间进行除法(/)和求余(%)运算时需要注意的问题。
(1)进行除法运算时需要注意的问题。
当在整数型数据和变量之间进行除法运算时,无论能否整除,运算结果都将是一个整数,并且并不是通过四舍五入得到的整数,而只是简单地去掉小数部分。例如,通过下面的代码分别计算10除以3和5除以2,最终输出的运算结果依次为3和2:
System.out.println(10 / 3); // 最终输出的运算结果为3
System.out.println(5 / 2); // 最终输出的运算结果为2
(2)进行求余运算时需要注意的问题。
当在整数型数据和变量之间进行求余运算时,运算结果为数学运算中的余数。例如,通过下面的代码分别计算10除以3求余数、10除以5求余数和10除以7求余数,最终输出的运算结果依次为1、0和3:
System.out.println(10 % 3); // 最终输出的运算结果为1
System.out.println(10 % 5); // 最终输出的运算结果为0
System.out.println(10 % 7); // 最终输出的运算结果为3
(3)关于0的问题。
与数学运算一样,0可以做被除数,但是不可以做除数。当0做被除数时,无论是除法运算,还是求余运算,运算结果都为0。例如,通过下面的代码分别计算0除以6和0除以6求余数,最终输出的运算结果均为0:
System.out.println(0 / 6); // 最终输出的运算结果为0
System.out.println(0 % 6); // 最终输出的运算结果为0
如果0做除数,虽然可以编译成功,但是在运行时会抛出java.lang.ArithmeticException异常,即算术运算异常。
2.有小数参与运算
在对浮点数型数据或变量进行算术运算时,如果在算术表达式中含有double型数据或变量,则运算结果为double型,否则运算结果为float型。
在对浮点数型数据或变量进行算术运算时,计算出的结果在小数点后可能会包含n位小数,这些小数在有些时候并不是精确的,计算出的结果反而会与数学运算中的结果存在一定的误差,只能是尽量接近数学运算中的结果。例如,在计算4.0减去2.1时,不同的数据类型会得到不同的计算结果,但是都是尽量接近或等于数学运算结果1.9,具体代码如下:
System.out.println(4.0F - 2.1F); // 输出的运算结果为1.9000001
System.out.println(4.0 - 2.1F); // 输出的运算结果为1.9000000953674316
System.out.println(4.0F - 2.1); // 输出的运算结果为1.9
System.out.println(4.0 - 2.1); // 输出的运算结果为1.9
如果被除数为浮点数型数据或变量,无论是除法运算,还是求余运算,0都可以做除数。如果是除法运算,当被除数是正数时,运算结果为Infinity,表示无穷大,当被除数是负数时,运算结果为-Infinity,表示无穷小;如果是求余运算,运算结果为NaN,例如下面的代码:
System.out.println(7.5 / 0); // 输出的运算结果为Infinity
System.out.println(-7.5 / 0); // 输出的运算结果为-Infinity
System.out.println(7.5 % 0); // 输出的运算结果为NaN
System.out.println(-7.5 % 0); // 输出的运算结果为NaN
3.1.3 关系运算符
关系运算符用于比较大小,运算结果为boolean型。当关系表达式成立时,运算结果为true;当关系表达式不成立时,运算结果为false。Java中的关系运算符如表3-2所示。
关系运算符
表3-2 关系运算符
运 算 符 |
功 能 |
举 例 |
运 算 结 果 |
可运算数据类型 |
---|---|---|---|---|
> |
大于 |
'a' > 'b' |
false |
整数型、浮点数型、字符型 |
< |
小于 |
2 < 3.0 |
true |
整数型、浮点数型、字符型 |
== |
等于 |
'X' == 88 |
true |
所有数据类型 |
!= |
不等于 |
true != true |
false |
所有数据类型 |
>= |
大于或等于 |
6.6 >= 8.8 |
false |
整数型、浮点数型、字符型 |
<= |
小于或等于 |
'M' <= 88 |
true |
整数型、浮点数型、字符型 |
从表3-2中可以看出,所有关系运算符均可用于整数型、浮点数型和字符型,其中“==”和“!=”还可用于boolean型和引用数据类型,即可用于所有的数据类型。
要注意关系运算符“==”和赋值运算符“=”的区别!
3.1.4 逻辑运算符
逻辑运算符用于对boolean型数据进行运算,运算结果仍为boolean型。Java中的逻辑运算符有“!(取反)”“^(异或)”“&(非简洁与)”“|(非简洁或)”“&&(简洁与)”和“||(简洁或)”,下面将依次介绍各个运算符的用法和特点。
逻辑运算符
1.运算符“! ”
运算符“!”用于对逻辑值进行取反运算。当逻辑值为true时,经过取反运算后运算结果为false;当逻辑值为false时,经过取反运算后运算结果则为true,例如下面的代码:
System.out.println(!true); // 输出的运算结果为false
System.out.println(!false); // 输出的运算结果为true
2.运算符“^”
运算符“^”用于对逻辑值进行异或运算。当运算符的两侧同时为true或false时,运算结果为false,否则运算结果为true,例如下面的代码:
System.out.println(true ^ true); // 输出的运算结果为false
System.out.println(true ^ false); // 输出的运算结果为true
System.out.println(false ^ true); // 输出的运算结果为true
System.out.println(false ^ false); // 输出的运算结果为false
3.运算符“&&”和“&”
运算符“&& ”和“&”均用于逻辑与运算。当运算符的两侧同时为true时,运算结果为true,否则运算结果均为false,例如下面的代码:
System.out.println(true & true); // 输出的运算结果为true
System.out.println(true & false); // 输出的运算结果为false
System.out.println(false & true); // 输出的运算结果为false
System.out.println(false & false); // 输出的运算结果为false
System.out.println(true && true); // 输出的运算结果为true
System.out.println(true && false); // 输出的运算结果为false
System.out.println(false && true); // 输出的运算结果为false
System.out.println(false && false); // 输出的运算结果为false
运算符“&&”为简洁与运算符,运算符“&”为非简洁与运算符,它们的区别如下:
(1)运算符“&&”只有在其左侧为true时,才运算其右侧的逻辑表达式,否则直接返回运算结果false;
(2)运算符“&”无论其左侧为true或false,都要运算其右侧的逻辑表达式,最后才返回运算结果。
下面首先声明两个int型变量x和y,并分别初始化为7和5,然后运算表达式“(x < y) && (x++ == y--)”,并输出表达式的运算结果。在这个表达式中,如果运算符“&&”右侧的表达式“(x++ == y--)”被执行,变量x和y的值将分别变为8和4,最后输出变量x和y的值,具体代码如下:
int x = 7, y = 5;
System.out.println((x < y) && (x++ == y--)); // 输出的运算结果为false
System.out.println("x=" + x); // 输出x的值为7
System.out.println("y=" + y); // 输出y的值为5
执行上面的代码,输出表达式的运算结果为false,输出变量x和y的值分别为7和5,说明当运算符“&&”的左侧为false时,并不执行右侧的表达式。下面将运算符“&&”修改为“&”,具体代码如下:
int x = 7, y = 5;
System.out.println((x < y) & (x++ == y--)); // 输出的运算结果为false
System.out.println("x=" + x); // 输出x的值为8
System.out.println("y=" + y); // 输出y的值为4
执行上面的代码,输出表达式的运算结果为false,输出变量x和y的值分别为8和4,说明当运算符“&”的左侧为false时,也要执行右侧的表达式。
4.运算符“||”和“|”
运算符“|| ”和“|”均用于逻辑或运算。当运算符的两侧同时为false时,运算结果为false,否则运算结果均为true,例如下面的代码:
System.out.println(true | true); // 输出的运算结果为true
System.out.println(true | false); // 输出的运算结果为true
System.out.println(false | true); // 输出的运算结果为true
System.out.println(false | false); // 输出的运算结果为false
System.out.println(true || true); // 输出的运算结果为true
System.out.println(true || false); // 输出的运算结果为true
System.out.println(false || true); // 输出的运算结果为true
System.out.println(false || false); // 输出的运算结果为false
运算符“||”为简洁或运算符,运算符“|”为非简洁或运算符,它们的区别如下:
(1)运算符“||”只有在其左侧为false时,才运算其右侧的逻辑表达式,否则直接返回运算结果true;
(2)运算符“|”无论其左侧为true或false,都要运算其右侧的逻辑表达式,最后才返回运算结果。
下面首先声明两个int型变量x和y,并分别初始化为7和5,然后运算表达式“(x > y) || (x++ == y--)”,并输出表达式的运算结果。在这个表达式中,如果运算符“||”右侧的表达式“(x++ == y--)”被执行,变量x和y的值将分别变为8和4,最后输出变量x和y的值,具体代码如下:
int x = 7, y = 5;
System.out.println((x > y) || (x++ == y--)); // 输出的运算结果为true
System.out.println("x=" + x); // 输出x的值为7
System.out.println("y=" + y); // 输出y的值为5
执行上面的代码,输出表达式的运算结果为true,输出变量x和y的值分别为7和5,说明当运算符“||”的左侧为true时,并不执行右侧的表达式。下面将运算符“||”修改为“|”,具体代码如下:
int x = 7, y = 5;
System.out.println((x > y) | (x++ == y--)); // 输出的运算结果为true
System.out.println("x=" + x); // 输出x的值为8
System.out.println("y=" + y); // 输出y的值为4
执行上面的代码,输出表达式的运算结果为true,输出变量x和y的值分别为8和4,说明当运算符“|”的左侧为true时,也要执行右侧的表达式。
3.1.5 位运算符
位运算是对操作数以二进制位为单位进行的操作和运算,运算结果均为整数型。位运算符又分为逻辑位运算符和移位运算符。
位运算符
1.逻辑位运算符
逻辑位运算符有“~(按位取反)”、“&(按位与)”、“|(按位或)”和“^(按位异或)”,用来对操作数进行按位运算,它们的运算规则如表3-3所示。
表3-3 逻辑位运算符的运算规则
操作数x |
操作数y |
~ x |
x & y |
x | y |
x ^ y |
---|---|---|---|---|---|
0 |
0 |
1 |
0 |
0 |
0 |
0 |
1 |
1 |
0 |
1 |
1 |
1 |
0 |
0 |
0 |
1 |
1 |
1 |
1 |
0 |
1 |
1 |
0 |
按位取反运算是将二进制位中的0修改为1,1修改为0;在进行按位与运算时,只有当两个二进制位都为1时,结果才为1;在进行按位或运算时,只要有一个二进制位为1,结果就为1;在进行按位异或运算时,当两个二进制位同时为0或1时,结果为0,否则结果为1。
【例3-1】 逻辑位运算符的运算规则。
下面是几个用来理解各个逻辑位运算符运算规则的例子,具体代码如下:
public class Example {
public static void main(String[] args) {
int a = 5 & -4; // 运算结果为4
int b = 3 | 6; // 运算结果为7
int c = 10 ^ 3; // 运算结果为9
int d = ~(-14); // 运算结果为13
}
}
上面代码中各表达式的运算过程分别如图3-1~图3-4所示。
图3-1 表达式“5 & -4”的运算过程
图3-2 表达式“3 | 6”的运算过程
图3-3 表达式“10 ^ 3”的运算过程
图3-4 表达式“~ (-14)”的运算过程
2.移位运算符
移位运算符有“<<(左移,低位添0补齐)”、“>>(右移,高位添符号位)”和“>>>(右移,高位添0补齐)”,用来对操作数进行移位运算。
【例3-2】 移位运算符的运算规则。
下面是几个用来理解各个移位运算符运算规则的例子,具体代码如下:
public class Example {
public static void main(String[] args) {
int a = -2 << 3; // 运算结果为-16,运算过程如图3-5所示
int c = 15 >> 2; // 运算结果为3,运算过程如图3-6所示
int e = 4 >>> 2; // 运算结果为1,运算过程如图3-7所示
int f = -5 >>> 1; // 运算结果为2147483645,运算过程如图3-8所示
}
}
上面代码中各表达式的运算过程分别如图3-5~图3-8所示。
图3-5 表达式“-2 << 3”的运算过程
图3-6 表达式“15 >> 2”的运算过程
图3-7 表达式“4 >>> 2”的运算过程
图3-8 表达式“-5 >>> 1”的运算过程
3.1.6 对象运算符
对象运算符(Instanceof)用来判断对象是否为某一类型,运算结果为boolean型,如果是则返回true,否则返回false。对象运算符的关键字为“instanceof”,它的用法为:
对象运算符
对象标识符 instanceof 类型标识符
例如:
java.util.Date date = new java.util.Date();
System.out.println(date instanceof java.util.Date); // 运算结果为true
System.out.println(date instanceof java.sql.Date); // 运算结果为false
3.1.7 其他运算符
除了前面介绍的几类运算符外,Java中还有一些不属于上述类别的运算符,如表3-4所示。
其他运算符
表3-4 其他运算符的运算规则
运算符 |
说 明 |
运算结果类型 |
---|---|---|
++ |
一元运算符,自动递增 |
与操作元的类型相同 |
-- |
一元运算符,自动递减 |
与操作元的类型相同 |
?: |
三元运算符,根据“?”左侧的逻辑值,决定返回“:”两侧中的一个值,类似“if...else”流程控制语句 |
与返回值的类型相同 |
[] |
用于声明、建立或访问数组的元素 |
若用于创建数组对象,则类型为数组;若用于访问数组元素,则类型为该数组的类型 |
. |
用来访问类的成员或对象的实例成员 |
若访问的是成员变量,则类型与该变量相同;若访问的是方法,则类型与该方法的返回值相同 |
1.自动递增、递减运算符
与C、C++相同,Java语言也提供了自动递增与递减运算符,其作用是自动将变量值加1或减1。它们既可以放在操作元的前面,也可以放在操作元的后面,根据运算符位置的不同,最终得到的结果也是不同的:放在操作元前面的自动递增、递减运算符,会先将变量的值加1,然后再使该变量参与表达式的运算;放在操作元后面的递增、递减运算符,会先使变量参与表达式的运算,然后再将该变量加1。例如:
int num1=3;
int num2=3;
int a=2+(++num1); //先将变量num1加1,然后再执行"2+4"
int b=2+(num2++); //先执行"2+3",然后再将变量num2加1
System.out.println(a); //输出结果为:6
System.out.println(b); //输出结果为:5
System.out.println(num1); //输出结果为:4
System.out.println(num2); //输出结果为:4
自动递增、递减运算符的操作元只能为变量,不能为字面常数和表达式,且该变量类型必须为整数型、浮点型或Java包装类型。例如,“++1”“(num+2)++”都是不合法的。
2.三元运算符“?:”
三元运算符“?:”的应用形式如下:
逻辑表达式 ? 表达式1 : 表达式2
三元运算符“?:”的运算规则为:若逻辑表达式的值为true,则整个表达式的值为表达式1的值,否则为表达式2的值。例如:
int store=12;
System.out.println(store<=5?"库存不足!":"库存量:"+store); //输出结果为"库存量:12"
以上代码等价于如下的“if...else”语句:
int store = 12;
if (store <= 5)
System.out.println("库存不足!");
else
System.out.println("库存:" + store);
应该注意的是,对于三元运算符“?:”中的表达式1和表达式2,只有其中的一个会被执行,例如:
int x = 7, y = 5;
System.out.println(x > y ? x++ : y++); // 输出结果为7
System.out.println("x=" + x); // x的值为8
System.out.println("y=" + y); // y的值为5
3.1.8 运算符的优先级别及结合性
当在一个表达式中存在多个运算符进行混合运算时,会根据运算符的优先级别来决定执行顺序。运算符优先级的顺序,如表3-5所示。
运算符的优先级别及结合性
表3-5 Java语言中运算符的优先级
优 先 级 |
说 明 |
运 算 符 |
||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
最高 |
括号 |
() |
|
|
|
|||||||||
↓ |
后置运算符 |
[] |
. |
|
|
|||||||||
正负号 |
+ |
- |
|
|
||||||||||
一元运算符 |
++ |
-- |
! |
~ |
||||||||||
乘除运算 |
* |
/ |
% |
|
||||||||||
加减运算 |
+ |
- |
|
|
||||||||||
移位运算 |
<< |
>> |
>>> |
|
||||||||||
比较大小 |
< |
> |
<= |
>= |
||||||||||
比较是否相等 |
== |
!= |
|
|
||||||||||
按位与运算 |
& |
|
|
|
||||||||||
按位异或运算 |
^ |
|
|
|
||||||||||
按位或运算 |
| |
|
|
|
||||||||||
逻辑与运算 |
&& |
|
|
|
||||||||||
逻辑或运算 |
|| |
|
|
|
||||||||||
三元运算符 |
?: |
|
|
|
||||||||||
最低 |
赋值及复合赋值 |
= |
*= |
/= |
%= |
+= |
- = |
>>= |
>>>= |
<<<= |
&= |
^ = |
| = |
表3-5所列运算符的优先级,由上而下逐渐降低。其中,优先级最高的是之前未提及的括号“()”,它的使用与数学运算中的括号一样,只是用来指定括号内的表达式要优先处理,括号内的多个运算符,仍然要依照表3-5的优先级顺序进行运算。
对于处在同一层级的运算符,则按照它们的结合性,即“先左后右”还是“先右后左”的顺序来执行。Java中除赋值运算符的结合性为“先右后左”外,其他所有运算符的结合性都是“先左后右”。
3.2 if语句
If语句也称条件语句,就是对语句中不同条件的值进行判断,从而根据不同的条件执行不同的语句。
3.2.1 简单的if条件语句
条件语句可分为以下3种形式:
简单的if条件语句
(1)简单的if条件语句;
(2)if...else条件语句;
(3)if...else if多分支条件语句。
简单的if条件语句就是对某种条件进行相应的处理。通常表现为“如果满足某种情况,那么就进行某种处理”。它的一般形式为:
if(表达式){
语句序列
}
例如:如果今天下雨,我们就不出去玩。
条件语句为:
if(今天下雨){
我们就不出去玩
}
表达式:必要参数。其值可以由多个表达式组成,但是最后结果一定是boolean类型,也就是结果只能是true或false。
语句序列:可选参数。一条或多条语句,当表达式的值为true时执行这些语句。当该语句序列省略时,可以保留大括号,也可以去掉大括号,然后在if语句的末尾添加分号“;”。如果该语句只有一条语句,大括号也可以省略不写。但为了增强程序的可读性,最好不省略。下面的代码都是正确的:
if(今天下雨);
if(今天下雨)
我们就不出去玩
简单if语句的执行过程如图3-9所示。
图3-9 简单if语句流程图
【例3-3】 使用if语句求出c的最终结果。
public class Example1{
public static void main(String args[]){
int a = 3,b = 4,c = 0;
if(a<b){ //比较a和b
c = a; //a的值赋值给c
}
if(a>b){ //比较a和b
c = b; //b值赋值给c
}
System.out.println("c的最终结果为:"+c); //输出c值
}
}
程序运行结果如图3-10所示。
图3-10 例3-3的运行结果
【例3-4】在腾宇超市管理系统中判断用户添加的信息是否完整。
if((oId.equals(""))||(wname.equals("")) ||(wDate.equals("")) ||
(count.equals("")) || (money.equals(""))){ //判断用户添加的信息是否完整
JOptionPane.showMessageDialog(getContentPane(), "请将带星号的内容填写完整!","信息提示框", JOptionPane.INFORMATION_MESSAGE); //给出提示信息
return; //退出程序
}
程序运行结果如图3-11所示。
图3-11 例3-4的运行结果
3.2.2 “if...else”条件语句
“if...else”条件语句也是条件语句的一种最通用形式。else是可选的,通常表现为“如果满足某种条件,就进行某种处理,否则进行另一种处理”。它的一般形式为:
“if...else”条件语句
if(表达式){
语句序列1
}else{
语句序列2
}
例如:如果指定年为闰年,二月份为29天,否则二月份为28天。
条件语句为:
if(指定年为闰年){
二月份为29天
}else{
二月份为28天
}
表达式:必要参数。其值可以由多个表达式组成,但是最后结果一定是boolean类型,也就是结果只能是true或false。
语句序列1:可选参数。一条或多条语句,当表达式的值为true时执行这些语句。
语句序列2:可选参数。一条或多条语句,当表达式的值为false时执行这些语句。
“if...else”条件语句的执行过程如图3-12所示。
图3-12 “if...else”条件语句流程图
【例3-5】用“if...else”语句判断69与29的大小。
public class Example2{
public static void main(String args[]){
int a = 69,b = 29;
if(a>b){ //判断a与b的大小
System.out.println(a+"大于"+b);
}else{
System.out.println(a+"小于"+b);
}
}
}
程序运行结果如图3-13所示。
图3-13 例3-5的运行结果
【例3-6】 在腾宇超市管理系统的显示采购订货窗体中,将用户选择的采购订货信息保存在文本文件中。
if (row < 0) {
JOptionPane.showMessageDialog(getParent(), "没有选择要修改的数据!",
"信息提示框", JOptionPane.INFORMATION_MESSAGE);
return;
} else {
File file = new File("filedd.txt"); //创建文件对象
try {
String column = dm.getValueAt(row, 1).toString();
//获取表格中的数据
file.createNewFile(); //新建文件
FileOutputStream out = new FileOutputStream(file);
out.write((Integer.parseInt(column))); //将数据写入文件中
UpdateStockFrame frame = new UpdateStockFrame();
//创建修改信息窗体
frame.setVisible(true);
out.close(); //将流关闭
repaint();
} catch (Exception ee) {
ee.printStackTrace();
}
}
程序运行结果如图3-14所示。
图3-14 例3-6的运行结果
3.2.3 “if...else if”多分支语句
“if...else if”多分支语句用于针对某一事件的多种情况进行处理。通常表现为“如果满足某种条件,就进行某种处理,否则如果满足另一种条件才执行另一种处理”。它的一般形式为:
“if...else if”多分支语句
if(表达式1){
语句序列1
}else if(表达式2){
语句序列2
}else{
语句序列n
}
例如:如果今天是星期一,上数学课;如果今天是星期二,上语文课;否则上自习。
条件语句为:
if(今天是星期一){
上数学课
}else if(今天是星期二){
上语文课
}else{
上自习
}
表达式1和表达式2:必要参数。其值可以由多个表达式组成,但是最后结果一定是boolean类型,也就是结果只能是true或false。
语句序列1:可选参数。一条或多条语句,当表达式1的值为true时执行这些语句。
语句序列2:可选参数。一条或多条语句,当表达式1的值为false,表达式2的值为true时执行这些语句。
语句序列n:可选参数。一条或多条语句,当表达式1的值为false,表达式2的值也为false时执行这些语句。
“if...else if”多分支语句的执行过程如图3-15所示。
图3-15 “if...else if”多分支语句流程图
3.2.4 if语句的嵌套
if语句的嵌套就是在if语句中又包含一个或多个if语句。这样的语句一般都用在比较复杂的分支语句中,它的一般形式为:
if语句的嵌套
if(表达式1){
if(表达式2){
语句序列1
}else{
语句序列2
}
}else{
if(表达式3){
语句序列3
}else{
语句序列4
}
}
表达式1、表达式2和表达式3:必要参数。其值可以由多个表达式组成,但是最后结果一定是boolean类型,也就是结果只能是true或false。
语句序列1:可选参数。一条或多条语句,当表达式1和表达式2的值都为true时执行这些语句。
语句序列2:可选参数。一条或多条语句,当表达式1值为ture,而表达式2的值为false时执行这些语句。
语句序列3:可选参数。一条或多条语句,当表达式1的值为false,而表达式的值3为ture时执行这些语句。
语句序列4:可选参数。一条或多条语句,当表达式1的值为false,且表达式3的值也为false时执行这些语句。
【例3-7】 用“if...else”嵌套实现:判断英语成绩得78分是处在什么阶段。条件为:成绩大于或等于90分为优,成绩在75~90分为良,成绩在60~75分为及格,成绩小于60分为不及格。
public class Example3 {
public static void main(String args[]){
int English = 78;
if(English> = 75){ //判断English分数是否大于等于75
if(English> = 90){ //判断English分数是否大于等于90
System.out.println("英语成绩为"+English+"分:");
System.out.println("英语是优");
}else{
System.out.println("英语成绩为"+English+"分:");
System.out.println("英语是良");
}
}else{
if(English>=60){ //判断English分数是否大于等于60
System.out.println("英语成绩为"+English+"分:");
System.out.println("英语及格了");
}else{
System.out.println("英语成绩为"+English+"分:");
System.out.println("英语不及格");
}
}
}
}
在嵌套的语句中最好不要省略大括号,以免造成视觉的错误与程序的混乱。
程序运行结果如图3-16所示。
图3-16 例3-7的运行结果
例如:
if(result> = 0)
if(result>0)
System.out.println("yes");
else
System.out.println("no");
这样即使result等于0,也会输出no,因此,很难判断else语句与哪个if配对。为了避免这种情况,最好加上大括号为代码划分界限。代码如下:
if(result> = 0){
if(result>0){
System.out.println("yes");
}
}else{
System.out.println("no");
}
3.3 switch多分支语句
switch语句是多分支的开关语句。根据表达式的值来执行输出的语句,这样的语句一般用于多条件多值的分支语句中。它的一般形式为:
switch多分支语句
switch(表达式){
case 常量表达式1: 语句序列1
[break;]
case 常量表达式2: 语句序列2
[break;]
…
case 常量表达式n: 语句序列n
[break;]
default: 语句序列n+1
[break;]
}
表达式:switch语句中表达式的值必须是整数型或字符型,即int、short、byte和char型。
常量表达式1:常量表达式1的值也必须是整数型或字符型,与表达式数据类型相兼容的值。
常量表达式n:与常量表达式1的值类似。
语句序列1:一条或多条语句。当常量表达式1的值与表达式的值相同时,则执行该语句序列。如果不同则继续判断,直到执行表达式n。
语句序列n:一条或多条语句。当表达式的值与常量表达式n的值相同时,则执行该语句序列。如果不同则执行default语句。
default:可选参数,如果没有该参数,并且所有常量值与表达式的值不匹配,那么switch语句就不会进行任何操作。
break:主要用于跳转语句。
switch多分支语句执行过程如图3-17所示。
图3-17 switch多分支语句流程图
【例3-8】 用switch语句判断:在10、20、30之间是否有符合5乘以7的结果。
public class Example4{
public static void main(String args[]){
int x=5,y=7;
switch(x*y){ //x乘以y作为判断条件
case 10 : //当x乘以y为10时
System.out.println("10");
break;
case 20 : //当x乘以y为20时
System.out.println("20");
break;
case 30: //当x乘以y为30时
System.out.println("30");
break;
default :
System.out.println("以上没有匹配的");
}
}
}
程序运行结果如图3-18所示。
图3-18 例3-8的运行结果
3.4 if语句和switch语句的区别
if语句和switch语句可以从使用的效率上来进行区别,也可以从实用性角度去区分。如果从使用的效率上进行区分,在对同一个变量的不同值进行条件判断时,可以用switch语句与if语句。使用switch语句的效率相对更高一些,尤其是判断的分支越多效果越明显。
if语句和switch语句的区别
如果从语句的实用性角度去区分,switch语句肯定不如if语句。if语句是应用最广泛和最实用的语句。
在程序开发的过程中,具体如何使用if和switch语句,要根据实际的情况而定。尽量做到物尽其用,不要因为switch语句的效率高就一味使用它,也不要因为if语句常用就不应用switch语句。要根据实际的情况,具体问题具体分析,使用最适合的条件语句。一般情况下,对于判断条件较少的可以使用if语句,在实现一些多条件的判断中,就应该使用switch语句。
3.5 循环语句
循环语句就是重复执行某段程序代码,直到满足特定条件为止。在Java语言中,循环语句有以下3种形式:
(1)while循环语句;
(2)do...while循环语句;
(3)for循环语句;
(4)for-each风格的for循环。
3.5.1 while循环语句
while语句是用一个表达式来控制循环的语句。它的一般形式为:
while循环语句
while(表达式){
语句序列
}
表达式:用于判断是否执行循环,它的值必须是boolean型的,也就是结果只能是true或false。当循环开始时,首先会执行表达式,如果表达式的值为true,则会执行语句序列,也就是循环体。当到达循环体的末尾时,会再次执行表达式,直到表达式的值为false,开始执行循环语句后面的语句。
while语句的执行过程如图3-19所示。
图3-19 while循环语句执行流程图
【例3-9】 计算1~99的整数和。
public class Example6{
public static void main(String args[]){
int sum=0;
int i = 1;
while(i<100){ //当i小于100
sum+=i; //累加i的值
i++;
}
System.out.println("从1到99的整数和为:"+sum);
}
}
程序运行结果如图3-20所示。
图3-20 例3-9的运行结果
一定要保证程序正常结束,否则会造成死循环。
例如:在这里0永远都小于100,运行后程序将不停地输出0。
int i=0; while(i<100){ System.out.println(i); }
3.5.2 “do...while”循环语句
“do...while”循环语句被称为后测试循环语句,它利用一个条件来控制是否要继续重复执行这个语句。它的一般形式为:
“do...while”循环语句
do{
语句序列
}while(表达式);
“do...while”循环语句的执行过程与while循环语句有所区别。“do...while”循环至少被执行一次,它先执行循环体的语句序列,然后再判断是否继续执行。
“do...while”循环语句的执行过程如图3-21所示。
图3-21 “do...while”循环语句执行流程图
【例3-10】 计算1~100的整数和。
public class Example7{
public static void main(String args[]){
int sum = 0,i = 0;
do{
sum+=i; //累加i的值
i++;
}while(i<=100); //当i小于等于100
system.out.println("从1到100的整数和为:"+sum);
}
}
程序运行结果如图3-22所示。
图3-22 例3-10的运行结果
一般情况下,如果while和“do...while”语句的循环体相同,它们的输出结果就相同。但是如果while后面的表达式一开始就是false,那么它们的结果就不同。
例如,在while和“do...while”循环语句的循环体相同,而且表达式的值为false 的情况下:
public class Example8{
public static void main(String args[]){
int i = 10;
int sum = i;
System.out.println("********当i的值为"+i+"时********");
System.out.println("通过do...while语句实现:");
do{
System.out.println(i); //输出i的值
i++;
sum+ = i; //累加i的值
} while (sum<10); //当累加和小于10时
i = 10;
sum = i;
System.out.println("通过while语句实现:");
while(sum<10){ //当累加和小于10时
System.out.println(i); //输出i的值
i++;
sum+ = i; //累加i的值
}
}
}
程序运行结果如图3-23所示。
图3-23 “do...while”和while语句的运行结果
在使用“do...while”循环语句时,一定要保证循环能正常结束,否则会造成死循环。
例如,因为0永远都小于100,下面这种情况就是死循环:
int i=0; do{ System.out.println(i); }while(i<100);
3.5.3 for循环语句
for语句是最常用的循环语句,一般用在循环次数已知的情况下。它的一般形式为:
for循环语句
for(初始化语句;循环条件;迭代语句){
语句序列
}
初始化语句:初始化循环体变量。
循环条件:起决定作用,用于判断是否继续执行循环体。其值是boolean型的表达式,即结果只能是true或false。
迭代语句:用于改变循环条件的语句。
语句序列:该语句序列被称为循环体,循环条件的结果为true时,重复执行。
for循环语句的流程:首先执行初始化语句,然后判断循环条件,当循环条件为true时,就执行一次循环体,最后执行迭代语句,改变循环变量的值,这样就结束了一轮的循环。接下来进行下一次循环,直到循环条件的值为false时,才结束循环。
for循环语句的执行过程如图3-24所示。
图3-24 for循环语句执行流程图
【例3-11】 用for循环语句实现打印1~10的所有整数。
public class Example5{
public static void main (String args[]){
System.out.println("10以内的所有整数为:");
for(int i = 1;i<=10;i++){
System.out.println(i);
}
}
}
程序运行结果如图3-25所示。
图3-25 例3-11的运行结果
千万不要让程序无止境地执行,否则会造成死循环。
例如:每执行一次“i++”,i就会加1,永远满足循环条件。这个循环永远不会终止。
for(int i=0;i>=0;i++){ System.out.println(i); }
【例3-12】 在腾宇超市管理系统的人员管理窗体中,调用查询所有部门信息的方法,并将查询出的
结果显示在窗体中。
List list = dao.selectDept(); //调用查询所有部门信息方法
String dName[] = new String[list.size() + 1]; //根据查询结果创建字符串数组对象
dName[0] = "";
for (int i = 0; i < list.size(); i++) { //循环遍历查询结果集
Dept dept = (Dept) list.get(i);
dName[i + 1] = dept.getdName(); //获取查询结果中部门名称
}
程序运行结果如图3-26所示。
图3-26 例3-12的运行结果
3.5.4 for-each风格的for循环
for-each循环在数组中用得比较多。它的一般形式为:
for (类型 变量名:要遍历的数组){
语句序列
}
例如,遍历数组num:
public class Demo {
public static void main(String[] args) {
int [] num={1,2,3,4,5};
for(int a :num){
System.out.println(a);
}
}
}
3.5.5 循环的嵌套
循环的嵌套就是在一个循环体内又包含另一个完整的循环结构,而在这个完整的循环体内还可以嵌套其他的循环结构。循环嵌套很复杂,在for语句、while语句和“do...while”语句中都可以嵌套,并且在它们之间也可以相互嵌套。下面是几种嵌套的形式。
循环的嵌套
1.for循环语句的嵌套
一般形式为:
for(; ;){
for(; ;){
语句序列
}
}
2.while循环语句嵌套
一般形式为:
while(条件表达式1){
while(条件表达式2){
语句序列
}
}
3.“do…while”循环语句嵌套
一般形式为:
do{
do{
语句序列
}while(条件表达式1);
}while(条件表达式2);
4.for循环语句与while循环语句嵌套
一般形式为:
for(; ;){
while(条件表达式){
语句序列
}
}
5.while循环语句与for循环语句嵌套
一般形式为:
while(条件表达式){
for(; ;){
语句序列
}
}
6.“do...while”循环语句与for循环语句嵌套
一般形式为:
do{
for(; ;){
语句序列
}
}while(条件表达式);
为了使读者更好地理解循环语句的嵌套,下面将举两个实例。
【例3-13】 打印九九乘法表。
public class Example9{
public static void main(String args[]){
for(int i = 1;i< = 9;i++){
for(int j=1;j< = i;j++){
System.out.print(i+"*"+j+"="+i*j+"\t");
}
System.out.print("\r\n"); //输出一个回车换行符
}
}
}
程序运行结果如图3-27所示。
图3-27 例3-13的运行结果
【例3-14】求100以内能被3和7整除的数。
public class Example10{
public static void main(String[] args){
int i = 1,num,num1;
System.out.println("100以内能被3和7整除的数为:");
while(i< = 100){
for(i = 1;i< = 100;i++){
num = i%3;
num1 = i%7;
if(num == 0){ //判断是否被3整除
if(num1 == 0){ //判断是否被7整除
System.out.println(i);
System.out.println();
}
}
i++;
}
}
}
}
程序运行结果如图3-28所示。
图3-28 例3-14的运行结果
3.6 跳转语句
Java语言中支持多种跳转语句,如break跳转语句、continue跳转语句和return跳转语句。
跳转语句
3.6.1 break跳转语句
break语句可以终止循环或其他控制结构。它在for、while或“do...while”循环中,用于强行终止循环。
只要执行到break语句,就会终止循环体的执行。break不仅在循环语句里适用,在switch多分支语句里也适用。
【例3-15】 求10以内的素数。
public class Example11{
public static void main(String[] args) {
System.out.println("10以内的素数为:");
int i,j,sum = 0;
for(i = 1;i< = 10;i++){
for(j = 2;j< = i/2;j++){
if(i%j == 0)
break;
}
if(j>i/2)
System.out.print(i);
}
}
}
程序运行结果如图3-29所示。
图3-29 例3-15的运行结果
3.6.2 continue跳转语句
continue语句应用在for、while和“do...while”等循环语句中,如果在某次循环体的执行中执行了continue语句,那么本次循环就结束,即不再执行本次循环中continue语句后面的语句,而进行下一次循环。
【例3-16】 求100以内能被9整除的数。
public class Example12{
public static void main(String args[]){
int t=1;
System.out.println("100以内能被9整除的数为:");
for(int i=1;i<100;i++){
if(i%9!=0){ //当i的值不能被9整除时
continue;
}
System.out.print(i+"\t"); //输出i的值
if(t%9==0){
System.out.print("\r\n"); //输出一个回车换行符
}
t++;
}
}
}
程序运行结果如图3-30所示。
图3-30 例3-16的运行结果
3.6.3 return跳转语句
return语句可以实现从一个方法返回,并把控制权交给调用它的语句。return语句通常被放在方法的最后,用于退出当前方法并返回一个值。它的语法格式为:
return [表达式];
表达式:可选参数,表示要返回的值,它的数据类型必须同方法声明中的返回值类型一致。例如,编写返回a和b两数相加之和的方法可以使用如下代码:
public int set(int a,int b){
return sum = a+b;
}
如果方法没有返回值,可以省略return关键字的表达式,使方法结束。代码如下:
public void set(int a,int b){
sum = a+b;
return;
}
【例3-17】 定义查询指定部门中所有员工信息的方法,该方法将查询结果以List形式返回。
public List selectBasicMessageByDept(int dept) {
conn = connection.getCon(); //获取数据库连接
List list = new ArrayList<String>(); //定义保存查询结果的集合对象
try {
Statement statement = conn.createStatement(); //实例化Statement对象
String sql = "select name from tb_basicMessage where dept = " + dept +""; //定义按照部门名称查询员工信息方法
ResultSet rest = statement.executeQuery(sql); //执行查询语句获取查询结果集
while (rest.next()) { //循环遍历查询结果集
list.add(rest.getString(1)); //将查询信息保存到集合中
}
} catch (SQLException e) {
e.printStackTrace();
}
return list; //返回查询集合
}
程序运行结果如图3-31所示。
图3-31 例3-17的运行结果
小结
本章介绍了有关运算符的分类和各种运算符的使用方法,以及运算符之间的优先级;流程控制的语句,主要包括分支语句、循环语句和跳转语句,这些流程控制语句是Java语言程序设计的关键基础。灵活使用流程控制语句,能够实现并提高程序的交互性,增加程序的可读性,使开发的程序更容易操作。
通过对本章的学习,读者应该掌握如何使用分支语句控制程序的流程。一个完善的Java程序,特别是面向对象的程序设计,必须能够对任何可能发生的情况进行判断,并进行相应的业务处理。使用循环语句可以提高程序的性能和可读性。对于批量的数据操作,在很多情况下使用循环语句可以大大精简程序的编码工作,提高工作效率,并且能够减轻计算机的工作量,提高程序运行的速度。本章最后讲解的跳转语句主要用于提高循环语句的灵活性,在其他代码位置也可以灵活使用,这也是本章需要掌握的重点。
习题
3-1 求从1加到100的和。
3-2 求从1加到100的奇数和。
3-3 求从1到10的阶乘和。
3-4 用循环语句输出“*”字符,运行效果如图3-32所示。
图3-32 习题3-4的运行效果图
3-5 求100以内的素数。
3-6 求1000以内能被7和9整除的数。
3-7 求表达式“1+1/2+1/3+1/4+1/5”的结果。