I would like to declare a pure abstract base class with a virtual destructor. I know three ways to do this, but I do not know which is best, or why.
My goal is to implement abstract base class interfaces in best-practice C++11 style, with optimal runtime performance. In particular, I would like to afford inlining/elimination of no-op destructors. I'd also like to eliminate warnings related to duplicate vtables, either by choosing an implementation that doesn't generate the duplicat vtables, or by making an informed decision to suppress the warnings.
Here are the three ways to implement an abstract base class that I know:
Option #1
/// A.h:
class A {
public:
virtual ~A() {}
virtual int f() = 0;
};
Option #2
/// A.h:
class A {
public:
virtual ~A();
virtual int f() = 0;
};
/// A.cpp:
A::~A() {}
Option #3
/// A.h:
class A {
public:
virtual ~A() = default;
virtual int f() = 0;
};
Are these my only options?
Which of #1, #2, #3, is considered best practice? If there are trade-offs (e.g. runtime vs. compile time performance) please describe them.
With option #1, will the inline destructor ever be inlined?
I understand that option #1 will put a vtable into every translation unit. Option #1 generates the -Wweak-vtables
warning in clang, and is covered by the "vague linkage" category in gcc[1]. Option #3 does not generate the clang warning -- does this mean that option #3 does not generate a vtable?
How exactly does option #3 differ from the other options?
Other questions have discussed similar issues with respect to clang's warnings, but I was unable to find a question that specifically addressed which option is considered best practice and why.
Aucun commentaire:
Enregistrer un commentaire