<div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">On Mon, May 28, 2018 at 7:43 AM, Fcs <span dir="ltr"><<a href="mailto:ftpronk@engits.com" target="_blank">ftpronk@engits.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">Using VTK for one of our projects, we are encountering some memory leaks<br>
which, in time, cripple our system. So I'm trying to have a better<br>
understanding of the VTK pointers<br>
<<a href="https://blog.kitware.com/a-tour-of-vtk-pointer-classes/" rel="noreferrer" target="_blank">https://blog.kitware.com/a-<wbr>tour-of-vtk-pointer-classes/</a>> . <br>
<br>
It was my (erroneous..?) belief that the *vtkSmartPointer*s would destroy<br>
the object they were holding when getting out of scope. Carefully reading<br>
the kitware blog post linked hereinabove, and playing around with a test<br>
code (code sample below), I now understand that it is objects held by<br>
*vtkNew* that will be destroyed when out-of-scope, and that<br>
*vtkSmartPointer*s, on the contrary, will keep them alive as long as the<br>
reference count is non-zero. Is this correct? <br></blockquote><div><br></div><div>No, that is not correct. The vtkNew class instantiates a vtkObject derived instance and will decrement its reference count when it goes out of scope. You can still store what was created by vtkNew in a vtkSmartPointer, increasing the reference count to two, and keeping that object alive even when the containing vtkNew goes out of scope.</div><div><br></div><div>In its simplest form, if you don't use other smart pointer classes with it then vtkNew acts much like a stack allocated object, where the object created is automatically deleted when it goes out of scope. You must remember that all vtkObject derived classes are implicitly reference counted - it is built into the API. The smart pointer classes just take care of incremementing/decrementing the reference count. </div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">
<br>
Now, from a practical point of view: does this mean that I can, in a class,<br>
create an entire VTK pipeline with *vtkSmartPointer*s, and only store the<br>
latest object in a member variable to keep every object alive (So, in my<br>
code below, only bookkeep the object returned by applyFilters())? And that<br>
when I'm finished, I can call ->Delete() on that object to clean-up the<br>
entire pipeline? Is this a good practice? Until now, I was painstakingly<br>
storing every object created for the lifetime of a pipeline, and I would<br>
like to know if I can simplify my code..<br>
<br></blockquote><div>In my opinion you should aim to never call Delete, but to have a smart pointer contain the things needed. I think all pipeline API will increase the reference count, and so you only usually need to keep a reference to the pipeline objects you are going to keep around/use. The debug leaks code will help you verify you got it right.</div><div><br></div><div>I would add that we have found in bigger applications that a passing debug leaks is not always enough, ensuring objects are deleted when they are done with is more difficult but necessary, especially in graphical applications that might run for some time. My honest summary of using the smart pointers (in classes, local code, etc) is:</div><div><br></div><div>vtkNew - when you will instantiate the object, and want to keep a strong reference (you can't change what instance a vtkNew variable points to)</div><div><br></div><div>vtkSmartPointer - when you might create, or use an instance passed in, and ensure it stays around for when you want to make calls. Assigning a different instance to one will decrement the one it points to before switching it to point to the new instance and incrementing.</div><div><br></div><div>vtkWeakPointer - when you want to call API if something is still around, check for nullptr before using, will not affect reference count.</div><div><br></div><div>I think I wrote something similar back then. Whenever I see code like</div><div><br></div><div><div>vtkSmartPointer<vtkRenderer> renderer = vtkSmartPointer<vtkRenderer>::New();</div></div><div><br></div><div>I want to replace it with</div><div><br></div><div>vtkNew<vtkRenderer> renderer;</div><div><br></div><div>It does the exact same thing with no repetition, and is clearer. The examples require backwards compatibility with older VTK, and I don't think Bill liked calling .GetPointer()/.Get() on the vtkNew object. You no longer have to do that, but it is a more recent addition to the vtkNew API - it will implicitly return the pointer to the contained object as vtkSmartPointer does.</div><div><br></div><div>Hopefully this makes things a little clearer. At the end of the day all vtkObject derived classes (read most of the vtk* classes) are implicitly reference counted, the choice of vtkNew/vtkSmartPointer should be made depending upon how those instances will be used in your code - both will decrement the reference count by one when they go out of scope.</div><div><br></div><div>Marcus</div></div></div></div>