9.1.5 技能训练
上机练习2
指导——输入行数,打印直角三角形
训练要点
二重循环及循环条件的设定。
使用 Scanner 对象接收用户输入。
需求说明
从控制台输入直角三角形的高度(行数)。
每行字符*的个数依次为1、3、5、7、9等。
程序运行结果如图 9.4 所示。
实现思路及关键代码
(1) 外层循环控制行数。根据用户输入的行数得到外层循环条件。例如,假如用户输入的行数是 5, 则外层循环变量 i 的值为 1〜5 。
(2) 分析每行打印的内容。每一行均打印字符*,某一行与该行字符*个数是什么关系呢?首先分析内层循环变量 j 的变化规律(假如用户输入的行数是 5):
第一行,i = 1,打印 1 个字符*, 内层循环 1 次,j 的取值只有 1 。
第二行,i = 2,打印 3 个字符*, 内层循环 3 次,j 的取值为 1〜3 。
第三行,i = 3,打印 5 个字符*, 内层循环 5 次,j 的取值为 1〜5 。
第四行,i = 4,打印 7 个字符*, 内层循环 7 次,j 的取值为 1〜7 。
第五行,i = 5,打印 9 个字符*, 内层循环 9 次,j 的取值为 1〜9 。
不难发现,对于每一行,j 的最大值为 2×i-1, 从而得到内层循环条件,即 2×i-1。
(3) 每一行打印字符*结束后要换行。
图 9.4 上机练习 2 的运行结果
参考解决方案
package cn.jbit.array; import java.util.Scanner; /** * 输入行数打印直角三角形 */ public class RTriAngle { public static void main(String[] args) { int rows = 0; //三角形行数 System.out.print("请输入直角三角形的行数:"); Scanner input = new Scanner(System.in); rows = input.nextInt(); //打印直角三角形 for(int i = 1; i <= rows; i++){ for(int j = 1; j <= 2*i-1; j++){ System.out.print("*"); } System.out.print("\n"); } } }
上机练习3
练习——输入行数,打印倒直角三角形
需求说明
从控制台输入直角三角形的高度(行数)。
每行字符*的个数从下至上依次为1、2、3、4等。
程序运行结果如图9.5所示。
图9.5上机练习3的运行结果
提示:
外层循环控制行数,根据用户输入的行数得到外层循环条件。
分析每行打印的内容:每一行均打印字符 * ,某一行与该行字符 * 个数之和等于行数加1,从而得到内层循环条件。
参考代码示范
package cn.jbit.array; import java.util.Scanner; /** * 输入行数打印倒直角三角形 */ public class InvertRTriAngle { public static void main(String[] args) { int rows = 0; //三角形行数 System.out.print("请输入直角三角形的行数:"); Scanner input = new Scanner(System.in); rows = input.nextInt(); //打印倒直角三角形 for(int i = 1; i <= rows; i++){ for(int j = 1; j <= rows+1-i; j++){ System.out.print("*"); } System.out.print("\n"); } } }
上机练习4
练习——输入行数,打印等腰三角形
需求说明
从控制台输入等腰三角形的高度(行数)。
每行字符*的个数依次为1、3、5、7等。
程序运行结果如图9.6所示。
图9.6上机练习4的运行结果
提示:外层循环控制行数,根据用户输入的行数得到外层循环条件。
分析每行打印的内容:每一行先打印空格,再打印字符*。打印空格和打印字符*用两个不同的for循环。为了清晰起见,下面以#号代替空格来分析每行空格数、字符*个数和行数的关系,程序运行结果如图9.7所示。
由图9.7可以看出,从第一行开始字符#个数分别为4、3、2、1,而字符*个数为1、3、5、7、9。因此我们可以得到如下关系:第i行的空格数与i 之和等于rows,第i 行字符*个数为2×i-l,从而得到两个内层for循环的循环条件。
图9.7上机练习4的运行结果分析
参考代码示范
package cn.jbit.array; import java.util.Scanner; /** * 输入行数打印等腰三角形 */ public class IsoTriangle2 { public static void main(String[] args) { int rows = 0; //三角形行数 System.out.print("请输入等腰三角形的行数:"); Scanner input = new Scanner(System.in); rows = input.nextInt(); //打印等腰三角形 for(int i = 1; i <= rows; i++){ for(int j = 1; j <= rows-i; j++){ System.out.print("#"); } for(int k = 1; k <= 2*i-1; k++){ System.out.print("*"); } System.out.print("\n"); } } }
上机练习5
指导——打印九九乘法表
训练要点
复杂的二重循环。
需求说明
利用二重循环实现九九乘法表。
程序运行结果如图9.8所示。
图9.8上机练习5的运行结果
实现思路及关键代码
(1)九九乘法表共有九行,因此:
for (int i = 1; i <= 9; i++) { //打印第 i 行; //换行; }
(2) 第i行上有i个式子,因此:
for(int i = 1; i <= 9; i++){ for(int j = 1; j <= i; j ++) { //打印第 i 行上的第 j 个式子; } //换行; }
(3) 分析第i行上的第j个式子,应该为j的值×i的值=j×i的值。
参考解决方案
package cn.jbit.array; /** * 打印九九乘法表 */ public class MuITable { public static void main(String[] args) { int rows = 9; //乘法表的行数 for(int i = 1; i<=rows; i++){ //一共9行 for(int j = 1; j <= i; j++){ //第i行有i个式子 System.out.print(j+"*"+i+"="+j*i+" "); } System.out.print("\n"); //打印完一行后换行 } } }
9.2跳转语句进阶
如果希望循环在某种条件下不按正常流程执行,需要用到continue或break语句。那么,如何在二重循环中使用continue和break语句呢?它们怎样控制程序的执行呢?
9.2.1 在二重循环中使用 continue 语句
示例3的代码是在示例1的基础上扩展的,同学们能看出它的作用吗?这段代码的作用就是统计成绩在85分及以上的学员共有多少名。
示例3
package cn.jbit.array; import java.util.Scanner; /** * continue断点演示:计算成绩85分以上的学员人数 * */ public class ContinueDemo { public static void main(String[] args) { int[] score = new int[4]; //成绩数组 int classnum = 3; //班级数目 double sum = 0.0; //成绩总和 double average = 0.0; //平均成绩 int count = 0; //记录85分以上学员人数 //循环输入学员成绩 Scanner input = new Scanner(System.in); for(int i = 0; i < classnum; i++){ sum = 0.0f; //成绩总和归0 System.out.println("请输入第" + (i+1) + "个班级的成绩"); for(int j = 0; j < score.length; j++){ System.out.print("第" + (j+1) + "个学员的成绩:"); score[j] = input.nextInt(); sum = sum + score[j]; //成绩累加 if(score[j] < 85){ //成绩小于85,则跳出本轮循环 continue; } count++; } average = sum / score.length; System.out.println("第" + (i+1) + "个班级参赛学员的平均分是:" + average + "\n"); } System.out.println("成绩85分以上的学员人数有" + count + "人"); } }
程序运行结果如图9.9所示。
从运行结果中可以看出,当输入的成绩小于85分时,continue语句后面的count++不会执行,而是回到内层for循环的开始继续输入下一个学员的成绩。如果输入的成绩大于85分,则会执行count++。输入完三个班级所有参赛学员的成绩后,打印出count的值。所以在内层循环中的continue语句,跳转时是跳过了内层循环中的剩余语句进入内层循环的下一次循环。
图9.9示例3的运行结果
9.2.2 在二重循环中使用 break 语句
问题:使用循环和break语句模拟购物结账问题。假设有五家衣服专卖店,每家限购三件衣服。用户可以选择离开,也可以买衣服。最后打印出总共购买了几件衣服。
分析:使用二重循环解决,其中外层循环控制去每个专卖店的过程,内层循环控制买衣服的过程。如果用户选择离开,则进入下一家店,因此购物过程大致如下。
for (int i = 0; i < 5; i++) { //每次进入一家店 for(int j = 0; j < 3; j ++) { //每家店限购三件衣服 if (离开这家店){ break; } //选购一件衣服; } //结账; }
示例4是实现的代码。
示例4
package cn.jbit.array; import java.util.Scanner; /* * break断点演示:实现购物结账 */ public class BreakDemo { public static void main(String[] args) { int count = 0; //记录一共买了几件衣服 String choice; //顾客选择是否离开 Scanner input = new Scanner(System.in); for(int i = 0; i < 5; i++){ System.out.println("欢迎光临第" + (i+1) + "家专卖店"); for(int j = 0; j < 3; j++){ System.out.print("要离开吗(y/n)?"); choice = input.nextLine(); if("y".equals(choice)){ //如果离开,则跳出,进入下一家店 break; } System.out.println("买了一件衣服"); count++; } System.out.println("离店结账\n"); } System.out.println("总共买了" + count + "件衣服"); choice = input.nextLine(); } }
根据专卖店的数量得到外层循环的条件,根据限购衣服的数量得到内层循环的条件。在内层循环中,如果用户选择离开,则跳出内层循环,离店结账,进入下一家店。当五家专卖店都购物完毕时,打印出总共购买了几件衣服。程序运行结果如图9.10所示。
图9.10示例4的运行结果
9.2.3 二重循环中 continue 和 break 语句的对比
当continue和break语句用在内层循环时,只会影响内层循环的执行,对外层循环没有影响,它们的不同点在于执行该语句后,程序跳转的位置不同,以二重for循环为例,两个语句的对比如表9-1所示。
表9-1 continue和break语句的对比
由表9_1可以看出,continue语句是跳出本次循环,进入下一次循环。而break是跳出本层循环,即提前结束本层循环,执行循环下面的语句。
9.2.4 技能训练
上机练习6
练习——统计打折商品的数量
需求说明
有三名顾客去商场购物,每人买了三件商品。规定:单价300元以上的商品享受八折优惠。请编写程序统计每人享受打折优惠的商品有多少。
程序运行结果如图9.11所示。
提示:
外层循环控制顾客数量,即i<3。
内层循环控制每人买了多少件商品,即j<3。
循环接收每人所购商品的价格。
判断商品单价是否高于300元。如果是,计数;否则跳过本次循环。
图9.11上机练习6的运行结果
参考代码示范
package cn.jbit.array; import java.util.Scanner; /** * 统计打折商品数量 */ public class Demo { public static void main(String[] args) { int count = 0; //记录打折商品数量 Scanner input = new Scanner(System.in); double price=0.0; //商品价格 for(int i = 0; i < 3; i++){ System.out.println("请输入第"+(i+1) +"个人所购的三件商品的价格:"); for(int j = 0; j < 3; j++){ price=input.nextDouble(); if(price<300) continue; count++ ; //累计 } System.out.println("第"+(i+1) +"个人共有" +count + "件商品享受8折优惠!"); count=0;//重置count值 } } }
本章总结
二重循环就是一个循环体内又包含另一个完整的循环结构的循环。
在二重循环中可以使用break、continue语句控制程序的执行。