Why use a C++ Interface as a connection between classes?
我有一些关于C++接口的问题。
据我所知,如果您想将一个基类与您已经想到的某些任务一起使用,并且为此声明了一些方法(但没有定义),那么就使用它们。但是每个派生类都需要实现这些方法以达到它们的特定目的,因此您可以将它们创建为抽象方法。抽象类和接口的唯一区别是抽象类至少有一个纯虚方法,而一些"普通"方法和接口只有纯虚方法。对吗?
我的教授把界面描述为两个班级相互交流的一种方式。例如,一个接口用于网络类,一个接口用于分析来自该网络的信息的分析器类。但是为什么我需要一个接口?我不能用一个普通的类来代替一个从接口派生的类吗?他说,为了从另一个类中提取信息,需要有一个接口派生类。在这里使用接口有什么好处吗?
我希望我的问题很清楚,英语不是我的第一语言。
编辑:抽象类:(1/3方法是纯虚拟的)
1 2 3 4 5 6 7 8 9 | class MyAbstractClass { public: virtual ~MyAbstractClass() {} virtual void Method1(); virtual void Method2(); virtual void Method3() = 0; }; |
接口:(所有方法都是纯虚拟的)
1 2 3 4 5 6 7 | class MyInterface { public: virtual ~MyInterface() {} virtual void Method1() = 0; virtual void Method2() = 0; }; |
免责声明:如果老师这么说的话,一定要为你的课程使用虚拟界面!以下只是您真正需要使用它们的一个解释。
事实证明,你可以使用一个普通的类使用一个名为模板的C++特性。例如,
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | /** ... * Network must have the following method: * size_t readsome(char* buffer_out, size_t buffer_size) */ template<typename Network> class Analyzer { public: Analyzer(/* constructor arguments */); void analyze(Network& network) { char[50] buffer; const size_t read = network.readsome(&buffer, 50); /* ... */ } /* I dunno maybe a view_log function should go here. */ private: /* ... */ }; |
这里,
现在您可以执行以下操作:
1 2 3 | CoolNetwork cool_network(/* ... */); Analyzer<CoolNetwork> analyzer(/* ... */); while (cool_network.is_open()) { analyzer.analyze(cool_network); } |
你可以分开做
1 2 3 | CoolerNetwork cooler_network(/* ... */); Analyzer<CoolerNetwork> analyzer(/* ... */); while (cooler_network.is_open()) { analyzer.analyze(cooler_network); } |
这是静态/编译时/参数多态性(请选择)。但是,如果您想在不同类型的网络上使用单个
1 2 3 4 5 | CoolNetwork cool_network(/* ... */); CoolerNetwork cooler_network(/* ... */); Analyzer<Network> analyzer(/* ... */); while (cool_network.is_open()) { analyzer.analyze(cool_network); } while (cooler_network.is_open()) { analyzer.analyze(cooler_network); } |
然后,您需要一个名为
1 2 3 4 5 6 | class Network { public: virtual size_t readsome(char* buffer_out, size_t buffer_size) = 0; //is_open doesn't have to be in the interface to make the above //snippet compile, but it would probably belong here }; |
显然,您应该做适合于类的事情,但一般来说(IMO)最好默认为模板+文档(更简单、更灵活、更具性能),然后在需要动态多态性时将其升级到接口。
假设您正在编写分析代码,但您的同事正在编写网络代码。你可以给你的collegaue一个接口,然后说"我不在乎你做什么,只要你写一些遵循这个接口的代码,我的代码就能够分析它"。
但你是对的,你不必使用接口,但有时它们是划分责任的有用方法。
But why do I need an interface for that? Couldn't I just use a normal class for that instead a class which is derived from an interface?
因为您通常希望在将来的扩展中保持代码的可修改性,或者添加新的分析器来与您的网络类交互。另外,与底层网络通信的方式可能不同,您需要以灵活透明的方式为分析器处理这些信息。
He made it sound that in order to extract information from another class you need to have a interface-derived class. Is there any benefit from using an interface here?
这不是严格必要的,但好处是,如果项目经理让您执行上面所述的某些东西(不同的分析算法或不同的网络传输),那么在不重写所有代码的情况下,进行这些更改将变得更加容易。
它的不变部分可以在抽象基类中提供,并在继承类中针对具体的用例进行扩展。