递归--单路递归

阶乘

用递归方法求阶乘

  • 阶乘的定义 n!= 1⋅2⋅3⋯(n-2)⋅(n-1)⋅n,其中 n 为自然数,当然 0! = 1

  • 递推关系

代码:

private static int f(int n) {
    if (n == 1) {
        return 1;
    }
    return n * f(n - 1);
}

拆解伪码如下,假设 n 初始值为 3

f(int n = 3) { // 解决不了,递
    return 3 * f(int n = 2) { // 解决不了,继续递
        return 2 * f(int n = 1) {
            if (n == 1) { // 可以解决, 开始归
                return 1;
            }
        }
    }
}

反向打印字符串

用递归反向打印字符串,n 为字符在整个字符串 str 中的索引位置

  • :n 从 0 开始,每次 n + 1,一直递到 n == str.length() - 1

  • :从 n == str.length() 开始归,从归打印,自然是逆序的

递推关系

代码:

public static void reversePrint(String str, int index) {
    if (index == str.length()) {
        return;
    }
    reversePrint(str, index + 1);
    System.out.println(str.charAt(index));
}
		//注意:在java语言中,我们实现这个方法有两种:上面是第一种,
        //第二种:我直接从这个n=3开始,也就是从str.length-1开始递归
        //每次让这个n-1,当n小于0时,则退出递归。
        //以上两种方法在java语言中是可以实现的,但是在C语言中这第二种方法就不行:
        //如果是用C语言还是要选择第一种方法,
        //因为,因为C语言中这个字符串来讲,该开始这个长度是未知的,所以一直得从0开始向后,
        //什么时候到字符串的结尾了,也就是遇到特殊字符'\0',才找到到字符串尾巴,这个时候要结束递归

拆解伪码如下,假设字符串为 "abc"

void reversePrint(String str, int index = 0) {
    void reversePrint(String str, int index = 1) {
        void reversePrint(String str, int index = 2) {
            void reversePrint(String str, int index = 3) { 
                if (index == str.length()) {
                    return; // 开始归
                }
            }
            System.out.println(str.charAt(index)); // 打印 c
        }
        System.out.println(str.charAt(index)); // 打印 b
    }
    System.out.println(str.charAt(index)); // 打印 a
}

递归实现二分查找

public static int search(int a[],int target){
    return f(a,target,0,a.length-1);
}

private static int f(int a[],int target,int i,int j){
    //对于二分查找递归的结束条件:1.找到了  2.没找到
    if(i>j){//没找到情况
        return -1;
    }
    //找到的情况
    int m=(i+j)>>>1;
    if(target<a[m]){
       return f(a,target,i,m-1);
    }else if(target>a[m]){
       return f(a,target,m+1,j);
    }else {
        return m;
    }
}

递归实现冒泡排序

 public static void main(String[] args) {
        int a[]={6,5,4,3,2,1};
        bubble(a,a.length-1);
        System.out.println(Arrays.toString(a));
    }

    //j 代表末排序区域右边界
    //在范围[0-j]内冒泡最大元素到右侧
    //a-数组
    private static void bubble(int a[],int j){
        //当只剩下一个数时即可结束递归
        if(j==0){
            return;
        }
        int x=0;//增加x是为了减少不必要的递归
        for (int i=0;i<j;i++){
            if(a[i]>a[i+1]){
                int t=a[i];
                a[i]=a[i+1];
                a[i+1]=t;
                x=i;  //当在每次循环中执行最后一次交换时,让x=i的索引时,此时x是处于有序与无序的分界线,
                //因为最后一次交换一定是i以后的的索引一定是有序的
            }
        }
        bubble(a,x);
    }

递归实现插入排序

public static void sort(int[] a){
    insertion(a,1);//初始Low的索引是在1
}


//low:未排序的初始索引
private static void insertion(int[] a,int low){
    //递归的结束标志
    if(low==a.length){
        return;
    }
    int t=a[low];//存放需要插入的数字
    int i=low-1;//已排序区域指针
    //没有找到插入位置  i>=0:是为了防止在插入位置在索引0的情况就要结束while循环
    while (i>=0&&a[i]>t){
        a[i+1]=a[i];//空出插入位置
        i--;
    }
    //找到插入位置
    a[i+1]=t;
    insertion(a,low+1);
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值