在创建跨平台多线程应用程序时考虑这种情况。
因此,当您这样做时,您可能会在某些类之间划分平台功能。例如,您需要简单的控制台来输出应用程序中的某些文本。执行此操作的可能方式是声明一些抽象类Console
,然后在某个平台上需要它时,继承它并使用派生类实例。
一切都行,直到你发现某个地方需要Console
实例(例如作为类成员)。您知道,如果您尝试在其他类中声明类Console
的成员变量,则会出现错误,因为不允许抽象类的实例。但是你仍然需要那个类,因为你认为在编译时派生类将被实现并且它是正确的,但你不知道该类的名称,或者根据平台可能有不同的名称。
这是一个复杂的例子。
开发跨平台多线程应用程序时,需要Syncer
(Synchronizer)之类的东西。它的类比是Windows API上的互斥对象。
你知道,根据平台,这个类会有所不同。但是你确实知道任何平台变体都有一些方法。例如,这些方法是lock
和unlock
。由于您不知道如何完成这些方法,因此您将它们声明为纯虚拟下一个:
class Syncer
{
public:
virtual void lock()=0;
virtual void unlock()=0;
}
现在,开发一些课程,你意识到,你不需要一个,但很多这个Syncer
- s。但是你不能这样做,因为这个课是抽象的。
我找到的可行解决方案是:
1)使用模板。例如:
template<class syncer>
class SyncUser
{
public:
syncer syncInstance;
SyncUser()
{
syncInstance().lock;
}
但问题是,类用户可以粘贴而不是syncer
参数任何其他类。(他会不会,这不重要。他可以做到这一点)。因此,该解决方案不如预期的一般解决方案那么好。
2)使用宏。如果使用这种方式,Syncer.h
的内容就像下一个:
class Syncer
{
public:
virtual void lock()=0;
virtual void unlock()=0;
}
#ifdef PLATFORM1
#include "platform1_sync_implement.h"
#else
#include "platform2_sync_implement.h"
#endif
当"platform1_sync_implement.h"
文件具有以下内容时:
#include "Syncer.h"
class SyncPlatform1 : public Syncer
{
//Correct implementation
}
#define Syncer SyncPlatform1
现在,包含Syncer.h
的任何人都会拥有已实施的版本。
但这种方式也不好,因为需要实现Sync
抽象的平台列表。这对大型项目来说并不是那么好,因为你只需要声明该类并关心其他程序员可以使用它。
所以问题是:是否有更好的方法来使用&#39;实例&#39;抽象类,知道它的子类将在某处实现。
P.S。:我知道这不是这个问题的最佳名称。 P.P.S。:抱歉英语不好。
答案 0 :(得分:1)
要在不同的平台上实现不同的实现,你不应该使用多态,你应该使用旧的#if __linux__,#if defined __mac__&amp;&amp;定义__darwin __,#if _WIN32等
如果您需要充分利用实际CPU,程序最终会运行,并且您希望为每个可能的CPU专门优化实现,那么这是一个不同的故事,因为您需要一些运行时机制来选择最佳实现。
答案 1 :(得分:0)
抽象类背后的想法是提供一个完成基类的点,但将来由基类的用户提供。
如果那是什么意思,那么使用抽象类。如果基类应该按原样使用,那么提供一个空例程
class BASE {
public:
void SomethingUnusedHere() {}
};
如果用户真正做什么并且在使用类中仍然不需要,那么用户也可以这样做。
class BASE {
:
void Func() = 0;
:
}
class CHILD : public BASE {
:
void Func() {}
:
}
当然,如果确实需要Func,那么它应该包含正确的代码;