Assignment 3: I Don’t Need No Stinkin’ Recursion¶
In this assignment, your task is to implement a binary search tree without
using any recursive functions. The details are in the comments for a3.h
given below.
Notes¶
Don’t put a
main
function ina3.h
— that will cause it to fail when it is marked! The marker will supply their own.cpp
file with amain
function that#include
s youra3.h
file.You may want to build your program using the
-B
option withmake
to force it to re-compile your program every time, e.g.:$ make -B a3
If
a3.cpp
#include
sa3.h
, then calling justmake a3.cpp
will not re-compilea3.cpp
if you’ve only made changes toa3.h
.Use
valgrind
to help ensure your program has no memory leaks or other memory errors, e.g.:$ make -B a3 $ valgrind ./a3 // ... lots of output ...
A program is considered to have no memory leaks or problems if:
- In the
LEAK SUMMARY
,definitely lost
,indirectly lost
, andpossibly lost
must all be 0. - The
ERROR SUMMARY
must report 0 errors. - It is usually okay if
still reachable
reports a non-zero number of bytes.
- In the
Use only
new
anddelete
to allocate and de-allocate memory. Do not usemalloc
andfree
.Do not use C++ smart pointers, such as
unique_ptr
orshared_ptr
. Stick to raw pointers, and usenew
anddelete
(ordelete[]
) and constructors/destructors (plusvalgrind
) to manage memory.Do not use any pre-defined data structures (such as arrays or vectors) or algorithms to implement your solution — do it using only basic C++ functions and features.
You must include the large comment section with student info and the statement of originality. If your submitted file does not have this, then we will assume your work is not original and it will not be marked.
If your program meets all these basic requirements, then it will graded using the marking scheme on Canvas.
Hints¶
- This is a binary search tree, so make sure the binary search tree property remains after all insertions and deletions.
- You don’t need to keep the tree short, i.e. simple insertion and deletion is fine for this assignment.
a3.h¶
// a3.h
/////////////////////////////////////////////////////////////////////////
//
// Student Info
// ------------
//
// Name : <put your full name here!>
// St.# : <put your full SFU student number here>
// Email: <put your SFU email address here>
//
//
// Statement of Originality
// ------------------------
//
// All the code and comments below are my own original work. For any non-
// original work, I have provided citations in the comments with enough
// detail so that someone can see the exact source and extent of the
// borrowed work.
//
// In addition, I have not shared this work with anyone else, and I have
// not seen solutions from other students, tutors, websites, books,
// etc.
//
/////////////////////////////////////////////////////////////////////////
#include "cmpt_error.h"
#include <iostream>
#include <string>
using namespace std;
///////////////////////////////////////////////////////////////////////////////
//
// Your task for this assignment is to implement all of the methods of the BST
// class given below, subject to a few important constraints.
//
// Here are the things your implementation **cannot** do:
//
// - You **cannot** use recursion anywhere in any of your code.
//
// - You **cannot** add new variables to the BST class, public or private. You
// cannot add any global variables.
//
// - You **cannot** #include any other files. If you borrow code or ideas from
// any other source, be sure to cite the source (e.g. as a comment in your
// code).
//
// - You **cannot** use arrays or vectors or any other pre-made data
// structure. As mentioned below, you may only use data structures that you
// implement yourself.
//
// Here are the things your implementation **can** do:
//
// - You **can** add helper methods, either public or private, to BST. You may
// also add helper functions outside of BST. Of course, any extra
// methods/functions you add must follow the "cannot" rules above.
//
// - You **can** add helper classes, either in BST or outside of BST. For
// instance, you could implement your own stack class.
//
// Put all the code necessary to implement BST correct inside a3.h, and then
// submit just this file when you are done. Put your testing code in a3.cpp.
//
// In the specification of the methods for BST, these variables are used:
//
// - n is the number of nodes in the BST
// - h is the height of the BST
// - T refers to the tree immediately before a method is called
// - T' refers to the tree immediately after the method is finished
//
///////////////////////////////////////////////////////////////////////////////
class BST {
private:
struct Node {
string value;
Node* left;
Node* right;
};
Node* root;
public:
// Pre-condition:
// none
// Post-condition:
// constructs a new empty BST
// Constraints:
// O(1) performance
BST();
// Pre-condition:
// none
// Post-condition:
// deletes all the nodes in this BST
// Constraints:
// O(n) performance
~BST();
// Pre-condition:
// none
// Post-condition:
// returns the number of string in this tree (i.e. n)
// Constraints:
// worst-case O(n) performance; does not use recursion!
int size() const;
// Pre-condition:
// none
// Post-condition:
// returns the height of this tree
// Constraints:
// worst-case O(n) performance; does not use recursion!
// Note:
// The height of a BST is the number of links in the longest
// root-to-leaf path in the tree. An empty tree is height 0,
// and a tree with a single node is also height 0.
int height() const;
// Pre-condition:
// none
// Post-condition:
// returns true if s is in this tree, and false otherwise
// Constraints:
// worst-case O(h) performance; does not use recursion!
bool contains(const string& s) const;
// Pre-condition:
// none
// Post-condition:
// T'.contains(s)
// Constraints:
// worst-case O(h) performance; does not use recursion!
// Note:
// If s is already in T, then insert(s) does nothing.
void insert(const string& s);
// Pre-condition:
// none
// Post-condition:
// !T'.contains(s)
// Constraints:
// worst-case O(h) performance; does not use recursion!
// Note:
// If s is not in T, then remove(s) does nothing.
void remove(const string& s);
// Pre-condition:
// none
// Post-condition:
// prints all the strings in T to cout in pre-order order
// Constraints:
// worst-case O(n) performance; does not use recursion!
void print_preorder() const;
// Pre-condition:
// none
// Post-condition:
// prints all the strings in T to cout in in-order order
// (i.e. alphabetical order)
// Constraints:
// worst-case O(n) performance; does not use recursion!
void print_inorder() const;
// Pre-condition:
// none
// Post-condition:
// prints all the strings in T to cout in post-order order
// Constraints:
// worst-case O(n) performance; does not use recursion!
void print_postorder() const;
}; // class BST