1

I am using the SparseMatrix class of the library Eigen. To create one, I use:

typedef Eigen::SparseMatrix<float>  matrix;
matrix M (10,10);

How can I call the destructor of this object ?

SingerOfTheFall
  • 29,228
  • 8
  • 68
  • 105
Tarek
  • 1,060
  • 4
  • 17
  • 38
  • 3
    [Don't](http://stackoverflow.com/questions/8829548/can-i-get-a-fresh-start-in-c-without-failing-again). – R. Martinho Fernandes Jul 26 '12 at 10:34
  • @Griwes because I need to reinitialize the same sparse matrix several times in a loop. I hope that destructing the matrix every time by its destructor will lead to minimal memory leakage. – Tarek Jul 26 '12 at 10:34
  • Maybe you should define a clear() function for this - after explicitely calling the destructor your object isn't usable any more. (you should also take a look inside the class if you want to prevent memory leakage) – C. Stoll Jul 26 '12 at 10:38
  • @Tarek: It will lead to undefined behaviour. Whether or not that involves leakage is undefined. – Mike Seymour Jul 26 '12 at 10:38

5 Answers5

9

You don't need to. Your object is being created on the stack and will be automatically deleted when it goes out of scope.

SingerOfTheFall
  • 29,228
  • 8
  • 68
  • 105
  • 2
    To add to that, if you put the `matrix` variable declaration inside the loop, it will be destroyed each time the loop block exists, which will happen every time the loop repeats. So, the minimal memory usage you want will be there. – Matthew Walton Jul 26 '12 at 10:35
7

(...) because I need to reinitialize the same sparse matrix several times in a loop. I hope that destructing the matrix every time by its destructor will lead to minimal memory leakage.

The clear, obvious, safest, and probably most efficient solution is to just use the normal C++ semantics. "Reinitialization" is done with assignment.

typedef Eigen::SparseMatrix<float>  matrix;
matrix M (10,10);
M = matrix(12, 12);

Declare the matrix inside the loop body, and it will be properly initialized and destroyed at every loop iteration.

Oh, and assuming a non-buggy library, there is zero memory leakage in all these cases. Just don't toss news around and don't play with fire (like calling destructors directly).

R. Martinho Fernandes
  • 228,013
  • 71
  • 433
  • 510
  • 2
    If assignment isn't the most efficient, then something like `matrix(12,12).swap(M);` could be better in C++03 (or in C++11, for a class that isn't move-enabled yet). You'd have to check the docs for the class. Since it's a *sparse* matrix, you'd hope that an "empty" matrix is very quick to create and destroy, and so the overhead of `M = matrix(12,12);` is small. – Steve Jessop Jul 26 '12 at 10:43
2

You don't call the destructor directly; it will be invoked when this variable goes out of scope.

void myFunction()
{
    matrix A (10,10);
    ... some code
    {
        matrix B (10,10);
    } // destructor of B is called here.
    ... some code
}// destructor of A is called here.

This is the behavior of an auto variable as you have in your code. The other way to invoke a destructor is if you have dynamically allocated the object with new, and you destroy the object with delete:

void myFunction()
{
    matrix* A = new matrix(10,10);
    ... some code
    {
        matrix* B = new matrix(10,10);
        delete B;// destructor of B is called
    }
    ... some code
    delete A;// destructor of A is called
}
Bakery
  • 406
  • 1
  • 5
  • 10
tenfour
  • 36,141
  • 15
  • 83
  • 142
2

There is only one case that I know of where you need to call a destructor explicitly: When using placement new, e.g.

class Foo { /* lots of stuff here */ };

char foo[sizeof(Foo)];
new (&foo[0]) Foo();
/* ... */
reinterpret_cast<Foo *>(&foo[0])->~Foo();
MadScientist
  • 3,390
  • 15
  • 19
0

While I'm really not sure why you want to do this, it is quite easy:

M.~SparseMatrix();

In general, you can explicitly invoke the destructor on any class, just by calling it like any other function. Templated classes are no different.

Jack Aidley
  • 19,439
  • 7
  • 43
  • 70