Hacker News new | ask | show | jobs
by beached_whale 2723 days ago
One hickup is that with unique_ptr you now have a rule of 5 thing, you need to declare a destructor which means you need to declar the copy/move constructor and assignment too. Not usually a big deal, but is extra code.
2 comments

This is why the rule of zero advocates are getting louder.
Rule of zero classes are awesome. It forces a separation of concerns too, generally a good thing :), as the handling of special things is done by a class that does that(e.g. unique_ptr, vector...) and your class describes only what is in it and how to interact with it. But no more detailed than that.
Totally agree. Recently used unique_ptr with a custom deleter is to consume a C library that requires heap allocation with its own alloc/free functions. No destructor!
I have a class, boringly called value_ptr, that is like unique ptr but if the underlying value supports copy will do a copy constructor and assignment too. Then I don’t have to make one is the classes like this too where I am using a ptr for other reasons. It also has const correctness
This is true. Fortunately, these do not need to be inlined, which can still free client code of compile time overhead.

It's a tradeoff between compile time and complexity.

Another option is something like pimp but keep the state in the public class. Now you get stack allocation but the private part is still private and firewalling all the other headers and details not needed for the public interface. Just pass this to the private methods.

Edit: Something like https://github.com/beached/stack_pimpl

I don’t get the example, can you explain? What does this buy that you don’t have by simply putting the content of private.cpp into stack_pimpl.cpp? The data members are already in stack_pimpl.h (so nothing private or hidden about that) and the methods are already declared in both and implmented in both cpp files, so what are you buying over just putting the declarations in one header and implementation in one source and not delegating from one to the other?

Was it just a oversimplistic example and the benefit is actually if priv_t has a bunch of internal methods that you want to keep out of the stack_pimpl.h interface?

So PIMPL is a compile firewall to keep the compile times and changes in one section from cascading and imacting your whole project with a recompile. It is not going to keep things secret as I can look at the binary and pick it apart.

So with that, it keeps the data(state) in the public facing class. This allows one to keep everythign stack allocated instead of defaulting to the heap. So for something this is created en mass(A vector of them) or created and destroyed often, this is a runtime win.

What it does is have a proxy that mirrors the public interface that is passed the this pointer. That proxy a friend class. Because only the proxies header(in this case private.h which I should probably rename firewalled.h) has static members that mirror the public members on the public class that limits the interaction between your classes users and it's implementation, as it is also with unique_ptr(or whatever pointer/heap way) based PIMPL designs. So changes in private.cpp that does all the work are only reflected in that one file. This file also brings in the heavy templates or algorithm code that may have large compile times.

So, you mean that changing private.h only requires private.cpp and stack_pimpl.cpp to be recompiled, whereas changing stack_pimpl.h would require anything that uses it to be recompiled too? Ok, that makes sense.

However...

> So with taht, it keeps the data(stat) in the public facing class. This allows one to keep everything stack allocated instaed of defaulting to the heap.

Ok, having it on the stack is useful, but in my personal experience, the state is exactly the thing that I find changes the most (typically together with the code), so by keeping the state in the public header, changes will still require recompiliation of anything that includes the header, so I’m not sure this really wins much (at least, based on my own C++ projects).

Never mind, I was thinking wrong and neglected the ABI stability
Please ignore the question I just posted regarding this topic. I only saw this comment after posting mine own.