题目
小球从某一高度落下,每次落地后反跳回原来高度的一半,再落下。
输入弹球的初始高度(大于0), 输出弹球第10次 回弹时的高度 和 所经过的距离
样例输入
10
样例输出
0.009765625
29.970703125
分析
10
回弹高度 经过的距离
-----------------------------------
5 15=10+5
2.5 22.5=10+5+5+2.5
1.25
0.625
代码
方法1
import java.text.DecimalFormat;
import java.util.Scanner;
public class Homework0513 {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
System.out.print("请输入弹球的初始高度:");
double height = sc.nextDouble(); //存放初始高度
System.out.print("请输入弹球的回弹次数:");
int num = sc.nextInt(); //存放回弹次数
System.out.println("方法1:循环");
method1( height, num ); //调用方法1
System.out.println();
System.out.println("方法2:递归");
System.out.println("回弹次数\t\t回弹高度\t\t经过的距离");
double[] result = method2( height, num ); //调用方法2,并接收
System.out.println("经过 " + num + " 次后,弹起高度为:" + result[0] + ";\t经过的路程为:" + result[1] ); //打印结果
}
/**
* 方法1:采用循环方法计算,较简单
* @param height 初始高度
* @param num 弹起次数
*/
public static void method1(double height, int num) {
DecimalFormat df = new DecimalFormat("0.00000"); //保留5位小数
double distance = 0; //定义走过的路程
System.out.println("回弹次数\t\t回弹高度\t\t经过的距离");
for(int i = 0; i < num; i++){
distance += height * 1.5; //下落加弹起,共走了1.5倍下落高度
height = height / 2; //每次弹起一半
System.out.println(" " + ( i + 1 ) + " \t\t" + df.format(height) + "\t\t" + df.format(distance)); //打印过程
}
System.out.println("经过 " + num + " 次后,弹起高度为:" + height + ";\t经过的路程为:" + distance ); //打印结果
}
/**
* 方法2:采用递归方法,较复杂
*/
public static double[] method2(double height, int num) {
DecimalFormat df = new DecimalFormat("0.00000"); //保留5位小数
double[] d = {0, 0}; //d[0] 存放弹起高度; d[1] 存放走过的路程
if(num == 1){ //递归结束条件,当num=1, 表示【最后 1 次】回弹
d[0] = height / 2; //第 1 次回弹,回弹高度为 初始高度/2
d[1] = height + d[0]; //第 1 次回弹,经过路程为 初始下落高度 + 第 1 回弹高度
System.out.println(" " + num + " \t\t" + df.format(d[0]) + "\t\t" + df.format(d[1])); //打印过程
return d; //返回数组
}else {
//递归调用,本次计算需采用上次结果
double[] temp = method2(height, num - 1); //定义临时数组,接收计算结果,temp[0] 存放弹起高度; temp[1] 存放走过的路程
d[0] = temp[0] / 2; //本次回弹高度 = 上次回弹高度 / 2
d[1] = temp[1] + temp[0] * 1.5; //本次经过距离 = 上次经过距离 + 上次回弹高度 * 1.5
System.out.println(" " + num + " \t\t" + df.format(d[0]) + "\t\t" + df.format(d[1]) ); //打印过程
return d; //返回数组
}
}
}
方法1 - 运行结果
请输入弹球的初始高度:5
请输入弹球的回弹次数:5
方法1:循环
回弹次数 回弹高度 经过的距离
1 2.50000 7.50000
2 1.25000 11.25000
3 0.62500 13.12500
4 0.31250 14.06250
5 0.15625 14.53125
经过 5 次后,弹起高度为:0.15625; 经过的路程为:14.53125
方法2:递归
回弹次数 回弹高度 经过的距离
1 2.50000 7.50000
2 1.25000 11.25000
3 0.62500 13.12500
4 0.31250 14.06250
5 0.15625 14.53125
经过 5 次后,弹起高度为:0.15625; 经过的路程为:14.53125
方法3
分开采用递归方法,实际计算过程略繁琐,故不推荐,
将此方法写出,为了加深对运算过程的理解
import java.text.DecimalFormat;
import java.util.Scanner;
public class Test01 {
public static void main(String[] args) {
DecimalFormat df = new DecimalFormat("0.00000"); //保留5位小数
Scanner sc = new Scanner(System.in);
System.out.print("请输入弹球的初始高度:");
double height = sc.nextDouble(); //存放初始高度
System.out.print("请输入弹球的回弹次数:");
int num = sc.nextInt(); //存放回弹次数
System.out.println("\n------------------------------------------------\n");
System.out.println("2\t" + "次数 \t高度");
double last_height = method2(num, height); //调用方法2
System.out.println("回弹次数\t回弹高度\t\t经过的距离");
double distance1 = method3(num, height); //调用方法3
System.out.println("\n------------------------------------------------\n");
System.out.println("经过 " + num + " 次后,小球弹起高度为:" + df.format(last_height) );
System.out.println("经过 " + num + " 次后,小球经过的路程为:" + df.format(distance1) );
}
//方法2 计算第i次的弹起高度
public static double method2(int num, double height) {
double result =0;
if(num == 1){
result = height / 2;
System.out.println("2++++" + num + "++++" + result);
//return result;
}else {
result = method2(num - 1, height) / 2;
System.out.println("2----" + num + "----" + result);
//return result;
}
//System.out.println("2\t" + num + "----" + result);
return result;
}
//方法3 计算第i次的行走路程
public static double method3(int num, double height) {
DecimalFormat df = new DecimalFormat("0.00000"); //保留5位小数
double result =0;
double h = 0.0;
if(num == 1){
//h = method2(num, height);
result = (h = method2(num, height)) + height ;
System.out.println( num + "\t-\t" + df.format(h) + "\t\t\t" + df.format(result) );
return result;
}else {
h = method2(num, height);
result = ( method2(num-1, height) ) * 1.5 + method3(num-1, height);
System.out.println( num + "\t+\t" + df.format(h) + "\t\t\t" + df.format(result) );
return result;
}
}
}
方法3 - 运行结果
请输入弹球的初始高度:5
请输入弹球的回弹次数:5
------------------------------------------------
2 次数 高度
2++++1++++2.5
2----2----1.25
2----3----0.625
2----4----0.3125
2----5----0.15625
/*实际运算过程
法2 次数 高度
2++++1++++2.5
2----2----1.25
2----3----0.625
2----4----0.3125
2----5----0.15625
2++++1++++2.5
2----2----1.25
2----3----0.625
2----4----0.3125
2++++1++++2.5
2----2----1.25
2----3----0.625
2----4----0.3125
2++++1++++2.5
2----2----1.25
2----3----0.625
2++++1++++2.5
2----2----1.25
2----3----0.625
2++++1++++2.5
2----2----1.25
2++++1++++2.5
2----2----1.25
2++++1++++2.5
2++++1++++2.5
*/
回弹次数 回弹高度 经过的距离
1 - 2.50000 7.50000
2 + 1.25000 11.25000
3 + 0.62500 13.12500
4 + 0.31250 14.06250
5 + 0.15625 14.53125
------------------------------------------------
经过 5 次后,小球弹起高度为:0.15625
经过 5 次后,小球经过的路程为:14.53125
总结
1.有效数字的保留位数方法
2.小球弹起高度与经历路程的计算方法
3.递归的使用
4.实际运算过程的理解