int BinarySearchTree :: breadthFirstTraversal (int number) const { Queue queue; BSTNode* current = root; queue.add(root); int count = 0; while (current != NULL) { //If there is right child, add it to queue if (current -> getLeft() != 0) queue.add(current -> getLeft()); //If there is right child, add it to queue if (current -> getRight() != 0) queue.add(current -> getRight()); queue.removeFromHead(current); if (current->getValue() == number) { return count; } current = getBSTNodeFromQueue(queue); count++; } return count; }// end breadthFirstTraversal
int main(int argc, const char *argv[]) { BST *bst = new BST(); int array[] = {6, 4, 9, 2, 5, 8, 10, 1, 3, 7 }; for (int i = 0; i < sizeof(array)/sizeof(int); ++i) { bst->insert(new BSTNode(array[i])); } std::cout << "In-Order:" << std::endl; inorder(bst->root()); std::cout << "Pre-Order:" << std::endl; preorder(bst->root()); std::cout << "Post-Order:" << std::endl; postorder(bst->root()); std::cout << "MAX: " << bst->max()->key() << std::endl; std::cout << "MIN: " << bst->min()->key() << std::endl; BSTNode *notexist = bst->search(11); std::cout << "Key 11 is " << (notexist == NULL ? "NOT existed" : "existed") << std::endl; BSTNode *nodes = bst->search(7); std::cout << "Successor of " << nodes->key() << " is " << bst->successor(nodes)->key() << std::endl; BSTNode *nodep = bst->search(3); std::cout << "Predecessor of " << nodep->key() << " is " << bst->predecessor(nodep)->key() << std::endl; BSTNode *suMAX = bst->successor(bst->max()); std::cout << "MAX Successor " << (suMAX == NULL ? "PASS" : "FAIL") << std::endl; BSTNode *preMIN = bst->predecessor(bst->min()); std::cout << "MIN Predecessor " << (preMIN == NULL ? "PASS" : "FAIL") << std::endl; bst->remove(bst->search(11)); std::cout << "In-Order:" << std::endl; inorder(bst->root()); delete bst; return 0; }
void SplayTree::splay(BSTNode* aNode){ if(aNode ==NULL || aNode->parent() ==NULL){ //two special cases return; } BSTNode* parent = aNode->parent(); BSTNode* grandParent = parent->parent(); cout<<"splaying the node: "<<aNode->key()<<endl; while(parent != NULL && grandParent != NULL){ //all zigzig zigzag zigzigzigzag(aNode); parent = aNode->parent(); //updating parent and grandparent if(parent ==NULL){ break; //effectively end the function } grandParent = parent->parent(); if(grandParent == NULL){ break; } } if(grandParent == NULL && parent != NULL){ //parent is the root if(parent->left() ==aNode){ zigLR(aNode, parent); }else{ zigRL(aNode, parent); } } debug_print(); //finly, dump the tree structe in Graphviz format }
/* * traverses the tree and removes the node containing the target * integer if present and returns true * return false if target integer is not in tree (or the tree is empty) */ bool BSTree::Remove(int content, BSTNode*& node) { if(node == NULL) { return false; } else { if(node->contents() == content && size_ == 1) //checking if root needs to be removed { delete node; node = NULL; size_ = 0; return true; } else if(content < node->contents()) //if less than node traverse to the left { Remove(content, node->left_child()); } else if(content > node->contents()) //if greater than node traverse to the right { Remove(content, node->right_child()); } else //if the node is equal to content { if(node->left_child() == NULL && node->right_child() == NULL) //if the node to remove has no left/right child { delete node; node = NULL; } else if(node->left_child() == NULL) //node to be removed has a right subtree { BSTNode* temp = node; node = node->right_child(); delete temp; } else if(node->right_child() == NULL) //node to be removed has a left subtree { BSTNode* temp = node; node = node->left_child(); delete temp; } else if(root_->contents() == node->contents()) { BSTNode* temp = new BSTNode(FindMin(node->left_child())); node->set_contents(temp->contents()); delete temp; node->left_child() = NULL; } else { BSTNode* temp = new BSTNode(FindMin(node->right_child())); node->set_contents(temp->contents()); delete temp; } size_--; return true; } } }
void WordIndex::Insert (const Word & word, const URL & url) { bool containsWord = Map<Word, OccurrenceSet>::Contains(word); if (true == containsWord) { // The word is already in this index -- increment occurrence OccurrenceSet dummySet; MapNode<Word, OccurrenceSet> mapNode(word, dummySet); BSTNode< MapNode<Word, OccurrenceSet> >* node = BST< MapNode<Word, OccurrenceSet> >::Find(mapNode); Occurrence wrapper(url); BSTNode<Occurrence> * oNode = node->GetValue().GetValue().Find(wrapper); if (NULL != oNode) { // word occurred on a known web page oNode->GetValue().increment(); } else { // word has an occurrence on a new web page bool wasInserted = node->GetValue().GetValue().Insert(wrapper); assert(wasInserted == true); } } else { // We need to add the word to this index OccurrenceSet set; Occurrence occurrence(url); bool wasAdded = set.Insert(occurrence); assert(wasAdded == true); Map<Word, OccurrenceSet>::Insert(word, set); } }
/** * creates a new BSTNode, Inserts it into the tree, and returns true * if the integer is already in the tree, does not Insert, and returns false */ bool BSTree::Insert(int contents, BSTNode*& root) { BSTNode* newNode = new BSTNode(contents); if (root == NULL) { root = newNode; size_ += 1; return true; } else if (newNode->contents() < root->contents()) { // if (root->left_child() == NULL) // { // root->set_left_child(newNode); // size_ += 1; // } // else Insert(contents, root->left_child()); } else if (newNode->contents() > root->contents()) { Insert(contents, root->right_child()); }else return false; }
//------------->>>>splay tree funcs bool SplayTree::find(string aKey){ //find a node, internal function, without splay cout<<"in splaytree::find()"<<endl; BSTNode* node = BST::find(aKey); //return the node or a node nearby cout<<"returning a node"<<endl; if(node ==NULL){ //in the case of empty tree return false; } if(node->key()==aKey){ return true; } return false; }
BSTNode<Data>* successor() { /* Determine if the right child or parent is successor. If neither, and parent exists, find out if one of the parents ancestors is the successor. If no successor exists, return 0. */ if (right!=NULL) { return right->leftmostNode(); } else if (parent==NULL) { return NULL; } else if (this==parent->left) { return parent; } else { return parent->ancestralSuccessor(); } }
void Crawler::addWords(BST < Pair < string,int > >* newOccurrences, string url){ BSTIterator<Pair <string,int> > iter = newOccurrences->Iterator(); BSTNode<Pair<string,int> > newNode(Pair<string,int>("",-1)); BSTNode<Word>* oldNode; Occurrence occ; occ.setURL(url); while(iter.hasNext()){ newNode = iter.next(); //is either a new node or an old node oldNode = words->Insert(Word(newNode.GetValue().getFirst())); occ.setOccurrences(newNode.GetValue().getSecond()); oldNode->GetValue().addOccurrence(occ); } }
void SplayTree::zigLR(BSTNode* aNode, BSTNode* aParent){ BSTNode* rightChild = aNode->right(); aNode->setRight(aParent); aParent->setParent(aNode); aParent->setLeft(rightChild); if(rightChild != NULL){ rightChild->setParent(aParent); } if(root() == aParent){ //updating the root setRoot(aNode); aNode->setParent(NULL); } // debug_print(); }
void SplayTree::zigRL(BSTNode* aNode, BSTNode* aParent){ BSTNode* leftChild = aNode->left(); aNode->setLeft(aParent); aParent->setParent(aNode); aParent->setRight(leftChild); if(leftChild != NULL){ leftChild->setParent(aParent); } if(root() == aParent){ setRoot(aNode); aNode->setParent(NULL); } // debug_print(); }
void SplayTree::load(string aKey, string aSong){ cout<<"in splaytree load()"<<endl; if(!SplayTree::find(aKey)){ //if the entry is already in the list cout<<"key not in tree"<<endl; BST::insert(aKey); //insert the key into BST cout<<"inseted a new key!"<<endl; } BSTNode* node = BST::find(aKey); cout<<"found the key"<<endl; splay(node); //splay to the root cout<<"splayed the node "<<endl; node->addSong(aSong); cout<<"song added"<<endl; }
void add(int value) { if (root) { root->add(value); } else { root = new BSTNode(value); } }
void add(int newValue) { subtreeSize++; if (newValue <= value) { if (left) { left->add(newValue); } else { left = new BSTNode(newValue); } } else { if (right) { right->add(newValue); } else { right = new BSTNode(newValue); } } }
/** Return the leftmost node of the subtree. * PRECONDITION: this BSTNode is a node in a BST. * POSTCONDITION: the BST is unchanged. * RETURNS: The BSTNode that is the leftmost node of the subtree. */ BSTNode<Data>* leftmostNode() { /* if this has a left child, recurse on that. Otherwise, return this. */ if (left!=NULL) { return left->leftmostNode(); } else { return this; } }
BSTNode<Data>* successor() { if (right!= NULL){ return right->lastLeftNode(); } else if (parent == NULL) { return 0; } else if (this == parent ->left) { return parent; } else { return parent -> lastSucc(); } }
void SplayTree::search(string aKey) { //search a musician BSTNode* node = BST::find(aKey);//this is the splayTree find() if(node ==NULL){ cout<<"playlist is currently empty"<<endl; return; } splay(node); //splay it to the root if(node->key() == aKey){ //using internal overloaded string comparison cout<<"Yes, the musician: "<<aKey<<" is in your playlist and plays: "; node->outputSong(); //print the songs cout<<endl; } else{ cout<<aKey<<" is currently not in the playlist"<<endl; cout<<"The closest search result is: "<<node->key()<<endl; } }
/** Return the inorder ancestral successor of this BSTNode in a BST, or * 0 if none. * PRECONDITION:this BSTNode is a node in a BST. * POSTCONDITION: the BST is unchanged. * RETURNS: the BSTNode that is the inorder ancestral successor of this * BSTNode, or 0 if there is none. */ BSTNode<Data>* ancestralSuccessor() { /* Find and return a successor that is an ancestor, if it exists. */ if (parent==NULL) { return NULL; } else if (this==parent->right) { return parent->ancestralSuccessor(); } else { return parent; } }
void SplayTree::zigRLzigRL(BSTNode* aNode, BSTNode* aParent, BSTNode* aGrandParent){ BSTNode* ggParent = aGrandParent->parent(); SplayTree::Orientation orient = SplayTree::NONE; if(ggParent !=NULL){ if(ggParent->left() == aGrandParent){ orient = SplayTree::LEFT; }else{ orient = SplayTree::RIGHT; } } zigRL(aParent, aGrandParent); //rotate right to left around grandparent first zigRL(aNode, aParent); if(orient ==SplayTree::LEFT){ ggParent->setLeft(aNode); aNode->setParent(ggParent); }else if(orient == SplayTree::RIGHT){ ggParent->setRight(aNode); aNode->setParent(ggParent); } // debug_print(); }
void SplayTree::zigLRzagRL(BSTNode* aNode, BSTNode* aParent, BSTNode* aGrandParent){ BSTNode* ggParent = aGrandParent->parent(); SplayTree::Orientation orient = SplayTree::NONE; if(ggParent!=NULL){ if(ggParent->left() == aGrandParent){ //in the case of left subtree orient = SplayTree::LEFT; }else{ orient = SplayTree::RIGHT; } } zigLR(aNode, aParent); zigRL(aNode, aGrandParent); if(orient ==SplayTree::LEFT){ ggParent->setLeft(aNode); aNode->setParent(ggParent); }else if(orient == SplayTree::RIGHT){ ggParent->setRight(aNode); aNode->setParent(ggParent); } debug_print(); }
void SplayTree::zagRLzigLR(BSTNode* aNode, BSTNode* aParent, BSTNode* aGrandParent){ // aNode is a right child of a left child BSTNode* ggParent = aGrandParent->parent(); SplayTree::Orientation orient = SplayTree::NONE; if(ggParent !=NULL){ if(ggParent->left() == aGrandParent){ orient = SplayTree::LEFT; }else{ orient = SplayTree::RIGHT; } } zigRL(aNode, aParent); //rotate from right to left around parent zigLR(aNode, aGrandParent); if(orient ==SplayTree::LEFT){ ggParent->setLeft(aNode); aNode->setParent(ggParent); }else if(orient == SplayTree::RIGHT){ ggParent->setRight(aNode); aNode->setParent(ggParent); } // debug_print(); }
bool WordIndex::Test (ostream & os) { bool success = true; const int PAGES = 3; const int WORDS = 30; string urlStrs[PAGES] = { "http://www.google.com/index.html" , "file:///home/file.txt" , "http://www.msn.com/sports.html" }; URL urls[PAGES] = { URL(urlStrs[0]) , URL(urlStrs[1]) , URL(urlStrs[2]) }; Word words[WORDS] = { "and", "the", "a", "wood", "couch", "potato", "Henry", "the", "a", "and" , "a", "house", "dog", "wood", "couch", "frisbee", "green", "then", "why", "how" , "a", "a", "yes", "no", "maybe", "Henry", "the", "frisbee", "green", "couch" }; WordIndex wordIndex; for (int i = 0; i < PAGES; i++) { for (int j = 0; j < WORDS; j++) { wordIndex.Insert(words[j], urls[i]); } } OccurrenceSet set = wordIndex.GetValue("a"); BSTNode<Occurrence>* node = set.Find(Occurrence(urls[1])); TEST (NULL != node); Occurrence current = node->GetValue(); TEST(current.getURL().getFullURL() == urls[1].getFullURL()); TEST(current.getCount() == 5); return success; }
void UnorderedLinkedList :: print () const { // cout<< "(" << ((left == 0)?0:left -> getValue()) <<")"; // cout<<value; // cout<< "(" << ((right == 0)?0:right -> getValue())<<")"; // cout<<endl; if (head != 0) { BSTNode *nodeHead = head -> getValue (); cout<< "Head -->" << ((head == 0)?0:nodeHead->getValue()); } cout<<endl; if (tail != 0) { BSTNode *nodeTail = tail -> getValue (); cout<< "Tail -->" << ((tail == 0)?0:nodeTail->getValue()); } cout<<endl; }//end print
//delete the entry void SplayTree::cut(string aKey){ cout<<"<<<------internal transcript----->>>"<<endl; BSTNode* node = BST::find(aKey); //the node contains the exact key if((node->key()!= aKey) || node ==NULL ){ splay(node); //splay it anyway [2] cout<<"\nsorry, the musician: "<<aKey<<" is not in the list"<<endl; return; } if(node->parent() != NULL && (node->key() ==aKey)){ cout<<"node: "<<node->key()<<" has parent"<<endl; node = node->parent(); //node now pting to its parent cout<<"node now pting to its parent: "<<node->key()<<endl; BST::remove(aKey); //remove the key splay(node); //splay the parent to the root [2] }else if (node->parent() ==NULL){ //in the case node is the root BST::remove(aKey); } cout<<"delete sucessful!"<<endl; }
void insertWithGrouping(SplayTree<string, Array<string> >& aSplayTree, string aArtist, string aMusicEntry) { static int debug_count = 0; ostringstream os; os << "debug" << debug_count++ << ".dot"; string filename = os.str(); // Here aArtist is the key and aMusicEntry contributes toward the value BSTNode<string, Array<string> >* place = aSplayTree.findInsertionPoint(aArtist); if (place == nullptr) { // First node to be inserted Array<string> musicList; musicList.add(aMusicEntry); aSplayTree.setRoot(new BSTNode<string, Array<string> >(aArtist, musicList)); } else if (aArtist == place->key()) { // Key matched // aArtist exists -- just group the current aMusicEntry with the existing // associated musicList Array<string> musicList = place->value(); // Aggregation musicList.add(aMusicEntry); // Replace the value with the updated musicList place->setValue(musicList); // Splay this node as it is just augmented aSplayTree.splay(place); } else { // Key not matched // So, this is going to be the first music entry for aArtist Array<string> musicList; musicList.add(aMusicEntry); BSTNode<string, Array<string> >* newNode = new BSTNode<string, Array<string> >(aArtist, musicList, nullptr, nullptr, place); if (aArtist < place->key()) { // Node on the left of place place->setLeft(newNode); } else { // Node on the right of place place->setRight(newNode); } // dumpSplayTree(aSplayTree, filename); aSplayTree.splay(newNode); } }
#define CATCH_CONFIG_MAIN #include "catch.hpp" void updateContents (int& contents, int newContents) { contents = newContents; } void updateLink (BSTNode*& link, BSTNode* newLink) { link = newLink; } TEST_CASE ("BSTNode basic functionality") { BSTNode node1; BSTNode node2(99); BSTNode node3(-1); CHECK(node1.getContents() == 0); CHECK(node1.getLeftChild() == NULL); CHECK(node1.getRightChild() == NULL); CHECK(node2.getContents() == 99); CHECK(node2.getLeftChild() == NULL); CHECK(node2.getRightChild() == NULL); node1.setLeftChild(&node2); CHECK(node1.getLeftChild() == &node2); node1.setRightChild(&node3);
* Author : Luke Sathrum * Description : Unit test to test Lab #24 Functionality */ #define CATCH_CONFIG_MAIN #include "catch.hpp" // For NULL #include <cstddef> #include "bs_tree.h" // To test for correct header guards #include "bst_node.h" #include "bst_node.h" #include "bs_tree.h" TEST_CASE("Default Constructor for BSTNode") { const BSTNode const_node; BSTNode node; BSTNode* p_node = &node; SECTION("Contents const Accessor") { CHECK(const_node.contents() == 0); } SECTION("Contents Accessor (Editable)") { node.contents() = 10; CHECK(node.contents() == 10); } SECTION("Left Child const Accessor") { CHECK(const_node.left_child() == NULL); }
/** Pre-increment operator. */ BSTIterator<Data>& operator++() { curr = curr->successor(); return *this; }
/** Post-increment operator. * Update this BSTIterator to point to the inorder successor of the current * BSTNode, and return a copy of the old, non-updated BSTIterator. */ BSTIterator<Data> operator++(int) { BSTIterator<Data> before(curr); BSTIterator<Data> now(curr->successor()); *this=now; return before; }
/** Pre-increment operator. * Update this BSTIterator to point to the inorder successor of the current * BSTNode, and return a reference to the updated BSTIterator. */ BSTIterator<Data>& operator++() { BSTIterator<Data> now(curr->successor()); *this=now; return *this; }