forward在C ++标头

时间:2016-08-10 22:11:29

标签: c++ private encapsulation public

我为C API编写了一个C ++包装类。

我的包装器类有一个在原始API中使用的typedef结构的私有实例成员。我不想修改API头文件,但我也想隐藏原始API的所有痕迹,所以我不想在包装类的标题中包含原始的API头文件。

我可能忽略了一些非常简单的东西,但我找不到它。 PIMPL是一个选项,但我更愿意在重构整个代码库之前寻找替代方案。

wrapper.hpp

class myWrapper
{
public:
    myWrapper();

private:
    originalTypedef *original; // forward declaration needed for originalTypedef 
};

wrapper.cpp

#include "wrapper.hpp"
#include "originalAPI.h"

myWrapper::myWrapper()
{
    original = originalAPI_get();
}

Main.cpp的

#include "wrapper.hpp"

int main()
{
    myWrapper wrapper = new myWrapper();
}

3 个答案:

答案 0 :(得分:3)

我能够快速思考的选项:

  1. 您可以在myWrapper.h中重复C API中的typedef

    typedef struct the_original_struct_type originalTypedef;
    
  2. 在调用C API之前,您可以在void*myWrapperreinterpret_cast中使用originalTypedef*作为成员变量。

    class myWrapper
    {
       private:
          void* original;
    };
    

答案 1 :(得分:1)

一个奇特的解决方案是编写一个读取original_c_api.h的代码生成器,并输出一个文件original_c_api_types.h,它只包含结构定义,类型等,但不包含任何函数,以及一个包含原始文件original_c_api_functions.h的文件。函数声明。然后wrapper.h包含original_c_api_types.h,wrapper.cpp包含wrapper.h和original_c_api_functions.h。代码生成器应作为makefile中的目标运行。

当然,如果您有权修改最简单的原始C api文件。

答案 2 :(得分:0)

您正在寻找的是像pImpl模式 - 您提供了一个C ++ API,并且实现从客户端进行了模糊处理:

标头文件

// forward declare obfuscated implementation
// we can do this because we're only using a ptr
class Implementation;

class Wrapper
{
   public:
      Wrapper();
      ~Wrapper();
      void doSomething();

   private:
      Implementation * pImpl;
  };

.cpp文件

  #include "originalAPI.h"
  class Implementation
  {
     public:
      void doSomething()
      {
         OriginalAPI_DoSomething();
      }
   };

   Wrapper::Wrapper()
   {
     this->pImpl = new Implementation();
   }

   Wrapper::~Wrapper()
   {
      delete pImpl;
   }

   void Wrapper::doSomething()
   {
      pImpl->doSomething;
   }