When first learned binary tree at school, given a binary tree, there are three basic orders to traverse all its nodes (in fact there are more than three orders): pre-order, mid-order, and post-order. Suppose that we have pre-order and mid-order at hand, the binary tree can be reconstructed and its post-order traversal can be generated (Notice that post-order and mid-order can also provide enough information to determine the binary tree whereas only pre-order and post-order cannot, because such situation that a non-leaf node has only one subtree exists and it cannot be determined whether the subtree is left child or right child). Below is the c++ implementation.
- #include <iostream>
- #include <assert.h>
- using namespace std;
- template <typename T>
- struct Node {
- T data;
- Node * left;
- Node * right;
- };
- // Find the index of an element in a sequence within a certain length.
- template <typename T>
- int IndexOf(T* sequence, int length, T element) {
- for(int i = 0; i < length; ++i) {
- if(element == sequence[i]) {
- return i;
- }
- }
- return -1;
- }
- // Reconstruct a binary tree through its pre- and mid-order traversal.
- template <typename T>
- Node<T>* TreeReconstruction(T* preOrder, T* midOrder, int length) {
- if(length == 0) {
- return NULL;
- }
- Node<T>* root = new Node<T>();
- root->data = preOrder[0];
- int index = IndexOf(midOrder, length, preOrder[0]); // Find index of root in mid-order sequence.
- assert(index != -1);
- root->left = TreeReconstruction(preOrder + 1, midOrder, index); // Reconstruct root's left child.
- root->right = TreeReconstruction(preOrder + 1 + index, midOrder +1 + index, length - 1 - index); //Reconstruct root's right child.
- return root;
- }
- // Print the post-order traversal of a binary tree.
- template <typename T>
- void PrintPostOrder(Node<T>* root) {
- if(root == NULL) {
- return;
- }
- PrintPostOrder(root->left);
- PrintPostOrder(root->right);
- cout << root->data;
- }
- // Test code: main.
- int main(int argc, char ** argv) {
- int pre[8] = {1,2,4,5,7,8,3,6};
- int mid[8] = {4,2,7,5,8,1,3,6};
- Node<int>* tree = TreeReconstruction(pre, mid, 8);
- PrintPostOrder(tree);
- cout << endl;
- return 0;
- }
The command line prints:
47852631
It works. As you see, recursive programming can be very helpful and useful when a data structure can be viewed as consisting of some similar substructures.