我有一些C ++代码,包括一个名为CreateDirectory().
的方法CreateDirectory().
以前的代码只使用STL和Boost,但是我最近不得不包含<windows.h>
所以我可以查找CSIDL_LOCAL_APPDATA
。
现在,这个代码:
filesystem.CreateDirectory(p->Pathname()); // Actually create it...
不再编译:
error C2039: 'CreateDirectoryA' : is not a member of ...
在winbase.h
对应这个macros:
#ifdef UNICODE #define CreateDirectory CreateDirectoryW #else #define CreateDirectory CreateDirectoryA #endif // !UNICODE
预处理器正在重新定义我的方法调用。 有没有可能的方法来避免这种命名冲突? 或者我必须重命名我的CreateDirectory()
方法?
如果你只是重命名你的CreateDirectory方法,你会更好。 如果你需要使用Windows API,与Windows.h交战是一场失败的战斗。
可以肯定的是,如果你在包含windows.h的时候是一致的 ,这仍然是编译的。 (虽然你可能在其他地方有问题)。
#undef CreateDirectory
您可以创建一个模块,其唯一目的是#include <windows.h>
并查找封装在函数中的CSIDL_LOCAL_APPDATA。
int get_CSIDL_LOCAL_APPDATA(void) { return CSIDL_LOCAL_APPDATA; }
顺便说一句,做好发生了什么事!
作为开发跨平台代码库的开发人员,这是一个问题。 处理这个问题的唯一方法是
或者,如果这是一个不愉快的命题,(这是对我来说)
如果你的可用性函数需要包含冲突符号的项目头文件,那么下面的模式是必须的:
#include <windows.h> #ifdef CreateDirectory #undef CreateDirectory #endif // etc #include "some_class_with_CreateDirectory_method.h" // ...
您将需要显式调用任何Windows API函数的非宏版本,您有#undef'd – CreateDirectoryA或W等
push
宏, undef
它,再次pop
宏:
#pragma push_macro("CreateDirectory") #undef CreateDirectory void MyClass::CreateDirectory() { // ... } #pragma pop_macro("CreateDirectory")
请注意,名称冲突通常来自包含某个头文件。 在那之前,像CreateDirectory和GetMessage这样的东西不会被拉进可视化和代码编译没有问题。
你可以将这样一个包含分离到一个包装头文件中,并在其末尾“#undef whatever”。 那么,不管你有什么名字相撞,都会消失。 当然,除非你需要在自己的代码中使用这些宏(是的,所以很可能…)
#pragma push_macro("CreateDirectory")
如果没有任何工作,而不是重命名,你可以使用自己的命名空间为您的功能。