Suppose I have a simple C++ class:
// MyCPPClass.hpp
class MyCPPClass {
std::uint8_t m_num1 = 0;
std::uint8_t m_num2 = 0;
std::string GetText() const;
}
and I want to use this in an Objective-C class:
// MyObjCClass.h
@interface MyObjCClass {
@public
MyCPPClass _cppObj;
}
What do I really gain from using PImpl idiom over just embedding it directly into the Obj-C class (as above), aside from having to write more code for the PImpl part ?
The downside is this C++ type MyCPPClass
is now in the header file MyObjCClass.h
, which other Objective-C classes that use MyObjCClass
will have to import. Importing a header is like putting it into the code, so these other Objective-C classes now have C++ in their code, and so will now have to be changed to Objective-C++ files or they won't compile. This is often not desirable, as these other files shouldn't need C++. Although this problem can be solved by declaring your instance variable not in the main class declaration in the header, but in the "extension" (declared like a category but with no name in the parentheses) or in the @implementation
, which are in the implementation file, so other classes don't have to import it.
Another problem with C++ classes as instance variables of Objective-C classes is that your C++ object can only be constructed using the default constructor (i.e. no constructor arguments), as there is no way to provide an initializer for an instance variable of an Objective-C class. So if you want to construct it with constructor arguments, you must use pimpl.