:
#include <iostream> #include <queue> //// Use Queue is available in C ++ using namespace std; // Node Cartesian tree. struct CTreapNode { int Key; // Ключ. int Priority; // Приоритет узла. CTreapNode* Left; // Левый дочерний узел. CTreapNode* Right; // Правый дочерний узел. CTreapNode(int _key, int _priority) : Key(_key), Priority(_priority), Left(0), Right(0) {} }; // Class Cartesian tree. class CTreap { public: // Constructor creates an empty tree. CTreap() : root(0) {} // The destructor deletes all the elements of the tree. ~CTreap(); // Add a node (key, priority) in the tree. // key and priority should be unique by definition, the Cartesian tree. void Insert(int key, int priority); // Print the tree traversal console from left to right. int getMaxWidth(); private: CTreapNode* root; // Tree root. void deleteSubTree(CTreapNode* node); void split(CTreapNode* node, int key, CTreapNode*& leftTree, CTreapNode*& rightTree); CTreapNode* merge(CTreapNode* leftTree, CTreapNode* rightTree); int getWidth(CTreapNode* root, int level); int height(CTreapNode* node); }; CTreap::~CTreap() { deleteSubTree(root); } // destroy the subtree whose root is node. void CTreap::deleteSubTree(CTreapNode* node) { if (node == 0) { // We got to the end of the tree. return; } deleteSubTree(node->Left); node->Left = 0; deleteSubTree(node->Right); node->Right = 0; delete node; } // Splits bunch into two parts. void CTreap::split(CTreapNode* node, int key, CTreapNode*& leftTree, CTreapNode*& rightTree) { if (node == 0) { leftTree = 0; rightTree = 0; return; } if (node->Key < key) { split(node->Right, key, node->Right, rightTree); leftTree = node; } else { split(node->Left, key, leftTree, node->Left); rightTree = node; } } //merges the two Cartesian tree into one.Elements in leftTree elements should be less rightTree. CTreapNode* CTreap::merge(CTreapNode* leftTree, CTreapNode* rightTree) { if (leftTree == 0) { return rightTree; } if (rightTree == 0) { return leftTree; } if (rightTree->Priority > leftTree->Priority) { rightTree->Left = merge(leftTree, rightTree->Left); return rightTree; } else { leftTree->Right = merge(leftTree->Right, rightTree); return leftTree; } } // Implemented inefficient version of the insert. void CTreap::Insert(int key, int priority) { if (root == 0) { root = new CTreapNode(key, priority); return; } CTreapNode* leftTree; CTreapNode* rightTree; split(root, key, leftTree, rightTree); root = merge(leftTree, new CTreapNode(key, priority)); root = merge(root, rightTree); } int CTreap::height(CTreapNode* node) { if (node == NULL) return 0; else { // compute the height of each subtree. int lHeight = height(node->Left); int rHeight = height(node->Right); // use the larger one. return (lHeight > rHeight) ? (lHeight + 1) : (rHeight + 1); } } int CTreap::getMaxWidth() { int maxWidth = 0; int width; int h = height(root); int i; // Get width of each level and compare the width with maximum width so far. for (i = 1; i <= h; i++) { width = getWidth(root, i); if (width > maxWidth) maxWidth = width; } return maxWidth; } // Get width of a given level int CTreap::getWidth(CTreapNode* root, int level) { if (root == NULL) return 0; if (level == 1) return 1; else if (level > 1) return getWidth(root->Left, level - 1) + getWidth(root->Right, level - 1); }
#include <iostream> #include <queue> //// Use Queue is available in C ++ using namespace std; // Node Cartesian tree. struct CTreapNode { int Key; // Ключ. int Priority; // Приоритет узла. CTreapNode* Left; // Левый дочерний узел. CTreapNode* Right; // Правый дочерний узел. CTreapNode(int _key, int _priority) : Key(_key), Priority(_priority), Left(0), Right(0) {} }; // Class Cartesian tree. class CTreap { public: // Constructor creates an empty tree. CTreap() : root(0) {} // The destructor deletes all the elements of the tree. ~CTreap(); // Add a node (key, priority) in the tree. // key and priority should be unique by definition, the Cartesian tree. void Insert(int key, int priority); // Print the tree traversal console from left to right. int getMaxWidth(); private: CTreapNode* root; // Tree root. void deleteSubTree(CTreapNode* node); void split(CTreapNode* node, int key, CTreapNode*& leftTree, CTreapNode*& rightTree); CTreapNode* merge(CTreapNode* leftTree, CTreapNode* rightTree); int getWidth(CTreapNode* root, int level); int height(CTreapNode* node); }; CTreap::~CTreap() { deleteSubTree(root); } // destroy the subtree whose root is node. void CTreap::deleteSubTree(CTreapNode* node) { if (node == 0) { // We got to the end of the tree. return; } deleteSubTree(node->Left); node->Left = 0; deleteSubTree(node->Right); node->Right = 0; delete node; } // Splits bunch into two parts. void CTreap::split(CTreapNode* node, int key, CTreapNode*& leftTree, CTreapNode*& rightTree) { if (node == 0) { leftTree = 0; rightTree = 0; return; } if (node->Key < key) { split(node->Right, key, node->Right, rightTree); leftTree = node; } else { split(node->Left, key, leftTree, node->Left); rightTree = node; } } //merges the two Cartesian tree into one.Elements in leftTree elements should be less rightTree. CTreapNode* CTreap::merge(CTreapNode* leftTree, CTreapNode* rightTree) { if (leftTree == 0) { return rightTree; } if (rightTree == 0) { return leftTree; } if (rightTree->Priority > leftTree->Priority) { rightTree->Left = merge(leftTree, rightTree->Left); return rightTree; } else { leftTree->Right = merge(leftTree->Right, rightTree); return leftTree; } } // Implemented inefficient version of the insert. void CTreap::Insert(int key, int priority) { if (root == 0) { root = new CTreapNode(key, priority); return; } CTreapNode* leftTree; CTreapNode* rightTree; split(root, key, leftTree, rightTree); root = merge(leftTree, new CTreapNode(key, priority)); root = merge(root, rightTree); } int CTreap::height(CTreapNode* node) { if (node == NULL) return 0; else { // compute the height of each subtree. int lHeight = height(node->Left); int rHeight = height(node->Right); // use the larger one. return (lHeight > rHeight) ? (lHeight + 1) : (rHeight + 1); } } int CTreap::getMaxWidth() { int maxWidth = 0; int width; int h = height(root); int i; // Get width of each level and compare the width with maximum width so far. for (i = 1; i <= h; i++) { width = getWidth(root, i); if (width > maxWidth) maxWidth = width; } return maxWidth; } // Get width of a given level int CTreap::getWidth(CTreapNode* root, int level) { if (root == NULL) return 0; if (level == 1) return 1; else if (level > 1) return getWidth(root->Left, level - 1) + getWidth(root->Right, level - 1); }