zoukankan      html  css  js  c++  java
  • c语言进阶5-递归算法

    一、  什么是递归

    程序调用自身的编程技巧称为递归( recursion)。

    递归做为一种算法程序设计语言中广泛应用。 一个过程或函数在其定义或说明中有直接或间接调用自身的一种方法,它通常把一个大型复杂的问题层层转化为一个与原问题相似的规模较小的问题来求解,递归策略只需少量的程序就可描述出解题过程所需要的多次重复计算,大大地减少了程序的代码量。递归的能力在于用有限的语句来定义对象的无限集合。一般来说,递归需要有边界条件、递归前进段和递归返回段。当边界条件不满足时,递归前进;当边界条件满足时,递归返回。

    注意:
    递归就是在过程或函数里调用自身;

    举个例子来说:

    从前有座山,山上有座庙,庙里有一个老和尚和一个小和尚,老和尚正在给小和尚讲故事。

    讲的是什么故事呢?他说,从前有座山,山上……

    我们发现这个故事是一直重复讲述的,我们之前是通过循环结构来实现重复执行某些代码的,那么如何通过递归代码来实现这个故事呢? 我们来看下面这段代码:

    #include "windows.h"
    
    void   tell_story( )
    
    {
    
           printf("从前有座山,山上有座庙,庙里有一个老和尚和一个小和尚
    ");
    
           printf("老和尚正在给小和尚讲故事。讲的是什么故事呢?他说:
    ");
    
           Sleep(1000);
    
           tell_story ( );      // tell_story 函数的递归调用
    
    }
    
    void main()
    
    {
    
       tell_story( );
    
    }

    我们发现, 通过递归调用,也就是函数调用自身这一方法来实现讲故事这以代码,代码是可以执行的,但是却形成了一个死循环.之前我们学习循环的时候,我们对循环是有控制条件的,那么在我们使用递归的时候是否应该和使用循环一样,应该有个控制递归的条件呢?这个控制条件应该是什么呢?

    注意:
    递归就是在过程或函数里调用自身;
    在使用递归策略时,必须有一个明确的递归结束条件,称为递归出口。

    汉诺塔游戏代码

    /* 汉诺塔游戏解决过程*/
    #include "stdio.h"
    //整型全局变量,预置1,步数
    int step=1;
    //void表示该函数没有返回值,只是执行了一些操作
    void move(int m,char p,char q,char r)
    {
        if(m==1)    //如果m为1,则为直接可解结点
        {
            //输出移盘信息
            printf("第%d步 move 1# from %c to %c
    ",step,p,r);
            //步数加1,准备进行下一步
            step++;    
        }
        else
        {
            move(m-1,p,r,q);//递归调用move(m-1)
            //直接可解结点,输出移盘信息
            printf("第%d步 move %d# from %c to %c
    ",step,m,p,r);
            //步数加1
            step++;
            //递归调用
            move(m-1,q,p,r);
        }    
    }
    
    void main()
    {
        int n;
        printf("请输入盘数:");
        scanf("%d",&n);
        printf("在3根柱子上移%d只盘的步骤为
    ",n);
        move(n,'A','B','C');        
    }

    斐波那契数列代码

    /* Note:Your choice is C IDE */
    #include "stdio.h"
    int fun(int n)
    {
        if(n==1||n==2)
        return 1;
        else
        return fun(n-1)+fun(n-2);
    }
    
    void main()
    {
        int n;
        printf("请输入月数:");
        scanf("%d",&n);
        printf("%d月有%d对兔子
    ",n,fun(n));
        
    }

    递归 求阶乘

    #include "stdio.h"
    int fun(int n)
    {
        if(n==1)
        return n;
        else
        return n*fun(n-1);
    }
    
    void main()
    {
        int n;
        printf("请输入一个数:");
        scanf("%d",&n);
        printf("%d!=%d
    ",n,fun(n));
        
    }
  • 相关阅读:
    nextSibling VS nextElementSibling
    线程实现连续启动停,并在某一时间段内运行
    线程:安全终止与重启
    监控知识体系
    后台服务变慢解决方案
    Java泛型类型擦除以及类型擦除带来的问题
    常见的 CSRF、XSS、sql注入、DDOS流量攻击
    Spring对象类型——单例和多例
    一次线上OOM过程的排查
    深入浅出理解基于 Kafka 和 ZooKeeper 的分布式消息队列
  • 原文地址:https://www.cnblogs.com/TimVerion/p/11190631.html
Copyright © 2011-2022 走看看