C++中接口与实现分离的技术

在用C++写要导出类的库时,我们经常只想暴露接口,而隐藏类的实现细节。也就是说我们提供的头文件里只提供要暴露的公共成员函数的声明,类的其他所有信息都不会在这个头文件里面显示出来。这个时候就要用到接口与实现分离的技术。 下面用一个最简单的例子来说明。 类ClxExp是我们要导出的类,其中有一个私有成员变量是ClxTest类的对象,各个文件内容如下: lxTest.h文件内容: class ClxTest { public: ClxTest(); virtual ~ClxTest(); void DoSomething(); }; lxTest.cpp文件内容: #include "lxTest.h" #include using namespace std; ClxTest::ClxTest() { } ClxTest::~ClxTest() { } void ClxTest::DoSomething() { cout << "Do something in class ClxTest!" << endl; } lxExp.h文件内容: #include "lxTest.h" class ClxExp { public: ClxExp(); virtual ~ClxExp(); void DoSomething(); private: ClxTest m_lxTest; void lxTest(); }; lxExp.cpp文件内容: #include "lxExp.h" ClxExp::ClxExp() { } ClxExp::~ClxExp() { } // 其实该方法在这里并没有必要,我这样只是为了说明调用关系 void ClxExp::lxTest() { m_lxTest.DoSomething(); } void ClxExp::DoSomething() { lxTest(); } 为了让用户能使用我们的类ClxExp,我们必须提供lxExp.h文件,这样类ClxExp的私有成员也暴露给用户了。而且,仅仅提供lxExp.h文件是不够的,因为lxExp.h文件include了lxTest.h文件,在这种情况下,我们还要提供lxTest.h文件。那样ClxExp类的实现细节就全暴露给用户了。另外,当我们对类ClxTest做了修改(如添加或删除一些成员变量或方法)时,我们还要给用户更新lxTest.h文件,而这个文件是跟接口无关的(用户还必须进行重新编译!)。当然上面的情况不是我们想看到的。对用户来说,他们只关心类ClxExp的接口DoSomething()方法。那我们怎么才能只暴露类ClxExp的DoSomething()方法而不又产生上面所说的那些问题呢?答案就是--接口与实现的分离。我可以让类ClxExp定义接口,而把实现放在另外一个类里面。下面是具体的方法: 首先,添加一个实现类ClxImplement来实现ClxExp的所有功能。注意:类ClxImplement有着跟类ClxExp一样的公有成员函数,因为他们的接口要完全一致。 lxImplement.h文件内容: #include "lxTest.h" class ClxImplement { public: ClxImplement(); virtual ~ClxImplement(); void DoSomething(); private: ClxTest m_lxTest; void lxTest(); }; lxImplement.cpp文件内容: #include "lxImplement.h" ClxImplement::ClxImplement() { } ClxImplement::~ClxImplement() { } void ClxImplement::lxTest() { m_lxTest.DoSomething(); } void ClxImplement::DoSomething() { lxTest(); } 然后,修改类ClxExp。 修改后的lxExp.h文件内容: // 前置声明 class ClxImplement; class ClxExp { public: ClxExp(); virtual ~ClxExp(); void DoSomething(); private: // 声明一个类ClxImplement的指针,不需要知道类ClxImplement的定义 ClxImplement *m_pImpl; }; 修改后的lxExp.cpp文件内容: // 在这里包含类ClxImplement的定义头文件 #include "lxImplement.h" ClxExp::ClxExp() { m_pImpl = new ClxImplement; } ClxExp::~ClxExp() { delete m_pImpl; } void ClxExp::DoSomething() { m_pImpl->DoSomething(); } 请注意两个文件中的注释。通过上面的方法就实现了类ClxExp的接口与实现的分离。我们只需给用户提供一个头文件lxExp.h就行了,不会暴露类ClxExp的任何实现细节。而且我们对类ClxTest的任何改动,都不需要再给用户更新头文件(当然,库文件是要更新的,这种情况下用户也不用重新编译!)。这样做还有一个好处就是,可以在分析阶段由系统分析员或者高级程序员来先把类的接口定义好,甚至可以把接口代码写好(例如上面修改后的lxExp.h文件和lxExp.cpp文件),而把类的具体实现交给其他程序员开发。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值