C# 二叉树的遍历

先总结一下

二叉树的遍历方式有四种

深度优先遍历有三种:这三种的循环遍历方法中都用到了栈stack。不建议采用递归的原因在于如果太深,会有可能导致栈溢出

前序遍历 (根左右)

中序遍历(左根右)

后序遍历(左右根)

 广度优先

层序遍历(从上到下,从左往右)用到了队列(queue):先进先出

附上源码:

 

using System.Collections;
using System.Collections.Generic;
using System.Linq;
using UnityEngine;

public class BinaryTree : MonoBehaviour
{
    private TreeNode startNode;
    public void AddTree()
    {
        TreeNode node=new TreeNode(1);
        startNode = node;
        node.leftChild=new TreeNode(2);
        node.leftChild.leftChild=new TreeNode(3);
        node.leftChild.leftChild.leftChild=new TreeNode(4);
        node.leftChild.leftChild.rightChild = new TreeNode(5);
        node.leftChild.rightChild = new TreeNode(6);
        node.leftChild.rightChild.leftChild = new TreeNode(7);
        node.rightChild = new TreeNode(8);
        node.rightChild.leftChild = new TreeNode(9);
        node.rightChild.rightChild = new TreeNode(10);
    }

    public class  TreeNode
    {
        public int value;
        public TreeNode leftChild;
        public TreeNode rightChild;
        public TreeNode(int v)
        {
            value = v;
        }
    }

    //前序遍历 中左右  递归
    public void PreOrder(TreeNode node)
    {
        if (node != null)
        {
            Debug.Log(node.value);
            PreOrder(node.leftChild);
            PreOrder(node.rightChild);
        }
    }
    //前序遍历 中左右  非递归
    public void PreOrderLoop(TreeNode _node)
    {
        Stack<TreeNode> stack=new Stack<TreeNode>();
        TreeNode node = _node;
        while (node != null||stack.Any())
        {
            if (node != null)
            {
                stack.Push(node);
                Debug.Log(node.value);
                node = node.leftChild;
            }
            else
            {
                var temNode = stack.Pop();
                node = temNode.rightChild;
            }
        }
    }


    //中序遍历 左中右  递归
    public void InOrder(TreeNode node)
    {
        if (node != null)
        {

            InOrder(node.leftChild);
            Debug.Log(node.value);
            InOrder(node.rightChild);
        }
    }
    //中序遍历 左中右  非递归
    public void InOrderLoop(TreeNode _node)
    {
        Stack<TreeNode> stack = new Stack<TreeNode>();
        TreeNode node = _node;
        while (node != null || stack.Any())
        {
            if (node != null)
            {
                stack.Push(node);
                node = node.leftChild;
            }
            else
            {
                var temNode = stack.Pop();
                Debug.Log(temNode.value);
                node = temNode.rightChild;

            }
        }
    }
    //中序遍历 左右中  递归
    public void PostOrder(TreeNode node)
    {
        if (node != null)
        {

            PostOrder(node.leftChild);
          
            PostOrder(node.rightChild);
            Debug.Log(node.value);
        }
    }
    //中序遍历 左右中  非递归 存储上一个变量
    public void PostOrderLoopPreNode(TreeNode _node)
    {
        Stack<TreeNode> stack = new Stack<TreeNode>();
        TreeNode node = _node;
        TreeNode pre = null;
        stack.Push(node);
        while (stack.Any())
        {
            node = stack.Peek();
            if ((node.leftChild == null&&node.rightChild==null)||
                (pre!=null&&(pre==node.leftChild||pre==node.rightChild))
                )
            {
               Debug.Log(node.value);
                pre = node;
                stack.Pop();
            }
            else
            {
                if (node.rightChild != null)
                {
                    stack.Push(node.rightChild);
                }
                if (node.leftChild != null)
                {
                    stack.Push(node.leftChild);
                }
            }
        }
    }
    //中序遍历 左右中  非递归 把检测过的节点放入哈希表
    public void PostOrderLoopHashSet(TreeNode _node)
    {
        Stack<TreeNode> stack = new Stack<TreeNode>();
        HashSet<TreeNode> hash = new HashSet<TreeNode>();
        TreeNode node = _node;
        while (node!=null||stack.Any())
        {
            if (node != null)
            {
                stack.Push(node);
                node = node.leftChild;
            }
            else
            {
                var temNode = stack.Peek();
                if (temNode.rightChild != null && !hash.Contains(temNode.rightChild))
                {
                    node = temNode.rightChild;
                    hash.Add(node);
                }
                else
                {
                    Debug.Log(temNode.value);
                    hash.Add(node);
                    stack.Pop();
                }
            }
        }
    }

    public void LevelOrder(TreeNode _node)
    {
        Queue<TreeNode> queue=new Queue<TreeNode>();
        TreeNode node = _node;
        queue.Enqueue(node);
        while (queue.Any())
        {
         var temNode=   queue.Dequeue();
            Debug.Log(temNode.value);
            if (temNode.leftChild != null)
            {
         
                queue.Enqueue(temNode.leftChild);
            }
            if (temNode.rightChild != null)
            {

                queue.Enqueue(temNode.rightChild);
            }
        }
    }

    // Start is called before the first frame update
    void Start()
    {
        AddTree();
        // PreOrder(startNode);
        // PreOrderLoop(startNode);
        //   InOrder(startNode);
        // InOrderLoop(startNode);
        //    PostOrder(startNode);
        // PostOrderLoopPreNode(startNode);
        // PostOrderLoopHashSet(startNode);
        LevelOrder(startNode);
    }
}

 

  • 2
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值