常见编译错误
B. 程序编译错误不知道是什么原因
不能通编译过的程序实际上还不是合法的程序,因为它不满足C语言对于程序的基本要求。
检查语法错误的第一要义:集中力量检查系统发现的第一个错误,弄清并改正它。
在编译过程中系统发现的错误主要有两类:基本语法错误和上下文关系错误。这些错误都在表面上,可以直接看得见。也是比较容易弄清,比较容易解决的。关键是需要熟悉C语言的语法规定和有关上下文关系的规定,按照这些规定检查程序正文,看看存在什么问题。
编译中系统发现错误都能指出错误的位置。不同系统在这方面的能力有差异,在错误定位的准确性方面有所不同。有的系统只能指明发现错误的行,有的系统还能够指明行内位置。
一般说,系统指明的位置未必是真实错误出现的位置。通常情况是错误出现在前,而系统发现错误在后,因为它检查到实际错误之后的某个地方,才能确认出了问题,因此报出错误信息。要确认第一个错误的原因,应该从系统指明的位置开始,在那里检查,并从那里开始向前检查。
系统的错误信息中都包含一段文字,说明它所认定的错误原因。应该仔细阅读这段文字,通常它提供了有关错误的重要线索。但也应该理解,错误信息未必准确,有时错误确实存在,但系统对错误的解释也可能不对。也就是说,在查找错误时,既要重视系统提供的错误信息,又不应为系统的错误信息所束缚。
发现了问题,要想清楚错误的真正原因,然后再修改。不要蛮干。在这时的最大诱惑就是想赶快改,看看错误会不会消失。但是蛮干的结果常常是原来的错误没有弄好,又搞出了新的错误。
另一个值得注意的地方:程序中的一个语法错误常常导致编译系统产生许多错误信息。如果你改正了程序中一个或几个错误,下面的弄不清楚了,那么就应该重新编译。改正一处常常能消去许多错误信息行。
解决语法错误
常见语法错误:
1)缺少语句、声明、定义结束的分号。
2)某种括号不配对。C语言中括号性质的东西很多,列举如下:
( ), [ ], { }, ' ', " ", /* */
在不同位置的括号不配对可能引起许多不同的错误信息。
3)关键字拼写错误。
较难认定的典型错误:
1)宏定义造成的错误。这种东西不能在源程序文件中直接看到,是在宏替换之后出现的。常见的能引起语法错误的宏定义错误:宏定义中有不配对的括号,宏定义最后加了不该有的分号,……
解决上下文关系错误
1)变量没有定义。产生这个问题的原因除了变量确实没有大意外,还可能是变量的拼写错误,变量的作用域问题(在不能使用某个变量的地方想去用那个变量)。
2)变量重复定义。例如在同一个作用域里用同样名字定义了两个变量,函数的局部变量与参数重名等。
3)函数的重复定义。可能是用同一个名字定义了两个不同的函数。或者是写出的函数原型在类型上与该函数的定义不相符。有时没有原型而直接写函数调用也可能导致这种错误信息,因为编译程序在遇到函数调用而没有看到函数原型或函数定义时,将给函数假定一个默认原型。如果后来见到的函数定义与假定不符,就会报告函数重复定义错误。
4)变量类型与有关运算对运算对象或者函数对参数的要求不符。例如有些运算(如 %)要求整数参数,而你用的是某种浮点数。
5)有些类型之间不能互相转换。例如你定义了一个结构变量,而后要用它给整数赋值。系统容许的转换包括:数值类型之间的转换,整数和指针之间的转换,指针之间的转换。其余转换(无论是隐含的,还是写出强制)都不允许。参见《C语言程序设计》(K&R)197-199页。
如何看待编译警告
当编译程序发现程序中某个地方有疑问,可能有问题时就会给出一个警告信息。警告信息可能意味着程序中隐含的大错误,也可能确实没有问题。对于警告的正确处理方式应该是:尽可能地消除之。对于编译程序给出的每个警告都应该仔细分析,看看是否真的有问题。只有那些确实无问题的警告才能放下不管。
注意:经验表明,警告常常意味着严重的隐含错误。
常见警告:
1)(局部自动)变量没有初始化就使用。如果对局部指针变量出现这种情况,后果不堪设想。对于一般局部自动变量,没有初始化就使用它的值也不会是有意义的。
2)在条件语句或循环语句的条件中写了赋值。大部分情况是误将 == (等于判断)写成 = 了。这是很常见的程序错误,有些编译程序对这种情况提出警告。
C. C语言编译、连接的各种错误
编译器错误 C2001 错误消息
常数中有换行符
字符串常数不能继续到第二行,除非进行下列操作:
•用反斜杠结束第一行。
•用一个双引号结束第一行上的字符串,并在下一行用另一个双引号开始该字符串。
用 \n 结束第一行是不够的。
编译器错误 C2002 错误消息
无效的宽字符常数
多字节字符常数是非法的。
通过检查下面的可能原因进行修复
1.宽字符常数包含的字节比需要的多。
2.未包括标准头文件 STDDEF.h。
3.宽字符不能与一般字符串连接。
4.宽字符常数之前必须是字符“L”:
编译器错误 C2003 错误消息
应输入“defined id”
标识符必须跟在预处理器关键字之后。
编译器错误 C2004 错误消息
应为“defined(id)”
标识符必须出现在预处理器关键字之后的括号中。
也可能由于为 Visual Studio .NET 2003 进行的编译器一致性工作生成此错误:在预处理器指
令中缺少括号。
如果预处理器指令缺少右括号,则编译器将生成一个错误。
编译器错误 C2005 错误消息
#line 应跟一个行号,却找到“token”
#line 指令后面必须跟行号。
编译器错误 C2006 错误消息
“directive”应输入文件名,却找到“token”
诸如 #include 或 #import 等指令需要文件名。若要解决该错误,请确保 token 是一个有效
文件名。并且将该文件名放在双引号或尖括号中。
编译器错误 C2007 错误消息
#define 语法
#define 后未出现标识符。若要解决该错误,请使用标识符。
编译器错误 C2008 错误消息
“character”: 宏定义中的意外
该字符紧跟在宏名之后。若要解决该错误,宏名之后必须有一个空格。
编译器错误 C2009 错误消息
宏形式“identifier”重复使用
宏定义的形参表多次使用该标识符。宏的参数列表中的标识符必须是唯一的。
编译器错误 C2010 错误消息
“character”: 宏形参表中的意外
该字符在宏定义的形参表中使用不正确。移除该字符以解决该错误。
编译器错误 C2011 错误消息
“identifier”:“type”类型重定义
该标识符已定义为 type 类型。如果多次将某个类型库导入同一个文件,也可能生成 C2011
。
编译器错误 C2012 错误消息
在“<”之后缺少名称
#include 指令缺少所需的文件名。
编译器错误 C2013 错误消息
缺少“>”
#include 指令缺少右尖括号。添加右尖括号以解决该错误。
编译器错误 C2014 错误消息
预处理器命令必须作为第一个非空白空间启动
预处理器指令的 # 符号必须是非空白行上的第一个字符。
编译器错误 C2015 错误消息
常数中的字符太多
一个字符常数包含的字符多于两个。标准字符常数只能包含一个字符,长字符常数只能包含两
个字符。
转义序列(如 \t)将被转换为单个字符。
当使用 Microsoft 扩展将字符常数转换为整数时,也可能发生 C2015。
编译器错误 C2017 错误消息
非法的转义序列
转义序列(如 \t)出现在字符或字符串常数之外。
当 stringize 运算符与包括转义序列的字符串一起使用时会发生 C2017。
编译器错误 C2018 错误消息
未知字符“hexnumber”
源文件包含一个意外的 ASCII 字符,该字符由其十六进制数标识。若要解决该错误,请移除
该字符。
编译器错误 C2019 错误消息
应找到预处理器指令,却找到“character”
该字符跟在 # 符号的后面,但它不是预处理器指令的第一个字母。
编译器错误 C2020 错误消息
“member”:“class”成员重定义
从基类或结构继承的成员被重定义。不能重定义继承成员,除非它在基类中被声明为 virtual
。
编译器错误 C2021 错误消息
应输入指数值,而非“character”
用作浮点常数的指数的字符是一个无效数字。确保使用的指数在范围之内。
编译器错误 C2022 错误消息
“number”: 对字符来说太大
字符或字符串常数中跟在反斜杠 (\) 后面的八进制数字太大,不能表示字符。
编译器错误 C2026 错误消息
字符串太大,已截断尾部字符
该字符串的长度超过了 16380 个单字节字符的**。
连接相邻字符串之前,字符串的长度不能超过 16380 个单字节字符。
大约为此长度的一半的 Unicode 字符串也会生成此错误。
编译器错误 C2027 错误消息
使用了未定义类型“type”
类型只有经过定义才能使用。若要解决该错误,请确保在引用类型前已对其进行了完全定义。
有可能声明一个指向已声明但未定义的类型的指针。但是 Visual C++ 不允许引用未定义的类
型。
编译器错误 C2028 错误消息
结构/联合成员必须在结构/联合中
结构或联合成员必须在结构或联合内部声明。
编译器错误 C2030 错误消息
“identifier”: 结构/联合成员重定义
结构或联合将同一标识符用于多个成员。
编译器错误 C2032 错误消息
“identifier”: 函数不能是结构/联合“structorunion”的成员
该结构或联合中的一个成员函数在 C++ 中允许使用而在 C 中却不允许。若要解决该错误,请
编译为 C++ 程序或移除该成员函数。
编译器错误 C2033 错误消息
“identifier”: 位域不能有间接寻址
该位域被声明为指针,这是不允许的。
编译器错误 C2034 错误消息
“identifier”: 位域类型对于位数太小
该位域声明中位的数目超过了基类型的大小。
编译器错误 C2036 错误消息
“identifier”: 未知的大小
对 identifier 的操作需要数据对象的大小,而该大小无法确定。
编译器错误 C2039 错误消息
“identifier1”: 不是“identifier2”的成员
该代码错误调用或引用了结构、类或联合的成员。
编译器错误 C2040 错误消息
“operator”:“identifier1”与“identifier2”的间接寻址级别不同
涉及该运算符的表达式具有不一致的间接寻址级别。
如果两个操作数都是算术的或都是非算术的(如数组或指针),则不用更改就可使用它们。如
果一个操作数是算术的,而另一个不是,则算术运算符将转换为非算术类型。
编译器错误 C2041 错误消息
非法的数字“character”(用于基“number”)
指定的字符不是基(如八进制或十六进制)的有效数字。
编译器错误 C2042 错误消息
signed/unsigned 关键字互相排斥
在单个声明中使用关键字 signed 和 unsigned。
编译器错误 C2043 错误消息
非法 break
break 仅在 do、for、while 或 switch 语句中合法。
编译器错误 C2044 错误消息
非法 continue
continue 仅在 do、for 或 while 语句中合法。
编译器错误 C2045 错误消息
“identifier”: 标签重定义
该标签出现在同一函数中的多条语句之前。
编译器错误 C2046 错误消息
非法的 case
关键字 case 只能出现在 switch 语句中。
编译器错误 C2047 错误消息
非法的 default
关键字 default 仅能出现在 switch 语句中。
编译器错误 C2048 错误消息
默认值多于一个
switch 语句包含多个 default 标签。删除其中一个 default 标签可解决该错误。
编译器错误 C2050 错误消息
switch 表达式不是整型
switch 表达式计算结果为一个非整数值。若要解决该错误,请在 switch 语句中只使用整数
值。
编译器错误 C2051 错误消息
case 表达式不是常数
Case 表达式必须是整数常数。
编译器错误 C2052 错误消息
“type”: 非法的 case 表达式类型
Case 表达式必须是整数常数。
编译器错误 C2053 错误消息
“identifier”: 宽字符串不匹配
宽字符串被分配给了一个不兼容的类型。
编译器错误 C2054 错误消息
在“identifier”之后应输入“(”
该函数标识符用在需要尾部括号的上下文中。
导致该错误的可能原因是省略了复杂初始化上的等号 (=)。
编译器错误 C2055 错误消息
应输入形参表,而不是类型表
函数定义包含参数类型列表而不包含形参表。ANSI C 需要命名的形参,除非它们是 void 或
是省略号 (...)。
编译器错误 C2056 错误消息
非法表达式
表达式因前一个错误而无效。
编译器错误 C2057 错误消息
应输入常数表达式
上下文要求常数表达式,即其值在编译时已知的表达式。
编译器错误 C2058 错误消息
常数表达式不是整型
该上下文需要整数常数表达式。
编译器错误 C2059 错误消息
语法错误 :“token”
该标记导致语法错误。
若要确定原因,则不仅要检查在错误信息中列出的行,还要检查该行上面的行。下面的示例对
声明 j 的行生成了错误信息,而该错误的真正源却出现在其上面的行中。
如果对行的检查没有获得有关可能出现的问题的任何线索,则尝试注释掉在错误信息中列出的
行以及可能出现在该行上面的若干行。
如果该错误信息在紧跟 typedef 变量的符号上出现,则检查该变量是否已在源代码中定义。
如果符号没有计算出任何结果(在使用 /Dsymbol= 编译时可能发生),可能会导致 C2059。
可能收到 C2059 的另一个特定原因是编译在函数的默认参数中指定了结构的应用程序。参数的
默认值必须是一个表达式。初始值设定项列表(如用于初始化结构的初始值设定项列表)不是表达式。其解决方法是定义一
个执行所需初始化的构造函数。
编译器错误 C2060 错误消息
语法错误 : 遇到文件结束
至少还需要一个标记。
编译器错误 C2061 错误消息
语法错误: 标识符“identifier”
编译器发现了不应在此出现的标识符。请确保在使用 identifier 之前对其进行声明。
初始值设定项可能括在了括号中。为避免该问题,请将声明符括在括号中或使其成为 typedef
。
在编译器将表达式作为类模板参数检测时也可能导致此错误;使用 typename 告诉编译器它是
一个类型。
编译器错误 C2062 错误消息
意外的类型“type”
编译器不需要类型名称。
编译器处理构造函数的参数列表中未定义类型的方式也可能导致 C2062。如果编译器遇到未定
义的(拼错了吗?)类型,则它假定构造函数是一个表达式,并发出 C2062。若要解决此错误,请只使用构造函数参数列表
中的定义类型。
编译器错误 C2063 错误消息
“identifier”: 不是函数
该标识符用作函数,但未声明为函数。
编译器错误 C2064 错误消息
项不会计算为接受“number”个参数的函数
通过表达式调用了函数。该表达式未计算为函数指针。
编译器错误 C2065 错误消息
“identifier”: 未声明的标识符
在可使用变量的类型前必须在声明中指定它。在可以使用函数前必须在声明或原型中指定该函
数使用的参数。
可能的原因:
1.您正在用 C 运行库的调试版本进行编译,在 for 循环中声明标准 C++ 库迭代器变量,然后
尝试在 for 循环范围外使用该迭代器变量。 用 C 运行库的调试版本编译标准 C++ 库代码暗指使用 /Zc:forScope。有关更
多信息,请参见调试迭代器支持。
2.可能正在调用当前不受生成环境支持的 SDK 头文件中的函数。
3.省略必要的包含文件,尤其是在定义 VC_EXTRALEAN、WIN32_LEAN_AND_MEAN 或
WIN32_EXTRA_LEAN 时。这些符号从 windows.h 和 afxv_w32.h 中排除了一些头文件以加快编译。(在 windows.h 和
afxv_w32.h 中查找排除的头文件的最新说明。)
4.标识符名拼写错误。
5.标识符使用了错误的大小写字母。
6.字符串常数的后面缺少右引号。
7.命名空间范围不正确。例如,若要解析 ANSI C++ 标准库函数和运算符,则必须用 using 指
令指定 std 命名空间。下面的示例未能编译,因为 using 指令被注释掉,并且在 std 命名空间中定义了 cout:
编译器错误 C2066 错误消息
转换到函数类型是非法的
在 ANSI C 中,函数指针和数据指针间的转换是非法的。
编译器错误 C2067 错误消息
转换到数组类型是非法的
对象被转换成了数组类型。
编译器错误 C2069 错误消息
“void”项到非“void”项的强制转换
类型 void 不能转换成任何其他类型。
编译器错误 C2070 错误消息
“type”: 非法的 sizeof 操作数
sizeof 运算符需要一个表达式或类型名称。
编译器错误 C2071 错误消息
“identifier”: 非法的存储类
声明 identifier 所用的存储类无效。
编译器错误 C2072 错误消息
“identifier”: 函数的初始化
错误指定了函数初始值设定项。
编译器错误 C2073 错误消息
“identifier”: 部分初始化数组的元素必须有默认构造函数
为用户定义的类型或常数的数组指定的初始值设定项太少。如果没有为数组成员指定明确的初
始值设定项及其对应的构造函数,则必须提供默认的构造函数。
编译器错误 C2074 错误消息
“identifier”:“class-key”初始化需要大括号
在指定的类、结构或联合初始值设定项两边没有大括号。
编译器错误 C2075 错误消息
“identifier”: 数组初始化需要大括号
在指定的数组初始值设定项两边没有大括号。
编译器错误 C2077 错误消息
非标量字段初始值设定项“identifier”
试图用非标量(结构、联合、数组或类)初始化位域。使用整数值或浮点值。
编译器错误 C2078 错误消息
初始值设定项太多
初始值设定项的数目超过了要初始化的对象数。
编译器错误 C2079 错误消息
“identifier”使用未定义的类/结构/联合“name”
指定的标识符是一个未定义的类、结构或联合。
初始化匿名联合时,可能会导致此错误。
编译器错误 C2081 错误消息
“identifier”: 形参表中的名称非法
标识符导致语法错误。
此错误可能是由使用形参表的旧形式导致的。必须在形参表中指定形参的类型。
编译器错误 C2082 错误消息
形参“identifier”的重定义
在函数体中重新声明了函数的形参。若要解决该错误,请移除该重定义。
编译器错误 C2083 错误消息
结构/联合比较非法
结构或联合直接与另一个用户定义的类型进行比较。这是不允许的,除非已经定义了比较运算
符或者存在到标量类型的转换。
编译器错误 C2084 错误消息
函数“function”已有主体
函数已经定义。
在以前的 Visual C++ 版本中,
•编译器将接受解析为同一实际类型的多个模板的专用化,尽管附加的定义将永远不可用。现
在编译器将检测这些多重定义。
•__int32 和 int 已被视为单独的类型。编译器现在将 __int32 作为 int 的同义词处理。这
意味着,如果函数同时在 __int32 和 int 上重载,编译器将检测多个定义,并提供一个错误。
编译器错误 C2085 错误消息
“identifier”: 不在形参表中
该标识符在函数定义中声明而未在形参表中声明。(仅用于 ANSI C)
编译器错误 C2086 错误消息
“identifier”: 重定义
多次定义了该标识符,或者后面的声明与前一个不同。
C2086 也可能是增量编译引用的 C# 程序集的结果。重新生成该 C# 程序集以解决此错误。
编译器错误 C2087 错误消息
“identifier”: 缺少下标
具有多个下标的数组的定义缺少大于 1 的维度的下标值。
编译器错误 C2088 错误消息
“operator”: 对于“class-key”非法
没有为结构或联合定义该运算符。该错误只对 C 代码有效。
编译器错误 C2089 错误消息
“identifier”:“class-key”太大
指定的结构或联合超过 4GB 的**。
编译器错误 C2090 错误消息
函数返回数组
函数不能返回数组。请返回指向数组的指针。
编译器错误 C2091 错误消息
函数返回函数
函数不能返回函数。请返回指向函数的指针。
编译器错误 C2092 错误消息
“array name”数组元素类型不能是函数
不允许使用函数数组。请使用指向函数的指针的数组。
编译器错误 C2093 错误消息
“variable1”: 无法使用自动变量“variable2”的地址初始化
在用 /Za 编译时,程序试图将自动变量的地址用作初始值设定项。
编译器错误 C2094 错误消息
标签“identifier”未定义
goto 语句使用的标签在函数中不存在。
编译器错误 C2095 错误消息
“function”: 实参具有类型“void”:“number”参数
传递给函数的参数为 void 类型,这是不允许的。请改为使用指向 void 的指针 (void *)。
number 指示哪一个参数为 void。
编译器错误 C2097 错误消息
非法的初始化
通过检查下面的可能原因进行修复
1.使用非常数值初始化变量。
2.用长地址初始化短地址。
3.在用 /Za 编译时,用非常数表达式初始化局部结构、联合或数组。
4.用包含逗号运算符的表达式初始化。
5.用既非常数又非符号的表达式初始化。
编译器错误 C2099 错误消息
初始值设定项不是常数
此错误只由 C 编译器发出,而且只对非自动变量发生。编译器在程序的开头对非自动变量进
行初始化,并且用于对这些变量进行初始化的值必须是常数。
由于编译时与运行时的浮点精度环境设置(有关更多信息,请参见 _controlfp_s)可能不同
,因此,编译器无法在 /fp:strict 下对表达式执行常数合并。在这种情况下,也可能发生 C2099。
当常数合并失败时,编译器调用动态初始化,这在 C 中是不允许的。
要解决此错误,请将模块编译为 .cpp 文件或对表达式进行简化。
D. C++编译链接错误
C++常见编译/链接错误及其解决办法
1. 解决error LNK2005: ___crtExitProcess 已经在 LIBCMTD.lib(crt0dat.obj) 中定义
有的时候, 在 Debug 模式下编译没问题, 换到 Release 模式就发生一堆问题.
典型的例子, 就是因为 c++ runtime library 设定不同, 所造成的重复定义连结错误.
而另一个常见的例子是 专案与 library 使用不同的字符集合设定
(如: 一个用 Unicode Character Set, 另一个用 Multi-Byte Character Set)
这个错误发生原因, 有可能是
1. 你 link 的 lib 使用 C++ Multi-threaded DLL (/MD)
2. 而你的 source 使用的 C++ runtime library 是 Multi-threaded (/MT)
导致重复定义
解决方法:
两个使用相同的 C++ runtime library.例如都使用 static 的 Multi-threaded (/MT).
2. 错误 1error LNK2005: "private: __thiscall type_info::type_info(class type_info const &)" (??0type_info@@AAE@ABV0@@Z) 已经在 LIBCMT.lib(typinfo.obj) 中定义 MSVCRTD.lib
项目 -> 属性 -> c/C++ -> 代码生成 -> 运行时库 设置为: 多线程调试 DLL (/MDd)
被引用的库和调用的程序编译选项不同,需要改成一致后编译
3.#pragma once与 #ifndef的区别
为了避免同一个文件被include多次
1 #ifndef方式
2 #pragma once方式
在能够支持这两种方式的编译器上,二者并没有太大的区别,但是两者仍然还是有一些细微的区别。
方式一:
#ifndef __SOMEFILE_H__
#define __SOMEFILE_H__
... ... // 一些声明语句
#endif
方式二:
#pragma once
... ... // 一些声明语句
#ifndef的方式依赖于宏名字不能冲突,这不光可以保证同一个文件不会被包含多次,也能保证内容完全相同的两个文件不会被不小心同时包含。当然,缺点就是如果不同头文件的宏名不小心“撞车”,可能就会导致头文件明明存在,编译器却硬说找不到声明的状况
#pragma once则由编译器提供保证:同一个文件不会被包含多次。注意这里所说的“同一个文件”是指物理上的一个文件,而不是指内容相同的两个文件。带来的好处是,你不必再费劲想个宏名了,当然也就不会出现宏名碰撞引发的奇怪问题。对应的缺点就是如果某个头文件有多份拷贝,本方法不能保证他们不被重复包含。当然,相比宏名碰撞引发的“找不到声明”的问题,重复包含更容易被发现并修正。
方式一由语言支持所以移植性好,方式二 可以避免名字冲突
4.error LNK2019: 无法解析的外部符号 __imp__PathCombineW
PathCombine是Shell api 需要引入库#pragma comment( lib, "shlwapi.lib")
5.error C2662: "MyClass::GetName()”: 不能将“this”指针从“const MyClass”转换为“MyClass &”
bool MyClass::operator==(const MyClass* n1) const
{return GetName() == n1->GetName();}
原因是不能在const函数中调用对象的非const方法,MyClass中的GetName()必须是const的。
6.template 模板
模板声明和定义必须在同一个文件中,而且只有实例话模板类型时才编译模板实例
7.error C2275: “MyClass”: 将此类型用作表达式非法 MyClass.Instance();
原因:Instance是静态方法,用.引用会出错。应该是MyClass::Instance()
8.error LNK2019: 无法解析的外部符号 "public: __thiscall MyClass(void)
原因:只声明了构造函数,MyClass(); ,但未定义。 可以定义空函数,或者直接注释掉,使用默认构造函数。
9.error C2504: “testing”: 未定义基类
class PackToolTest : testing.Test {}
原因:Test是testing命名空间下的一个类,需要用域操作符,testing::Test
还有一个问题,缺少基类继承权限(public、protected、private)
10.error C2864: “MyClass::_nullpack”: 只有静态常量整型数据成员才可以在类中初始化
class MyClass {string _nullpack = "test";}
原因:c++ 中,成员变量不能在声明时初始化,而是在构造函数初始化列表中先初始化
11.error LNK2019: 无法解析的外部符号_WinMain@16int main()
原因:由于创建的是Win32 Project,和Win32 console Project的链接库不同
方法1:在程序最开始的地方加上以下语句
#pragma comment(linker, "/subsystem:console ")
方法2:project > > setting > > 在link 的project options 中将/subsystem:windows(console)删了
12.类似“已经在 msvcprtd.lib(MSVCP80D.dll) 中定义”问题
vs2005 Debug /Release需要分别配制
分析一下错误来源,会发现:
1. 错误来源主要是重复定义的问题,而且重复定义的基本上都是VC Runtime和Standard C++ Library中的函数
2. LIBCMT和LIBCPMT为Release下的Lib,本来不应该出现在Debug版本的链接的Lib中
3. 重复定义的问题主要出现在:LIBCMT, LIBCPMT, MSVCPRTD, MSVCRTD
来看看出问题的LIB是那些:
1. LIBCMT:C Runtime库的多线程静态链接的Release版本
2. LIBCPMT:C++ Standard Library的多线程静态链接的Release版本
3. MSVCPRTD:C++ Standard Library的多线程DLL的Debug版本
4. MSVCRTD:C Runtime Library的多线程DLL的Debug版本
当 前我们的配置是多线程DLL的Debug版,因此3和4是应该出现在link的列表中的,不属于多余。而后两者则是只是当多线程静态链接Release版 中才会出现。这提示我在项目中加入的ANTLR.LIB可能是造成这个问题的根源,因为静态库的编译选项很容易和主程序发生冲突,并且根据实际信息我们可 以看出ANTLR.LIB应该是用多线程静态链接的Release版本来编译的。
解决方法:
1、首先查看编译项目依赖的其他项目的运行时库是否一致
2、如果不一致,改为同样的运行时库,如在下编译的是:“多线程调试 DLL (/MDd)”,现在需要把所有的依赖项目的运行时库都改为一致的库,就OK了。
13.error C2143: 语法错误 : 缺少“;”(在“*”的前面)
原因:产生错误处,某类型未include,可能头文件名拼写错误、头文件名已更改
14.error C2572: “MyClass::Invoke”: 重定义默认参数 : 参数 2
string MyClass::Invoke(const CParam& paraObj, INVOKETYPE type = ASYN)
原因:默认参数,只需在声明时指定。方法定义的时候无需指定默认参数。
string MyClass::Invoke(const CParam& paraObj, INVOKETYPE type )
{ ... }
15.错误 C2558 没有可用的复制构造函数或复制构造函数声明为“explicit”
试图复制其复制构造函数为 private 的类。在大多数情况下,不应复制具有 private 复制构造函数的类。通用编程技术声明 private 复制构造函数以防止直接使用类。该类本身可能无用,或需要另一个类才能正常工作。
尝试复制其复制构造函数为 explicit 的类。用 explicit 声明复制构造函数会阻止将类的对象传递到函数或从函数返回类的对象。
原因: 拷贝构造函数、赋值函数参数必须用const修饰
16.不能创建抽象类对象
原因: 1. 存在虚函数未实现; 2. 由于疏忽重载虚函数格式错误(此问题需要仔细检查才能发现); 3. 虚函数名称与系统中已有的虚函数重名,导致重载失败(这点很纳闷)。
17.没有找到MSCRV80D.dll
工程属性: 配置类型 由 exe 改成 lib 后生成, 然后再改回来,运行时会出现 “没有找到MSCRV80D.dll” 的异常
解决方法:
工程属性:MFC的使用 由 “使用标准Windows库” 改成 “在静态库中使用MFC“ 生成 ,然后再改回来,生成、运行 OK
18.CVTRES : fatal error CVT1100: 重复的资源。type:MANIFEST, name:1, language:0x0409
另一个则提示为:
LINK : fatal error LNK1123: 转换到 COFF 期间失败: 文件无效或损坏
已经到了链接期,应该说,问题就不像编译通不过那么别扭了,而查阅MSDN关于这两个问题的说明,终于找到了解决的方法,现简单的陈述如下:
首先,出现这两个问题的原因都是一个,即文件中的现有资源文件和新资源字符串表 ID 冲突。微软也给出了解决这个问题的方法,但是,在现有的情况下,这个方法是靠不住的,因为,不可能不使用wx.rc资源。所以,一个变通的解决方法就是:
工程属性->配置属性-> 清单工具->输入和输出->嵌入清单,选择[否],即可。
E. 编译错误怎么解决
如果使用C的编译器,应该是能编译通过 因为C编译器如果没有写明函数的返回值的话默认的函数返回值是int 如果使用C++的编译器就编译不过了 因为C++比C更严格了,不允许默认的int返回值
F. 内核编译错误—“mkimage”
在内核编译时经常出现各种错误。下图是内核编译常见问题之一:
"mkimage" command not found -U-Boot images will not be built
make[1]: *** [arch/arm/boot/uImage] Error 1
make: *** [uImage] Error 2
根据上图提示信息,"mkimage" command not found -U-Boot images will not be built,先尝试在linux系统里面安装依赖包mkimage,
输入命令:sudo apt-get install uboot-mkimage
如下图:
运行命令后,提示uboot-mkimage包不可用,被其它包引用了,意味着uboot-mkimage包丢失、废弃或从其它源来获得。
根据提示,可以用另一个包u-boot-tools替代,下面安装u-boot-tools,
输入命令:sudo apt-get install u-boot-tools
如下图:
安装u-boot-tools包后,再继续编译内核,如下图,显示uImage is ready,说明内核编译成功。接着可以给板子上电,启动内核。
G. 关于C语言在编译时常出现的错误有哪些
1、fatal error C1010: unexpected end of file while looking for precompiled header directive。
寻找预编译头文件路径时遇到了不该遇到的文件尾。(一般是没有#include "stdafx.h")
2、fatal error C1083: Cannot open include file: 'R…….h': No such file or directory
不能打开包含文件“R…….h”:没有这样的文件或目录。
3、error C2011: 'C……': 'class' type redefinition
类“C……”重定义。
4、error C2018: unknown character '0xa3'
不认识的字符'0xa3'。(一般是汉字或中文标点符号)
5、error C2057: expected constant expression
希望是常量表达式。(一般出现在switch语句的case分支中)
6、error C2065: 'IDD_MYDIALOG' : undeclared identifier
“IDD_MYDIALOG”:未声明过的标识符。
7、error C2082: redefinition of formal parameter 'bReset'
函数参数“bReset”在函数体中重定义。
8、error C2143: syntax error: missing ':' before '{'
句法错误:“{”前缺少“;”。
9、error C2146: syntax error : missing ';' before identifier 'dc'
句法错误:在“dc”前丢了“;”。
10、error C2196: case value '69' already used
值69已经用过。(一般出现在switch语句的case分支中)
11、error C2509: 'OnTimer' : member function not declared in 'CHelloView'
成员函数“OnTimer”没有在“CHelloView”中声明。
12、error C2511: 'reset': overloaded member function 'void (int)' not found in 'B'
重载的函数“void reset(int)”在类“B”中找不到。
13、error C2555: 'B::f1': overriding virtual function differs from 'A::f1' only by return type or calling convention
类B对类A中同名函数f1的重载仅根据返回值或调用约定上的区别。
14、error C2660: 'SetTimer' : function does not take 2 parameters
“SetTimer”函数不传递2个参数。
15、warning C4035: 'f……': no return value
“f……”的return语句没有返回值。
16、warning C4553: '= =' : operator has no effect; did you intend '='?
没有效果的运算符“= =”;是否改为“=”?
17、warning C4700: local variable 'bReset' used without having been initialized
局部变量“bReset”没有初始化就使用。
18、error C4716: 'CMyApp::InitInstance' : must return a value
“CMyApp::InitInstance”函数必须返回一个值。
19、LINK : fatal error LNK1168: cannot open Debug/P1.exe for writing
连接错误:不能打开P1.exe文件,以改写内容。(一般是P1.Exe还在运行,未关闭)
20、error LNK2001: unresolved external symbol "public: virtual _ _thiscall C……::~C……(void)"
连接时发现没有实现的外部符号(变量、函数等)。
function call missing argument list 调用函数的时候没有给参数。
member function definition looks like a ctor, but name does not match enclosing class 成员函数声明了但没有使用
unexpected end of file while looking for precompiled header directive 在寻找预编译头文件时文件意外结束,编译不正常终止可能造成这种情况