宏重写类成员

Macro Overriding Class Member

本文关键字:成员 重写      更新时间:2023-10-16

我正在学习为多个平台编程,我看到许多包含/库使用宏来告诉编译器在特定平台上调用哪些函数。

所以我定义了以下内容:

#if defined _WIN32 || defined _WIN64
    #define Close(Handle) CloseHandle(Handle)
#else
    #define Close(Handle) close(Handle)
#endif

但是我的Socket类有以下成员函数:

Socket::Close()
{
    //Close socket and clean up..
}

当我执行以下操作时:

Socket sock(Port, LocalHost);
sock.Close();

:

error: 'class Socket' has no member named 'CloseHandle'
     #define Close(Handle) CloseHandle(Handle)
                           ^
note: in expansion of macro 'Close'
       sock.Close();
            ^

有任何想法我可以如何修复它,或者我应该摆脱关闭,使它成为一个类型定义?

最简单的解决方案就是为您的宏使用另一个名称。

但这不是正确的做法:在某些平台上,您可能需要更复杂的逻辑来执行特定于平台的操作(例如,您可能需要在'close'之前执行'flush'之类的操作)。因此,最好将#ifdef隔离在函数中:

void Close(Handle handle) {
#if defined _WIN32 || defined _WIN64
    CloseHandle(handle);
#else
    close(handle);
#endif
}
Socket::Close()
{
    //Close socket and clean up..
    ::Close(...);
}

如果您定义一个抽象类(Environment),为所有系统特定的操作提供接口,并为每个具体平台编写一个类的实现(在子类中- WindowsEnvironment, PosixEnvironment),那将更加优雅。类的实例可以是全局可访问的单例,选择合适的环境完全可以不使用宏来执行——只需在项目中编译正确的源文件。

您应该为您的类创建跨平台的接口。例如,您需要创建close()方法。此方法应该存在于所有平台上。如果不同平台上的实现不同,则应该使用宏为每个平台添加单独的实现。应该在cpp文件中完成。

. h 文件:

void close(Handle handle);
<<p> . cpp/strong>文件:
void Socket::close(Handle handle) {
  #if defined _WIN32 || defined _WIN64
    CloseHandle(handle);
  #else
    close(handle);
  #endif
}