《WINDOWS程序设计》(024)2.2 宽字符和C语言-2.2.4 维护一个源代码文件
2.2.4维护一个源代码文件当然,使用Unicode肯定也有某些缺点。首先同时也是最重要的是,程序中的每一个字符会占用两倍的空间。此外,你会看到,宽字符运行库函数比正常的函数要大。为此,你可能希望创建两个版本的程序,一个用ASCII字符串而另一个使用Unicode字符串。而最好的办法则是维护一个单一的源代码文件,但可以编译成ASCII或Unicode。
但这是有问题的,因为运行库函数具有不同名称,字符变量的定义也不同,还有那个讨厌的在字符串字面之前必须要加的L。
一个答案是使用包含在Microsoft Visual C++中的TCHAR.H头文件。这个头文件并不是ANSI C标准的一部分,所以其中定义的每一个函数和宏都有一个下划线前缀。TCHAR.H为那些需要字符串参数的普通运行库函数(例如,_tprintf和_tcslen)提供了一系列的替代名称。这些函数有时被称为“通用”的函数名字,因为它们可以指Unicode或非Unicode版本的函数。
如果一个命名为_UNICODE的标识符被定义了并且TCHAR.H头文件被包含在你的程序中,_tcslen就被定义为wcslen:
#define _tcslen wcslen如果UNICODE并没有被定义,那么_tcslen就被定义为strlen:
#define _tcslen strlen
以此类推。TCHAR.H也用一个命名为TCHAR的新的数据类型解决了两个字符数据类型的问题。如果_UNICODE标识符被定义了,TCHAR就是wchar_t:
typedef wchar_t TCHAR;
否则的话,TCHAR就是一个简单的char:
typedef char TCHAR;
现在是时候来解决字符串文字中L这一棘手的问题。如果_UNICODE标识符被定义,一个叫做__T的宏是如下定义的:
#define __T(x) L ## x
这是相当模糊的语法,但它在ANSI C标准的C预处理器中。那一对数字符号被称为“令牌粘贴”,它使得字母L和宏参数拼接在一起。因此,如果宏参数是“Hello!”,那么L##x就是L”Hello!”。
如果_UNICODE标识符没有被定义,__T宏就简单定义如下:
#define __T(x) x
无论如何,其他两个宏是定义成和__T一样的:
#define _T(x)__T(x)
#define _TEXT(x)__T(x)
Win32控制台程序使用哪一种取决于你所需要的简明或详细程序。基本上,必须用下列方式将字符串字面定义在_T或_TEXT宏内:
_TEXT(“Hello!”);
这样作的结果是,如果_UNICODE标识符被定义了,字符串就被解释成是由宽字符组成的,如果没有被定义,它则被解释成8位的字符串。
【课外资料】
_T、_TEXT、TEXT 三者效果相同
tchar.h是运行时的头文件,_T、_TEXT 根据_UNICODE来确定宏。
winnt.h是Win的头文件根据,TEXT 根据UNICODE 来确定宏。
如果需要同时使用这3个宏,则需同时定义 UNICODE 和 _UNICODE
VS2010 ,设置:项目–属性–配置属性–常规–字符集–使用Unicode字符集, 那么编译器命令选项中的确同时加入了_UNICODE和UNICODE。 注:项目–属性–配置属性–C/C++–命令行
_UNICODE宏用于C运行期头文件,
UNICODE宏则用于Windows头文件.
当编译源代码模块时,通常必须同时定义这两个宏。
页:
[1]