[ISSUE] Morris Binary Tree

Describe

Besides the realization of tradictional binary tree based on recursion or stack, which needs O(n) space complexity, there also exit one structure using O(1) space complexity called Morris Binary Tree. This structure utilizes the right pointer of each leaf node to realize the searching order.

Code

In-order:

void morrisInorder() {
    node *it = &root;
    while(it) {
        if (it->left) {
            node *tend = it->left;
            while (tend->right && tend->right!=it) {
                tend = tend->right;
            }
            if (tend->right) {
                cout<<' '<<it->val;
                // tend->right = NULL;
                it = it->right;
            } else {
                tend->right = it;
                it = it->left;
            }
        } else {
            cout<<' '<<it->val;
            it = it->right;
        }
    }
    cout<<endl;
}

Pre-order:

void morrisPreorder() {
    node *it = &root;
    while(it) {
        cout<<' '<<it->val;
        if (it->left) {
            node *tend = it->left;
            while (tend->right && tend->right!=it) {
                tend = tend->right;
            }
            tend->right = it->right;
            it = it->left;
        } else {
            it = it->right;
        }
    }
    cout<<endl;
}

Post-order:

void reversePrint(node *begin, node *end) {
    node *it = begin;
    if (it == end) {
        cout<<' '<<it->val;
        return;
    }
    node *head = new node{0,NULL,NULL};
    do {
        node *nnode = new node{it->val,NULL,NULL};
        nnode->right = head->right;
        head->right = nnode;
        it = it->right;
    } while (it != end);
    cout<<' '<<it->val;
    it = head->right;
    while (it) {
        cout<<' '<<it->val;
        it = it->right;
    }
}

void morrisPostorder() {
    node *it = new node{0,&root,NULL};
    while(it) {
        if (it->left) {
            node *tend = it->left;
            while (tend->right && tend->right!=it) {
                tend = tend->right;
            }
            if (tend->right) {
                node *tmp = it->left;
                reversePrint(tmp, tend);
                it = it->right;
            } else {
                tend->right = it;
                it = it->left;
            }
        } else {
            // cout<<' '<<it->val;
            it = it->right;
        }
    }
    cout<<endl;
}

Example:

struct node {
    int val;
    struct node *left;
    struct node *right;
} root;

int tree[] = {0,6,2,7,1,4,0,9,0,0,3,5,0,0,8,0};
node* ptree[7];

void build() {
    root.val = tree[1];
    node *p = &root;
    ptree[1] = p;
    for (int i=1; i<=7; ++i) {
        p = ptree[i];
        if (tree[2*i] != 0) {
            p->left = new node{tree[2*i],NULL,NULL};
            ptree[2*i] = p->left;
        }
        if (tree[2*i+1] != 0) { 
            p->right = new node{tree[2*i+1],NULL,NULL};
            ptree[2*i+1] = p->right;
        }
    }
}

void print(const node* p) {
    if (!p)
        return;
    print(p->left);
    cout<<' '<<p->val;
    print(p->right);
}

int main() {
    build();
    // print(&root);
    // cout<<endl;

    morrisInorder();
    // morrisPreorder();
    // morrisPostorder();
    return 0;
}

 

源引自己的github.io

http://awarrior.github.io/morris-binary-tree/

 

 

 

posted @ 2015-03-30 13:48  awarrior  阅读(202)  评论(0编辑  收藏  举报