匈牙利表示法是微软雇员Charles Simonyi博士的发明。它之所以称为匈牙利表示法,是因为Charles来自匈牙利。基本上,这是一个命名约定:在每一个变量名前添加表示变量类型的字母前缀,并继以一个大写字母开头的对变量的简短描述。例如,如果需要用一个整数型变量来保存游戏中的得分,会把它命名为iScore。匈牙利表示法的发明来自于为微软程序员建立一个可遵循的编程规范的迫切需求。如果一个公司所有的程序员各自使用不同的命名约定,一切将变得非常混乱。
尽管这个系统看上去挺繁琐,有些名字看起来似乎更像来自一个遥远国家的语言,但当你一旦接受了之后就会觉得它确实挺有用。有一些程序员厌恶这种表示法,在Usenet上充斥着关于匈牙利表示法的好与不好的争论帖。竟然有那么多人为此措辞严厉,情绪激动,这真是有点不可思议。这只是一个个人爱好问题。但无论持何种观点,了解这种命名约定对将来学习Windows编程还是有帮助的。这是一些起码的知识。这些前缀的具体含义是什么?可参看表1.3,在表中列出了一些较常用的前缀。
表1.3 匈牙利记号表示法前缀
前 缀 | 类 型 |
sz | 指向一个以零字符结尾的字符串中的第一个字符 |
str | 字符串 |
i | int |
n | 数或int |
ui | Unsigned int |
c | char |
w | WORD(unsigned short) |
dw | DWORD(unsigned long) |
fn | 函数指针(function pointer) |
d | Double |
by | byte |
l | long |
p | pointer |
lp | long pointer |
lpstr | 指向字符串的long pointer |
h | 句柄(handle) |
m_ | 类成员(class member) |
g_ | 全局型(global type) |
hwnd | 窗口的句柄(Window handle) |
hdc | Windows设备上下文(device context)的句柄 |
现在,当看到诸如g_iScore、szWindowClassName和m_dSpeed的变量名,你就能够知道它们具体描述什么了。你会在笔者的代码中发现,笔者使用了个人版本的匈牙利表示法,因为觉得它极为有用。有了匈牙利表示法,就可以在阅读他人的代码的时候立即理解变量类型而不用来回查找它们的定义。还有一点必须在这里说明的是,笔者并不对每个变量都使用匈牙利表示法。如果在一个小函数里用到一个变量,那么笔者会用任何我觉得适当的名字,因为这变量是什么是显而易见的。例如,一个函数来接收一个错误字符串作为参数,并显示一个消息框,程序如下:
void ErrorMsg(char* error);
而非:
void ErrorMsg(char* szError);
另外,笔者用大写字母C作为所有类的前缀,大写字母S作为所有结构的前缀(读者可以想一下这是为什么)。在一些诸如2D/3D矢量和STL vector类的声明上,也使用了笔者所习惯的匈牙利表示法。由此,一个典型的类定义是这样的:
class CmyClass
{
private:
int m_iHealth;
S2DVector m_vPosition;
vector<float> m_vecfWeights;
public:
CMyClass();
};