二叉查找樹的前序遍歷,後序遍歷和中序遍歷互求算法模板

遍歷模板node


其實這個問題想清楚了很簡單,只要把這三個概念理解透徹就能夠作出來了,好比前序遍歷的第一個值必定是根節點,而後這個根節點對應到中序遍歷裏面,在中序遍歷的這個值的兩邊的值,必定在以此節點爲根節點的兩個子樹上,同理,後序遍歷也同樣。ios

已知前序遍歷和後序遍歷是不能求惟一的中序遍歷樹的。spa

 

#include <iostream> #include <string>

using std::string; template<typename _Val>
struct TreeNodeBase { TreeNodeBase<_Val> *left; TreeNodeBase<_Val> *right; _Val val; }; //已知前序遍歷和中序遍歷,找後序遍歷
template<typename _Iter, typename _sizeType, typename _TreeNodeType = TreeNodeBase<char>> _TreeNodeType *preOrderInfixOrderToSufixOrder(_Iter &pre, _Iter &in, _sizeType length) { if (length == 0) return nullptr; auto node = new _TreeNodeType; _sizeType index = 0; for (; index != length; index++)//找到對應的前序遍歷的點
        if (*(in + index) == *(pre)) break; node->left = preOrderInfixOrderToSufixOrder(pre + 1, in, index); node->right = preOrderInfixOrderToSufixOrder(pre + index + 1, in + index + 1, length - (index + 1)); node->val = *pre; std::cout << node->val << " "; return node; } //已知後序遍歷和中序遍歷,找前序遍歷
template<typename _Iter, typename _sizeType, typename _TreeNodeType = TreeNodeBase<char>> _TreeNodeType *sufixOrderInfixOrderToPreOrder(_Iter &sufix, _Iter &in, _sizeType length) { if (length == 0) return nullptr; auto node = new _TreeNodeType; node->val = *(sufix + length - 1); std::cout << node->val << " "; _sizeType index = 0; for (;index != length ;index++) if (*(in + index) == *(sufix + length - 1)) break; node->left = sufixOrderInfixOrderToPreOrder(sufix, in, index); node->right = sufixOrderInfixOrderToPreOrder(sufix + index, in + index + 1, length - (index + 1)); return node; } //已知前序遍歷/後序遍歷 + 中序遍歷求後序遍歷/前序遍歷 /*int main() { string preOrder("GDAFEMHZ"); string infixOrder("ADEFGHMZ"); string sufixOrder("AEFDHZMG"); auto root1 = preOrderInfixOrderToSufixOrder(preOrder.begin(), infixOrder.begin(), preOrder.size()); std::cout << std::endl; auto root2 = sufixOrderInfixOrderToPreOrder(sufixOrder.begin(), infixOrder.begin(), preOrder.size()); system("pause"); return 0; }*/

 

線索二叉樹與前序遍歷,後序遍歷,中序遍歷的聯繫code


 

線索二叉樹是利用了二叉樹中的null節點,在遍歷二叉樹時,若是咱們要找一個子節點的前繼和後序,每每咱們只能經過遞歸的方法,可是用了線索二叉樹之後就不用了,直接while循環就能夠了(注意後序線索二叉樹不能夠,必需要輔助棧)blog

 

寫了個C++模板來玩:遞歸

    typedef enum { Node, Thread } ChildType; struct __trueType{ }; struct __falseType { }; template<typename _Val>
    struct TreeNodeBase { typedef __falseType __isThreadingTree; TreeNodeBase() :left(nullptr), right(nullptr), val(0) { } _Val val; void *left, *right; virtual ~TreeNodeBase() { } }; template<typename _Val>
    struct ThreadingTreeNodeBase :public TreeNodeBase<_Val> { typedef __trueType __isThreadingTree; ThreadingTreeNodeBase() :leftType(ChildType::Node),rightType(ChildType::Node){ } ThreadingTreeNodeBase<_Val> *left; ThreadingTreeNodeBase<_Val> *right; ChildType leftType, rightType; ~ThreadingTreeNodeBase() { } }; template<typename _TnBase>
    class TreeHelper final { public: inline static void createInOrderThreadingTree(_TnBase *root); inline static void createPreOrderThreadingTree(_TnBase *root); inline static void createSufixOrderThreadingTree(_TnBase *root); static void inOrderShow(std::ostream &os, _TnBase *root); static void preOrderShow(std::ostream &os, _TnBase *root); static void sufixOrderShow(std::ostream &os, _TnBase *const root); template<typename _Iter, typename _sizeType> inline static _TnBase *preOrderInfixOrderToSufixOrder(_Iter &pre, _Iter &in, _sizeType length); static void setOstream(std::ostream &os) { _os = os; } static std::ostream &getOstream() { return _os; } private: template<typename _Iter, typename _sizeType> inline static _TnBase *preOrderInfixOrderToSufixOrderPirvate(_Iter &pre, _Iter &in, _sizeType length, __trueType); template<typename _Iter, typename _sizeType>
        static _TnBase *preOrderInfixOrderToSufixOrderPirvate1(_Iter &pre, _Iter &in, _sizeType length, __trueType); template<typename _Iter, typename _sizeType> inline static _TnBase *preOrderInfixOrderToSufixOrderPirvate(_Iter &pre, _Iter &in, _sizeType length, __falseType); template<typename _Iter, typename _sizeType>
        static _TnBase *preOrderInfixOrderToSufixOrderPirvate1(_Iter &pre, _Iter &in, _sizeType length, __falseType); static void createInOrderThreadingTreePrivate(_TnBase *root, _TnBase *&_preNode); static void createPreOrderThreadingTreePrivate(_TnBase *root, _TnBase *&_preNode); static void createSufixOrderThreadingTreePrivate(_TnBase *root, _TnBase *&_preNode); static _TnBase *_preNode; static std::ostream &_os; static void clearNodeType(_TnBase *root); TreeHelper() = delete; TreeHelper(const TreeHelper< _TnBase> &) = delete; TreeHelper(TreeHelper< _TnBase> &&) = delete; }; template<typename _TnBase>
    void TreeHelper<_TnBase>::inOrderShow(std::ostream &os, _TnBase *root) { if (root == nullptr) return; while (root) { while (root->leftType == ChildType::Node) root = reinterpret_cast<_TnBase *>(root->left); while (root != nullptr) { os << root->val << " "; if (root->rightType == ChildType::Thread) root = reinterpret_cast<_TnBase *>(root->right); else { root = reinterpret_cast<_TnBase *>(root->right); while (root->leftType == ChildType::Node) root = reinterpret_cast<_TnBase *>(root->left); } } } } template<typename _TnBase>
    void TreeHelper<_TnBase>::preOrderShow(std::ostream &os, _TnBase *root) { if (root == nullptr) return; while (root) { while (root != nullptr) { os << root->val << " "; if (root->rightType == ChildType::Thread) root = reinterpret_cast<_TnBase *>(root->right); else root = root->leftType == ChildType::Node ? reinterpret_cast<_TnBase *>(root->left) : reinterpret_cast<_TnBase *>(root->right); } } } template<typename _TnBase>
    void TreeHelper<_TnBase>::sufixOrderShow(std::ostream &os, _TnBase *const root) { //注意:後序遍歷不能真正經過線索走完全部節點,要用棧
        if (root == nullptr) return; _TnBase *p = root; using std::stack; stack<_TnBase *> s; _TnBase *pre = nullptr; while (true) { while (p->leftType != ChildType::Thread) { if (p->leftType == ChildType::Node &&  p->rightType == ChildType::Node) s.push(p); p = reinterpret_cast<_TnBase *>(p->left); } //pre節點跟蹤右節點的狀況
            while (p && p->rightType == ChildType::Thread) { os << p->val << " "; pre = reinterpret_cast<_TnBase *>(p); p = reinterpret_cast<_TnBase *>(p->right); } while (p->right == pre && !s.empty()) { os << p->val << " "; pre = p; s.pop(); if (!s.empty()) p = s.top(); } if (s.empty()) break; if (p != nullptr && p->rightType != ChildType::Thread) p = reinterpret_cast<_TnBase *>(p->right); } } template<typename _TnBase> std::ostream &TreeHelper<_TnBase>::_os = std::cout; template<typename _TnBase>
    void TreeHelper<_TnBase>::clearNodeType(_TnBase *root) { if (root->leftType == ChildType::Thread) { root->leftType = ChildType::Node; root->left = nullptr; } if (root->rightType == ChildType::Thread) { root->rightType = ChildType::Node; root->right = nullptr; } } template<typename _TnBase>
    void TreeHelper<_TnBase>::createInOrderThreadingTree(_TnBase *root) { _TnBase *_preNode = root; createInOrderThreadingTreePrivate(root, _preNode); if (_preNode->right == nullptr) _preNode->rightType = ChildType::Thread; } template<typename _TnBase>
    void TreeHelper<_TnBase>::createPreOrderThreadingTree(_TnBase *root) { _TnBase *_preNode = root; createPreOrderThreadingTreePrivate(root, _preNode); if (_preNode->right == nullptr) _preNode->rightType = ChildType::Thread; } template<typename _TnBase>
    void TreeHelper<_TnBase>::createSufixOrderThreadingTree(_TnBase *root) { _TnBase *_preNode = nullptr; createSufixOrderThreadingTreePrivate(root, _preNode); if (_preNode->right == nullptr) _preNode->rightType = ChildType::Thread; } template<typename _TnBase>
    void TreeHelper<_TnBase>::createInOrderThreadingTreePrivate(_TnBase *root, _TnBase *&_preNode) { if (root == nullptr) return; clearNodeType(root); if (root->leftType != ChildType::Thread) createInOrderThreadingTreePrivate(reinterpret_cast<_TnBase *>(root->left), _preNode); if (root->left == nullptr) { root->leftType = ChildType::Thread; root->left = _preNode; } if (_preNode->right == nullptr) { _preNode->rightType = ChildType::Thread; _preNode->right = root; } _preNode = root; if (root->rightType != ChildType::Thread) createInOrderThreadingTreePrivate(reinterpret_cast<_TnBase *>(root->right), _preNode); } template<typename _TnBase>
    void TreeHelper<_TnBase>::createPreOrderThreadingTreePrivate(_TnBase *root, _TnBase *&_preNode) { if (root == nullptr) return; clearNodeType(root); if (root->left == nullptr) { root->leftType = ChildType::Thread; root->left = _preNode; } if (_preNode->right == nullptr) { _preNode->rightType = ChildType::Thread; _preNode->right = root; } _preNode = root; if (root->leftType != ChildType::Thread) createPreOrderThreadingTreePrivate(reinterpret_cast<_TnBase *>(root->left), _preNode); if (root->rightType != ChildType::Thread) createPreOrderThreadingTreePrivate(reinterpret_cast<_TnBase *>(root->right), _preNode); } template<typename _TnBase>
    void TreeHelper<_TnBase>::createSufixOrderThreadingTreePrivate(_TnBase *root, _TnBase *&_preNode) { if (root == nullptr) return; clearNodeType(root); if (root->leftType != ChildType::Thread) createSufixOrderThreadingTreePrivate(reinterpret_cast<_TnBase *>(root->left), _preNode); if (root->rightType != ChildType::Thread) createSufixOrderThreadingTreePrivate(reinterpret_cast<_TnBase *>(root->right), _preNode); if (root->left == nullptr) { root->leftType = ChildType::Thread; root->left = _preNode; } if (_preNode != nullptr && _preNode->right == nullptr) { _preNode->rightType = ChildType::Thread; _preNode->right = root; } _preNode = root; } template<typename _TnBase> template<typename _Iter, typename _sizeType> inline _TnBase *TreeHelper<_TnBase>::preOrderInfixOrderToSufixOrder(_Iter &pre, _Iter &in, _sizeType length) { return preOrderInfixOrderToSufixOrderPirvate(pre, in, length, _TnBase::__isThreadingTree()); } template<typename _TnBase> template<typename _Iter, typename _sizeType> inline static _TnBase * TreeHelper<_TnBase>::preOrderInfixOrderToSufixOrderPirvate(_Iter &pre, _Iter &in, _sizeType length, __trueType) { return preOrderInfixOrderToSufixOrderPirvate1(pre, in, length, __trueType()); } template<typename _TnBase> template<typename _Iter, typename _sizeType> inline static _TnBase * TreeHelper<_TnBase>::preOrderInfixOrderToSufixOrderPirvate(_Iter &pre, _Iter &in, _sizeType length, __falseType) { return preOrderInfixOrderToSufixOrderPirvate1(pre, in, length, __falseType()); } template<typename _TnBase> template<typename _Iter, typename _sizeType> _TnBase *TreeHelper<_TnBase>::preOrderInfixOrderToSufixOrderPirvate1(_Iter &pre, _Iter &in, _sizeType length, __trueType) { if (length == 0) return nullptr; auto node = new _TnBase; _sizeType index = 0; for (; index != length; index++)//找到對應的前序遍歷的點
            if (*(in + index) == *(pre)) break; node->left = preOrderInfixOrderToSufixOrderPirvate1(pre + 1, in, index, __trueType()); node->right = preOrderInfixOrderToSufixOrderPirvate1(pre + index + 1, in + index + 1, length - (index + 1), __trueType()); node->val = *pre; _os << node->val << " "; return node; } template<typename _TnBase> template<typename _Iter, typename _sizeType> _TnBase *TreeHelper<_TnBase>::preOrderInfixOrderToSufixOrderPirvate1(_Iter &pre, _Iter &in, _sizeType length, __falseType) { if (length == 0) return nullptr; auto node = new _TnBase; _sizeType index = 0; for (; index != length; index++)//找到對應的前序遍歷的點
            if (*(in + index) == *(pre)) break; node->left = preOrderInfixOrderToSufixOrderPirvate1(pre + 1, in, index, __falseType()); node->right = preOrderInfixOrderToSufixOrderPirvate1(pre + index + 1, in + index + 1, length - (index + 1), __falseType()); node->val = *pre; _os << node->val << " "; return node; }
相關文章
相關標籤/搜索