輸入一棵二叉搜尋樹,將該二叉搜尋樹轉換成乙個排序的雙向鍊錶。要求不能建立任何新的結點,只能調整樹中結點指標的指向。
思路:分為迴圈版本和遞迴版本。
迴圈版本:
二叉搜尋樹的中序遍歷就是遞增序列,所以本題本質就是中序遍歷。有兩點非常需要注意:
1)開始自己認為需要對鍊錶的首尾節點進行特殊處理,比如開始節點需要left指向nullptr,但是畫個圖就會非常明顯,中序遍歷是左中右的順序,所以頭節點是遍歷到最左邊的葉子節點才開始處理,此時頭結點left和right指標都指向nullptr,同理尾節點也是一樣的,所以不需要進行特殊處理,需要注意的時候因為最後需要返回乙個頭節點,所以需要乙個bool變數記錄第一次遍歷得到的頭結點儲存起來,後面進行return。
2)開始自己想的是將中序遍歷的結果使用乙個陣列儲存下來,但是不需要這麼做,只需要遍歷的過程中,進行交換即可,乙個傳入的root變數,乙個pre節點,
root -> left =pre;pre -> right = root;
/*struct treenode
};*/
class
solution
//inorder
stacks;
treenode* pre =nullptr;
treenode* root =pre;
bool isfirst = true
;
while(!s.empty() || prootoftree !=nullptr)
if(!s.empty())
else
prootoftree = prootoftree ->right;}}
return
root;
}};
2、遞迴版本
將左子樹轉換為有序雙向鍊錶,然後找到左子樹對應鍊錶的最後乙個節點leftlast,將leftlast和root節點連線起來,然後對右子樹進行同樣的處理,得到右子樹對應的煉表頭結點是righthead,將root和righthead連線起來,放回結果的時候需要判斷lefthead是否為空,為空的時候需要返回root。
這裡關鍵的理解就是helper這個遞迴函式每次返回的是乙個鍊錶的頭結點,不管是左子樹還是右子樹呼叫返回的都是對應部分的頭結點。
/*struct treenode
};*/
class
solution
treenode* lefthead = helper(root ->left);
treenode* leftlast =lefthead;
if(leftlast !=nullptr)
leftlast -> right =root;
root -> left =leftlast;
}treenode* righthead = helper(root ->right);
if(righthead !=nullptr)
return (lefthead != nullptr) ?lefthead : root;
}treenode* convert(treenode*prootoftree)
return
helper(prootoftree);
}};
二叉搜尋樹與雙向鍊錶
1.問題描述 輸入一顆二叉搜尋樹,將該二叉搜尋樹轉換成乙個排序的雙向鍊錶。要求不能建立任何新的結點,只能調整樹中結點指標的指向。來自 劍指offer 2.分析 對於二叉搜尋樹我們知道,樹的左孩子都比根節點要下,樹的右孩子都比根結點要大,根據這個特點,我們進行中序遍歷得到的序列就會滿足題目的要求,我們...
二叉搜尋樹與雙向鍊錶
問題描述 輸入一棵二叉搜尋樹,將該二叉搜尋樹轉換成乙個排序的雙向鍊錶。要求不能建立任何新的結點,只能調整樹中結點指標的指向。演算法 struct binarytreenode binarytreenode convert binarytreenode prootoftree plastnodeinl...
二叉搜尋樹與雙向鍊錶
排序二叉樹與雙向鍊錶.cpp 定義控制台應用程式的入口點。題目描述 輸入一棵二叉搜尋樹,將該二叉搜尋樹轉換成乙個排序的雙向鍊錶。要求不能建立任何新的結點,只能調整樹中結點指標的指向。思路 通過對一顆排序二叉樹的認識可知一顆排序二叉樹中序輸出就是有序的 通過後序遍歷讓子樹分別找到自己的left和rig...