SO上有几个关于pimpl习惯用语的问题,但是我对它在实践中被利用的频率更加好奇。

我知道性能和封装之间需要权衡取舍,由于额外的重定向,还会带来一些调试烦恼。

这样一来,是否应该在每个类(class)或全有或全无的基础上采用这种方法?这是最佳做法还是个人喜好?

我意识到这有点主观,所以让我列出我的首要任务:

  • 代码清晰度
  • 代码可维护性
  • 性能

  • 我始终认为我有时需要将我的代码作为库公开,因此这也是一个考虑因素。

    编辑:任何其他完成同一件事的选择都是值得欢迎的建议。

    最佳答案

    我想说的是,您是按类(class)学习还是按全有或全无的方式进行学习,这取决于您为什么首先选择pimpl习惯用法。建立图书馆时,我的原因如下:

  • 想要隐藏实现以避免泄露信息(是的,这不是一个FOSS项目:)
  • 想要隐藏实现以减少客户端代码的依赖性。如果构建共享库(DLL),则无需重新编译应用程序即可更改pimpl类。
  • 希望减少使用该库编译类所花费的时间。
  • 想要解决 namespace 冲突(或类似问题)。

  • 这些原因都没有提示采用全有或全无的方法。在第一个例子中,您只放大了您想隐藏的内容,而在第二个例子中,对于您希望更改的类来说,这样做就足够了。同样出于第三个和第四个原因,隐藏非平凡成员反过来又需要额外的 header (例如,第三方库甚至是STL),这只会带来好处。

    无论如何,我的意思是,我通常不会找到像这样有用的东西:
    class Point {
      public:
        Point(double x, double y);
        Point(const Point& src);
        ~Point();
        Point& operator= (const Point& rhs);
    
        void setX(double x);
        void setY(double y);
        double getX() const;
        double getY() const;
    
      private:
        class PointImpl;
        PointImpl* pimpl;
    }
    

    在这种情况下,折衷方案开始对您造成打击,因为需要取消引用指针,并且无法内联方法。但是,如果仅对非平凡的类执行此操作,那么通常可以容忍轻微的开销而不会出现任何问题。

    关于c++ - 实践中的Pimpl成语,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/843389/

    10-11 18:28