这实际上是一个相当有趣的错误;错误消息并没有太多的告诉你问题是什么。
宏定义:
#ifndef uint32_t
#define unsigned int uint32_t;
#endif
有不正当的几个层次。在宏定义,被定义的宏变为第一,其次,它展开为序列 - 其通常应该不被由分号结束:
#define uint32_t unsigned int
使用宏用于此目的的是一种,但馊主意;一个typedef
要好得多:
typedef unsigned int uint32_t;
(注意,被定义的标识进入最后的,并且需要一个分号;宏定义和typedef
■找非常不同的语法)。不像宏,没有办法测试typedef
是否已经被定义。
的uint32_t
应该已经在<stdint.h>
或<cstdint>
定义 - 但是这是由1999 ISO C标准添加到C一个标准的头,并用C采用++仅由2011 ISO C++标准,所以有一个像样的机会它将不可用,具体取决于您使用的C++实现。如果头存在,你可以使用#ifdef UINT_MAX
以确定是否uint32_t
定义,但如果你担心不具有一个32位无符号类型的所有系统,这只是有用的。
但你的代码甚至不指uint32_t
- 为啥宏定义会导致问题?
因为你得到的顺序不对,你的宏定义没有定义uint32_t
,它定义unsigned
,使这个词出现的任何将扩大到int uint32_t;
(包括分号)。
但你不指unsigned
或者 - 至少没有直接。这个问题,那么,在你的_tmain
定义:
int _tmain(int argc, _TCHAR* argv[])
两个_tmain
作为程序的入口点和类型名称_TCHAR
是微软特有的。我没有进入目前微软的编译器,但你看到的错误消息,_TCHAR
(逻辑上应该被一个typedef)可能是一个可扩展为类似unsigned short
宏(使用16判断因为Windows喜欢使用UTF-16的16位宽字符)。
所以,你的定义:
int _tmain(int argc, _TCHAR* argv[])
扩展为:
int _tmain(int argc, unsigned short* argv[])
它,因为你无意中重新定义unsigned
,则扩展为:
int _tmain(int argc, int uint32_t; short* argv[])
而且,由于参数声明用逗号分隔,而不是用分号分隔,这是一个语法错误。我不知道为什么这会导致您所看到的特定错误信息,但这并不令人吃惊。语法错误,尤其是涉及错误定义的宏的错误,通常会导致错误消息的混淆。
这样的事情最好的策略是通常看最早行,编译器会报告错误。如果错误信息本身没有照亮,请忽略它并研究源,试图弄清楚你可能弄错了什么。
如果失败(因为它会在这种情况下),试图通过只预处理器运行程序。大多数基于Unix的编译器(包括gcc)都使用-E
选项;我不知道微软的相应选项。预处理器的输出可能是非常冗长(这将包括直接或间接所有你包括报头的错位副本),但研究它可能会导致你一些有用的东西。
在这种特殊情况下,注释掉您的#define
指令会导致错误消失,这将暗示#define
存在问题,即使它与错误消息之间的关系远不明显。
UPDATE:
我的猜测是不正确大部分。 _TCHAR
不是宏;显然这是一个typedef。错误是没有的_tmain
的定义,它是在成员声明:
uint32_t emp_id;
而且由于uint32_t
还没有明确规定它根本没有。
错误消息仍然是误导。由于uint32_t
尚未声明,因此它被视为普通标识符而不是类型名称 - 类型名称被视为语法不同于普通标识符。编译器试图通过猜测uint32_t
可能是一个成员的名字,这意味着它应该有一个分号从错误中恢复 - 但随后的声明
uint32_t;
将宣布一员,没有明确的类型。在C的旧版本中,这将是合法的并且会使该成员成为int
。编译器对代码实际意义的猜测是错误的。顺便说一句,如果你显示一条错误信息,请告诉我们它适用于哪条线。
'_TCHAR'必须是一个宏,可能扩展为'unsigned char'或'unsigned short'。 –
我认为这是一个比它最初看起来更好的问题。问题是'#define',但是它和错误信息之间的关系远不明显;详情请参阅我的答案。 –