JAVA基础03选择

本文详细介绍了Java中的选择结构,包括boolean数据类型、if语句、双分支if-else、嵌套if和多分支if-else,以及switch语句的使用。讲解了条件表达式、逻辑操作符和调试技巧,提供了常见错误和陷阱的分析,帮助读者掌握如何在Java中进行条件判断和决策执行。

3.选择

3.1 boolean 数据类型

boolean 数据类型声明一个具有值 true 或者 false 的变量

Java 提供六种关系操作符relational operator) ,也称为比较操作符comparison operator),用于两个值的比较假设表中的半径值为 5 )

 

相等的关系操作符是两个等号==), 而不是一个等号(=), 后者是指赋值操作符

比较的结果是一个布尔值true (false (例如下面的语句显示 true:

double radius = 1;
System.out.println(radius > 0);

具有布尔值的变量称为布尔变量boolean variable), boolean 数据类型用于声明布尔型变量。boolean 型变量可以是以下这两个值中的一个true false例如下述语句将true 赋值给变量 lightsOn

boolean lightsOn = true;

true false 都是直接量就像 10 这样的数字它们被当作保留字一样不能用做程序中的标识符。

 

 

3.2 if 语句

if 语句是一个结构允许程序确定执行的路径

Java 有几种类型的选择语句单分支 if 语句双分支 if - else 语句嵌套 if 语句多分支 if - else 语句switch 语句和条件表达式

单分支 if 语句是指当且仅当条件为 true 时执行一个动作单分支 if 语句的语法如下:

if (布尔表达式){
    语句(组):
}

语句流程图

布尔表达式应该用括号括住例如下面图 a 中的代码是错误的应该将它改为如图 所示。

如果花括号内只有一条语句则可以省略花括号例如下面两个语句是等价的

注意省略括号可以让代码更加简短但是容易产生错误当你返回去修改略去代码的时候,容易忘记加上括号这是一个常犯的错误

 

 

3.3 双分支 if-else 语句

if-else 语句根据条件是真或者是假决定执行的路径

根据条件为 true false, 双分支 if 语句可以指定不同的操作

下面是双分支 if - else 语句的语法:

if (布尔表达式> {
    布尔表达式为其时执行的语句(组);
}
else{
    布尔表达式为假时执行的语句(组);
}

语句流程图

如果布尔表达式的计算结果为 true, 则执行条件为 true 时该执行的语句否则执行条件为 false 时该执行的语句例如考虑下面的代码

if(radius >= 0){
    area = radius * radius * PI;
    System.out.println("The area for the circle of radius " + radius + “is” + area);
}else {
    System.out•println("Negative input");
}

radius>=0true, 则计算并显示 area ; 如果 radius> = 0为 false, 则打印信息 "Negative input"

通常如果花括号中只有一条语句则可以省略花括号因此前例中用于括住语句 System,out.println("Negative input")的花括号可以省略

 

 

3.4 嵌套的 if 语句和多分支 if - else 语句

if 语句可以在另外一个 if 语句中形成嵌套的 if 语句

if if -else 语句中的语句可以是任意合法的 Java 语句甚至可以是其他的 if if - else 语句内层 if 语句称为是嵌套在外层 if 语句里的内层 if 语句还可以包含其他的 if 语句;事实上对嵌套的深度没有限制例如下面就是一个嵌套的 if 语句

1f(i > k){
    if (j > k)
    System.out.println("i and» j are greater than k");
}else{
    System.out.println("i is less than or equal to kM);
}

嵌套的 if 语句可用于实现多重选择例如:下中所给出的语句使用了多重选择, 根据分数给变量 grade 赋一个用字母表示的级别。

 

可以使用多分支 if-else 语句来给出一个分数

 

 

 

3.5 常见错误和陷阱

忘记必要的括号在错误的地方结束 if 语句== 错当作=使用悬空 else分支,是选择语句中常见的错误if - else 语句中重复的语句,以及测试双精度值的相等是常见的陷阱。

  • 常见错误 1: 忘记必要的括号

如果块中只有一条语句就可以忽略花括号但是当需要用花括号将多条语句括在一起时,忘记花括号是一个常见的程序设计错误如果通过在没有花括号的 if 语句中添加一条新语句来修改代码,就必须插入花括号例如下面图 a 中的代码是错误的应该用花括号将多个语句放在一起,如图 b 所示:

  • 常见错误 2: if 行出现错误的分号

如下面的图 a 中所示if 行加上了一个分号,这是一个常见错误:

这个错误是很难发现的,因为它既不是编译错误也不是运行错误而是一个逻辑错误。图 a 中的代码等价于一个带空块的图 b 中的代码

当使用换行块风格时经常会出现这个错误所以使用行尾块风格可帮助防止出现此类错误。

  • 常见错误 3: 对布尔值的冗余测试

为了检测测试条件中的布尔型变量是 true 还是 false, 像图 a 中的代码这样使用相等比较操作符是多余的。

难以发现的错误使用 = 操作符而不是 == 操作符去比较测试条件中的两项是否相等是一个常见错误。它可能会导致出现下面的错误语句
 

if (even = true){

    System.out.println("It is even."); 
}

这条语句没有编译错误它给 even 赋值 true, 这样 even 永远都是 true。

 

  • 常见错误 4: 悬空 else 出现的歧义

下面图 a 中的代码有两个 if 子句和一个 else 子句那么哪个 if 子句和这个 else 匹配呢?这里的缩进表明 else 子句匹配第一个 if 子句但是else 实际匹配的是第二个 if 子句。这种现象就称为悬空 else 歧义dangling-else ambiguity)在同一个块中else 总是和离它最近的 if 子句匹配这样a 中的语句就等价于图 b 中的语句

由于i>j)为假所以图 a 和图 b 中的语句不打印任何东西为强制这个 else 匹配第一个 if 子句必须添加一对花括号

int i= 1 , j=  2 , k= 3;
if (i > j){
    if (i > k){
        System.out.println("A");
    }
}else{
    System,out.printlnC'B");
}

这条语句会打印出 B

 

  • 常见错误 5: 两个浮点数值的相等测试

浮点数具有有限的计算精度涉及浮点数的计算可能引人取整错误。因此两个浮点数值的相等测试并不可靠比如你期望代码显示 true,但是会让人意外的显示 false。

double x = 1.0 - 0.1 - 0.1 - 0.1 - 0.1 - 0.1;
System.out .println(x == 0. 5);

这里X 并不是精确等于 0.5, 而是 0.5000000000000001虽然不能依赖于两个浮点数值的相等测试,但是可以通过测试两个数的差距小于某个阈值来比较它们是否已经足够接近。

 

  • 常见陷阱 1: 简化布尔变量赋值

通常编程新手编写将一个条件测试赋给 boolean 变量的代码会如 a 中代码

这没有错但是写成 b 中代码形式会更好

 

  • 常见陷阱 2: 避免不同情形中的重复代码

编程新手经常会在不同情形中写重复的代码这些代码应该写在一处的例如下面高亮的语句是重复的。

if (inState) {
    tuition = 5000;
    System.out.println(" The tuition is " tuition);
}else {
    tuition = 15000;
    System.out.println("The tuition is tuition);
}

这没有错,但是写成如下代码形式会更好。
 

If (inState) {
    tuition = 5000;
}else {
    tuition = 15000;
}
System.out.println(" The tuirion is " + tuition);

新的代码去掉了重复代码使得代码更加易于维护因为如果打印语句需要修改你只需要修改一处地方。

 

 

3.6 产生随机数

你可以使用 Math.randomO 来获得一个 0.0 1.0 之间的随机 double 不包括 1.0

使用 Math 类中的 randomO 方法调用这个方法会返回一个双精度的随机值 d 且满足 0.0 <= d < 1.0

 

 

3.7 逻辑操作符

逻辑操作符 &&丨丨和 ^  可以用于产生复合布尔表达式

有时候是否执行一条语句是由几个条件的组合来决定的。可以使用逻辑操作符组合这些条件逻辑操作符( logical operator ) 也称为布尔操作符 ( boolean operator), 是对布尔值进行的运算,它会创建新的布尔值

 

 

3.8 switch 语句

if 语句是根据单独的一个 true false 条件做出选择的根据变量 status 的值会有多种计算的情况为了全面考虑所有的情况需要使用嵌套的 if 语句。过多地使用嵌套的 if 语句会使程序很难阅读Java 提供 switch 语句来有效地处理多重条件的问题。可以使用下述 switch 语句替换嵌套 if 语句

 

上面的 switch 语句的流程图如下图所示

这条语句依次检査 status 是否能匹配 012 3如果匹配就计算相应的税金;如果不匹配就显示一条消息下面是 switch 语句的完整语法

switch (switch 表达式){
    case 值 1: 语句(组)1;
    break;
    case 值 2: 语句(组)2;
    break;
    case 值 N: 语句(组)Nv
    break;
    default:R认情况下执行的语句(组)
}

switch 语句遵从下述规则

  • switch 表达式必须能计算出一个 charbyteshort,int 或者 String 型值并且必须总是要用括号括住
  • valuel...valueN 必须与 switch 表 达 式 的 值 具 有 相 同 的 数 据 类 型注 意valuel, valueN 都是常量表达式也就是说这里的表达式是不能包含变量的例如不允许出现 1+X
  • switch 表达式的值与 case 语句的值相匹配时执行从该 case 开始的语句直到遇到一个 break 语句或到达该 switch 语句的结束
  • 默认情况default)是可选的当没有一个给出的 case switch 表达式匹配时用来执行该操作
  • 关键字 break 是可选的break 语句会立即终止 switch 语句

 

 

3.9 条件表达式

条件表达式基于一个条件计算表达式的值

有时可能需要给有特定条件限制的变量赋值例如下面的语句在 X 大于 0 时给 y 赋1;当 x 小于等于 0时给 y 赋值 - 1。

if (x > 0){
    y=1;
}else {
    y=-1;
}

在这个例子中还可以选择使用如下的条件表达式也能达到同样的效果

y = (x >0) ? 1 : -1;

 

 

操作符的优先级和结合规则

操作符的优先级和结合规则确定了操作符计算的顺序。会依照优先级规则和结合规则进行运算。

优先级规则定义了操作符的先后次序,如表所示,它包含了目前所学的所有操作符。它们从上到下按优先级递减的方式排列。逻辑操作符的优先级比关系操作符的低,而关系操作符的优先级比算术操作符的低。优先级相同的操作符排在同一行。Java 操作符及其优先级的完整列表参见附录

如果优先级相同的操作符相邻则结合规则( associativity ) 决定它们的执行顺序。除了赋值操作符之外,所有的二元操作符都是左结合的( left - associative)例如由于 + 和 - 的所以表达式

赋值操作符是右结合的right-associative)因此表达式:

假设赋值前 ab c 都是1, 在计算表达式之后a 变成 6,b 变 成 6, c 变成 5注意: 左结合对赋值操作符而言是说不通的。

 

 

3.10 调 试

调试是在程序中找到和修改错误的过程

因为编译器可以明确指出错误的位置以及出错的原因所以语法错误是容易发现和纠正的。运行时错误也不难找因为在程序异常中止时,错误的原因和位置都会显示在控制台上。然而査找逻辑错误就很富有挑战性。逻辑错误也称为臭虫(bug)査找和改正错误的过程称为调试debugging)调试的一般途径是采用各种方法逐步缩小程序中 bug 所在的范围可以手工跟踪hand trace) 程序即通过读程序找错误)也可以插入打印语句显示变量的值或程序的执行流程这种方法适用于短小、简单的程序对于庞大复杂的程序最有效的调试方法还是使用调试工具

JDK 包含了一个命令行调试器jdb, 结合一个类名来调用该命令Jdb 本身也是一个 Java 程序运行自身的一个 Java 解释器的拷贝所有的 Java IDE 工具比如 Eclipse 和 NetBeans 包含集成的调试器调试器应用让你可以跟踪一个程序的执行它们因系统而不同,但是都支持以下有用的特征中的多数

 

一次执行一条语句调试器允许你一次执行一条语句从而可以看到每条语句的效果。

跟踪进入或者一步运行过一个方法如果一个方法正在被执行你可以让调试器跟踪进入方法内部,并且一次执行方法里面的一条语句或者你也可以让调试器一步运行过整个方法。如果你知道方法是可行的你应该一次运行过整个的方法比如,通常都会一步运行过系统提供的方法,比如 Systeiout.println

设置断点你也可以在一条特定的语句上面设置断点当遇到一个断点时你的程序将暂停。你可以设置任意多的断点当你知道程序错误从什么地方可能开始的时候,断点特别有用。你可以将断点设置在那条语句上让程序先执行到断点处

显示变量调试器让你选择多个变量并且显示它们的值当你跟踪一个程序的时候,变量的内容持续更新。

显示调用堆栈调试器让你跟踪所有的方法调用当你需要看到程序执行流程的宏观图景的时候,这个特征非常有用。

修改变量一些调试器允许你在调试的过程中修改变量的值当你希望用不同的示例来测试程序,而又不希望离开调试器的时候,这是非常方便的。

 

 

 

 

 

 

 

附录

 

 

 

 

 

编译运算练习

1.

 

 

2.

 

 

3.

 

 

4.

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值