递归
1.递归的设计经验
- 找重复(子问题)
- 找重复中的变化量(参数)
- 找参数的变化趋势
- 找出边界(递归结束的条件)
2.典型的例题
- 求阶乘
public static int fn(int n){
if(n == 1){
return 1;
}
return n * fn(n-1);
}
- 用递归打印i~j的所有数
public static void printij(int i, int j){
System.out.println(i);
if(i < j) {
printij(i + 1, j);
}
}
- 用递归实现数组求和
public static int sum(int[] arr){
return sum(arr, arr.length-1);
}
private static int sum(int[] arr, int n){
if(n == 0){
return arr[n];
}
return sum(arr, n-1) + arr[n];
}
- 反转字符串
public static String reverse(String s){
return reverse(s, s.length()-1);
}
private static String reverse(String s, int n){
if(n == 0){
return "" + s.charAt(0);
}
return s.charAt(n) + reverse(s, n-1);
}
- 斐波那契数列
public static int fib(int n){
if(n == 1 || n ==2) return 1;
return fib(n-1) + fib(n-2);
}
- 求最大公约数
public static int gcd(int m, int n){
if(m % n == 0){
return n;
}
return gcd(n, m%n);
}
- 插入排序递归实现
public static void insertSort(int[] arr){
insertSort(arr, arr.length-1);
}
private static void insertSort(int[] arr, int k){
if(k == 0) return;
insertSort(arr, k-1);
int i = k-1;
int x = arr[k];
while (i > 0 && arr[i] > x){
arr[i+1] = arr[i];
i--;
}
arr[i+1] = x;
}
- 二分查找的递归实现
public static void binarySerach(int[] arr, int num){
Serach(arr, 0, arr.length-1, num);
}
private static void Serach(int[] arr, int low, int high, int num){
if(low > high){
System.out.println("数列中没有该值!");
return;
}
int mid = (low+high)/2;
int midVal = arr[mid];
if(num > midVal){
Serach(arr, mid+1, high, num);
}else if(num < midVal){
Serach(arr, low, mid-1, num);
}else{
System.out.println("找到" + num + ",在第" + (mid+1) + "位!");
}
}
- 汉诺塔问题
public static void hanoiTower(int n){
hanoiTower(n, 'A', 'B', 'C');
}
private static void hanoiTower(int n, char a, char b, char c){
if(n == 1){
System.out.println("第1个盘子:" + a + "->" + c);
}else {
hanoiTower(n - 1, a, c, b);
System.out.println("第" + n + "个盘子:" + a + "->" + c);
hanoiTower(n - 1, b, c, a);
}
}
- 上台阶进阶版,一次可以跳1-n阶
public static int JFII(int target){
if(target == 0) return 0;
if(target == 1) return 1;
return 2*JumpFloorII(target-1);
}
public static int JumpFloorII(int target) {
if(target == 0) return 0;
if(target == 1) return 1;
int a = 1;
while (target > 1){
a = 2*a;
target--;
}
return a;
}