Implementing a virtual destructor in C++
c++, virtual-destructor
Solution
First off, why do you think that the destructor should be `virtual`? Are you using polymorphism?
Second, you are using `delete` incorrectly for your array.
Since you used:
data = new T[length];
You must use the array syntax:
delete [] data;
Third, you need to put the namespace in front of all of your class function definitions:
template <class T>
Vector<T>::~Vector()
{
delete [] data;
}
And just for your information, you declare the destructor like so...
virtual ~Vector(void);
As I mentioned, `virtual` is unnecessary unless you are using this class as a base or derived class in a polymorphic manner. For more information on when you need to use `virtual` destructors, look at the answer to this question.
In addition, the `void` in the parameters is also unnecessary. This used to be required in old C standard, but it is not in C++.
You should be able to declare it like so:
~Vector();
If you define `AssociativeArray<P,Q>` with a has-a relationship to `Vector<T>`, then you can simply make the class contain a `Vector<Pair<P,Q> >`. Declaring `virtual` methods in this case, are not needed, but can still be used--with some extra overhead.
If you define `AssociativeArray<P,Q>` with a is-a relationship to `Vector<Pair<P,Q> >`, then you should define some `virtual` methods in `Vector<T>`, including a `virtual` destructor.
The use of `virtual` methods only matters when using objects polymorphically through pointers and references. See this page.
AssociativeArray<String,Int>* myDerivedMap = new AssociativeArray<String,Int>();
delete myDerivedMap; //NO virtual methods necessary here. using a pointer to derived class
Vector<Pair<String,Int> >* myBaseMap = new AssociativeArray<String,Int>();
delete myBaseMap; //virtual methods ARE necessary here. using a pointer to base class
Problem
I'm starting to learn c++ but I'm stuck in the destructor. We need to implement a vector and this is what I have so far. ``` #include<string.h> #include<cassert> #include<iostream> using namespace std; template<class T> class Vector { template<class U> friend ostream& operator<<(ostream&, const Vector<U>&); private: T* data; unsigned len; unsigned capacity; public: Vector(unsigned = 10); Vector(const Vector<T>&); virtual ~Vector(void); Vector<T>& operator =(const Vector<T>&); bool operator==(const Vector<T>&); T& operator[](unsigned); }; //PROBLEM! template <class T> ~ Vector() { delete data; } template<class T> Vector<T>::Vector(unsigned int _capacity) { capacity = _capacity; len = _capacity; data = new T[_capacity]; } template<class T> Vector<T>::Vector(const Vector<T> & v) { len = v.len; capacity = v.capacity; data = new T[len]; for (unsigned int i = 0; i < len; i++) data[i] = v.data[i]; } template<class T> Vector<T> & Vector<T>::operator = (const Vector<T> & v) { delete[ ] data; len = v.len; capacity = v.capacity; data = new T [len]; for (unsigned int i = 0; i < len; i++) data[i] = v.data[i]; return *this; } template<class T> bool Vector<T>::operator == (const Vector<T> & v) { bool check = true; check &= (len == v.len); if (!check) return false; check &= (capacity == v.capacity); if (!check) return false; for (unsigned int i = 0; i < len; i++) { check &= (data[i] == v.data[i]); if (!check) return false; } return true; } template<class T> T& Vector<T>::operator[](unsigned int index) { return data[index]; } ``` The interface is given and I need to implement it. But this is so different from C and Java, that I'm a bit lost. In the second exercise we need to implement something like this using a) the previous Vector implementation as derived class and b) the Vector as composition class, so maybe we will use the virtual destructor in one of the approaches? ``` void testAssociativeArray() { AssociativeArray<String, int> table; table["abc"] = 15; table["jkl"] = 12; table["xyz"] = 85; assert(table["jkl"], 12); } template<class P, class Q> class Pair { P p; Q q; public: Pair(const P& _p = P(), const Q& _q = Q()): p(_p), q(_q) {} P& objectP() {return p;} Q& objectQ() {return q;} }; ```