0

I've got some problems whith the overload of operator=. My code is

#include <stdlib.h>
#include <iostream>


const std::size_t DIM = 10;


template <typename T>

class rowvec
  {
    private:
      T* m_pnt;
      std::size_t m_dim;

    public:
      rowvec();
      rowvec(std::size_t);
      ~rowvec();

      rowvec<T>& operator=(const rowvec<T>& x);

      T* pnt();
  };


template <typename T>
rowvec<T>::rowvec()
  {
    m_dim = DIM;
    m_pnt = (T*) calloc (DIM ,sizeof(T));
  }


template <typename T>
rowvec<T>::rowvec(std::size_t n)
  {
    m_dim = n;
    m_pnt = (T*) calloc(m_dim,sizeof(T));
  }


template <typename T>
rowvec<T>::~rowvec()
      {free(m_pnt);}


template <typename T>
rowvec<T>& rowvec<T>::operator=(const rowvec<T> &x)
  {
    std::cout << "hello" << std::endl;
    if (this != &x)
      {
        free (m_pnt);
        this->m_dim=x.m_dim;
        m_pnt = (T*) calloc (m_dim,sizeof(T));
        for (int i=0; i!=m_dim; i++)
          *(m_pnt+i)=*(x.m_pnt+i);
      }
    return *this;
  }


template <typename T>
T* rowvec<T>::pnt()
  {return m_pnt;}  




int main()
  {
    rowvec<int> k(3);

    rowvec<int> c=k;

    std::cout << "ok" << std::endl;

    return 0;
  } 

There are no compiling error, but when I run the result is:

ok
*** Error in `./blog': double free or corruption (fasttop): 0x0000000001a5e010 ***

If I change code in this way:

int main()
  {
    rowvec<int> k(3);

    rowvec<int> c;

    c=k;

    std::cout << "ok" << std::endl;

    return 0;
  }

everything is ok (output is)

hello
hello
ok

Is there a way to allow a declaretion like "rowvec c=k;" ?

  • u need a copy constructor –  Aug 08 '14 at 13:43
  • 5
    Related: [What is the rule of three?](http://stackoverflow.com/questions/4172722/what-is-the-rule-of-three) – πάντα ῥεῖ Aug 08 '14 at 13:46
  • Possible duplicate of http://stackoverflow.com/questions/14063791/double-free-or-corruption-but-why – eerorika Aug 08 '14 at 13:49
  • Use a vector and you don't need to add any copy constructor or assignment operator. – Neil Kirk Aug 08 '14 at 14:42
  • Your class, even if you fixed the allocation errors, will blow up as soon as you try a `rowvec`. The reason is that you're using `calloc`, and `calloc` does not construct objects. In general, you're using `C` constructs in a C++ program, and those C constructs do not work with non-POD types. – PaulMcKenzie Aug 08 '14 at 14:48

1 Answers1

4

Even though there's a = in it, rowvec<int> c=k; is copy-initialization and uses the copy constructor rather than the copy assignment operator.

Since your class doesn't define one, the default one which simply performs memberwise copy is used. That will only copy the pointer, which later causes the double free since both c and k's destructors will call free() on the same pointer.

Give your class a proper copy constructor (making a deep copy) and the double delete should go away.

Also, you are using C++. Don't use calloc/free. Use new and delete.

T.C.
  • 133,968
  • 17
  • 288
  • 421