
On Tue, May 31, 2016 at 4:59 PM, Gavin Lambert <gavinl@compacsort.com> wrote:
On 1/06/2016 09:12, charleyb123 . wrote:
This is why I'm such a fan of CRTP (curiously-recurring-template-pattern), where it should work for this PIMPL design with no virtual and no overhead.
I've been quiet on this thread, but:
*- I like the PIMPL pattern very much *- I like your approach *- I want no overhead *- I vote CRTP *- CRTP also allows template-member-functions (requested by Chris, also desired by me) *- I'm generally disappointed with namespaces
This already uses CRTP, eg:
struct T : public pimpl<T>::shared {...};
Is there some other application of this that you actually meant instead?
//"IMPL" interface consistent with "std_impl<>" template<typename IMPL> struct std_pimpl { using P = typename IMPL::TYPE; IMPL* impl_; ... std_pimpl<IMPL>& clone(void) const { assert(impl_); return *new std_pimpl(IMPL::Clone(*impl_)); } ...standard pimpl interface forwarding to IMPL::... }; template<typename D, typename F> struct std_impl { using TYPE = F; F* impl_; const F& getImpl(void) const { assert(impl_); return *impl_; } D& clone(void) const { return D::Clone(static_cast<const D&>(*this)); } static D& Clone(const D& clone_from) { //..default implementation return *new D(clone_from); } ...standard impl interface... }; class Foo {}; struct FooImpl : public std_impl<FooImpl,Foo> { using BASE = std_impl<FooImpl,Foo>; //... static F& Clone(const Foo& clone_from) { // Override BASE::Clone() return *new D(clone_from.getImpl().cloneNew()); } }; using FooPimp = std_pimpl<FooImpl>; ------------ In short, what I like: *- some kind of "std_pimpl<>" provides a standardized interface, and "plumbing"/implementation. *- CRTP in the "std_impl<>" allows for a zero-cost compile-time implementation-override. *- If necessary, implementation can permit "std_pimpl<>" to be parameterized with merely a "Foo" declaration. --charley