头文件和实现文件如何在C ++中工作?

时间:2011-07-20 00:01:33

标签: c++

我对C ++中标题和实现文件之间的关系有疑问。

我收到了两个空头文件和一个空实现文件。当我说“空”时,我的意思是文件只包含方法声明;我必须在每个方法中实现代码。 (我认为发布这三个文件的代码是多余的,因为它们只包含声明..)

这三个文件是:

  • interface_complexmutex.h
  • complexmutex.h
  • complexmutex.cpp

interface_complexmutex.hcomplexmutex提供了虚拟方法。此外,complexmutex类继承自interface_complexmutex

这些文件具有我必须实现的基本互斥函数。我有两个问题:

  1. 为什么我需要interface_complexmutex.h?它实际上没有.cpp文件,整个实现都在complexmutex个文件中,对吗?

  2. 我应该如何包含这些文件并在程序中使用complexmutex类? (例如,如果我在init()中使用complexmutex.cpp方法)

    main.cpp应该是这样的吗?

    #include <stdlib.h>
    #include <stdio.h>
    #include "interface_complexmutex.h"
    #include "complexmutex.h"
    using namespace std;
    int main(){
    
        complexmutex a;
    
        /* do something with mutex to test */
    
        return 0;
    }
    

    我制作了自己的Makefile,到目前为止上面的代码运行正常。

2 个答案:

答案 0 :(得分:2)

1)只有在以后可能会改变实施时,才需要接口。这将使您可以自由地对代码的内部进行所需的所有更改,而不会影响使用它来创建软件的人员。这意味着用户应查看接口类,从不实现。

为此,您需要实现所谓的factory模式。这是一个函数,它将创建实现类的实例并将其作为指针(或引用)返回给接口类。您可能可以将该函数编写为接口类的静态方法。

2)在程序中,您应该想象您是代码的用户。用户不关心如何实现您的功能,因此根本不应该使用该实现。如果可能,它应该只包括接口头并调用工厂方法,如下所示:

 #include "interface_complexmutex.h"
 using namespace std;

 int main(...) {
     interface_complemutex* mutex = interface_complexmutex::create_new(...);
     // do something interesting with the mutex
 }

在此示例中,create_new是您的工厂方法。如果你有不同的实现,你可以有它的参数(通常是枚举)。

使用接口(实际上是C ++中的抽象类)时,需要使用指针或引用。您无法为抽象类创建值。当然,如果您编写测试代码,它会有所不同,因为测试代码不会被您的库用户看到/使用。

注意:

我要指出,命名非常糟糕。接口应该命名为complexmutex和实现complexmutex_impl,因为用户应该更多地使用接口,它的名称应该更短(并且你可以用相关的东西替换“impl”,如“pthread”,如果你使用pthreads来实现你的互斥类。

作为PS注释,在C ++ 0x中有一个包含互斥锁的线程库。它已经得到了一些编译器的支持。

答案 1 :(得分:1)

接口类(包含所有虚函数的C ++类)有助于重用接口设计。理想情况下,这些类只捕获接口而不是实现。因此,它们只有.h文件而不是相应的.cpp文件。

开始重用,假设我们需要定义另一个互斥类,实现完全不同。我们将无法重用complexmutex类实现,但仍能够重用interface_complexmutex类。另外,可以使用新互斥类的对象代替complexmutex,因为它们具有通用接口。