二叉樹的序列化和反序列化,特別有意思的一個題目,最近忽然發現用好遞歸真的能夠很是優雅的寫好代碼!java
那將是我畢生追求的目標!---------------->儘管現狀並不盡如人意,但是多磨鍊一下本身有什麼很差呢?spa
之因此選這個題目進行整理,是由於二叉樹的序列化和反序列化都用到了遞歸的思想,並且結合了二叉樹的前序遍歷,我以爲很是有意思,爲了增強本身的記憶,寫出來code
你們一塊兒交流吧!blog
首先畫一個簡單的樹的模型一塊兒看一下:排序
String Serialize(TreeNode root) { if(root==null) return "#"; return root.val + " "+Serialize(root.left)+" "+Serialize(root.right); }
序列化部分的代碼比較簡單,咱們畫一幅樹一會兒就能夠理解,我以爲樹的前序遍歷過程自己就是一個遞歸的思想,能夠回顧一下咱們腦子是如何寫一棵樹的前序遍歷的遞歸
1--->2-->4-->5--->3-->6-->7 !就是樹的完整的前序遍歷的過程,當咱們進到左子樹的時候,自己也是將上一個的程序壓如腦棧!而後左子樹根節點爲根節點,繼續遵循中左右的原則進行排序吧!內存
因此序列化的代碼其實很簡單:字符串
1先是遞歸結束的條件 ---> if(root==null) 那麼就return"#";string
2 若是根節點不是null的話,那麼就遵循着前序遍歷的條件輸出 root.val+" "+Serialize(root.left)+" "+Serialize(root.right); !!!跟人寫前序遍歷的時候的思惟徹底一致!class
String dstr=""; TreeNode Deserialize(String str) { dstr = str; return deserialize(); } private TreeNode deserialize() { int index = dstr.indexOf(" "); String Node = index==-1?dstr:dstr.substring(0,index); dstr = index==-1?"":dstr.substring(index+1); if(Node.equals("#"))//必定要注意字符串的相等用equals來判斷不能用== return null; int value = Integer.parseInt(Node); TreeNode t = new TreeNode(value); t.left = deserialize(); t.right = deserialize(); return t; }
反序列化的代碼也用到了遞歸的思想,上面那棵樹,咱們寫一下它的序列化的結構是:
1-->2-->4-->#-->#-->5-->#-->#-->3-->6-->#-->#-->7-->#-->#
#號表明的就是null!那麼咱們來分析一下這個代碼,
首先須要明確 序列化以後的代碼是用" "進行分隔的,因此咱們就是要找int index= dstr.indexOf(" ");這樣分紅能找到和找不到兩種狀況
若是index=-1說明找不到,那麼String Node = dstr,找不到說明只有一個Node所有是value,若是找到了就切分substring(0,index)--->index取不到恰好是一個value
而後咱們須要將全局的dstr進行切分,也就是說若是你已經把1這個值取出來了,須要切掉!dstr = index==-1?"":dstr.substring(index+1);//從這個空格的下一個字符開始,恰好是下一個value;
以後就是新建TreeNode的節點,而後進行樹的構造過程!
t.left = deserialize();
t.right = deserialize();
return t;
能夠發現反序列化真的和序列化產生的字符串配合的十分恰當,讓人 感嘆遞歸的神奇之處!