奇怪的错误C2065:'错误':未声明的标识符

作为更大项目的一部分(Mozilla Firefox的fx activex插件),有这样的代码片段:

if (CombineRgn(hrgnClip, hrgnClip, hRGN, RGN_AND) != ERROR) { ::InvalidateRgn(m_hWndParent, hrgnClip, fErase); } 

当我build立VS2012时,我得到“ 错误C2065:'错误':未声明的标识符 ”ERROR在wingdi.h中定义如下:

 ... /* Region Flags */ #define ERROR 0 // it wont build when this macro is used #define NULLREGION 1 // it builds when this macro is used #define SIMPLEREGION 2 #define COMPLEXREGION 3 #define RGN_ERROR ERROR ... 

奇怪的是,如果我在上面的if语句中用NULLREGION或SIMPLEREGION(它们是同一个文件中的macros,只有两行下面的代码)replaceERROR(只是为了查看是否可以生成OK),代码就会生成OK。 当我使用错误,代码将不会build立。 上面定义的ERRORmacros是否有可能被某个关键字或另一个macros或Visual Studio中的一些macros所掩盖?

这里的问题是ERROR实际上出现在编译错误信息中。 这不应该发生,预处理器应该用0代替它。

因此,在windows.h之后的某个 .h文件中,有些程序员花了10秒的时间来处理宏名称冲突问题,并写下了这个问题:

  #undef ERROR 

您需要找到该行并将其删除。 这可能是困难的,很容易给你一个维护头痛,因为这是一个你不拥有的文件,并可能在未来更新,迫使你一遍又一遍地做这个改变。 另一种方法是自己重新定义它:

 #define MYGDIERROR 0 ... if (CombineRgn(hrgnClip, hrgnClip, hRGN, RGN_AND) != MYGDIERROR) //etc... 

这仍然给你一个维护问题,并要求你打赌CombineRgn()的返回值定义永远不会改变。 这是一个非常安全的赌注,GDI投在石头上。