I try to make use of Cocoa Bindings whenever possible but I had never used the displayPatternValue binding. According to Apple this binding is often used to display the size of a selection compared to the size of the entire data set. It can essentially be used like NSString’s stringWithFormat: method to combine multiple bound values into a single string. It is one of the bindings available for a NSTableColumn and that is where I was using it when I discovered this leak. It took me most of the morning to isolate the cause in a small example application I could provide to Apple.
While I can’t tell you what caused me to discover this leak I can give you more detail on its behavior. You could populate and unpopulate a NSTableView and never encounter this leak and that is what makes it a bit odd in my view. Depending on how you remove data from the table you many not leak memory. The assumption is that you have a NSTableColumn displayPatternValue binding set to one or more properties of an object in a NSArrayController. Several rows of data are added to your table and the binding displays information using the format you specified. A row, we’ll say the first row, is removed. If you are watching the instances of your data object in ObjectAlloc you will see one of them disappear from the list. It has been successfully deallocated. Now the row that had been the second row is the first row of the table. If this row is removed you will see that it is not successfully deallocated but it is removed from the table’s display.
The memory leak will always occur when trying to remove a row at an index that has previously been removed. This means that the only way to clear the table without encountering the leak is to always remove the last row of the table. As to why this is the case I’m afraid I don’t know. I’ve reported it to Apple and provided a small example application that illustrates it reliably. I don’t imagine too many people are using this binding in a NSTableColumn so it isn’t likely a big problem, but it is something to keep an eye out for.


