Windows API 和 GetClassName()? 另一个名字?
我有一些代码,它有一个 C++ 动态类系统,其中有一个名为 GetClassName() 的成员,这是一个人们想象的相当无害的名称。 然而,当包含在带有 Windows 标头的大型项目中时,一切都崩溃了。 显然,Windows 使用 #define GetClassName(GetClassNameA 或 GetClassNameW),它搞砸了一切,我的虚拟调用树变得一团糟,让我在黑暗中愚蠢的编译器调试中浪费了一天的时间,试图找出问题所在。
因此,除了我咒骂微软为 #define 使用如此可怕的容易冲突的名称(我的意思是有人应该为此被枪杀!)之外,我还要求 3 个目的。
- 还有什么好名字 获取类名() ?
- 有没有办法 解决这个问题,以便将来,其他 我的代码库的开发人员不会 遭受相似的
- 命运 当别人的后代 遇到类似的情况 莫名其妙的错误
I have some code that has a dynamic-class system in C++ that has a member called GetClassName(), a rather harmless name one would imagine. However when included in a large project with Windows headers all hell broke loose. Apparently Windows uses a #define GetClassName (GetClassNameA or GetClassNameW) which screws up everything, and my virtual call tree became all messed up making me lose a day in stupid compiler debugging in the dark, trying to figure out what was wrong.
So besides the point that I'm cursing Microsoft for using such a horribly easy to clash name for a #define (I mean someone should honestly be shot for this!) I'm asking for 3 purposes.
- What's another good name for
GetClassName() ? - Is there anyway to
fix this, so in the future, other
developers of my code base won't
suffer similar fate - And for
posterity when someone else
encounters this similarly
inexplicable error
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
ClassGetName()
#undef GetClassName
#include
它们。ClassGetName()
#undef GetClassName
#include
them.我会重命名该方法。
当然可以说,
但这并不干净,代码的用户应该记住在调用 win32 函数时编写::GetClassNameW。
可以在他的类中提供 GetClassNameA 和 GetClassNameW 方法,但它非常丑陋。
我看到两种方法:延长或缩短名称:)
1) 为子系统中的所有函数添加前缀 fe TI_ (用于类型信息):
2) 或将它们放入某个 IClass 接口中
并从单个方法返回该接口,
这样 GetClassName() 就变成
I would rename the method.
Of course one can say
but it is not clean, users of one's code should remember to write ::GetClassNameW when they call win32 function.
One can provide GetClassNameA and GetClassNameW methods in his class, but it's plain ugly.
I see two approaches : either lengthen or shorten the name:)
1) add a prefix for all functions in the subsystem, f.e TI_ (for type info):
2) or put them into some IClass interface
and return that interface from single method,
so that GetClassName() becomes
也许是 GetWindowClassName? 事实上,GetClassName 对于这个 API 来说并不是一个坏名字,因为它与窗口类相关。 真正的问题是它是一个 C API 声明,而 C 声明无法引入不会污染全局命名空间的可重用声明。
这与其说是微软的失败,不如说是C语言的失败。
GetWindowClassName perhaps? In reality GetClassName is not a bad name for this API as it relates to window classes. The real problem is that it's a C API declaration and C declarations have no way to introduce a re-usable declaration which doesn't pollute the global namespace.
This is much more a failing of the C language than microsoft.
Windows API 充满了具有干净名称的宏,这些宏扩展为带有指示 ASCII/UTF-16 后缀的函数名称,具体取决于构建选项。 如果他们在所有内容前面加上“W32”或类似的前缀(OS X 上的“NS”),那就太好了,但他们选择不保持 API 的“干净”。
由于更改代码比更改 API 容易得多,因此这里有一些建议:
1) 学习 Windows API(实际上没那么大!),或者至少熟悉 MSDN 以便您在遇到莫名其妙的程序流程时可以查找名称冲突。
2) 在代码中尽可能使用显式作用域解析 (MyClass::GetClassName())。 不幸的是,这会破坏虚拟函数调度,所以要小心这一点。
3) 在代码中使用不同的命名约定。 MS 始终使用 CamelCase,因此如果您选择其他约定(get_class_name()、getClassName() 等),则不会发生冲突。
4)就我个人而言,我讨厌命名我的吸气剂和吸气剂。 setter“GetX()”和“SetX()”,但更喜欢依靠重载机制,并使用“xtype X() const”作为 getters,使用“void X(xtype newval)”作为 setters。 您的里程可能会有所不同,但我发现它更干净且更干净。 从参数来看,get/set 是显而易见的。 显然,如果您使用默认参数,则必须小心。
祝你好运!
The Windows API is chock full of macros with clean names that expand to function names with a suffix indicating ASCII/UTF-16, dependent on build options. It would have been nice if they prefixed everything with "W32" or similar (a la "NS" on OS X), but they chose not to presumably to keep the API "clean".
Since it's a lot easier to change your code than their API, here are a few suggestions:
1) Learn the Windows API (it's actually not that big!), or at least become familiar with MSDN so that you can look for name clashes when you encounter inexplicable program flow.
2) Use explicit scope resolution in your code where you can (MyClass::GetClassName()). Unfortunately, this will break virtual function dispatch, so be careful with this.
3) Use a different naming convention in your code. MS always uses CamelCase, so you won't clash if you pick some other convention (get_class_name(), getClassName(), etc.).
4) Personally, I hate naming my getters & setters "GetX()" and "SetX()", but prefer to lean on the overloading mechanism and use "xtype X() const" for getters and "void X(xtype newval)" for setters. Your mileage may vary, but I find it cleaner & the get/set is obvious from the arguments. Obviously you have to be careful if you're using default arguments.
Good luck!