Question: In this assignment, you will implement the following inorder, preorder, and postorder traversal functions on a binary search tree: Each of these traversal methods matches
In this assignment, you will implement the following inorder, preorder, and postorder traversal functions on a binary search tree:

Each of these traversal methods matches a public method that takes a function pointer as a parameter with an overloaded private method that takes a function pointer and a binary-search-tree node pointer as parameters. The private method is recursive. The reason the matching of public and private functions is necessary is that the private function takes a node pointer in the second parameter position; node pointers are private to the binary search tree.
Do not alter the class definition or driver code in any way. Programs that crash are subject to a 50% penalty. Please submit the class header file only (bst.h). PLEASE NOTE: You may not use any Standard Template Library (STL) classes for this assignment; use code provided below only.
Please make sure to compile your code and check for errors before submitting code that is not working.
Here is an example: suppose you have the following BST:

BST.inOrder(); yields 14->21->24->25->28->31->32->36->39->41->47
BST.preOrder(); yields 32->24->21->14->28->25->31->41->36->39->47
BST.postOrder(); yields 14->21->25->31->28->24->39->36->47->41->32
bst.h:
#pragma once
#include
#include
namespace cs20a
{
template class bst;
template
class bst_node {
friend class bst;
private:
T value;
bst_node *left, *right, *parent;
bst_node() : value(), left(nullptr), right(nullptr), parent(nullptr) {}
bst_node(const T& t, bst_node *left = nullptr, bst_node *right = nullptr, bst_node *parent = nullptr)
: value(t), left(left), right(right), parent(parent) {};
};
template
class bst {
public:
bst();
bst(const bst &rhs);
~bst();
bst& operator =(const bst & rhs);
bool empty() const;
void clear();
size_t size() const;
void insert(const T & value);
void remove(const T & value);
bool contains(const T & value) const;
T & retrieve(T & value) const;
void print();
//*** Implement these functions
void inOrder(void(*func)(const T &) = nullptr) const;
void preOrder(void(*func)(const T &) = nullptr) const;
void postOrder(void(*func)(const T &) = nullptr) const;
//***
private:
bst_node *root;
size_t _size;
void init();
void makeEmpty(bst_node* node);
void copy(const bst_node* node);
void insert(const T & value, bst_node* node);
void remove(const T & value, bst_node* node);
bool contains(const T& value, bst_node* node) const;
T & retrieve(T & value, bst_node* node) const;
void print(bst_node* node, size_t level) const;
//*** Implement these functions
void inOrder(void(*func)(const T &), bst_node* node) const;
void preOrder(void(*func)(const T &), bst_node* node) const;
void postOrder(void(*func)(const T &), bst_node* node) const;
//***
bst_node * findNode(const T &) const;
bst_node * findNode(const T &, bst_node* node) const;
bst_node * findParentNode(bst_node* node) const;
bst_node * findParentNode(bst_node* node, bst_node* child, bst_node* parent) const;
bst_node * getMaxNode(bst_node* node) const;
bst_node * getMinNode(bst_node* node) const;
};
template
bst::bst() {
init();
}
template
bst::bst(const bst &rhs) {
init();
copy(rhs.root);
}
template
bst& bst::operator=(const bst& rhs) {
if (this != &rhs) {
clear();
copy(rhs.root);
}
return *this;
}
template
bst::~bst() {
makeEmpty(root);
}
template
bool bst::empty() const {
return root == nullptr;
}
template
void bst::clear() {
makeEmpty(root);
init();
}
template
size_t bst::size() const {
return _size;
}
template
void bst::copy(const bst_node* node) {
if (node != NULL)
insert(node->value);
if (node->left != NULL)
copy(node->left);
if (node->right != NULL)
copy(node->right);
}
template
void bst::makeEmpty(bst_node* node) {
if (node != NULL) {
if (node->left != NULL)
makeEmpty(node->left);
if (node->right != NULL)
makeEmpty(node->right);
delete node;
node = NULL;
_size--;
}
}
template
void bst::init() {
root = nullptr;
_size = 0;
}
template
void bst::insert(const T &value) {
if (root == nullptr)
{
root = new bst_node(value, nullptr, nullptr, nullptr);
_size++;
}
else
{
insert(value, root);
}
}
template
void bst::insert(const T &value, bst_node* node) {
if (value value)
{
if (node->left == nullptr)
{
node->left = new bst_node(value, nullptr, nullptr, node);
_size++;
}
else
{
insert(value, node->left);
}
}
else
if (value > node->value)
{
if (node->right == nullptr)
{
node->right = new bst_node(value, nullptr, nullptr, node);
_size++;
}
else
{
insert(value, node->right);
}
}
}
template
void bst::remove(const T &value) {
if (root != nullptr)
remove(value, root);
}
template
void bst::remove(const T &value, bst_node* node) {
bst_node* current = findNode(value, node);
if (current == nullptr)
return;
bst_node* parent = findParentNode(current);
// Case 1: node to be deleted has no children
if (current->left == nullptr && current->right == nullptr)
{
if (parent != nullptr)
{
if (current->value value)
parent->left = nullptr;
else
parent->right = nullptr;
}
delete current;
_size--;
}
// Case 2: node to be deleted has one child
else if (current->left != nullptr && current->right == nullptr)
{
if (parent != nullptr)
{
current->left->parent = parent;
if (current->value value)
parent->left = current->left;
else
parent->right = current->left;
}
delete current;
_size--;
}
else if (current->left == nullptr && current->right != nullptr)
{
if (parent != nullptr)
{
current->right->parent = parent;
if (current->value value)
parent->left = current->right;
else
parent->right = current->right;
}
delete current;
_size--;
}
// Case 3: node to be deleted has two children
else if (current->left != nullptr && current->right != nullptr)
{
bst_node* maxNode = getMaxNode(current->left);
bst_node* maxParentNode = findParentNode(maxNode);
current->value = maxNode->value;
// Delete maxNode: right pointer is nullptr
if (maxParentNode != nullptr)
{
if (maxNode->left != nullptr)
maxNode->left->parent = maxParentNode;
if (maxNode->value value)
maxParentNode->left = maxNode->left;
else
maxParentNode->right = maxNode->left;
}
delete maxNode;
_size--;
}
else
{
return;
}
}
template
bst_node * bst::findNode(const T &value) const {
return findNode(value, root);
}
template
bst_node * bst::findNode(const T &value, bst_node* node) const {
if (node == nullptr)
return nullptr;
else if (value value)
return findNode(value, node->left);
else if (value > node->value)
return findNode(value, node->right);
else // value == node->value
return node;
}
template
bst_node * bst::findParentNode(bst_node* node) const {
bst_node *parent = nullptr;
bst_node *child = root;
return findParentNode(node, child, parent);
}
template
bst_node * bst::findParentNode(bst_node* node, bst_node* child, bst_node* parent) const {
if (child == nullptr)
return nullptr;
else if (node->value value)
{
parent = child;
return findParentNode(node, child->left, parent);
}
else if (node->value > child->value)
{
parent = child;
return findParentNode(node, child->right, parent);
}
else // child == node
return parent;
}
template
T & bst::retrieve(T &value) const {
return retrieve(value, root);
}
template
T & bst::retrieve(T &value, bst_node* node) const {
if (node == nullptr)
throw std::logic_error("Node does not exist.");
else if (value value)
return retrieve(value, node->left);
else if (value > node->value)
return retrieve(value, node->right);
else
return node->value;
}
template
void bst::print()
{
size_t indent = 0;
print(root, indent);
}
template
void bst::print(bst_node* node, size_t level) const
{
if (node != nullptr)
{
print(node->left, level + 1);
cout value
print(node->right, level + 1);
}
}
template
bool bst::contains(const T &value) const {
if (root == nullptr)
return false;
else
return contains(value, root);
}
template
bool bst::contains(const T &value, bst_node *node) const {
if (node == nullptr)
return false;
else if (value value)
return contains(value, node->left);
else if (value > node->value)
return contains(value, node->right);
else // value == node->value
return true;
}
template
void bst::inOrder(void(*func)(const T &)) const {
}
template
void bst::inOrder(void(*func)(const T &), bst_node* node) const {
}
template
void bst::preOrder(void(*func)(const T &)) const {
}
template
void bst::preOrder(void(*func)(const T &), bst_node* node) const {
}
template
void bst::postOrder(void(*func)(const T &)) const {
}
template
void bst::postOrder(void(*func)(const T &), bst_node* node) const {
}
template
bst_node * bst::getMaxNode(bst_node* node) const {
if (node == nullptr)
return node;
if (node->right != nullptr)
return getMaxNode(node->right);
else
return node;
}
template
bst_node * bst::getMinNode(bst_node* node) const {
if (node == nullptr)
return node;
if (node->left != nullptr)
return getMinNode(node->left);
else
return node;
}
}
BSTMenu.cpp:
#include
#include "bst.h"
using namespace std;
using namespace cs20a;
void printValue(const int &value);
enum CHOICE { MAKEEMPTY, ISEMPTY, INSERT, REMOVE, QUIT, PRINT, INORDER, PREORDER, POSTORDER, OTHER };
CHOICE menu();
int main(int argc, char* argv[]) {
int value;
bst bst;
CHOICE choice;
do {
choice = menu();
switch (choice) {
case MAKEEMPTY:
bst.clear();
break;
case ISEMPTY:
if (bst.empty()) {
cout
}
else {
cout
}
break;
case REMOVE:
if (bst.empty())
cout
else
cout
cin >> value;
bst.remove(value);
break;
case INSERT:
cout
cin >> value;
bst.insert(value);
break;
case PRINT:
bst.print();
cout
break;
case INORDER:
cout
bst.inOrder(printValue);
break;
case PREORDER:
cout
bst.preOrder(printValue);
break;
case POSTORDER:
cout
bst.postOrder(printValue);
break;
case OTHER:
cout
break;
}
} while (choice != QUIT);
return(0);
}
CHOICE menu() {
char choice;
CHOICE result;
cout
cin >> choice;
switch (choice) {
case 'M':
case 'm':
result = MAKEEMPTY;
break;
case 'E':
case 'e':
result = ISEMPTY;
break;
case 'I':
case 'i':
result = INSERT;
break;
case 'Q':
case 'q':
result = QUIT;
break;
case 'R':
case 'r':
result = REMOVE;
break;
case 'P':
case 'p':
result = PRINT;
break;
case '1':
result = INORDER;
break;
case '2':
result = PREORDER;
break;
case '3':
result = POSTORDER;
break;
default:
result = OTHER;
break;
}
return(result);
}
void printValue(const int & value)
{
cout
}
public: void inorder (void(* func const T &) const void preorder (void(* func const T &)) const void postorder (void func const T &)) const private: void inorder (void func const T &) bst node KT node const void reorder (void(* func const T &) bst node KT node const void postorder (void *func) (const T &), bst node node const KT
Step by Step Solution
There are 3 Steps involved in it
Get step-by-step solutions from verified subject matter experts
