class MyClassPrivate
{
//My members.
};
//and then
class MyClass {
private:
MyClassPrivate* const d;
};
What is the reason of using this 'pattern'? How it's correctly called?
This is called "Pointer to implementation" or "pimpl". See http://en.wikibooks.org/wiki/C++_Programming/Idioms#Pointer_To_Implementation_.28pImpl.29
When you use this pattern you would forward declare the implementation class, and declare the body elsewhere, i.e.:
// header
class MyClassPrivate;
class MyClass {
public:
MyClass();
~MyClass();
private:
MyClassPrivate* const d;
};
// cpp
class MyClassPrivate {
};
MyClass::MyClass() : d(new MyClassPrivate) {}
MyClass::~MyClass() { delete d; }
The advantage of doing this is that the implementation of MyClass is not exposed to other users of MyClass. If the implementation changes, the other users of MyClass does not need to be recompiled. Any header files that has to be included for members also need not be exposed, which improves compilation time.
The most usage is Pimlp idiom.
Why should the “PIMPL” idiom be used?
Pimpl idiom
The Pimpl
The Pimpl idiom describes a way for making your header files
impervious to change. You often hear advices like "Avoid change your
public interface!" So you can modify your private interface, but how
can you avoid recompilation when your header file defines the private
methods. This is what the Pimpl does – Reduce compilation damages when
your private interface changes[3].
From Here:
Benefits:
Changing private member variables of a class does not require recompiling classes that depend on it, thus make times are faster, and the FragileBinaryInterfaceProblem is reduced.
The header file does not need to #include classes that are used 'by value' in private member variables, thus compile times are faster.
This is sorta like the way SmallTalk automatically handles classes... more pure encapsulation.
Drawbacks:
More work for the implementer.
Doesn't work for 'protected' members where access by subclasses is required.
Somewhat harder to read code, since some information is no longer in the header file.
Run-time performance is slightly compromised due to the pointer indirection, especially if function calls are virtual (branch prediction for indirect branches is generally poor).
How to do it:
Put all the private member variables into a struct.
Put the struct definition in the .cpp file.
In the header file, put only the ForwardDeclaration of the struct.
In the class definition, declare a (smart) pointer to the struct as the only private member variable.
The constructors for the class need to create the struct.
The destructor of the class needs to destroy the struct (possibly implicitly due to use of a smart pointer).
The assignment operator and CopyConstructor need to copy the struct appropriately or else be disabled.
You can use this for the PIMPL idiom, when you want to separate interface from iplementation.
Many design patterns use a "pointer" to a private attribute as well, such as the Strategy Pattern. This patterns allows you to select a different algorithm at run-time.
Also, if you make the manipulation of your data adhere to the same interface, you can encapsulate the data in a Private Class, make this class a part of a hierarchy and switch between different data implementations during run time (or compile time for that matter :)).
A good example of this is a geometrical class that holds data on polygons. Each Polygon provides access to the points, you can also delete the Polygon edge and do various other topological operations. If you provide an abstract base class for the Polygon class with the methods such as deletePoint, addPoint, swapEdge, you can test different Polygon implementations.
You may define a polygon as a list of Point types directly, and store the points in different contaienrs (list or vector). The Polygon class may be defined via indirect addressing, where the polygon is actually a list of IDs to the list of points (I am talking about lists in the general sense). This way, you can test different algorithms of the PolygonGeometry class and see how they work with differtn Polygon implementations.
There is a design principle behind this: Prefer Composition to Inheritance. Whenever you are using Composition and you are relying on the type to be deterimined at run-time, you will have a private attribute pointer.
Related
First things first: I know thats it's quite probable that my question is based on a general missunderstanding, but I hope I can make my point clear to you.
I know that when putting code into diffrent files in C++ we have do create a .h (for Definitions) and a .cpp (for implementations).
When writing a class-library for example I have to put a definitioj of both, private and public members in the header. But what to do if - for some reason - I want to hide the private things from the user?
Thanks!
You use the Pimpl idiom. Pimpl stands for "pointer to implementation". Basically, you don't store the implementation details in the class. Instead you store an opaque pointer to implementation as such:
class MyClass
{
public:
//public functions here
private:
class Impl; //no definition, opaque
Impl* pimpl;
};
And then you go on to define your MyClass::Impl class in the .cpp file only, because only the function definitions need it.
The PIMPL idiom has the additional benefit that as long as the interface of the class does not change, any changes made to the implementation do not require the recompilation of class clients.
You can't. This is one of the drawbacks of C++: things marked private are still part of the class declaration and so will be present in the header.
If you really want to hide the functionality, then using the pImpl Idiom can help. Personally though I prefer to live with the drawback as using the idiom can cause other problems such as your class no longer being trivially copyable.
See Why should the "PIMPL" idiom be used?
Suppose I have class like this (simplified):
class Foo_p;
class Foo
{
private:
Foo_p *p;
public:
Foo();
/* methods, etc... */
};
This class is a part of an API.
The Foo_p is all the private parts of the class, which are not
declared in the class Foo itself as usual, but rather in a separate forward-declared class that is only used by the underlying implementation not visible on the outside.
I've seen this pattern used in a couple of projects, is there a name for it?
Also, how do I use it properly (e.g. exception safety, etc.)? Where should the actual implementation go? In class Foo, as usual, only using Foo_p for storage of data, or in the Foo_p class with Foo being just a wrapper?
That is the pimpl idiom
See
Handle/Body Idiom - close cousin and the seminal idea for pimpl EDIT Found an online copy of this original James Coplien talk
GotW #100: Compilation Firewalls (Difficulty: 6/10)
GotW #101: Compilation Firewalls, Part 2 (Difficulty: 8/10) for the most recent on this
This is known is PIMPL. private/pointer-to-private implementation. The class, Foo_p, your class would have been is implemented privately and accessed through a pointer to it so that rather than displaying the true class to clients, they only get to see the public interface you chose to expose. It essentially abstracts away from the header the vestiges of implementation detail present in the protected and private members.
I've found it unwieldy in VC++- it breaks code completion. It is useful if you are very sure of your implementation and don't want the private and protected members on display in the header.
I put the actual implementation of class Foo_p in the cpp file for class Foo, although this may have been the cause of the code-completion breaking, at least I don't have to run the risk of the class being reused by inclusion of its header.
It's a d-pointer which is a type of opaque-pointer. Similar to the PIMPL idiom.
One type of opaque pointer commonly used in C++ class declarations is
the d-pointer. The d-pointer is the only private data member of the
class and points to an instance of a struct. Named by Arnt Gulbrandsen
of Trolltech, this method allows class declarations to omit private
data members, except for the d-pointer itself.[6] The result is that
more of the class' implementation is hidden from view, that adding new
data members to the private struct does not affect binary
compatibility, and that the header file containing the class
declaration only has to #include those other files that are needed for
the class interface, rather than for its implementation. As a side
benefit, compiles are faster because the header file changes less
often. The d-pointer is heavily used in the Qt and KDE libraries.
https://en.wikipedia.org/wiki/Opaque_pointer#C.2B.2B
I'm implementing several classes using the pimpl idiom and am coming across some design issues.
Firstly, I've always seen pimpl done like this
class Object
{
public:
Visible();
~Visible();
.. etc ..
private:
class ObjectImpl *_pimpl;
};
I have several classes which use this approach and my problem is that several of these classes need access to each others implementation details but the _pimpl pointer is delcared private.
Can anyone see the downside of declaring the _pimpl public. Obviously, if it's public then someone may accidentally (or deliberately) reassign it. (I'm ignoring the fact that "private" could be #defined as "public" and grant access anyway. If you do this then you deserve what you get).
I appreciate that my design may be flawed and would welcome any comments along those lines also.
I'm really loathe to use friends and am not sure they'll even help as you can't forward declare the Object::ObjectImpl without fully defining Object.
i.e.
...
private:
class ObjectImpl *_pimpl;
friend class OtherObject::OtherObjectImpl; // this needs a fully qualified OtherObject
};
Thx
Mark.
* UPDATE - More detail **
I have two classes, one called Command, the other called Results. I have methods on Command which return a vector of Results.
Both Command and Results use the pimpl idiom. I want the interface to Results to be as small as possible.
class Command
{
public:
void getResults( std::vector< Results > & results );
void prepareResults( std::vector< Results > & results );
private:
class CommandImpl *_pimpl;
};
class Results
{
public:
class ResultsImpl;
Results( ResultsImpl * pimpl ) :
_pimpl( impl )
{
}
private
ResultsImpl *_pimpl;
};
Now in Command::getResults(). I inject the ResultsImpl into the Results. in Command::prepareResults() I need access to the ResultsImpl.
M.
I doubt there is a good reason to make the implementation public: you can always expose the implementation's functionality using public methods:
class Object
{
public:
Object();
~Object();
int GetImplementationDetail();
private:
std::unique_ptr< ObjectImpl > _pimpl;
};
int Object::GetImplementationDetail()
{
return pimpl->GetImplementationDetail();
}
Apart from that a class should be responsible for one thing, one thing only, and should have the bare minimum of dependencies to other classes; if you think other classes should be able to access your Object's pimpl then your design is likely flawed.
edit following the author's update: although your example is still rather vague (or at least I cannot tell the full intent of it), you seem to be misinterpreting the idiom and now try to apply it to a case where it is not usefull. As others pointed out, the 'P' stands for private. Your results class doesn't have much private implementation since all of it is public. So either try to use what I mention above and do not 'inject' anything, or just get rid of the pimpl all together and use just the Result class. If your Result's class interface should be so small that it's nothing but a pointer to another class it doesn't seem to be of much use in this case.
Why exactly do your classes depend on details of each other? You may re-think your design. Classes should depend on abstractions.
If you really deem your design proper, nothing stops you from providing a "source-file-private" header, like:
include/
foo.h
src/
foo.impl.h
foo.c
bar.c
and then #include foo.impl.h in both foo.c and bar.c
foo.c:
#include "foo.impl.h"
...
bar.c:
#include "foo.impl.h"
...
But again: Generally,
Dependency Inversion Principle:
A. High Level Modules should not depend upon low level modules. Both should depend upon abstractions.
B. Abstractions should not depend upon details. Details should depend upon abstractions.
Also make very sure to check out SOLID and GRASP, especially the point about loose coupling.
It is unnecessary to qualify the friend thusly.
If you just use friend class OtherObject, then the OtherObject class may access the necessary internals.
Personally my Pimpl are just a struct (bundle of data) and I leave the methods to operate on it in the original class.
Making the the data member _pimple public won't buy you anything as long as those other classes do not see the definition of its type ObjectImpl - which is the very thing Pimple set out to prevent.
What you can do instead is to add a private interface to your Object class which will allow befriended classes to do whatever they need to do with an Object.
Of course, the common disclaimers about friend being a tool that should be used as rarely as possible all apply.
I just noticed a new term pimpl idiom, what's the difference between this idiom with Bridge design pattern? I am confused about that.
I also noticed the pimpl idiom is always used for swap function, what's that? Could anybody give me an example?
PIMPL is a way of hiding the implementation, primarily to break compilation dependencies.
The Bridge pattern, on the other hand, is a way of supporting multiple implementations.
swap is a standard C++ function for exchanging the values of two objects. If you swap the pointer to the implementation for a different implementation, you are essentially changing the mechanism of the class at runtime.
But in its basic and common form, a class using PIMPL points to a single implementation, so there is no abstract class with distinct subclasses — just one class, forward declared, and compiled elsewhere. Changing the implementation class does not require any recompilation of sources that include the main header.
For example, say you have a lot of private member functions, private enums, and private data. And these private "bits" change fairly frequently as the class is developed and maintained. If the #include dependencies are such that touching this header file causes a large number of sources to be recompiled, you have a good candidate for PIMPL.
So the Bridge pattern is about object-oriented design, while the PIMPL idiom is about physical design of files.
(For more on physical design, I recommend the book Large-Scale C++ Software Design by John Lakos.)
I have used pointer impl to hide implementation details from public interface/include file
Basically interface look like this:
struct Interface {
private:
class Impl;
Impl *pImpl;
};
Then somewhere in inside Interface::Impl is defined and implemented, but details not exposed.
as far as swap, this is the first time I hear it. Can you elaborate on it?
Pimpl: In short the pimpl pattern is really good for hiding the private implementation. If you wanted to expose your header files for clients that needed to build against your public interface but you didn't want to expose your private implementation details you could use the pimpl pattern to hide the details. You would do this for a few reasons but mainly your header file would not have to change when you change your private implementation details change which otherwise would force your clients to have to recompile. In this way you decouple along with hide your private implementation details. Usually you should hold the impl pointer in a RAII container like a unqiue pointer to make sure it is freed upon destruction.
Pimpl
// my_class.h
class my_class {
public:
// public here
private:
class impl; //forward declare impl
unique_ptr<impl> pimpl; // private implementation pointer
};
// my_class.cpp
class my_class::impl { // defined privately here
// ... all private data and functions: all of these
// can now change without recompiling callers ...
};
my_class::my_class(): pimpl( new impl )
{
// ... set impl values ...
my_class& operator=(my_class other);
friend void swap (my_class& lhs, myclass& rhs); // used for assignment
}
Swap probably came up because when you are doing an assignment operator for this class and implementing your own swap routine to assign the members you need to be aware of assigning this pointer as well
my_class& my_class::operator=(my_class other)
{
swap(*this,other);
return *this;
}
void swap ( my_class& lhs, myclass& rhs )
{
using std::swap // now use default swap if override doesn't exist
// call swap for other members
// swap (lhs.data,rhs.data);
// call swap on unique_ptr
lhs.pimpl.swap(rhs.pimpl); // doesn't throw exceptions
}
Bridge is a totally separate pattern that is used to bridge items together. The similarity between the patterns would be that you may have a process method in your class that hides the actual call since it will delegate this call to the contained object that will handle the actual method call. In other words if you had a request interface base class that contained a request implementor base class pointer. Therefore, at run time you could "bridge" the systems by initializing the bridge with a specific request implementor type but someone calling the bridge would just call the process request method which would delegate the call to the specific derived implementor request method at run time. There are several sources on google with nice diagrams that can explain this more clearly as well.
There is currently a Boost library under review that implements the Pimpl pattern. I've cobbled together a few basic examples using the proposed Boost Pimpl implementation if anyone wants a jump on using this code internally:
https://github.com/sean-/Boost.Examples/tree/a148be39abcb21428857aa50495f8c352600741e/pimpl
UPDATE: The above link has been updated to point to the archived version. It doesn't seem likely that Boost.Pimpl will be accepted in to boost at this point in time in favor of std::unique_ptr<> as a viable replacement (albeit less complete than Boost.Pimpl for some less common usecases).
If you have access to C++11, you are probably better off using std::unique_ptr<> as a PIMPL implementation:
class MyClass {
public:
// ...
private:
class Impl;
std::unique_ptr<Impl> impl_;
};
You can see a full example using std::unique_ptr<> in my C++11 reentrant class locking strategy question.
Using std::unique_ptr<>'s swap() method, it becomes convenient and very practical for C++11's move semantics to move the guts of an object from one owner to another. For example, suppose MyClass exports a swap() implementation that just forwards to std::unique_ptr<>'s swap:
void MyClass::swap(MyClass *c) { impl_.swap(c); }
MyClass c1, c2;
c1.swap(c2);
This is now an exception safe way of transferring c2's contents to c1. Another great reason to use a the PIMPL idiom is to preserve/maintain a stable ABI.
Well, here is PIMPL idiom: http://en.wikipedia.org/wiki/Opaque_pointer It is pretty clear what it does.
And Bridge Pattern is more involved - it does not just hold data. http://en.wikipedia.org/wiki/Bridge_pattern#C.2B.2B
I was wondering what would make a programmer to choose either Pimpl idiom or pure virtual class and inheritance.
I understand that pimpl idiom comes with one explicit extra indirection for each public method and the object creation overhead.
The Pure virtual class in the other hand comes with implicit indirection(vtable) for the inheriting implementation and I understand that no object creation overhead.
EDIT: But you'd need a factory if you create the object from the outside
What makes the pure virtual class less desirable than the pimpl idiom?
When writing a C++ class, it's appropriate to think about whether it's going to be
A Value Type
Copy by value, identity is never important. It's appropriate for it to be a key in a std::map. Example, a "string" class, or a "date" class, or a "complex number" class. To "copy" instances of such a class makes sense.
An Entity type
Identity is important. Always passed by reference, never by "value". Often, doesn't make sense to "copy" instances of the class at all. When it does make sense, a polymorphic "Clone" method is usually more appropriate. Examples: A Socket class, a Database class, a "policy" class, anything that would be a "closure" in a functional language.
Both pImpl and pure abstract base class are techniques to reduce compile time dependencies.
However, I only ever use pImpl to implement Value types (type 1), and only sometimes when I really want to minimize coupling and compile-time dependencies. Often, it's not worth the bother. As you rightly point out, there's more syntactic overhead because you have to write forwarding methods for all of the public methods. For type 2 classes, I always use a pure abstract base class with associated factory method(s).
Pointer to implementation is usually about hiding structural implementation details. Interfaces are about instancing different implementations. They really serve two different purposes.
The pimpl idiom helps you reduce build dependencies and times especially in large applications, and minimizes header exposure of the implementation details of your class to one compilation unit. The users of your class should not even need to be aware of the existence of a pimple (except as a cryptic pointer to which they are not privy!).
Abstract classes (pure virtuals) is something of which your clients must be aware: if you try to use them to reduce coupling and circular references, you need to add some way of allowing them to create your objects (e.g. through factory methods or classes, dependency injection or other mechanisms).
I was searching an answer for the same question.
After reading some articles and some practice I prefer using "Pure virtual class interfaces".
They are more straight forward (this is a subjective opinion). Pimpl idiom makes me feel I'm writing code "for the compiler", not for the "next developer" that will read my code.
Some testing frameworks have direct support for Mocking pure virtual classes
It's true that you need a factory to be accessible from the outside.
But if you want to leverage polymorphism: that's also "pro", not a "con". ...and a simple factory method does not really hurts so much
The only drawback (I'm trying to investigate on this) is that pimpl idiom could be faster
when the proxy-calls are inlined, while inheriting necessarily need an extra access to the object VTABLE at runtime
the memory footprint the pimpl public-proxy-class is smaller (you can do easily optimizations for faster swaps and other similar optimizations)
I hate pimples! They do the class ugly and not readable. All methods are redirected to pimple. You never see in headers, what functionalities has the class, so you can not refactor it (e. g. simply change the visibility of a method). The class feels like "pregnant". I think using iterfaces is better and really enough to hide the implementation from the client. You can event let one class implement several interfaces to hold them thin. One should prefer interfaces!
Note: You do not necessary need the factory class. Relevant is that the class clients communicate with it's instances via the appropriate interface.
The hiding of private methods I find as a strange paranoia and do not see reason for this since we hav interfaces.
There's a very real problem with shared libraries that the pimpl idiom circumvents neatly that pure virtuals can't: you cannot safely modify/remove data members of a class without forcing users of the class to recompile their code. That may be acceptable under some circumstances, but not e.g. for system libraries.
To explain the problem in detail, consider the following code in your shared library/header:
// header
struct A
{
public:
A();
// more public interface, some of which uses the int below
private:
int a;
};
// library
A::A()
: a(0)
{}
The compiler emits code in the shared library that calculates the address of the integer to be initialized to be a certain offset (probably zero in this case, because it's the only member) from the pointer to the A object it knows to be this.
On the user side of the code, a new A will first allocate sizeof(A) bytes of memory, then hand a pointer to that memory to the A::A() constructor as this.
If in a later revision of your library you decide to drop the integer, make it larger, smaller, or add members, there'll be a mismatch between the amount of memory user's code allocates, and the offsets the constructor code expects. The likely result is a crash, if you're lucky - if you're less lucky, your software behaves oddly.
By pimpl'ing, you can safely add and remove data members to the inner class, as the memory allocation and constructor call happen in the shared library:
// header
struct A
{
public:
A();
// more public interface, all of which delegates to the impl
private:
void * impl;
};
// library
A::A()
: impl(new A_impl())
{}
All you need to do now is keep your public interface free of data members other than the pointer to the implementation object, and you're safe from this class of errors.
Edit: I should maybe add that the only reason I'm talking about the constructor here is that I didn't want to provide more code - the same argumentation applies to all functions that access data members.
We must not forget that inheritance is a stronger, closer coupling than delegation. I would also take into account all the issues raised in the answers given when deciding what design idioms to employ in solving a particular problem.
Although broadly covered in the other answers maybe I can be a bit more explicit about one benefit of pimpl over virtual base classes:
A pimpl approach is transparent from the user view point, meaning you can e.g. create objects of the class on the stack and use them directly in containers. If you try to hide the implementation using an abstract virtual base class, you will need to return a shared pointer to the base class from a factory, complicating it's use. Consider the following equivalent client code:
// Pimpl
Object pi_obj(10);
std::cout << pi_obj.SomeFun1();
std::vector<Object> objs;
objs.emplace_back(3);
objs.emplace_back(4);
objs.emplace_back(5);
for (auto& o : objs)
std::cout << o.SomeFun1();
// Abstract Base Class
auto abc_obj = ObjectABC::CreateObject(20);
std::cout << abc_obj->SomeFun1();
std::vector<std::shared_ptr<ObjectABC>> objs2;
objs2.push_back(ObjectABC::CreateObject(13));
objs2.push_back(ObjectABC::CreateObject(14));
objs2.push_back(ObjectABC::CreateObject(15));
for (auto& o : objs2)
std::cout << o->SomeFun1();
In my understanding these two things serve completely different purposes. The purpose of the pimple idiom is basically give you a handle to your implementation so you can do things like fast swaps for a sort.
The purpose of virtual classes is more along the line of allowing polymorphism, i.e. you have a unknown pointer to an object of a derived type and when you call function x you always get the right function for whatever class the base pointer actually points to.
Apples and oranges really.
The most annoying problem about the pimpl idiom is it makes it extremely hard to maintain and analyse existing code. So using pimpl you pay with developer time and frustration only to "reduce build dependencies and times and minimize header exposure of the implementation details". Decide yourself, if it is really worth it.
Especially "build times" is a problem you can solve by better hardware or using tools like Incredibuild ( www.incredibuild.com, also already included in Visual Studio 2017 ), thus not affecting your software design. Software design should be generally independent of the way the software is built.