• 第二篇 递归思想


       今天说说递归思想,在我们编码时,有的时候递归能够让我们的算法更加通俗易懂,并且代码量也是大大的减少。比如我先前的系列中说到了

    关于树的“先序,中序和后序”遍历,那么看看用递归来描叙这个问题是多少的简洁,多么的轻松。

    复制代码
     1 #region 二叉树的先序遍历
     2          /// <summary>
     3  /// 二叉树的先序遍历
     4  /// </summary>
     5  /// <typeparam name="T"></typeparam>
     6  /// <param name="tree"></param>
     7          public void BinTree_DLR<T>(ChainTree<T> tree)
     8          {
     9              if (tree == null)
    10                  return;
    11  
    12              //先输出根元素
    13              Console.Write(tree.data + "	");
    14  
    15              //然后遍历左子树
    16              BinTree_DLR(tree.left);
    17  
    18              //最后遍历右子树
    19              BinTree_DLR(tree.right);
    20          }
    21          #endregion
    22  
    23          #region 二叉树的中序遍历
    24          /// <summary>
    25  /// 二叉树的中序遍历
    26  /// </summary>
    27  /// <typeparam name="T"></typeparam>
    28  /// <param name="tree"></param>
    29          public void BinTree_LDR<T>(ChainTree<T> tree)
    30          {
    31              if (tree == null)
    32                  return;
    33  
    34              //优先遍历左子树
    35              BinTree_LDR(tree.left);
    36  
    37              //然后输出节点
    38              Console.Write(tree.data + "	");
    39  
    40              //最后遍历右子树
    41              BinTree_LDR(tree.right);
    42          }
    43          #endregion
    44  
    45          #region 二叉树的后序遍历
    46          /// <summary>
    47  /// 二叉树的后序遍历
    48  /// </summary>
    49  /// <typeparam name="T"></typeparam>
    50  /// <param name="tree"></param>
    51          public void BinTree_LRD<T>(ChainTree<T> tree)
    52          {
    53              if (tree == null)
    54                  return;
    55  
    56              //优先遍历左子树
    57              BinTree_LRD(tree.left);
    58  
    59              //然后遍历右子树
    60              BinTree_LRD(tree.right);
    61  
    62              //最后输出节点元素
    63              Console.Write(tree.data + "	");
    64          }
    65          #endregion
    复制代码

    看看,多么简洁明了。当然递归都是可以改成非递归的,但是就不见得简洁和通俗易懂了。

    一: 概念

           递归,说白了就是直接或者间接的调用自己的一种算法。它是把求解问题转化为规模较小的子问题,然后通过多次递归一直到可以得出结果

    的最小解,然后通过最小解逐层向上返回调用,最终得到整个问题的解。总之递归可以概括为一句话就是:“能进则进,不进则退”。

    二:三要素

          <1>  递归中每次循环都必须使问题规模有所缩小。

          <2>  递归操作的每两步都是有紧密的联系,如在“递归”的“归操作时”,前一次的输出就是后一次的输入。

          <3>  当子问题的规模足够小时,必须能够直接求出该规模问题的解,其实也就是必须要有结束递归的条件。

    三: 注意

           <1>  前面也说了,递归必须要有一个递归出口。

           <2>  深层次的递归会涉及到频繁进栈出栈和分配内存空间,所以运行效率比较低,当问题规模较大时,不推荐使用。

           <3>  在递归过程中,每次调用中的参数,方法返回点,局部变量都是存放在堆栈中的,如果当问题规模非常大时,容易造成堆栈溢出。

  • 相关阅读:
    GoJS实例1
    MAVEN 添加本地jar
    找不到xml、找不到类
    office365激活码序列号密钥:
    【转载】EF Core & Castle DynamicProxy基本用法(AOP)
    【转载】SQL Server
    【转载】对象克隆(C# 快速高效率复制对象另一种方式 表达式树转)
    [转载] Emit动态生成代码
    【转载】Windows 下搭建 wmi_exporter+Prometheus+Grafana 服务器性能监控平台
    Java RMI 使用
  • 原文地址:https://www.cnblogs.com/mmcmmc/p/3946138.html
Copyright © 2020-2023  润新知