zoukankan      html  css  js  c++  java
  • 序列化二叉树和反序列化二叉树

    二叉树被记录成文件的过程叫作二叉树的序列化,通过文件内容重建原来的二叉树过程叫做二叉树反序列化,

    废话不多说我们来做这两个功能,首先给定一颗二叉树的节点head,并已知二叉树结点的值类型为32位整型,

    补充说明:这里是通过先序遍历来实现序列化和反序列化过程(及先输出当前节点,再输出左节点,最后输出右节点)

    序列化的思路:

    首先加上序列化的结果字符串为str,初始时 str=" "。先遍历二叉树,如果遇到null节点,就在str的末尾加上“#!","#"表示这个节点为空,

    节点值不存在,“!”表示一个值结束;如果遇到不为空的节点,假设值为3,就在str的末尾加上“3!"。

    用这个数为例子他序列化出来的字符串为:1!2!4!#!7!#!#!#!3!5!#!#!6!#!#!

    我们先写序列化的代码

     1 public class Node
     2 {
     3     public int value;
     4     public Node left;
     5     public Node right;
     6 
     7     public Node(int data)
     8     {
     9         this.value = data;
    10     }
    11 
    12     /**************序列化二叉树和反序列化二叉树***************/
    13     //首先把二叉树每个数输出字符串并加上"!"
    14     //如果是空数据则返回"#!",然后使用先序来保存数据结构
    15 
    16     /// <summary>
    17     /// 序列化先序遍历二叉树
    18     /// 将二叉树序列按先序遍历输成字符
    19     /// </summary>
    20     /// <param name="head">结点</param>
    21     /// <returns></returns>
    22     public string SerialByPre(Node head)
    23     {
    24         //如果节点没有数据则结束递归,返回 "#!"
    25         if (head == null) return "#!";
    26         //将当前节点的数据变成字符 “1!”
    27         string res = head.value + "!";
    28         //递归遍历左节点
    29         res += SerialByPre(head.left);
    30         //递归遍历右节点
    31         res += SerialByPre(head.right);
    32         //返回字符
    33         return res;
    34     }

    然后继续完成反序列化的代码

     1  /// <summary>
     2     /// 反序列化二叉树
     3     /// </summary>
     4     /// <param name="preStr">字符串</param>
     5     /// <returns></returns>
     6     public Node ReconByPreString(string preStr)
     7     {
     8         //将序列化的二叉树元素分别保存到数组
     9         string[] values = preStr.Split('!');
    10         //创建队列
    11         Queue<string> queue = new Queue<string>();
    12        //循环将二叉树元素字符加入队列中
    13         for (int i = 0; i <values.Length; i++)
    14         {
    15             queue.Enqueue(values[i]);
    16         }
    17         //创建二叉树
    18         return ReconPreOrder(queue);
    19     }
    20 
    21     /// <summary>
    22     /// 根据队列创建二叉树
    23     /// </summary>
    24     /// <param name="queue">队列</param>
    25     /// <returns></returns>
    26     public Node ReconPreOrder(Queue<string> queue)
    27     {
    28         //从队列取出头元素并删除
    29         string value = queue.Dequeue();
    30         //如果没数据则退出递归
    31         if (value.Equals("#")) return null;
    32         //创建一个新的结点并给它赋值
    33         Node head = new Node(int.Parse(value));
    34         //递归得到当前结点的左孩子(遇到“#”则结束)
    35         head.left = ReconPreOrder(queue);
    36         //递归得到当前结点的右孩子(遇到“#”则结束)
    37         head.right = ReconPreOrder(queue);
    38         //返回这个二叉树的头结点
    39         return head;
    40     }

    最后还需要一个先序遍历函数输出这个数来验收结果

    1 //先序输出二叉树数据结构
    2     public void PreOrderUnRecur(Node head)
    3     {
    4         if (head == null) return;
    5         Console.Write(head.value + " ");
    6         PreOrderUnRecur(head.left);
    7         PreOrderUnRecur(head.right);
    8     }

    最后我们来调用这序列化和反序列化函数

     1   static void Main(string[] args)
     2         {
     3             Node A = new Node(1);
     4             Node B = new Node(2);
     5             Node C = new Node(3);
     6             Node D = new Node(4);
     7             Node E = new Node(5);
     8             Node F = new Node(6);
     9             Node G = new Node(7);
    10 
    11             A.left = B;
    12             A.right = C;
    13             B.left = D;
    14             D.right = G;
    15             C.left = E;
    16             C.right = F;
    17 
    18             string res= A.SerialByPre(A);
    19             Console.WriteLine(res);
    20             Node head=A.ReconByPreString(res);
    21             A.PreOrderUnRecur(head);
    22             Console.ReadKey();
    23         }

    输出了正确的结果

  • 相关阅读:
    Centos 下安装php
    php 基础 PHP保留两位小数的几种方法
    php基础 php 全局变量
    php 基础 语句include和require的区别是什么?为避免多次包含同一文件,可用(?)语句代替它们?
    php 基础 获取远程连接
    php 基础 php获取前一天,前一个月,前一年的时间
    redis 基础 Redis 数据类型
    [Poj2349]Arctic Network(二分,最小生成树)
    [USACO07DEC]Sightseeing Cows(负环,0/1分数规划)
    [Tyvj2032]升降梯上(最短路)
  • 原文地址:https://www.cnblogs.com/BigDong/p/8018086.html
Copyright © 2011-2022 走看看