I have a design-related question in C++.
I’m building a tree for a HW assignment.
The tree implementation is pretty straightforward. Basically it’s a templated class
template <typename TYPE, typename KEY>
class Tree
{
public:
void Insert(TYPE& node);
void Remove(TYPE& node);
TYPE& Find (KEY key);
//etc.
};
So far is just background.
Now, later when I use Tree, I have an Employee class that I want to have 2 trees of, but once use ID as the key and in the other use Salary as the key, but I don’t want to duplicate the data.
Obviously I need to implement 2 different comparison functions. My first attempt was to do something like this:
class Employee { public: int ID; float Salary; };enum COMPARE_RESULT { LESS_THAN = -1, EVEN = 0, GREATER_THAN = 1 } template class IComparable { public: virtual COMPARE_RESULT Compare (const T& other) const = 0; };
class EmployeeCompareByID : public Employee, public IComparable { public: Compare (const T& other) const { //Compare IDs and return result } };
class EmployeeCompareBySalary : public Employee, public IComparable { public: Compare (const T& other) const { //Compare Salaries and return result } };
typedef union { Employee employeeData; EmployeeCompareByID employeeCompareByID; EmployeeCompareBySalary employeeCompareBySalary; }EmployeeUnion;
//finally the main would do something like this: int main() { //first tree key is by ID Tree empTreeByID; //second tree key is by salary Tree empTreeBySalary;
EmployeeUnion emp; emp.employeeData.ID = 1; emp.employeeData.Salary = 1000.11; empTreeByID.Insert(emp.employeeCompareByID); empTreeBySalary.Insert(emp.employeeCompareBySlary); //the same emp is referenced in both trees. Each by it's relevant member in union}
but this approach fails because my Employee class has a constructor, copy constructor and operator overloading so defining a union on Employee is impossible.
Furthermore, this approach requires the Tree implementation to do a static_cast on the TYPE
template-argument to IComparable which seems fine to me.Another possible solution is to pass a function-pointer to the Tree constructor, with a pointer to the appropriate Compare function for that instance, but this seems to me an inelegant solution, and possibly quite messy and hard to debug later.
Googling on the limitations of using unions with classes, I found a post suggesting to solve a problem similar to mine using Conversion operator overloading but didn't expand much.
I'm sure this is a fairly common problem that has a common design solution, and I just don't know it.
Any thoughts or comments are appreciated
The actual problem in your code is that you try to place the comparision and the employee data structure to the same object. They should be different objects like this:
and then obviously you need to modify the Tree constructor: